Merge branch 'upstream/master' into main

Change-Id: Id6f67665a9ee7f90cf5114727c525727a6c4cb19
diff --git a/.cz.json b/.cz.json
new file mode 100644
index 0000000..cb500ba
--- /dev/null
+++ b/.cz.json
@@ -0,0 +1,5 @@
+{
+    "path": "./node_modules/cz-conventional-changelog",
+    "maxHeaderWidth": 50,
+    "maxLineWidth": 72
+}
\ No newline at end of file
diff --git a/.editorconfig b/.editorconfig
index f523ca1..12f786d 100644
--- a/.editorconfig
+++ b/.editorconfig
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2017-2019, Arm Limited and Contributors. All rights reserved.
+# Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -38,10 +38,10 @@
 insert_final_newline = true
 
 # [LCS] Chapter 2: Breaking long lines and strings
-#       "The limit on the length of lines is 80 columns"
+#       "The limit on the length of lines is 100 columns"
 #   This is a "soft" requirement for Arm-TF, and should not be the sole
 #   reason for changes.
-max_line_length = 80
+max_line_length = 100
 
 # [LCS] Chapter 1: Indentation
 #       "Tabs are 8 characters"
diff --git a/.gitignore b/.gitignore
index 64b389b..f524658 100644
--- a/.gitignore
+++ b/.gitignore
@@ -15,6 +15,10 @@
 tools/renesas/rcar_layout_create/*.srec
 tools/renesas/rcar_layout_create/*.map
 tools/renesas/rcar_layout_create/*.elf
+tools/renesas/rzg_layout_create/*.bin
+tools/renesas/rzg_layout_create/*.srec
+tools/renesas/rzg_layout_create/*.map
+tools/renesas/rzg_layout_create/*.elf
 tools/fiptool/fiptool
 tools/fiptool/fiptool.exe
 tools/cert_create/src/*.o
@@ -38,3 +42,5 @@
 # Ctags
 tags
 
+# Node.js
+node_modules/
diff --git a/.husky/.gitignore b/.husky/.gitignore
new file mode 100644
index 0000000..31354ec
--- /dev/null
+++ b/.husky/.gitignore
@@ -0,0 +1 @@
+_
diff --git a/.husky/commit-msg b/.husky/commit-msg
new file mode 100755
index 0000000..c1c9600
--- /dev/null
+++ b/.husky/commit-msg
@@ -0,0 +1,7 @@
+#!/bin/sh
+
+# shellcheck source=./_/husky.sh
+. "$(dirname "$0")/_/husky.sh"
+
+"$(dirname "$0")/commit-msg.gerrit" "$@"
+"$(dirname "$0")/commit-msg.commitlint" "$@"
diff --git a/.husky/commit-msg.commitlint b/.husky/commit-msg.commitlint
new file mode 100755
index 0000000..ca25ce1
--- /dev/null
+++ b/.husky/commit-msg.commitlint
@@ -0,0 +1,3 @@
+#!/bin/sh
+
+npx --no-install commitlint --edit "$1"
diff --git a/.husky/commit-msg.gerrit b/.husky/commit-msg.gerrit
new file mode 100755
index 0000000..b8ce477
--- /dev/null
+++ b/.husky/commit-msg.gerrit
@@ -0,0 +1,194 @@
+#!/bin/sh
+# From Gerrit Code Review 2.14.20
+#
+# Part of Gerrit Code Review (https://www.gerritcodereview.com/)
+#
+# Copyright (C) 2009 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+
+unset GREP_OPTIONS
+
+CHANGE_ID_AFTER="Bug|Depends-On|Issue|Test|Feature|Fixes|Fixed"
+MSG="$1"
+
+# Check for, and add if missing, a unique Change-Id
+#
+add_ChangeId() {
+	clean_message=`sed -e '
+		/^diff --git .*/{
+			s///
+			q
+		}
+		/^Signed-off-by:/d
+		/^#/d
+	' "$MSG" | git stripspace`
+	if test -z "$clean_message"
+	then
+		return
+	fi
+
+	# Do not add Change-Id to temp commits
+	if echo "$clean_message" | head -1 | grep -q '^\(fixup\|squash\)!'
+	then
+		return
+	fi
+
+	if test "false" = "`git config --bool --get gerrit.createChangeId`"
+	then
+		return
+	fi
+
+	# Does Change-Id: already exist? if so, exit (no change).
+	if grep -i '^Change-Id:' "$MSG" >/dev/null
+	then
+		return
+	fi
+
+	id=`_gen_ChangeId`
+	T="$MSG.tmp.$$"
+	AWK=awk
+	if [ -x /usr/xpg4/bin/awk ]; then
+		# Solaris AWK is just too broken
+		AWK=/usr/xpg4/bin/awk
+	fi
+
+	# Get core.commentChar from git config or use default symbol
+	commentChar=`git config --get core.commentChar`
+	commentChar=${commentChar:-#}
+
+	# How this works:
+	# - parse the commit message as (textLine+ blankLine*)*
+	# - assume textLine+ to be a footer until proven otherwise
+	# - exception: the first block is not footer (as it is the title)
+	# - read textLine+ into a variable
+	# - then count blankLines
+	# - once the next textLine appears, print textLine+ blankLine* as these
+	#   aren't footer
+	# - in END, the last textLine+ block is available for footer parsing
+	$AWK '
+	BEGIN {
+		if (match(ENVIRON["OS"], "Windows")) {
+			RS="\r?\n" # Required on recent Cygwin
+		}
+		# while we start with the assumption that textLine+
+		# is a footer, the first block is not.
+		isFooter = 0
+		footerComment = 0
+		blankLines = 0
+	}
+
+	# Skip lines starting with commentChar without any spaces before it.
+	/^'"$commentChar"'/ { next }
+
+	# Skip the line starting with the diff command and everything after it,
+	# up to the end of the file, assuming it is only patch data.
+	# If more than one line before the diff was empty, strip all but one.
+	/^diff --git / {
+		blankLines = 0
+		while (getline) { }
+		next
+	}
+
+	# Count blank lines outside footer comments
+	/^$/ && (footerComment == 0) {
+		blankLines++
+		next
+	}
+
+	# Catch footer comment
+	/^\[[a-zA-Z0-9-]+:/ && (isFooter == 1) {
+		footerComment = 1
+	}
+
+	/]$/ && (footerComment == 1) {
+		footerComment = 2
+	}
+
+	# We have a non-blank line after blank lines. Handle this.
+	(blankLines > 0) {
+		print lines
+		for (i = 0; i < blankLines; i++) {
+			print ""
+		}
+
+		lines = ""
+		blankLines = 0
+		isFooter = 1
+		footerComment = 0
+	}
+
+	# Detect that the current block is not the footer
+	(footerComment == 0) && (!/^\[?[a-zA-Z0-9-]+:/ || /^[a-zA-Z0-9-]+:\/\//) {
+		isFooter = 0
+	}
+
+	{
+		# We need this information about the current last comment line
+		if (footerComment == 2) {
+			footerComment = 0
+		}
+		if (lines != "") {
+			lines = lines "\n";
+		}
+		lines = lines $0
+	}
+
+	# Footer handling:
+	# If the last block is considered a footer, splice in the Change-Id at the
+	# right place.
+	# Look for the right place to inject Change-Id by considering
+	# CHANGE_ID_AFTER. Keys listed in it (case insensitive) come first,
+	# then Change-Id, then everything else (eg. Signed-off-by:).
+	#
+	# Otherwise just print the last block, a new line and the Change-Id as a
+	# block of its own.
+	END {
+		unprinted = 1
+		if (isFooter == 0) {
+			print lines "\n"
+			lines = ""
+		}
+		changeIdAfter = "^(" tolower("'"$CHANGE_ID_AFTER"'") "):"
+		numlines = split(lines, footer, "\n")
+		for (line = 1; line <= numlines; line++) {
+			if (unprinted && match(tolower(footer[line]), changeIdAfter) != 1) {
+				unprinted = 0
+				print "Change-Id: I'"$id"'"
+			}
+			print footer[line]
+		}
+		if (unprinted) {
+			print "Change-Id: I'"$id"'"
+		}
+	}' "$MSG" > "$T" && mv "$T" "$MSG" || rm -f "$T"
+}
+_gen_ChangeIdInput() {
+	echo "tree `git write-tree`"
+	if parent=`git rev-parse "HEAD^0" 2>/dev/null`
+	then
+		echo "parent $parent"
+	fi
+	echo "author `git var GIT_AUTHOR_IDENT`"
+	echo "committer `git var GIT_COMMITTER_IDENT`"
+	echo
+	printf '%s' "$clean_message"
+}
+_gen_ChangeId() {
+	_gen_ChangeIdInput |
+	git hash-object -t commit --stdin
+}
+
+
+add_ChangeId
diff --git a/.husky/prepare-commit-msg b/.husky/prepare-commit-msg
new file mode 100755
index 0000000..593dfa8
--- /dev/null
+++ b/.husky/prepare-commit-msg
@@ -0,0 +1,6 @@
+#!/bin/sh
+
+# shellcheck source=./_/husky.sh
+. "$(dirname "$0")/_/husky.sh"
+
+"$(dirname "$0")/prepare-commit-msg.cz" "$@"
diff --git a/.husky/prepare-commit-msg.cz b/.husky/prepare-commit-msg.cz
new file mode 100755
index 0000000..724527d
--- /dev/null
+++ b/.husky/prepare-commit-msg.cz
@@ -0,0 +1,28 @@
+#!/bin/bash
+
+file="$1"
+type="$2"
+
+if [ -z "$type" ]; then # only run on new commits
+    #
+    # Save any commit message trailers generated by Git.
+    #
+
+    trailers=$(git interpret-trailers --parse "$file")
+
+    #
+    # Execute the Commitizen hook.
+    #
+
+    (exec < "/dev/tty" && npx --no-install git-cz --hook) || true
+
+    #
+    # Restore any trailers that Commitizen might have overwritten.
+    #
+
+    printf "\n" >> "$file"
+
+    while IFS= read -r trailer; do
+        git interpret-trailers --in-place --trailer "$trailer" "$file"
+    done <<< "$trailers"
+fi
diff --git a/Makefile b/Makefile
index 5c9186e..4905291 100644
--- a/Makefile
+++ b/Makefile
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -8,7 +8,7 @@
 # Trusted Firmware Version
 #
 VERSION_MAJOR			:= 2
-VERSION_MINOR			:= 4
+VERSION_MINOR			:= 5
 
 # Default goal is build all images
 .DEFAULT_GOAL			:= all
@@ -129,12 +129,27 @@
         $(error Unknown BRANCH_PROTECTION value ${BRANCH_PROTECTION})
 endif
 
+# FEAT_RME
+ifeq (${ENABLE_RME},1)
+# RME doesn't support PIE
+ifneq (${ENABLE_PIE},0)
+        $(error ENABLE_RME does not support PIE)
+endif
+# RME requires AARCH64
+ifneq (${ARCH},aarch64)
+        $(error ENABLE_RME requires AArch64)
+endif
+# RME requires el2 context to be saved for now.
+CTX_INCLUDE_EL2_REGS := 1
+CTX_INCLUDE_AARCH32_REGS := 0
+ARM_ARCH_MAJOR := 8
+ARM_ARCH_MINOR := 6
+endif
+
 # USE_SPINLOCK_CAS requires AArch64 build
 ifeq (${USE_SPINLOCK_CAS},1)
 ifneq (${ARCH},aarch64)
         $(error USE_SPINLOCK_CAS requires AArch64)
-else
-        $(info USE_SPINLOCK_CAS is an experimental feature)
 endif
 endif
 
@@ -185,13 +200,14 @@
 else
 target32-directive	= 	-target armv8a-none-eabi
 
-# Set the compiler's target architecture profile based on ARM_ARCH_MINOR option
+# Set the compiler's target architecture profile based on
+# ARM_ARCH_MAJOR ARM_ARCH_MINOR options
 ifeq (${ARM_ARCH_MINOR},0)
-march32-directive	= 	-march=armv8-a
-march64-directive	= 	-march=armv8-a
+march32-directive	= 	-march=armv${ARM_ARCH_MAJOR}-a
+march64-directive	= 	-march=armv${ARM_ARCH_MAJOR}-a
 else
-march32-directive	= 	-march=armv8.${ARM_ARCH_MINOR}-a
-march64-directive	= 	-march=armv8.${ARM_ARCH_MINOR}-a
+march32-directive	= 	-march=armv${ARM_ARCH_MAJOR}.${ARM_ARCH_MINOR}-a
+march64-directive	= 	-march=armv${ARM_ARCH_MAJOR}.${ARM_ARCH_MINOR}-a
 endif
 endif
 
@@ -203,22 +219,52 @@
 endif
 endif
 
-# Enabled required option for memory stack tagging. Currently, these options are
-# enabled only for clang and armclang compiler.
+# Get architecture feature modifiers
+arch-features		=	${ARM_ARCH_FEATURE}
+
+# Enable required options for memory stack tagging.
+# Currently, these options are enabled only for clang and armclang compiler.
 ifeq (${SUPPORT_STACK_MEMTAG},yes)
 ifdef mem_tag_arch_support
+# Check for armclang and clang compilers
 ifneq ( ,$(filter $(notdir $(CC)),armclang clang))
-march64-directive       =       -march=armv${ARM_ARCH_MAJOR}.${ARM_ARCH_MINOR}-a+memtag
+# Add "memtag" architecture feature modifier if not specified
+ifeq ( ,$(findstring memtag,$(arch-features)))
+arch-features       	:=       $(arch-features)+memtag
+endif	# memtag
 ifeq ($(notdir $(CC)),armclang)
 TF_CFLAGS		+=	-mmemtag-stack
 else ifeq ($(notdir $(CC)),clang)
 TF_CFLAGS		+=	-fsanitize=memtag
-endif
-endif
+endif	# armclang
+endif	# armclang clang
 else
 $(error "Error: stack memory tagging is not supported for architecture \
 	${ARCH},armv${ARM_ARCH_MAJOR}.${ARM_ARCH_MINOR}-a")
+endif	# mem_tag_arch_support
+endif	# SUPPORT_STACK_MEMTAG
+
+# Set the compiler's architecture feature modifiers
+ifneq ($(arch-features), none)
+# Strip "none+" from arch-features
+arch-features		:=	$(subst none+,,$(arch-features))
+ifeq ($(ARCH), aarch32)
+march32-directive	:=	$(march32-directive)+$(arch-features)
+else
+march64-directive	:=	$(march64-directive)+$(arch-features)
 endif
+# Print features
+$(info Arm Architecture Features specified: $(subst +, ,$(arch-features)))
+endif	# arch-features
+
+# Determine if FEAT_RNG is supported
+ENABLE_FEAT_RNG		=	$(if $(findstring rng,${arch-features}),1,0)
+
+# Determine if FEAT_SB is supported
+ENABLE_FEAT_SB		=	$(if $(findstring sb,${arch-features}),1,0)
+
+ifeq "8.5" "$(word 1, $(sort 8.5 $(ARM_ARCH_MAJOR).$(ARM_ARCH_MINOR)))"
+ENABLE_FEAT_SB		= 	1
 endif
 
 ifneq ($(findstring armclang,$(notdir $(CC))),)
@@ -303,7 +349,7 @@
 
 # General warnings
 WARNINGS		:=	-Wall -Wmissing-include-dirs -Wunused	\
-				-Wdisabled-optimization	-Wvla -Wshadow	\
+				-Wdisabled-optimization -Wvla -Wshadow	\
 				-Wno-unused-parameter -Wredundant-decls
 
 # Additional warnings
@@ -477,7 +523,6 @@
     endif
 
     ifeq (${SPD},spmd)
-        $(warning "SPMD is an experimental feature")
         # SPMD is located in std_svc directory
         SPD_DIR := std_svc
 
@@ -490,6 +535,18 @@
         ifeq ($(findstring optee_sp,$(ARM_SPMC_MANIFEST_DTS)),optee_sp)
             DTC_CPPFLAGS	+=	-DOPTEE_SP_FW_CONFIG
         endif
+
+        ifeq ($(TS_SP_FW_CONFIG),1)
+            DTC_CPPFLAGS	+=	-DTS_SP_FW_CONFIG
+        endif
+
+        ifneq ($(ARM_BL2_SP_LIST_DTS),)
+            DTC_CPPFLAGS += -DARM_BL2_SP_LIST_DTS=$(ARM_BL2_SP_LIST_DTS)
+        endif
+
+        ifneq ($(SP_LAYOUT_FILE),)
+            BL2_ENABLE_SP_LOAD := 1
+        endif
     else
         # All other SPDs in spd directory
         SPD_DIR := spd
@@ -516,6 +573,18 @@
 endif
 
 ################################################################################
+# Include rmmd Makefile if RME is enabled
+################################################################################
+
+ifneq (${ENABLE_RME},0)
+ifneq (${ARCH},aarch64)
+	$(error ENABLE_RME requires AArch64)
+endif
+include services/std_svc/rmmd/rmmd.mk
+$(warning "RME is an experimental feature")
+endif
+
+################################################################################
 # Include the platform specific Makefile after the SPD Makefile (the platform
 # makefile may use all previous definitions in this file)
 ################################################################################
@@ -548,11 +617,9 @@
 endif
 	BL31_CFLAGS	+=	-fpie
 	BL31_LDFLAGS	+=	$(PIE_LDFLAGS)
-ifeq ($(ARCH),aarch64)
 	BL32_CFLAGS	+=	-fpie
 	BL32_LDFLAGS	+=	$(PIE_LDFLAGS)
 endif
-endif
 
 ifeq (${ARCH},aarch64)
 BL1_CPPFLAGS += -DIMAGE_AT_EL3
@@ -661,12 +728,7 @@
 
 # SDEI_IN_FCONF is only supported when SDEI_SUPPORT is enabled.
 ifeq ($(SDEI_SUPPORT)-$(SDEI_IN_FCONF),0-1)
-$(error "SDEI_IN_FCONF is an experimental feature and is only supported when \
-	SDEI_SUPPORT is enabled")
-endif
-
-ifeq ($(COT_DESC_IN_DTB),1)
-    $(info CoT in device tree is an experimental feature)
+$(error "SDEI_IN_FCONF is only supported when SDEI_SUPPORT is enabled")
 endif
 
 # If pointer authentication is used in the firmware, make sure that all the
@@ -681,35 +743,28 @@
 ifeq ($(CTX_INCLUDE_PAUTH_REGS),1)
     ifneq (${ARCH},aarch64)
         $(error CTX_INCLUDE_PAUTH_REGS requires AArch64)
-    else
-        $(info CTX_INCLUDE_PAUTH_REGS is an experimental feature)
     endif
 endif
 
-ifeq ($(ENABLE_PAUTH),1)
-    $(info Pointer Authentication is an experimental feature)
-endif
-
-ifeq ($(ENABLE_BTI),1)
-    $(info Branch Protection is an experimental feature)
-endif
-
 ifeq ($(CTX_INCLUDE_MTE_REGS),1)
     ifneq (${ARCH},aarch64)
         $(error CTX_INCLUDE_MTE_REGS requires AArch64)
-    else
-        $(info CTX_INCLUDE_MTE_REGS is an experimental feature)
     endif
 endif
 
+# Trusted Boot is a prerequisite for Measured Boot. It provides trust that the
+# code taking the measurements and recording them has not been tampered
+# with. This is referred to as the Root of Trust for Measurement.
 ifeq ($(MEASURED_BOOT),1)
     ifneq (${TRUSTED_BOARD_BOOT},1)
         $(error MEASURED_BOOT requires TRUSTED_BOARD_BOOT=1)
-    else
-        $(info MEASURED_BOOT is an experimental feature)
     endif
 endif
 
+ifeq ($(PSA_FWU_SUPPORT),1)
+    $(info PSA_FWU_SUPPORT is an experimental feature)
+endif
+
 ifeq (${ARM_XLAT_TABLES_LIB_V1}, 1)
     ifeq (${ALLOW_RO_XLAT_TABLES}, 1)
         $(error "ALLOW_RO_XLAT_TABLES requires translation tables library v2")
@@ -719,8 +774,52 @@
 ifneq (${DECRYPTION_SUPPORT},none)
     ifeq (${TRUSTED_BOARD_BOOT}, 0)
         $(error TRUSTED_BOARD_BOOT must be enabled for DECRYPTION_SUPPORT to be set)
-    else
-        $(info DECRYPTION_SUPPORT is an experimental feature)
+    endif
+endif
+
+# SME/SVE only supported on AArch64
+ifeq (${ARCH},aarch32)
+    ifeq (${ENABLE_SME_FOR_NS},1)
+        $(error "ENABLE_SME_FOR_NS cannot be used with ARCH=aarch32")
+    endif
+    ifeq (${ENABLE_SVE_FOR_NS},1)
+        # Warning instead of error due to CI dependency on this
+        $(warning "ENABLE_SVE_FOR_NS cannot be used with ARCH=aarch32")
+        $(warning "Forced ENABLE_SVE_FOR_NS=0")
+        override ENABLE_SVE_FOR_NS	:= 0
+    endif
+endif
+
+# Ensure ENABLE_RME is not used with SME
+ifeq (${ENABLE_RME},1)
+    ifeq (${ENABLE_SME_FOR_NS},1)
+        $(error "ENABLE_SME_FOR_NS cannot be used with ENABLE_RME")
+    endif
+endif
+
+# Secure SME/SVE requires the non-secure component as well
+ifeq (${ENABLE_SME_FOR_SWD},1)
+    ifeq (${ENABLE_SME_FOR_NS},0)
+        $(error "ENABLE_SME_FOR_SWD requires ENABLE_SME_FOR_NS")
+    endif
+endif
+ifeq (${ENABLE_SVE_FOR_SWD},1)
+    ifeq (${ENABLE_SVE_FOR_NS},0)
+        $(error "ENABLE_SVE_FOR_SWD requires ENABLE_SVE_FOR_NS")
+    endif
+endif
+
+# SVE and SME cannot be used with CTX_INCLUDE_FPREGS since secure manager does
+# its own context management including FPU registers.
+ifeq (${CTX_INCLUDE_FPREGS},1)
+    ifeq (${ENABLE_SME_FOR_NS},1)
+        $(error "ENABLE_SME_FOR_NS cannot be used with CTX_INCLUDE_FPREGS")
+    endif
+    ifeq (${ENABLE_SVE_FOR_NS},1)
+        # Warning instead of error due to CI dependency on this
+        $(warning "ENABLE_SVE_FOR_NS cannot be used with CTX_INCLUDE_FPREGS")
+        $(warning "Forced ENABLE_SVE_FOR_NS=0")
+        override ENABLE_SVE_FOR_NS	:= 0
     endif
 endif
 
@@ -728,10 +827,16 @@
 # Process platform overrideable behaviour
 ################################################################################
 
-# Using BL2 implies that a BL33 image also needs to be supplied for the FIP and
-# Certificate generation tools. This flag can be overridden by the platform.
+ifdef BL1_SOURCES
+NEED_BL1 := yes
+endif
+
 ifdef BL2_SOURCES
-        ifdef EL3_PAYLOAD_BASE
+	NEED_BL2 := yes
+
+	# Using BL2 implies that a BL33 image also needs to be supplied for the FIP and
+	# Certificate generation tools. This flag can be overridden by the platform.
+	ifdef EL3_PAYLOAD_BASE
                 # If booting an EL3 payload there is no need for a BL33 image
                 # in the FIP file.
                 NEED_BL33		:=	no
@@ -746,6 +851,10 @@
         endif
 endif
 
+ifdef BL2U_SOURCES
+NEED_BL2U := yes
+endif
+
 # If SCP_BL2 is given, we always want FIP to include it.
 ifdef SCP_BL2
         NEED_SCP_BL2		:=	yes
@@ -783,6 +892,10 @@
 FIP_ARGS += --align ${FIP_ALIGN}
 endif
 
+ifdef FDT_SOURCES
+NEED_FDT := yes
+endif
+
 ################################################################################
 # Include libraries' Makefile that are used in all BL
 ################################################################################
@@ -826,30 +939,22 @@
 ################################################################################
 # Include BL specific makefiles
 ################################################################################
-ifdef BL1_SOURCES
-NEED_BL1 := yes
+
+ifeq (${NEED_BL1},yes)
 include bl1/bl1.mk
 endif
 
-ifdef BL2_SOURCES
-NEED_BL2 := yes
+ifeq (${NEED_BL2},yes)
 include bl2/bl2.mk
 endif
 
-ifdef BL2U_SOURCES
-NEED_BL2U := yes
+ifeq (${NEED_BL2U},yes)
 include bl2u/bl2u.mk
 endif
 
 ifeq (${NEED_BL31},yes)
-ifdef BL31_SOURCES
 include bl31/bl31.mk
 endif
-endif
-
-ifdef FDT_SOURCES
-NEED_FDT := yes
-endif
 
 ################################################################################
 # Build options checks
@@ -858,6 +963,7 @@
 $(eval $(call assert_booleans,\
     $(sort \
         ALLOW_RO_XLAT_TABLES \
+        BL2_ENABLE_SP_LOAD \
         COLD_BOOT_SINGLE_CPU \
         CREATE_KEYS \
         CTX_INCLUDE_AARCH32_REGS \
@@ -867,17 +973,25 @@
         CTX_INCLUDE_EL2_REGS \
         CTX_INCLUDE_NEVE_REGS \
         DEBUG \
+        DISABLE_MTPMU \
         DYN_DISABLE_AUTH \
         EL3_EXCEPTION_HANDLING \
         ENABLE_AMU \
+        ENABLE_AMU_AUXILIARY_COUNTERS \
+        ENABLE_AMU_FCONF \
+        AMU_RESTRICT_COUNTERS \
         ENABLE_ASSERTIONS \
         ENABLE_MPAM_FOR_LOWER_ELS \
         ENABLE_PIE \
         ENABLE_PMF \
         ENABLE_PSCI_STAT \
+        ENABLE_RME \
         ENABLE_RUNTIME_INSTRUMENTATION \
+        ENABLE_SME_FOR_NS \
+        ENABLE_SME_FOR_SWD \
         ENABLE_SPE_FOR_LOWER_ELS \
         ENABLE_SVE_FOR_NS \
+        ENABLE_SVE_FOR_SWD \
         ERROR_DEPRECATED \
         FAULT_INJECTION_SUPPORT \
         GENERATE_COT \
@@ -918,6 +1032,15 @@
         RAS_TRAP_LOWER_EL_ERR_ACCESS \
         COT_DESC_IN_DTB \
         USE_SP804_TIMER \
+        ENABLE_FEAT_RNG \
+        ENABLE_FEAT_SB \
+        PSA_FWU_SUPPORT \
+        ENABLE_TRBE_FOR_NS \
+        ENABLE_SYS_REG_TRACE_FOR_NS \
+        ENABLE_TRF_FOR_NS \
+        ENABLE_FEAT_HCX \
+        ENABLE_MPMM \
+        ENABLE_MPMM_FCONF \
 )))
 
 $(eval $(call assert_numerics,\
@@ -926,6 +1049,8 @@
         ARM_ARCH_MINOR \
         BRANCH_PROTECTION \
         FW_ENC_STATUS \
+        NR_OF_FW_BANKS \
+        NR_OF_IMAGES_IN_FW_BANK \
 )))
 
 ifdef KEY_SIZE
@@ -947,6 +1072,7 @@
         ALLOW_RO_XLAT_TABLES \
         ARM_ARCH_MAJOR \
         ARM_ARCH_MINOR \
+        BL2_ENABLE_SP_LOAD \
         COLD_BOOT_SINGLE_CPU \
         CTX_INCLUDE_AARCH32_REGS \
         CTX_INCLUDE_FPREGS \
@@ -956,7 +1082,11 @@
         CTX_INCLUDE_EL2_REGS \
         CTX_INCLUDE_NEVE_REGS \
         DECRYPTION_SUPPORT_${DECRYPTION_SUPPORT} \
+        DISABLE_MTPMU \
         ENABLE_AMU \
+        ENABLE_AMU_AUXILIARY_COUNTERS \
+        ENABLE_AMU_FCONF \
+        AMU_RESTRICT_COUNTERS \
         ENABLE_ASSERTIONS \
         ENABLE_BTI \
         ENABLE_MPAM_FOR_LOWER_ELS \
@@ -964,9 +1094,13 @@
         ENABLE_PIE \
         ENABLE_PMF \
         ENABLE_PSCI_STAT \
+        ENABLE_RME \
         ENABLE_RUNTIME_INSTRUMENTATION \
+        ENABLE_SME_FOR_NS \
+        ENABLE_SME_FOR_SWD \
         ENABLE_SPE_FOR_LOWER_ELS \
         ENABLE_SVE_FOR_NS \
+        ENABLE_SVE_FOR_SWD \
         ENCRYPT_BL31 \
         ENCRYPT_BL32 \
         ERROR_DEPRECATED \
@@ -991,6 +1125,7 @@
         SPM_MM \
         SPMD_SPM_AT_SEL2 \
         TRUSTED_BOARD_BOOT \
+        TRNG_SUPPORT \
         USE_COHERENT_MEM \
         USE_DEBUGFS \
         ARM_IO_IN_DTB \
@@ -1007,6 +1142,17 @@
         RAS_TRAP_LOWER_EL_ERR_ACCESS \
         COT_DESC_IN_DTB \
         USE_SP804_TIMER \
+        ENABLE_FEAT_RNG \
+        ENABLE_FEAT_SB \
+        NR_OF_FW_BANKS \
+        NR_OF_IMAGES_IN_FW_BANK \
+        PSA_FWU_SUPPORT \
+        ENABLE_TRBE_FOR_NS \
+        ENABLE_SYS_REG_TRACE_FOR_NS \
+        ENABLE_TRF_FOR_NS \
+        ENABLE_FEAT_HCX \
+        ENABLE_MPMM \
+        ENABLE_MPMM_FCONF \
 )))
 
 ifeq (${SANITIZE_UB},trap)
@@ -1036,9 +1182,6 @@
 # Generate and include sp_gen.mk if SPD is spmd and SP_LAYOUT_FILE is defined
 ifeq (${SPD},spmd)
 ifdef SP_LAYOUT_FILE
-        ifeq (${SPMD_SPM_AT_SEL2},0)
-            $(error "SPMD with SPM at S-EL1 does not require SP_LAYOUT_FILE")
-        endif
         -include $(BUILD_PLAT)/sp_gen.mk
         FIP_DEPS += sp
         CRT_DEPS += sp
@@ -1076,7 +1219,9 @@
 
 # Expand build macros for the different images
 ifeq (${NEED_BL1},yes)
-$(eval $(call MAKE_BL,1))
+BL1_SOURCES := $(sort ${BL1_SOURCES})
+
+$(eval $(call MAKE_BL,bl1))
 endif
 
 ifeq (${NEED_BL2},yes)
@@ -1084,8 +1229,10 @@
 FIP_BL2_ARGS := tb-fw
 endif
 
+BL2_SOURCES := $(sort ${BL2_SOURCES})
+
 $(if ${BL2}, $(eval $(call TOOL_ADD_IMG,bl2,--${FIP_BL2_ARGS})),\
-	$(eval $(call MAKE_BL,2,${FIP_BL2_ARGS})))
+	$(eval $(call MAKE_BL,bl2,${FIP_BL2_ARGS})))
 endif
 
 ifeq (${NEED_SCP_BL2},yes)
@@ -1098,10 +1245,10 @@
 BL31_SOURCES := $(sort ${BL31_SOURCES})
 ifneq (${DECRYPTION_SUPPORT},none)
 $(if ${BL31}, $(eval $(call TOOL_ADD_IMG,bl31,--soc-fw,,$(ENCRYPT_BL31))),\
-	$(eval $(call MAKE_BL,31,soc-fw,,$(ENCRYPT_BL31))))
+	$(eval $(call MAKE_BL,bl31,soc-fw,,$(ENCRYPT_BL31))))
 else
 $(if ${BL31}, $(eval $(call TOOL_ADD_IMG,bl31,--soc-fw)),\
-	$(eval $(call MAKE_BL,31,soc-fw)))
+	$(eval $(call MAKE_BL,bl31,soc-fw)))
 endif
 endif
 
@@ -1114,14 +1261,25 @@
 BUILD_BL32 := $(if $(BL32),,$(if $(BL32_SOURCES),1))
 
 ifneq (${DECRYPTION_SUPPORT},none)
-$(if ${BUILD_BL32}, $(eval $(call MAKE_BL,32,tos-fw,,$(ENCRYPT_BL32))),\
+$(if ${BUILD_BL32}, $(eval $(call MAKE_BL,bl32,tos-fw,,$(ENCRYPT_BL32))),\
 	$(eval $(call TOOL_ADD_IMG,bl32,--tos-fw,,$(ENCRYPT_BL32))))
 else
-$(if ${BUILD_BL32}, $(eval $(call MAKE_BL,32,tos-fw)),\
+$(if ${BUILD_BL32}, $(eval $(call MAKE_BL,bl32,tos-fw)),\
 	$(eval $(call TOOL_ADD_IMG,bl32,--tos-fw)))
 endif
 endif
 
+# If RMM image is needed but RMM is not defined, Test Realm Payload (TRP)
+# needs to be built from RMM_SOURCES.
+ifeq (${NEED_RMM},yes)
+# Sort RMM source files to remove duplicates
+RMM_SOURCES := $(sort ${RMM_SOURCES})
+BUILD_RMM := $(if $(RMM),,$(if $(RMM_SOURCES),1))
+
+$(if ${BUILD_RMM}, $(eval $(call MAKE_BL,rmm,rmm-fw)),\
+         $(eval $(call TOOL_ADD_IMG,rmm,--rmm-fw)))
+endif
+
 # Add the BL33 image if required by the platform
 ifeq (${NEED_BL33},yes)
 $(eval $(call TOOL_ADD_IMG,bl33,--nt-fw))
@@ -1129,7 +1287,7 @@
 
 ifeq (${NEED_BL2U},yes)
 $(if ${BL2U}, $(eval $(call TOOL_ADD_IMG,bl2u,--ap-fwu-cfg,FWU_)),\
-	$(eval $(call MAKE_BL,2u,ap-fwu-cfg,FWU_)))
+	$(eval $(call MAKE_BL,bl2u,ap-fwu-cfg,FWU_)))
 endif
 
 # Expand build macros for the different images
@@ -1210,7 +1368,8 @@
 		echo "    with ${CHECKPATCH_OPTS} option(s)";		\
 	fi
 	${Q}COMMON_COMMIT=$$(git merge-base HEAD ${BASE_COMMIT});	\
-	for commit in `git rev-list $$COMMON_COMMIT..HEAD`; do		\
+	for commit in `git rev-list --no-merges $$COMMON_COMMIT..HEAD`;	\
+	do								\
 		printf "\n[*] Checking style of '$$commit'\n\n";	\
 		git log --format=email "$$commit~..$$commit"		\
 			-- ${CHECK_PATHS} |				\
@@ -1222,8 +1381,7 @@
 
 certtool: ${CRTTOOL}
 
-.PHONY: ${CRTTOOL}
-${CRTTOOL}:
+${CRTTOOL}: FORCE
 	${Q}${MAKE} PLAT=${PLAT} USE_TBBR_DEFS=${USE_TBBR_DEFS} COT=${COT} OPENSSL_DIR=${OPENSSL_DIR} CRTTOOL=${CRTTOOL} --no-print-directory -C ${CRTTOOLPATH}
 	@${ECHO_BLANK_LINE}
 	@echo "Built $@ successfully"
@@ -1239,6 +1397,7 @@
 endif
 
 ${BUILD_PLAT}/${FIP_NAME}: ${FIP_DEPS} ${FIPTOOL}
+	$(eval ${CHECK_FIP_CMD})
 	${Q}${FIPTOOL} create ${FIP_ARGS} $@
 	${Q}${FIPTOOL} info $@
 	@${ECHO_BLANK_LINE}
@@ -1255,6 +1414,7 @@
 endif
 
 ${BUILD_PLAT}/${FWU_FIP_NAME}: ${FWU_FIP_DEPS} ${FIPTOOL}
+	$(eval ${CHECK_FWU_FIP_CMD})
 	${Q}${FIPTOOL} create ${FWU_FIP_ARGS} $@
 	${Q}${FIPTOOL} info $@
 	@${ECHO_BLANK_LINE}
@@ -1265,10 +1425,7 @@
 fip: ${BUILD_PLAT}/${FIP_NAME}
 fwu_fip: ${BUILD_PLAT}/${FWU_FIP_NAME}
 
-.PHONY: ${FIPTOOL}
-${FIPTOOL}:
-	@${ECHO_BLANK_LINE}
-	@echo "Building $@"
+${FIPTOOL}: FORCE
 ifdef UNIX_MK
 	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" FIPTOOL=${FIPTOOL} --no-print-directory -C ${FIPTOOLPATH}
 else
@@ -1276,15 +1433,12 @@
 # to pass the gnumake flags to nmake.
 	${Q}set MAKEFLAGS= && ${MSVC_NMAKE} /nologo /f ${FIPTOOLPATH}/Makefile.msvc FIPTOOLPATH=$(subst /,\,$(FIPTOOLPATH)) FIPTOOL=$(subst /,\,$(FIPTOOL))
 endif
-	@${ECHO_BLANK_LINE}
 
 sptool: ${SPTOOL}
-.PHONY: ${SPTOOL}
-${SPTOOL}:
+${SPTOOL}: FORCE
 	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" SPTOOL=${SPTOOL} --no-print-directory -C ${SPTOOLPATH}
 
-.PHONY: libraries
-romlib.bin: libraries
+romlib.bin: libraries FORCE
 	${Q}${MAKE} PLAT_DIR=${PLAT_DIR} BUILD_PLAT=${BUILD_PLAT} ENABLE_BTI=${ENABLE_BTI} ARM_ARCH_MINOR=${ARM_ARCH_MINOR} INCLUDES='${INCLUDES}' DEFINES='${DEFINES}' --no-print-directory -C ${ROMLIBPATH} all
 
 # Call print_memory_map tool
@@ -1297,8 +1451,7 @@
 
 enctool: ${ENCTOOL}
 
-.PHONY: ${ENCTOOL}
-${ENCTOOL}:
+${ENCTOOL}: FORCE
 	${Q}${MAKE} PLAT=${PLAT} BUILD_INFO=0 OPENSSL_DIR=${OPENSSL_DIR} ENCTOOL=${ENCTOOL} --no-print-directory -C ${ENCTOOLPATH}
 	@${ECHO_BLANK_LINE}
 	@echo "Built $@ successfully"
@@ -1352,3 +1505,6 @@
 	@echo ""
 	@echo "example: build all targets for the FVP platform:"
 	@echo "  CROSS_COMPILE=aarch64-none-elf- make PLAT=fvp all"
+
+.PHONY: FORCE
+FORCE:;
diff --git a/bl1/aarch32/bl1_entrypoint.S b/bl1/aarch32/bl1_entrypoint.S
index 6a15566..94dfd37 100644
--- a/bl1/aarch32/bl1_entrypoint.S
+++ b/bl1/aarch32/bl1_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -49,7 +49,8 @@
 		_secondary_cold_boot=!COLD_BOOT_SINGLE_CPU	\
 		_init_memory=1					\
 		_init_c_runtime=1				\
-		_exception_vectors=bl1_vector_table
+		_exception_vectors=bl1_vector_table		\
+		_pie_fixup_size=0
 
 	/* -----------------------------------------------------
 	 * Perform BL1 setup
diff --git a/bl1/aarch64/bl1_context_mgmt.c b/bl1/aarch64/bl1_context_mgmt.c
index 2a8d58e..b9a7e5b 100644
--- a/bl1/aarch64/bl1_context_mgmt.c
+++ b/bl1/aarch64/bl1_context_mgmt.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,6 +16,7 @@
 
 /* Following contains the cpu context pointers. */
 static void *bl1_cpu_context_ptr[2];
+entry_point_info_t *bl2_ep_info;
 
 
 void *cm_get_context(uint32_t security_state)
@@ -30,6 +31,40 @@
 	bl1_cpu_context_ptr[security_state] = context;
 }
 
+#if ENABLE_RME
+/*******************************************************************************
+ * This function prepares the entry point information to run BL2 in Root world,
+ * i.e. EL3, for the case when FEAT_RME is enabled.
+ ******************************************************************************/
+void bl1_prepare_next_image(unsigned int image_id)
+{
+	image_desc_t *bl2_desc;
+
+	assert(image_id == BL2_IMAGE_ID);
+
+	/* Get the image descriptor. */
+	bl2_desc = bl1_plat_get_image_desc(BL2_IMAGE_ID);
+	assert(bl2_desc != NULL);
+
+	/* Get the entry point info. */
+	bl2_ep_info = &bl2_desc->ep_info;
+
+	bl2_ep_info->spsr = (uint32_t)SPSR_64(MODE_EL3, MODE_SP_ELX,
+						DISABLE_ALL_EXCEPTIONS);
+
+	/*
+	 * Flush cache since bl2_ep_info is accessed after MMU is disabled
+	 * before jumping to BL2.
+	 */
+	flush_dcache_range((uintptr_t)bl2_ep_info, sizeof(entry_point_info_t));
+
+	/* Indicate that image is in execution state. */
+	bl2_desc->state = IMAGE_STATE_EXECUTED;
+
+	/* Print debug info and flush the console before running BL2. */
+	print_entry_point_info(bl2_ep_info);
+}
+#else
 /*******************************************************************************
  * This function prepares the context for Secure/Normal world images.
  * Normal world images are transitioned to EL2(if supported) else EL1.
@@ -93,3 +128,4 @@
 
 	print_entry_point_info(next_bl_ep);
 }
+#endif /* ENABLE_RME */
diff --git a/bl1/aarch64/bl1_entrypoint.S b/bl1/aarch64/bl1_entrypoint.S
index 00f2718..f61c060 100644
--- a/bl1/aarch64/bl1_entrypoint.S
+++ b/bl1/aarch64/bl1_entrypoint.S
@@ -1,13 +1,15 @@
 /*
- * Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <arch.h>
+#include <common/bl_common.h>
 #include <el3_common_macros.S>
 
 	.globl	bl1_entrypoint
+	.globl	bl1_run_bl2_in_root
 
 
 	/* -----------------------------------------------------
@@ -66,5 +68,41 @@
 	 * Do the transition to next boot image.
 	 * --------------------------------------------------
 	 */
+#if ENABLE_RME
+	b	bl1_run_bl2_in_root
+#else
 	b	el3_exit
+#endif
 endfunc bl1_entrypoint
+
+	/* -----------------------------------------------------
+	 * void bl1_run_bl2_in_root();
+	 * This function runs BL2 in root/EL3 when RME is enabled.
+	 * -----------------------------------------------------
+	 */
+
+func bl1_run_bl2_in_root
+	/* read bl2_ep_info */
+	adrp	x20, bl2_ep_info
+	add	x20, x20, :lo12:bl2_ep_info
+	ldr	x20, [x20]
+
+	/* ---------------------------------------------
+	 * MMU needs to be disabled because BL2 executes
+	 * in EL3. It will initialize the address space
+	 * according to its own requirements.
+	 * ---------------------------------------------
+	 */
+	bl	disable_mmu_icache_el3
+	tlbi	alle3
+
+	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
+	msr	elr_el3, x0
+	msr	spsr_el3, x1
+
+	ldp	x6, x7, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x30)]
+	ldp	x4, x5, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x20)]
+	ldp	x2, x3, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x10)]
+	ldp	x0, x1, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x0)]
+	exception_return
+endfunc bl1_run_bl2_in_root
diff --git a/bl1/bl1.mk b/bl1/bl1.mk
index b839990..9f63fd5 100644
--- a/bl1/bl1.mk
+++ b/bl1/bl1.mk
@@ -1,14 +1,14 @@
 #
-# Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
-BL1_SOURCES		+=	bl1/bl1_main.c				\
-				bl1/${ARCH}/bl1_arch_setup.c		\
+BL1_SOURCES		+=	bl1/${ARCH}/bl1_arch_setup.c		\
 				bl1/${ARCH}/bl1_context_mgmt.c		\
 				bl1/${ARCH}/bl1_entrypoint.S		\
 				bl1/${ARCH}/bl1_exceptions.S		\
+				bl1/bl1_main.c				\
 				lib/cpus/${ARCH}/cpu_helpers.S		\
 				lib/cpus/errata_report.c		\
 				lib/el3_runtime/${ARCH}/context_mgmt.c	\
@@ -16,6 +16,10 @@
 				plat/common/${ARCH}/platform_up_stack.S \
 				${MBEDTLS_SOURCES}
 
+ifeq (${DISABLE_MTPMU},1)
+BL1_SOURCES		+=	lib/extensions/mtpmu/${ARCH}/mtpmu.S
+endif
+
 ifeq (${ARCH},aarch64)
 BL1_SOURCES		+=	lib/cpus/aarch64/dsu_helpers.S		\
 				lib/el3_runtime/aarch64/context.S
diff --git a/bl1/bl1_main.c b/bl1/bl1_main.c
index fd60232..663ec64 100644
--- a/bl1/bl1_main.c
+++ b/bl1/bl1_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -126,6 +126,9 @@
 	auth_mod_init();
 #endif /* TRUSTED_BOARD_BOOT */
 
+	/* Initialize the measured boot */
+	bl1_plat_mboot_init();
+
 	/* Perform platform setup in BL1. */
 	bl1_platform_setup();
 
@@ -147,6 +150,9 @@
 	else
 		NOTICE("BL1-FWU: *******FWU Process Started*******\n");
 
+	/* Teardown the measured boot driver */
+	bl1_plat_mboot_finish();
+
 	bl1_prepare_next_image(image_id);
 
 	console_flush();
diff --git a/bl1/bl1_private.h b/bl1/bl1_private.h
index 2cfeeea..e119ba7 100644
--- a/bl1/bl1_private.h
+++ b/bl1/bl1_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,6 +11,8 @@
 
 #include <common/bl_common.h>
 
+extern entry_point_info_t *bl2_ep_info;
+
 /******************************************
  * Function prototypes
  *****************************************/
@@ -18,6 +20,7 @@
 void bl1_arch_next_el_setup(void);
 
 void bl1_prepare_next_image(unsigned int image_id);
+void bl1_run_bl2_in_root(void);
 
 u_register_t bl1_fwu_smc_handler(unsigned int smc_fid,
 		u_register_t x1,
diff --git a/bl2/aarch32/bl2_el3_entrypoint.S b/bl2/aarch32/bl2_el3_entrypoint.S
index 2e851e6..40154aa 100644
--- a/bl2/aarch32/bl2_el3_entrypoint.S
+++ b/bl2/aarch32/bl2_el3_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,7 +10,6 @@
 #include <el3_common_macros.S>
 
 	.globl	bl2_entrypoint
-	.globl	bl2_run_next_image
 
 
 func bl2_entrypoint
@@ -26,7 +25,8 @@
                 _secondary_cold_boot=!COLD_BOOT_SINGLE_CPU      \
                 _init_memory=1                                  \
                 _init_c_runtime=1                               \
-                _exception_vectors=bl2_vector_table
+                _exception_vectors=bl2_vector_table		\
+		_pie_fixup_size=0
 
 	/*
 	 * Restore parameters of boot rom
@@ -55,37 +55,3 @@
 	no_ret	plat_panic_handler
 
 endfunc bl2_entrypoint
-
-func bl2_run_next_image
-	mov	r8,r0
-
-	/*
-	 * MMU needs to be disabled because both BL2 and BL32 execute
-	 * in PL1, and therefore share the same address space.
-	 * BL32 will initialize the address space according to its
-	 * own requirement.
-	 */
-	bl	disable_mmu_icache_secure
-	stcopr	r0, TLBIALL
-	dsb	sy
-	isb
-	mov	r0, r8
-	bl	bl2_el3_plat_prepare_exit
-
-	/*
-	 * Extract PC and SPSR based on struct `entry_point_info_t`
-	 * and load it in LR and SPSR registers respectively.
-	 */
-	ldr	lr, [r8, #ENTRY_POINT_INFO_PC_OFFSET]
-	ldr	r1, [r8, #(ENTRY_POINT_INFO_PC_OFFSET + 4)]
-	msr	spsr_xc, r1
-
-	/* Some BL32 stages expect lr_svc to provide the BL33 entry address */
-	cps	#MODE32_svc
-	ldr	lr, [r8, #ENTRY_POINT_INFO_LR_SVC_OFFSET]
-	cps	#MODE32_mon
-
-	add	r8, r8, #ENTRY_POINT_INFO_ARGS_OFFSET
-	ldm	r8, {r0, r1, r2, r3}
-	exception_return
-endfunc bl2_run_next_image
diff --git a/bl2/aarch32/bl2_entrypoint.S b/bl2/aarch32/bl2_entrypoint.S
index 102fd2f..6e8e2c1 100644
--- a/bl2/aarch32/bl2_entrypoint.S
+++ b/bl2/aarch32/bl2_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -80,12 +80,14 @@
 	 * ---------------------------------------------
 	 */
 	ldr	r0, =__BSS_START__
-	ldr	r1, =__BSS_SIZE__
+	ldr	r1, =__BSS_END__
+	sub 	r1, r1, r0
 	bl	zeromem
 
 #if USE_COHERENT_MEM
 	ldr	r0, =__COHERENT_RAM_START__
-	ldr	r1, =__COHERENT_RAM_UNALIGNED_SIZE__
+	ldr	r1, =__COHERENT_RAM_END_UNALIGNED__
+	sub 	r1, r1, r0
 	bl	zeromem
 #endif
 
diff --git a/bl2/aarch32/bl2_run_next_image.S b/bl2/aarch32/bl2_run_next_image.S
new file mode 100644
index 0000000..0b3554e
--- /dev/null
+++ b/bl2/aarch32/bl2_run_next_image.S
@@ -0,0 +1,46 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+
+	.globl	bl2_run_next_image
+
+
+func bl2_run_next_image
+	mov	r8,r0
+
+	/*
+	 * MMU needs to be disabled because both BL2 and BL32 execute
+	 * in PL1, and therefore share the same address space.
+	 * BL32 will initialize the address space according to its
+	 * own requirement.
+	 */
+	bl	disable_mmu_icache_secure
+	stcopr	r0, TLBIALL
+	dsb	sy
+	isb
+	mov	r0, r8
+	bl	bl2_el3_plat_prepare_exit
+
+	/*
+	 * Extract PC and SPSR based on struct `entry_point_info_t`
+	 * and load it in LR and SPSR registers respectively.
+	 */
+	ldr	lr, [r8, #ENTRY_POINT_INFO_PC_OFFSET]
+	ldr	r1, [r8, #(ENTRY_POINT_INFO_PC_OFFSET + 4)]
+	msr	spsr_xc, r1
+
+	/* Some BL32 stages expect lr_svc to provide the BL33 entry address */
+	cps	#MODE32_svc
+	ldr	lr, [r8, #ENTRY_POINT_INFO_LR_SVC_OFFSET]
+	cps	#MODE32_mon
+
+	add	r8, r8, #ENTRY_POINT_INFO_ARGS_OFFSET
+	ldm	r8, {r0, r1, r2, r3}
+	exception_return
+endfunc bl2_run_next_image
diff --git a/bl2/aarch64/bl2_el3_entrypoint.S b/bl2/aarch64/bl2_el3_entrypoint.S
index 4eab39c..45bac7d 100644
--- a/bl2/aarch64/bl2_el3_entrypoint.S
+++ b/bl2/aarch64/bl2_el3_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -12,8 +12,6 @@
 #include <el3_common_macros.S>
 
 	.globl	bl2_entrypoint
-	.globl	bl2_el3_run_image
-	.globl	bl2_run_next_image
 
 #if BL2_IN_XIP_MEM
 #define FIXUP_SIZE	0
@@ -72,36 +70,3 @@
 	 */
 	no_ret	plat_panic_handler
 endfunc bl2_entrypoint
-
-func bl2_run_next_image
-	mov	x20,x0
-	/* ---------------------------------------------
-	 * MMU needs to be disabled because both BL2 and BL31 execute
-	 * in EL3, and therefore share the same address space.
-	 * BL31 will initialize the address space according to its
-	 * own requirement.
-	 * ---------------------------------------------
-	 */
-	bl	disable_mmu_icache_el3
-	tlbi	alle3
-	bl	bl2_el3_plat_prepare_exit
-
-#if ENABLE_PAUTH
-	/* ---------------------------------------------
-	 * Disable pointer authentication before jumping
-	 * to next boot image.
-	 * ---------------------------------------------
-	 */
-	bl	pauth_disable_el3
-#endif /* ENABLE_PAUTH */
-
-	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
-	msr	elr_el3, x0
-	msr	spsr_el3, x1
-
-	ldp	x6, x7, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x30)]
-	ldp	x4, x5, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x20)]
-	ldp	x2, x3, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x10)]
-	ldp	x0, x1, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x0)]
-	exception_return
-endfunc bl2_run_next_image
diff --git a/bl2/aarch64/bl2_rme_entrypoint.S b/bl2/aarch64/bl2_rme_entrypoint.S
new file mode 100644
index 0000000..076e326
--- /dev/null
+++ b/bl2/aarch64/bl2_rme_entrypoint.S
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <platform_def.h>
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <el3_common_macros.S>
+
+	.globl	bl2_entrypoint
+
+
+func bl2_entrypoint
+	/* Save arguments x0-x3 from previous Boot loader */
+	mov	x20, x0
+	mov	x21, x1
+	mov	x22, x2
+	mov	x23, x3
+
+	el3_entrypoint_common                                   \
+		_init_sctlr=0                                   \
+		_warm_boot_mailbox=0                            \
+		_secondary_cold_boot=0                          \
+		_init_memory=0                                  \
+		_init_c_runtime=1                               \
+		_exception_vectors=bl2_el3_exceptions           \
+		_pie_fixup_size=0
+
+	/* ---------------------------------------------
+	 * Restore parameters of boot rom
+	 * ---------------------------------------------
+	 */
+	mov	x0, x20
+	mov	x1, x21
+	mov	x2, x22
+	mov	x3, x23
+
+	/* ---------------------------------------------
+	 * Perform BL2 setup
+	 * ---------------------------------------------
+	 */
+	bl	bl2_setup
+
+#if ENABLE_PAUTH
+	/* ---------------------------------------------
+	 * Program APIAKey_EL1 and enable pointer authentication.
+	 * ---------------------------------------------
+	 */
+	bl	pauth_init_enable_el3
+#endif /* ENABLE_PAUTH */
+
+	/* ---------------------------------------------
+	 * Jump to main function.
+	 * ---------------------------------------------
+	 */
+	bl	bl2_main
+
+	/* ---------------------------------------------
+	 * Should never reach this point.
+	 * ---------------------------------------------
+	 */
+	no_ret	plat_panic_handler
+endfunc bl2_entrypoint
diff --git a/bl2/aarch64/bl2_run_next_image.S b/bl2/aarch64/bl2_run_next_image.S
new file mode 100644
index 0000000..f0a8be8
--- /dev/null
+++ b/bl2/aarch64/bl2_run_next_image.S
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+
+	.globl	bl2_run_next_image
+
+
+func bl2_run_next_image
+	mov	x20,x0
+	/* ---------------------------------------------
+	 * MMU needs to be disabled because both BL2 and BL31 execute
+	 * in EL3, and therefore share the same address space.
+	 * BL31 will initialize the address space according to its
+	 * own requirement.
+	 * ---------------------------------------------
+	 */
+	bl	disable_mmu_icache_el3
+	tlbi	alle3
+	bl	bl2_el3_plat_prepare_exit
+
+#if ENABLE_PAUTH
+	/* ---------------------------------------------
+	 * Disable pointer authentication before jumping
+	 * to next boot image.
+	 * ---------------------------------------------
+	 */
+	bl	pauth_disable_el3
+#endif /* ENABLE_PAUTH */
+
+	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
+	msr	elr_el3, x0
+	msr	spsr_el3, x1
+
+	ldp	x6, x7, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x30)]
+	ldp	x4, x5, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x20)]
+	ldp	x2, x3, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x10)]
+	ldp	x0, x1, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x0)]
+	exception_return
+endfunc bl2_run_next_image
diff --git a/bl2/bl2.ld.S b/bl2/bl2.ld.S
index 37849c3..d332ec0 100644
--- a/bl2/bl2.ld.S
+++ b/bl2/bl2.ld.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -25,7 +25,11 @@
 #if SEPARATE_CODE_AND_RODATA
     .text . : {
         __TEXT_START__ = .;
+#if ENABLE_RME
+        *bl2_rme_entrypoint.o(.text*)
+#else /* ENABLE_RME */
         *bl2_entrypoint.o(.text*)
+#endif /* ENABLE_RME */
         *(SORT_BY_ALIGNMENT(.text*))
         *(.vectors)
         . = ALIGN(PAGE_SIZE);
diff --git a/bl2/bl2.mk b/bl2/bl2.mk
index 6dc0f18..7a973e5 100644
--- a/bl2/bl2.mk
+++ b/bl2/bl2.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -15,16 +15,33 @@
 BL2_SOURCES		+=	common/aarch64/early_exceptions.S
 endif
 
-ifeq (${BL2_AT_EL3},0)
+ifeq (${ENABLE_RME},1)
+# Using RME, run BL2 at EL3
+include lib/gpt_rme/gpt_rme.mk
+
+BL2_SOURCES		+=      bl2/${ARCH}/bl2_rme_entrypoint.S	\
+				bl2/${ARCH}/bl2_el3_exceptions.S	\
+				bl2/${ARCH}/bl2_run_next_image.S	\
+				${GPT_LIB_SRCS}
+BL2_LINKERFILE		:=	bl2/bl2.ld.S
+
+else ifeq (${BL2_AT_EL3},0)
+# Normal operation, no RME, no BL2 at EL3
 BL2_SOURCES		+=	bl2/${ARCH}/bl2_entrypoint.S
 BL2_LINKERFILE		:=	bl2/bl2.ld.S
 
 else
+# BL2 at EL3, no RME
 BL2_SOURCES		+=	bl2/${ARCH}/bl2_el3_entrypoint.S	\
 				bl2/${ARCH}/bl2_el3_exceptions.S	\
+				bl2/${ARCH}/bl2_run_next_image.S        \
 				lib/cpus/${ARCH}/cpu_helpers.S		\
 				lib/cpus/errata_report.c
 
+ifeq (${DISABLE_MTPMU},1)
+BL2_SOURCES		+=	lib/extensions/mtpmu/${ARCH}/mtpmu.S
+endif
+
 ifeq (${ARCH},aarch64)
 BL2_SOURCES		+=	lib/cpus/aarch64/dsu_helpers.S
 endif
diff --git a/bl2/bl2_main.c b/bl2/bl2_main.c
index 203e1d4..90fe39b 100644
--- a/bl2/bl2_main.c
+++ b/bl2/bl2_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,9 +14,7 @@
 #include <common/debug.h>
 #include <drivers/auth/auth_mod.h>
 #include <drivers/console.h>
-#if MEASURED_BOOT
-#include <drivers/measured_boot/measured_boot.h>
-#endif
+#include <drivers/fwu/fwu.h>
 #include <lib/extensions/pauth.h>
 #include <plat/common/platform.h>
 
@@ -28,31 +26,9 @@
 #define NEXT_IMAGE	"BL32"
 #endif
 
-#if !BL2_AT_EL3
+#if BL2_AT_EL3
 /*******************************************************************************
- * Setup function for BL2.
- ******************************************************************************/
-void bl2_setup(u_register_t arg0, u_register_t arg1, u_register_t arg2,
-	       u_register_t arg3)
-{
-	/* Perform early platform-specific setup */
-	bl2_early_platform_setup2(arg0, arg1, arg2, arg3);
-
-	/* Perform late platform-specific setup */
-	bl2_plat_arch_setup();
-
-#if CTX_INCLUDE_PAUTH_REGS
-	/*
-	 * Assert that the ARMv8.3-PAuth registers are present or an access
-	 * fault will be triggered when they are being saved or restored.
-	 */
-	assert(is_armv8_3_pauth_present());
-#endif /* CTX_INCLUDE_PAUTH_REGS */
-}
-
-#else /* if BL2_AT_EL3 */
-/*******************************************************************************
- * Setup function for BL2 when BL2_AT_EL3=1.
+ * Setup function for BL2 when BL2_AT_EL3=1
  ******************************************************************************/
 void bl2_el3_setup(u_register_t arg0, u_register_t arg1, u_register_t arg2,
 		   u_register_t arg3)
@@ -71,6 +47,27 @@
 	assert(is_armv8_3_pauth_present());
 #endif /* CTX_INCLUDE_PAUTH_REGS */
 }
+#else /* BL2_AT_EL3 */
+/*******************************************************************************
+ * Setup function for BL2 when BL2_AT_EL3=0
+ ******************************************************************************/
+void bl2_setup(u_register_t arg0, u_register_t arg1, u_register_t arg2,
+	       u_register_t arg3)
+{
+	/* Perform early platform-specific setup */
+	bl2_early_platform_setup2(arg0, arg1, arg2, arg3);
+
+	/* Perform late platform-specific setup */
+	bl2_plat_arch_setup();
+
+#if CTX_INCLUDE_PAUTH_REGS
+	/*
+	 * Assert that the ARMv8.3-PAuth registers are present or an access
+	 * fault will be triggered when they are being saved or restored.
+	 */
+	assert(is_armv8_3_pauth_present());
+#endif /* CTX_INCLUDE_PAUTH_REGS */
+}
 #endif /* BL2_AT_EL3 */
 
 /*******************************************************************************
@@ -88,29 +85,28 @@
 	/* Perform remaining generic architectural setup in S-EL1 */
 	bl2_arch_setup();
 
+#if PSA_FWU_SUPPORT
+	fwu_init();
+#endif /* PSA_FWU_SUPPORT */
+
 #if TRUSTED_BOARD_BOOT
 	/* Initialize authentication module */
 	auth_mod_init();
-
-#if MEASURED_BOOT
-	/* Initialize measured boot module */
-	measured_boot_init();
-
-#endif /* MEASURED_BOOT */
 #endif /* TRUSTED_BOARD_BOOT */
 
+	/* Initialize the Measured Boot backend */
+	bl2_plat_mboot_init();
+
 	/* Initialize boot source */
 	bl2_plat_preload_setup();
 
 	/* Load the subsequent bootloader images. */
 	next_bl_ep_info = bl2_load_images();
 
-#if MEASURED_BOOT
-	/* Finalize measured boot */
-	measured_boot_finish();
-#endif /* MEASURED_BOOT */
+	/* Teardown the Measured Boot backend */
+	bl2_plat_mboot_finish();
 
-#if !BL2_AT_EL3
+#if !BL2_AT_EL3 && !ENABLE_RME
 #ifndef __aarch64__
 	/*
 	 * For AArch32 state BL1 and BL2 share the MMU setup.
@@ -135,7 +131,7 @@
 	 * be passed to next BL image as an argument.
 	 */
 	smc(BL1_SMC_RUN_IMAGE, (unsigned long)next_bl_ep_info, 0, 0, 0, 0, 0, 0);
-#else /* if BL2_AT_EL3 */
+#else /* if BL2_AT_EL3 || ENABLE_RME */
 	NOTICE("BL2: Booting " NEXT_IMAGE "\n");
 	print_entry_point_info(next_bl_ep_info);
 	console_flush();
@@ -148,5 +144,5 @@
 #endif /* ENABLE_PAUTH */
 
 	bl2_run_next_image(next_bl_ep_info);
-#endif /* BL2_AT_EL3 */
+#endif /* BL2_AT_EL3 && ENABLE_RME */
 }
diff --git a/bl2u/aarch32/bl2u_entrypoint.S b/bl2u/aarch32/bl2u_entrypoint.S
index 6391f53..e4dd03d 100644
--- a/bl2u/aarch32/bl2u_entrypoint.S
+++ b/bl2u/aarch32/bl2u_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -79,7 +79,8 @@
 	 * ---------------------------------------------
 	 */
 	ldr	r0, =__BSS_START__
-	ldr	r1, =__BSS_SIZE__
+	ldr	r1, =__BSS_END__
+	sub 	r1, r1, r0
 	bl	zeromem
 
 	/* --------------------------------------------
diff --git a/bl2u/aarch64/bl2u_entrypoint.S b/bl2u/aarch64/bl2u_entrypoint.S
index 3e37b44..15978b6 100644
--- a/bl2u/aarch64/bl2u_entrypoint.S
+++ b/bl2u/aarch64/bl2u_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -69,8 +69,11 @@
 	 *   - the coherent memory section.
 	 * ---------------------------------------------
 	 */
-	ldr	x0, =__BSS_START__
-	ldr	x1, =__BSS_SIZE__
+	adrp	x0, __BSS_START__
+	add	x0, x0, :lo12:__BSS_START__
+	adrp	x1, __BSS_END__
+	add	x1, x1, :lo12:__BSS_END__
+	sub	x1, x1, x0
 	bl	zeromem
 
 	/* --------------------------------------------
diff --git a/bl31/aarch64/bl31_entrypoint.S b/bl31/aarch64/bl31_entrypoint.S
index 2d672dd..ed05864 100644
--- a/bl31/aarch64/bl31_entrypoint.S
+++ b/bl31/aarch64/bl31_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -195,6 +195,19 @@
 #endif
 	bl	bl31_plat_enable_mmu
 
+#if ENABLE_RME
+	/*
+	 * At warm boot GPT data structures have already been initialized in RAM
+	 * but the sysregs for this CPU need to be initialized. Note that the GPT
+	 * accesses are controlled attributes in GPCCR and do not depend on the
+	 * SCR_EL3.C bit.
+	 */
+	bl	gpt_enable
+	cbz	x0, 1f
+	no_ret plat_panic_handler
+1:
+#endif
+
 #if ENABLE_PAUTH
 	/* --------------------------------------------------------------------
 	 * Program APIAKey_EL1 and enable pointer authentication
diff --git a/bl31/aarch64/ea_delegate.S b/bl31/aarch64/ea_delegate.S
index 1d28d5e..f9c789f 100644
--- a/bl31/aarch64/ea_delegate.S
+++ b/bl31/aarch64/ea_delegate.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,6 +15,7 @@
 #include <context.h>
 
 	.globl	handle_lower_el_ea_esb
+	.globl  handle_lower_el_async_ea
 	.globl	enter_lower_el_sync_ea
 	.globl	enter_lower_el_async_ea
 
@@ -133,6 +134,7 @@
 	 */
 	str	x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
 
+handle_lower_el_async_ea:
 	/*
 	 * Save general purpose and ARMv8.3-PAuth registers (if enabled).
 	 * If Secure Cycle Counter is not disabled in MDCR_EL3 when
diff --git a/bl31/aarch64/runtime_exceptions.S b/bl31/aarch64/runtime_exceptions.S
index bfe13f3..0d0a12d 100644
--- a/bl31/aarch64/runtime_exceptions.S
+++ b/bl31/aarch64/runtime_exceptions.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -45,8 +45,9 @@
 	 * instruction. When an error is thus synchronized, the handling is
 	 * delegated to platform EA handler.
 	 *
-	 * Without RAS_EXTENSION, this macro just saves x30, and unmasks
-	 * Asynchronous External Aborts.
+	 * Without RAS_EXTENSION, this macro synchronizes pending errors using
+         * a DSB, unmasks Asynchronous External Aborts and saves X30 before
+	 * setting the flag CTX_IS_IN_EL3.
 	 */
 	.macro check_and_unmask_ea
 #if RAS_EXTENSION
@@ -79,13 +80,89 @@
 	bl	restore_gp_pmcr_pauth_regs
 1:
 #else
+	/*
+	 * For SoCs which do not implement RAS, use DSB as a barrier to
+	 * synchronize pending external aborts.
+	 */
+	dsb	sy
+
 	/* Unmask the SError interrupt */
 	msr	daifclr, #DAIF_ABT_BIT
 
+	/* Use ISB for the above unmask operation to take effect immediately */
+	isb
+
+	/*
+	 * Refer Note 1. No need to restore X30 as both handle_sync_exception
+	 * and handle_interrupt_exception macro which follow this macro modify
+	 * X30 anyway.
+	 */
 	str	x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
+	mov 	x30, #1
+	str	x30, [sp, #CTX_EL3STATE_OFFSET + CTX_IS_IN_EL3]
+	dmb	sy
 #endif
 	.endm
 
+#if !RAS_EXTENSION
+	/*
+	 * Note 1: The explicit DSB at the entry of various exception vectors
+	 * for handling exceptions from lower ELs can inadvertently trigger an
+	 * SError exception in EL3 due to pending asynchronous aborts in lower
+	 * ELs. This will end up being handled by serror_sp_elx which will
+	 * ultimately panic and die.
+	 * The way to workaround is to update a flag to indicate if the exception
+	 * truly came from EL3. This flag is allocated in the cpu_context
+	 * structure and located at offset "CTX_EL3STATE_OFFSET + CTX_IS_IN_EL3"
+	 * This is not a bullet proof solution to the problem at hand because
+	 * we assume the instructions following "isb" that help to update the
+	 * flag execute without causing further exceptions.
+	 */
+
+	/* ---------------------------------------------------------------------
+	 * This macro handles Asynchronous External Aborts.
+	 * ---------------------------------------------------------------------
+	 */
+	.macro	handle_async_ea
+	/*
+	 * Use a barrier to synchronize pending external aborts.
+	 */
+	dsb	sy
+
+	/* Unmask the SError interrupt */
+	msr	daifclr, #DAIF_ABT_BIT
+
+	/* Use ISB for the above unmask operation to take effect immediately */
+	isb
+
+	/* Refer Note 1 */
+	str	x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
+	mov 	x30, #1
+	str	x30, [sp, #CTX_EL3STATE_OFFSET + CTX_IS_IN_EL3]
+	dmb	sy
+
+	b	handle_lower_el_async_ea
+	.endm
+
+	/*
+	 * This macro checks if the exception was taken due to SError in EL3 or
+	 * because of pending asynchronous external aborts from lower EL that got
+	 * triggered due to explicit synchronization in EL3. Refer Note 1.
+	 */
+	.macro check_if_serror_from_EL3
+	/* Assumes SP_EL3 on entry */
+	str	x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
+	ldr	x30, [sp, #CTX_EL3STATE_OFFSET + CTX_IS_IN_EL3]
+	cbnz	x30, exp_from_EL3
+
+	/* Handle asynchronous external abort from lower EL */
+	b	handle_lower_el_async_ea
+
+exp_from_EL3:
+	/* Jump to plat_handle_el3_ea which does not return */
+	.endm
+#endif
+
 	/* ---------------------------------------------------------------------
 	 * This macro handles Synchronous exceptions.
 	 * Only SMC exceptions are supported.
@@ -272,6 +349,9 @@
 end_vector_entry fiq_sp_elx
 
 vector_entry serror_sp_elx
+#if !RAS_EXTENSION
+	check_if_serror_from_EL3
+#endif
 	no_ret	plat_handle_el3_ea
 end_vector_entry serror_sp_elx
 
@@ -305,8 +385,12 @@
 
 vector_entry serror_aarch64
 	apply_at_speculative_wa
+#if RAS_EXTENSION
 	msr	daifclr, #DAIF_ABT_BIT
 	b	enter_lower_el_async_ea
+#else
+	handle_async_ea
+#endif
 end_vector_entry serror_aarch64
 
 	/* ---------------------------------------------------------------------
@@ -339,8 +423,12 @@
 
 vector_entry serror_aarch32
 	apply_at_speculative_wa
+#if RAS_EXTENSION
 	msr	daifclr, #DAIF_ABT_BIT
 	b	enter_lower_el_async_ea
+#else
+	handle_async_ea
+#endif
 end_vector_entry serror_aarch32
 
 #ifdef MONITOR_TRAPS
@@ -412,6 +500,21 @@
 	stp	x16, x17, [x6, #CTX_EL3STATE_OFFSET + CTX_SPSR_EL3]
 	str	x18, [x6, #CTX_EL3STATE_OFFSET + CTX_SCR_EL3]
 
+	/* Clear flag register */
+	mov	x7, xzr
+
+#if ENABLE_RME
+	/* Copy SCR_EL3.NSE bit to the flag to indicate caller's security */
+	ubfx	x7, x18, #SCR_NSE_SHIFT, 1
+
+	/*
+	 * Shift copied SCR_EL3.NSE bit by 5 to create space for
+	 * SCR_EL3.NS bit. Bit 5 of the flag correspondes to
+	 * the SCR_EL3.NSE bit.
+	 */
+	lsl	x7, x7, #5
+#endif /* ENABLE_RME */
+
 	/* Copy SCR_EL3.NS bit to the flag to indicate caller's security */
 	bfi	x7, x18, #0, #1
 
diff --git a/bl31/bl31.mk b/bl31/bl31.mk
index cd6549b..e751824 100644
--- a/bl31/bl31.mk
+++ b/bl31/bl31.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -22,6 +22,8 @@
   endif
 endif
 
+include lib/extensions/amu/amu.mk
+include lib/mpmm/mpmm.mk
 include lib/psci/psci_lib.mk
 
 BL31_SOURCES		+=	bl31/bl31_main.c				\
@@ -40,6 +42,9 @@
 				${SPMD_SOURCES}					\
 				${SPM_SOURCES}
 
+ifeq (${DISABLE_MTPMU},1)
+BL31_SOURCES		+=	lib/extensions/mtpmu/aarch64/mtpmu.S
+endif
 
 ifeq (${ENABLE_PMF}, 1)
 BL31_SOURCES		+=	lib/pmf/pmf_main.c
@@ -65,28 +70,64 @@
 				services/std_svc/sdei/sdei_state.c
 endif
 
+ifeq (${TRNG_SUPPORT},1)
+BL31_SOURCES		+=	services/std_svc/trng/trng_main.c	\
+				services/std_svc/trng/trng_entropy_pool.c
+endif
+
 ifeq (${ENABLE_SPE_FOR_LOWER_ELS},1)
 BL31_SOURCES		+=	lib/extensions/spe/spe.c
 endif
 
 ifeq (${ENABLE_AMU},1)
-BL31_SOURCES		+=	lib/extensions/amu/aarch64/amu.c		\
-				lib/extensions/amu/aarch64/amu_helpers.S
+BL31_SOURCES		+=	${AMU_SOURCES}
 endif
 
+ifeq (${ENABLE_MPMM},1)
+BL31_SOURCES		+=	${MPMM_SOURCES}
+endif
+
+ifeq (${ENABLE_SME_FOR_NS},1)
+BL31_SOURCES		+=	lib/extensions/sme/sme.c
+BL31_SOURCES		+=	lib/extensions/sve/sve.c
+else
 ifeq (${ENABLE_SVE_FOR_NS},1)
 BL31_SOURCES		+=	lib/extensions/sve/sve.c
 endif
+endif
 
 ifeq (${ENABLE_MPAM_FOR_LOWER_ELS},1)
 BL31_SOURCES		+=	lib/extensions/mpam/mpam.c
 endif
 
+ifeq (${ENABLE_TRBE_FOR_NS},1)
+BL31_SOURCES		+=	lib/extensions/trbe/trbe.c
+endif
+
+ifeq (${ENABLE_SYS_REG_TRACE_FOR_NS},1)
+BL31_SOURCES		+=      lib/extensions/sys_reg_trace/aarch64/sys_reg_trace.c
+endif
+
+ifeq (${ENABLE_TRF_FOR_NS},1)
+BL31_SOURCES		+=	lib/extensions/trf/aarch64/trf.c
+endif
+
 ifeq (${WORKAROUND_CVE_2017_5715},1)
 BL31_SOURCES		+=	lib/cpus/aarch64/wa_cve_2017_5715_bpiall.S	\
 				lib/cpus/aarch64/wa_cve_2017_5715_mmu.S
 endif
 
+ifeq ($(SMC_PCI_SUPPORT),1)
+BL31_SOURCES		+=	services/std_svc/pci_svc.c
+endif
+
+ifeq (${ENABLE_RME},1)
+include lib/gpt_rme/gpt_rme.mk
+
+BL31_SOURCES		+=	${GPT_LIB_SRCS}					\
+				${RMMD_SOURCES}
+endif
+
 BL31_LINKERFILE		:=	bl31/bl31.ld.S
 
 # Flag used to indicate if Crash reporting via console should be included
diff --git a/bl31/bl31_context_mgmt.c b/bl31/bl31_context_mgmt.c
index 9175ee3..34f69ad 100644
--- a/bl31/bl31_context_mgmt.c
+++ b/bl31/bl31_context_mgmt.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -19,9 +19,9 @@
  ******************************************************************************/
 void *cm_get_context(uint32_t security_state)
 {
-	assert(security_state <= NON_SECURE);
+	assert(sec_state_is_valid(security_state));
 
-	return get_cpu_data(cpu_context[security_state]);
+	return get_cpu_data(cpu_context[get_cpu_context_index(security_state)]);
 }
 
 /*******************************************************************************
@@ -30,9 +30,10 @@
  ******************************************************************************/
 void cm_set_context(void *context, uint32_t security_state)
 {
-	assert(security_state <= NON_SECURE);
+	assert(sec_state_is_valid(security_state));
 
-	set_cpu_data(cpu_context[security_state], context);
+	set_cpu_data(cpu_context[get_cpu_context_index(security_state)],
+			context);
 }
 
 /*******************************************************************************
@@ -46,7 +47,8 @@
 {
 	assert(sec_state_is_valid(security_state));
 
-	return get_cpu_data_by_index(cpu_idx, cpu_context[security_state]);
+	return get_cpu_data_by_index(cpu_idx,
+			cpu_context[get_cpu_context_index(security_state)]);
 }
 
 /*******************************************************************************
@@ -58,5 +60,7 @@
 {
 	assert(sec_state_is_valid(security_state));
 
-	set_cpu_data_by_index(cpu_idx, cpu_context[security_state], context);
+	set_cpu_data_by_index(cpu_idx,
+			cpu_context[get_cpu_context_index(security_state)],
+			context);
 }
diff --git a/bl31/bl31_main.c b/bl31/bl31_main.c
index 44bf32c..9ac10e2 100644
--- a/bl31/bl31_main.c
+++ b/bl31/bl31_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -35,6 +35,13 @@
  ******************************************************************************/
 static int32_t (*bl32_init)(void);
 
+/*****************************************************************************
+ * Function used to initialise RMM if RME is enabled
+ *****************************************************************************/
+#if ENABLE_RME
+static int32_t (*rmm_init)(void);
+#endif
+
 /*******************************************************************************
  * Variable to indicate whether next image to execute after BL31 is BL33
  * (non-secure & default) or BL32 (secure).
@@ -85,6 +92,15 @@
 	/* Perform late platform-specific setup */
 	bl31_plat_arch_setup();
 
+#if ENABLE_FEAT_HCX
+	/*
+	 * Assert that FEAT_HCX is supported on this system, without this check
+	 * an exception would occur during context save/restore if enabled but
+	 * not supported.
+	 */
+	assert(is_feat_hcx_present());
+#endif /* ENABLE_FEAT_HCX */
+
 #if CTX_INCLUDE_PAUTH_REGS
 	/*
 	 * Assert that the ARMv8.3-PAuth registers are present or an access
@@ -130,12 +146,15 @@
 
 	/*
 	 * All the cold boot actions on the primary cpu are done. We now need to
-	 * decide which is the next image (BL32 or BL33) and how to execute it.
+	 * decide which is the next image and how to execute it.
 	 * If the SPD runtime service is present, it would want to pass control
 	 * to BL32 first in S-EL1. In that case, SPD would have registered a
 	 * function to initialize bl32 where it takes responsibility of entering
-	 * S-EL1 and returning control back to bl31_main. Once this is done we
-	 * can prepare entry into BL33 as normal.
+	 * S-EL1 and returning control back to bl31_main. Similarly, if RME is
+	 * enabled and a function is registered to initialize RMM, control is
+	 * transferred to RMM in R-EL2. After RMM initialization, control is
+	 * returned back to bl31_main. Once this is done we can prepare entry
+	 * into BL33 as normal.
 	 */
 
 	/*
@@ -146,9 +165,27 @@
 
 		int32_t rc = (*bl32_init)();
 
-		if (rc == 0)
+		if (rc == 0) {
 			WARN("BL31: BL32 initialization failed\n");
+		}
 	}
+
+	/*
+	 * If RME is enabled and init hook is registered, initialize RMM
+	 * in R-EL2.
+	 */
+#if ENABLE_RME
+	if (rmm_init != NULL) {
+		INFO("BL31: Initializing RMM\n");
+
+		int32_t rc = (*rmm_init)();
+
+		if (rc == 0) {
+			WARN("BL31: RMM initialization failed\n");
+		}
+	}
+#endif
+
 	/*
 	 * We are ready to enter the next EL. Prepare entry into the image
 	 * corresponding to the desired security state after the next ERET.
@@ -227,3 +264,14 @@
 {
 	bl32_init = func;
 }
+
+#if ENABLE_RME
+/*******************************************************************************
+ * This function initializes the pointer to RMM init function. This is expected
+ * to be called by the RMMD after it finishes all its initialization
+ ******************************************************************************/
+void bl31_register_rmm_init(int32_t (*func)(void))
+{
+	rmm_init = func;
+}
+#endif
diff --git a/bl32/sp_min/aarch32/entrypoint.S b/bl32/sp_min/aarch32/entrypoint.S
index f3a1e44..39f1065 100644
--- a/bl32/sp_min/aarch32/entrypoint.S
+++ b/bl32/sp_min/aarch32/entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -23,6 +23,8 @@
 	.globl	sp_min_handle_smc
 	.globl	sp_min_handle_fiq
 
+#define FIXUP_SIZE	((BL32_LIMIT) - (BL32_BASE))
+
 	.macro route_fiq_to_sp_min reg
 		/* -----------------------------------------------------
 		 * FIQs are secure interrupts trapped by Monitor and non
@@ -87,7 +89,8 @@
 		_secondary_cold_boot=0				\
 		_init_memory=0					\
 		_init_c_runtime=1				\
-		_exception_vectors=sp_min_vector_table
+		_exception_vectors=sp_min_vector_table		\
+		_pie_fixup_size=FIXUP_SIZE
 
 	/* ---------------------------------------------------------------------
 	 * Relay the previous bootloader's arguments to the platform layer
@@ -106,7 +109,8 @@
 		_secondary_cold_boot=!COLD_BOOT_SINGLE_CPU	\
 		_init_memory=1					\
 		_init_c_runtime=1				\
-		_exception_vectors=sp_min_vector_table
+		_exception_vectors=sp_min_vector_table		\
+		_pie_fixup_size=FIXUP_SIZE
 
 	/* ---------------------------------------------------------------------
 	 * For RESET_TO_SP_MIN systems, BL32 (SP_MIN) is the first bootloader
@@ -306,7 +310,8 @@
 		_secondary_cold_boot=0				\
 		_init_memory=0					\
 		_init_c_runtime=0				\
-		_exception_vectors=sp_min_vector_table
+		_exception_vectors=sp_min_vector_table		\
+		_pie_fixup_size=0
 
 	/*
 	 * We're about to enable MMU and participate in PSCI state coordination.
diff --git a/bl32/sp_min/sp_min.ld.S b/bl32/sp_min/sp_min.ld.S
index f202c7a..475affa 100644
--- a/bl32/sp_min/sp_min.ld.S
+++ b/bl32/sp_min/sp_min.ld.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -92,6 +92,7 @@
     __RW_START__ = . ;
 
     DATA_SECTION >RAM
+    RELA_SECTION >RAM
 
 #ifdef BL32_PROGBITS_LIMIT
     ASSERT(. <= BL32_PROGBITS_LIMIT, "BL32 progbits has exceeded its limit.")
@@ -141,5 +142,9 @@
 
     __BL32_END__ = .;
 
+    /DISCARD/ : {
+        *(.dynsym .dynstr .hash .gnu.hash)
+    }
+
     ASSERT(. <= BL32_LIMIT, "BL32 image has exceeded its limit.")
 }
diff --git a/bl32/sp_min/sp_min.mk b/bl32/sp_min/sp_min.mk
index 6233299..590b032 100644
--- a/bl32/sp_min/sp_min.mk
+++ b/bl32/sp_min/sp_min.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -8,6 +8,7 @@
 	$(error SP_MIN is only supported on AArch32 platforms)
 endif
 
+include lib/extensions/amu/amu.mk
 include lib/psci/psci_lib.mk
 
 INCLUDES		+=	-Iinclude/bl32/sp_min
@@ -19,13 +20,16 @@
 				services/std_svc/std_svc_setup.c	\
 				${PSCI_LIB_SOURCES}
 
+ifeq (${DISABLE_MTPMU},1)
+BL32_SOURCES		+=	lib/extensions/mtpmu/aarch32/mtpmu.S
+endif
+
 ifeq (${ENABLE_PMF}, 1)
 BL32_SOURCES		+=	lib/pmf/pmf_main.c
 endif
 
-ifeq (${ENABLE_AMU}, 1)
-BL32_SOURCES		+=	lib/extensions/amu/aarch32/amu.c\
-				lib/extensions/amu/aarch32/amu_helpers.S
+ifeq (${ENABLE_AMU},1)
+BL32_SOURCES		+=	${AMU_SOURCES}
 endif
 
 ifeq (${WORKAROUND_CVE_2017_5715},1)
@@ -33,6 +37,19 @@
 				bl32/sp_min/wa_cve_2017_5715_icache_inv.S
 endif
 
+ifeq (${TRNG_SUPPORT},1)
+BL32_SOURCES		+=	services/std_svc/trng/trng_main.c	\
+				services/std_svc/trng/trng_entropy_pool.c
+endif
+
+ifeq (${ENABLE_SYS_REG_TRACE_FOR_NS},1)
+BL32_SOURCES		+=	lib/extensions/sys_reg_trace/aarch32/sys_reg_trace.c
+endif
+
+ifeq (${ENABLE_TRF_FOR_NS},1)
+BL32_SOURCES		+=	lib/extensions/trf/aarch32/trf.c
+endif
+
 BL32_LINKERFILE	:=	bl32/sp_min/sp_min.ld.S
 
 # Include the platform-specific SP_MIN Makefile
diff --git a/bl32/tsp/aarch64/tsp_entrypoint.S b/bl32/tsp/aarch64/tsp_entrypoint.S
index a007bab..7d77f47 100644
--- a/bl32/tsp/aarch64/tsp_entrypoint.S
+++ b/bl32/tsp/aarch64/tsp_entrypoint.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -100,11 +100,27 @@
 	 * sections. This is done to safeguard against
 	 * possible corruption of this memory by dirty
 	 * cache lines in a system cache as a result of
-	 * use by an earlier boot loader stage.
+	 * use by an earlier boot loader stage. If PIE
+	 * is enabled however, RO sections including the
+	 * GOT may be modified during pie fixup.
+	 * Therefore, to be on the safe side, invalidate
+	 * the entire image region if PIE is enabled.
 	 * ---------------------------------------------
 	 */
-	adr	x0, __RW_START__
-	adr	x1, __RW_END__
+#if ENABLE_PIE
+#if SEPARATE_CODE_AND_RODATA
+	adrp	x0, __TEXT_START__
+	add	x0, x0, :lo12:__TEXT_START__
+#else
+	adrp	x0, __RO_START__
+	add	x0, x0, :lo12:__RO_START__
+#endif /* SEPARATE_CODE_AND_RODATA */
+#else
+	adrp	x0, __RW_START__
+	add	x0, x0, :lo12:__RW_START__
+#endif /* ENABLE_PIE */
+	adrp	x1, __RW_END__
+	add     x1, x1, :lo12:__RW_END__
 	sub	x1, x1, x0
 	bl	inv_dcache_range
 
@@ -114,13 +130,19 @@
 	 *   - the coherent memory section.
 	 * ---------------------------------------------
 	 */
-	ldr	x0, =__BSS_START__
-	ldr	x1, =__BSS_SIZE__
+	adrp	x0, __BSS_START__
+	add	x0, x0, :lo12:__BSS_START__
+	adrp	x1, __BSS_END__
+	add	x1, x1, :lo12:__BSS_END__
+	sub	x1, x1, x0
 	bl	zeromem
 
 #if USE_COHERENT_MEM
-	ldr	x0, =__COHERENT_RAM_START__
-	ldr	x1, =__COHERENT_RAM_UNALIGNED_SIZE__
+	adrp	x0, __COHERENT_RAM_START__
+	add	x0, x0, :lo12:__COHERENT_RAM_START__
+	adrp	x1, __COHERENT_RAM_END_UNALIGNED__
+	add	x1, x1, :lo12:__COHERENT_RAM_END_UNALIGNED__
+	sub	x1, x1, x0
 	bl	zeromem
 #endif
 
diff --git a/bl32/tsp/aarch64/tsp_request.S b/bl32/tsp/aarch64/tsp_request.S
index 5ad16da..6e238ea 100644
--- a/bl32/tsp/aarch64/tsp_request.S
+++ b/bl32/tsp/aarch64/tsp_request.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2014, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,28 +9,19 @@
 
 	.globl tsp_get_magic
 
-
 /*
  * This function raises an SMC to retrieve arguments from secure
  * monitor/dispatcher, saves the returned arguments the array received in x0,
  * and then returns to the caller
  */
 func tsp_get_magic
-	/* Save address to stack */
-	stp	x0, xzr, [sp, #-16]!
-
 	/* Load arguments */
 	ldr	w0, _tsp_fid_get_magic
 
 	/* Raise SMC */
 	smc	#0
 
-	/* Restore address from stack */
-	ldp	x4, xzr, [sp], #16
-
-	/* Store returned arguments to the array */
-	stp	x0, x1, [x4, #0]
-
+	/* Return arguments in x1:x0 */
 	ret
 endfunc tsp_get_magic
 
diff --git a/bl32/tsp/tsp_interrupt.c b/bl32/tsp/tsp_interrupt.c
index 4e500b3..430b5dd 100644
--- a/bl32/tsp/tsp_interrupt.c
+++ b/bl32/tsp/tsp_interrupt.c
@@ -5,6 +5,7 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
 
 #include <platform_def.h>
 
@@ -36,7 +37,7 @@
 
 #if LOG_LEVEL >= LOG_LEVEL_VERBOSE
 	spin_lock(&console_lock);
-	VERBOSE("TSP: cpu 0x%lx sync s-el1 interrupt request from 0x%llx\n",
+	VERBOSE("TSP: cpu 0x%lx sync s-el1 interrupt request from 0x%" PRIx64 "\n",
 		read_mpidr(), elr_el3);
 	VERBOSE("TSP: cpu 0x%lx: %d sync s-el1 interrupt requests,"
 		" %d sync s-el1 interrupt returns\n",
diff --git a/bl32/tsp/tsp_main.c b/bl32/tsp/tsp_main.c
index e947838..55e1532 100644
--- a/bl32/tsp/tsp_main.c
+++ b/bl32/tsp/tsp_main.c
@@ -1,10 +1,12 @@
 /*
- * Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <arch_features.h>
 #include <arch_helpers.h>
@@ -271,7 +273,7 @@
 
 #if LOG_LEVEL >= LOG_LEVEL_INFO
 	spin_lock(&console_lock);
-	INFO("TSP: cpu 0x%lx resumed. maximum off power level %lld\n",
+	INFO("TSP: cpu 0x%lx resumed. maximum off power level %" PRId64 "\n",
 	     read_mpidr(), max_off_pwrlvl);
 	INFO("TSP: cpu 0x%lx: %d smcs, %d erets %d cpu resume requests\n",
 		read_mpidr(),
@@ -363,8 +365,10 @@
 			       uint64_t arg6,
 			       uint64_t arg7)
 {
+	uint128_t service_args;
+	uint64_t service_arg0;
+	uint64_t service_arg1;
 	uint64_t results[2];
-	uint64_t service_args[2];
 	uint32_t linear_id = plat_my_core_pos();
 
 	/* Update this cpu's statistics */
@@ -373,7 +377,7 @@
 
 #if LOG_LEVEL >= LOG_LEVEL_INFO
 	spin_lock(&console_lock);
-	INFO("TSP: cpu 0x%lx received %s smc 0x%llx\n", read_mpidr(),
+	INFO("TSP: cpu 0x%lx received %s smc 0x%" PRIx64 "\n", read_mpidr(),
 		((func >> 31) & 1) == 1 ? "fast" : "yielding",
 		func);
 	INFO("TSP: cpu 0x%lx: %d smcs, %d erets\n", read_mpidr(),
@@ -387,10 +391,12 @@
 	results[1] = arg2;
 
 	/*
-	 * Request a service back from dispatcher/secure monitor. This call
-	 * return and thereafter resume execution
+	 * Request a service back from dispatcher/secure monitor.
+	 * This call returns and thereafter resumes execution.
 	 */
-	tsp_get_magic(service_args);
+	service_args = tsp_get_magic();
+	service_arg0 = (uint64_t)service_args;
+	service_arg1 = (uint64_t)(service_args >> 64U);
 
 #if CTX_INCLUDE_MTE_REGS
 	/*
@@ -403,20 +409,20 @@
 	/* Determine the function to perform based on the function ID */
 	switch (TSP_BARE_FID(func)) {
 	case TSP_ADD:
-		results[0] += service_args[0];
-		results[1] += service_args[1];
+		results[0] += service_arg0;
+		results[1] += service_arg1;
 		break;
 	case TSP_SUB:
-		results[0] -= service_args[0];
-		results[1] -= service_args[1];
+		results[0] -= service_arg0;
+		results[1] -= service_arg1;
 		break;
 	case TSP_MUL:
-		results[0] *= service_args[0];
-		results[1] *= service_args[1];
+		results[0] *= service_arg0;
+		results[1] *= service_arg1;
 		break;
 	case TSP_DIV:
-		results[0] /= service_args[0] ? service_args[0] : 1;
-		results[1] /= service_args[1] ? service_args[1] : 1;
+		results[0] /= service_arg0 ? service_arg0 : 1;
+		results[1] /= service_arg1 ? service_arg1 : 1;
 		break;
 	default:
 		break;
diff --git a/bl32/tsp/tsp_private.h b/bl32/tsp/tsp_private.h
index cbd527f..38d9732 100644
--- a/bl32/tsp/tsp_private.h
+++ b/bl32/tsp/tsp_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -61,7 +61,7 @@
  */
 CASSERT(TSP_ARGS_SIZE == sizeof(tsp_args_t), assert_sp_args_size_mismatch);
 
-void tsp_get_magic(uint64_t args[4]);
+uint128_t tsp_get_magic(void);
 
 tsp_args_t *tsp_cpu_resume_main(uint64_t max_off_pwrlvl,
 				uint64_t arg1,
diff --git a/commitlint.config.js b/commitlint.config.js
new file mode 100644
index 0000000..94cad8f
--- /dev/null
+++ b/commitlint.config.js
@@ -0,0 +1,14 @@
+/* eslint-env node */
+
+"use strict";
+
+const config = require("./.cz.json");
+
+module.exports = {
+    extends: ["@commitlint/config-conventional"],
+    rules: {
+        "header-max-length": [1, "always", config.maxHeaderWidth], /* Warning */
+        "body-max-line-length": [1, "always", config.maxLineWidth], /* Warning */
+        "signed-off-by": [0, "always", "Signed-off-by:"] /* Disabled - buggy */
+    }
+};
diff --git a/common/aarch64/debug.S b/common/aarch64/debug.S
index ad6acd9..d105d08 100644
--- a/common/aarch64/debug.S
+++ b/common/aarch64/debug.S
@@ -208,6 +208,9 @@
 	sub	x4, x4, #4
 	bl	asm_print_hex
 
+	/* Print new line */
+	bl	asm_print_newline
+
 	bl	plat_crash_console_flush
 
 _panic_handler:
diff --git a/common/bl_common.c b/common/bl_common.c
index f17afcb..eb2352a 100644
--- a/common/bl_common.c
+++ b/common/bl_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -202,12 +202,26 @@
 		return -EAUTH;
 	}
 
-	/*
-	 * Flush the image to main memory so that it can be executed later by
-	 * any CPU, regardless of cache and MMU state. This is only needed for
-	 * child images, not for the parents (certificates).
-	 */
 	if (is_parent_image == 0) {
+		/*
+		 * Measure the image.
+		 * We do not measure its parents because these only play a role
+		 * in authentication, which is orthogonal to measured boot.
+		 *
+		 * TODO: Change this code if we change our minds about measuring
+		 * certificates.
+		 */
+		rc = plat_mboot_measure_image(image_id, image_data);
+		if (rc != 0) {
+			return rc;
+		}
+
+		/*
+		 * Flush the image to main memory so that it can be executed
+		 * later by any CPU, regardless of cache and MMU state. This
+		 * is only needed for child images, not for the parents
+		 * (certificates).
+		 */
 		flush_dcache_range(image_data->image_base,
 				   image_data->image_size);
 	}
@@ -239,9 +253,18 @@
 {
 	int err;
 
+/*
+ * All firmware banks should be part of the same non-volatile storage as per
+ * PSA FWU specification, hence don't check for any alternate boot source
+ * when PSA FWU is enabled.
+ */
+#if PSA_FWU_SUPPORT
+	err = load_auth_image_internal(image_id, image_data);
+#else
 	do {
 		err = load_auth_image_internal(image_id, image_data);
 	} while ((err != 0) && (plat_try_next_boot_source() != 0));
+#endif /* PSA_FWU_SUPPORT */
 
 	return err;
 }
diff --git a/common/fdt_fixup.c b/common/fdt_fixup.c
index e88a550..de02b46 100644
--- a/common/fdt_fixup.c
+++ b/common/fdt_fixup.c
@@ -188,6 +188,8 @@
  *
  * See reserved-memory/reserved-memory.txt in the (Linux kernel) DT binding
  * documentation for details.
+ * According to this binding, the address-cells and size-cells must match
+ * those of the root node.
  *
  * Return: 0 on success, a negative error value otherwise.
  ******************************************************************************/
@@ -195,23 +197,37 @@
 			    uintptr_t base, size_t size)
 {
 	int offs = fdt_path_offset(dtb, "/reserved-memory");
-	uint32_t addresses[3];
+	uint32_t addresses[4];
+	int ac, sc;
+	unsigned int idx = 0;
 
+	ac = fdt_address_cells(dtb, 0);
+	sc = fdt_size_cells(dtb, 0);
 	if (offs < 0) {			/* create if not existing yet */
 		offs = fdt_add_subnode(dtb, 0, "reserved-memory");
-		if (offs < 0)
+		if (offs < 0) {
 			return offs;
-		fdt_setprop_u32(dtb, offs, "#address-cells", 2);
-		fdt_setprop_u32(dtb, offs, "#size-cells", 1);
+		}
+		fdt_setprop_u32(dtb, offs, "#address-cells", ac);
+		fdt_setprop_u32(dtb, offs, "#size-cells", sc);
 		fdt_setprop(dtb, offs, "ranges", NULL, 0);
 	}
 
-	addresses[0] = cpu_to_fdt32(HIGH_BITS(base));
-	addresses[1] = cpu_to_fdt32(base & 0xffffffff);
-	addresses[2] = cpu_to_fdt32(size & 0xffffffff);
+	if (ac > 1) {
+		addresses[idx] = cpu_to_fdt32(HIGH_BITS(base));
+		idx++;
+	}
+	addresses[idx] = cpu_to_fdt32(base & 0xffffffff);
+	idx++;
+	if (sc > 1) {
+		addresses[idx] = cpu_to_fdt32(HIGH_BITS(size));
+		idx++;
+	}
+	addresses[idx] = cpu_to_fdt32(size & 0xffffffff);
+	idx++;
 	offs = fdt_add_subnode(dtb, offs, node_name);
 	fdt_setprop(dtb, offs, "no-map", NULL, 0);
-	fdt_setprop(dtb, offs, "reg", addresses, 12);
+	fdt_setprop(dtb, offs, "reg", addresses, idx * sizeof(uint32_t));
 
 	return 0;
 }
@@ -382,6 +398,7 @@
  * fdt_adjust_gic_redist() - Adjust GICv3 redistributor size
  * @dtb: Pointer to the DT blob in memory
  * @nr_cores: Number of CPU cores on this system.
+ * @gicr_base: Base address of the first GICR frame, or ~0 if unchanged
  * @gicr_frame_size: Size of the GICR frame per core
  *
  * On a GICv3 compatible interrupt controller, the redistributor provides
@@ -394,17 +411,19 @@
  * A GICv4 compatible redistributor uses four 64K pages per core, whereas GICs
  * without support for direct injection of virtual interrupts use two 64K pages.
  * The @gicr_frame_size parameter should be 262144 and 131072, respectively.
+ * Also optionally allow adjusting the GICR frame base address, when this is
+ * different due to ITS frames between distributor and redistributor.
  *
  * Return: 0 on success, negative error value otherwise.
  */
 int fdt_adjust_gic_redist(void *dtb, unsigned int nr_cores,
-			  unsigned int gicr_frame_size)
+			  uintptr_t gicr_base, unsigned int gicr_frame_size)
 {
 	int offset = fdt_node_offset_by_compatible(dtb, 0, "arm,gic-v3");
-	uint64_t redist_size_64;
-	uint32_t redist_size_32;
+	uint64_t reg_64;
+	uint32_t reg_32;
 	void *val;
-	int parent;
+	int parent, ret;
 	int ac, sc;
 
 	if (offset < 0) {
@@ -421,13 +440,34 @@
 		return -EINVAL;
 	}
 
+	if (gicr_base != INVALID_BASE_ADDR) {
+		if (ac == 1) {
+			reg_32 = cpu_to_fdt32(gicr_base);
+			val = &reg_32;
+		} else {
+			reg_64 = cpu_to_fdt64(gicr_base);
+			val = &reg_64;
+		}
+		/*
+		 * The redistributor base address is the second address in
+		 * the "reg" entry, so we have to skip one address and one
+		 * size cell.
+		 */
+		ret = fdt_setprop_inplace_namelen_partial(dtb, offset,
+							  "reg", 3,
+							  (ac + sc) * 4,
+							  val, ac * 4);
+		if (ret < 0) {
+			return ret;
+		}
+	}
+
 	if (sc == 1) {
-		redist_size_32 = cpu_to_fdt32(nr_cores * gicr_frame_size);
-		val = &redist_size_32;
+		reg_32 = cpu_to_fdt32(nr_cores * gicr_frame_size);
+		val = &reg_32;
 	} else {
-		redist_size_64 = cpu_to_fdt64(nr_cores *
-					      (uint64_t)gicr_frame_size);
-		val = &redist_size_64;
+		reg_64 = cpu_to_fdt64(nr_cores * (uint64_t)gicr_frame_size);
+		val = &reg_64;
 	}
 
 	/*
diff --git a/common/fdt_wrappers.c b/common/fdt_wrappers.c
index 5aad14e..2a9673f 100644
--- a/common/fdt_wrappers.c
+++ b/common/fdt_wrappers.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,12 +7,16 @@
 /* Helper functions to offer easier navigation of Device Tree Blob */
 
 #include <assert.h>
+#include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <libfdt.h>
 
 #include <common/debug.h>
 #include <common/fdt_wrappers.h>
+#include <common/uuid.h>
 
 /*
  * Read cells from a given property of the given node. Any number of 32-bit
@@ -33,7 +37,7 @@
 	/* Access property and obtain its length (in bytes) */
 	prop = fdt_getprop(dtb, node, prop_name, &value_len);
 	if (prop == NULL) {
-		WARN("Couldn't find property %s in dtb\n", prop_name);
+		VERBOSE("Couldn't find property %s in dtb\n", prop_name);
 		return -FDT_ERR_NOTFOUND;
 	}
 
@@ -152,6 +156,39 @@
 }
 
 /*
+ * Read UUID from a given property of the given node. Returns 0 on success,
+ * and a negative value upon error.
+ */
+int fdtw_read_uuid(const void *dtb, int node, const char *prop,
+		   unsigned int length, uint8_t *uuid)
+{
+	/* Buffer for UUID string (plus NUL terminator) */
+	char uuid_string[UUID_STRING_LENGTH + 1U];
+	int err;
+
+	assert(dtb != NULL);
+	assert(prop != NULL);
+	assert(uuid != NULL);
+	assert(node >= 0);
+
+	if (length < UUID_BYTES_LENGTH) {
+		return -EINVAL;
+	}
+
+	err = fdtw_read_string(dtb, node, prop, uuid_string,
+			       UUID_STRING_LENGTH + 1U);
+	if (err != 0) {
+		return err;
+	}
+
+	if (read_uuid(uuid, uuid_string) != 0) {
+		return -FDT_ERR_BADVALUE;
+	}
+
+	return 0;
+}
+
+/*
  * Write cells in place to a given property of the given node. At most 2 cells
  * of the property are written. Returns 0 on success, and -1 upon error.
  */
@@ -367,7 +404,7 @@
 	addr_range = fdt_read_prop_cells(value + child_addr_size +
 				parent_addr_size,
 				range_size);
-	VERBOSE("DT: Address %llx mapped to %llx with range %llx\n",
+	VERBOSE("DT: Address %" PRIx64 " mapped to %" PRIx64 " with range %" PRIx64 "\n",
 		local_address, parent_address, addr_range);
 
 	/* Perform range check */
@@ -378,8 +415,8 @@
 
 	/* Found hit for the addr range that needs to be translated */
 	*translated_addr = parent_address + (base_address - local_address);
-	VERBOSE("DT: child address %llx mapped to %llx in parent bus\n",
-			local_address, parent_address);
+	VERBOSE("DT: child address %" PRIx64 "mapped to %" PRIx64 " in parent bus\n",
+		local_address, parent_address);
 	return true;
 }
 
@@ -435,8 +472,8 @@
 		next_entry = next_entry + ncells_xlat;
 	}
 
-	INFO("DT: No translation found for address %llx in node %s\n",
-		base_address, fdt_get_name(dtb, local_bus, NULL));
+	INFO("DT: No translation found for address %" PRIx64 " in node %s\n",
+	     base_address, fdt_get_name(dtb, local_bus, NULL));
 	return ILLEGAL_ADDR;
 }
 
@@ -537,3 +574,47 @@
 	/* Translate the local device address recursively */
 	return fdtw_translate_address(dtb, local_bus_node, global_address);
 }
+
+/*
+ * For every CPU node (`/cpus/cpu@n`) in an FDT, execute a callback passing a
+ * pointer to the FDT and the offset of the CPU node. If the return value of the
+ * callback is negative, it is treated as an error and the loop is aborted. In
+ * this situation, the value of the callback is returned from the function.
+ *
+ * Returns `0` on success, or a negative integer representing an error code.
+ */
+int fdtw_for_each_cpu(const void *dtb,
+		      int (*callback)(const void *dtb, int node, uintptr_t mpidr))
+{
+	int ret = 0;
+	int parent, node = 0;
+
+	parent = fdt_path_offset(dtb, "/cpus");
+	if (parent < 0) {
+		return parent;
+	}
+
+	fdt_for_each_subnode(node, dtb, parent) {
+		const char *name;
+		int len;
+
+		uintptr_t mpidr = 0U;
+
+		name = fdt_get_name(dtb, node, &len);
+		if (strncmp(name, "cpu@", 4) != 0) {
+			continue;
+		}
+
+		ret = fdt_get_reg_props_by_index(dtb, node, 0, &mpidr, NULL);
+		if (ret < 0) {
+			break;
+		}
+
+		ret = callback(dtb, node, mpidr);
+		if (ret < 0) {
+			break;
+		}
+	}
+
+	return ret;
+}
diff --git a/common/fdt_wrappers.mk b/common/fdt_wrappers.mk
new file mode 100644
index 0000000..62b8c6e
--- /dev/null
+++ b/common/fdt_wrappers.mk
@@ -0,0 +1,7 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+FDT_WRAPPERS_SOURCES	:=	common/fdt_wrappers.c
diff --git a/common/tf_crc32.c b/common/tf_crc32.c
new file mode 100644
index 0000000..b33d36e
--- /dev/null
+++ b/common/tf_crc32.c
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdarg.h>
+#include <assert.h>
+
+#include <arm_acle.h>
+#include <common/debug.h>
+#include <common/tf_crc32.h>
+
+/* compute CRC using Arm intrinsic function
+ *
+ * This function is useful for the platforms with the CPU ARMv8.0
+ * (with CRC instructions supported), and onwards.
+ * Platforms with CPU ARMv8.0 should make sure to add a compile switch
+ * '-march=armv8-a+crc" for successful compilation of this file.
+ *
+ * @crc: previous accumulated CRC
+ * @buf: buffer base address
+ * @size: the size of the buffer
+ *
+ * Return calculated CRC value
+ */
+uint32_t tf_crc32(uint32_t crc, const unsigned char *buf, size_t size)
+{
+	assert(buf != NULL);
+
+	uint32_t calc_crc = ~crc;
+	const unsigned char *local_buf = buf;
+	size_t local_size = size;
+
+	/*
+	 * calculate CRC over byte data
+	 */
+	while (local_size != 0UL) {
+		calc_crc = __crc32b(calc_crc, *local_buf);
+		local_buf++;
+		local_size--;
+	}
+
+	return ~calc_crc;
+}
diff --git a/common/tf_log.c b/common/tf_log.c
index 08d3cf4..68f1be4 100644
--- a/common/tf_log.c
+++ b/common/tf_log.c
@@ -49,6 +49,20 @@
 	va_end(args);
 }
 
+void tf_log_newline(const char log_fmt[2])
+{
+	unsigned int log_level = log_fmt[0];
+
+	/* Verify that log_level is one of LOG_MARKER_* macro defined in debug.h */
+	assert((log_level > 0U) && (log_level <= LOG_LEVEL_VERBOSE));
+	assert((log_level % 10U) == 0U);
+
+	if (log_level > max_log_level)
+		return;
+
+	putchar('\n');
+}
+
 /*
  * The helper function to set the log level dynamically by platform. The
  * maximum log level is determined by `LOG_LEVEL` build flag at compile time
diff --git a/common/uuid.c b/common/uuid.c
new file mode 100644
index 0000000..ac6db50
--- /dev/null
+++ b/common/uuid.c
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <common/uuid.h>
+
+/* Return the hex nibble value of a char */
+static int8_t hex_val(char hex)
+{
+	int8_t val = 0;
+
+	if ((hex >= '0') && (hex <= '9')) {
+		val = (int8_t)(hex - '0');
+	} else if ((hex >= 'a') && (hex <= 'f')) {
+		val = (int8_t)(hex - 'a' + 0xa);
+	} else if ((hex >= 'A') && (hex <= 'F')) {
+		val = (int8_t)(hex - 'A' + 0xa);
+	} else {
+		val = -1;
+	}
+
+	return val;
+}
+
+/*
+ * Read hex_src_len hex characters from hex_src, convert to bytes and
+ * store in buffer pointed to by dest
+ */
+static int read_hex(uint8_t *dest, char *hex_src, unsigned int hex_src_len)
+{
+	int8_t nibble;
+	uint8_t byte;
+
+	/*
+	 * The string length must be a multiple of 2 to represent an
+	 * exact number of bytes.
+	 */
+	assert((hex_src_len % 2U) == 0U);
+
+	for (unsigned int i = 0U; i < (hex_src_len / 2U); i++) {
+		nibble = 0;
+		byte = 0U;
+
+		nibble = hex_val(hex_src[2U * i]);
+		if (nibble < 0) {
+			return -1;
+		}
+		byte = (uint8_t)nibble;
+		byte <<= 4U;
+
+		nibble = hex_val(hex_src[(2U * i) + 1U]);
+		if (nibble < 0) {
+			return -1;
+		}
+		byte |= (uint8_t)nibble;
+
+		*dest = byte;
+		dest++;
+	}
+
+	return 0;
+}
+
+/* Parse UUIDs of the form aabbccdd-eeff-4099-8877-665544332211 */
+int read_uuid(uint8_t *dest, char *uuid)
+{
+	int err;
+	uint8_t *dest_start = dest;
+
+	/* Check that we have enough characters */
+	if (strnlen(uuid, UUID_STRING_LENGTH) != UUID_STRING_LENGTH) {
+		WARN("UUID string is too short\n");
+		return -EINVAL;
+	}
+
+	/* aabbccdd */
+	err = read_hex(dest, uuid, 8);
+	uuid += 8;
+	dest += 4;
+
+	/* Check for '-' */
+	err |= ((*uuid == '-') ? 0 : -1);
+	uuid++;
+
+	/* eeff */
+	err |= read_hex(dest, uuid, 4);
+	uuid += 4;
+	dest += 2;
+
+	/* Check for '-' */
+	err |= ((*uuid == '-') ? 0 : -1);
+	uuid++;
+
+	/* 4099 */
+	err |= read_hex(dest, uuid, 4);
+	uuid += 4;
+	dest += 2;
+
+	/* Check for '-' */
+	err |= ((*uuid == '-') ? 0 : -1);
+	uuid++;
+
+	/* 8877 */
+	err |= read_hex(dest, uuid, 4);
+	uuid += 4;
+	dest += 2;
+
+	/* Check for '-' */
+	err |= ((*uuid == '-') ? 0 : -1);
+	uuid++;
+
+	/* 665544332211 */
+	err |= read_hex(dest, uuid, 12);
+	uuid += 12;
+	dest += 6;
+
+	if (err < 0) {
+		WARN("Error parsing UUID\n");
+		/* Clear the buffer on error */
+		memset((void *)dest_start, '\0', UUID_BYTES_LENGTH * sizeof(uint8_t));
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
diff --git a/docs/_static/css/custom.css b/docs/_static/css/custom.css
new file mode 100644
index 0000000..f6f5fa0
--- /dev/null
+++ b/docs/_static/css/custom.css
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/*
+ * Set the white-space property of tables to normal.
+ * With this setting sequences of whitespace inside
+ * a table will collapse into a single whitespace,
+ * and text will wrap when necessary.
+ */
+.wy-table-responsive table td {
+white-space: normal;
+}
diff --git a/docs/about/features.rst b/docs/about/features.rst
index 964cb25..4b7fbe5 100644
--- a/docs/about/features.rst
+++ b/docs/about/features.rst
@@ -74,7 +74,7 @@
    loading of a hardware configuration (for example, a kernel device tree)
    as part of the FIP, to be passed through the firmware stages.
    This feature is now incorporated inside the firmware configuration framework
-   (fconf), which is still flagged as experimental.
+   (fconf).
 
 -  Support for alternative boot flows, for example to support platforms where
    the EL3 Runtime Software is loaded using other firmware or a separate
@@ -94,9 +94,7 @@
 -  Support for ARMv8.3 pointer authentication in the normal and secure worlds.
    The use of pointer authentication in the normal world is enabled whenever
    architectural support is available, without the need for additional build
-   flags. Use of pointer authentication in the secure world remains an
-   experimental configuration at this time and requires the
-   ``BRANCH_PROTECTION`` option to be set to non-zero.
+   flags.
 
 -  Position-Independent Executable (PIE) support. Currently for BL2, BL31, and
    TSP, with further support to be added in a future release.
@@ -108,7 +106,7 @@
 
 -  Refinements to Position Independent Executable (PIE) support.
 
--  Continued support for the PSA FF-A v1.0 (formally known as SPCI) specification, to enable the
+-  Continued support for the FF-A v1.0 (formally known as SPCI) specification, to enable the
    use of secure partition management in the secure world.
 
 -  Documentation enhancements.
@@ -126,4 +124,4 @@
 
 --------------
 
-*Copyright (c) 2019-2020, Arm Limited. All rights reserved.*
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
diff --git a/docs/about/maintainers.rst b/docs/about/maintainers.rst
index ab2d3f9..7a48601 100644
--- a/docs/about/maintainers.rst
+++ b/docs/about/maintainers.rst
@@ -9,42 +9,45 @@
 
 More details may be found in the `Project Maintenance Process`_ document.
 
+.. |M| replace:: **Mail**
+.. |G| replace:: **GitHub ID**
+.. |F| replace:: **Files**
 
 .. _maintainers:
 
 Maintainers
 -----------
 
-:M: Dan Handley <dan.handley@arm.com>
-:G: `danh-arm`_
-:M: Soby Mathew <soby.mathew@arm.com>
-:G: `soby-mathew`_
-:M: Sandrine Bailleux <sandrine.bailleux@arm.com>
-:G: `sandrine-bailleux-arm`_
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:M: Mark Dykes <mark.dykes@arm.com>
-:G: `mardyk01`_
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:M: Bipin Ravi <bipin.ravi@arm.com>
-:G: `bipinravi-arm`_
-:M: Joanna Farley <joanna.farley@arm.com>
-:G: `joannafarley-arm`_
-:M: Julius Werner <jwerner@chromium.org>
-:G: `jwerner-chromium`_
-:M: Varun Wadekar <vwadekar@nvidia.com>
-:G: `vwadekar`_
-:M: Andre Przywara <andre.przywara@arm.com>
-:G: `Andre-ARM`_
-:M: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
-:G: `laurenw-arm`_
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:M: Raghu Krishnamurthy <raghu.ncstate@icloud.com>
-:G: `raghuncstate`_
+:|M|: Dan Handley <dan.handley@arm.com>
+:|G|: `danh-arm`_
+:|M|: Soby Mathew <soby.mathew@arm.com>
+:|G|: `soby-mathew`_
+:|M|: Sandrine Bailleux <sandrine.bailleux@arm.com>
+:|G|: `sandrine-bailleux-arm`_
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Mark Dykes <mark.dykes@arm.com>
+:|G|: `mardyk01`_
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|M|: Bipin Ravi <bipin.ravi@arm.com>
+:|G|: `bipinravi-arm`_
+:|M|: Joanna Farley <joanna.farley@arm.com>
+:|G|: `joannafarley-arm`_
+:|M|: Julius Werner <jwerner@chromium.org>
+:|G|: `jwerner-chromium`_
+:|M|: Varun Wadekar <vwadekar@nvidia.com>
+:|G|: `vwadekar`_
+:|M|: Andre Przywara <andre.przywara@arm.com>
+:|G|: `Andre-ARM`_
+:|M|: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
+:|G|: `laurenw-arm`_
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|M|: Raghu Krishnamurthy <raghu.ncstate@icloud.com>
+:|G|: `raghuncstate`_
 
 
 .. _code owners:
@@ -52,487 +55,621 @@
 Code owners
 -----------
 
-Core Code
-~~~~~~~~~
+Common Code
+~~~~~~~~~~~
 
 Armv7-A architecture port
 ^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Etienne Carriere <etienne.carriere@linaro.org>
-:G: `etienne-lms`_
+:|M|: Etienne Carriere <etienne.carriere@linaro.org>
+:|G|: `etienne-lms`_
 
 Build Definitions for CMake Build System
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
-:G: `javieralso-arm`_
-:M: Chris Kay <chris.kay@arm.com>
-:G: `CJkay`_
-:F: /
+:|M|: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
+:|G|: `javieralso-arm`_
+:|M|: Chris Kay <chris.kay@arm.com>
+:|G|: `CJKay`_
+:|F|: /
 
 Software Delegated Exception Interface (SDEI)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Mark Dykes <mark.dykes@arm.com>
-:G: `mardyk01`_
-:M: John Powell <John.Powell@arm.com>
-:G: `john-powell-arm`_
-:F: services/std_svc/sdei/
+:|M|: Mark Dykes <mark.dykes@arm.com>
+:|G|: `mardyk01`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|F|: services/std_svc/sdei/
 
 Trusted Boot
 ^^^^^^^^^^^^
-:M: Sandrine Bailleux <sandrine.bailleux@arm.com>
-:G: `sandrine-bailleux-arm`_
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:M: Manish Badarkhe <manish.badarkhe@arm.com>
-:G: `ManishVB-Arm`_
-:F: drivers/auth/
+:|M|: Sandrine Bailleux <sandrine.bailleux@arm.com>
+:|G|: `sandrine-bailleux-arm`_
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Manish Badarkhe <manish.badarkhe@arm.com>
+:|G|: `ManishVB-Arm`_
+:|F|: drivers/auth/
 
 Secure Partition Manager (SPM)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:M: Maksims Svecovs <maksims.svecovs@arm.com>
-:G: `max-shvetsov`_
-:M: Joao Alves <Joao.Alves@arm.com>
-:G: `J-Alves`_
-:F: services/std_svc/spm\*
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Maksims Svecovs <maksims.svecovs@arm.com>
+:|G|: `max-shvetsov`_
+:|M|: Joao Alves <Joao.Alves@arm.com>
+:|G|: `J-Alves`_
+:|F|: services/std_svc/spm\*
 
 Exception Handling Framework (EHF)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Manish Badarkhe <manish.badarkhe@arm.com>
-:G: `ManishVB-Arm`_
-:M: John Powell <John.Powell@arm.com>
-:G: `john-powell-arm`_
-:F: bl31/ehf.c
+:|M|: Manish Badarkhe <manish.badarkhe@arm.com>
+:|G|: `ManishVB-Arm`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|F|: bl31/ehf.c
 
+Realm Management Extension (RME)
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Bipin Ravi <bipin.ravi@arm.com>
+:|G|: `bipinravi-arm`_
+:|M|: Mark Dykes <mark.dykes@arm.com>
+:|G|: `mardyk01`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
 
 Drivers, Libraries and Framework Code
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 Console API framework
 ^^^^^^^^^^^^^^^^^^^^^
-:M: Julius Werner <jwerner@chromium.org>
-:G: `jwerner-chromium`_
-:F: drivers/console/
-:F: include/drivers/console.h
-:F: plat/common/aarch64/crash_console_helpers.S
+:|M|: Julius Werner <jwerner@chromium.org>
+:|G|: `jwerner-chromium`_
+:|F|: drivers/console/
+:|F|: include/drivers/console.h
+:|F|: plat/common/aarch64/crash_console_helpers.S
 
 coreboot support libraries
 ^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Julius Werner <jwerner@chromium.org>
-:G: `jwerner-chromium`_
-:F: drivers/coreboot/
-:F: include/drivers/coreboot/
-:F: include/lib/coreboot.h
-:F: lib/coreboot/
+:|M|: Julius Werner <jwerner@chromium.org>
+:|G|: `jwerner-chromium`_
+:|F|: drivers/coreboot/
+:|F|: include/drivers/coreboot/
+:|F|: include/lib/coreboot.h
+:|F|: lib/coreboot/
 
 eMMC/UFS drivers
 ^^^^^^^^^^^^^^^^
-:M: Haojian Zhuang <haojian.zhuang@linaro.org>
-:G: `hzhuang1`_
-:F: drivers/partition/
-:F: drivers/synopsys/emmc/
-:F: drivers/synopsys/ufs/
-:F: drivers/ufs/
-:F: include/drivers/dw_ufs.h
-:F: include/drivers/ufs.h
-:F: include/drivers/synopsys/dw_mmc.h
+:|M|: Haojian Zhuang <haojian.zhuang@linaro.org>
+:|G|: `hzhuang1`_
+:|F|: drivers/partition/
+:|F|: drivers/synopsys/emmc/
+:|F|: drivers/synopsys/ufs/
+:|F|: drivers/ufs/
+:|F|: include/drivers/dw_ufs.h
+:|F|: include/drivers/ufs.h
+:|F|: include/drivers/synopsys/dw_mmc.h
+
+JTAG DCC console driver
+^^^^^^^^^^^^^^^^^^^^^^^
+:M: Michal Simek <michal.simek@xilinx.com>
+:G: `michalsimek`_
+:M: Venkatesh Yadav Abbarapu <venkatesh.abbarapu@xilinx.com>
+:G: `venkatesh`_
+:F: drivers/arm/dcc/
+:F: include/drivers/arm/dcc.h
 
 Power State Coordination Interface (PSCI)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
-:G: `javieralso-arm`_
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:M: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
-:G: `laurenw-arm`_
-:M: Zelalem Aweke <Zelalem.Aweke@arm.com>
-:G: `zelalem-aweke`_
-:F: lib/psci/
+:|M|: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
+:|G|: `javieralso-arm`_
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|M|: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
+:|G|: `laurenw-arm`_
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
+:|F|: lib/psci/
 
 DebugFS
 ^^^^^^^
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:F: lib/debugfs/
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|F|: lib/debugfs/
 
 Firmware Configuration Framework (FCONF)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:M: Manish Badarkhe <manish.badarkhe@arm.com>
-:G: `ManishVB-Arm`_
-:M: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
-:G: `laurenw-arm`_
-:F: lib/fconf/
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|M|: Manish Badarkhe <manish.badarkhe@arm.com>
+:|G|: `ManishVB-Arm`_
+:|M|: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
+:|G|: `laurenw-arm`_
+:|F|: lib/fconf/
 
 Performance Measurement Framework (PMF)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Joao Alves <Joao.Alves@arm.com>
-:G: `J-Alves`_
-:M: Jimmy Brisson <Jimmy.Brisson@arm.com>
-:G: `theotherjimmy`_
-:F: lib/pmf/
+:|M|: Joao Alves <Joao.Alves@arm.com>
+:|G|: `J-Alves`_
+:|M|: Jimmy Brisson <Jimmy.Brisson@arm.com>
+:|G|: `theotherjimmy`_
+:|F|: lib/pmf/
 
 Arm CPU libraries
 ^^^^^^^^^^^^^^^^^
-:M: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
-:G: `laurenw-arm`_
-:M: John Powell <John.Powell@arm.com>
-:G: `john-powell-arm`_
-:F: lib/cpus/
+:|M|: Lauren Wehrmeister <Lauren.Wehrmeister@arm.com>
+:|G|: `laurenw-arm`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|F|: lib/cpus/
 
 Reliability Availability Serviceabilty (RAS) framework
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:F: lib/extensions/ras/
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|F|: lib/extensions/ras/
 
 Activity Monitors Unit (AMU) extensions
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:F: lib/extensions/amu/
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: Chris Kay <chris.kay@arm.com>
+:|G|: `CJKay`_
+:|F|: lib/extensions/amu/
 
 Memory Partitioning And Monitoring (MPAM) extensions
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Zelalem Aweke <Zelalem.Aweke@arm.com>
-:G: `zelalem-aweke`_
-:M: Jimmy Brisson <Jimmy.Brisson@arm.com>
-:G: `theotherjimmy`_
-:F: lib/extensions/mpam/
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
+:|M|: Jimmy Brisson <Jimmy.Brisson@arm.com>
+:|G|: `theotherjimmy`_
+:|F|: lib/extensions/mpam/
 
 Pointer Authentication (PAuth) and Branch Target Identification (BTI) extensions
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:M: Zelalem Aweke <Zelalem.Aweke@arm.com>
-:G: `zelalem-aweke`_
-:F: lib/extensions/pauth/
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
+:|F|: lib/extensions/pauth/
 
 Statistical Profiling Extension (SPE)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Zelalem Aweke <Zelalem.Aweke@arm.com>
-:G: `zelalem-aweke`_
-:M: Jimmy Brisson <Jimmy.Brisson@arm.com>
-:G: `theotherjimmy`_
-:F: lib/extensions/spe/
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
+:|M|: Jimmy Brisson <Jimmy.Brisson@arm.com>
+:|G|: `theotherjimmy`_
+:|F|: lib/extensions/spe/
 
 Scalable Vector Extension (SVE)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Jimmy Brisson <Jimmy.Brisson@arm.com>
-:G: `theotherjimmy`_
-:F: lib/extensions/sve/
+:|M|: Jimmy Brisson <Jimmy.Brisson@arm.com>
+:|G|: `theotherjimmy`_
+:|F|: lib/extensions/sve/
 
 Standard C library
 ^^^^^^^^^^^^^^^^^^
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:M: John Powell <John.Powell@arm.com>
-:G: `john-powell-arm`_
-:F: lib/libc/
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|F|: lib/libc/
 
 Library At ROM (ROMlib)
 ^^^^^^^^^^^^^^^^^^^^^^^
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:F: lib/romlib/
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|F|: lib/romlib/
 
 Translation tables (``xlat_tables``) library
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
-:G: `javieralso-arm`_
-:M: Joao Alves <Joao.Alves@arm.com>
-:G: `J-Alves`_
-:F: lib/xlat\_tables_\*/
+:|M|: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
+:|G|: `javieralso-arm`_
+:|M|: Joao Alves <Joao.Alves@arm.com>
+:|G|: `J-Alves`_
+:|F|: lib/xlat\_tables_\*/
 
 IO abstraction layer
 ^^^^^^^^^^^^^^^^^^^^
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:F: drivers/io/
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|F|: drivers/io/
 
 GIC driver
 ^^^^^^^^^^
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:M: Olivier Deprez <olivier.deprez@arm.com>
-:G: `odeprez`_
-:F: drivers/arm/gic/
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|M|: Olivier Deprez <olivier.deprez@arm.com>
+:|G|: `odeprez`_
+:|F|: drivers/arm/gic/
 
 Libfdt wrappers
 ^^^^^^^^^^^^^^^
-:M: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
-:G: `madhukar-Arm`_
-:M: Manish Badarkhe <manish.badarkhe@arm.com>
-:G: `ManishVB-Arm`_
-:F: common/fdt_wrappers.c
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|M|: Manish Badarkhe <manish.badarkhe@arm.com>
+:|G|: `ManishVB-Arm`_
+:|F|: common/fdt_wrappers.c
 
 Firmware Encryption Framework
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Sumit Garg <sumit.garg@linaro.org>
-:G: `b49020`_
-:F: drivers/io/io_encrypted.c
-:F: include/drivers/io/io_encrypted.h
-:F: include/tools_share/firmware_encrypted.h
+:|M|: Sumit Garg <sumit.garg@linaro.org>
+:|G|: `b49020`_
+:|F|: drivers/io/io_encrypted.c
+:|F|: include/drivers/io/io_encrypted.h
+:|F|: include/tools_share/firmware_encrypted.h
 
 Measured Boot
 ^^^^^^^^^^^^^
-:M: Alexei Fedorov <Alexei.Fedorov@arm.com>
-:G: `AlexeiFedorov`_
-:M: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
-:G: `javieralso-arm`_
-:F: drivers/measured_boot
-:F: include/drivers/measured_boot
-:F: plat/arm/board/fvp/fvp_measured_boot.c
+:|M|: Alexei Fedorov <Alexei.Fedorov@arm.com>
+:|G|: `AlexeiFedorov`_
+:|M|: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
+:|G|: `javieralso-arm`_
+:|F|: drivers/measured_boot
+:|F|: include/drivers/measured_boot
+:|F|: plat/arm/board/fvp/fvp_measured_boot.c
+
+System Control and Management Interface (SCMI) Server
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Etienne Carriere <etienne.carriere@st.com>
+:|G|: `etienne-lms`_
+:|M|: Peng Fan <peng.fan@nxp.com>
+:|G|: `MrVan`_
+:|F|: drivers/scmi-msg
+:|F|: include/drivers/scmi\*
+
+Max Power Mitigation Mechanism (MPMM)
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Chris Kay <chris.kay@arm.com>
+:|G|: `CJKay`_
+:|F|: include/lib/mpmm/
+:|F|: lib/mpmm/
+
+Granule Protection Tables Library (GPT-RME)
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Mark Dykes <mark.dykes@arm.com>
+:|G|: `mardyk01`_
+:|M|: John Powell <john.powell@arm.com>
+:|G|: `john-powell-arm`_
+:|F|: lib/gpt_rme
+:|F|: include/lib/gpt_rme
 
 Platform Ports
 ~~~~~~~~~~~~~~
 
 Allwinner ARMv8 platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Andre Przywara <andre.przywara@arm.com>
-:G: `Andre-ARM`_
-:M: Samuel Holland <samuel@sholland.org>
-:G: `smaeul`_
-:F: docs/plat/allwinner.rst
-:F: plat/allwinner/
-:F: drivers/allwinner/
+:|M|: Andre Przywara <andre.przywara@arm.com>
+:|G|: `Andre-ARM`_
+:|M|: Samuel Holland <samuel@sholland.org>
+:|G|: `smaeul`_
+:|F|: docs/plat/allwinner.rst
+:|F|: plat/allwinner/
+:|F|: drivers/allwinner/
 
 Amlogic Meson S905 (GXBB) platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Andre Przywara <andre.przywara@arm.com>
-:G: `Andre-ARM`_
-:F: docs/plat/meson-gxbb.rst
-:F: drivers/amlogic/
-:F: plat/amlogic/gxbb/
+:|M|: Andre Przywara <andre.przywara@arm.com>
+:|G|: `Andre-ARM`_
+:|F|: docs/plat/meson-gxbb.rst
+:|F|: drivers/amlogic/
+:|F|: plat/amlogic/gxbb/
 
 Amlogic Meson S905x (GXL) platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Remi Pommarel <repk@triplefau.lt>
-:G: `remi-triplefault`_
-:F: docs/plat/meson-gxl.rst
-:F: plat/amlogic/gxl/
+:|M|: Remi Pommarel <repk@triplefau.lt>
+:|G|: `remi-triplefault`_
+:|F|: docs/plat/meson-gxl.rst
+:|F|: plat/amlogic/gxl/
 
 Amlogic Meson S905X2 (G12A) platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Carlo Caione <ccaione@baylibre.com>
-:G: `carlocaione`_
-:F: docs/plat/meson-g12a.rst
-:F: plat/amlogic/g12a/
+:|M|: Carlo Caione <ccaione@baylibre.com>
+:|G|: `carlocaione`_
+:|F|: docs/plat/meson-g12a.rst
+:|F|: plat/amlogic/g12a/
 
 Amlogic Meson A113D (AXG) platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Carlo Caione <ccaione@baylibre.com>
-:G: `carlocaione`_
-:F: docs/plat/meson-axg.rst
-:F: plat/amlogic/axg/
+:|M|: Carlo Caione <ccaione@baylibre.com>
+:|G|: `carlocaione`_
+:|F|: docs/plat/meson-axg.rst
+:|F|: plat/amlogic/axg/
 
 Arm FPGA platform port
 ^^^^^^^^^^^^^^^^^^^^^^
-:M: Andre Przywara <andre.przywara@arm.com>
-:G: `Andre-ARM`_
-:M: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
-:G: `javieralso-arm`_
-:F: plat/arm/board/arm_fpga
+:|M|: Andre Przywara <andre.przywara@arm.com>
+:|G|: `Andre-ARM`_
+:|M|: Javier Almansa Sobrino <Javier.AlmansaSobrino@arm.com>
+:|G|: `javieralso-arm`_
+:|F|: plat/arm/board/arm_fpga
 
-Arm System Guidance for Infrastructure / Mobile FVP platforms
-^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Nariman Poushin <nariman.poushin@linaro.org>
-:G: `npoushin`_
-:M: Thomas Abraham <thomas.abraham@arm.com>
-:G: `thomas-arm`_
-:F: plat/arm/css/sgi/
-:F: plat/arm/css/sgm/
-:F: plat/arm/board/sgi575/
-:F: plat/arm/board/sgm775/
+Arm FVP Platform port
+^^^^^^^^^^^^^^^^^^^^^
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Madhukar Pappireddy <Madhukar.Pappireddy@arm.com>
+:|G|: `madhukar-Arm`_
+:|F|: plat/arm/board/fvp
+
+Arm Juno Platform port
+^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|M|: Chris Kay <chris.kay@arm.com>
+:|G|: `CJKay`_
+:|F|: plat/arm/board/juno
+
+Arm Morello and N1SDP Platform ports
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Manoj Kumar <manoj.kumar3@arm.com>
+:|G|: `manojkumar-arm`_
+:|M|: Chandni Cherukuri <chandni.cherukuri@arm.com>
+:|G|: `chandnich`_
+:|F|: plat/arm/board/morello
+:|F|: plat/arm/board/n1sdp
+
+Arm Rich IoT Platform ports
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Abdellatif El Khlifi <abdellatif.elkhlifi@arm.com>
+:|G|: `abdellatif-elkhlifi`_
+:|M|: Vishnu Banavath <vishnu.banavath@arm.com>
+:|G|: `vishnu-banavath`_
+:|F|: plat/arm/board/corstone700
+:|F|: plat/arm/board/a5ds
+:|F|: plat/arm/board/diphda
+
+Arm Reference Design platform ports
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Thomas Abraham <thomas.abraham@arm.com>
+:|G|: `thomas-arm`_
+:|M|: Vijayenthiran Subramaniam <vijayenthiran.subramaniam@arm.com>
+:|G|: `vijayenthiran-arm`_
+:|F|: plat/arm/css/sgi/
+:|F|: plat/arm/board/rde1edge/
+:|F|: plat/arm/board/rdn1edge/
+:|F|: plat/arm/board/rdn2/
+:|F|: plat/arm/board/rdv1/
+:|F|: plat/arm/board/rdv1mc/
+:|F|: plat/arm/board/sgi575/
+
+Arm Total Compute platform port
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Arunachalam Ganapathy <arunachalam.ganapathy@arm.com>
+:|G|: `arugan02`_
+:|M|: Usama Arif <usama.arif@arm.com>
+:|G|: `uarif1`_
+:|F|: plat/arm/board/tc
 
 HiSilicon HiKey and HiKey960 platform ports
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Haojian Zhuang <haojian.zhuang@linaro.org>
-:G: `hzhuang1`_
-:F: docs/plat/hikey.rst
-:F: docs/plat/hikey960.rst
-:F: plat/hisilicon/hikey/
-:F: plat/hisilicon/hikey960/
+:|M|: Haojian Zhuang <haojian.zhuang@linaro.org>
+:|G|: `hzhuang1`_
+:|F|: docs/plat/hikey.rst
+:|F|: docs/plat/hikey960.rst
+:|F|: plat/hisilicon/hikey/
+:|F|: plat/hisilicon/hikey960/
 
 HiSilicon Poplar platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Shawn Guo <shawn.guo@linaro.org>
-:G: `shawnguo2`_
-:F: docs/plat/poplar.rst
-:F: plat/hisilicon/poplar/
+:|M|: Shawn Guo <shawn.guo@linaro.org>
+:|G|: `shawnguo2`_
+:|F|: docs/plat/poplar.rst
+:|F|: plat/hisilicon/poplar/
 
 Intel SocFPGA platform ports
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Tien Hock Loh <tien.hock.loh@intel.com>
-:G: `thloh85-intel`_
-:M: Hadi Asyrafi <muhammad.hadi.asyrafi.abdul.halim@intel.com>
-:G: mabdulha
-:F: plat/intel/soc
-:F: drivers/intel/soc/
+:|M|: Tien Hock Loh <tien.hock.loh@intel.com>
+:|G|: `thloh85-intel`_
+:|M|: Hadi Asyrafi <muhammad.hadi.asyrafi.abdul.halim@intel.com>
+:|G|: mabdulha
+:|F|: plat/intel/soc
+:|F|: drivers/intel/soc/
 
 MediaTek platform ports
 ^^^^^^^^^^^^^^^^^^^^^^^
-:M: Yidi Lin (林以廸) <yidi.lin@mediatek.com>
-:G: `mtk09422`_
-:F: plat/mediatek/
+:|M|: Rex-BC Chen <rex-bc.chen@mediatek.com>
+:|G|: `mtk-rex-bc-chen`_
+:|F|: plat/mediatek/
 
 Marvell platform ports and SoC drivers
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Konstantin Porotchkin <kostap@marvell.com>
-:G: `kostapr`_
-:F: docs/plat/marvell/
-:F: plat/marvell/
-:F: drivers/marvell/
-:F: tools/marvell/
+:|M|: Konstantin Porotchkin <kostap@marvell.com>
+:|G|: `kostapr`_
+:|F|: docs/plat/marvell/
+:|F|: plat/marvell/
+:|F|: drivers/marvell/
+:|F|: tools/marvell/
 
 NVidia platform ports
 ^^^^^^^^^^^^^^^^^^^^^
-:M: Varun Wadekar <vwadekar@nvidia.com>
-:G: `vwadekar`_
-:F: docs/plat/nvidia-tegra.rst
-:F: include/lib/cpus/aarch64/denver.h
-:F: lib/cpus/aarch64/denver.S
-:F: plat/nvidia/
+:|M|: Varun Wadekar <vwadekar@nvidia.com>
+:|G|: `vwadekar`_
+:|F|: docs/plat/nvidia-tegra.rst
+:|F|: include/lib/cpus/aarch64/denver.h
+:|F|: lib/cpus/aarch64/denver.S
+:|F|: plat/nvidia/
 
 NXP QorIQ Layerscape platform ports
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Jiafei Pan <jiafei.pan@nxp.com>
-:G: `qoriq-open-source`_
-:F: docs/plat/ls1043a.rst
-:F: plat/layerscape/
+:|M|: Jiafei Pan <jiafei.pan@nxp.com>
+:|G|: `qoriq-open-source`_
+:|F|: docs/plat/ls1043a.rst
+:|F|: plat/layerscape/
 
 NXP i.MX 7 WaRP7 platform port and SoC drivers
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
-:G: `bryanodonoghue`_
-:M: Jun Nie <jun.nie@linaro.org>
-:G: `niej`_
-:F: docs/plat/warp7.rst
-:F: plat/imx/common/
-:F: plat/imx/imx7/
-:F: drivers/imx/timer/
-:F: drivers/imx/uart/
-:F: drivers/imx/usdhc/
+:|M|: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
+:|G|: `bryanodonoghue`_
+:|M|: Jun Nie <jun.nie@linaro.org>
+:|G|: `niej`_
+:|F|: docs/plat/warp7.rst
+:|F|: plat/imx/common/
+:|F|: plat/imx/imx7/
+:|F|: drivers/imx/timer/
+:|F|: drivers/imx/uart/
+:|F|: drivers/imx/usdhc/
 
 NXP i.MX 8 platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Anson Huang <Anson.Huang@nxp.com>
-:G: `Anson-Huang`_
-:F: docs/plat/imx8.rst
-:F: plat/imx/
+:|M|: Peng Fan <peng.fan@nxp.com>
+:|G|: `MrVan`_
+:|F|: docs/plat/imx8.rst
+:|F|: plat/imx/
 
 NXP i.MX8M platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Jacky Bai <ping.bai@nxp.com>
-:G: `JackyBai`_
-:F: docs/plat/imx8m.rst
-:F: plat/imx/imx8m/
+:|M|: Jacky Bai <ping.bai@nxp.com>
+:|G|: `JackyBai`_
+:|F|: docs/plat/imx8m.rst
+:|F|: plat/imx/imx8m/
+
+NXP QorIQ Layerscape common code for platform ports
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Pankaj Gupta <pankaj.gupta@nxp.com>
+:|G|: `pangupta`_
+:|F|: docs/plat/nxp/
+:|F|: plat/nxp/
+:|F|: drivers/nxp/
+:|F|: tools/nxp/
+
+NXP SoC Part LX2160A and its platform port
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Pankaj Gupta <pankaj.gupta@nxp.com>
+:|G|: `pangupta`_
+:|F|: plat/nxp/soc-lx2160a
+:|F|: plat/nxp/soc-lx2160a/lx2162aqds
+:|F|: plat/nxp/soc-lx2160a/lx2160aqds
+:|F|: plat/nxp/soc-lx2160a/lx2160ardb
 
 QEMU platform port
 ^^^^^^^^^^^^^^^^^^
-:M: Jens Wiklander <jens.wiklander@linaro.org>
-:G: `jenswi-linaro`_
-:F: docs/plat/qemu.rst
-:F: plat/qemu/
+:|M|: Jens Wiklander <jens.wiklander@linaro.org>
+:|G|: `jenswi-linaro`_
+:|F|: docs/plat/qemu.rst
+:|F|: plat/qemu/
 
 QTI platform port
 ^^^^^^^^^^^^^^^^^
-:M: Saurabh Gorecha <sgorecha@codeaurora.org>
-:G: `sgorecha`_
-:M: Debasish Mandal <dmandal@codeaurora.org>
-:M: QTI TF Maintainers <qti.trustedfirmware.maintainers@codeaurora.org>
-:F: docs/plat/qti.rst
-:F: plat/qti/
+:|M|: Saurabh Gorecha <sgorecha@codeaurora.org>
+:|G|: `sgorecha`_
+:|M|: Lachit Patel <lpatel@codeaurora.org>
+:|G|: `lachitp`_
+:|M|: Sreevyshanavi Kare <skare@codeaurora.org>
+:|G|: `sreekare`_
+:|M|: QTI TF Maintainers <qti.trustedfirmware.maintainers@codeaurora.org>
+:|F|: docs/plat/qti.rst
+:|F|: plat/qti/
 
 Raspberry Pi 3 platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Ying-Chun Liu (PaulLiu) <paul.liu@linaro.org>
-:G: `grandpaul`_
-:F: docs/plat/rpi3.rst
-:F: plat/rpi/rpi3/
-:F: plat/rpi/common/
-:F: drivers/rpi3/
-:F: include/drivers/rpi3/
+:|M|: Ying-Chun Liu (PaulLiu) <paul.liu@linaro.org>
+:|G|: `grandpaul`_
+:|F|: docs/plat/rpi3.rst
+:|F|: plat/rpi/rpi3/
+:|F|: plat/rpi/common/
+:|F|: drivers/rpi3/
+:|F|: include/drivers/rpi3/
 
 Raspberry Pi 4 platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Andre Przywara <andre.przywara@arm.com>
-:G: `Andre-ARM`_
-:F: docs/plat/rpi4.rst
-:F: plat/rpi/rpi4/
-:F: plat/rpi/common/
-:F: drivers/rpi3/
-:F: include/drivers/rpi3/
+:|M|: Andre Przywara <andre.przywara@arm.com>
+:|G|: `Andre-ARM`_
+:|F|: docs/plat/rpi4.rst
+:|F|: plat/rpi/rpi4/
+:|F|: plat/rpi/common/
+:|F|: drivers/rpi3/
+:|F|: include/drivers/rpi3/
 
 Renesas rcar-gen3 platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Jorge Ramirez-Ortiz  <jramirez@baylibre.com>
-:G: `ldts`_
-:M: Marek Vasut <marek.vasut@gmail.com>
-:G: `marex`_
-:F: docs/plat/rcar-gen3.rst
-:F: plat/renesas/rcar
-:F: drivers/renesas/rcar
-:F: tools/renesas/rcar_layout_create
+:|M|: Jorge Ramirez-Ortiz  <jramirez@baylibre.com>
+:|G|: `ldts`_
+:|M|: Marek Vasut <marek.vasut@gmail.com>
+:|G|: `marex`_
+:|F|: docs/plat/rcar-gen3.rst
+:|F|: plat/renesas/common
+:|F|: plat/renesas/rcar
+:|F|: drivers/renesas/common
+:|F|: drivers/renesas/rcar
+:|F|: tools/renesas/rcar_layout_create
+
+Renesas RZ/G2 platform port
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+:|M|: Biju Das <biju.das.jz@bp.renesas.com>
+:|G|: `bijucdas`_
+:|M|: Marek Vasut <marek.vasut@gmail.com>
+:|G|: `marex`_
+:|M|: Lad Prabhakar <prabhakar.mahadev-lad.rj@bp.renesas.com>
+:|G|: `prabhakarlad`_
+:|F|: docs/plat/rz-g2.rst
+:|F|: plat/renesas/common
+:|F|: plat/renesas/rzg
+:|F|: drivers/renesas/common
+:|F|: drivers/renesas/rzg
+:|F|: tools/renesas/rzg_layout_create
 
 RockChip platform port
 ^^^^^^^^^^^^^^^^^^^^^^
-:M: Tony Xie <tony.xie@rock-chips.com>
-:G: `TonyXie06`_
-:G: `rockchip-linux`_
-:M: Heiko Stuebner <heiko@sntech.de>
-:G: `mmind`_
-:F: plat/rockchip/
+:|M|: Tony Xie <tony.xie@rock-chips.com>
+:|G|: `TonyXie06`_
+:|G|: `rockchip-linux`_
+:|M|: Heiko Stuebner <heiko@sntech.de>
+:|G|: `mmind`_
+:|M|: Julius Werner <jwerner@chromium.org>
+:|G|: `jwerner-chromium`_
+:|F|: plat/rockchip/
 
 STM32MP1 platform port
 ^^^^^^^^^^^^^^^^^^^^^^
-:M: Yann Gautier <yann.gautier@st.com>
-:G: `Yann-lms`_
-:F: docs/plat/stm32mp1.rst
-:F: drivers/st/
-:F: fdts/stm32\*
-:F: include/drivers/st/
-:F: include/dt-bindings/\*/stm32\*
-:F: plat/st/
-:F: tools/stm32image/
+:|M|: Yann Gautier <yann.gautier@st.com>
+:|G|: `Yann-lms`_
+:|F|: docs/plat/stm32mp1.rst
+:|F|: drivers/st/
+:|F|: fdts/stm32\*
+:|F|: include/drivers/st/
+:|F|: include/dt-bindings/\*/stm32\*
+:|F|: plat/st/
+:|F|: tools/stm32image/
 
 Synquacer platform port
 ^^^^^^^^^^^^^^^^^^^^^^^
-:M: Sumit Garg <sumit.garg@linaro.org>
-:G: `b49020`_
-:F: docs/plat/synquacer.rst
-:F: plat/socionext/synquacer/
+:|M|: Sumit Garg <sumit.garg@linaro.org>
+:|G|: `b49020`_
+:|F|: docs/plat/synquacer.rst
+:|F|: plat/socionext/synquacer/
 
 Texas Instruments platform port
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Andrew F. Davis <afd@ti.com>
-:G: `glneo`_
-:F: docs/plat/ti-k3.rst
-:F: plat/ti/
+:|M|: Nishanth Menon <nm@ti.com>
+:|G|: `nmenon`_
+:|F|: docs/plat/ti-k3.rst
+:|F|: plat/ti/
 
 UniPhier platform port
 ^^^^^^^^^^^^^^^^^^^^^^
-:M: Orphan
-:F: docs/plat/socionext-uniphier.rst
-:F: plat/socionext/uniphier/
+:|M|: Orphan
+:|F|: docs/plat/socionext-uniphier.rst
+:|F|: plat/socionext/uniphier/
 
 Xilinx platform port
 ^^^^^^^^^^^^^^^^^^^^
-:M: Siva Durga Prasad Paladugu <siva.durga.paladugu@xilinx.com>
-:G: `sivadur`_
-:F: docs/plat/xilinx-zynqmp.rst
-:F: plat/xilinx/
+:|M|: Michal Simek <michal.simek@xilinx.com>
+:|G|: `michalsimek`_
+:|M|: Venkatesh Yadav Abbarapu <venkatesh.abbarapu@xilinx.com>
+:|G|: `venkatesh`_
+:|F|: docs/plat/xilinx-zynqmp.rst
+:|F|: plat/xilinx/
 
 
 Secure Payloads and Dispatchers
@@ -540,65 +677,80 @@
 
 OP-TEE dispatcher
 ^^^^^^^^^^^^^^^^^
-:M: Jens Wiklander <jens.wiklander@linaro.org>
-:G: `jenswi-linaro`_
-:F: docs/components/spd/optee-dispatcher.rst
-:F: services/spd/opteed/
+:|M|: Jens Wiklander <jens.wiklander@linaro.org>
+:|G|: `jenswi-linaro`_
+:|F|: docs/components/spd/optee-dispatcher.rst
+:|F|: services/spd/opteed/
 
 TLK/Trusty secure payloads
 ^^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Varun Wadekar <vwadekar@nvidia.com>
-:G: `vwadekar`_
-:F: docs/components/spd/tlk-dispatcher.rst
-:F: docs/components/spd/trusty-dispatcher.rst
-:F: include/bl32/payloads/tlk.h
-:F: services/spd/tlkd/
-:F: services/spd/trusty/
+:|M|: Varun Wadekar <vwadekar@nvidia.com>
+:|G|: `vwadekar`_
+:|F|: docs/components/spd/tlk-dispatcher.rst
+:|F|: docs/components/spd/trusty-dispatcher.rst
+:|F|: include/bl32/payloads/tlk.h
+:|F|: services/spd/tlkd/
+:|F|: services/spd/trusty/
 
 Test Secure Payload (TSP)
 ^^^^^^^^^^^^^^^^^^^^^^^^^
-:M: Manish Badarkhe <manish.badarkhe@arm.com>
-:G: `ManishVB-Arm`_
-:F: bl32/tsp/
-:F: services/spd/tspd/
+:|M|: Manish Badarkhe <manish.badarkhe@arm.com>
+:|G|: `ManishVB-Arm`_
+:|F|: bl32/tsp/
+:|F|: services/spd/tspd/
 
 Tools
 ~~~~~
 
 Fiptool
 ^^^^^^^
-:M: Joao Alves <Joao.Alves@arm.com>
-:G: `J-Alves`_
-:F: tools/fiptool/
+:|M|: Joao Alves <Joao.Alves@arm.com>
+:|G|: `J-Alves`_
+:|F|: tools/fiptool/
 
 Cert_create tool
 ^^^^^^^^^^^^^^^^
-:M: Sandrine Bailleux <sandrine.bailleux@arm.com>
-:G: `sandrine-bailleux-arm`_
-:F: tools/cert_create/
+:|M|: Sandrine Bailleux <sandrine.bailleux@arm.com>
+:|G|: `sandrine-bailleux-arm`_
+:|F|: tools/cert_create/
 
 Encrypt_fw tool
 ^^^^^^^^^^^^^^^
-:M: Sumit Garg <sumit.garg@linaro.org>
-:G: `b49020`_
-:F: tools/encrypt_fw/
+:|M|: Sumit Garg <sumit.garg@linaro.org>
+:|G|: `b49020`_
+:|F|: tools/encrypt_fw/
 
 Sptool
 ^^^^^^
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:F: tools/sptool/
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|F|: tools/sptool/
 
 Build system
 ^^^^^^^^^^^^
-:M: Manish Pandey <manish.pandey2@arm.com>
-:G: `manish-pandey-arm`_
-:F: Makefile
-:F: make_helpers/
+:|M|: Manish Pandey <manish.pandey2@arm.com>
+:|G|: `manish-pandey-arm`_
+:|F|: Makefile
+:|F|: make_helpers/
+
+Threat Model
+~~~~~~~~~~~~~
+:|M|: Zelalem Aweke <Zelalem.Aweke@arm.com>
+:|G|: `zelalem-aweke`_
+:|M|: Sandrine Bailleux <sandrine.bailleux@arm.com>
+:|G|: `sandrine-bailleux-arm`_
+:|M|: Joanna Farley <joanna.farley@arm.com>
+:|G|: `joannafarley-arm`_
+:|M|: Raghu Krishnamurthy <raghu.ncstate@icloud.com>
+:|G|: `raghuncstate`_
+:|M|: Varun Wadekar <vwadekar@nvidia.com>
+:|G|: `vwadekar`_
+:|F|: docs/threat_model/
 
 .. _AlexeiFedorov: https://github.com/AlexeiFedorov
 .. _Andre-ARM: https://github.com/Andre-ARM
 .. _Anson-Huang: https://github.com/Anson-Huang
+.. _bijucdas: https://github.com/bijucdas
 .. _bryanodonoghue: https://github.com/bryanodonoghue
 .. _b49020: https://github.com/b49020
 .. _carlocaione: https://github.com/carlocaione
@@ -611,26 +763,31 @@
 .. _jenswi-linaro: https://github.com/jenswi-linaro
 .. _jwerner-chromium: https://github.com/jwerner-chromium
 .. _kostapr: https://github.com/kostapr
+.. _lachitp: https://github.com/lachitp
 .. _ldts: https://github.com/ldts
 .. _marex: https://github.com/marex
 .. _masahir0y: https://github.com/masahir0y
+.. _michalsimek: https://github.com/michalsimek
 .. _mmind: https://github.com/mmind
-.. _mtk09422: https://github.com/mtk09422
+.. _MrVan: https://github.com/MrVan
+.. _mtk-rex-bc-chen: https://github.com/mtk-rex-bc-chen
 .. _niej: https://github.com/niej
 .. _npoushin: https://github.com/npoushin
+.. _prabhakarlad: https://github.com/prabhakarlad
 .. _qoriq-open-source: https://github.com/qoriq-open-source
 .. _remi-triplefault: https://github.com/repk
 .. _rockchip-linux: https://github.com/rockchip-linux
 .. _sandrine-bailleux-arm: https://github.com/sandrine-bailleux-arm
 .. _sgorecha: https://github.com/sgorecha
 .. _shawnguo2: https://github.com/shawnguo2
-.. _sivadur: https://github.com/sivadur
 .. _smaeul: https://github.com/smaeul
 .. _soby-mathew: https://github.com/soby-mathew
+.. _sreekare: https://github.com/sreekare
 .. _thloh85-intel: https://github.com/thloh85-intel
 .. _thomas-arm: https://github.com/thomas-arm
 .. _TonyXie06: https://github.com/TonyXie06
 .. _vwadekar: https://github.com/vwadekar
+.. _venkatesh: https://github.com/vabbarap
 .. _Yann-lms: https://github.com/Yann-lms
 .. _manish-pandey-arm: https://github.com/manish-pandey-arm
 .. _mardyk01: https://github.com/mardyk01
@@ -648,5 +805,14 @@
 .. _john-powell-arm: https://github.com/john-powell-arm
 .. _raghuncstate: https://github.com/raghuncstate
 .. _CJKay: https://github.com/cjkay
+.. _nmenon: https://github.com/nmenon
+.. _manojkumar-arm: https://github.com/manojkumar-arm
+.. _chandnich: https://github.com/chandnich
+.. _abdellatif-elkhlifi: https://github.com/abdellatif-elkhlifi
+.. _vishnu-banavath: https://github.com/vishnu-banavath
+.. _vijayenthiran-arm: https://github.com/vijayenthiran-arm
+.. _arugan02: https://github.com/arugan02
+.. _uarif1: https://github.com/uarif1
+.. _pangupta: https://github.com/pangupta
 
 .. _Project Maintenance Process: https://developer.trustedfirmware.org/w/collaboration/project-maintenance-process/
diff --git a/docs/about/release-information.rst b/docs/about/release-information.rst
index 55c8bda..b65571d 100644
--- a/docs/about/release-information.rst
+++ b/docs/about/release-information.rst
@@ -44,7 +44,9 @@
 +-----------------+---------------------------+------------------------------+
 | v2.4            | 2nd week of Nov '20       | 4th week of Oct '20          |
 +-----------------+---------------------------+------------------------------+
-| v2.5            | 2nd week of May '21       | 4th week of Apr '21          |
+| v2.5            | 3rd week of May '21       | 5th week of Apr '21          |
++-----------------+---------------------------+------------------------------+
+| v2.6            | 4th week of Nov '21       | 2nd week of Nov '21          |
 +-----------------+---------------------------+------------------------------+
 
 Removal of Deprecated Interfaces
@@ -64,4 +66,4 @@
 
 --------------
 
-*Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2018-2021, Arm Limited and Contributors. All rights reserved.*
diff --git a/docs/change-log-upcoming.rst b/docs/change-log-upcoming.rst
deleted file mode 100644
index 03806d9..0000000
--- a/docs/change-log-upcoming.rst
+++ /dev/null
@@ -1,149 +0,0 @@
-Change Log for Upcoming Release
-===============================
-
-This document contains a summary of the new features, changes, fixes and known
-issues to be included in the upcoming release of Trusted Firmware-A. The contents
-of this file will be moved to the collective change-log.rst file at the time of
-release code freeze.
-
-
-Upcoming Release Version 2.4
-----------------------------
-
-**Trusted Firmware-A Contributors,
-Please log all relevant new features, changes, fixes, and known issues for the
-upcoming release.  For the CPU support, drivers, and tools sections please preface
-the log description with the relevant key word, example: "<CPU>: <CPU Support
-addition>".  Use the RST format convention already used in the Change Log.**
-
-New Features
-^^^^^^^^^^^^
-
-- Arm Architecture
-   - Example: "Add support for Branch Target Identification (BTI)"
-
-- BL-specific
-   - Example: "Enhanced BL2 bootloader flow to load secure partitions based
-     on firmware configuration data (fconf)."
-
-- Build System
-   - Example: "Modify FVP makefile for CPUs that support both AArch64/32"
-
-- CPU Support
-   - Example: "cortex-a55: Workaround for erratum 1221012"
-
-- Drivers
-   - Example: "console: Allow the console to register multiple times"
-
-- Libraries
-   - Example: "Introduce BTI support in Library at ROM (romlib)"
-
-- New Platforms Support
-   - Example: "qemu/qemu_sbsa: New platform support added for QEMU SBSA platform"
-
-- Platforms
-   - Example: "arm/common: Introduce wrapper functions to setup secure watchdog"
-
-- PSCI
-   - Example: "Adding new optional PSCI hook ``pwr_domain_on_finish_late``"
-
-- Security
-   - Example: "UBSAN support and handlers"
-
-- Tools
-   - Example: "fiptool: Add support to build fiptool on Windows."
-
-
-Changed
-^^^^^^^
-
-- Arm Architecture
-   - Example: "Refactor ARMv8.3 Pointer Authentication support code"
-
-- BL-Specific
-   - Example: "BL2: Invalidate dcache build option for BL2 entry at EL3"
-
-- Boot Flow
-   - Example: "Add helper to parse BL31 parameters (both versions)"
-
-- Drivers
-   - Example: "gicv3: Prevent pending G1S interrupt from becoming G0 interrupt"
-
-- Platforms
-   - Example: "arm/common: Shorten the Firmware Update (FWU) process"
-
-- PSCI
-   - Example: "PSCI: Lookup list of parent nodes to lock only once"
-
-- Secure Partition Manager (SPM)
-   - Example: "Move shim layer to TTBR1_EL1"
-
-- Security
-   - Example: "Refactor SPSR initialisation code"
-
-- Tools
-   - Example: "cert_create: Remove RSA PKCS#1 v1.5 support"
-
-
-Resolved Issues
-^^^^^^^^^^^^^^^
-
-- Arm Architecture
-   - Example: "Fix restoration of PAuth context"
-
-- BL-Specific
-   - Example: "Fix BL31 crash reporting on AArch64 only platforms"
-
-- Build System
-   - Example: "Remove several warnings reported with W=2 and W=1"
-
-- Code Quality
-   - Example: "Unify type of "cpu_idx" across PSCI module"
-
-- CPU Support
-   - Example: "cortex-a12: Fix MIDR mask"
-
-- Drivers
-   - Example: "scmi: Fix wrong payload length"
-
-- Library Code
-   - Example: "libc: Fix memchr implementation"
-
-- Platforms
-   - Example: "rpi: rpi3: Fix compilation error when stack protector is enabled"
-
-- Security
-   - Example: "AArch32: Disable Secure Cycle Counter"
-
-Deprecations
-^^^^^^^^^^^^
-
-- Common Code
-   - Example: "Remove MULTI_CONSOLE_API flag and references to it"
-
-- Drivers
-   - Example: "console: Remove deprecated finish_console_register"
-
-- Secure Partition Manager (SPM):
-   - Example: "Prototype SPCI-based SPM (services/std_svc/spm) will be replaced
-     with alternative methods of secure partitioning support."
-
-Known Issues
-^^^^^^^^^^^^
-
-- Build System
-   - dtb: DTB creation not supported when building on a Windows host.
-
-     This step in the build process is skipped when running on a Windows host. A
-     known issue from the 1.6 release.
-
-- Platforms
-   - arm/juno: System suspend from Linux does not function as documented in the
-     user guide
-
-     Following the instructions provided in the user guide document does not
-     result in the platform entering system suspend state as expected. A message
-     relating to the hdlcd driver failing to suspend will be emitted on the
-     Linux terminal.
-
-   - mediatek/mt6795: This platform does not build in this release
diff --git a/docs/change-log.rst b/docs/change-log.rst
index 3b8f836..9c47568 100644
--- a/docs/change-log.rst
+++ b/docs/change-log.rst
@@ -4,6 +4,675 @@
 This document contains a summary of the new features, changes, fixes and known
 issues in each release of Trusted Firmware-A.
 
+Version 2.5
+-----------
+
+New Features
+^^^^^^^^^^^^
+
+- Architecture support
+    - Added support for speculation barrier(``FEAT_SB``) for non-Armv8.5
+      platforms starting from Armv8.0
+    - Added support for Activity Monitors Extension version 1.1(``FEAT_AMUv1p1``)
+    - Added helper functions for Random number generator(``FEAT_RNG``) registers
+    - Added support for Armv8.6 Multi-threaded PMU extensions (``FEAT_MTPMU``)
+    - Added support for MTE Asymmetric Fault Handling extensions(``FEAT_MTE3``)
+    - Added support for Privileged Access Never extensions(``FEAT_PANx``)
+
+- Bootloader images
+    - Added PIE support for AArch32 builds
+    - Enable Trusted Random Number Generator service for BL32(sp_min)
+
+- Build System
+    - Added build option for Arm Feature Modifiers
+
+- Drivers
+    - Added support for interrupts in TZC-400 driver
+
+    - Broadcom
+        - Added support for I2C, MDIO and USB drivers
+
+    - Marvell
+        - Added support for secure read/write of dfc register-set
+        - Added support for thermal sensor driver
+        - Implement a3700_core_getc API in console driver
+        - Added rx training on 10G port
+
+    - Marvell Mochi
+        - Added support for cn913x in PCIe mode
+
+    - Marvell Armada A8K
+        - Added support for TRNG-IP-76 driver and accessing RNG register
+
+    - Mediatek MT8192
+        - Added support for following drivers
+            - MPU configuration for SCP/PCIe
+            - SPM suspend
+            - Vcore DVFS
+            - LPM
+            - PTP3
+            - UART save and restore
+            - Power-off
+            - PMIC
+            - CPU hotplug and MCDI support
+            - SPMC
+            - MPU
+
+    - Mediatek MT8195
+        - Added support for following drivers
+            - GPIO, NCDI, SPMC drivers
+            - Power-off
+            - CPU hotplug, reboot and MCDI
+            - Delay timer and sys timer
+            - GIC
+
+    - NXP
+        - Added support for
+            - non-volatile storage API
+            - chain of trust and trusted board boot using two modes: MBEDTLS and CSF
+            - fip-handler necessary for DDR initialization
+            - SMMU and console drivers
+            - crypto hardware accelerator driver
+            - following drivers: SD, EMMC, QSPI, FLEXSPI, GPIO, GIC, CSU, PMU, DDR
+            - NXP Security Monitor and SFP driver
+            - interconnect config APIs using ARM CCN-CCI driver
+            - TZC APIs to configure DDR region
+            - generic timer driver
+            - Device configuration driver
+
+    - IMX
+        - Added support for image loading and io-storage driver for TBBR fip booting
+
+    - Renesas
+        - Added support for PFC and EMMC driver
+
+        - RZ Family:
+            - G2N, G2E and G2H SoCs
+                - Added support for watchdog, QoS, PFC and DRAM initialization
+
+        - RZG Family:
+            - G2M
+                - Added support for QoS and DRAM initialization
+
+    - Xilinx
+        - Added JTAG DCC support for Versal and ZynqMP SoC family.
+
+- Libraries
+    - C standard library
+        - Added support to print ``%`` in ``snprintf()`` and ``printf()`` APIs
+        - Added support for strtoull, strtoll, strtoul, strtol APIs from FreeBSD project
+
+    - CPU support
+        - Added support for
+            - Cortex_A78C CPU
+            - Makalu ELP CPU
+            - Makalu CPU
+            - Matterhorn ELP CPU
+            - Neoverse-N2 CPU
+
+    - CPU Errata
+        - Arm Cortex-A76: Added workaround for erratum 1946160
+
+        - Arm Cortex-A77: Added workaround for erratum 1946167
+
+        - Arm Cortex-A78: Added workaround for erratum 1941498 and 1951500
+
+        - Arm Neoverse-N1: Added workaround for erratum 1946160
+
+    - Flattened device tree(libfdt)
+        - Added support for wrapper function to read UUIDs in string format from dtb
+
+- Platforms
+    - Added support for MediaTek MT8195
+    - Added support for Arm RD-N2 board
+
+    - Allwinner
+        - Added support for H616 SoC
+
+    - Arm
+        - Added support for GPT parser
+        - Protect GICR frames for fused/unused cores
+
+    - Arm Morello
+        - Added VirtIO network device to Morello FVP fdts
+
+    - Arm RD-N2
+        - Added support for variant 1 of RD-N2 platform
+        - Enable AMU support
+
+    - Arm RD-V1
+        - Enable AMU support
+
+    - Arm SGI
+        - Added support for platform variant build option
+
+    - Arm TC0
+        - Added Matterhorn ELP CPU support
+        - Added support for opteed
+
+    - Arm Juno
+        - Added support to use hw_config in BL31
+        - Use TRNG entropy source for SMCCC TRNG interface
+        - Condition Juno entropy source with CRC instructions
+
+    - Marvell Mochi
+        - Added support for detection of secure mode
+
+    - Marvell ARMADA
+        - Added support for new compile option A3720_DB_PM_WAKEUP_SRC
+        - Added support doing system reset via CM3 secure coprocessor
+        - Made several makefile enhancements required to build WTMI_MULTI_IMG and TIMDDRTOOL
+        - Added support for building DOIMAGETOOL tool
+        - Added new target mrvl_bootimage
+
+    - Mediatek MT8192
+        - Added support for rtc power off sequence
+
+    - Mediatek MT8195
+        - Added support for SiP service
+
+    - STM32MP1
+        - Added support for
+            - Seeed ODYSSEY SoM and board
+            - SDMMC2 and I2C2 pins in pinctrl
+            - I2C2 peripheral in DTS
+            - PIE for BL32
+            - TZC-400 interrupt managament
+            - Linux Automation MC-1 board
+
+    - Renesas RZG
+        - Added support for identifying EK874 RZ/G2E board
+        - Added support for identifying HopeRun HiHope RZ/G2H and RZ/G2H boards
+
+    - Rockchip
+        - Added support for stack protector
+
+    - QEMU
+        - Added support for ``max`` CPU
+        - Added Cortex-A72 support to ``virt`` platform
+        - Enabled trigger reboot from secure pl061
+
+    - QEMU SBSA
+        - Added support for sbsa-ref Embedded Controller
+
+    - NXP
+        - Added support for warm reset to retain ddr content
+        - Added support for image loader necessary for loading fip image
+
+        - lx2160a SoC Family
+            - Added support for
+                - new platform lx2160a-aqds
+                - new platform lx2160a-rdb
+                - new platform lx2162a-aqds
+                - errata handling
+
+    - IMX imx8mm
+        - Added support for trusted board boot
+
+    - TI K3
+        - Added support for lite device board
+        - Enabled Cortex-A72 erratum 1319367
+        - Enabled Cortex-A53 erratum 1530924
+
+    - Xilinx ZynqMP
+        - Added support for PS and system reset on WDT restart
+        - Added support for error management
+        - Enable support for log messages necessary for debug
+        - Added support for PM API SMC call for efuse and register access
+
+- Processes
+    - Introduced process for platform deprecation
+    - Added documentation for TF-A threat model
+    - Provided a copy of the MIT license to comply with the license
+      requirements of the arm-gic.h source file (originating from the Linux
+      kernel project and re-distributed in TF-A).
+
+- Services
+    - Added support for TRNG firmware interface service
+
+    - Arm
+        - Added SiP service to configure Ethos-N NPU
+
+    - SPMC
+        - Added documentation for SPM(Hafnium) SMMUv3 driver
+
+    - SPMD
+        - Added support for
+            - FFA_INTERRUPT forwading ABI
+            - FFA_SECONDARY_EP_REGISTER ABI
+            - FF-A v1.0 boot time power management, SPMC secondary core boot and
+              early run-time power management
+
+- Tools
+
+    - FIPTool
+        - Added mechanism to allow platform specific image UUID
+
+    - git hooks
+        - Added support for conventional commits through commitlint hook,
+          commitizen hook and husky configuration files.
+
+    - NXP tool
+        - Added support for a tool that creates pbl file from BL2
+
+    - Renesas RZ/G2
+        - Added tool support for creating bootparam and cert_header images
+
+    - CertCreate
+        - Added support for platform-defined certificates, keys, and extensions using
+          the platform's makefile
+
+    - shared tools
+        - Added EFI_GUID representation to uuid helper data structure
+
+Changed
+^^^^^^^
+
+- Common components
+    - Print newline after hex address in aarch64 el3_panic function
+    - Use proper ``#address-cells`` and ``#size-cells`` for reserved-memory in dtbs
+
+- Drivers
+
+    - Move SCMI driver from ST platform directory and make it common to all platforms
+
+    - Arm GICv3
+        - Shift eSPI register offset in GICD_OFFSET_64()
+        - Use mpidr to probe GICR for current CPU
+
+    - Arm TZC-400
+        - Adjust filter tag if it set to FILTER_BIT_ALL
+
+    - Cadence
+        - Enhance UART driver APIs to put characters to fifo
+
+    - Mediatek MT8192
+        - Move timer driver to common folder
+        - Enhanced sys_cirq driver to add more IC services
+
+    - Renesas
+        - Move ddr and delay driver to common directory
+
+    - Renesas rcar
+        - Treat log as device memory in console driver
+
+    - Renesas RZ Family:
+        - G2N and G2H SoCs
+             - Select MMC_CH1 for eMMC channel
+
+    - Marvell
+        - Added support for checking if TRNG unit is present
+
+    - Marvell A3K
+        - Set TXDCLK_2X_SEL bit during PCIe initialization
+        - Set mask parameter for every reg_set call
+
+    - Marvell Mochi
+        - Added missing stream IDs configurations
+
+    - MbedTLS
+        - Migrated to Mbed TLS v2.26.0
+
+    - IMX imx8mp
+        - Change the bl31 physical load address
+
+    - QEMU SBSA
+        - Enable secure variable storage
+
+    - SCMI
+        - Update power domain protocol version to 2.0
+
+    - STM32
+        - Remove dead code from nand FMC driver
+
+- Libraries
+    - C Standard Library
+        - Use macros to reduce duplicated code between snprintf and printf
+
+    - CPU support
+        - Sanity check pointers before use in AArch32 builds
+
+        - Arm Cortex-A78
+            - Remove rainier cpu workaround for errata 1542319
+
+        - Arm Makalu ELP
+            - Added "_arm" suffix to Makalu ELP CPU lib
+
+
+- Miscellaneous
+    - Editorconfig
+        - set max line length to 100
+
+- Platforms
+    - Allwinner
+        - Added reserved-memory node to DT
+        - Express memmap more dynamically
+        - Move SEPARATE_NOBITS_REGION to platforms
+        - Limit FDT checks to reduce code size
+        - Use CPUIDLE hardware when available
+        - Allow conditional compilation of SCPI and native PSCI ops
+        - Always use a 3MHz RSB bus clock
+        - Enable workaround for Cortex-A53 erratum 1530924
+        - Fixed non-default PRELOADED_BL33_BASE
+        - Leave CPU power alone during BL31 setup
+        - Added several psci hooks enhancements to improve system shutdown/reset
+          sequence
+        - Return the PMIC to I2C mode after use
+        - Separate code to power off self and other CPUs
+        - Split native and SCPI-based PSCI implementations
+
+    - Allwinner H6
+        - Added R_PRCM security setup for H6 board
+        - Added SPC security setup for H6 board
+        - Use RSB for the PMIC connection on H6
+
+    - Arm
+        - Store UUID as a string, rather than ints
+        - Replace FIP base and size macro with a generic name
+        - Move compile time switch from source to dt file
+        - Don't provide NT_FW_CONFIG when booting hafnium
+        - Do not setup 'disabled' regulator
+        - Increase SP max size
+        - Remove false dependency of ARM_LINUX_KERNEL_AS_BL33 on RESET_TO_BL31
+          and allow it to be enabled independently
+
+    - Arm FVP
+        - Do not map GIC region in BL1 and BL2
+
+    - Arm Juno
+        - Refactor juno_getentropy() to return 64 bits on each call
+
+    - Arm Morello
+        - Remove "virtio-rng" from Morello FVP
+        - Enable virtIO P9 device for Morello fvp
+
+    - Arm RDV1
+        - Allow all PSCI callbacks on RD-V1
+        - Rename rddaniel to rdv1
+
+    - Arm RDV1MC
+        - Rename rddanielxlr to rdv1mc
+        - Initialize TZC-400 controllers
+
+    - Arm TC0
+        - Updated GICR base address
+        - Use scmi_dvfs clock index 1 for cores 4-7 through fdt
+        - Added reserved-memory node for OP-TEE fdts
+        - Enabled Theodul DSU in TC platform
+        - OP-TEE as S-EL1 SP with SPMC at S-EL2
+        - Update Matterhorm ELP DVFS clock index
+
+    - Arm SGI
+        - Allow access to TZC controller on all chips
+        - Define memory regions for multi-chip platforms
+        - Allow access to nor2 flash and system registers from S-EL0
+        - Define default list of memory regions for DMC-620 TZC
+        - Improve macros defining cper buffer memory region
+        - Refactor DMC-620 error handling SMC function id
+        - Refactor SDEI specific macros
+        - Added platform id value for RDN2 platform
+        - Refactored header file inclusions and inclusion of memory mapping
+
+    - Arm RDN2
+        - Allow usage of secure partitions on RDN2 platform
+        - Update GIC redistributor and TZC base address
+
+    - Arm SGM775
+        - Deprecate Arm sgm775 FVP platform
+
+    - Marvell
+        - Increase TX FIFO EMPTY timeout from 2ms to 3ms
+        - Update delay code to be compatible with 1200 MHz CPU
+
+    - Marvell ARMADA
+        - Postpone MSS CPU startup to BL31 stage
+        - Allow builds without MSS support
+        - Use MSS SRAM in secure mode
+        - Added missing FORCE, .PHONY and clean targets
+        - Cleanup MSS SRAM if used for copy
+        - Move definition of mrvl_flash target to common marvell_common.mk file
+        - Show informative build messages and blank lines
+
+    - Marvell ARMADA A3K
+        - Added a new target mrvl_uart which builds UART image
+        - Added checks that WTP, MV_DDR_PATH and CRYPTOPP_PATH are correctly defined
+        - Allow use of the system Crypto++ library
+        - Build $(WTMI_ENC_IMG) in $(BUILD_PLAT) directory
+        - Build intermediate files in $(BUILD_PLAT) directory
+        - Build UART image files directly in $(BUILD_UART) subdirectory
+        - Correctly set DDR_TOPOLOGY and CLOCKSPRESET for WTMI
+        - Do not use 'echo -e' in Makefile
+        - Improve 4GB DRAM usage from 3.375 GB to 3.75 GB
+        - Remove unused variable WTMI_SYSINIT_IMG from Makefile
+        - Simplify check if WTP variable is defined
+        - Split building $(WTMI_MULTI_IMG) and $(TIMDDRTOOL)
+
+    - Marvell ARMADA A8K
+        - Allow CP1/CP2 mapping at BLE stage
+
+    - Mediatek MT8183
+        - Added timer V20 compensation
+
+    - Nvidia Tegra
+        - Rename SMC API
+
+    - TI K3
+        - Make plat_get_syscnt_freq2 helper check CNT_FID0 register
+        - Fill non-message data fields in sec_proxy with 0x0
+        - Update ti_sci_msg_req_reboot ABI to include domain
+        - Enable USE_COHERENT_MEM only for the generic board
+        - Explicitly map SEC_SRAM_BASE to 0x0
+        - Use BL31_SIZE instead of computing
+        - Define the correct number of max table entries and increase SRAM size
+          to account for additional table
+
+    - Raspberry Pi4
+        - Switch to gicv2.mk and GICV2_SOURCES
+
+    - Renesas
+        - Move headers and assembly files to common folder
+
+    - Renesas rzg
+        - Added device tree memory node enhancements
+
+    - Rockchip
+        - Switch to using common gicv3.mk
+
+    - STM32MP1
+        - Set BL sizes regardless of flags
+
+    - QEMU
+        - Include gicv2.mk for compiling GICv2 source files
+        - Change DEVICE2 definition for MMU
+        - Added helper to calculate the position shift from MPIDR
+
+    - QEMU SBSA
+        - Include libraries for Cortex-A72
+        - Increase SHARED_RAM_SIZE
+        - Addes support in spm_mm for upto 512 cores
+        - Added support for topology handling
+
+    - QTI
+        - Mandate SMC implementation
+
+    - Xilinx
+        - Rename the IPI CRC checksum macro
+        - Use fno-jump-tables flag in CPPFLAGS
+
+    - Xilinx versal
+        - Added the IPI CRC checksum macro support
+        - Mark IPI calls secure/non-secure
+        - Enable sgi to communicate with linux using IPI
+        - Remove Cortex-A53 compilation
+
+    - Xilinx ZynqMP
+        - Configure counter frequency during initialization
+        - Filter errors related to clock gate permissions
+        - Implement pinctrl request/release EEMI API
+        - Reimplement pinctrl get/set config parameter EEMI API calls
+        - Reimplement pinctrl set/get function EEMI API
+        - Update error codes to match Linux and PMU Firmware
+        - Update PM version and support PM version check
+        - Update return type in query functions
+        - Added missing ids for 43/46/47dr devices
+        - Checked for DLL status before doing reset
+        - Disable ITAPDLYENA bit for zero ITAP delay
+        - Include GICv2 makefile
+        - Remove the custom crash implementation
+
+- Services
+
+    - SPMD
+        - Lock the g_spmd_pm structure
+        - Declare third cactus instance as UP SP
+        - Provide number of vCPUs and VM size for first SP
+        - Remove ``chosen`` node from SPMC manifests
+        - Move OP-TEE SP manifest DTS to FVP platform
+        - Update OP-TEE SP manifest with device-regions node
+        - Remove device-memory node from SPMC manifests
+
+    - SPM_MM
+        - Use sp_boot_info to set SP context
+
+    - SDEI
+        - Updata the affinity of shared event
+
+- Tools
+    - FIPtool
+        - Do not print duplicate verbose lines about building fiptool
+
+    - CertCreate
+        - Updated tool for platform defined certs, keys & extensions
+        - Create only requested certificates
+        - Avoid duplicates in extension stack
+
+Resolved Issues
+^^^^^^^^^^^^^^^
+- Several fixes for typos and mis-spellings in documentation
+
+- Build system
+    - Fixed ${FIP_NAME} to be rebuilt only when needed in Makefile
+    - Do not mark file targets as .PHONY target in Makefile
+
+- Drivers
+    - Authorization
+        - Avoid NV counter upgrade without certificate validation
+
+    - Arm GICv3
+        - Fixed logical issue for num_eints
+        - Limit SPI ID to avoid misjudgement in GICD_OFFSET()
+        - Fixed potential GICD context override with ESPI enabled
+
+    - Marvell A3700
+        - Fixed configuring polarity invert bits
+
+    - Arm TZC-400
+        - Correct FAIL_CONTROL Privileged bit
+        - Fixed logical error in FILTER_BIT definitions
+
+    - Renesas rcar
+        - Fixed several coding style violations reported by checkpatch
+
+- Libraries
+    - Arch helpers
+        - Fixed assertions in processing dynamic relocations for AArch64 builds
+
+    - C standard library
+        - Fixed MISRA issues in memset() ABI
+
+    - RAS
+        - Fixed bug of binary search in RAS interrupt handler
+
+- Platforms
+
+    - Arm
+        - Fixed missing copyrights in arm-gic.h file
+        - Fixed the order of header files in several dts files
+        - Fixed error message printing in board makefile
+        - Fixed bug of overriding the last node in image load helper API
+        - Fixed stdout-path in fdts files of TC0 and N1SDP platforms
+        - Turn ON/OFF redistributor in sync with GIC CPU interface ON/OFF for css platforms
+
+    - Arm FVP
+        - Fixed Generic Timer interrupt types in platform dts files
+
+    - Arm Juno
+        - Fixed parallel build issue for romlib config
+
+    - Arm SGI
+        - Fixed bug in SDEI receive event of RAS handler
+
+    - Intel Agilex
+        - Fixed PLAT_MAX_PWR_LVL value
+
+    - Marvell
+        - Fixed SPD handling in dram port
+
+    - Marvell ARMADA
+        - Fixed TRNG return SMC handling
+        - Fixed the logic used for LD selector mask
+        - Fixed MSS firmware loader for A8K family
+
+    - ST
+        - Fixed few violations reported by coverity static checks
+
+    - STM32MP1
+        - Fixed SELFREF_TO_X32 mask in ddr driver
+        - Do not keep mmc_device_info in stack
+        - Correct plat_crash_console_flush()
+
+    - QEMU SBSA
+        - Fixed memory type of secure NOR flash
+
+    - QTI
+        - Fixed NUM_APID and REG_APID_MAP() argument in SPMI driver
+
+    - Intel
+        - Do not keep mmc_device_info in stack
+
+    - Hisilicon
+        - Do not keep mmc_device_info in stack
+
+
+- Services
+
+    - EL3 runtime
+        - Fixed the EL2 context save/restore routine by removing EL2 generic
+          timer system registers
+        - Added fix for exception handler in BL31 by synchronizing pending EA
+          using DSB barrier
+
+    - SPMD
+        - Fixed error codes to use int32_t type
+
+    - TSPD
+        - Added bug fix in tspd interrupt handling when TSP_NS_INTR_ASYNC_PREEMPT is enabled
+
+    - TRNG
+        - Fixed compilation errors with -O0 compile option
+
+    - DebugFS
+        - Checked channel index before calling clone function
+
+    - PSCI
+        - Fixed limit of 256 CPUs caused by cast to unsigned char
+
+    - TSP
+        - Fixed compilation erros when built with GCC 11.0.0 toolchain
+
+- Tools
+    - FIPtool
+        - Do not call ``make clean`` for ``all`` target
+
+    - CertCreate
+        - Fixed bug to avoid cleaning when building the binary
+        - Used preallocated parts of the HASH struct to avoid leaking HASH struct fields
+        - Free arguments copied with strdup
+        - Free keys after use
+        - Free X509_EXTENSION structures on stack to avoid leaking them
+        - Optimized the code to avoid unnecessary attempts to create non-requested
+          certificates
+
 Version 2.4
 -----------
 
@@ -89,7 +758,7 @@
             - Added workaround for erratum 1800714
             - Added workaround for erratum 1925769
 
-        - Arm Neoverse N1
+        - Arm Neoverse-N1
             - Added workaround for erratum 1868343
 
     - EL3 Runtime
@@ -689,10 +1358,10 @@
    - arm/common: Allow boards to specify second DRAM Base address
      and to define PLAT_ARM_TZC_FILTERS
 
-   - arm/cornstone700: Add support for mhuv2 and stack protector
+   - arm/corstone700: Add support for mhuv2 and stack protector
 
    - arm/fvp: Add support for fconf in BL31 and SP_MIN. Populate power
-     domain desciptor dynamically by leveraging fconf APIs.
+     domain descriptor dynamically by leveraging fconf APIs.
    - arm/fvp: Add Cactus/Ivy Secure Partition information and use two
      instances of Cactus at S-EL1
    - arm/fvp: Add support to run BL32 in TDRAM and BL31 in secure DRAM
@@ -967,7 +1636,7 @@
      cpu clock, Move versal_def.h and versal_private to include directory
 
 - Tools
-   - sptool: Updated sptool to accomodate building secure partition packages.
+   - sptool: Updated sptool to accommodate building secure partition packages.
 
 Resolved Issues
 ^^^^^^^^^^^^^^^
diff --git a/docs/components/activity-monitors.rst b/docs/components/activity-monitors.rst
new file mode 100644
index 0000000..dd45c43
--- /dev/null
+++ b/docs/components/activity-monitors.rst
@@ -0,0 +1,34 @@
+Activity Monitors
+=================
+
+FEAT_AMUv1 of the Armv8-A architecture introduces the Activity Monitors
+extension. This extension describes the architecture for the Activity Monitor
+Unit (|AMU|), an optional non-invasive component for monitoring core events
+through a set of 64-bit counters.
+
+When the ``ENABLE_AMU=1`` build option is provided, Trusted Firmware-A sets up
+the |AMU| prior to its exit from EL3, and will save and restore architected
+|AMU| counters as necessary upon suspend and resume.
+
+.. _Activity Monitor Auxiliary Counters:
+
+Auxiliary counters
+------------------
+
+FEAT_AMUv1 describes a set of implementation-defined auxiliary counters (also
+known as group 1 counters), controlled by the ``ENABLE_AMU_AUXILIARY_COUNTERS``
+build option.
+
+As a security precaution, Trusted Firmware-A does not enable these by default.
+Instead, platforms may configure their auxiliary counters through one of two
+possible mechanisms:
+
+- |FCONF|, controlled by the ``ENABLE_AMU_FCONF`` build option.
+- A platform implementation of the ``plat_amu_topology`` function (the default).
+
+See :ref:`Activity Monitor Unit (AMU) Bindings` for documentation on the |FCONF|
+device tree bindings.
+
+--------------
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
diff --git a/docs/components/fconf/amu-bindings.rst b/docs/components/fconf/amu-bindings.rst
new file mode 100644
index 0000000..047f75e
--- /dev/null
+++ b/docs/components/fconf/amu-bindings.rst
@@ -0,0 +1,142 @@
+Activity Monitor Unit (AMU) Bindings
+====================================
+
+To support platform-defined Activity Monitor Unit (|AMU|) auxiliary counters
+through FCONF, the ``HW_CONFIG`` device tree accepts several |AMU|-specific
+nodes and properties.
+
+Bindings
+^^^^^^^^
+
+.. contents::
+    :local:
+
+``/cpus/cpus/cpu*`` node properties
+"""""""""""""""""""""""""""""""""""
+
+The ``cpu`` node has been augmented to support a handle to an associated |AMU|
+view, which should describe the counters offered by the core.
+
++---------------+-------+---------------+-------------------------------------+
+| Property name | Usage | Value type    | Description                         |
++===============+=======+===============+=====================================+
+| ``amu``       | O     | ``<phandle>`` | If present, indicates that an |AMU| |
+|               |       |               | is available and its counters are   |
+|               |       |               | described by the node provided.     |
++---------------+-------+---------------+-------------------------------------+
+
+``/cpus/amus`` node properties
+""""""""""""""""""""""""""""""
+
+The ``amus`` node describes the |AMUs| implemented by the cores in the system.
+This node does not have any properties.
+
+``/cpus/amus/amu*`` node properties
+"""""""""""""""""""""""""""""""""""
+
+An ``amu`` node describes the layout and meaning of the auxiliary counter
+registers of one or more |AMUs|, and may be shared by multiple cores.
+
++--------------------+-------+------------+------------------------------------+
+| Property name      | Usage | Value type | Description                        |
++====================+=======+============+====================================+
+| ``#address-cells`` | R     | ``<u32>``  | Value shall be 1. Specifies that   |
+|                    |       |            | the ``reg`` property array of      |
+|                    |       |            | children of this node uses a       |
+|                    |       |            | single cell.                       |
++--------------------+-------+------------+------------------------------------+
+| ``#size-cells``    | R     | ``<u32>``  | Value shall be 0. Specifies that   |
+|                    |       |            | no size is required in the ``reg`` |
+|                    |       |            | property in children of this node. |
++--------------------+-------+------------+------------------------------------+
+
+``/cpus/amus/amu*/counter*`` node properties
+""""""""""""""""""""""""""""""""""""""""""""
+
+A ``counter`` node describes an auxiliary counter belonging to the parent |AMU|
+view.
+
++-------------------+-------+-------------+------------------------------------+
+| Property name     | Usage | Value type  | Description                        |
++===================+=======+=============+====================================+
+| ``reg``           | R     | array       | Represents the counter register    |
+|                   |       |             | index, and must be a single cell.  |
++-------------------+-------+-------------+------------------------------------+
+| ``enable-at-el3`` | O     | ``<empty>`` | The presence of this property      |
+|                   |       |             | indicates that this counter should |
+|                   |       |             | be enabled prior to EL3 exit.      |
++-------------------+-------+-------------+------------------------------------+
+
+Example
+^^^^^^^
+
+An example system offering four cores made up of two clusters, where the cores
+of each cluster share different |AMUs|, may use something like the following:
+
+.. code-block::
+
+    cpus {
+        #address-cells = <2>;
+        #size-cells = <0>;
+
+        amus {
+            amu0: amu-0 {
+                #address-cells = <1>;
+                #size-cells = <0>;
+
+                counterX: counter@0 {
+                    reg = <0>;
+
+                    enable-at-el3;
+                };
+
+                counterY: counter@1 {
+                    reg = <1>;
+
+                    enable-at-el3;
+                };
+            };
+
+            amu1: amu-1 {
+                #address-cells = <1>;
+                #size-cells = <0>;
+
+                counterZ: counter@0 {
+                    reg = <0>;
+
+                    enable-at-el3;
+                };
+            };
+        };
+
+        cpu0@00000 {
+            ...
+
+            amu = <&amu0>;
+        };
+
+        cpu1@00100 {
+            ...
+
+            amu = <&amu0>;
+        };
+
+        cpu2@10000 {
+            ...
+
+            amu = <&amu1>;
+        };
+
+        cpu3@10100 {
+            ...
+
+            amu = <&amu1>;
+        };
+    }
+
+In this situation, ``cpu0`` and ``cpu1`` (the two cores in the first cluster),
+share the view of their AMUs defined by ``amu0``. Likewise, ``cpu2`` and
+``cpu3`` (the two cores in the second cluster), share the view of their |AMUs|
+defined by ``amu1``. This will cause ``counterX`` and ``counterY`` to be enabled
+for both ``cpu0`` and ``cpu1``, and ``counterZ`` to be enabled for both ``cpu2``
+and ``cpu3``.
diff --git a/docs/components/fconf/index.rst b/docs/components/fconf/index.rst
index 9020633..029f324 100644
--- a/docs/components/fconf/index.rst
+++ b/docs/components/fconf/index.rst
@@ -145,3 +145,5 @@
   :maxdepth: 1
 
   fconf_properties
+  amu-bindings
+  mpmm-bindings
diff --git a/docs/components/fconf/mpmm-bindings.rst b/docs/components/fconf/mpmm-bindings.rst
new file mode 100644
index 0000000..d3cc857
--- /dev/null
+++ b/docs/components/fconf/mpmm-bindings.rst
@@ -0,0 +1,48 @@
+Maximum Power Mitigation Mechanism (MPMM) Bindings
+==================================================
+
+|MPMM| support cannot be determined at runtime by the firmware. Instead, these
+DTB bindings allow the platform to communicate per-core support for |MPMM| via
+the ``HW_CONFIG`` device tree blob.
+
+Bindings
+^^^^^^^^
+
+.. contents::
+    :local:
+
+``/cpus/cpus/cpu*`` node properties
+"""""""""""""""""""""""""""""""""""
+
+The ``cpu`` node has been augmented to allow the platform to indicate support
+for |MPMM| on a given core.
+
++-------------------+-------+-------------+------------------------------------+
+| Property name     | Usage | Value type  | Description                        |
++===================+=======+=============+====================================+
+| ``supports-mpmm`` | O     | ``<empty>`` | If present, indicates that |MPMM|  |
+|                   |       |             | is available on this core.         |
++-------------------+-------+-------------+------------------------------------+
+
+Example
+^^^^^^^
+
+An example system offering two cores, one with support for |MPMM| and one
+without, can be described as follows:
+
+.. code-block::
+
+    cpus {
+        #address-cells = <2>;
+        #size-cells = <0>;
+
+        cpu0@00000 {
+            ...
+
+            supports-mpmm;
+        };
+
+        cpu1@00100 {
+            ...
+        };
+    }
diff --git a/docs/components/ffa-manifest-binding.rst b/docs/components/ffa-manifest-binding.rst
new file mode 100644
index 0000000..df2985c
--- /dev/null
+++ b/docs/components/ffa-manifest-binding.rst
@@ -0,0 +1,252 @@
+FF-A manifest binding to device tree
+========================================
+
+This document defines the nodes and properties used to define a partition,
+according to the FF-A specification.
+
+Version 1.0
+-----------
+
+Partition Properties
+^^^^^^^^^^^^^^^^^^^^
+
+- compatible [mandatory]
+   - value type: <string>
+   - Must be the string "arm,ffa-manifest-X.Y" which specifies the major and
+     minor versions of the device tree binding for the FFA manifest represented
+     by this node. The minor number is incremented if the binding changes in a
+     backwards compatible manner.
+
+      - X is an integer representing the major version number of this document.
+      - Y is an integer representing the minor version number of this document.
+
+- ffa-version [mandatory]
+   - value type: <u32>
+   - Must be two 16 bits values (X, Y), concatenated as 31:16 -> X,
+     15:0 -> Y, where:
+
+      - X is the major version of FF-A expected by the partition at the FFA
+        instance it will execute.
+      - Y is the minor version of FF-A expected by the partition at the FFA
+        instance it will execute.
+
+- uuid [mandatory]
+   - value type: <prop-encoded-array>
+   - An array consisting of 4 <u32> values, identifying the UUID of the service
+     implemented by this partition. The UUID format is described in RFC 4122.
+
+- id
+   - value type: <u32>
+   - Pre-allocated partition ID.
+
+- auxiliary-id
+   - value type: <u32>
+   - Pre-allocated ID that could be used in memory management transactions.
+
+- description
+   - value type: <string>
+   - Name of the partition e.g. for debugging purposes.
+
+- execution-ctx-count [mandatory]
+   - value type: <u32>
+   - Number of vCPUs that a VM or SP wants to instantiate.
+
+      - In the absence of virtualization, this is the number of execution
+        contexts that a partition implements.
+      - If value of this field = 1 and number of PEs > 1 then the partition is
+        treated as UP & migrate capable.
+      - If the value of this field > 1 then the partition is treated as a MP
+        capable partition irrespective of the number of PEs.
+
+- exception-level [mandatory]
+   - value type: <u32>
+   - The target exception level for the partition:
+
+      - 0x0: EL1
+      - 0x1: S_EL0
+      - 0x2: S_EL1
+
+- execution-state [mandatory]
+   - value type: <u32>
+   - The target execution state of the partition:
+
+      - 0: AArch64
+      - 1: AArch32
+
+- load-address
+   - value type: <u64>
+   - Physical base address of the partition in memory. Absence of this field
+     indicates that the partition is position independent and can be loaded at
+     any address chosen at boot time.
+
+- entrypoint-offset
+   - value type: <u64>
+   - Offset from the base of the partition's binary image to the entry point of
+     the partition. Absence of this field indicates that the entry point is at
+     offset 0x0 from the base of the partition's binary.
+
+- xlat-granule [mandatory]
+   - value type: <u32>
+   - Translation granule used with the partition:
+
+      - 0x0: 4k
+      - 0x1: 16k
+      - 0x2: 64k
+
+- boot-order
+   - value type: <u32>
+   - A unique number amongst all partitions that specifies if this partition
+     must be booted before others. The partition with the smaller number will be
+     booted first.
+
+- rx-tx-buffer
+   - value type: "memory-regions" node
+   - Specific "memory-regions" nodes that describe the RX/TX buffers expected
+     by the partition.
+     The "compatible" must be the string "arm,ffa-manifest-rx_tx-buffer".
+
+- messaging-method [mandatory]
+   - value type: <u8>
+   - Specifies which messaging methods are supported by the partition, set bit
+     means the feature is supported, clear bit - not supported:
+
+      - Bit[0]: partition can receive direct requests if set
+      - Bit[1]: partition can send direct requests if set
+      - Bit[2]: partition can send and receive indirect messages
+
+- managed-exit
+   - value type: <empty>
+   - Specifies if managed exit is supported.
+
+- has-primary-scheduler
+   - value type: <empty>
+   - Presence of this field indicates that the partition implements the primary
+     scheduler. If so, run-time EL must be EL1.
+
+- run-time-model
+   - value type: <u32>
+   - Run time model that the SPM must enforce for this SP:
+
+      - 0x0: Run to completion
+      - 0x1: Preemptible
+
+- time-slice-mem
+   - value type: <empty>
+   - Presence of this field indicates that the partition doesn't expect the
+     partition manager to time slice long running memory management functions.
+
+- gp-register-num
+   - value type: <u32>
+   - Presence of this field indicates that the partition expects the
+     ffa_init_info structure to be passed in via the specified general purpose
+     register.
+     The field specifies the general purpose register number but not its width.
+     The width is derived from the partition's execution state, as specified in
+     the partition properties. For example, if the number value is 1 then the
+     general-purpose register used will be x1 in AArch64 state and w1 in AArch32
+     state.
+
+- stream-endpoint-ids
+   - value type: <prop-encoded-array>
+   - List of <u32> tuples, identifying the IDs this partition is acting as
+     proxy for.
+
+Memory Regions
+--------------
+
+- compatible [mandatory]
+   - value type: <string>
+   - Must be the string "arm,ffa-manifest-memory-regions".
+
+- description
+   - value type: <string>
+   - Name of the memory region e.g. for debugging purposes.
+
+- pages-count [mandatory]
+   - value type: <u32>
+   - Count of pages of memory region as a multiple of the translation granule
+     size
+
+- attributes [mandatory]
+   - value type: <u32>
+   - Mapping modes: ORed to get required permission
+
+      - 0x1: Read
+      - 0x2: Write
+      - 0x4: Execute
+
+- base-address
+   - value type: <u64>
+   - Base address of the region. The address must be aligned to the translation
+     granule size.
+     The address given may be a Physical Address (PA), Virtual Address (VA), or
+     Intermediate Physical Address (IPA). Refer to the FFA specification for
+     more information on the restrictions around the address type.
+     If the base address is omitted then the partition manager must map a memory
+     region of the specified size into the partition's translation regime and
+     then communicate the region properties (including the base address chosen
+     by the partition manager) to the partition.
+
+Device Regions
+--------------
+
+- compatible [mandatory]
+   - value type: <string>
+   - Must be the string "arm,ffa-manifest-device-regions".
+
+- description
+   - value type: <string>
+   - Name of the device region e.g. for debugging purposes.
+
+- reg [mandatory]
+   - value type: <prop-encoded-array>
+   - A (address, num-pages) pair describing the device, where:
+
+      - address: The physical base address <u64> value of the device MMIO
+        region.
+      - num-pages: The <u32> number of pages of the region. The total size of
+        the region is this value multiplied by the translation granule size.
+
+- attributes [mandatory]
+   - value type: <u32>
+   - Mapping modes: ORed to get required permission
+
+     - 0x1: Read
+     - 0x2: Write
+     - 0x4: Execute
+
+- smmu-id
+   - value type: <u32>
+   - On systems with multiple System Memory Management Units (SMMUs) this
+     identifier is used to inform the partition manager which SMMU the device is
+     upstream of. If the field is omitted then it is assumed that the device is
+     not upstream of any SMMU.
+
+- stream-ids
+   - value type: <prop-encoded-array>
+   - A list of (id, mem-manage) pair, where:
+
+      - id: A unique <u32> value amongst all devices assigned to the partition.
+
+- interrupts [mandatory]
+   - value type: <prop-encoded-array>
+   - A list of (id, attributes) pair describing the device interrupts, where:
+
+      - id: The <u32> interrupt IDs.
+      - attributes: A <u32> value,
+        containing the attributes for each interrupt ID:
+
+         - Interrupt type: SPI, PPI, SGI
+         - Interrupt configuration: Edge triggered, Level triggered
+         - Interrupt security state: Secure, Non-secure
+         - Interrupt priority value
+         - Target execution context/vCPU for each SPI
+
+- exclusive-access
+   - value type: <empty>
+   - Presence of this field implies that this endpoint must be granted exclusive
+     access and ownership of this device's MMIO region.
+
+--------------
+
+*Copyright (c) 2019-2021, Arm Limited and Contributors. All rights reserved.*
diff --git a/docs/components/granule-protection-tables-design.rst b/docs/components/granule-protection-tables-design.rst
new file mode 100644
index 0000000..07637dd
--- /dev/null
+++ b/docs/components/granule-protection-tables-design.rst
@@ -0,0 +1,235 @@
+Granule Protection Tables Library
+=================================
+
+This document describes the design of the granule protection tables (GPT)
+library used by Trusted Firmware-A (TF-A). This library provides the APIs needed
+to initialize the GPTs based on a data structure containing information about
+the systems memory layout, configure the system registers to enable granule
+protection checks based on these tables, and transition granules between
+different PAS (physical address spaces) at runtime.
+
+Arm CCA adds two new security states for a total of four: root, realm, secure, and
+non-secure. In addition to new security states, corresponding physical address
+spaces have been added to control memory access for each state. The PAS access
+allowed to each security state can be seen in the table below.
+
+.. list-table:: Security states and PAS access rights
+   :widths: 25 25 25 25 25
+   :header-rows: 1
+
+   * -
+     - Root state
+     - Realm state
+     - Secure state
+     - Non-secure state
+   * - Root PAS
+     - yes
+     - no
+     - no
+     - no
+   * - Realm PAS
+     - yes
+     - yes
+     - no
+     - no
+   * - Secure PAS
+     - yes
+     - no
+     - yes
+     - no
+   * - Non-secure PAS
+     - yes
+     - yes
+     - yes
+     - yes
+
+The GPT can function as either a 1 level or 2 level lookup depending on how a
+PAS region is configured. The first step is the level 0 table, each entry in the
+level 0 table controls access to a relatively large region in memory (block
+descriptor), and the entire region can belong to a single PAS when a one step
+mapping is used, or a level 0 entry can link to a level 1 table where relatively
+small regions (granules) of memory can be assigned to different PAS with a 2
+step mapping. The type of mapping used for each PAS is determined by the user
+when setting up the configuration structure.
+
+Design Concepts and Interfaces
+------------------------------
+
+This section covers some important concepts and data structures used in the GPT
+library.
+
+There are three main parameters that determine how the tables are organized and
+function: the PPS (protected physical space) which is the total amount of
+protected physical address space in the system, PGS (physical granule size)
+which is how large each level 1 granule is, and L0GPTSZ (level 0 GPT size) which
+determines how much physical memory is governed by each level 0 entry. A granule
+is the smallest unit of memory that can be independently assigned to a PAS.
+
+L0GPTSZ is determined by the hardware and is read from the GPCCR_EL3 register.
+PPS and PGS are passed into the APIs at runtime and can be determined in
+whatever way is best for a given platform, either through some algorithm or hard
+coded in the firmware.
+
+GPT setup is split into two parts: table creation and runtime initialization. In
+the table creation step, a data structure containing information about the
+desired PAS regions is passed into the library which validates the mappings,
+creates the tables in memory, and enables granule protection checks. In the
+runtime initialization step, the runtime firmware locates the existing tables in
+memory using the GPT register configuration and saves important data to a
+structure used by the granule transition service which will be covered more
+below.
+
+In the reference implementation for FVP models, you can find an example of PAS
+region definitions in the file ``include/plat/arm/common/arm_pas_def.h``. Table
+creation API calls can be found in ``plat/arm/common/arm_bl2_setup.c`` and
+runtime initialization API calls can be seen in
+``plat/arm/common/arm_bl31_setup.c``.
+
+Defining PAS regions
+~~~~~~~~~~~~~~~~~~~~
+
+A ``pas_region_t`` structure is a way to represent a physical address space and
+its attributes that can be used by the GPT library to initialize the tables.
+
+This structure is composed of the following:
+
+#. The base physical address
+#. The region size
+#. The desired attributes of this memory region (mapping type, PAS type)
+
+See the ``pas_region_t`` type in ``include/lib/gpt_rme/gpt_rme.h``.
+
+The programmer should provide the API with an array containing ``pas_region_t``
+structures, then the library will check the desired memory access layout for
+validity and create tables to implement it.
+
+``pas_region_t`` is a public type, however it is recommended that the macros
+``GPT_MAP_REGION_BLOCK`` and ``GPT_MAP_REGION_GRANULE`` be used to populate
+these structures instead of doing it manually to reduce the risk of future
+compatibility issues. These macros take the base physical address, region size,
+and PAS type as arguments to generate the pas_region_t structure. As the names
+imply, ``GPT_MAP_REGION_BLOCK`` creates a region using only L0 mapping while
+``GPT_MAP_REGION_GRANULE`` creates a region using L0 and L1 mappings.
+
+Level 0 and Level 1 Tables
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+The GPT initialization APIs require memory to be passed in for the tables to be
+constructed, ``gpt_init_l0_tables`` takes a memory address and size for building
+the level 0 tables and ``gpt_init_pas_l1_tables`` takes an address and size for
+building the level 1 tables which are linked from level 0 descriptors. The
+tables should have PAS type ``GPT_GPI_ROOT`` and a typical system might place
+its level 0 table in SRAM and its level 1 table(s) in DRAM.
+
+Granule Transition Service
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+The Granule Transition Service allows memory mapped with GPT_MAP_REGION_GRANULE
+ownership to be changed using SMC calls. Non-secure granules can be transitioned
+to either realm or secure space, and realm and secure granules can be
+transitioned back to non-secure. This library only allows memory mapped as
+granules to be transitioned, memory mapped as blocks have their GPIs fixed after
+table creation.
+
+Library APIs
+------------
+
+The public APIs and types can be found in ``include/lib/gpt_rme/gpt_rme.h`` and this
+section is intended to provide additional details and clarifications.
+
+To create the GPTs and enable granule protection checks the APIs need to be
+called in the correct order and at the correct time during the system boot
+process.
+
+#. Firmware must enable the MMU.
+#. Firmware must call ``gpt_init_l0_tables`` to initialize the level 0 tables to
+   a default state, that is, initializing all of the L0 descriptors to allow all
+   accesses to all memory. The PPS is provided to this function as an argument.
+#. DDR discovery and initialization by the system, the discovered DDR region(s)
+   are then added to the L1 PAS regions to be initialized in the next step and
+   used by the GTSI at runtime.
+#. Firmware must call ``gpt_init_pas_l1_tables`` with a pointer to an array of
+   ``pas_region_t`` structures containing the desired memory access layout. The
+   PGS is provided to this function as an argument.
+#. Firmware must call ``gpt_enable`` to enable granule protection checks by
+   setting the correct register values.
+#. In systems that make use of the granule transition service, runtime
+   firmware must call ``gpt_runtime_init`` to set up the data structures needed
+   by the GTSI to find the tables and transition granules between PAS types.
+
+API Constraints
+~~~~~~~~~~~~~~~
+
+The values allowed by the API for PPS and PGS are enumerated types
+defined in the file ``include/lib/gpt_rme/gpt_rme.h``.
+
+Allowable values for PPS along with their corresponding size.
+
+* ``GPCCR_PPS_4GB`` (4GB protected space, 0x100000000 bytes)
+* ``GPCCR_PPS_64GB`` (64GB protected space, 0x1000000000 bytes)
+* ``GPCCR_PPS_1TB`` (1TB protected space, 0x10000000000 bytes)
+* ``GPCCR_PPS_4TB`` (4TB protected space, 0x40000000000 bytes)
+* ``GPCCR_PPS_16TB`` (16TB protected space, 0x100000000000 bytes)
+* ``GPCCR_PPS_256TB`` (256TB protected space, 0x1000000000000 bytes)
+* ``GPCCR_PPS_4PB`` (4PB protected space, 0x10000000000000 bytes)
+
+Allowable values for PGS along with their corresponding size.
+
+* ``GPCCR_PGS_4K`` (4KB granules, 0x1000 bytes)
+* ``GPCCR_PGS_16K`` (16KB granules, 0x4000 bytes)
+* ``GPCCR_PGS_64K`` (64KB granules, 0x10000 bytes)
+
+Allowable values for L0GPTSZ along with the corresponding size.
+
+* ``GPCCR_L0GPTSZ_30BITS`` (1GB regions, 0x40000000 bytes)
+* ``GPCCR_L0GPTSZ_34BITS`` (16GB regions, 0x400000000 bytes)
+* ``GPCCR_L0GPTSZ_36BITS`` (64GB regions, 0x1000000000 bytes)
+* ``GPCCR_L0GPTSZ_39BITS`` (512GB regions, 0x8000000000 bytes)
+
+Note that the value of the PPS, PGS, and L0GPTSZ definitions is an encoded value
+corresponding to the size, not the size itself. The decoded hex representations
+of the sizes have been provided for convenience.
+
+The L0 table memory has some constraints that must be taken into account.
+
+* The L0 table must be aligned to either the table size or 4096 bytes, whichever
+  is greater. L0 table size is the total protected space (PPS) divided by the
+  size of each L0 region (L0GPTSZ) multiplied by the size of each L0 descriptor
+  (8 bytes). ((PPS / L0GPTSZ) * 8)
+* The L0 memory size must be greater than or equal to the table size.
+* The L0 memory must fall within a PAS of type GPT_GPI_ROOT.
+
+The L1 memory also has some constraints.
+
+* The L1 tables must be aligned to their size. The size of each L1 table is the
+  size of each L0 region (L0GPTSZ) divided by the granule size (PGS) divided by
+  the granules controlled in each byte (2). ((L0GPTSZ / PGS) / 2)
+* There must be enough L1 memory supplied to build all requested L1 tables.
+* The L1 memory must fall within a PAS of type GPT_GPI_ROOT.
+
+If an invalid combination of parameters is supplied, the APIs will print an
+error message and return a negative value. The return values of APIs should be
+checked to ensure successful configuration.
+
+Sample Calculation for L0 memory size and alignment
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Let PPS=GPCCR_PPS_4GB and L0GPTSZ=GPCCR_L0GPTSZ_30BITS
+
+We can find the total L0 table size with ((PPS / L0GPTSZ) * 8)
+
+Substitute values to get this: ((0x100000000 / 0x40000000) * 8)
+
+And solve to get 32 bytes. In this case, 4096 is greater than 32, so the L0
+tables must be aligned to 4096 bytes.
+
+Sample calculation for L1 table size and alignment
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Let PGS=GPCCR_PGS_4K and L0GPTSZ=GPCCR_L0GPTSZ_30BITS
+
+We can find the size of each L1 table with ((L0GPTSZ / PGS) / 2).
+
+Substitute values: ((0x40000000 / 0x1000) / 2)
+
+And solve to get 0x20000 bytes per L1 table.
diff --git a/docs/components/index.rst b/docs/components/index.rst
index ffeef80..95fe42c 100644
--- a/docs/components/index.rst
+++ b/docs/components/index.rst
@@ -7,18 +7,22 @@
    :numbered:
 
    spd/index
+   activity-monitors
    arm-sip-service
    debugfs-design
    exception-handling
    fconf/index
    firmware-update
    measured_boot/index
+   mpmm
    platform-interrupt-controller-API
    ras
    romlib-design
    sdei
    secure-partition-manager
    secure-partition-manager-mm
-   psa-ffa-manifest-binding
+   ffa-manifest-binding
    xlat-tables-lib-v2-design
    cot-binding
+   realm-management-extension
+   granule-protection-tables-design
diff --git a/docs/components/measured_boot/event_log.rst b/docs/components/measured_boot/event_log.rst
index 5347dcc..0881248 100644
--- a/docs/components/measured_boot/event_log.rst
+++ b/docs/components/measured_boot/event_log.rst
@@ -9,7 +9,7 @@
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 Measured Boot driver expects a *tpm_event_log* node with the following field
-in 'nt_fw_config' and 'tsp_fw_config' DTS files:
+in 'tb_fw_config', 'nt_fw_config' and 'tsp_fw_config' DTS files:
 
 - compatible [mandatory]
    - value type: <string>
diff --git a/docs/components/mpmm.rst b/docs/components/mpmm.rst
new file mode 100644
index 0000000..1b1c6d8
--- /dev/null
+++ b/docs/components/mpmm.rst
@@ -0,0 +1,30 @@
+Maximum Power Mitigation Mechanism (MPMM)
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+|MPMM| is an optional microarchitectural power management mechanism supported by
+some Arm Armv9-A cores, beginning with the Cortex-X2, Cortex-A710 and
+Cortex-A510 cores. This mechanism detects and limits high-activity events to
+assist in |SoC| processor power domain dynamic power budgeting and limit the
+triggering of whole-rail (i.e. clock chopping) responses to overcurrent
+conditions.
+
+|MPMM| is enabled on a per-core basis by the EL3 runtime firmware. The presence
+of |MPMM| cannot be determined at runtime by the firmware, and therefore the
+platform must expose this information through one of two possible mechanisms:
+
+- |FCONF|, controlled by the ``ENABLE_MPMM_FCONF`` build option.
+- A platform implementation of the ``plat_mpmm_topology`` function (the
+  default).
+
+See :ref:`Maximum Power Mitigation Mechanism (MPMM) Bindings` for documentation
+on the |FCONF| device tree bindings.
+
+.. warning::
+
+    |MPMM| exposes gear metrics through the auxiliary |AMU| counters. An
+    external power controller can use these metrics to budget SoC power by
+    limiting the number of cores that can execute higher-activity workloads or
+    switching to a different DVFS operating point. When this is the case, the
+    |AMU| counters that make up the |MPMM| gears must be enabled by the EL3
+    runtime firmware - please see :ref:`Activity Monitor Auxiliary Counters` for
+    documentation on enabling auxiliary |AMU| counters.
diff --git a/docs/components/psa-ffa-manifest-binding.rst b/docs/components/psa-ffa-manifest-binding.rst
deleted file mode 100644
index 09894ae..0000000
--- a/docs/components/psa-ffa-manifest-binding.rst
+++ /dev/null
@@ -1,247 +0,0 @@
-PSA FF-A manifest binding to device tree
-========================================
-
-This document defines the nodes and properties used to define a partition,
-according to the PSA FF-A specification.
-
-Version 1.0
------------
-
-Partition Properties
-^^^^^^^^^^^^^^^^^^^^
-
-- compatible [mandatory]
-   - value type: <string>
-   - Must be the string "arm,ffa-manifest-X.Y" which specifies the major and
-     minor versions fo the device tree binding for the FFA manifest represented
-     by this node. The minor number is incremented if the binding changes in a
-     backwards compatible manner.
-
-      - X is an integer representing the major version number of this document.
-      - Y is an integer representing the minor version number of this document.
-
-- ffa-version [mandatory]
-   - value type: <u32>
-   - Must be two 16 bits values (X, Y), concatenated as 31:16 -> X,
-     15:0 -> Y, where:
-
-      - X is the major version of PSA-FF-A expected by the partition at the FFA
-        instance it will execute.
-      - Y is the minor version of PSA-FF-A expected by the partition at the FFA
-        instance it will execute.
-
-- uuid [mandatory]
-   - value type: <prop-encoded-array>
-   - An array consisting of 4 <u32> values, identifying the UUID of the service
-     implemented by this partition. The UUID format is described in RFC 4122.
-
-- id
-   - value type: <u32>
-   - Pre-allocated partition ID.
-
-- auxiliary-id
-   - value type: <u32>
-   - Pre-allocated ID that could be used in memory management transactions.
-
-- description
-   - value type: <string>
-   - Name of the partition e.g. for debugging purposes.
-
-- execution-ctx-count [mandatory]
-   - value type: <u32>
-   - Number of vCPUs that a VM or SP wants to instantiate.
-
-      - In the absence of virtualization, this is the number of execution
-        contexts that a partition implements.
-      - If value of this field = 1 and number of PEs > 1 then the partition is
-        treated as UP & migrate capable.
-      - If the value of this field > 1 then the partition is treated as a MP
-        capable partition irrespective of the number of PEs.
-
-- exception-level [mandatory]
-   - value type: <u32>
-   - The target exception level for the partition:
-
-      - 0x0: EL1
-      - 0x1: S_EL0
-      - 0x2: S_EL1
-
-- execution-state [mandatory]
-   - value type: <u32>
-   - The target execution state of the partition:
-
-      - 0: AArch64
-      - 1: AArch32
-
-- load-address
-   - value type: <u64>
-   - Physical base address of the partition in memory. Absence of this field
-     indicates that the partition is position independent and can be loaded at
-     any address chosen at boot time.
-
-- entrypoint-offset
-   - value type: <u64>
-   - Offset from the base of the partition's binary image to the entry point of
-     the partition. Absence of this field indicates that the entry point is at
-     offset 0x0 from the base of the partition's binary.
-
-- xlat-granule [mandatory]
-   - value type: <u32>
-   - Translation granule used with the partition:
-
-      - 0x0: 4k
-      - 0x1: 16k
-      - 0x2: 64k
-
-- boot-order
-   - value type: <u32>
-   - A unique number amongst all partitions that specifies if this partition
-     must be booted before others. The partition with the smaller number will be
-     booted first.
-
-- rx-tx-buffer
-   - value type: "memory-regions" node
-   - Specific "memory-regions" nodes that describe the RX/TX buffers expected
-     by the partition.
-     The "compatible" must be the string "arm,ffa-manifest-rx_tx-buffer".
-
-- messaging-method [mandatory]
-   - value type: <u32>
-   - Specifies which messaging methods are supported by the partition:
-
-      - 0x0: direct messaging method
-      - 0x1: indirect messaging method
-      - 0x2: both direct and indirect messaging methods
-
-- has-primary-scheduler
-   - value type: <empty>
-   - Presence of this field indicates that the partition implements the primary
-     scheduler. If so, run-time EL must be EL1.
-
-- run-time-model
-   - value type: <u32>
-   - Run time model that the SPM must enforce for this SP:
-
-      - 0x0: Run to completion
-      - 0x1: Preemptible
-
-- time-slice-mem
-   - value type: <empty>
-   - Presence of this field indicates that the partition doesn't expect the
-     partition manager to time slice long running memory management functions.
-
-- gp-register-num
-   - value type: <u32>
-   - Presence of this field indicates that the partition expects the
-     ffa_init_info structure to be passed in via the specified general purpose
-     register.
-     The field specifies the general purpose register number but not its width.
-     The width is derived from the partition's execution state, as specified in
-     the partition properties. For example, if the number value is 1 then the
-     general-purpose register used will be x1 in AArch64 state and w1 in AArch32
-     state.
-
-- stream-endpoint-ids
-   - value type: <prop-encoded-array>
-   - List of <u32> tuples, identifying the IDs this partition is acting as
-     proxy for.
-
-Memory Regions
---------------
-
-- compatible [mandatory]
-   - value type: <string>
-   - Must be the string "arm,ffa-manifest-memory-regions".
-
-- description
-   - value type: <string>
-   - Name of the memory region e.g. for debugging purposes.
-
-- pages-count [mandatory]
-   - value type: <u32>
-   - Count of pages of memory region as a multiple of the translation granule
-     size
-
-- attributes [mandatory]
-   - value type: <u32>
-   - Mapping modes: ORed to get required permission
-
-      - 0x1: Read
-      - 0x2: Write
-      - 0x4: Execute
-
-- base-address
-   - value type: <u64>
-   - Base address of the region. The address must be aligned to the translation
-     granule size.
-     The address given may be a Physical Address (PA), Virtual Address (VA), or
-     Intermediate Physical Address (IPA). Refer to the FFA specification for
-     more information on the restrictions around the address type.
-     If the base address is omitted then the partition manager must map a memory
-     region of the specified size into the partition's translation regime and
-     then communicate the region properties (including the base address chosen
-     by the partition manager) to the partition.
-
-Device Regions
---------------
-
-- compatible [mandatory]
-   - value type: <string>
-   - Must be the string "arm,ffa-manifest-device-regions".
-
-- description
-   - value type: <string>
-   - Name of the device region e.g. for debugging purposes.
-
-- reg [mandatory]
-   - value type: <prop-encoded-array>
-   - A (address, num-pages) pair describing the device, where:
-
-      - address: The physical base address <u64> value of the device MMIO
-        region.
-      - num-pages: The <u32> number of pages of the region. The total size of
-        the region is this value multiplied by the translation granule size.
-
-- attributes [mandatory]
-   - value type: <u32>
-   - Mapping modes: ORed to get required permission
-
-     - 0x1: Read
-     - 0x2: Write
-     - 0x4: Execute
-
-- smmu-id
-   - value type: <u32>
-   - On systems with multiple System Memory Management Units (SMMUs) this
-     identifier is used to inform the partition manager which SMMU the device is
-     upstream of. If the field is omitted then it is assumed that the device is
-     not upstream of any SMMU.
-
-- stream-ids
-   - value type: <prop-encoded-array>
-   - A list of (id, mem-manage) pair, where:
-
-      - id: A unique <u32> value amongst all devices assigned to the partition.
-
-- interrupts [mandatory]
-   - value type: <prop-encoded-array>
-   - A list of (id, attributes) pair describing the device interrupts, where:
-
-      - id: The <u32> interrupt IDs.
-      - attributes: A <u32> value,
-        containing the attributes for each interrupt ID:
-
-         - Interrupt type: SPI, PPI, SGI
-         - Interrupt configuration: Edge triggered, Level triggered
-         - Interrupt security state: Secure, Non-secure
-         - Interrupt priority value
-         - Target execution context/vCPU for each SPI
-
-- exclusive-access
-   - value type: <empty>
-   - Presence of this field implies that this endpoint must be granted exclusive
-     access and ownership of this devices's MMIO region.
-
---------------
-
-*Copyright (c) 2019-2020, Arm Limited and Contributors. All rights reserved.*
diff --git a/docs/components/realm-management-extension.rst b/docs/components/realm-management-extension.rst
new file mode 100644
index 0000000..2c4e0b8
--- /dev/null
+++ b/docs/components/realm-management-extension.rst
@@ -0,0 +1,263 @@
+
+Realm Management Extension (RME)
+====================================
+
+FEAT_RME (or RME for short) is an Armv9-A extension and is one component of the
+`Arm Confidential Compute Architecture (Arm CCA)`_. TF-A supports RME starting
+from version 2.6. This chapter discusses the changes to TF-A to support RME and
+provides instructions on how to build and run TF-A with RME.
+
+RME support in TF-A
+---------------------
+
+The following diagram shows an Arm CCA software architecture with TF-A as the
+EL3 firmware. In the Arm CCA architecture there are two additional security
+states and address spaces: ``Root`` and ``Realm``. TF-A firmware runs in the
+Root world. In the realm world, a Realm Management Monitor firmware (RMM)
+manages the execution of Realm VMs and their interaction with the hypervisor.
+
+.. image:: ../resources/diagrams/arm-cca-software-arch.png
+
+RME is the hardware extension to support Arm CCA. To support RME, various
+changes have been introduced to TF-A. We discuss those changes below.
+
+Changes to translation tables library
+***************************************
+RME adds Root and Realm Physical address spaces. To support this, two new
+memory type macros, ``MT_ROOT`` and ``MT_REALM``, have been added to the
+:ref:`Translation (XLAT) Tables Library`. These macros are used to configure
+memory regions as Root or Realm respectively.
+
+.. note::
+
+ Only version 2 of the translation tables library supports the new memory
+ types.
+
+Changes to context management
+*******************************
+A new CPU context for the Realm world has been added. The existing
+:ref:`CPU context management API<PSCI Library Integration guide for Armv8-A
+AArch32 systems>` can be used to manage Realm context.
+
+Boot flow changes
+*******************
+In a typical TF-A boot flow, BL2 runs at Secure-EL1. However when RME is
+enabled, TF-A runs in the Root world at EL3. Therefore, the boot flow is
+modified to run BL2 at EL3 when RME is enabled. In addition to this, a
+Realm-world firmware (RMM) is loaded by BL2 in the Realm physical address
+space.
+
+The boot flow when RME is enabled looks like the following:
+
+1. BL1 loads and executes BL2 at EL3
+2. BL2 loads images including RMM
+3. BL2 transfers control to BL31
+4. BL31 initializes SPM (if SPM is enabled)
+5. BL31 initializes RMM
+6. BL31 transfers control to Normal-world software
+
+Granule Protection Tables (GPT) library
+*****************************************
+Isolation between the four physical address spaces is enforced by a process
+called Granule Protection Check (GPC) performed by the MMU downstream any
+address translation. GPC makes use of Granule Protection Table (GPT) in the
+Root world that describes the physical address space assignment of every
+page (granule). A GPT library that provides APIs to initialize GPTs and to
+transition granules between different physical address spaces has been added.
+More information about the GPT library can be found in the
+:ref:`Granule Protection Tables Library` chapter.
+
+RMM Dispatcher (RMMD)
+************************
+RMMD is a new standard runtime service that handles the switch to the Realm
+world. It initializes the RMM and handles Realm Management Interface (RMI)
+SMC calls from Non-secure and Realm worlds.
+
+Test Realm Payload (TRP)
+*************************
+TRP is a small test payload that runs at R-EL2 and implements a subset of
+the Realm Management Interface (RMI) commands to primarily test EL3 firmware
+and the interface between R-EL2 and EL3. When building TF-A with RME enabled,
+if a path to an RMM image is not provided, TF-A builds the TRP by default
+and uses it as RMM image.
+
+Building and running TF-A with RME
+------------------------------------
+
+This section describes how you can build and run TF-A with RME enabled.
+We assume you have all the :ref:`Prerequisites` to build TF-A.
+
+To enable RME, you need to set the ENABLE_RME build flag when building
+TF-A. Currently, this feature is only supported for the FVP platform.
+
+The following instructions show you how to build and run TF-A with RME
+for two scenarios: TF-A with TF-A Tests, and four-world execution with
+Hafnium and TF-A Tests. The instructions assume you have already obtained
+TF-A. You can use the following command to clone TF-A.
+
+.. code:: shell
+
+ git clone https://git.trustedfirmware.org/TF-A/trusted-firmware-a.git
+
+To run the tests, you need an FVP model. Please use the :ref:`latest version
+<Arm Fixed Virtual Platforms (FVP)>` of *FVP_Base_RevC-2xAEMvA* model.
+
+.. note::
+
+ ENABLE_RME build option is currently experimental.
+
+Building TF-A with TF-A Tests
+********************************************
+Use the following instructions to build TF-A with `TF-A Tests`_ as the
+non-secure payload (BL33).
+
+**1. Obtain and build TF-A Tests**
+
+.. code:: shell
+
+ git clone https://git.trustedfirmware.org/TF-A/tf-a-tests.git
+ cd tf-a-tests
+ make CROSS_COMPILE=aarch64-none-elf- PLAT=fvp DEBUG=1
+
+This produces a TF-A Tests binary (*tftf.bin*) in the *build/fvp/debug* directory.
+
+**2. Build TF-A**
+
+.. code:: shell
+
+ cd trusted-firmware-a
+ make CROSS_COMPILE=aarch64-none-elf- \
+ PLAT=fvp \
+ ENABLE_RME=1 \
+ FVP_HW_CONFIG_DTS=fdts/fvp-base-gicv3-psci-1t.dts \
+ DEBUG=1 \
+ BL33=<path/to/tftf.bin> \
+ all fip
+
+This produces *bl1.bin* and *fip.bin* binaries in the *build/fvp/debug* directory.
+The above command also builds TRP. The TRP binary is packaged in *fip.bin*.
+
+Four-world execution with Hafnium and TF-A Tests
+****************************************************
+Four-world execution involves software components at each security state: root,
+secure, realm and non-secure. This section describes how to build TF-A
+with four-world support. We use TF-A as the root firmware, `Hafnium`_ as the
+secure component, TRP as the realm-world firmware and TF-A Tests as the
+non-secure payload.
+
+Before building TF-A, you first need to build the other software components.
+You can find instructions on how to get and build TF-A Tests above.
+
+**1. Obtain and build Hafnium**
+
+.. code:: shell
+
+ git clone --recurse-submodules https://git.trustedfirmware.org/hafnium/hafnium.git
+ cd hafnium
+ make PROJECT=reference
+
+The Hafnium binary should be located at
+*out/reference/secure_aem_v8a_fvp_clang/hafnium.bin*
+
+**2. Build TF-A**
+
+Build TF-A with RME as well as SPM enabled.
+
+.. code:: shell
+
+ make CROSS_COMPILE=aarch64-none-elf- \
+ PLAT=fvp \
+ ENABLE_RME=1 \
+ FVP_HW_CONFIG_DTS=fdts/fvp-base-gicv3-psci-1t.dts \
+ SPD=spmd \
+ SPMD_SPM_AT_SEL2=1 \
+ BRANCH_PROTECTION=1 \
+ CTX_INCLUDE_PAUTH_REGS=1 \
+ DEBUG=1 \
+ SP_LAYOUT_FILE=<path/to/tf-a-tests>/build/fvp/debug/sp_layout.json> \
+ BL32=<path/to/hafnium.bin> \
+ BL33=<path/to/tftf.bin> \
+ all fip
+
+Running the tests
+*********************
+Use the following command to run the tests on FVP. TF-A Tests should boot
+and run the default tests including RME tests.
+
+.. code:: shell
+
+ FVP_Base_RevC-2xAEMvA \
+ -C bp.flashloader0.fname=<path/to/fip.bin> \
+ -C bp.secureflashloader.fname=<path/to/bl1.bin> \
+ -C bp.refcounter.non_arch_start_at_default=1 \
+ -C bp.refcounter.use_real_time=0 \
+ -C bp.ve_sysregs.exit_on_shutdown=1 \
+ -C cache_state_modelled=1 \
+ -C cluster0.NUM_CORES=4 \
+ -C cluster0.PA_SIZE=48 \
+ -C cluster0.ecv_support_level=2 \
+ -C cluster0.gicv3.cpuintf-mmap-access-level=2 \
+ -C cluster0.gicv3.without-DS-support=1 \
+ -C cluster0.gicv4.mask-virtual-interrupt=1 \
+ -C cluster0.has_arm_v8-6=1 \
+ -C cluster0.has_branch_target_exception=1 \
+ -C cluster0.has_rme=1 \
+ -C cluster0.has_rndr=1 \
+ -C cluster0.has_amu=1 \
+ -C cluster0.has_v8_7_pmu_extension=2 \
+ -C cluster0.max_32bit_el=-1 \
+ -C cluster0.restriction_on_speculative_execution=2 \
+ -C cluster0.restriction_on_speculative_execution_aarch32=2 \
+ -C cluster1.NUM_CORES=4 \
+ -C cluster1.PA_SIZE=48 \
+ -C cluster1.ecv_support_level=2 \
+ -C cluster1.gicv3.cpuintf-mmap-access-level=2 \
+ -C cluster1.gicv3.without-DS-support=1 \
+ -C cluster1.gicv4.mask-virtual-interrupt=1 \
+ -C cluster1.has_arm_v8-6=1 \
+ -C cluster1.has_branch_target_exception=1 \
+ -C cluster1.has_rme=1 \
+ -C cluster1.has_rndr=1 \
+ -C cluster1.has_amu=1 \
+ -C cluster1.has_v8_7_pmu_extension=2 \
+ -C cluster1.max_32bit_el=-1 \
+ -C cluster1.restriction_on_speculative_execution=2 \
+ -C cluster1.restriction_on_speculative_execution_aarch32=2 \
+ -C pci.pci_smmuv3.mmu.SMMU_AIDR=2 \
+ -C pci.pci_smmuv3.mmu.SMMU_IDR0=0x0046123B \
+ -C pci.pci_smmuv3.mmu.SMMU_IDR1=0x00600002 \
+ -C pci.pci_smmuv3.mmu.SMMU_IDR3=0x1714 \
+ -C pci.pci_smmuv3.mmu.SMMU_IDR5=0xFFFF0475 \
+ -C pci.pci_smmuv3.mmu.SMMU_S_IDR1=0xA0000002 \
+ -C pci.pci_smmuv3.mmu.SMMU_S_IDR2=0 \
+ -C pci.pci_smmuv3.mmu.SMMU_S_IDR3=0 \
+ -C bp.pl011_uart0.out_file=uart0.log \
+ -C bp.pl011_uart1.out_file=uart1.log \
+ -C bp.pl011_uart2.out_file=uart2.log \
+ -C pctl.startup=0.0.0.0 \
+ -Q 1000 \
+ "$@"
+
+The bottom of the output from *uart0* should look something like the following.
+
+.. code-block:: shell
+
+ ...
+
+ > Test suite 'FF-A Interrupt'
+                                                                Passed
+ > Test suite 'SMMUv3 tests'
+                                                                Passed
+ > Test suite 'PMU Leakage'
+                                                                Passed
+ > Test suite 'DebugFS'
+                                                                Passed
+ > Test suite 'Realm payload tests'
+                                                                Passed
+ ...
+
+
+.. _Arm Confidential Compute Architecture (Arm CCA): https://www.arm.com/why-arm/architecture/security-features/arm-confidential-compute-architecture
+.. _Arm Architecture Models website: https://developer.arm.com/tools-and-software/simulation-models/fixed-virtual-platforms/arm-ecosystem-models
+.. _TF-A Tests: https://trustedfirmware-a-tests.readthedocs.io/en/latest
+.. _Hafnium: https://www.trustedfirmware.org/projects/hafnium
diff --git a/docs/components/secure-partition-manager-mm.rst b/docs/components/secure-partition-manager-mm.rst
index d532901..4cdb96c 100644
--- a/docs/components/secure-partition-manager-mm.rst
+++ b/docs/components/secure-partition-manager-mm.rst
@@ -6,7 +6,7 @@
 
 Two implementations of a Secure Partition Manager co-exist in the TF-A codebase:
 
--  SPM based on the PSA FF-A specification (:ref:`Secure Partition Manager`).
+-  SPM based on the FF-A specification (:ref:`Secure Partition Manager`).
 -  SPM based on the MM interface.
 
 Both implementations differ in their architectures and only one can be selected
@@ -134,8 +134,8 @@
 the rest of this document.
 
 To enable SPM support in TF-A, the source code must be compiled with the build
-flag ``SPM_MM=1``, along with ``EL3_EXCEPTION_HANDLING=1``. On Arm
-platforms the build option ``ARM_BL31_IN_DRAM`` must be set to 1. Also, the
+flag ``SPM_MM=1``, along with ``EL3_EXCEPTION_HANDLING=1`` and ``ENABLE_SVE_FOR_NS=0``.
+On Arm platforms the build option ``ARM_BL31_IN_DRAM`` must be set to 1. Also, the
 location of the binary that contains the BL32 image
 (``BL32=path/to/image.bin``) must be specified.
 
@@ -148,7 +148,7 @@
 .. code:: shell
 
     BL32=path/to/standalone/mm/sp BL33=path/to/bl33.bin \
-    make PLAT=fvp SPM_MM=1 EL3_EXCEPTION_HANDLING=1 ARM_BL31_IN_DRAM=1 all fip
+    make PLAT=fvp SPM_MM=1 EL3_EXCEPTION_HANDLING=1 ENABLE_SVE_FOR_NS=0 ARM_BL31_IN_DRAM=1 all fip
 
 Describing Secure Partition resources
 -------------------------------------
@@ -822,7 +822,7 @@
 
 --------------
 
-*Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _Armv8-A ARM: https://developer.arm.com/docs/ddi0487/latest/arm-architecture-reference-manual-armv8-for-armv8-a-architecture-profile
 .. _instructions in the EDK2 repository: https://github.com/tianocore/edk2-staging/blob/AArch64StandaloneMm/HowtoBuild.MD
diff --git a/docs/components/secure-partition-manager.rst b/docs/components/secure-partition-manager.rst
index 9a65e64..0572261 100644
--- a/docs/components/secure-partition-manager.rst
+++ b/docs/components/secure-partition-manager.rst
@@ -6,162 +6,176 @@
 Acronyms
 ========
 
-+--------+-----------------------------------+
-| DTB    | Device Tree Blob                  |
-+--------+-----------------------------------+
-| DTS    | Device Tree Source                |
-+--------+-----------------------------------+
-| EC     | Execution Context                 |
-+--------+-----------------------------------+
-| FIP    | Firmware Image Package            |
-+--------+-----------------------------------+
-| FF-A   | Firmware Framework for A-class    |
-+--------+-----------------------------------+
-| IPA    | Intermediate Physical Address     |
-+--------+-----------------------------------+
-| NWd    | Normal World                      |
-+--------+-----------------------------------+
-| ODM    | Original Design Manufacturer      |
-+--------+-----------------------------------+
-| OEM    | Original Equipment Manufacturer   |
-+--------+-----------------------------------+
-| PA     | Physical Address                  |
-+--------+-----------------------------------+
-| PE     | Processing Element                |
-+--------+-----------------------------------+
-| PVM    | Primary VM                        |
-+--------+-----------------------------------+
-| PSA    | Platform Security Architecture    |
-+--------+-----------------------------------+
-| SP     | Secure Partition                  |
-+--------+-----------------------------------+
-| SPM    | Secure Partition Manager          |
-+--------+-----------------------------------+
-| SPMC   | SPM Core                          |
-+--------+-----------------------------------+
-| SPMD   | SPM Dispatcher                    |
-+--------+-----------------------------------+
-| SiP    | Silicon Provider                  |
-+--------+-----------------------------------+
-| SWd    | Secure World                      |
-+--------+-----------------------------------+
-| TLV    | Tag-Length-Value                  |
-+--------+-----------------------------------+
-| TOS    | Trusted Operating System          |
-+--------+-----------------------------------+
-| VM     | Virtual Machine                   |
-+--------+-----------------------------------+
++--------+--------------------------------------+
+| CoT    | Chain of Trust                       |
++--------+--------------------------------------+
+| DMA    | Direct Memory Access                 |
++--------+--------------------------------------+
+| DTB    | Device Tree Blob                     |
++--------+--------------------------------------+
+| DTS    | Device Tree Source                   |
++--------+--------------------------------------+
+| EC     | Execution Context                    |
++--------+--------------------------------------+
+| FIP    | Firmware Image Package               |
++--------+--------------------------------------+
+| FF-A   | Firmware Framework for Arm A-profile |
++--------+--------------------------------------+
+| IPA    | Intermediate Physical Address        |
++--------+--------------------------------------+
+| NWd    | Normal World                         |
++--------+--------------------------------------+
+| ODM    | Original Design Manufacturer         |
++--------+--------------------------------------+
+| OEM    | Original Equipment Manufacturer      |
++--------+--------------------------------------+
+| PA     | Physical Address                     |
++--------+--------------------------------------+
+| PE     | Processing Element                   |
++--------+--------------------------------------+
+| PM     | Power Management                     |
++--------+--------------------------------------+
+| PVM    | Primary VM                           |
++--------+--------------------------------------+
+| SMMU   | System Memory Management Unit        |
++--------+--------------------------------------+
+| SP     | Secure Partition                     |
++--------+--------------------------------------+
+| SPD    | Secure Payload Dispatcher            |
++--------+--------------------------------------+
+| SPM    | Secure Partition Manager             |
++--------+--------------------------------------+
+| SPMC   | SPM Core                             |
++--------+--------------------------------------+
+| SPMD   | SPM Dispatcher                       |
++--------+--------------------------------------+
+| SiP    | Silicon Provider                     |
++--------+--------------------------------------+
+| SWd    | Secure World                         |
++--------+--------------------------------------+
+| TLV    | Tag-Length-Value                     |
++--------+--------------------------------------+
+| TOS    | Trusted Operating System             |
++--------+--------------------------------------+
+| VM     | Virtual Machine                      |
++--------+--------------------------------------+
 
 Foreword
 ========
 
 Two implementations of a Secure Partition Manager co-exist in the TF-A codebase:
 
--  SPM based on the PSA FF-A specification `[1]`_.
--  SPM based on the MM interface to communicate with an S-EL0 partition `[2]`_.
+- SPM based on the FF-A specification `[1]`_.
+- SPM based on the MM interface to communicate with an S-EL0 partition `[2]`_.
 
 Both implementations differ in their architectures and only one can be selected
 at build time.
 
 This document:
 
--  describes the PSA FF-A implementation where the Secure Partition Manager
-   resides at EL3 and S-EL2 (or EL3 and S-EL1).
--  is not an architecture specification and it might provide assumptions
-   on sections mandated as implementation-defined in the specification.
--  covers the implications to TF-A used as a bootloader, and Hafnium
-   used as a reference code base for an S-EL2 secure firmware on
-   platforms implementing Armv8.4-SecEL2.
+- describes the FF-A implementation where the Secure Partition Manager
+  resides at EL3 and S-EL2 (or EL3 and S-EL1).
+- is not an architecture specification and it might provide assumptions
+  on sections mandated as implementation-defined in the specification.
+- covers the implications to TF-A used as a bootloader, and Hafnium
+  used as a reference code base for an S-EL2 secure firmware on
+  platforms implementing the FEAT_SEL2 (formerly Armv8.4 Secure EL2)
+  architecture extension.
 
 Terminology
 -----------
 
--  Hypervisor refers to the NS-EL2 component managing Virtual Machines (or
-   partitions) in the Normal World.
--  SPMC refers to the S-EL2 component managing Virtual Machines (or Secure
-   Partitions) in the Secure World when Armv8.4-SecEL2 extension is implemented.
--  Alternatively, SPMC can refer to an S-EL1 component, itself being a Secure
-   Partition and implementing the FF-A ABI on pre-Armv8.4 platforms.
--  VM refers to a Normal World Virtual Machine managed by an Hypervisor.
--  SP refers to a Secure World "Virtual Machine" managed by the SPMC component.
+- The term Hypervisor refers to the NS-EL2 component managing Virtual Machines
+  (or partitions) in the normal world.
+- The term SPMC refers to the S-EL2 component managing secure partitions in
+  the secure world when the FEAT_SEL2 architecture extension is implemented.
+- Alternatively, SPMC can refer to an S-EL1 component, itself being a secure
+  partition and implementing the FF-A ABI on platforms not implementing the
+  FEAT_SEL2 architecture extension.
+- The term VM refers to a normal world Virtual Machine managed by an Hypervisor.
+- The term SP refers to a secure world "Virtual Machine" managed by an SPMC.
 
 Support for legacy platforms
 ----------------------------
 
-In the implementation, the SPM is split into SPMD and SPMC components
-(although not strictly mandated by the specification). SPMD is located
-at EL3 and principally relays FF-A messages from NWd (Hypervisor or OS
-kernel) to SPMC located either at S-EL1 or S-EL2.
+In the implementation, the SPM is split into SPMD and SPMC components.
+The SPMD is located at EL3 and mainly relays FF-A messages from
+NWd (Hypervisor or OS kernel) to SPMC located either at S-EL1 or S-EL2.
 
-Hence TF-A must support both cases where SPMC is either located at:
+Hence TF-A supports both cases where the SPMC is located either at:
 
--  S-EL1 supporting pre-Armv8.4 platforms. SPMD conveys FF-A protocol
-   from EL3 to S-EL1.
--  S-EL2 supporting platforms implementing Armv8.4-SecEL2 extension.
-   SPMD conveys FF-A protocol from EL3 to S-EL2.
+- S-EL1 supporting platforms not implementing the FEAT_SEL2 architecture
+  extension. The SPMD relays the FF-A protocol from EL3 to S-EL1.
+- or S-EL2 supporting platforms implementing the FEAT_SEL2 architecture
+  extension. The SPMD relays the FF-A protocol from EL3 to S-EL2.
 
-The same SPMD component is used to support both configurations. The SPMC
-execution level is a build time choice.
+The same TF-A SPMD component is used to support both configurations.
+The SPMC exception level is a build time choice.
 
 Sample reference stack
 ======================
 
-The following diagram illustrates a possible configuration with SPMD and SPMC,
-one or multiple Secure Partitions, with or without an optional Hypervisor:
+The following diagram illustrates a possible configuration when the
+FEAT_SEL2 architecture extension is implemented, showing the SPMD
+and SPMC, one or multiple secure partitions, with an optional
+Hypervisor:
 
 .. image:: ../resources/diagrams/ff-a-spm-sel2.png
 
 TF-A build options
 ==================
 
-The following TF-A build options are provisioned:
+This section explains the TF-A build options involved in building with
+support for an FF-A based SPM where the SPMD is located at EL3 and the
+SPMC located at S-EL1 or S-EL2:
 
--  **SPD=spmd**: this option selects the SPMD component to relay FF-A
-   protocol from NWd to SWd back and forth. It is not possible to
-   enable another Secure Payload Dispatcher when this option is chosen.
--  **SPMD_SPM_AT_SEL2**: this option adjusts the SPMC execution
-   level to being S-EL1 or S-EL2. It defaults to enabled (value 1) when
-   SPD=spmd is chosen.
--  **CTX_INCLUDE_EL2_REGS**: this option permits saving (resp.
-   restoring) the EL2 system register context before entering (resp.
-   after leaving) the SPMC. It is mandatory when ``SPMD_SPM_AT_SEL2`` is
-   enabled. The context save/restore routine and exhaustive list of
-   registers is visible at `[4]`_.
--  **SP_LAYOUT_FILE**: this option provides a text description file
-   providing paths to SP binary images and DTS format manifests
-   (see `Specifying partition binary image and DT`_). It
-   is required when ``SPMD_SPM_AT_SEL2`` is enabled hence when multiple
-   secure partitions are to be loaded on behalf of SPMC.
+- **SPD=spmd**: this option selects the SPMD component to relay the FF-A
+  protocol from NWd to SWd back and forth. It is not possible to
+  enable another Secure Payload Dispatcher when this option is chosen.
+- **SPMD_SPM_AT_SEL2**: this option adjusts the SPMC exception
+  level to being S-EL1 or S-EL2. It defaults to enabled (value 1) when
+  SPD=spmd is chosen.
+- **CTX_INCLUDE_EL2_REGS**: this option permits saving (resp.
+  restoring) the EL2 system register context before entering (resp.
+  after leaving) the SPMC. It is mandatorily enabled when
+  ``SPMD_SPM_AT_SEL2`` is enabled. The context save/restore routine
+  and exhaustive list of registers is visible at `[4]`_.
+- **SP_LAYOUT_FILE**: this option specifies a text description file
+  providing paths to SP binary images and manifests in DTS format
+  (see `Describing secure partitions`_). It
+  is required when ``SPMD_SPM_AT_SEL2`` is enabled hence when multiple
+  secure partitions are to be loaded on behalf of the SPMC.
 
-+------------------------------+----------------------+------------------+
-|                              | CTX_INCLUDE_EL2_REGS | SPMD_SPM_AT_SEL2 |
-+------------------------------+----------------------+------------------+
-| SPMC at S-EL1 (e.g. OP-TEE)  |           0          |        0         |
-+------------------------------+----------------------+------------------+
-| SPMC at S-EL2 (e.g. Hafnium) |           1          | 1 (default when  |
-|                              |                      |    SPD=spmd)     |
-+------------------------------+----------------------+------------------+
++---------------+----------------------+------------------+
+|               | CTX_INCLUDE_EL2_REGS | SPMD_SPM_AT_SEL2 |
++---------------+----------------------+------------------+
+| SPMC at S-EL1 |         0            |        0         |
++---------------+----------------------+------------------+
+| SPMC at S-EL2 |         1            | 1 (default when  |
+|               |                      |    SPD=spmd)     |
++---------------+----------------------+------------------+
 
 Other combinations of such build options either break the build or are not
 supported.
 
-Note, the ``CTX_INCLUDE_EL2_REGS`` option provides the generic support for
-barely saving/restoring EL2 registers from an Arm arch perspective. As such
-it is decoupled from the ``SPD=spmd`` option.
+Notes:
 
-BL32 option is re-purposed to specify the SPMC image. It can specify either the
-Hafnium binary path (built for the secure world) or the path to a TEE binary
-implementing the FF-A protocol.
-
-BL33 option can specify either:
-
--  the TFTF binary or
--  the Hafnium binary path (built for the normal world) if VMs were loaded by
-   TF-A beforehand or
--  a minimal loader performing the loading of VMs and Hafnium.
+- Only Arm's FVP platform is supported to use with the TF-A reference software
+  stack.
+- The reference software stack uses FEAT_PAuth (formerly Armv8.3-PAuth) and
+  FEAT_BTI (formerly Armv8.5-BTI) architecture extensions by default at EL3
+  and S-EL2.
+- The ``CTX_INCLUDE_EL2_REGS`` option provides the generic support for
+  barely saving/restoring EL2 registers from an Arm arch perspective. As such
+  it is decoupled from the ``SPD=spmd`` option.
+- BL32 option is re-purposed to specify the SPMC image. It can specify either
+  the Hafnium binary path (built for the secure world) or the path to a TEE
+  binary implementing FF-A interfaces.
+- BL33 option can specify the TFTF binary or a normal world loader
+  such as U-Boot or the UEFI framework.
 
 Sample TF-A build command line when SPMC is located at S-EL1
-(typically pre-Armv8.4):
+(e.g. when the FEAT_EL2 architecture extension is not implemented):
 
 .. code:: shell
 
@@ -170,67 +184,108 @@
     SPD=spmd \
     SPMD_SPM_AT_SEL2=0 \
     BL32=<path-to-tee-binary> \
-    BL33=<path-to-nwd-binary> \
+    BL33=<path-to-bl33-binary> \
     PLAT=fvp \
     all fip
 
-Sample TF-A build command line for an Armv8.4-SecEL2 enabled system
-where SPMC is located at S-EL2:
+Sample TF-A build command line for a FEAT_SEL2 enabled system where the SPMC is
+located at S-EL2:
 
 .. code:: shell
 
     make \
     CROSS_COMPILE=aarch64-none-elf- \
+    PLAT=fvp \
     SPD=spmd \
     CTX_INCLUDE_EL2_REGS=1 \
-    ARM_ARCH_MINOR=4 \
-    BL32=<path-to-swd-hafnium-binary>
-    BL33=<path-to-nwd-binary> \
+    ARM_ARCH_MINOR=5 \
+    BRANCH_PROTECTION=1 \
+    CTX_INCLUDE_PAUTH_REGS=1 \
+    BL32=<path-to-hafnium-binary> \
+    BL33=<path-to-bl33-binary> \
     SP_LAYOUT_FILE=sp_layout.json \
-    PLAT=fvp \
     all fip
 
-Build options to enable secure boot:
+Same as above with enabling secure boot in addition:
 
 .. code:: shell
 
     make \
     CROSS_COMPILE=aarch64-none-elf- \
+    PLAT=fvp \
     SPD=spmd \
     CTX_INCLUDE_EL2_REGS=1 \
-    ARM_ARCH_MINOR=4 \
-    BL32=<path-to-swd-hafnium-binary>
-    BL33=<path-to-nwd-binary> \
-    SP_LAYOUT_FILE=../tf-a-tests/build/fvp/debug/sp_layout.json \
+    ARM_ARCH_MINOR=5 \
+    BRANCH_PROTECTION=1 \
+    CTX_INCLUDE_PAUTH_REGS=1 \
+    BL32=<path-to-hafnium-binary> \
+    BL33=<path-to-bl33-binary> \
+    SP_LAYOUT_FILE=sp_layout.json \
     MBEDTLS_DIR=<path-to-mbedtls-lib> \
     TRUSTED_BOARD_BOOT=1 \
     COT=dualroot \
     ARM_ROTPK_LOCATION=devel_rsa \
     ROT_KEY=plat/arm/board/common/rotpk/arm_rotprivk_rsa.pem \
     GENERATE_COT=1 \
-    PLAT=fvp \
     all fip
 
+FVP model invocation
+====================
+
+The FVP command line needs the following options to exercise the S-EL2 SPMC:
+
++---------------------------------------------------+------------------------------------+
+| - cluster0.has_arm_v8-5=1                         | Implements FEAT_SEL2, FEAT_PAuth,  |
+| - cluster1.has_arm_v8-5=1                         | and FEAT_BTI.                      |
++---------------------------------------------------+------------------------------------+
+| - pci.pci_smmuv3.mmu.SMMU_AIDR=2                  | Parameters required for the        |
+| - pci.pci_smmuv3.mmu.SMMU_IDR0=0x0046123B         | SMMUv3.2 modeling.                 |
+| - pci.pci_smmuv3.mmu.SMMU_IDR1=0x00600002         |                                    |
+| - pci.pci_smmuv3.mmu.SMMU_IDR3=0x1714             |                                    |
+| - pci.pci_smmuv3.mmu.SMMU_IDR5=0xFFFF0472         |                                    |
+| - pci.pci_smmuv3.mmu.SMMU_S_IDR1=0xA0000002       |                                    |
+| - pci.pci_smmuv3.mmu.SMMU_S_IDR2=0                |                                    |
+| - pci.pci_smmuv3.mmu.SMMU_S_IDR3=0                |                                    |
++---------------------------------------------------+------------------------------------+
+| - cluster0.has_branch_target_exception=1          | Implements FEAT_BTI.               |
+| - cluster1.has_branch_target_exception=1          |                                    |
++---------------------------------------------------+------------------------------------+
+| - cluster0.restriction_on_speculative_execution=2 | Required by the EL2 context        |
+| - cluster1.restriction_on_speculative_execution=2 | save/restore routine.              |
++---------------------------------------------------+------------------------------------+
+
+Sample FVP command line invocation:
+
+.. code:: shell
+
+    <path-to-fvp-model>/FVP_Base_RevC-2xAEMv8A -C pctl.startup=0.0.0.0
+    -C cluster0.NUM_CORES=4 -C cluster1.NUM_CORES=4 -C bp.secure_memory=1 \
+    -C bp.secureflashloader.fname=trusted-firmware-a/build/fvp/debug/bl1.bin \
+    -C bp.flashloader0.fname=trusted-firmware-a/build/fvp/debug/fip.bin \
+    -C bp.pl011_uart0.out_file=fvp-uart0.log -C bp.pl011_uart1.out_file=fvp-uart1.log \
+    -C bp.pl011_uart2.out_file=fvp-uart2.log \
+    -C cluster0.has_arm_v8-5=1 -C cluster1.has_arm_v8-5=1 -C pci.pci_smmuv3.mmu.SMMU_AIDR=2 \
+    -C pci.pci_smmuv3.mmu.SMMU_IDR0=0x0046123B -C pci.pci_smmuv3.mmu.SMMU_IDR1=0x00600002 \
+    -C pci.pci_smmuv3.mmu.SMMU_IDR3=0x1714 -C pci.pci_smmuv3.mmu.SMMU_IDR5=0xFFFF0472 \
+    -C pci.pci_smmuv3.mmu.SMMU_S_IDR1=0xA0000002 -C pci.pci_smmuv3.mmu.SMMU_S_IDR2=0 \
+    -C pci.pci_smmuv3.mmu.SMMU_S_IDR3=0 \
+    -C cluster0.has_branch_target_exception=1 \
+    -C cluster1.has_branch_target_exception=1 \
+    -C cluster0.restriction_on_speculative_execution=2 \
+    -C cluster1.restriction_on_speculative_execution=2
+
 Boot process
 ============
 
-Loading Hafnium and Secure Partitions in the secure world
+Loading Hafnium and secure partitions in the secure world
 ---------------------------------------------------------
 
-The Hafnium implementation in normal world requires VMs to be loaded in
-memory prior to booting. The mechanism upon which VMs are loaded and
-exposed to Hafnium are either:
+TF-A BL2 is the bootlader for the SPMC and SPs in the secure world.
 
--  by supplying a ramdisk image where VM images are concatenated (1)
--  or by providing VM load addresses within Hafnium manifest (2)
-
-TF-A is the bootlader for the Hafnium and SPs in the secure world. TF-A
-does not provide tooling or libraries manipulating ramdisks as required
-by (1). Thus BL2 loads SPs payloads independently.
 SPs may be signed by different parties (SiP, OEM/ODM, TOS vendor, etc.).
-Thus they are supplied as distinct “self-contained” signed entities within
-the FIP flash image. The FIP image itself is not signed hence providing
-ability to upgrade SPs in the field.
+Thus they are supplied as distinct signed entities within the FIP flash
+image. The FIP image itself is not signed hence this provides the ability
+to upgrade SPs in the field.
 
 Booting through TF-A
 --------------------
@@ -239,26 +294,27 @@
 ~~~~~~~~~~~~
 
 An SP manifest describes SP attributes as defined in `[1]`_
-section 3.1 (partition manifest at virtual FF-A instance) in DTS text format. It
-is represented as a single file associated with the SP. A sample is
+(partition manifest at virtual FF-A instance) in DTS format. It is
+represented as a single file associated with the SP. A sample is
 provided by `[5]`_. A binding document is provided by `[6]`_.
 
 Secure Partition packages
 ~~~~~~~~~~~~~~~~~~~~~~~~~
 
-Secure Partitions are bundled as independent package files consisting
+Secure partitions are bundled as independent package files consisting
 of:
 
--  a header
--  a DTB
--  an image payload
+- a header
+- a DTB
+- an image payload
 
 The header starts with a magic value and offset values to SP DTB and
 image payload. Each SP package is loaded independently by BL2 loader
 and verified for authenticity and integrity.
 
-The SP package identified by its UUID (matching FF-A uuid) is inserted
-as a single entry into the FIP at end of the TF-A build flow as shown:
+The SP package identified by its UUID (matching FF-A uuid property) is
+inserted as a single entry into the FIP at end of the TF-A build flow
+as shown:
 
 .. code:: shell
 
@@ -276,18 +332,17 @@
 
 .. uml:: ../resources/diagrams/plantuml/fip-secure-partitions.puml
 
-Specifying partition binary image and DT
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Describing secure partitions
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-A description file (json format) is passed to the build flow specifying
-paths to the SP binary image and associated DTS partition manifest file.
-The latter is going through the dtc compiler to generate the dtb fed into
-the SP package.
-This file also specifies the owner of the SP, which is an optional field and
-identifies the signing domain in case of dualroot CoT.
-The possible owner of an SP could either be Silicon Provider or Platform, and
-the corresponding "owner" field value could either be "SiP" or "Plat".
-In absence of "owner" field, it defaults to "SiP".
+A json-formatted description file is passed to the build flow specifying paths
+to the SP binary image and associated DTS partition manifest file. The latter
+is processed by the dtc compiler to generate a DTB fed into the SP package.
+This file also specifies the SP owner (as an optional field) identifying the
+signing domain in case of dual root CoT.
+The SP owner can either be the silicon or the platform provider. The
+corresponding "owner" field value can either take the value of "SiP" or "Plat".
+In absence of "owner" field, it defaults to "SiP" owner.
 
 .. code:: shell
 
@@ -308,14 +363,16 @@
 SPMC manifest
 ~~~~~~~~~~~~~
 
-This manifest contains an SPMC attributes node consumed by SPMD at boot time. It
-is implementing the description from `[1]`_ section 3.2 (SP manifest at physical
-FF-A instance). The SP manifest at physical FF-A instance is used by the SPMD to
-setup a SP that co-resides with the SPMC and executes at S-EL1 or Secure
-Supervisor mode.
+This manifest contains the SPMC *attribute* node consumed by the SPMD at boot
+time. It implements `[1]`_ (SP manifest at physical FF-A instance) and serves
+two different cases:
 
-In this implementation its usage is extended to the secure physical FF-A
-instance where SPMC executes at S-EL2.
+- The SPMC resides at S-EL1: the SPMC manifest is used by the SPMD to setup a
+  SP that co-resides with the SPMC and executes at S-EL1 or Secure Supervisor
+  mode.
+- The SPMC resides at S-EL2: the SPMC manifest is used by the SPMD to setup
+  the environment required by the SPMC to run at S-EL2. SPs run at S-EL1 or
+  S-EL0.
 
 .. code:: shell
 
@@ -329,166 +386,147 @@
         binary_size = <0x60000>;
     };
 
--  *spmc_id* defines the endpoint ID value that SPMC can query through
-   ``FFA_ID_GET``.
--  *maj_ver/min_ver*. SPMD checks provided version versus its internal
-   version and aborts if not matching.
--  *exec_state* defines SPMC execution state (can be AArch64 for
-   Hafnium, or AArch64/AArch32 for OP-TEE at S-EL1).
--  *load_address* and *binary_size* are mostly used to verify secondary
-   entry points fit into the loaded binary image.
--  *entrypoint* defines the cold boot primary core entry point used by
-   SPMD (currently matches ``BL32_BASE``)
+- *spmc_id* defines the endpoint ID value that SPMC can query through
+  ``FFA_ID_GET``.
+- *maj_ver/min_ver*. SPMD checks provided version versus its internal
+  version and aborts if not matching.
+- *exec_state* defines the SPMC execution state (AArch64 or AArch32).
+  Notice Hafnium used as a SPMC only supports AArch64.
+- *load_address* and *binary_size* are mostly used to verify secondary
+  entry points fit into the loaded binary image.
+- *entrypoint* defines the cold boot primary core entry point used by
+  SPMD (currently matches ``BL32_BASE``) to enter the SPMC.
 
 Other nodes in the manifest are consumed by Hafnium in the secure world.
 A sample can be found at [7]:
 
--  The *chosen* node is currently unused in SWd. It is meant for NWd to
-   specify the init ramdisk image.
--  The *hypervisor* node describes SPs. *is_ffa_partition* boolean
-   attribute indicates an SP. Load-addr field specifies the load address
-   at which TF-A loaded the SP package.
--  *cpus* node provide the platform topology and allows MPIDR to VMPIDR
-   mapping. Notice with current implementation primary cpu is declared
-   first, then secondary cpus must be declared in reverse order.
+- The *hypervisor* node describes SPs. *is_ffa_partition* boolean attribute
+  indicates a FF-A compliant SP. The *load_address* field specifies the load
+  address at which TF-A loaded the SP package.
+- *cpus* node provide the platform topology and allows MPIDR to VMPIDR mapping.
+  Note the primary core is declared first, then secondary core are declared
+  in reverse order.
+- The *memory* node provides platform information on the ranges of memory
+  available to the SPMC.
 
 SPMC boot
 ~~~~~~~~~
 
 The SPMC is loaded by BL2 as the BL32 image.
 
-The SPMC manifest is loaded by BL2 as the ``TOS_FW_CONFIG`` image.
+The SPMC manifest is loaded by BL2 as the ``TOS_FW_CONFIG`` image `[9]`_.
 
 BL2 passes the SPMC manifest address to BL31 through a register.
 
-BL31(SPMD) runs from primary core, initializes the core contexts and
-launches BL32 passing the SPMC manifest address through a register.
+At boot time, the SPMD in BL31 runs from the primary core, initializes the core
+contexts and launches the SPMC (BL32) passing the following information through
+registers:
+
+- X0 holds the ``TOS_FW_CONFIG`` physical address (or SPMC manifest blob).
+- X1 holds the ``HW_CONFIG`` physical address.
+- X4 holds the currently running core linear id.
 
 Loading of SPs
 ~~~~~~~~~~~~~~
 
+At boot time, BL2 loads SPs sequentially in addition to the SPMC as depicted
+below:
+
 .. uml:: ../resources/diagrams/plantuml/bl2-loading-sp.puml
 
-
-Notice this boot flow is an implementation sample on Arm's FVP platform. Platforms
-not using FW_CONFIG would adjust to a different implementation.
+Note this boot flow is an implementation sample on Arm's FVP platform.
+Platforms not using TF-A's *Firmware CONFiguration* framework would adjust to a
+different implementation.
 
 Secure boot
 ~~~~~~~~~~~
 
 The SP content certificate is inserted as a separate FIP item so that BL2 loads SPMC,
-SPMC manifest and Secure Partitions and verifies them for authenticity and integrity.
+SPMC manifest, secure partitions and verifies them for authenticity and integrity.
 Refer to TBBR specification `[3]`_.
 
-The multiple-signing domain feature (in current state dual signing domain) allows
-the use of two root keys namely S-ROTPK and NS-ROTPK (see `[8]`_):
+The multiple-signing domain feature (in current state dual signing domain `[8]`_) allows
+the use of two root keys namely S-ROTPK and NS-ROTPK:
 
--  SPMC (BL32) and SPMC manifest are signed by the SiP using the S-ROTPK.
--  BL33 may be signed by the OEM using NS-ROTPK.
--  An SP may be signed either by SiP (using S-ROTPK) or by OEM (using NS-ROTPK).
+- SPMC (BL32) and SPMC manifest are signed by the SiP using the S-ROTPK.
+- BL33 may be signed by the OEM using NS-ROTPK.
+- An SP may be signed either by SiP (using S-ROTPK) or by OEM (using NS-ROTPK).
 
-Longer term multiple signing domain will allow additional signing keys, e.g.
-if SPs originate from different parties.
-
-See `TF-A build options`_ for a sample build command line.
+Also refer to `Describing secure partitions`_ and `TF-A build options`_ sections.
 
 Hafnium in the secure world
 ===========================
 
-**NOTE: this section is work in progress. Descriptions and implementation choices
-are subject to evolve.**
-
 General considerations
 ----------------------
 
 Build platform for the secure world
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-The implementation might add specific code parts only relevant to the
-secure world. Such code parts might be isolated into different files
-and/or conditional code enclosed by a ``SECURE_WORLD`` macro.
+In the Hafnium reference implementation specific code parts are only relevant to
+the secure world. Such portions are isolated in architecture specific files
+and/or enclosed by a ``SECURE_WORLD`` macro.
 
-Secure Partitions CPU scheduling
+Secure partitions CPU scheduling
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-In the normal world, VMs are scheduled by the FFA_RUN ABI invoked from the
-primary scheduler (in the primary VM), or by a direct message request or
-response.
+The FF-A v1.0 specification `[1]`_ provides two ways to relinquinsh CPU time to
+secure partitions. For this a VM (Hypervisor or OS kernel), or SP invokes one of:
 
-With the FF-A EAC specification, Secure Partitions are scheduled by direct
-message invocations from a NWd VM or another SP.
+- the FFA_MSG_SEND_DIRECT_REQ interface.
+- the FFA_RUN interface.
 
 Platform topology
 ~~~~~~~~~~~~~~~~~
 
-As stated in `[1]`_ section 4.4.1 the SPMC implementation assumes the
+The *execution-ctx-count* SP manifest field can take the value of one or the
+total number of PEs. The FF-A v1.0 specification `[1]`_  recommends the
 following SP types:
 
--  Pinned MP SPs: an Execution Context id matches a physical PE id. MP
-   SPs must implement the same number of ECs as the number of PEs in the
-   platform. Hence the *execution-ctx-count* as defined by
-   `[1]`_ (or NWd-Hafnium *vcpu_count*) can only take the
-   value of one or the number of physical PEs.
--  Migratable UP SPs: a single execution context can run and be migrated
-   on any physical PE. It declares a single EC in its SP manifest. An UP
-   SP can receive a direct message request on any physical core.
-
-Usage of PSCI services in the secure world
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-- The normal world Hypervisor (optional) or OS kernel issues PSCI service
-  invocations e.g. to request PSCI version, wake-up a secondary core, or request
-  core suspend. This happens at the non-secure physical FF-A instance. In the
-  example case of Hafnium in the normal world, it boots on the primary core and
-  one of the first initialization step is to request the PSCI version. It then
-  launches the primary VM. The primary VM upon initializing performs PSCI service
-  calls (at non-secure virtual FF-A instance) which are trapped by the
-  Hypervisor. Invocation from OS Kernel ends straight at EL3. The PVM issues
-  ``PSCI_CPU_ON`` service calls to wake-up secondary cores by passing an
-  ``MPIDR``, entry point address and a CPU context address. The EL3 PSCI layer
-  then performs an exception return to the secondary core entry point on the
-  targeted core. Other PSCI calls can happen at run-time from the PVM e.g. to
-  request core suspend.
-- In the existing TF-A PSCI standard library, PSCI service calls are filtered at
-  EL3 to only originate from the NWd. Thus concerning the SPMC (at secure
-  physical FF-A instance) the PSCI service invocations cannot happen as in the
-  normal world. For example, a ``PSCI_CPU_ON`` service invocation from the SPMC
-  does not reach the PSCI layer.
+- Pinned MP SPs: an execution context matches a physical PE. MP SPs must
+  implement the same number of ECs as the number of PEs in the platform.
+- Migratable UP SPs: a single execution context can run and be migrated on any
+  physical PE. Such SP declares a single EC in its SP manifest. An UP SP can
+  receive a direct message request originating from any physical core targeting
+  the single execution context.
 
 Parsing SP partition manifests
 ------------------------------
 
-Hafnium must be able to consume SP manifests as defined in
-`[1]`_ section 3.1, at least for the mandatory fields.
+Hafnium consumes SP manifests as defined in `[1]`_ and `SP manifests`_.
+Note the current implementation may not implement all optional fields.
 
-The SP manifest may contain memory and device regions nodes.
+The SP manifest may contain memory and device regions nodes. In case of
+an S-EL2 SPMC:
 
--  Memory regions shall be mapped in the SP Stage-2 translation regime at
-   load time. A memory region node can specify RX/TX buffer regions in which
-   case it is not necessary for an SP to explicitly call the ``FFA_RXTX_MAP``
-   service.
--  Device regions shall be mapped in SP Stage-2 translation regime as
-   peripherals and possibly allocate additional resources (e.g. interrupts)
+- Memory regions are mapped in the SP EL1&0 Stage-2 translation regime at
+  load time (or EL1&0 Stage-1 for an S-EL1 SPMC). A memory region node can
+  specify RX/TX buffer regions in which case it is not necessary for an SP
+  to explicitly invoke the ``FFA_RXTX_MAP`` interface.
+- Device regions are mapped in the SP EL1&0 Stage-2 translation regime (or
+  EL1&0 Stage-1 for an S-EL1 SPMC) as peripherals and possibly allocate
+  additional resources (e.g. interrupts).
 
-Base addresses for memory and device region nodes are IPAs provided SPMC
-identity maps IPAs to PAs within SP Stage-2 translation regime.
+For the S-EL2 SPMC, base addresses for memory and device region nodes are IPAs
+provided the SPMC identity maps IPAs to PAs within SP EL1&0 Stage-2 translation
+regime.
 
-Note: currently both VTTBR_EL2 and VSTTBR_EL2 resolve to the same set of page
-tables. It is still open whether two sets of page tables shall be provided per
-SP. The memory region node as defined in the spec (section 3.1 Table 10)
+Note: in the current implementation both VTTBR_EL2 and VSTTBR_EL2 point to the
+same set of page tables. It is still open whether two sets of page tables shall
+be provided per SP. The memory region node as defined in the specification
 provides a memory security attribute hinting to map either to the secure or
-non-secure stage-2 table.
+non-secure EL1&0 Stage-2 table if it exists.
 
 Passing boot data to the SP
 ---------------------------
 
-`[1]`_ Section 3.4.2 “Protocol for passing data” defines a
-method to passing boot data to SPs (not currently implemented).
+In `[1]`_ , the "Protocol for passing data" section defines a method for passing
+boot data to SPs (not currently implemented).
 
-Provided that the whole Secure Partition package image (see `Secure
-Partition packages`_) is mapped to the SP's secure Stage-2 translation
-regime, an SP can access its own manifest DTB blob and extract its partition
-manifest properties.
+Provided that the whole secure partition package image (see
+`Secure Partition packages`_) is mapped to the SP secure EL1&0 Stage-2
+translation regime, an SP can access its own manifest DTB blob and extract its
+partition manifest properties.
 
 SP Boot order
 -------------
@@ -497,347 +535,540 @@
 dependencies such as an SP providing a service required to properly boot
 another SP.
 
+It is possible for an SP to call into another SP through a direct request
+provided the latter SP has already been booted.
+
 Boot phases
 -----------
 
 Primary core boot-up
 ~~~~~~~~~~~~~~~~~~~~
 
-The SPMC performs its platform initializations then loads and creates
-secure partitions based on SP packages and manifests. Then each secure
-partition is launched in sequence (see `SP Boot order`_) on their primary
-Execution Context.
+Upon boot-up, BL31 hands over to the SPMC (BL32) on the primary boot physical
+core. The SPMC performs its platform initializations and registers the SPMC
+secondary physical core entry point physical address by the use of the
+FFA_SECONDARY_EP_REGISTER interface (SMC invocation from the SPMC to the SPMD
+at secure physical FF-A instance). This interface is implementation-defined in
+context of FF-A v1.0.
 
-Notice the primary physical core may not be core 0. Hence if the primary
-core linear id is N, the 1:1 mapping requires MP SPs are launched using
-EC[N] on PE[N] (see `Platform topology`_).
+The SPMC then creates secure partitions based on SP packages and manifests. Each
+secure partition is launched in sequence (`SP Boot order`_) on their "primary"
+execution context. If the primary boot physical core linear id is N, an MP SP is
+started using EC[N] on PE[N] (see `Platform topology`_). If the partition is a
+UP SP, it is started using its unique EC0 on PE[N].
 
-The SP's primary Execution Context (or the EC used when the partition is booted)
-exits through ``FFA_MSG_WAIT`` to indicate successful initialization.
+The SP primary EC (or the EC used when the partition is booted as described
+above):
 
-Secondary physical core boot-up
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+- Performs the overall SP boot time initialization, and in case of a MP SP,
+  prepares the SP environment for other execution contexts.
+- In the case of a MP SP, it invokes the FFA_SECONDARY_EP_REGISTER at secure
+  virtual FF-A instance (SMC invocation from SP to SPMC) to provide the IPA
+  entry point for other execution contexts.
+- Exits through ``FFA_MSG_WAIT`` to indicate successful initialization or
+  ``FFA_ERROR`` in case of failure.
 
-Upon boot-up, the SPMC running on the primary core performs
-implementation-defined SPMD service calls at secure physical FF-A instance
-to register the secondary physical cores entry points and context information:
+Secondary cores boot-up
+~~~~~~~~~~~~~~~~~~~~~~~
 
--  This is done through a direct message request invocation to the SPMD
-   (``SET_ENTRY_POINT``). This service call does not wake-up the targeted
-   core immediately. The secondary core is woken up later by a NWd
-   ``PSCI_CPU_ON`` service invocation. A notification is passed from EL3
-   PSCI layer to the SPMD, and then to SPMC through an implementation-defined
-   interface.
--  The SPMC/SPMD interface can consist of FF-A direct message requests/responses
-   transporting PM events.
+Once the system is started and NWd brought up, a secondary physical core is
+woken up by the ``PSCI_CPU_ON`` service invocation. The TF-A SPD hook mechanism
+calls into the SPMD on the newly woken up physical core. Then the SPMC is
+entered at the secondary physical core entry point.
 
-If there is no Hypervisor in the normal world, the OS Kernel issues
-``PSCI_CPU_ON`` calls that are directly trapped to EL3.
+In the current implementation, the first SP is resumed on the coresponding EC
+(the virtual CPU which matches the physical core). The implication is that the
+first SP must be a MP SP.
 
-When a secondary physical core wakes-up the SPMD notifies the SPMC which updates
-its internal states reflecting current physical core is being turned on.
-It might then return straight to the SPMD and then to the NWd.
+In a linux based system, once secure and normal worlds are booted but prior to
+a NWd FF-A driver has been loaded:
 
-*(under discussion)* There may be possibility that an SP registers "PM events"
-(during primary EC boot stage) through an ad-hoc interface. Such events would
-be relayed by SPMC to one or more registered SPs on need basis
-(see `Power management`_).
+- The first SP has initialized all its ECs in response to primary core boot up
+  (at system initialization) and secondary core boot up (as a result of linux
+  invoking PSCI_CPU_ON for all secondary cores).
+- Other SPs have their first execution context initialized as a result of secure
+  world initialization on the primary boot core. Other ECs for those SPs have to
+  be run first through ffa_run to complete their initialization (which results
+  in the EC completing with FFA_MSG_WAIT).
 
-Secondary virtual core boot-up
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-In the example case where Hafnium exists in the normal world, secondary VMs
-issue a ``PSCI_CPU_ON`` service call which is trapped to the Hypervisor. The
-latter then enables the vCPU context for the targeted core, and switches to
-the PVM down to the kernel driver with an ``HF_WAKE_UP`` message. The NWd
-driver in PVM can then schedule the newly woken up vCPU context.
-
-In the secure world the primary EC of a given SP passes the secondary EC entry
-point and context. The SMC service call is trapped into the SPMC. This can be
-either *(under discussion)*:
-
--  a specific interface registering the secondary EC entry point,
-   similarly to above ``SET_ENTRY_POINT`` service.
--  Re-purposing the ``PSCI_CPU_ON`` function id. It is
-   assumed that even if the input arguments are the same as the ones defined in
-   the PSCI standard, the usage deviates by the fact the secondary EC is not
-   woken up immediately. At least for the PSA-FF-A EAC where only
-   direct messaging is allowed, it is only after the first direct
-   message invocation that the secondary EC is entered. This option
-   might be preferred when the same code base is re-used for a VM or
-   an SP. The ABI to wake-up a secondary EC can remain similar.
-
-SPs are always scheduled from the NWd, this paradigm did not change from legacy
-TEEs. There must always be some logic (or driver) in the NWd to relinquish CPU
-cycles to the SWd. If primary core is 0, an SP EC[x>0] entry point is supplied
-by the SP EC[0] when the system boots in SWd. But this EC[x] is not immediately
-entered at boot. Later in the boot process when NWd is up, a direct message
-request issued from physical core 1 ends up in SP EC[1], and only at this stage
-this context is effectively scheduled.
-
-It should be possible for an SP to call into another SP through direct message
-provided the latter SP has been booted already. The "boot-order" field in
-partition manifests (`SP Boot order`_) fulfills the dependency towards availability
-of a service within an SP offered to another SP.
+Refer to `Power management`_ for further details.
 
 Mandatory interfaces
 --------------------
 
-The following interfaces must be exposed to any VM or SP:
+The following interfaces are exposed to SPs:
 
--  ``FFA_STATUS``
--  ``FFA_ERROR``
--  ``FFA_INTERRUPT``
 -  ``FFA_VERSION``
 -  ``FFA_FEATURES``
 -  ``FFA_RX_RELEASE``
 -  ``FFA_RXTX_MAP``
--  ``FFA_RXTX_UNMAP``
+-  ``FFA_RXTX_UNMAP`` (not implemented)
 -  ``FFA_PARTITION_INFO_GET``
 -  ``FFA_ID_GET``
+-  ``FFA_MSG_WAIT``
+-  ``FFA_MSG_SEND_DIRECT_REQ``
+-  ``FFA_MSG_SEND_DIRECT_RESP``
+-  ``FFA_MEM_DONATE``
+-  ``FFA_MEM_LEND``
+-  ``FFA_MEM_SHARE``
+-  ``FFA_MEM_RETRIEVE_REQ``
+-  ``FFA_MEM_RETRIEVE_RESP``
+-  ``FFA_MEM_RELINQUISH``
+-  ``FFA_MEM_RECLAIM``
+-  ``FFA_SECONDARY_EP_REGISTER``
 
 FFA_VERSION
 ~~~~~~~~~~~
 
-Per `[1]`_ section 8.1 ``FFA_VERSION`` requires a
-*requested_version* parameter from the caller.
+``FFA_VERSION`` requires a *requested_version* parameter from the caller.
+The returned value depends on the caller:
 
-In the current implementation when ``FFA_VERSION`` is invoked from:
-
--  Hypervisor in NS-EL2: the SPMD returns the SPMC version specified
-   in the SPMC manifest.
--  OS kernel in NS-EL1 when NS-EL2 is not present: the SPMD returns the
-   SPMC version specified in the SPMC manifest.
--  VM in NWd: the Hypervisor returns its implemented version.
--  SP in SWd: the SPMC returns its implemented version.
--  SPMC at S-EL1/S-EL2: the SPMD returns its implemented version.
+- Hypervisor or OS kernel in NS-EL1/EL2: the SPMD returns the SPMC version
+  specified in the SPMC manifest.
+- SP: the SPMC returns its own implemented version.
+- SPMC at S-EL1/S-EL2: the SPMD returns its own implemented version.
 
 FFA_FEATURES
 ~~~~~~~~~~~~
 
-FF-A features may be discovered by Secure Partitions while booting
-through the SPMC. However, SPMC cannot get features from Hypervisor
-early at boot time as NS world is not setup yet.
+FF-A features supported by the SPMC may be discovered by secure partitions at
+boot (that is prior to NWd is booted) or run-time.
 
-The Hypervisor may decide to gather FF-A features from SPMC through SPMD
-once at boot time and store the result. Later when a VM requests FF-A
-features, the Hypervisor can adjust its own set of features with what
-SPMC advertised, if necessary. Another approach is to always forward FF-A
-features to the SPMC when a VM requests it to the Hypervisor. Although
-the result is not supposed to change over time so there may not be added
-value doing the systematic forwarding.
+The SPMC calling FFA_FEATURES at secure physical FF-A instance always get
+FFA_SUCCESS from the SPMD.
+
+The request made by an Hypervisor or OS kernel is forwarded to the SPMC and
+the response relayed back to the NWd.
 
 FFA_RXTX_MAP/FFA_RXTX_UNMAP
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-VM mailboxes are re-purposed to serve as SP RX/TX buffers. The RX/TX
-map API maps the send and receive buffer IPAs to the SP Stage-2 translation regime.
+When invoked from a secure partition FFA_RXTX_MAP maps the provided send and
+receive buffers described by their IPAs to the SP EL1&0 Stage-2 translation
+regime as secure buffers in the MMU descriptors.
 
-Hafnium in the normal world defines VMs and their attributes as logical structures,
-including a mailbox used for FF-A indirect messaging, memory sharing, or the
-`FFA_PARTITION_INFO_GET`_  ABI.
-This same mailbox structure is re-used in the SPMC. `[1]`_ states only direct
-messaging is allowed to SPs. Thus mailbox usage is restricted to implementing
-`FFA_PARTITION_INFO_GET`_ and memory sharing ABIs.
+When invoked from the Hypervisor or OS kernel, the buffers are mapped into the
+SPMC EL2 Stage-1 translation regime and marked as NS buffers in the MMU
+descriptors.
+
+Note:
+
+- FFA_RXTX_UNMAP is not implemented.
 
 FFA_PARTITION_INFO_GET
 ~~~~~~~~~~~~~~~~~~~~~~
 
-Partition info get service call can originate:
+Partition info get call can originate:
 
--  from SP to SPM
--  from VM to Hypervisor
--  from Hypervisor to SPM
-
-For the latter case, the service call must be forwarded through the SPMD.
+- from SP to SPMC
+- from Hypervisor or OS kernel to SPMC. The request is relayed by the SPMD.
 
 FFA_ID_GET
 ~~~~~~~~~~
 
-The SPMD returns:
-
--  a default zero value on invocation from the Hypervisor.
--  The ``spmc_id`` value specified in the SPMC manifest on invocation from
-   the SPMC (see `SPMC manifest`_)
-
 The FF-A id space is split into a non-secure space and secure space:
 
--  FF-A id with bit 15 clear refer to normal world VMs.
--  FF-A id with bit 15 set refer to secure world SPs
+- FF-A ID with bit 15 clear relates to VMs.
+- FF-A ID with bit 15 set related to SPs.
+- FF-A IDs 0, 0xffff, 0x8000 are assigned respectively to the Hypervisor, SPMD
+  and SPMC.
 
-Such convention helps the SPMC discriminating the origin and destination worlds
-in an FF-A service invocation. In particular the SPMC shall filter unauthorized
+The SPMD returns:
+
+- The default zero value on invocation from the Hypervisor.
+- The ``spmc_id`` value specified in the SPMC manifest on invocation from
+  the SPMC (see `SPMC manifest`_)
+
+This convention helps the SPMC to determine the origin and destination worlds in
+an FF-A ABI invocation. In particular the SPMC shall filter unauthorized
 transactions in its world switch routine. It must not be permitted for a VM to
-use a secure FF-A id as origin world through spoofing:
+use a secure FF-A ID as origin world by spoofing:
 
--  A VM-to-SP messaging passing shall have an origin world being non-secure
-   (FF-A id bit 15 clear) and destination world being secure (FF-A id bit 15
-   set).
--  Similarly, an SP-to-SP message shall have FF-A id bit 15 set for both origin
-   and destination ids.
+- A VM-to-SP direct request/response shall set the origin world to be non-secure
+  (FF-A ID bit 15 clear) and destination world to be secure (FF-A ID bit 15
+  set).
+- Similarly, an SP-to-SP direct request/response shall set the FF-A ID bit 15
+  for both origin and destination IDs.
 
 An incoming direct message request arriving at SPMD from NWd is forwarded to
 SPMC without a specific check. The SPMC is resumed through eret and "knows" the
 message is coming from normal world in this specific code path. Thus the origin
-endpoint id must be checked by SPMC for being a normal world id.
+endpoint ID must be checked by SPMC for being a normal world ID.
 
 An SP sending a direct message request must have bit 15 set in its origin
-endpoint id and this can be checked by the SPMC when the SP invokes the ABI.
+endpoint ID and this can be checked by the SPMC when the SP invokes the ABI.
 
 The SPMC shall reject the direct message if the claimed world in origin endpoint
-id is not consistent:
+ID is not consistent:
 
--  It is either forwarded by SPMD and thus origin endpoint id must be a "normal
-   world id",
--  or initiated by an SP and thus origin endpoint id must be a "secure world id".
+-  It is either forwarded by SPMD and thus origin endpoint ID must be a "normal
+   world ID",
+-  or initiated by an SP and thus origin endpoint ID must be a "secure world ID".
 
-Direct messaging
-----------------
 
-This is a mandatory interface for Secure Partitions consisting in direct
-message request and responses.
+FFA_MSG_SEND_DIRECT_REQ/FFA_MSG_SEND_DIRECT_RESP
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-The ``ffa_handler`` Hafnium function may:
+This is a mandatory interface for secure partitions consisting in direct request
+and responses with the following rules:
 
--  trigger a world change e.g. when an SP invokes the direct message
-   response ABI to a VM.
--  handle multiple requests from the NWd without resuming an SP.
+- An SP can send a direct request to another SP.
+- An SP can receive a direct request from another SP.
+- An SP can send a direct response to another SP.
+- An SP cannot send a direct request to an Hypervisor or OS kernel.
+- An Hypervisor or OS kernel can send a direct request to an SP.
+- An SP can send a direct response to an Hypervisor or OS kernel.
 
-SP-to-SP
-~~~~~~~~
+SPMC-SPMD direct requests/responses
+-----------------------------------
 
--  An SP can send a direct message request to another SP
--  An SP can receive a direct message response from another SP.
+Implementation-defined FF-A IDs are allocated to the SPMC and SPMD.
+Using those IDs in source/destination fields of a direct request/response
+permits SPMD to SPMC communication and either way.
 
-VM-to-SP
-~~~~~~~~
+- SPMC to SPMD direct request/response uses SMC conduit.
+- SPMD to SPMC direct request/response uses ERET conduit.
 
--  A VM can send a direct message request to an SP
--  An SP can send a direct message response to a VM
+PE MMU configuration
+--------------------
 
-SPMC-SPMD messaging
-~~~~~~~~~~~~~~~~~~~
+With secure virtualization enabled, two IPA spaces are output from the secure
+EL1&0 Stage-1 translation (secure and non-secure). The EL1&0 Stage-2 translation
+hardware is fed by:
 
-Specific implementation-defined endpoint IDs are allocated to the SPMC and SPMD.
-Referring those IDs in source/destination fields of a direct message
-request/response permits SPMD to SPMC messaging back and forth.
+- A single secure IPA space when the SP EL1&0 Stage-1 MMU is disabled.
+- Two IPA spaces (secure and non-secure) when the SP EL1&0 Stage-1 MMU is
+  enabled.
 
-Per `[1]`_ Table 114 Config No. 1 (physical FF-A instance):
+``VTCR_EL2`` and ``VSTCR_EL2`` provide configuration bits for controlling the
+NS/S IPA translations.
+``VSTCR_EL2.SW`` = 0, ``VSTCR_EL2.SA`` = 0,``VTCR_EL2.NSW`` = 0, ``VTCR_EL2.NSA`` = 1:
 
--  SPMC=>SPMD direct message request uses SMC conduit
--  SPMD=>SPMC direct message request uses ERET conduit
+- Stage-2 translations for the NS IPA space access the NS PA space.
+- Stage-2 translation table walks for the NS IPA space are to the secure PA space.
 
-Per `[1]`_ Table 118 Config No. 1 (physical FF-A instance):
-
--  SPMC=>SPMD direct message response uses SMC conduit
--  SPMD=>SPMC direct message response uses ERET conduit
-
-Memory management
------------------
-
-This section only deals with the PE MMU configuration.
-
-Hafnium in the normal world deals with NS buffers only and provisions
-a single root page table directory to VMs. In context of S-EL2 enabled
-firmware, two IPA spaces are output from Stage-1 translation (secure
-and non-secure). The Stage-2 translation handles:
-
--  A single secure IPA space when an SP Stage-1 MMU is disabled.
--  Two IPA spaces (secure and non-secure) when Stage-1 MMU is enabled.
-
-``VTCR_EL2`` and ``VSTCR_EL2`` provide additional bits for controlling the
-NS/S IPA translations (``VSTCR_EL2.SW``, ``VSTCR_EL2.SA``, ``VTCR_EL2.NSW``,
-``VTCR_EL2.NSA``). There may be two approaches:
-
--  secure and non-secure mappings are rooted as two separate root page
-   tables
--  secure and non-secure mappings use the same root page table. Access
-   from S-EL1 to an NS region translates to a secure physical address
-   space access.
+Secure and non-secure IPA regions use the same set of Stage-2 page tables within
+a SP.
 
 Interrupt management
 --------------------
 
-Road to a para-virtualized interface
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+GIC ownership
+~~~~~~~~~~~~~
 
-Current Hafnium implementation uses an ad-hoc mechanism for a VM to get
-a pending interrupt number through an hypercall. The PVM injects
-interrupts to VMs by delegation from the Hypervisor. The PVM probes a
-pending interrupt directly from the GIC distributor.
+The SPMC owns the GIC configuration. Secure and non-secure interrupts are
+trapped at S-EL2. The SPMC manages interrupt resources and allocates interrupt
+IDs based on SP manifests. The SPMC acknowledges physical interrupts and injects
+virtual interrupts by setting the use of vIRQ/vFIQ bits before resuming a SP.
 
-The short-term plan is to have Hafnium/SPMC in the secure world owner
-of the GIC configuration.
+Non-secure interrupt handling
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
-The SPMC fully owns the GIC configuration at S-EL2. The SPMC manages
-interrupt resources and allocates interrupt ID based on SP manifests.
-The SPMC acknowledges physical interrupts and injects virtual interrupts
-by setting the vIRQ bit when resuming an SP. A Secure Partition gathers
-the interrupt number through an hypercall.
+The following illustrate the scenarios of non secure physical interrupts trapped
+by the SPMC:
 
-Notice the SPMC/SPMD has to handle Group0 secure interrupts in addition
-to Group1 S/NS interrupts.
+- The SP handles a managed exit operation:
+
+.. image:: ../resources/diagrams/ffa-ns-interrupt-handling-managed-exit.png
+
+- The SP is pre-empted without managed exit:
+
+.. image:: ../resources/diagrams/ffa-ns-interrupt-handling-sp-preemption.png
+
+Secure interrupt handling
+-------------------------
+
+This section documents the support implemented for secure interrupt handling in
+SPMC as per the guidance provided by FF-A v1.1 Beta0 specification.
+The following assumptions are made about the system configuration:
+
+  - In the current implementation, S-EL1 SPs are expected to use the para
+    virtualized ABIs for interrupt management rather than accessing virtual GIC
+    interface.
+  - Unless explicitly stated otherwise, this support is applicable only for
+    S-EL1 SPs managed by SPMC.
+  - Secure interrupts are configured as G1S or G0 interrupts.
+  - All physical interrupts are routed to SPMC when running a secure partition
+    execution context.
+
+A physical secure interrupt could preempt normal world execution. Moreover, when
+the execution is in secure world, it is highly likely that the target of a
+secure interrupt is not the currently running execution context of an SP. It
+could be targeted to another FF-A component. Consequently, secure interrupt
+management depends on the state of the target execution context of the SP that
+is responsible for handling the interrupt. Hence, the spec provides guidance on
+how to signal start and completion of secure interrupt handling as discussed in
+further sections.
+
+Secure interrupt signaling mechanisms
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Signaling refers to the mechanisms used by SPMC to indicate to the SP execution
+context that it has a pending virtual interrupt and to further run the SP
+execution context, such that it can handle the virtual interrupt. SPMC uses
+either the FFA_INTERRUPT interface with ERET conduit or vIRQ signal for signaling
+to S-EL1 SPs. When normal world execution is preempted by a secure interrupt,
+the SPMD uses the FFA_INTERRUPT ABI with ERET conduit to signal interrupt to SPMC
+running in S-EL2.
+
++-----------+---------+---------------+---------------------------------------+
+| SP State  | Conduit | Interface and | Description                           |
+|           |         | parameters    |                                       |
++-----------+---------+---------------+---------------------------------------+
+| WAITING   | ERET,   | FFA_INTERRUPT,| SPMC signals to SP the ID of pending  |
+|           | vIRQ    | Interrupt ID  | interrupt. It pends vIRQ signal and   |
+|           |         |               | resumes execution context of SP       |
+|           |         |               | through ERET.                         |
++-----------+---------+---------------+---------------------------------------+
+| BLOCKED   | ERET,   | FFA_INTERRUPT | SPMC signals to SP that an interrupt  |
+|           | vIRQ    |               | is pending. It pends vIRQ signal and  |
+|           |         |               | resumes execution context of SP       |
+|           |         |               | through ERET.                         |
++-----------+---------+---------------+---------------------------------------+
+| PREEMPTED | vIRQ    | NA            | SPMC pends the vIRQ signal but does   |
+|           |         |               | not resume execution context of SP.   |
++-----------+---------+---------------+---------------------------------------+
+| RUNNING   | ERET,   | NA            | SPMC pends the vIRQ signal and resumes|
+|           | vIRQ    |               | execution context of SP through ERET. |
++-----------+---------+---------------+---------------------------------------+
+
+Secure interrupt completion mechanisms
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+A SP signals secure interrupt handling completion to the SPMC through the
+following mechanisms:
+
+  - ``FFA_MSG_WAIT`` ABI if it was in WAITING state.
+  - ``FFA_RUN`` ABI if its was in BLOCKED state.
+
+In the current implementation, S-EL1 SPs use para-virtualized HVC interface
+implemented by SPMC to perform priority drop and interrupt deactivation (we
+assume EOImode = 0, i.e. priority drop and deactivation are done together).
+
+If normal world execution was preempted by secure interrupt, SPMC uses
+FFA_NORMAL_WORLD_RESUME ABI to indicate completion of secure interrupt handling
+and further return execution to normal world. If the current SP execution
+context was preempted by a secure interrupt to be handled by execution context
+of target SP, SPMC resumes current SP after signal completion by target SP
+execution context.
+
+An action is broadly a set of steps taken by the SPMC in response to a physical
+interrupt. In order to simplify the design, the current version of secure
+interrupt management support in SPMC (Hafnium) does not fully implement the
+Scheduling models and Partition runtime models. However, the current
+implementation loosely maps to the following actions that are legally allowed
+by the specification. Please refer to the Table 8.4 in the spec for further
+description of actions. The action specified for a type of interrupt when the
+SP is in the message processing running state cannot be less permissive than the
+action specified for the same type of interrupt when the SP is in the interrupt
+handling running state.
+
++--------------------+--------------------+------------+-------------+
+| Runtime Model      | NS-Int             | Self S-Int | Other S-Int |
++--------------------+--------------------+------------+-------------+
+| Message Processing | Signalable with ME | Signalable | Signalable  |
++--------------------+--------------------+------------+-------------+
+| Interrupt Handling | Queued             | Queued     | Queued      |
++--------------------+--------------------+------------+-------------+
+
+Abbreviations:
+
+  - NS-Int: A Non-secure physical interrupt. It requires a switch to the Normal
+    world to be handled.
+  - Other S-Int: A secure physical interrupt targeted to an SP different from
+    the one that is currently running.
+  - Self S-Int: A secure physical interrupt targeted to the SP that is currently
+    running.
+
+The following figure describes interrupt handling flow when secure interrupt
+triggers while in normal world:
+
+.. image:: ../resources/diagrams/ffa-secure-interrupt-handling-nwd.png
+
+A brief description of the events:
+
+  - 1) Secure interrupt triggers while normal world is running.
+  - 2) FIQ gets trapped to EL3.
+  - 3) SPMD signals secure interrupt to SPMC at S-EL2 using FFA_INTERRUPT ABI.
+  - 4) SPMC identifies target vCPU of SP and injects virtual interrupt (pends
+       vIRQ).
+  - 5) Since SP1 vCPU is in WAITING state, SPMC signals using FFA_INTERRUPT with
+       interrupt id as argument and resume it using ERET.
+  - 6) Execution traps to vIRQ handler in SP1 provided that interrupt is not
+       masked i.e., PSTATE.I = 0
+  - 7) SP1 services the interrupt and invokes the de-activation HVC call.
+  - 8) SPMC does internal state management and further de-activates the physical
+       interrupt and resumes SP vCPU.
+  - 9) SP performs secure interrupt completion through FFA_MSG_WAIT ABI.
+  - 10) SPMC returns control to EL3 using FFA_NORMAL_WORLD_RESUME.
+  - 11) EL3 resumes normal world execution.
+
+The following figure describes interrupt handling flow when secure interrupt
+triggers while in secure world:
+
+.. image:: ../resources/diagrams/ffa-secure-interrupt-handling-swd.png
+
+A brief description of the events:
+
+  - 1) Secure interrupt triggers while SP2 is running and SP1 is blocked.
+  - 2) Gets trapped to SPMC as IRQ.
+  - 3) SPMC finds the target vCPU of secure partition responsible for handling
+       this secure interrupt. In this scenario, it is SP1.
+  - 4) SPMC pends vIRQ for SP1 and signals through FFA_INTERRUPT interface.
+       SPMC further resumes SP1 through ERET conduit.
+  - 5) Execution traps to vIRQ handler in SP1 provided that interrupt is not
+       masked i.e., PSTATE.I = 0
+  - 6) SP1 services the secure interrupt and invokes the de-activation HVC call.
+  - 7) SPMC does internal state management, de-activates the physical interrupt
+       and resumes SP1 vCPU.
+  - 8) Assuming SP1 is in BLOCKED state, SP1 performs secure interrupt completion
+       through FFA_RUN ABI.
+  - 9) SPMC resumes the pre-empted vCPU of SP2.
+
 
 Power management
 ----------------
 
-Assumption on the Nwd:
+In platforms with or without secure virtualization:
 
--  NWd is the best candidate to own the platform Power Management
-   policy. It is master to invoking PSCI service calls from physical
-   CPUs.
--  EL3 monitor is in charge of the PM control part (its PSCI layer
-   actually writing to platform registers).
--  It is fine for the Hypervisor to trap PSCI calls and relay to EL3, or
-   OS kernel driver to emit PSCI service calls.
+- The NWd owns the platform PM policy.
+- The Hypervisor or OS kernel is the component initiating PSCI service calls.
+- The EL3 PSCI library is in charge of the PM coordination and control
+  (eventually writing to platform registers).
+- While coordinating PM events, the PSCI library calls backs into the Secure
+  Payload Dispatcher for events the latter has statically registered to.
 
-PSCI notification are relayed through the SPMD/SPD PM hooks to the SPMC.
-This can either be through re-use of PSCI FIDs or an FF-A direct message
-from SPMD to SPMC.
+When using the SPMD as a Secure Payload Dispatcher:
 
-The SPMD performs an exception return to the SPMC which is resumed to
-its ``eret_handler`` routine. It is then either consuming a PSCI FID or
-an FF-A FID. Depending on the servicing, the SPMC may return directly to
-the SPMD (and then NWd) without resuming an SP at this stage. An example
-of this is invocation of ``FFA_PARTITION_INFO_GET`` from NWd relayed by
-the SPMD to the SPMC. The SPMC returns the needed partition information
-to the SPMD (then NWd) without actually resuming a partition in secure world.
+- A power management event is relayed through the SPD hook to the SPMC.
+- In the current implementation only cpu on (svc_on_finish) and cpu off
+  (svc_off) hooks are registered.
+- The behavior for the cpu on event is described in `Secondary cores boot-up`_.
+  The SPMC is entered through its secondary physical core entry point.
+- The cpu off event occurs when the NWd calls PSCI_CPU_OFF. The method by which
+  the PM event is conveyed to the SPMC is implementation-defined in context of
+  FF-A v1.0 (`SPMC-SPMD direct requests/responses`_). It consists in a SPMD-to-SPMC
+  direct request/response conveying the PM event details and SPMC response.
+  The SPMD performs a synchronous entry into the SPMC. The SPMC is entered and
+  updates its internal state to reflect the physical core is being turned off.
+  In the current implementation no SP is resumed as a consequence. This behavior
+  ensures a minimal support for CPU hotplug e.g. when initiated by the NWd linux
+  userspace.
 
-*(under discussion)*
-About using PSCI FIDs from SPMD to SPMC to notify of PM events, it is still
-questioned what to use as the return code from the SPMC.
-If the function ID used by the SPMC is not an FF-A ID when doing SMC, then the
-EL3 std svc handler won't route the response to the SPMD. That's where comes the
-idea to embed the notification into an FF-A message. The SPMC can discriminate
-this message as being a PSCI event, process it, and reply with an FF-A return
-message that the SPMD receives as an acknowledgement.
+SMMUv3 support in Hafnium
+=========================
 
-SP notification
+An SMMU is analogous to an MMU in a CPU. It performs address translations for
+Direct Memory Access (DMA) requests from system I/O devices.
+The responsibilities of an SMMU include:
+
+-  Translation: Incoming DMA requests are translated from bus address space to
+   system physical address space using translation tables compliant to
+   Armv8/Armv7 VMSA descriptor format.
+-  Protection: An I/O device can be prohibited from read, write access to a
+   memory region or allowed.
+-  Isolation: Traffic from each individial device can be independently managed.
+   The devices are differentiated from each other using unique translation
+   tables.
+
+The following diagram illustrates a typical SMMU IP integrated in a SoC with
+several I/O devices along with Interconnect and Memory system.
+
+.. image:: ../resources/diagrams/MMU-600.png
+
+SMMU has several versions including SMMUv1, SMMUv2 and SMMUv3. Hafnium provides
+support for SMMUv3 driver in both normal and secure world. A brief introduction
+of SMMUv3 functionality and the corresponding software support in Hafnium is
+provided here.
+
+SMMUv3 features
 ---------------
 
-Power management notifications are conveyed from PSCI library to the
-SPMD / SPD hooks. A range of events can be relayed to SPMC.
+-  SMMUv3 provides Stage1, Stage2 translation as well as nested (Stage1 + Stage2)
+   translation support. It can either bypass or abort incoming translations as
+   well.
+-  Traffic (memory transactions) from each upstream I/O peripheral device,
+   referred to as Stream, can be independently managed using a combination of
+   several memory based configuration structures. This allows the SMMUv3 to
+   support a large number of streams with each stream assigned to a unique
+   translation context.
+-  Support for Armv8.1 VMSA where the SMMU shares the translation tables with
+   a Processing Element. AArch32(LPAE) and AArch64 translation table format
+   are supported by SMMUv3.
+-  SMMUv3 offers non-secure stream support with secure stream support being
+   optional. Logically, SMMUv3 behaves as if there is an indepdendent SMMU
+   instance for secure and non-secure stream support.
+-  It also supports sub-streams to differentiate traffic from a virtualized
+   peripheral associated with a VM/SP.
+-  Additionally, SMMUv3.2 provides support for PEs implementing Armv8.4-A
+   extensions. Consequently, SPM depends on Secure EL2 support in SMMUv3.2
+   for providing Secure Stage2 translation support to upstream peripheral
+   devices.
 
-SPs may need to be notified about specific PM events.
+SMMUv3 Programming Interfaces
+-----------------------------
 
--  SPs might register PM events to the SPMC
--  On SPMD to SPMC notification, a limited range of SPs may be notified
-   through a direct message.
--  This assumes the mentioned SPs supports managed exit.
+SMMUv3 has three software interfaces that are used by the Hafnium driver to
+configure the behaviour of SMMUv3 and manage the streams.
 
-The SPMC is the first to be notified about PM events from the SPMD. It is up
-to the SPMC to arbitrate to which SP it needs to send PM events.
-An SP explicitly registers to receive notifications to specific PM events.
-The register operation can either be an implementation-defined service call
-to the SPMC when the primary SP EC boots, or be supplied through the SP
-manifest.
+-  Memory based data strutures that provide unique translation context for
+   each stream.
+-  Memory based circular buffers for command queue and event queue.
+-  A large number of SMMU configuration registers that are memory mapped during
+   boot time by Hafnium driver. Except a few registers, all configuration
+   registers have independent secure and non-secure versions to configure the
+   behaviour of SMMUv3 for translation of secure and non-secure streams
+   respectively.
+
+Peripheral device manifest
+--------------------------
+
+Currently, SMMUv3 driver in Hafnium only supports dependent peripheral devices.
+These devices are dependent on PE endpoint to initiate and receive memory
+management transactions on their behalf. The acccess to the MMIO regions of
+any such device is assigned to the endpoint during boot. Moreover, SMMUv3 driver
+uses the same stage 2 translations for the device as those used by partition
+manager on behalf of the PE endpoint. This ensures that the peripheral device
+has the same visibility of the physical address space as the endpoint. The
+device node of the corresponding partition manifest (refer to `[1]`_ section 3.2
+) must specify these additional properties for each peripheral device in the
+system :
+
+-  smmu-id: This field helps to identify the SMMU instance that this device is
+   upstream of.
+-  stream-ids: List of stream IDs assigned to this device.
+
+.. code:: shell
+
+    smmuv3-testengine {
+        base-address = <0x00000000 0x2bfe0000>;
+        pages-count = <32>;
+        attributes = <0x3>;
+        smmu-id = <0>;
+        stream-ids = <0x0 0x1>;
+        interrupts = <0x2 0x3>, <0x4 0x5>;
+        exclusive-access;
+    };
+
+SMMUv3 driver limitations
+-------------------------
+
+The primary design goal for the Hafnium SMMU driver is to support secure
+streams.
+
+-  Currently, the driver only supports Stage2 translations. No support for
+   Stage1 or nested translations.
+-  Supports only AArch64 translation format.
+-  No support for features such as PCI Express (PASIDs, ATS, PRI), MSI, RAS,
+   Fault handling, Performance Monitor Extensions, Event Handling, MPAM.
+-  No support for independent peripheral devices.
 
 References
 ==========
 
 .. _[1]:
 
-[1] `Platform Security Architecture Firmware Framework for Arm® v8-A 1.0 Platform Design Document <https://developer.arm.com/docs/den0077/latest>`__
+[1] `Arm Firmware Framework for Arm A-profile <https://developer.arm.com/docs/den0077/latest>`__
 
 .. _[2]:
 
@@ -846,7 +1077,7 @@
 .. _[3]:
 
 [3] `Trusted Boot Board Requirements
-Client <https://developer.arm.com/docs/den0006/latest/trusted-board-boot-requirements-client-tbbr-client-armv8-a>`__
+Client <https://developer.arm.com/documentation/den0006/d/>`__
 
 .. _[4]:
 
@@ -854,11 +1085,11 @@
 
 .. _[5]:
 
-[5] https://git.trustedfirmware.org/TF-A/tf-a-tests.git/tree/spm/cactus/cactus.dts
+[5] https://git.trustedfirmware.org/TF-A/tf-a-tests.git/tree/spm/cactus/plat/arm/fvp/fdts/cactus.dts
 
 .. _[6]:
 
-[6] https://trustedfirmware-a.readthedocs.io/en/latest/components/psa-ffa-manifest-binding.html
+[6] https://trustedfirmware-a.readthedocs.io/en/latest/components/ffa-manifest-binding.html
 
 .. _[7]:
 
@@ -866,8 +1097,12 @@
 
 .. _[8]:
 
-[8] https://developer.trustedfirmware.org/w/tf_a/poc-multiple-signing-domains/
+[8] https://lists.trustedfirmware.org/pipermail/tf-a/2020-February/000296.html
+
+.. _[9]:
+
+[9] https://trustedfirmware-a.readthedocs.io/en/latest/design/firmware-design.html#dynamic-configuration-during-cold-boot
 
 --------------
 
-*Copyright (c) 2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2020-2021, Arm Limited and Contributors. All rights reserved.*
diff --git a/docs/components/xlat-tables-lib-v2-design.rst b/docs/components/xlat-tables-lib-v2-design.rst
index af5151f..cac32f5 100644
--- a/docs/components/xlat-tables-lib-v2-design.rst
+++ b/docs/components/xlat-tables-lib-v2-design.rst
@@ -10,7 +10,7 @@
 More specifically, some use cases that this library aims to support are:
 
 #. Statically allocate translation tables and populate them (at run-time) based
-   on a description of the memory layout. The memory layout is typically
+   upon a description of the memory layout. The memory layout is typically
    provided by the platform port as a list of memory regions;
 
 #. Support for generating translation tables pertaining to a different
@@ -26,22 +26,28 @@
 #. Support for changing memory attributes of memory regions at run-time.
 
 
-About version 1 and version 2
------------------------------
+About version 1, version 2 and MPU libraries
+--------------------------------------------
 
 This document focuses on version 2 of the library, whose sources are available
 in the ``lib/xlat_tables_v2`` directory. Version 1 of the library can still be
 found in ``lib/xlat_tables`` directory but it is less flexible and doesn't
-support dynamic mapping. Although potential bug fixes will be applied to both
-versions, future features enhancements will focus on version 2 and might not be
-back-ported to version 1. Therefore, it is recommended to use version 2,
-especially for new platform ports.
+support dynamic mapping. ``lib/xlat_mpu``, which configures Arm's MPU
+equivalently, is also addressed here. The ``lib/xlat_mpu`` is experimental,
+meaning that its API may change. It currently strives for consistency and
+code-reuse with xlat_tables_v2.  Future versions may be more MPU-specific (e.g.,
+removing all mentions of virtual addresses). Although potential bug fixes will
+be applied to all versions of the xlat_* libs, future feature enhancements will
+focus on version 2 and might not be back-ported to version 1 and MPU versions.
+Therefore, it is recommended to use version 2, especially for new platform
+ports (unless the platform uses an MPU).
 
-However, please note that version 2 is still in active development and is not
-considered stable yet. Hence, compatibility breaks might be introduced.
+However, please note that version 2 and the MPU version are still in active
+development and is not considered stable yet. Hence, compatibility breaks might
+be introduced.
 
 From this point onwards, this document will implicitly refer to version 2 of the
-library.
+library, unless stated otherwise.
 
 
 Design concepts and interfaces
@@ -102,6 +108,16 @@
 library will choose the mapping granularity for this region as it sees fit (more
 details can be found in `The memory mapping algorithm`_ section below).
 
+The MPU library also uses ``struct mmap_region`` to specify translations, but
+the MPU's translations are limited to specification of valid addresses and
+access permissions.  If the requested virtual and physical addresses mismatch
+the system will panic. Being register-based for deterministic memory-reference
+timing, the MPU hardware does not involve memory-resident translation tables.
+
+Currently, the MPU library is also limited to MPU translation at EL2 with no
+MMU translation at other ELs.  These limitations, however, are expected to be
+overcome in future library versions.
+
 Translation Context
 ~~~~~~~~~~~~~~~~~~~
 
@@ -215,7 +231,8 @@
 The ``MAP_REGION()`` and ``MAP_REGION_FLAT()`` macros do not allow specifying a
 mapping granularity, which leaves the library implementation free to choose
 it. However, in cases where a specific granularity is required, the
-``MAP_REGION2()`` macro might be used instead.
+``MAP_REGION2()`` macro might be used instead. Using ``MAP_REGION_FLAT()`` only
+to define regions for the MPU library is strongly recommended.
 
 As explained earlier in this document, when the dynamic mapping feature is
 disabled, there is no notion of dynamic regions. Conceptually, there are only
@@ -374,6 +391,9 @@
 refer to the comments in the source code of the core module for more details
 about the sorting algorithm in use.
 
+This mapping algorithm does not apply to the MPU library, since the MPU hardware
+directly maps regions by "base" and "limit" (bottom and top) addresses.
+
 TLB maintenance operations
 ~~~~~~~~~~~~~~~~~~~~~~~~~~
 
@@ -390,6 +410,11 @@
 is deferred to the ``enable_mmu*()`` family of functions, just before the MMU is
 turned on.
 
+Regarding enabling and disabling memory management, for the MPU library, to
+reduce confusion, calls to enable or disable the MPU use ``mpu`` in their names
+in place of ``mmu``. For example, the ``enable_mmu_el2()`` call is changed to
+``enable_mpu_el2()``.
+
 TLB invalidation is not required when adding dynamic regions either. Dynamic
 regions are not allowed to overlap existing memory region. Therefore, if the
 dynamic mapping request is deemed legitimate, it automatically concerns memory
@@ -412,6 +437,6 @@
 
 --------------
 
-*Copyright (c) 2017-2019, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. |Alignment Example| image:: ../resources/diagrams/xlat_align.png
diff --git a/docs/conf.py b/docs/conf.py
index a100241..356be99 100644
--- a/docs/conf.py
+++ b/docs/conf.py
@@ -1,6 +1,6 @@
 # -*- coding: utf-8 -*-
 #
-# Copyright (c) 2019, Arm Limited. All rights reserved.
+# Copyright (c) 2019-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -76,6 +76,14 @@
     'style_external_links': True # Display an icon next to external links
 }
 
+# Path to _static directory
+html_static_path = ['_static']
+
+# Path to css file relative to html_static_path
+html_css_files = [
+    'css/custom.css',
+]
+
 # -- Options for autosectionlabel --------------------------------------------
 
 # Only generate automatic section labels for document titles
diff --git a/docs/design/cpu-specific-build-macros.rst b/docs/design/cpu-specific-build-macros.rst
index c976b8b..9d0dd5e 100644
--- a/docs/design/cpu-specific-build-macros.rst
+++ b/docs/design/cpu-specific-build-macros.rst
@@ -241,9 +241,6 @@
 -  ``ERRATA_A76_1791580``: This applies errata 1791580 workaround to Cortex-A76
    CPU. This needs to be enabled only for revision <= r4p0 of the CPU.
 
--  ``ERRATA_A76_1800710``: This applies errata 1800710 workaround to Cortex-A76
-   CPU. This needs to be enabled only for revision <= r4p0 of the CPU.
-
 -  ``ERRATA_A76_1165522``: This applies errata 1165522 workaround to all
    revisions of Cortex-A76 CPU. This errata is fixed in r3p0 but due to
    limitation of errata framework this errata is applied to all revisions
@@ -252,22 +249,59 @@
 -  ``ERRATA_A76_1868343``: This applies errata 1868343 workaround to Cortex-A76
    CPU. This needs to be enabled only for revision <= r4p0 of the CPU.
 
+-  ``ERRATA_A76_1946160``: This applies errata 1946160 workaround to Cortex-A76
+   CPU. This needs to be enabled only for revisions r3p0 - r4p1 of the CPU.
+
 For Cortex-A77, the following errata build flags are defined :
 
 -  ``ERRATA_A77_1508412``: This applies errata 1508412 workaround to Cortex-A77
    CPU. This needs to be enabled only for revision <= r1p0 of the CPU.
 
--  ``ERRATA_A77_1800714``: This applies errata 1800714 workaround to Cortex-A77
-   CPU. This needs to be enabled only for revision <= r1p1 of the CPU.
-
 -  ``ERRATA_A77_1925769``: This applies errata 1925769 workaround to Cortex-A77
    CPU. This needs to be enabled only for revision <= r1p1 of the CPU.
 
+-  ``ERRATA_A77_1946167``: This applies errata 1946167 workaround to Cortex-A77
+   CPU. This needs to be enabled only for revision <= r1p1 of the CPU.
+
+-  ``ERRATA_A77_1791578``: This applies errata 1791578 workaround to Cortex-A77
+   CPU. This needs to be enabled for r0p0, r1p0, and r1p1, it is still open.
+
 For Cortex-A78, the following errata build flags are defined :
 
 -  ``ERRATA_A78_1688305``: This applies errata 1688305 workaround to Cortex-A78
    CPU. This needs to be enabled only for revision r0p0 - r1p0 of the CPU.
 
+-  ``ERRATA_A78_1941498``: This applies errata 1941498 workaround to Cortex-A78
+   CPU. This needs to be enabled for revisions r0p0, r1p0, and r1p1 of the CPU.
+
+-  ``ERRATA_A78_1951500``: This applies errata 1951500 workaround to Cortex-A78
+   CPU. This needs to be enabled for revisions r1p0 and r1p1, r0p0 has the same
+   issue but there is no workaround for that revision.
+
+-  ``ERRATA_A78_1821534``: This applies errata 1821534 workaround to Cortex-A78
+   CPU. This needs to be enabled for revisions r0p0 and r1p0.
+
+-  ``ERRATA_A78_1952683``: This applies errata 1952683 workaround to Cortex-A78
+   CPU. This needs to be enabled for revision r0p0, it is fixed in r1p0.
+
+-  ``ERRATA_A78_2132060``: This applies errata 2132060 workaround to Cortex-A78
+   CPU. This needs to be enabled for revisions r0p0, r1p0, r1p1, and r1p2. It
+   is still open.
+
+-  ``ERRATA_A78_2242635``: This applies errata 2242635 workaround to Cortex-A78
+   CPU. This needs to be enabled for revisions r1p0, r1p1, and r1p2. The issue
+   is present in r0p0 but there is no workaround. It is still open.
+
+For Cortex-A78 AE, the following errata build flags are defined :
+
+- ``ERRATA_A78_AE_1941500`` : This applies errata 1941500 workaround to Cortex-A78
+   AE CPU. This needs to be enabled for revisions r0p0 and r0p1. This erratum is
+   still open.
+
+- ``ERRATA_A78_AE_1951502`` : This applies errata 1951502 workaround to Cortex-A78
+  AE CPU. This needs to be enabled for revisions r0p0 and r0p1. This erratum is
+  still open.
+
 For Neoverse N1, the following errata build flags are defined :
 
 -  ``ERRATA_N1_1073348``: This applies errata 1073348 workaround to Neoverse-N1
@@ -306,6 +340,107 @@
 -  ``ERRATA_N1_1868343``: This applies errata 1868343 workaround to Neoverse-N1
    CPU. This needs to be enabled only for revision <= r4p0 of the CPU.
 
+-  ``ERRATA_N1_1946160``: This applies errata 1946160 workaround to Neoverse-N1
+   CPU. This needs to be enabled for revisions r3p0, r3p1, r4p0, and r4p1, for
+   revisions r0p0, r1p0, and r2p0 there is no workaround.
+
+For Neoverse V1, the following errata build flags are defined :
+
+-  ``ERRATA_V1_1774420``: This applies errata 1774420 workaround to Neoverse-V1
+   CPU. This needs to be enabled only for revisions r0p0 and r1p0, it is fixed
+   in r1p1.
+
+-  ``ERRATA_V1_1791573``: This applies errata 1791573 workaround to Neoverse-V1
+   CPU. This needs to be enabled only for revisions r0p0 and r1p0, it is fixed
+   in r1p1.
+
+-  ``ERRATA_V1_1852267``: This applies errata 1852267 workaround to Neoverse-V1
+   CPU. This needs to be enabled only for revisions r0p0 and r1p0, it is fixed
+   in r1p1.
+
+-  ``ERRATA_V1_1925756``: This applies errata 1925756 workaround to Neoverse-V1
+   CPU. This needs to be enabled for r0p0, r1p0, and r1p1, it is still open.
+
+-  ``ERRATA_V1_1940577``: This applies errata 1940577 workaround to Neoverse-V1
+   CPU. This needs to be enabled only for revision r1p0 and r1p1 of the
+   CPU.
+
+-  ``ERRATA_V1_1966096``: This applies errata 1966096 workaround to Neoverse-V1
+   CPU. This needs to be enabled for revisions r1p0 and r1p1 of the CPU, the
+   issue is present in r0p0 as well but there is no workaround for that
+   revision.  It is still open.
+
+-  ``ERRATA_V1_2139242``: This applies errata 2139242 workaround to Neoverse-V1
+   CPU. This needs to be enabled for revisions r0p0, r1p0, and r1p1 of the
+   CPU.  It is still open.
+
+-  ``ERRATA_V1_2108267``: This applies errata 2108267 workaround to Neoverse-V1
+   CPU. This needs to be enabled for revisions r0p0, r1p0, and r1p1 of the CPU.
+   It is still open.
+
+-  ``ERRATA_V1_2216392``: This applies errata 2216392 workaround to Neoverse-V1
+   CPU. This needs to be enabled for revisions r1p0 and r1p1 of the CPU, the
+   issue is present in r0p0 as well but there is no workaround for that
+   revision.  It is still open.
+
+For Cortex-A710, the following errata build flags are defined :
+
+-  ``ERRATA_A710_1987031``: This applies errata 1987031 workaround to
+   Cortex-A710 CPU. This needs to be enabled only for revisions r0p0, r1p0 and
+   r2p0 of the CPU. It is still open.
+
+-  ``ERRATA_A710_2081180``: This applies errata 2081180 workaround to
+   Cortex-A710 CPU. This needs to be enabled only for revisions r0p0, r1p0 and
+   r2p0 of the CPU. It is still open.
+
+-  ``ERRATA_A710_2055002``: This applies errata 2055002 workaround to
+   Cortex-A710 CPU. This needs to be enabled for revisions r1p0, r2p0 of the CPU
+   and is still open.
+
+-  ``ERRATA_A710_2017096``: This applies errata 2017096 workaround to
+   Cortex-A710 CPU. This needs to be enabled for revisions r0p0, r1p0 and r2p0
+   of the CPU and is still open.
+
+-  ``ERRATA_A710_2083908``: This applies errata 2083908 workaround to
+   Cortex-A710 CPU. This needs to be enabled for revision r2p0 of the CPU and
+   is still open.
+
+-  ``ERRATA_A710_2058056``: This applies errata 2058056 workaround to
+   Cortex-A710 CPU. This needs to be enabled for revisions r0p0, r1p0 and r2p0
+   of the CPU and is still open.
+
+For Neoverse N2, the following errata build flags are defined :
+
+-  ``ERRATA_N2_2002655``: This applies errata 2002655 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU, it is still open.
+
+-  ``ERRATA_N2_2067956``: This applies errata 2067956 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2025414``: This applies errata 2025414 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2189731``: This applies errata 2189731 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2138956``: This applies errata 2138956 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2138953``: This applies errata 2138953 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2242415``: This applies errata 2242415 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2138958``: This applies errata 2138958 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2242400``: This applies errata 2242400 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
+-  ``ERRATA_N2_2280757``: This applies errata 2280757 workaround to Neoverse-N2
+   CPU. This needs to be enabled for revision r0p0 of the CPU and is still open.
+
 DSU Errata Workarounds
 ----------------------
 
@@ -369,14 +504,15 @@
    Cortex-A57 based platform must make its own decision on whether to use
    the optimization. This flag is disabled by default.
 
--  ``NEOVERSE_N1_EXTERNAL_LLC``: This flag indicates that an external last
+-  ``NEOVERSE_Nx_EXTERNAL_LLC``: This flag indicates that an external last
    level cache(LLC) is present in the system, and that the DataSource field
    on the master CHI interface indicates when data is returned from the LLC.
    This is used to control how the LL_CACHE* PMU events count.
+   Default value is 0 (Disabled).
 
 --------------
 
-*Copyright (c) 2014-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2014-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _CVE-2017-5715: http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-5715
 .. _CVE-2018-3639: http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2018-3639
diff --git a/docs/design/firmware-design.rst b/docs/design/firmware-design.rst
index c12e73f..0831dc0 100644
--- a/docs/design/firmware-design.rst
+++ b/docs/design/firmware-design.rst
@@ -26,6 +26,13 @@
 
 TF-A can be built to support either AArch64 or AArch32 execution state.
 
+.. note::
+
+ The descriptions in this chapter are for the Arm TrustZone architecture.
+ For changes to the firmware design for the
+ `Arm Confidential Compute Architecture (Arm CCA)`_ please refer to the
+ chapter :ref:`Realm Management Extension (RME)`.
+
 Cold boot
 ---------
 
@@ -2616,8 +2623,6 @@
    ``CTX_INCLUDE_PAUTH_REGS`` to 1. This enables pointer authentication in BL1,
    BL2, BL31, and the TSP if it is used.
 
-   These options are experimental features.
-
    Note that Pointer Authentication is enabled for Non-secure world irrespective
    of the value of these build flags if the CPU supports it.
 
@@ -2629,8 +2634,7 @@
 ~~~~~~~~~
 
 -  Branch Target Identification feature is selected by ``BRANCH_PROTECTION``
-   option set to 1. This option defaults to 0 and this is an experimental
-   feature.
+   option set to 1. This option defaults to 0.
 
 -  Memory Tagging Extension feature is unconditionally enabled for both worlds
    (at EL0 and S-EL0) if it is only supported at EL0. If instead it is
@@ -2725,7 +2729,7 @@
 
 --------------
 
-*Copyright (c) 2013-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _Power State Coordination Interface PDD: http://infocenter.arm.com/help/topic/com.arm.doc.den0022d/Power_State_Coordination_Interface_PDD_v1_1_DEN0022D.pdf
 .. _SMCCC: https://developer.arm.com/docs/den0028/latest
@@ -2734,5 +2738,6 @@
 .. _Arm ARM: https://developer.arm.com/docs/ddi0487/latest
 .. _SMC Calling Convention: https://developer.arm.com/docs/den0028/latest
 .. _Trusted Board Boot Requirements CLIENT (TBBR-CLIENT) Armv8-A (ARM DEN0006D): https://developer.arm.com/docs/den0006/latest/trusted-board-boot-requirements-client-tbbr-client-armv8-a
+.. _Arm Confidential Compute Architecture (Arm CCA): https://www.arm.com/why-arm/architecture/security-features/arm-confidential-compute-architecture
 
 .. |Image 1| image:: ../resources/diagrams/rt-svc-descs-layout.png
diff --git a/docs/design/trusted-board-boot.rst b/docs/design/trusted-board-boot.rst
index 96cf24c..46177d7 100644
--- a/docs/design/trusted-board-boot.rst
+++ b/docs/design/trusted-board-boot.rst
@@ -239,9 +239,6 @@
 R060_TBBR_FUNCTION as specified in the `Trusted Board Boot Requirements (TBBR)`_
 document.
 
-Note that due to security considerations and complexity of this feature, it is
-marked as experimental.
-
 Firmware Encryption Tool
 ------------------------
 
diff --git a/docs/design_documents/index.rst b/docs/design_documents/index.rst
index 187510a..c82d2ee 100644
--- a/docs/design_documents/index.rst
+++ b/docs/design_documents/index.rst
@@ -7,6 +7,7 @@
    :numbered:
 
    cmake_framework
+   measured_boot_poc
 
 --------------
 
diff --git a/docs/design_documents/measured_boot_poc.rst b/docs/design_documents/measured_boot_poc.rst
new file mode 100644
index 0000000..3ae539b
--- /dev/null
+++ b/docs/design_documents/measured_boot_poc.rst
@@ -0,0 +1,507 @@
+Interaction between Measured Boot and an fTPM (PoC)
+===================================================
+
+Measured Boot is the process of cryptographically measuring the code and
+critical data used at boot time, for example using a TPM, so that the
+security state can be attested later.
+
+The current implementation of the driver included in Trusted Firmware-A
+(TF-A) stores the measurements into a `TGC event log`_ in secure
+memory. No other means of recording measurements (such as a discrete TPM) is
+supported right now.
+
+The driver also provides mechanisms to pass the Event Log to normal world if
+needed.
+
+This manual provides instructions to build a proof of concept (PoC) with the
+sole intention of showing how Measured Boot can be used in conjunction with
+a firmware TPM (fTPM) service implemented on top of OP-TEE.
+
+.. note::
+   The instructions given in this document are meant to be used to build
+   a PoC to show how Measured Boot on TF-A can interact with a third
+   party (f)TPM service and they try to be as general as possible. Different
+   platforms might have different needs and configurations (e.g. different
+   SHA algorithms) and they might also use different types of TPM services
+   (or even a different type of service to provide the attestation)
+   and therefore the instuctions given here might not apply in such scenarios.
+
+Components
+~~~~~~~~~~
+
+The PoC is built on top of the `OP-TEE Toolkit`_, which has support to build
+TF-A with support for Measured Boot enabled (and run it on a Foundation Model)
+since commit cf56848.
+
+The aforementioned toolkit builds a set of images that contain all the components
+needed to test that the Event Log was properly created. One of these images will
+contain a third party fTPM service which in turn will be used to process the
+Event Log.
+
+The reason to choose OP-TEE Toolkit to build our PoC around it is mostly
+for convenience. As the fTPM service used is an OP-TEE TA, it was easy to add
+build support for it to the toolkit and then build the PoC around it.
+
+The most relevant components installed in the image that are closely related to
+Measured Boot/fTPM functionality are:
+
+   - **OP-TEE**: As stated earlier, the fTPM service used in this PoC is built as an
+     OP-TEE TA and therefore we need to include the OP-TEE OS image.
+     Support to interfacing with Measured Boot was added to version 3.9.0 of
+     OP-TEE by implementing the ``PTA_SYSTEM_GET_TPM_EVENT_LOG`` syscall, which
+     allows the former to pass a copy of the Event Log to any TA requesting it.
+     OP-TEE knows the location of the Event Log by reading the DTB bindings
+     received from TF-A. Visit :ref:`DTB binding for Event Log properties`
+     for more details on this.
+
+   - **fTPM Service**: We use a third party fTPM service in order to validate
+     the Measured Boot functionality. The chosen fTPM service is a sample
+     implementation for Aarch32 architecture included on the `ms-tpm-20-ref`_
+     reference implementation from Microsoft. The service was updated in order
+     to extend the Measured Boot Event Log at boot up and it uses the
+     aforementioned ``PTA_SYSTEM_GET_TPM_EVENT_LOG`` call to retrieve a copy
+     of the former.
+
+   .. note::
+      Arm does not provide an fTPM implementation. The fTPM service used here
+      is a third party one which has been updated to support Measured Boot
+      service as provided by TF-A. As such, it is beyond the scope of this
+      manual to test and verify the correctness of the output generated by the
+      fTPM service.
+
+   - **TPM Kernel module**: In order to interact with the fTPM service, we need
+     a kernel module to forward the request from user space to the secure world.
+
+   - `tpm2-tools`_: This is a set of tools that allow to interact with the
+     fTPM service. We use this in order to read the PCRs with the measurements.
+
+Building the PoC for the Arm FVP platform
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+As mentioned before, this PoC is based on the OP-TEE Toolkit with some
+extensions to enable Measured Boot and an fTPM service. Therefore, we can rely
+on the instructions to build the original OP-TEE Toolkit. As a general rule,
+the following steps should suffice:
+
+(1) Start by following the `Get and build the solution`_ instructions to build
+    the OP-TEE toolkit. On step 3, you need to get the manifest for FVP
+    platform from the main branch:
+
+    .. code:: shell
+
+       $ repo init -u https://github.com/OP-TEE/manifest.git -m fvp.xml
+
+    Then proceed synching the repos as stated in step 3. Continue following
+    the instructions and stop before step 5.
+
+(2) Next you should obtain the `Armv8-A Foundation Platform (For Linux Hosts Only)`_.
+    The binary should be untar'ed to the root of the repo tree, i.e., like
+    this: ``<fvp-project>/Foundation_Platformpkg``. In the end, after cloning
+    all source code, getting the toolchains and "installing"
+    Foundation_Platformpkg, you should have a folder structure that looks like
+    this:
+
+    .. code:: shell
+
+       $ ls -la
+       total 80
+       drwxrwxr-x 20 tf-a_user tf-a_user 4096 Jul  1 12:16 .
+       drwxr-xr-x 23 tf-a_user tf-a_user 4096 Jul  1 10:40 ..
+       drwxrwxr-x 12 tf-a_user tf-a_user 4096 Jul  1 10:45 build
+       drwxrwxr-x 16 tf-a_user tf-a_user 4096 Jul  1 12:16 buildroot
+       drwxrwxr-x 51 tf-a_user tf-a_user 4096 Jul  1 10:45 edk2
+       drwxrwxr-x  6 tf-a_user tf-a_user 4096 Jul  1 12:14 edk2-platforms
+       drwxr-xr-x  7 tf-a_user tf-a_user 4096 Jul  1 10:52 Foundation_Platformpkg
+       drwxrwxr-x 17 tf-a_user tf-a_user 4096 Jul  2 10:40 grub
+       drwxrwxr-x 25 tf-a_user tf-a_user 4096 Jul  2 10:39 linux
+       drwxrwxr-x 15 tf-a_user tf-a_user 4096 Jul  1 10:45 mbedtls
+       drwxrwxr-x  6 tf-a_user tf-a_user 4096 Jul  1 10:45 ms-tpm-20-ref
+       drwxrwxr-x  8 tf-a_user tf-a_user 4096 Jul  1 10:45 optee_client
+       drwxrwxr-x 10 tf-a_user tf-a_user 4096 Jul  1 10:45 optee_examples
+       drwxrwxr-x 12 tf-a_user tf-a_user 4096 Jul  1 12:13 optee_os
+       drwxrwxr-x  8 tf-a_user tf-a_user 4096 Jul  1 10:45 optee_test
+       drwxrwxr-x  7 tf-a_user tf-a_user 4096 Jul  1 10:45 .repo
+       drwxrwxr-x  4 tf-a_user tf-a_user 4096 Jul  1 12:12 toolchains
+       drwxrwxr-x 21 tf-a_user tf-a_user 4096 Jul  1 12:15 trusted-firmware-a
+
+(3) Now enter into ``ms-tpm-20-ref`` and get its dependencies:
+
+   .. code:: shell
+
+      $ cd ms-tpm-20-ref
+      $ git submodule init
+      $ git submodule update
+      Submodule path 'external/wolfssl': checked out '9c87f979a7f1d3a6d786b260653d566c1d31a1c4'
+
+(4) Now, you should be able to continue with step 5 in "`Get and build the solution`_"
+    instructions. In order to enable support for Measured Boot, you need to
+    set the ``MEASURED_BOOT`` build option:
+
+    .. code:: shell
+
+       $ MEASURED_BOOT=y make -j `nproc`
+
+    .. note::
+       The build process will likely take a long time. It is strongly recommended to
+       pass the ``-j`` option to make to run the process faster.
+
+   After this step, you should be ready to run the image.
+
+Running and using the PoC on the Armv8-A Foundation AEM FVP
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+With everything built, you can now run the image:
+
+.. code:: shell
+
+   $ make run-only
+
+.. note::
+   Using ``make run`` will build and run the image and it can be used instead
+   of simply ``make``. However, once the image is built, it is recommended to
+   use ``make run-only`` to avoid re-running all the building rules, which
+   would take time.
+
+When FVP is launched, two terminal windows will appear. ``FVP terminal_0``
+is the userspace terminal whereas ``FVP terminal_1`` is the counterpart for
+the secure world (where TAs will print their logs, for instance).
+
+Log into the image shell with user ``root``, no password will be required.
+Then we can issue the ``ftpm`` command, which is an alias that
+
+(1) loads the ftpm kernel module and
+
+(2) calls ``tpm2_pcrread``, which will access the fTPM service to read the
+    PCRs.
+
+When loading the ftpm kernel module, the fTPM TA is loaded into the secure
+world. This TA then requests a copy of the Event Log generated during the
+booting process so it can retrieve all the entries on the log and record them
+first thing.
+
+.. note::
+   For this PoC, nothing loaded after BL33 and NT_FW_CONFIG is recorded
+   in the Event Log.
+
+The secure world terminal should show the debug logs for the fTPM service,
+including all the measurements available in the Event Log as they are being
+processed:
+
+.. code:: shell
+
+	M/TA: Preparing to extend the following TPM Event Log:
+	M/TA: TCG_EfiSpecIDEvent:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 3
+	M/TA:   Digest             : 00
+	M/TA: 			   : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	M/TA: 			   : 00 00 00
+	M/TA:   EventSize          : 33
+	M/TA:   Signature          : Spec ID Event03
+	M/TA:   PlatformClass      : 0
+	M/TA:   SpecVersion        : 2.0.2
+	M/TA:   UintnSize          : 1
+	M/TA:   NumberOfAlgorithms : 1
+	M/TA:   DigestSizes        :
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        DigestSize    : 32
+	M/TA:   VendorInfoSize     : 0
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 3
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	M/TA: 			   : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	M/TA:   EventSize          : 17
+	M/TA:   Signature          : StartupLocality
+	M/TA:   StartupLocality    : 0
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 58 26 32 6e 64 45 64 da 45 de 35 db 96 fd ed 63
+	M/TA: 			   : 2a 6a d4 0d aa 94 b0 b1 55 e4 72 e7 1f 0a e0 d5
+	M/TA:   EventSize          : 5
+	M/TA:   Event              : BL_2
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : cf f9 7d a3 5c 73 ac cb 7b a0 25 80 6a 6e 50 a5
+	M/TA: 			   : 6b 2e d2 8c c9 36 92 7d 46 c5 b9 c3 a4 6c 51 7c
+	M/TA:   EventSize          : 6
+	M/TA:   Event              : BL_31
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 23 b0 a3 5d 54 d9 43 1a 5c b9 89 63 1c da 06 c2
+	M/TA: 			   : e5 de e7 7e 99 17 52 12 7d f7 45 ca 4f 4a 39 c0
+	M/TA:   EventSize          : 10
+	M/TA:   Event              : HW_CONFIG
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 4e e4 8e 5a e6 50 ed e0 b5 a3 54 8a 1f d6 0e 8a
+	M/TA: 			   : ea 0e 71 75 0e a4 3f 82 76 ce af cd 7c b0 91 e0
+	M/TA:   EventSize          : 14
+	M/TA:   Event              : SOC_FW_CONFIG
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 01 b0 80 47 a1 ce 86 cd df 89 d2 1f 2e fc 6c 22
+	M/TA: 			   : f8 19 ec 6e 1e ec 73 ba 5a be d0 96 e3 5f 6d 75
+	M/TA:   EventSize          : 6
+	M/TA:   Event              : BL_32
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 5d c6 ef 35 5a 90 81 b4 37 e6 3b 52 da 92 ab 8e
+	M/TA: 			   : d9 6e 93 98 2d 40 87 96 1b 5a a7 ee f1 f4 40 63
+	M/TA:   EventSize          : 18
+	M/TA:   Event              : BL32_EXTRA1_IMAGE
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 39 b7 13 b9 93 db 32 2f 1b 48 30 eb 2c f2 5c 25
+	M/TA: 			   : 00 0f 38 dc 8e c8 02 cd 79 f2 48 d2 2c 25 ab e2
+	M/TA:   EventSize          : 6
+	M/TA:   Event              : BL_33
+	M/TA: PCR_Event2:
+	M/TA:   PCRIndex           : 0
+	M/TA:   EventType          : 1
+	M/TA:   Digests Count      : 1
+	M/TA:     #0 AlgorithmId   : SHA256
+	M/TA:        Digest        : 25 10 60 5d d4 bc 9d 82 7a 16 9f 8a cc 47 95 a6
+	M/TA: 			   : fd ca a0 c1 2b c9 99 8f 51 20 ff c6 ed 74 68 5a
+	M/TA:   EventSize          : 13
+	M/TA:   Event              : NT_FW_CONFIG
+
+These logs correspond to the measurements stored by TF-A during the measured
+boot process and therefore, they should match the logs dumped by the former
+during the boot up process. These can be seen on the terminal_0:
+
+.. code:: shell
+
+	NOTICE:  Booting Trusted Firmware
+	NOTICE:  BL1: v2.5(release):v2.5
+	NOTICE:  BL1: Built : 10:41:20, Jul  2 2021
+	NOTICE:  BL1: Booting BL2
+	NOTICE:  BL2: v2.5(release):v2.5
+	NOTICE:  BL2: Built : 10:41:20, Jul  2 2021
+	NOTICE:  TCG_EfiSpecIDEvent:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 3
+	NOTICE:    Digest             : 00
+	NOTICE:  		      : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	NOTICE:  		      : 00 00 00
+	NOTICE:    EventSize          : 33
+	NOTICE:    Signature          : Spec ID Event03
+	NOTICE:    PlatformClass      : 0
+	NOTICE:    SpecVersion        : 2.0.2
+	NOTICE:    UintnSize          : 1
+	NOTICE:    NumberOfAlgorithms : 1
+	NOTICE:    DigestSizes        :
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         DigestSize    : 32
+	NOTICE:    VendorInfoSize     : 0
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 3
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	NOTICE:  		      : 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
+	NOTICE:    EventSize          : 17
+	NOTICE:    Signature          : StartupLocality
+	NOTICE:    StartupLocality    : 0
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 58 26 32 6e 64 45 64 da 45 de 35 db 96 fd ed 63
+	NOTICE:  		      : 2a 6a d4 0d aa 94 b0 b1 55 e4 72 e7 1f 0a e0 d5
+	NOTICE:    EventSize          : 5
+	NOTICE:    Event              : BL_2
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : cf f9 7d a3 5c 73 ac cb 7b a0 25 80 6a 6e 50 a5
+	NOTICE:  		      : 6b 2e d2 8c c9 36 92 7d 46 c5 b9 c3 a4 6c 51 7c
+	NOTICE:    EventSize          : 6
+	NOTICE:    Event              : BL_31
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 23 b0 a3 5d 54 d9 43 1a 5c b9 89 63 1c da 06 c2
+	NOTICE:  		      : e5 de e7 7e 99 17 52 12 7d f7 45 ca 4f 4a 39 c0
+	NOTICE:    EventSize          : 10
+	NOTICE:    Event              : HW_CONFIG
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 4e e4 8e 5a e6 50 ed e0 b5 a3 54 8a 1f d6 0e 8a
+	NOTICE:  		      : ea 0e 71 75 0e a4 3f 82 76 ce af cd 7c b0 91 e0
+	NOTICE:    EventSize          : 14
+	NOTICE:    Event              : SOC_FW_CONFIG
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 01 b0 80 47 a1 ce 86 cd df 89 d2 1f 2e fc 6c 22
+	NOTICE:  		      : f8 19 ec 6e 1e ec 73 ba 5a be d0 96 e3 5f 6d 75
+	NOTICE:    EventSize          : 6
+	NOTICE:    Event              : BL_32
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 5d c6 ef 35 5a 90 81 b4 37 e6 3b 52 da 92 ab 8e
+	NOTICE:  		      : d9 6e 93 98 2d 40 87 96 1b 5a a7 ee f1 f4 40 63
+	NOTICE:    EventSize          : 18
+	NOTICE:    Event              : BL32_EXTRA1_IMAGE
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 39 b7 13 b9 93 db 32 2f 1b 48 30 eb 2c f2 5c 25
+	NOTICE:  		      : 00 0f 38 dc 8e c8 02 cd 79 f2 48 d2 2c 25 ab e2
+	NOTICE:    EventSize          : 6
+	NOTICE:    Event              : BL_33
+	NOTICE:  PCR_Event2:
+	NOTICE:    PCRIndex           : 0
+	NOTICE:    EventType          : 1
+	NOTICE:    Digests Count      : 1
+	NOTICE:      #0 AlgorithmId   : SHA256
+	NOTICE:         Digest        : 25 10 60 5d d4 bc 9d 82 7a 16 9f 8a cc 47 95 a6
+	NOTICE:  		      : fd ca a0 c1 2b c9 99 8f 51 20 ff c6 ed 74 68 5a
+	NOTICE:    EventSize          : 13
+	NOTICE:    Event              : NT_FW_CONFIG
+	NOTICE:  BL1: Booting BL31
+	NOTICE:  BL31: v2.5(release):v2.5
+	NOTICE:  BL31: Built : 10:41:20, Jul  2 2021
+
+Following up with the fTPM startup process, we can see that all the
+measurements in the Event Log are extended and recorded in the appropriate PCR:
+
+.. code:: shell
+
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: TPM2_PCR_EXTEND_COMMAND returned value:
+	M/TA: 	ret_tag = 0x8002, size = 0x00000013, rc = 0x00000000
+	M/TA: 9 Event logs processed
+
+After the fTPM TA is loaded, the call to ``insmod`` issued by the ``ftpm``
+alias to load the ftpm kernel module returns, and then the TPM PCRs are read
+by means of ``tpm_pcrread`` command. Note that we are only interested in the
+SHA256 logs here, as this is the algorithm we used on TF-A for the measurements
+(see the field ``AlgorithmId`` on the logs above):
+
+.. code:: shell
+
+	sha256:
+	0 : 0xA6EB3A7417B8CFA9EBA2E7C22AD5A4C03CDB8F3FBDD7667F9C3EF2EA285A8C9F
+	1 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	2 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	3 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	4 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	5 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	6 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	7 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	8 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	9 : 0x0000000000000000000000000000000000000000000000000000000000000000
+	10: 0x0000000000000000000000000000000000000000000000000000000000000000
+	11: 0x0000000000000000000000000000000000000000000000000000000000000000
+	12: 0x0000000000000000000000000000000000000000000000000000000000000000
+	13: 0x0000000000000000000000000000000000000000000000000000000000000000
+	14: 0x0000000000000000000000000000000000000000000000000000000000000000
+	15: 0x0000000000000000000000000000000000000000000000000000000000000000
+	16: 0x0000000000000000000000000000000000000000000000000000000000000000
+	17: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	18: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	19: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	20: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	21: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	22: 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
+	23: 0x0000000000000000000000000000000000000000000000000000000000000000
+
+In this PoC we are only interested in PCR0, which must be non-null. This is
+because the boot process records all the images in this PCR (see field ``PCRIndex``
+on the Event Log above). The rest of the records must be 0 at this point.
+
+.. note::
+   The fTPM service used has support only for 16 PCRs, therefore the content
+   of PCRs above 15 can be ignored.
+
+.. note::
+   As stated earlier, Arm does not provide an fTPM implementation and therefore
+   we do not validate here if the content of PCR0 is correct or not. For this
+   PoC, we are only focused on the fact that the event log could be passed to a third
+   party fTPM and its records were properly extended.
+
+Fine-tuning the fTPM TA
+~~~~~~~~~~~~~~~~~~~~~~~
+
+As stated earlier, the OP-TEE Toolkit includes support to build a third party fTPM
+service. The build options for this service are tailored for the PoC and defined in
+the build environment variable ``FTPM_FLAGS`` (see ``<toolkit_home>/build/common.mk``)
+but they can be modified if needed to better adapt it to a specific scenario.
+
+The most relevant options for Measured Boot support are:
+
+   - **CFG_TA_DEBUG**: Enables debug logs in the Terminal_1 console.
+   - **CFG_TEE_TA_LOG_LEVEL**: Defines the log level used for the debug messages.
+   - **CFG_TA_MEASURED_BOOT**: Enables support for measured boot on the fTPM.
+   - **CFG_TA_EVENT_LOG_SIZE**: Defines the size, in bytes, of the larger event log that
+     the fTPM is able to store, as this buffer is allocated at build time. This must be at
+     least the same as the size of the event log generated by TF-A. If this build option
+     is not defined, the fTPM falls back to a default value of 1024 bytes, which is enough
+     for this PoC, so this variable is not defined in FTPM_FLAGS.
+
+--------------
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
+
+.. _OP-TEE Toolkit: https://github.com/OP-TEE/build
+.. _ms-tpm-20-ref: https://github.com/microsoft/ms-tpm-20-ref
+.. _Get and build the solution: https://optee.readthedocs.io/en/latest/building/gits/build.html#get-and-build-the-solution
+.. _Armv8-A Foundation Platform (For Linux Hosts Only): https://developer.arm.com/tools-and-software/simulation-models/fixed-virtual-platforms/arm-ecosystem-models
+.. _tpm2-tools: https://github.com/tpm2-software/tpm2-tools
+.. _TGC event log: https://trustedcomputinggroup.org/resource/tcg-efi-platform-specification/
diff --git a/docs/getting_started/build-options.rst b/docs/getting_started/build-options.rst
index 8adf4ad..7662a14 100644
--- a/docs/getting_started/build-options.rst
+++ b/docs/getting_started/build-options.rst
@@ -22,10 +22,20 @@
    directory containing the SP source, relative to the ``bl32/``; the directory
    is expected to contain a makefile called ``<aarch32_sp-value>.mk``.
 
+-  ``AMU_RESTRICT_COUNTERS``: Register reads to the group 1 counters will return
+   zero at all but the highest implemented exception level.  Reads from the
+   memory mapped view are unaffected by this control.
+
 -  ``ARCH`` : Choose the target build architecture for TF-A. It can take either
    ``aarch64`` or ``aarch32`` as values. By default, it is defined to
    ``aarch64``.
 
+-  ``ARM_ARCH_FEATURE``: Optional Arm Architecture build option which specifies
+   one or more feature modifiers. This option has the form ``[no]feature+...``
+   and defaults to ``none``. It translates into compiler option
+   ``-march=armvX[.Y]-a+[no]feature+...``. See compiler's documentation for the
+   list of supported feature modifiers.
+
 -  ``ARM_ARCH_MAJOR``: The major version of Arm Architecture to target when
    compiling TF-A. Its value must be numeric, and defaults to 8 . See also,
    *Armv8 Architecture Extensions* and *Armv7 Architecture Extensions* in
@@ -45,6 +55,9 @@
 -  ``BL2_AT_EL3``: This is an optional build option that enables the use of
    BL2 at EL3 execution level.
 
+-  ``BL2_ENABLE_SP_LOAD``: Boolean option to enable loading SP packages from the
+   FIP. Automatically enabled if ``SP_LAYOUT_FILE`` is provided.
+
 -  ``BL2_IN_XIP_MEM``: In some use-cases BL2 will be stored in eXecute In Place
    (XIP) memory, like BL1. In these use-cases, it is necessary to initialize
    the RW sections in RAM, while leaving the RO sections in place. This option
@@ -107,7 +120,7 @@
    |   4   |     bti      |   N   |  Y  |
    +-------+--------------+-------+-----+
 
-   This option defaults to 0 and this is an experimental feature.
+   This option defaults to 0.
    Note that Pointer Authentication is enabled for Non-secure world
    irrespective of the value of this option if the CPU supports it.
 
@@ -168,7 +181,7 @@
 -  ``CTX_INCLUDE_PAUTH_REGS``: Boolean option that, when set to 1, enables
    Pointer Authentication for Secure world. This will cause the ARMv8.3-PAuth
    registers to be included when saving and restoring the CPU context as
-   part of world switch. Default value is 0 and this is an experimental feature.
+   part of world switch. Default value is 0.
    Note that Pointer Authentication is enabled for Non-secure world irrespective
    of the value of this flag if the CPU supports it.
 
@@ -179,12 +192,17 @@
    authenticated decryption algorithm to be used to decrypt firmware/s during
    boot. It accepts 2 values: ``aes_gcm`` and ``none``. The default value of
    this flag is ``none`` to disable firmware decryption which is an optional
-   feature as per TBBR. Also, it is an experimental feature.
+   feature as per TBBR.
 
 -  ``DISABLE_BIN_GENERATION``: Boolean option to disable the generation
    of the binary image. If set to 1, then only the ELF image is built.
    0 is the default.
 
+-  ``DISABLE_MTPMU``: Boolean option to disable FEAT_MTPMU if implemented
+   (Armv8.6 onwards). Its default value is 0 to keep consistency with platforms
+   that do not implement FEAT_MTPMU. For more information on FEAT_MTPMU,
+   check the latest Arm ARM.
+
 -  ``DYN_DISABLE_AUTH``: Provides the capability to dynamically disable Trusted
    Board Boot authentication at runtime. This option is meant to be enabled only
    for development platforms. ``TRUSTED_BOARD_BOOT`` flag must be set if this
@@ -202,6 +220,14 @@
    v8.2 implementations also implement an AMU and this option can be used to
    enable this feature on those systems as well. Default is 0.
 
+-  ``ENABLE_AMU_AUXILIARY_COUNTERS``: Enables support for AMU auxiliary counters
+   (also known as group 1 counters). These are implementation-defined counters,
+   and as such require additional platform configuration. Default is 0.
+
+-  ``ENABLE_AMU_FCONF``: Enables configuration of the AMU through FCONF, which
+   allows platforms with auxiliary counters to describe them via the
+   ``HW_CONFIG`` device tree blob. Default is 0.
+
 -  ``ENABLE_ASSERTIONS``: This option controls whether or not calls to ``assert()``
    are compiled out. For debug builds, this option defaults to 1, and calls to
    ``assert()`` are left in place. For release builds, this option defaults to 0
@@ -220,6 +246,10 @@
    builds, but this behaviour can be overridden in each platform's Makefile or
    in the build command line.
 
+-  ``ENABLE_FEAT_HCX``: This option sets the bit SCR_EL3.HXEn in EL3 to allow
+   access to HCRX_EL2 (extended hypervisor control register) from EL2 as well as
+   adding HCRX_EL2 to the EL2 context save/restore operations.
+
 -  ``ENABLE_LTO``: Boolean option to enable Link Time Optimization (LTO)
    support in GCC for TF-A. This option is currently only supported for
    AArch64. Default is 0.
@@ -235,9 +265,20 @@
    partitioning in EL3, however. Platform initialisation code should configure
    and use partitions in EL3 as required. This option defaults to ``0``.
 
+-  ``ENABLE_MPMM``: Boolean option to enable support for the Maximum Power
+   Mitigation Mechanism supported by certain Arm cores, which allows the SoC
+   firmware to detect and limit high activity events to assist in SoC processor
+   power domain dynamic power budgeting and limit the triggering of whole-rail
+   (i.e. clock chopping) responses to overcurrent conditions. Defaults to ``0``.
+
+-  ``ENABLE_MPMM_FCONF``: Enables configuration of MPMM through FCONF, which
+   allows platforms with cores supporting MPMM to describe them via the
+   ``HW_CONFIG`` device tree blob. Default is 0.
+
 -  ``ENABLE_PIE``: Boolean option to enable Position Independent Executable(PIE)
    support within generic code in TF-A. This option is currently only supported
-   in BL2_AT_EL3, BL31, and BL32 (TSP). Default is 0.
+   in BL2_AT_EL3, BL31, and BL32 (TSP) for AARCH64 binaries, and in BL32
+   (SP_min) for AARCH32. Default is 0.
 
 -  ``ENABLE_PMF``: Boolean option to enable support for optional Performance
    Measurement Framework(PMF). Default is 0.
@@ -248,12 +289,31 @@
    be enabled. If ``ENABLE_PMF`` is set, the residency statistics are tracked in
    software.
 
+- ``ENABLE_RME``: Boolean option to enable support for the ARMv9 Realm
+   Management Extension. Default value is 0. This is currently an experimental
+   feature.
+
 -  ``ENABLE_RUNTIME_INSTRUMENTATION``: Boolean option to enable runtime
    instrumentation which injects timestamp collection points into TF-A to
    allow runtime performance to be measured. Currently, only PSCI is
    instrumented. Enabling this option enables the ``ENABLE_PMF`` build option
    as well. Default is 0.
 
+-  ``ENABLE_SME_FOR_NS``: Boolean option to enable Scalable Matrix Extension
+   (SME), SVE, and FPU/SIMD for the non-secure world only. These features share
+   registers so are enabled together. Using this option without
+   ENABLE_SME_FOR_SWD=1 will cause SME, SVE, and FPU/SIMD instructions in secure
+   world to trap to EL3. SME is an optional architectural feature for AArch64
+   and TF-A support is experimental. At this time, this build option cannot be
+   used on systems that have SPD=spmd/SPM_MM or ENABLE_RME, and attempting to
+   build with these options will fail. Default is 0.
+
+-  ``ENABLE_SME_FOR_SWD``: Boolean option to enable the Scalable Matrix
+   Extension for secure world use along with SVE and FPU/SIMD, ENABLE_SME_FOR_NS
+   must also be set to use this. If enabling this, the secure world MUST
+   handle context switching for SME, SVE, and FPU/SIMD registers to ensure that
+   no data is leaked to non-secure world. This is experimental. Default is 0.
+
 -  ``ENABLE_SPE_FOR_LOWER_ELS`` : Boolean option to enable Statistical Profiling
    extensions. This is an optional architectural feature for AArch64.
    The default is 1 but is automatically disabled when the target architecture
@@ -262,13 +322,20 @@
 -  ``ENABLE_SVE_FOR_NS``: Boolean option to enable Scalable Vector Extension
    (SVE) for the Non-secure world only. SVE is an optional architectural feature
    for AArch64. Note that when SVE is enabled for the Non-secure world, access
-   to SIMD and floating-point functionality from the Secure world is disabled.
+   to SIMD and floating-point functionality from the Secure world is disabled by
+   default and controlled with ENABLE_SVE_FOR_SWD.
    This is to avoid corruption of the Non-secure world data in the Z-registers
    which are aliased by the SIMD and FP registers. The build option is not
    compatible with the ``CTX_INCLUDE_FPREGS`` build option, and will raise an
    assert on platforms where SVE is implemented and ``ENABLE_SVE_FOR_NS`` set to
-   1. The default is 1 but is automatically disabled when the target
-   architecture is AArch32.
+   1. The default is 1 but is automatically disabled when ENABLE_SME_FOR_NS=1
+   since SME encompasses SVE. At this time, this build option cannot be used on
+   systems that have SPM_MM enabled.
+
+-  ``ENABLE_SVE_FOR_SWD``: Boolean option to enable SVE for the Secure world.
+   SVE is an optional architectural feature for AArch64. Note that this option
+   requires ENABLE_SVE_FOR_NS to be enabled.  The default is 0 and it is
+   automatically disabled when the target architecture is AArch32.
 
 -  ``ENABLE_STACK_PROTECTOR``: String option to enable the stack protection
    checks in GCC. Allowed values are "all", "strong", "default" and "none". The
@@ -279,20 +346,18 @@
    component of the option ``-fstack-protector-$ENABLE_STACK_PROTECTOR``.
 
 -  ``ENCRYPT_BL31``: Binary flag to enable encryption of BL31 firmware. This
-   flag depends on ``DECRYPTION_SUPPORT`` build flag which is marked as
-   experimental.
+   flag depends on ``DECRYPTION_SUPPORT`` build flag.
 
 -  ``ENCRYPT_BL32``: Binary flag to enable encryption of Secure BL32 payload.
-   This flag depends on ``DECRYPTION_SUPPORT`` build flag which is marked as
-   experimental.
+   This flag depends on ``DECRYPTION_SUPPORT`` build flag.
 
 -  ``ENC_KEY``: A 32-byte (256-bit) symmetric key in hex string format. It could
    either be SSK or BSSK depending on ``FW_ENC_STATUS`` flag. This value depends
-   on ``DECRYPTION_SUPPORT`` build flag which is marked as experimental.
+   on ``DECRYPTION_SUPPORT`` build flag.
 
 -  ``ENC_NONCE``: A 12-byte (96-bit) encryption nonce or Initialization Vector
    (IV) in hex string format. This value depends on ``DECRYPTION_SUPPORT``
-   build flag which is marked as experimental.
+   build flag.
 
 -  ``ERROR_DEPRECATED``: This option decides whether to treat the usage of
    deprecated platform APIs, helper functions or drivers within Trusted
@@ -331,8 +396,7 @@
      1: Encryption is done with Binding Secret Symmetric Key (BSSK) which is
         unique per device.
 
-   This flag depends on ``DECRYPTION_SUPPORT`` build flag which is marked as
-   experimental.
+   This flag depends on ``DECRYPTION_SUPPORT`` build flag.
 
 -  ``GENERATE_COT``: Boolean flag used to build and execute the ``cert_create``
    tool to create certificates as per the Chain of Trust described in
@@ -392,7 +456,7 @@
    library is not supported.
 
 -  ``INVERTED_MEMMAP``: memmap tool print by default lower addresses at the
-   bottom, higher addresses at the top. This buid flag can be set to '1' to
+   bottom, higher addresses at the top. This build flag can be set to '1' to
    invert this behavior. Lower addresses will be printed at the top and higher
    addresses at the bottom.
 
@@ -447,9 +511,11 @@
    the build. The default value is 40 in debug builds and 20 in release builds.
 
 -  ``MEASURED_BOOT``: Boolean flag to include support for the Measured Boot
-   feature. If this flag is enabled ``TRUSTED_BOARD_BOOT`` must be set.
-   This option defaults to 0 and is an experimental feature in the stage of
-   development.
+   feature. If this flag is enabled ``TRUSTED_BOARD_BOOT`` must be set as well
+   in order to provide trust that the code taking the measurements and recording
+   them has not been tampered with.
+
+   This option defaults to 0.
 
 -  ``NON_TRUSTED_WORLD_KEY``: This option is used when ``GENERATE_COT=1``. It
    specifies the file that contains the Non-Trusted World private key in PEM
@@ -559,10 +625,15 @@
 -  ``SEPARATE_NOBITS_REGION``: Setting this option to ``1`` allows the NOBITS
    sections of BL31 (.bss, stacks, page tables, and coherent memory) to be
    allocated in RAM discontiguous from the loaded firmware image. When set, the
-   platform is expected to provide definitons for ``BL31_NOBITS_BASE`` and
+   platform is expected to provide definitions for ``BL31_NOBITS_BASE`` and
    ``BL31_NOBITS_LIMIT``. When the option is ``0`` (the default), NOBITS
    sections are placed in RAM immediately following the loaded firmware image.
 
+-  ``SMC_PCI_SUPPORT``: This option allows platforms to handle PCI configuration
+   access requests via a standard SMCCC defined in `DEN0115`_. When combined with
+   UEFI+ACPI this can provide a certain amount of OS forward compatibility
+   with newer platforms that aren't ECAM compliant.
+
 -  ``SPD``: Choose a Secure Payload Dispatcher component to be built into TF-A.
    This build option is only valid if ``ARCH=aarch64``. The value should be
    the path to the directory containing the SPD source, relative to
@@ -654,26 +725,25 @@
 -  ``ARM_IO_IN_DTB``: This flag determines whether to use IO based on the
    firmware configuration framework. This will move the io_policies into a
    configuration device tree, instead of static structure in the code base.
-   This is currently an experimental feature.
 
 -  ``COT_DESC_IN_DTB``: This flag determines whether to create COT descriptors
    at runtime using fconf. If this flag is enabled, COT descriptors are
    statically captured in tb_fw_config file in the form of device tree nodes
    and properties. Currently, COT descriptors used by BL2 are moved to the
    device tree and COT descriptors used by BL1 are retained in the code
-   base statically. This is currently an experimental feature.
+   base statically.
 
 -  ``SDEI_IN_FCONF``: This flag determines whether to configure SDEI setup in
    runtime using firmware configuration framework. The platform specific SDEI
    shared and private events configuration is retrieved from device tree rather
-   than static C structures at compile time. This is currently an experimental
-   feature and is only supported if SDEI_SUPPORT build flag is enabled.
+   than static C structures at compile time. This is only supported if
+   SDEI_SUPPORT build flag is enabled.
 
 -  ``SEC_INT_DESC_IN_FCONF``: This flag determines whether to configure Group 0
    and Group1 secure interrupts using the firmware configuration framework. The
    platform specific secure interrupt property descriptor is retrieved from
    device tree in runtime rather than depending on static C structure at compile
-   time. This is currently an experimental feature.
+   time.
 
 -  ``USE_ROMLIB``: This flag determines whether library at ROM will be used.
    This feature creates a library of functions to be placed in ROM and thus
@@ -745,6 +815,21 @@
   functions that wait for an arbitrary time length (udelay and mdelay). The
   default value is 0.
 
+- ``ENABLE_TRBE_FOR_NS``: This flag is used to enable access of trace buffer
+  control registers from NS ELs, NS-EL2 or NS-EL1(when NS-EL2 is implemented
+  but unused) when FEAT_TRBE is implemented. TRBE is an optional architectural
+  feature for AArch64. The default is 0 and it is automatically disabled when
+  the target architecture is AArch32.
+
+- ``ENABLE_SYS_REG_TRACE_FOR_NS``: Boolean option to enable trace system
+  registers access from NS ELs, NS-EL2 or NS-EL1 (when NS-EL2 is implemented
+  but unused). This feature is available if trace unit such as ETMv4.x, and
+  ETE(extending ETM feature) is implemented. This flag is disabled by default.
+
+- ``ENABLE_TRF_FOR_NS``: Boolean option to enable trace filter control registers
+  access from NS ELs, NS-EL2 or NS-EL1 (when NS-EL2 is implemented but unused),
+  if FEAT_TRF is implemented. This flag is disabled by default.
+
 GICv3 driver options
 --------------------
 
@@ -760,6 +845,11 @@
    GIC-600, so is safe to select even for a GIC500 implementation.
    This option defaults to 0.
 
+- ``GICV3_SUPPORT_GIC600AE_FMU``: Add support for the Fault Management Unit
+   for GIC-600 AE. Enabling this option will introduce support to initialize
+   the FMU. Platforms should call the init function during boot to enable the
+   FMU and its safety mechanisms. This option defaults to 0.
+
 -  ``GICV3_IMPL_GIC600_MULTICHIP``: Selects GIC-600 variant with multichip
    functionality. This option defaults to 0
 
@@ -830,6 +920,30 @@
     # Resume execution
     continue
 
+Firmware update options
+-----------------------
+
+-  ``NR_OF_FW_BANKS``: Define the number of firmware banks. This flag is used
+   in defining the firmware update metadata structure. This flag is by default
+   set to '2'.
+
+-  ``NR_OF_IMAGES_IN_FW_BANK``: Define the number of firmware images in each
+   firmware bank. Each firmware bank must have the same number of images as per
+   the `PSA FW update specification`_.
+   This flag is used in defining the firmware update metadata structure. This
+   flag is by default set to '1'.
+
+-  ``PSA_FWU_SUPPORT``: Enable the firmware update mechanism as per the
+   `PSA FW update specification`_. The default value is 0, and this is an
+   experimental feature.
+   PSA firmware update implementation has some limitations, such as BL2 is
+   not part of the protocol-updatable images, if BL2 needs to be updated, then
+   it should be done through another platform-defined mechanism, and it assumes
+   that the platform's hardware supports CRC32 instructions.
+
 --------------
 
-*Copyright (c) 2019-2020, Arm Limited. All rights reserved.*
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
+
+.. _DEN0115: https://developer.arm.com/docs/den0115/latest
+.. _PSA FW update specification: https://developer.arm.com/documentation/den0118/a/
diff --git a/docs/getting_started/image-terminology.rst b/docs/getting_started/image-terminology.rst
index 5993d6e..a90ec0b 100644
--- a/docs/getting_started/image-terminology.rst
+++ b/docs/getting_started/image-terminology.rst
@@ -92,6 +92,14 @@
 abbreviated name should identify the vendor as well as the image
 function. For example, ``AP_BL3_ARM_RAS``.
 
+Realm Monitor Management Firmware: ``RMM``
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+This is the Realm-EL2 firmware. It is required if
+:ref:`Realm Management Extension (RME)` feature is enabled. If a path to RMM
+image is not provided, TF-A builds Test Realm Payload (TRP) image by default
+and uses it as the RMM image.
+
 SCP Boot ROM: ``SCP_BL1`` (previously ``BL0``)
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
diff --git a/docs/getting_started/porting-guide.rst b/docs/getting_started/porting-guide.rst
index 19e26e4..92ff39f 100644
--- a/docs/getting_started/porting-guide.rst
+++ b/docs/getting_started/porting-guide.rst
@@ -116,7 +116,7 @@
    by ``plat/common/aarch64/platform_mp_stack.S`` and
    ``plat/common/aarch64/platform_up_stack.S``.
 
--  **define : CACHE_WRITEBACK_GRANULE**
+-  **#define : CACHE_WRITEBACK_GRANULE**
 
    Defines the size in bits of the largest cache line across all the cache
    levels in the platform.
@@ -562,15 +562,6 @@
    doesn't print anything to the console. If ``PLAT_LOG_LEVEL_ASSERT`` isn't
    defined, it defaults to ``LOG_LEVEL``.
 
-If the platform port uses the Activity Monitor Unit, the following constant
-may be defined:
-
--  **PLAT_AMU_GROUP1_COUNTERS_MASK**
-   This mask reflects the set of group counters that should be enabled.  The
-   maximum number of group 1 counters supported by AMUv1 is 16 so the mask
-   can be at most 0xffff. If the platform does not define this mask, no group 1
-   counters are enabled.
-
 File : plat_macros.S [mandatory]
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
@@ -891,8 +882,55 @@
 
 On success the function should return 0 and a negative error code otherwise.
 
-Note that this API depends on ``DECRYPTION_SUPPORT`` build flag which is
-marked as experimental.
+Note that this API depends on ``DECRYPTION_SUPPORT`` build flag.
+
+Function : plat_fwu_set_images_source() [when PSA_FWU_SUPPORT == 1]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : struct fwu_metadata *metadata
+    Return   : void
+
+This function is mandatory when PSA_FWU_SUPPORT is enabled.
+It provides a means to retrieve image specification (offset in
+non-volatile storage and length) of active/updated images using the passed
+FWU metadata, and update I/O policies of active/updated images using retrieved
+image specification information.
+Further I/O layer operations such as I/O open, I/O read, etc. on these
+images rely on this function call.
+
+In Arm platforms, this function is used to set an I/O policy of the FIP image,
+container of all active/updated secure and non-secure images.
+
+Function : plat_fwu_set_metadata_image_source() [when PSA_FWU_SUPPORT == 1]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : unsigned int image_id, uintptr_t *dev_handle,
+               uintptr_t *image_spec
+    Return   : int
+
+This function is mandatory when PSA_FWU_SUPPORT is enabled. It is
+responsible for setting up the platform I/O policy of the requested metadata
+image (either FWU_METADATA_IMAGE_ID or BKUP_FWU_METADATA_IMAGE_ID) that will
+be used to load this image from the platform's non-volatile storage.
+
+FWU metadata can not be always stored as a raw image in non-volatile storage
+to define its image specification (offset in non-volatile storage and length)
+statically in I/O policy.
+For example, the FWU metadata image is stored as a partition inside the GUID
+partition table image. Its specification is defined in the partition table
+that needs to be parsed dynamically.
+This function provides a means to retrieve such dynamic information to set
+the I/O policy of the FWU metadata image.
+Further I/O layer operations such as I/O open, I/O read, etc. on FWU metadata
+image relies on this function call.
+
+It returns '0' on success, otherwise a negative error value on error.
+Alongside, returns device handle and image specification from the I/O policy
+of the requested FWU metadata image.
 
 Common optional modifications
 -----------------------------
@@ -1151,6 +1189,25 @@
 the SMCCC function specified in the argument; otherwise returns
 SMC_ARCH_CALL_NOT_SUPPORTED.
 
+Function : plat_mboot_measure_image()
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : unsigned int, image_info_t *
+    Return   : void
+
+When the MEASURED_BOOT flag is enabled:
+
+-  This function measures the given image and records its measurement using
+   the measured boot backend driver.
+-  On the Arm FVP port, this function measures the given image using its
+   passed id and information and then records that measurement in the
+   Event Log buffer.
+-  This function must return 0 on success, a negative error code otherwise.
+
+When the MEASURED_BOOT flag is disabled, this function doesn't do anything.
+
 Modifications specific to a Boot Loader stage
 ---------------------------------------------
 
@@ -1402,6 +1459,42 @@
 The default implementation of this function asserts therefore platforms must
 override it when using the FWU feature.
 
+Function : bl1_plat_mboot_init() [optional]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : void
+    Return   : void
+
+When the MEASURED_BOOT flag is enabled:
+
+-  This function is used to initialize the backend driver(s) of measured boot.
+-  On the Arm FVP port, this function is used to initialize the Event Log
+   backend driver, and also to write header information in the Event Log buffer.
+
+When the MEASURED_BOOT flag is disabled, this function doesn't do anything.
+
+Function : bl1_plat_mboot_finish() [optional]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : void
+    Return   : void
+
+When the MEASURED_BOOT flag is enabled:
+
+-  This function is used to finalize the measured boot backend driver(s),
+   and also, set the information for the next bootloader component to
+   extend the measurement if needed.
+-  On the Arm FVP port, this function is used to pass the base address of
+   the Event Log buffer and its size to BL2 via tb_fw_config to extend the
+   Event Log buffer with the measurement of various images loaded by BL2.
+   It results in panic on error.
+
+When the MEASURED_BOOT flag is disabled, this function doesn't do anything.
+
 Boot Loader Stage 2 (BL2)
 -------------------------
 
@@ -1690,6 +1783,42 @@
 This function returns 0 on success, a negative error code otherwise.
 This function is included if SCP_BL2U_BASE is defined.
 
+Function : bl2_plat_mboot_init() [optional]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : void
+    Return   : void
+
+When the MEASURED_BOOT flag is enabled:
+
+-  This function is used to initialize the backend driver(s) of measured boot.
+-  On the Arm FVP port, this function is used to initialize the Event Log
+   backend driver with the Event Log buffer information (base address and
+   size) received from BL1. It results in panic on error.
+
+When the MEASURED_BOOT flag is disabled, this function doesn't do anything.
+
+Function : bl2_plat_mboot_finish() [optional]
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+::
+
+    Argument : void
+    Return   : void
+
+When the MEASURED_BOOT flag is enabled:
+
+-  This function is used to finalize the measured boot backend driver(s),
+   and also, set the information for the next bootloader component to extend
+   the measurement if needed.
+-  On the Arm FVP port, this function is used to pass the Event Log buffer
+   information (base address and size) to non-secure(BL33) and trusted OS(BL32)
+   via nt_fw and tos_fw config respectively. It results in panic on error.
+
+When the MEASURED_BOOT flag is disabled, this function doesn't do anything.
+
 Boot Loader Stage 3-1 (BL31)
 ----------------------------
 
@@ -1742,9 +1871,9 @@
     which is list of executable images following BL31,
 
     arg1 - Points to load address of SOC_FW_CONFIG if present
-           except in case of Arm FVP platform.
+           except in case of Arm FVP and Juno platform.
 
-           In case of Arm FVP platform, Points to load address
+           In case of Arm FVP and Juno platform, points to load address
            of FW_CONFIG.
 
     arg2 - Points to load address of HW_CONFIG if present
@@ -2009,6 +2138,53 @@
 
 The default implementation only prints out a warning message.
 
+.. _porting_guide_trng_requirements:
+
+TRNG porting requirements
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+The |TRNG| backend requires the platform to provide the following values
+and mandatory functions.
+
+Values
+......
+
+value: uuid_t plat_trng_uuid [mandatory]
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+This value must be defined to the UUID of the TRNG backend that is specific to
+the hardware after ``plat_trng_setup`` function is called. This value must
+conform to the SMCCC calling convention; The most significant 32 bits of the
+UUID must not equal ``0xffffffff`` or the signed integer ``-1`` as this value in
+w0 indicates failure to get a TRNG source.
+
+Functions
+.........
+
+Function: void plat_entropy_setup(void) [mandatory]
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+::
+
+  Argument: none
+  Return: none
+
+This function is expected to do platform-specific initialization of any TRNG
+hardware. This may include generating a UUID from a hardware-specific seed.
+
+Function: bool plat_get_entropy(uint64_t \*out) [mandatory]
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+::
+
+  Argument: uint64_t *
+  Return: bool
+  Out : when the return value is true, the entropy has been written into the
+  storage pointed to
+
+This function writes entropy into storage provided by the caller. If no entropy
+is available, it must return false and the storage must not be written.
+
 Power State Coordination Interface (in BL31)
 --------------------------------------------
 
@@ -2941,7 +3117,7 @@
 
 --------------
 
-*Copyright (c) 2013-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _PSCI: http://infocenter.arm.com/help/topic/com.arm.doc.den0022c/DEN0022C_Power_State_Coordination_Interface.pdf
 .. _Arm Generic Interrupt Controller version 2.0 (GICv2): http://infocenter.arm.com/help/topic/com.arm.doc.ihi0048b/index.html
diff --git a/docs/getting_started/prerequisites.rst b/docs/getting_started/prerequisites.rst
index 91ecdf3..f45193a 100644
--- a/docs/getting_started/prerequisites.rst
+++ b/docs/getting_started/prerequisites.rst
@@ -26,7 +26,7 @@
 |TF-A| can be built with any of the following *cross-compiler* toolchains that
 target the Armv7-A or Armv8-A architectures:
 
-- GCC >= 9.2-2019.12 (from the `Arm Developer website`_)
+- GCC >= 10.3-2021.07 (from the `Arm Developer website`_)
 - Clang >= 4.0
 - Arm Compiler >= 6.0
 
@@ -60,7 +60,7 @@
 
 The following libraries are required for Trusted Board Boot support:
 
-- mbed TLS == 2.24.0 (tag: ``mbedtls-2.24.0``)
+- mbed TLS == 2.26.0 (tag: ``mbedtls-2.26.0``)
 
 These tools are optional:
 
@@ -75,6 +75,12 @@
    The standard software package used for debugging software on Arm development
    platforms and |FVP| models.
 
+- Node.js >= 14
+
+   Highly recommended, and necessary in order to install and use the packaged
+   Git hooks and helper tools. Without these tools you will need to rely on the
+   CI for feedback on commit message conformance.
+
 Package Installation (Linux)
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
@@ -91,11 +97,22 @@
 
     sudo apt install device-tree-compiler
 
+Additionally, to install an up-to-date version of Node.js, you can use the `Node
+Version Manager`_ to install a version of your choosing (we recommend 14, but
+later LTS versions might offer a more stable experience):
+
+.. code:: shell
+
+    curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.38.0/install.sh | "$SHELL"
+    exec "$SHELL" -ic "nvm install 14; exec $SHELL"
+
+.. _Node Version Manager: https://github.com/nvm-sh/nvm#install--update-script
+
 Supporting Files
 ----------------
 
 TF-A has been tested with pre-built binaries and file systems from `Linaro
-Release 19.06`_. Alternatively, you can build the binaries from source using
+Release 20.01`_. Alternatively, you can build the binaries from source using
 instructions in :ref:`Performing an Initial Build`.
 
 .. _prerequisites_get_source:
@@ -109,28 +126,44 @@
 
 .. code:: shell
 
-    git clone "https://review.trustedfirmware.org/TF-A/trusted-firmware-a" && (cd "trusted-firmware-a" && mkdir -p .git/hooks && curl -Lo `git rev-parse --git-dir`/hooks/commit-msg https://review.trustedfirmware.org/tools/hooks/commit-msg; chmod +x `git rev-parse --git-dir`/hooks/commit-msg)
+    git clone "https://review.trustedfirmware.org/TF-A/trusted-firmware-a"
 
-This will clone the Git repository also install a *commit hook* that
-automatically inserts appropriate *Change-Id:* lines at the end of your
-commit messages. These change IDs are required when committing changes that you
-intend to push for review via our Gerrit system.
+Additional Steps for Contributors
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-You can read more about Git hooks in the *githooks* page of the Git documentation,
-available at: https://git-scm.com/docs/githooks
+If you are planning on contributing back to TF-A, there are some things you'll
+want to know.
 
-Alternatively, you can clone without the commit hook using:
+TF-A is hosted by a `Gerrit Code Review`_ server. Gerrit requires that all
+commits include a ``Change-Id`` footer, and this footer is typically
+automatically generated by a Git hook installed by you, the developer.
+
+If you have Node.js installed already, you can automatically install this hook,
+along with any additional hooks and Javascript-based tooling that we use, by
+running from within your newly-cloned repository:
 
 .. code:: shell
 
-    git clone "https://review.trustedfirmware.org/TF-A/trusted-firmware-a"
+    npm install --no-save
+
+If you have opted **not** to install Node.js, you can install the Gerrit hook
+manually by running:
+
+.. code:: shell
+
+    curl -Lo $(git rev-parse --git-dir)/hooks/commit-msg https://review.trustedfirmware.org/tools/hooks/commit-msg
+    chmod +x $(git rev-parse --git-dir)/hooks/commit-msg
+
+You can read more about Git hooks in the *githooks* page of the Git
+documentation, available `here <https://git-scm.com/docs/githooks>`_.
 
 --------------
 
-*Copyright (c) 2019, Arm Limited. All rights reserved.*
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
 
 .. _Arm Developer website: https://developer.arm.com/open-source/gnu-toolchain/gnu-a/downloads
+.. _Gerrit Code Review: https://www.gerritcodereview.com/
 .. _Linaro Release Notes: https://community.arm.com/dev-platforms/w/docs/226/old-release-notes
 .. _Linaro instructions: https://community.arm.com/dev-platforms/w/docs/304/arm-reference-platforms-deliverables
 .. _Development Studio 5 (DS-5): https://developer.arm.com/products/software-development-tools/ds-5-development-studio
-.. _Linaro Release 19.06: http://releases.linaro.org/members/arm/platforms/19.06
+.. _Linaro Release 20.01: http://releases.linaro.org/members/arm/platforms/20.01
diff --git a/docs/getting_started/rt-svc-writers-guide.rst b/docs/getting_started/rt-svc-writers-guide.rst
index b3758b8..5a4be4d 100644
--- a/docs/getting_started/rt-svc-writers-guide.rst
+++ b/docs/getting_started/rt-svc-writers-guide.rst
@@ -200,13 +200,13 @@
        SMC_RET1(handle, SMC_UNK);
 
 #. Determining if the requested function is valid for the calling security
-   state. SMC Calls can be made from both the normal and trusted worlds and
+   state. SMC Calls can be made from Non-secure, Secure or Realm worlds and
    the framework will forward all calls to the service handler.
 
    The ``flags`` parameter to this function indicates the caller security state
-   in bit[0], where a value of ``1`` indicates a non-secure caller. The
-   ``is_caller_secure(flags)`` and ``is_caller_non_secure(flags)`` can be used to
-   test this condition.
+   in bits 0 and 5. The ``is_caller_secure(flags)``, ``is_caller_non_secure(flags)``
+   and ``is_caller_realm(flags)`` helper functions can be used to determine whether
+   the caller's security state is Secure, Non-secure or Realm respectively.
 
    If invalid, the request should be completed with:
 
@@ -314,7 +314,7 @@
 
 --------------
 
-*Copyright (c) 2014-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2014-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _SMCCC: https://developer.arm.com/docs/den0028/latest
 .. _PSCI: http://infocenter.arm.com/help/topic/com.arm.doc.den0022c/DEN0022C_Power_State_Coordination_Interface.pdf
diff --git a/docs/global_substitutions.txt b/docs/global_substitutions.txt
index d33155b..af15146 100644
--- a/docs/global_substitutions.txt
+++ b/docs/global_substitutions.txt
@@ -1,5 +1,7 @@
 .. |AArch32| replace:: :term:`AArch32`
 .. |AArch64| replace:: :term:`AArch64`
+.. |AMU| replace:: :term:`AMU`
+.. |AMUs| replace:: :term:`AMUs <AMU>`
 .. |API| replace:: :term:`API`
 .. |BTI| replace:: :term:`BTI`
 .. |CoT| replace:: :term:`CoT`
@@ -23,6 +25,7 @@
 .. |Linaro| replace:: :term:`Linaro`
 .. |MMU| replace:: :term:`MMU`
 .. |MPAM| replace:: :term:`MPAM`
+.. |MPMM| replace:: :term:`MPMM`
 .. |MPIDR| replace:: :term:`MPIDR`
 .. |MTE| replace:: :term:`MTE`
 .. |OEN| replace:: :term:`OEN`
@@ -56,6 +59,7 @@
 .. |TF-M| replace:: :term:`TF-M`
 .. |TLB| replace:: :term:`TLB`
 .. |TLK| replace:: :term:`TLK`
+.. |TRNG| replace:: :term:`TRNG`
 .. |TSP| replace:: :term:`TSP`
 .. |TZC| replace:: :term:`TZC`
 .. |UBSAN| replace:: :term:`UBSAN`
diff --git a/docs/glossary.rst b/docs/glossary.rst
index 08add3a..aeeb133 100644
--- a/docs/glossary.rst
+++ b/docs/glossary.rst
@@ -15,6 +15,10 @@
    AArch64
       64-bit execution state of the ARMv8 ISA
 
+   AMU
+      Activity Monitor Unit, a hardware monitoring unit introduced by FEAT_AMUv1
+      that exposes CPU core runtime metrics as a set of counter registers.
+
    API
       Application Programming Interface
 
@@ -60,8 +64,8 @@
    FDT
       Flattened Device Tree
 
-   FFA
-      Firmware Framework for A-class processors
+   FF-A
+      Firmware Framework for Arm A-profile
 
    FIP
       Firmware Image Package
@@ -88,6 +92,10 @@
    MPAM
       Memory Partitioning And Monitoring. An optional Armv8.4 extension.
 
+   MPMM
+     Maximum Power Mitigation Mechanism, an optional power management mechanism
+     supported by some Arm Armv9-A cores.
+
    MPIDR
       Multiprocessor Affinity Register
 
@@ -193,6 +201,9 @@
    TLK
       Trusted Little Kernel. A Trusted OS from NVIDIA.
 
+   TRNG
+      True Randon Number Generator (hardware based)
+
    TSP
       Test Secure Payload
 
diff --git a/docs/index.rst b/docs/index.rst
index cb53127..edc2535 100644
--- a/docs/index.rst
+++ b/docs/index.rst
@@ -15,8 +15,8 @@
    perf/index
    security_advisories/index
    design_documents/index
+   threat_model/index
    change-log
-   change-log-upcoming
    glossary
    license
 
@@ -30,6 +30,7 @@
 -  `SMC Calling Convention`_
 -  `System Control and Management Interface (SCMI)`_
 -  `Software Delegated Exception Interface (SDEI)`_
+-  `PSA FW update specification`_
 
 Where possible, the code is designed for reuse or porting to other Armv7-A and
 Armv8-A model and hardware platforms.
@@ -83,7 +84,7 @@
 
 --------------
 
-*Copyright (c) 2013-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.*
 
 .. _Armv7-A and Armv8-A: https://developer.arm.com/products/architecture/a-profile
 .. _Secure Monitor: http://www.arm.com/products/processors/technologies/trustzone/tee-smc.php
@@ -92,3 +93,4 @@
 .. _System Control and Management Interface (SCMI): http://infocenter.arm.com/help/topic/com.arm.doc.den0056a/DEN0056A_System_Control_and_Management_Interface.pdf
 .. _Software Delegated Exception Interface (SDEI): http://infocenter.arm.com/help/topic/com.arm.doc.den0054a/ARM_DEN0054A_Software_Delegated_Exception_Interface.pdf
 .. _SMC Calling Convention: https://developer.arm.com/docs/den0028/latest
+.. _PSA FW update specification: https://developer.arm.com/documentation/den0118/a/
diff --git a/docs/license.rst b/docs/license.rst
index 2f97043..80f1118 100644
--- a/docs/license.rst
+++ b/docs/license.rst
@@ -76,5 +76,15 @@
    BSD-3-Clause license. Any contributions to this code must be made under the
    terms of both licenses.
 
+-  Some source files originating from the Linux source tree, which are
+   disjunctively dual licensed (GPL-2.0 OR MIT), are redistributed under the
+   terms of the MIT license. These files are:
+
+   -  ``include/dt-bindings/interrupt-controller/arm-gic.h``
+   -  ``include/dt-bindings/interrupt-controller/irq.h``
+
+   See the original `Linux MIT license`_.
+
 .. _FreeBSD: http://www.freebsd.org
+.. _Linux MIT license: https://raw.githubusercontent.com/torvalds/linux/master/LICENSES/preferred/MIT
 .. _SCC: http://www.simple-cc.org/
diff --git a/docs/plat/allwinner.rst b/docs/plat/allwinner.rst
index d82380d..b696989 100644
--- a/docs/plat/allwinner.rst
+++ b/docs/plat/allwinner.rst
@@ -5,22 +5,8 @@
 SoCs with ARMv8 cores. Only BL31 is used to provide proper EL3 setup and
 PSCI runtime services.
 
-U-Boot's SPL acts as a loader, loading both BL31 and BL33 (typically U-Boot).
-Loading is done from SD card, eMMC or SPI flash, also via an USB debug
-interface (FEL).
-
-BL31 lives in SRAM A2, which is documented to be accessible from secure
-world only.
-
-Current limitations:
-
--  Missing PMIC support
-
-After building bl31.bin, the binary must be fed to the U-Boot build system
-to include it in the FIT image that the SPL loader will process.
-bl31.bin can be either copied (or sym-linked) into U-Boot's root directory,
-or the environment variable BL31 must contain the binary's path.
-See the respective `U-Boot documentation`_ for more details.
+Building TF-A
+-------------
 
 To build for machines with an A64 or H5 SoC:
 
@@ -34,8 +20,75 @@
 
     make CROSS_COMPILE=aarch64-linux-gnu- PLAT=sun50i_h6 DEBUG=1 bl31
 
+To build for machines with an H616 or H313 SoC:
+
+.. code:: shell
+
+    make CROSS_COMPILE=aarch64-linux-gnu- PLAT=sun50i_h616 DEBUG=1 bl31
+
+
+Installation
+------------
+
+U-Boot's SPL acts as a loader, loading both BL31 and BL33 (typically U-Boot).
+Loading is done from SD card, eMMC or SPI flash, also via an USB debug
+interface (FEL).
+
+After building bl31.bin, the binary must be fed to the U-Boot build system
+to include it in the FIT image that the SPL loader will process.
+bl31.bin can be either copied (or sym-linked) into U-Boot's root directory,
+or the environment variable BL31 must contain the binary's path.
+See the respective `U-Boot documentation`_ for more details.
+
 .. _U-Boot documentation: https://gitlab.denx.de/u-boot/u-boot/-/blob/master/board/sunxi/README.sunxi64
 
+Memory layout
+-------------
+
+A64, H5 and H6 SoCs
+~~~~~~~~~~~~~~~~~~~
+
+BL31 lives in SRAM A2, which is documented to be accessible from secure
+world only. Since this SRAM region is very limited (48 KB), we take
+several measures to reduce memory consumption. One of them is to confine
+BL31 to only 28 bits of virtual address space, which reduces the number
+of required page tables (each occupying 4KB of memory).
+The mapping we use on those SoCs is as follows:
+
+::
+
+   0 64K         16M             1GB         1G+160M     physical address
+   +-+------+-+---+------+--...---+-------+----+------+----------
+   |B|      |S|///|      |//...///|       |////|      |
+   |R| SRAM |C|///| dev  |//...///| (sec) |////| BL33 |  DRAM ...
+   |O|      |P|///| MMIO |//...///| DRAM  |////|      |
+   |M|      | |///|      |//...///| (32M) |////|      |
+   +-+------+-+---+------+--...---+-------+----+------+----------
+   | |      | |   |      |       /       /   /      /
+   | |      | |   |      |      /       /  /      /
+   | |      | |   |      |     /       / /      /
+   | |      | |   |      |    /       //      /
+   | |      | |   |      |   /       /      /
+   +-+------+-+---+------+--+-------+------+
+   |B|      |S|///|      |//|       |      |
+   |R| SRAM |C|///| dev  |//|  sec  | BL33 |
+   |O|      |P|///| MMIO |//| DRAM  |      |
+   |M|      | |///|      |//|       |      |
+   +-+------+-+---+------+--+-------+------+
+   0 64K         16M       160M    192M  256M             virtual address
+
+
+H616 SoC
+~~~~~~~~
+
+The H616 lacks the secure SRAM region present on the other SoCs, also
+lacks the "ARISC" management processor (SCP) we use. BL31 thus needs to
+run from DRAM, which prevents our compressed virtual memory map described
+above. Since running in DRAM also lifts the restriction of the limited
+SRAM size, we use the normal 1:1 mapping with 32 bits worth of virtual
+address space. So the virtual addresses used in BL31 match the physical
+addresses as presented above.
+
 Trusted OS dispatcher
 ---------------------
 
diff --git a/docs/plat/arm/arm-build-options.rst b/docs/plat/arm/arm-build-options.rst
index 2e50068..339ebbe 100644
--- a/docs/plat/arm/arm-build-options.rst
+++ b/docs/plat/arm/arm-build-options.rst
@@ -91,9 +91,33 @@
    platforms. If this option is specified, then the path to the CryptoCell
    SBROM library must be specified via ``CCSBROM_LIB_PATH`` flag.
 
+-  ``ARM_ETHOSN_NPU_DRIVER``: boolean option to enable a SiP service that can
+   configure an Arm Ethos-N NPU. To use this service the target platform's
+   ``HW_CONFIG`` must include the device tree nodes for the NPU. Currently, only
+   the Arm Juno platform has this included in its ``HW_CONFIG`` and the platform
+   only loads the ``HW_CONFIG`` in AArch64 builds. Default is 0.
+
 -  ``ARM_SPMC_MANIFEST_DTS`` : path to an alternate manifest file used as the
    SPMC Core manifest. Valid when ``SPD=spmd`` is selected.
 
+-  ``ARM_BL2_SP_LIST_DTS``: Path to DTS file snippet to override the hardcoded
+   SP nodes in tb_fw_config.
+
+-  ``OPTEE_SP_FW_CONFIG``: DTC build flag to include OP-TEE as SP in tb_fw_config
+   device tree. This flag is defined only when ``ARM_SPMC_MANIFEST_DTS`` manifest
+   file name contains pattern optee_sp.
+
+-  ``TS_SP_FW_CONFIG``: DTC build flag to include Trusted Services (Crypto and
+   internal-trusted-storage) as SP in tb_fw_config device tree.
+
+-  ``ARM_GPT_SUPPORT``: Enable GPT parser to get the entry address and length of
+   the various partitions present in the GPT image. This support is available
+   only for the BL2 component, and it is disabled by default.
+   The following diagram shows the view of the FIP partition inside the GPT
+   image:
+
+   |FIP in a GPT image|
+
 For a better understanding of these options, the Arm development platform memory
 map is explained in the :ref:`Firmware Design`.
 
@@ -122,6 +146,14 @@
    valid value greater than 1, the platform code performs required configuration
    to support multi-chip operation.
 
+- ``CSS_SGI_PLATFORM_VARIANT``: Selects the variant of a SGI/RD platform. A
+    particular SGI/RD platform may have multiple variants which may differ in
+    core count, cluster count or other peripherals. This build option is used
+    to select the appropriate platform variant for the build. The range of
+    valid values is platform specific.
+
 --------------
 
-*Copyright (c) 2019-2020, Arm Limited. All rights reserved.*
+.. |FIP in a GPT image| image:: ../../resources/diagrams/FIP_in_a_GPT_image.png
+
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
diff --git a/docs/plat/arm/diphda/index.rst b/docs/plat/arm/diphda/index.rst
new file mode 100644
index 0000000..27afda4
--- /dev/null
+++ b/docs/plat/arm/diphda/index.rst
@@ -0,0 +1,61 @@
+Diphda Platform
+==========================
+
+Some of the features of the Diphda platform referenced in TF-A include:
+
+- Cortex-A35 application processor (64-bit mode)
+- Secure Enclave
+- GIC-400
+- Trusted Board Boot
+
+Boot Sequence
+-------------
+
+The board boot relies on CoT (chain of trust). The trusted-firmware-a
+BL2 is extracted from the FIP and verified by the Secure Enclave
+processor. BL2 verification relies on the signature area at the
+beginning of the BL2 image. This area is needed by the SecureEnclave
+bootloader.
+
+Then, the application processor is released from reset and starts by
+executing BL2.
+
+BL2 performs the actions described in the trusted-firmware-a TBB design
+document.
+
+Build Procedure (TF-A only)
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+-  Obtain AArch64 ELF bare-metal target `toolchain <https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-a/downloads>`_.
+   Set the CROSS_COMPILE environment variable to point to the toolchain folder.
+
+-  Build TF-A:
+
+   .. code:: shell
+
+      make LD=aarch64-none-elf-ld \
+      CC=aarch64-none-elf-gcc \
+      V=1 \
+      BUILD_BASE=<path to the build folder> \
+      PLAT=diphda \
+      SPD=spmd \
+      SPMD_SPM_AT_SEL2=0 \
+      DEBUG=1 \
+      MBEDTLS_DIR=mbedtls \
+      OPENSSL_DIR=<path to openssl usr folder> \
+      RUNTIME_SYSROOT=<path to the sysroot> \
+      ARCH=aarch64 \
+      TARGET_PLATFORM=<fpga or fvp> \
+      ENABLE_PIE=1 \
+      BL2_AT_EL3=1 \
+      CREATE_KEYS=1 \
+      GENERATE_COT=1 \
+      TRUSTED_BOARD_BOOT=1 \
+      COT=tbbr \
+      ARM_ROTPK_LOCATION=devel_rsa \
+      ROT_KEY=plat/arm/board/common/rotpk/arm_rotprivk_rsa.pem \
+      BL32=<path to optee binary> \
+      BL33=<path to u-boot binary> \
+      bl2
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
diff --git a/docs/plat/arm/fvp/index.rst b/docs/plat/arm/fvp/index.rst
index 3a13268..2aaf195 100644
--- a/docs/plat/arm/fvp/index.rst
+++ b/docs/plat/arm/fvp/index.rst
@@ -12,46 +12,50 @@
 (64-bit host machine only).
 
 .. note::
-   The FVP models used are Version 11.12 Build 38, unless otherwise stated.
+   The FVP models used are Version 11.16 Build 16, unless otherwise stated.
 
--  ``FVP_Base_AEMvA``
--  ``FVP_Base_AEMv8A-AEMv8A``
+-  ``Foundation_Platform``
 -  ``FVP_Base_AEMv8A-AEMv8A-AEMv8A-AEMv8A-CCN502``
--  ``FVP_Base_RevC-2xAEMv8A``
--  ``FVP_Base_Cortex-A32x4``
+-  ``FVP_Base_AEMv8A-AEMv8A`` (For certain configurations also uses 11.14/21)
+-  ``FVP_Base_AEMv8A-GIC600AE``
+-  ``FVP_Base_AEMvA``         (For certain configurations also uses 0.0/6684)
+-  ``FVP_Base_Cortex-A32x4``  (Version 11.12/38)
 -  ``FVP_Base_Cortex-A35x4``
 -  ``FVP_Base_Cortex-A53x4``
--  ``FVP_Base_Cortex-A55x4+Cortex-A75x4``
 -  ``FVP_Base_Cortex-A55x4``
+-  ``FVP_Base_Cortex-A55x4+Cortex-A75x4``
 -  ``FVP_Base_Cortex-A57x1-A53x1``
 -  ``FVP_Base_Cortex-A57x2-A53x4``
 -  ``FVP_Base_Cortex-A57x4-A53x4``
 -  ``FVP_Base_Cortex-A57x4``
--  ``FVP_Base_Cortex-A65x4``
 -  ``FVP_Base_Cortex-A65AEx8``
+-  ``FVP_Base_Cortex-A65x4``
+-  ``FVP_Base_Cortex-A710x4``
 -  ``FVP_Base_Cortex-A72x4-A53x4``
 -  ``FVP_Base_Cortex-A72x4``
 -  ``FVP_Base_Cortex-A73x4-A53x4``
 -  ``FVP_Base_Cortex-A73x4``
 -  ``FVP_Base_Cortex-A75x4``
--  ``FVP_Base_Cortex-A76x4``
 -  ``FVP_Base_Cortex-A76AEx4``
 -  ``FVP_Base_Cortex-A76AEx8``
+-  ``FVP_Base_Cortex-A76x4``
 -  ``FVP_Base_Cortex-A77x4``
 -  ``FVP_Base_Cortex-A78x4``
 -  ``FVP_Base_Neoverse-E1x1``
 -  ``FVP_Base_Neoverse-E1x2``
 -  ``FVP_Base_Neoverse-E1x4``
 -  ``FVP_Base_Neoverse-N1x4``
+-  ``FVP_Base_Neoverse-N2x4`` (Version 11.12 build 38)
 -  ``FVP_Base_Neoverse-V1x4``
--  ``FVP_CSS_SGI-575``     (Version 11.10 build 36)
--  ``FVP_CSS_SGM-775``
--  ``FVP_RD_E1_edge``      (Version 11.9 build 41)
--  ``FVP_RD_N1_edge``      (Version 11.10 build 36)
--  ``FVP_RD_N1_edge_dual`` (Version 11.10 build 36)
--  ``FVP_RD_Daniel``       (Version 11.10 build 36)
--  ``FVP_TC0``             (Version 0.0 build 6114)
--  ``Foundation_Platform``
+-  ``FVP_Base_RevC-2xAEMvA``  (For certain configurations also uses 0.0/6557)
+-  ``FVP_CSS_SGI-575``        (Version 11.15/26)
+-  ``FVP_Morello``            (Version 0.11/19)
+-  ``FVP_RD_E1_edge``         (Version 11.15/26)
+-  ``FVP_RD_N1_edge_dual``    (Version 11.15/26)
+-  ``FVP_RD_N1_edge``         (Version 11.15/26)
+-  ``FVP_RD_V1``              (Version 11.15/26)
+-  ``FVP_TC0``
+-  ``FVP_TC1``
 
 The latest version of the AArch32 build of TF-A has been tested on the
 following Arm FVPs without shifted affinities, and that do not support threaded
@@ -96,7 +100,7 @@
    the models. The models can be launched with ``-Q 100`` option if they are
    required to match the run time characteristics of the older versions.
 
-All the above platforms have been tested with `Linaro Release 19.06`_.
+All the above platforms have been tested with `Linaro Release 20.01`_.
 
 .. _build_options_arm_fvp_platform:
 
@@ -141,6 +145,11 @@
    HW_CONFIG blob instead of the DTS file. This option is useful to override
    the default HW_CONFIG selected by the build system.
 
+-  ``FVP_GICR_REGION_PROTECTION``: Mark the redistributor pages of
+   inactive/fused CPU cores as read-only. The default value of this option
+   is ``0``, which means the redistributor pages of all CPU cores are marked
+   as read and write.
+
 Booting Firmware Update images
 ------------------------------
 
@@ -516,8 +525,8 @@
 
 Notes:
 
--  If Position Independent Executable (PIE) support is enabled for BL31
-   in this config, it can be loaded at any valid address for execution.
+-  Position Independent Executable (PIE) support is enabled in this
+   config allowing BL31 to be loaded at any valid address for execution.
 
 -  Since a FIP is not loaded when using BL31 as reset entrypoint, the
    ``--data="<path-to><bl31|bl32|bl33-binary>"@<base-address-of-binary>``
@@ -578,8 +587,8 @@
     --data cluster0.cpu0="<path-to>/<ramdisk>"@0x84000000
 
 .. note::
-   The load address of ``<bl32-binary>`` depends on the value ``BL32_BASE``.
-   It should match the address programmed into the RVBAR register as well.
+   Position Independent Executable (PIE) support is enabled in this
+   config allowing SP_MIN to be loaded at any valid address for execution.
 
 Running on the Cortex-A57-A53 Base FVP with reset to BL31 entrypoint
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -634,10 +643,10 @@
 
 --------------
 
-*Copyright (c) 2019-2020, Arm Limited. All rights reserved.*
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
 
 .. _TB_FW_CONFIG for FVP: https://git.trustedfirmware.org/TF-A/trusted-firmware-a.git/tree/plat/arm/board/fvp/fdts/fvp_tb_fw_config.dts
 .. _Arm's website: `FVP models`_
 .. _FVP models: https://developer.arm.com/products/system-design/fixed-virtual-platforms
-.. _Linaro Release 19.06: http://releases.linaro.org/members/arm/platforms/19.06
+.. _Linaro Release 20.01: http://releases.linaro.org/members/arm/platforms/20.01
 .. _Arm FVP website: https://developer.arm.com/products/system-design/fixed-virtual-platforms
diff --git a/docs/plat/arm/fvp_r/index.rst b/docs/plat/arm/fvp_r/index.rst
new file mode 100644
index 0000000..8af16ba
--- /dev/null
+++ b/docs/plat/arm/fvp_r/index.rst
@@ -0,0 +1,46 @@
+ARM V8-R64 Fixed Virtual Platform (FVP)
+=======================================
+
+Some of the features of Armv8-R AArch64 FVP platform referenced in Trusted
+Boot R-class include:
+
+- Secure World Support Only
+- EL2 as Maximum EL support (No EL3)
+- MPU Support only at EL2
+- MPU or MMU Support at EL0/EL1
+- AArch64 Support Only
+- Trusted Board Boot
+
+Further information on v8-R64 FVP is available at `info <https://developer.arm.com/documentation/ddi0600/latest/>`_
+
+Boot Sequence
+-------------
+
+BL1 –> BL33
+
+The execution begins from BL1 which loads the BL33 image, a boot-wrapped (bootloader + Operating System)
+Operating System, from FIP to DRAM.
+
+Build Procedure
+~~~~~~~~~~~~~~~
+
+-  Obtain arm `toolchain <https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-a/downloads>`_.
+   Set the CROSS_COMPILE environment variable to point to the toolchain folder.
+
+-  Build TF-A:
+
+   .. code:: shell
+
+      make PLAT=fvp_r BL33=<path_to_os.bin> all fip
+
+   Enable TBBR by adding the following options to the make command:
+
+   .. code:: shell
+
+      MBEDTLS_DIR=<path_to_mbedtls_directory>  \
+      TRUSTED_BOARD_BOOT=1 \
+      GENERATE_COT=1 \
+      ARM_ROTPK_LOCATION=devel_rsa  \
+      ROT_KEY=plat/arm/board/common/rotpk/arm_rotprivk_rsa.pem
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
diff --git a/docs/plat/arm/index.rst b/docs/plat/arm/index.rst
index f72992b..f262dc0 100644
--- a/docs/plat/arm/index.rst
+++ b/docs/plat/arm/index.rst
@@ -7,11 +7,13 @@
 
    juno/index
    fvp/index
+   fvp_r/index
    fvp-ve/index
-   tc0/index
+   tc/index
    arm_fpga/index
    arm-build-options
    morello/index
+   diphda/index
 
 This chapter holds documentation related to Arm's development platforms,
 including both software models (FVPs) and hardware development boards
@@ -19,4 +21,4 @@
 
 --------------
 
-*Copyright (c) 2019, Arm Limited. All rights reserved.*
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
diff --git a/docs/plat/arm/juno/index.rst b/docs/plat/arm/juno/index.rst
index cf328fa..8b9d453 100644
--- a/docs/plat/arm/juno/index.rst
+++ b/docs/plat/arm/juno/index.rst
@@ -12,24 +12,21 @@
 
 This version of TF-A has been tested on variants r0, r1 and r2 of Juno.
 
-To execute the software stack on Juno, the version of the Juno board recovery
-image indicated in the `Linaro Release Notes`_ must be installed. If you have an
-earlier version installed or are unsure which version is installed, please
-re-install the recovery image by following the
-`Instructions for using Linaro's deliverables on Juno`_.
+To run TF-A on Juno, you need to first prepare an SD card with Juno software
+stack that includes TF-A. This version of TF-A is tested with pre-built
+`Linaro release software stack`_ version 20.01. You can alternatively
+build the software stack yourself by following the
+`Juno platform software user guide`_. Once you prepare the software stack
+on an SD card, you can replace the ``bl1.bin`` and ``fip.bin``
+binaries in the ``SOFTWARE/`` directory with custom built TF-A binaries.
 
 Preparing TF-A images
 ---------------------
 
-After building TF-A, the files ``bl1.bin`` and ``fip.bin`` need copying to the
-``SOFTWARE/`` directory of the Juno SD card.
-
-Creating a Firmware Image Package (FIP)
----------------------------------------
-
 This section provides Juno and FVP specific instructions to build Trusted
 Firmware, obtain the additional required firmware, and pack it all together in
-a single FIP binary. It assumes that a Linaro release has been installed.
+a single FIP binary. It assumes that a Linaro release software stack has been
+installed.
 
 .. note::
    Pre-built binaries for AArch32 are available from Linaro Release 16.12
@@ -57,9 +54,16 @@
 
        make realclean
 
-#. Obtain SCP_BL2 (Juno) and BL33 (all platforms)
+#. Obtain SCP binaries (Juno)
 
-   Use the fiptool to extract the SCP_BL2 and BL33 images from the FIP
+   This version of TF-A is tested with SCP version 2.8.0 on Juno. You can
+   download pre-built SCP binaries (``scp_bl1.bin`` and ``scp_bl2.bin``)
+   from `TF-A downloads page`_. Alternatively, you can `build
+   the binaries from source`_.
+
+#. Obtain BL33 (all platforms)
+
+   Use the fiptool to extract the BL33 image from the FIP
    package included in the Linaro release:
 
    .. code:: shell
@@ -71,8 +75,7 @@
        ./tools/fiptool/fiptool unpack <path-to-linaro-release>/[SOFTWARE]/fip.bin
 
    The unpack operation will result in a set of binary images extracted to the
-   current working directory. The SCP_BL2 image corresponds to
-   ``scp-fw.bin`` and BL33 corresponds to ``nt-fw.bin``.
+   current working directory. BL33 corresponds to ``nt-fw.bin``.
 
    .. note::
       The fiptool will complain if the images to be unpacked already
@@ -102,7 +105,7 @@
 
    .. code:: shell
 
-       make PLAT=juno BL33=nt-fw.bin SCP_BL2=scp-fw.bin all fip
+       make PLAT=juno BL33=nt-fw.bin SCP_BL2=scp_bl2.bin all fip
 
    For AArch32:
 
@@ -144,7 +147,7 @@
       .. code:: shell
 
           make ARCH=aarch64 PLAT=juno JUNO_AARCH32_EL3_RUNTIME=1 \
-          BL33=nt-fw.bin SCP_BL2=scp-fw.bin \
+          BL33=nt-fw.bin SCP_BL2=scp_bl2.bin \
           BL32=<path-to-temporary>/bl32.bin all fip
 
 The resulting BL1 and FIP images may be found in:
@@ -159,6 +162,8 @@
     ./build/fvp/release/bl1.bin
     ./build/fvp/release/fip.bin
 
+After building TF-A, the files ``bl1.bin``, ``fip.bin`` and ``scp_bl1.bin``
+need to be copied to the ``SOFTWARE/`` directory on the Juno SD card.
 
 Booting Firmware Update images
 ------------------------------
@@ -236,10 +241,12 @@
 
 --------------
 
-*Copyright (c) 2019, Arm Limited. All rights reserved.*
+*Copyright (c) 2019-2021, Arm Limited. All rights reserved.*
 
-.. _Linaro Release Notes: https://community.arm.com/dev-platforms/w/docs/226/old-release-notes
-.. _Instructions for using Linaro's deliverables on Juno: https://community.arm.com/dev-platforms/w/docs/303/juno
+.. _Linaro release software stack: http://releases.linaro.org/members/arm/platforms/
+.. _Juno platform software user guide: https://git.linaro.org/landing-teams/working/arm/arm-reference-platforms.git/about/docs/juno/user-guide.rst
+.. _TF-A downloads page: https://downloads.trustedfirmware.org/tf-a/css_scp_2.8.0/juno/
+.. _build the binaries from source: https://github.com/ARM-software/SCP-firmware/blob/master/user_guide.md#scp-firmware-user-guide
 .. _Arm Platforms Portal: https://community.arm.com/dev-platforms/
 .. _Juno Getting Started Guide: http://infocenter.arm.com/help/topic/com.arm.doc.dui0928e/DUI0928E_juno_arm_development_platform_gsg.pdf
 .. _PSCI: http://infocenter.arm.com/help/topic/com.arm.doc.den0022d/Power_State_Coordination_Interface_PDD_v1_1_DEN0022D.pdf
diff --git a/docs/plat/arm/tc/index.rst b/docs/plat/arm/tc/index.rst
new file mode 100644
index 0000000..20d3e56
--- /dev/null
+++ b/docs/plat/arm/tc/index.rst
@@ -0,0 +1,56 @@
+TC Total Compute Platform
+==========================
+
+Some of the features of TC platform referenced in TF-A include:
+
+- A `System Control Processor <https://github.com/ARM-software/SCP-firmware>`_
+  to abstract power and system management tasks away from application
+  processors. The RAM firmware for SCP is included in the TF-A FIP and is
+  loaded by AP BL2 from FIP in flash to SRAM for copying by SCP (SCP has access
+  to AP SRAM).
+- GICv4
+- Trusted Board Boot
+- SCMI
+- MHUv2
+
+Currently, the main difference between TC0 (TARGET_PLATFORM=0) and TC1
+(TARGET_PLATFORM=1) platforms w.r.t to TF-A is the CPUs supported. TC0 has
+support for Cortex A510, Cortex A710 and Cortex X2, while TC1 has support for
+Cortex A510, Cortex Makalu and Cortex Makalu ELP Arm CPUs.
+
+
+Boot Sequence
+-------------
+
+The execution begins from SCP_BL1. SCP_BL1 powers up the AP which starts
+executing AP_BL1 and then executes AP_BL2 which loads the SCP_BL2 from
+FIP to SRAM. The SCP has access to AP SRAM. The address and size of SCP_BL2
+is communicated to SCP using SDS. SCP copies SCP_BL2 from SRAM to its own
+RAM and starts executing it. The AP then continues executing the rest of TF-A
+stages including BL31 runtime stage and hands off executing to
+Non-secure world (u-boot).
+
+Build Procedure (TF-A only)
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+-  Obtain arm `toolchain <https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-a/downloads>`_.
+   Set the CROSS_COMPILE environment variable to point to the toolchain folder.
+
+-  Build TF-A:
+
+   .. code:: shell
+
+      make PLAT=tc BL33=<path_to_uboot.bin> \
+      SCP_BL2=<path_to_scp_ramfw.bin> TARGET_PLATFORM={0,1} all fip
+
+   Enable TBBR by adding the following options to the make command:
+
+   .. code:: shell
+
+      MBEDTLS_DIR=<path_to_mbedtls_directory>  \
+      TRUSTED_BOARD_BOOT=1 \
+      GENERATE_COT=1 \
+      ARM_ROTPK_LOCATION=devel_rsa  \
+      ROT_KEY=plat/arm/board/common/rotpk/arm_rotprivk_rsa.pem
+
+*Copyright (c) 2020-2021, Arm Limited. All rights reserved.*
diff --git a/docs/plat/arm/tc0/index.rst b/docs/plat/arm/tc0/index.rst
deleted file mode 100644
index 34d1f13..0000000
--- a/docs/plat/arm/tc0/index.rst
+++ /dev/null
@@ -1,50 +0,0 @@
-TC0 Total Compute Platform
-==========================
-
-Some of the features of TC0 platform referenced in TF-A include:
-
-- A `System Control Processor <https://github.com/ARM-software/SCP-firmware>`_
-  to abstract power and system management tasks away from application
-  processors. The RAM firmware for SCP is included in the TF-A FIP and is
-  loaded by AP BL2 from FIP in flash to SRAM for copying by SCP (SCP has access
-  to AP SRAM).
-- GICv4
-- Trusted Board Boot
-- SCMI
-- MHUv2
-
-Boot Sequence
--------------
-
-The execution begins from SCP_BL1. SCP_BL1 powers up the AP which starts
-executing AP_BL1 and then executes AP_BL2 which loads the SCP_BL2 from
-FIP to SRAM. The SCP has access to AP SRAM. The address and size of SCP_BL2
-is communicated to SCP using SDS. SCP copies SCP_BL2 from SRAM to its own
-RAM and starts executing it. The AP then continues executing the rest of TF-A
-stages including BL31 runtime stage and hands off executing to
-Non-secure world (u-boot).
-
-Build Procedure (TF-A only)
-~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
--  Obtain arm `toolchain <https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-a/downloads>`_.
-   Set the CROSS_COMPILE environment variable to point to the toolchain folder.
-
--  Build TF-A:
-
-   .. code:: shell
-
-      make PLAT=tc0 BL33=<path_to_uboot.bin> \
-      SCP_BL2=<path_to_scp_ramfw.bin>  all fip
-
-   Enable TBBR by adding the following options to the make command:
-
-   .. code:: shell
-
-      MBEDTLS_DIR=<path_to_mbedtls_directory>  \
-      TRUSTED_BOARD_BOOT=1 \
-      GENERATE_COT=1 \
-      ARM_ROTPK_LOCATION=devel_rsa  \
-      ROT_KEY=plat/arm/board/common/rotpk/arm_rotprivk_rsa.pem
-
-*Copyright (c) 2020, Arm Limited. All rights reserved.*
diff --git a/docs/plat/deprecated.rst b/docs/plat/deprecated.rst
new file mode 100644
index 0000000..7cc4258
--- /dev/null
+++ b/docs/plat/deprecated.rst
@@ -0,0 +1,20 @@
+Deprecated platforms
+====================
+
+Process of deprecating a platform
+---------------------------------
+
+Platform can be deprecated and its source can be kept in repository for a cooling
+off period before deleting it or it can be deleted straight away. For later types
+Deprecated/Deleted version would be same.
+
+List of deprecated platforms
+----------------------------
+
++----------------+----------------+--------------------+--------------------+
+|    Platform    |     Vendor     | Deprecated version |  Deleted version   |
++================+================+====================+====================+
+|    sgm775      |      Arm       |        2.5         |       2.7          |
++----------------+----------------+--------------------+--------------------+
+|    mt6795      |      MTK       |        2.5         |       2.7          |
++----------------+----------------+--------------------+--------------------+
diff --git a/docs/plat/imx8m.rst b/docs/plat/imx8m.rst
index f184b69..0fe15c9 100644
--- a/docs/plat/imx8m.rst
+++ b/docs/plat/imx8m.rst
@@ -6,6 +6,9 @@
 reliability and embedded security needed to drive the growth of fast-growing
 edge node computing, streaming multimedia, and machine learning applications.
 
+imx8mq is dropped in TF-A CI build due to the small OCRAM size, but still actively
+maintained in NXP official release.
+
 Boot Sequence
 -------------
 
@@ -43,3 +46,17 @@
 used to generate flash.bin, and flash.bin needs to be flashed into SD card
 with certain offset for BOOT ROM. the u-boot and imx-mkimage will be upstreamed
 soon, this doc will be updated once they are ready, and the link will be posted.
+
+TBBR Boot Sequence
+------------------
+
+When setting NEED_BL2=1 on imx8mm. We support an alternative way of
+boot sequence to support TBBR.
+
+Bootrom --> SPL --> BL2 --> BL31 --> BL33(u-boot with UEFI) --> grub
+
+This helps us to fulfill the SystemReady EBBR standard.
+BL2 will be in the FIT image and SPL will verify it.
+All of the BL3x will be put in the FIP image. BL2 will verify them.
+In U-boot we turn on the UEFI secure boot features so it can verify
+grub. And we use grub to verify linux kernel.
diff --git a/docs/plat/index.rst b/docs/plat/index.rst
index fb60e56..5848005 100644
--- a/docs/plat/index.rst
+++ b/docs/plat/index.rst
@@ -9,6 +9,7 @@
 
    allwinner
    arm/index
+   deprecated
    meson-axg
    meson-gxbb
    meson-gxl
@@ -20,11 +21,13 @@
    marvell/index
    mt8183
    mt8192
+   mt8195
    nvidia-tegra
    warp7
    imx8
    imx8m
    ls1043a
+   nxp/index
    poplar
    qemu
    qemu-sbsa
@@ -32,6 +35,7 @@
    rpi3
    rpi4
    rcar-gen3
+   rz-g2
    rockchip
    socionext-uniphier
    synquacer
diff --git a/docs/plat/marvell/armada/build.rst b/docs/plat/marvell/armada/build.rst
index e21fb3c..6872f56 100644
--- a/docs/plat/marvell/armada/build.rst
+++ b/docs/plat/marvell/armada/build.rst
@@ -26,7 +26,7 @@
 
        *u-boot.bin* should be used and not *u-boot-spl.bin*
 
-Set MSS/SCP image path (mandatory only for A7K/8K/CN913x)
+Set MSS/SCP image path (mandatory only for A7K/8K/CN913x when MSS_SUPPORT=1)
 
     .. code:: shell
 
@@ -51,6 +51,20 @@
 
 There are several build options:
 
+- PLAT
+
+        Supported Marvell platforms are:
+
+            - a3700        - A3720 DB, EspressoBin and Turris MOX
+            - a70x0
+            - a70x0_amc    - AMC board
+            - a70x0_mochabin - Globalscale MOCHAbin
+            - a80x0
+            - a80x0_mcbin  - MacchiatoBin
+            - a80x0_puzzle - IEI Puzzle-M801
+            - t9130        - CN913x
+            - t9130_cex7_eval - CN913x CEx7 Evaluation Board
+
 - DEBUG
 
         Default is without debug information (=0). in order to enable it use ``DEBUG=1``.
@@ -61,17 +75,17 @@
 
         Defines the level of logging which will be purged to the default output port.
 
-        LOG_LEVEL_NONE		0
-        LOG_LEVEL_ERROR		10
-        LOG_LEVEL_NOTICE	20
-        LOG_LEVEL_WARNING	30
-        LOG_LEVEL_INFO		40
-        LOG_LEVEL_VERBOSE	50
+            -  0 - LOG_LEVEL_NONE
+            - 10 - LOG_LEVEL_ERROR
+            - 20 - LOG_LEVEL_NOTICE (default for DEBUG=0)
+            - 30 - LOG_LEVEL_WARNING
+            - 40 - LOG_LEVEL_INFO (default for DEBUG=1)
+            - 50 - LOG_LEVEL_VERBOSE
 
 - USE_COHERENT_MEM
 
         This flag determines whether to include the coherent memory region in the
-        BL memory map or not.
+        BL memory map or not. Enabled by default.
 
 - LLC_ENABLE
 
@@ -89,25 +103,23 @@
 - MARVELL_SECURE_BOOT
 
         Build trusted(=1)/non trusted(=0) image, default is non trusted.
-
-- BLE_PATH
-
-        Points to BLE (Binary ROM extension) sources folder.
-        Only required for A7K/8K/CN913x builds.
-        The parameter is optional, its default value is ``plat/marvell/armada/a8k/common/ble``.
+        This parameter is used only for ``mrvl_flash`` and ``mrvl_uart`` targets.
 
 - MV_DDR_PATH
 
-        For A7K/8K/CN913x, use this parameter to point to mv_ddr driver sources to allow BLE build. For A37x0,
-        it is used for ddr_tool build.
+        This parameter is required for ``mrvl_flash`` and ``mrvl_uart`` targets.
+        For A7K/8K/CN913x it is used for BLE build and for Armada37x0 it used
+        for ddr_tool build.
 
-        Usage example: MV_DDR_PATH=path/to/mv_ddr
+        Specify path to the full checkout of Marvell mv-ddr-marvell git
+        repository. Checkout must contain also .git subdirectory because
+        mv-ddr build process calls git commands.
 
-        The parameter is optional for A7K/8K/CN913x, when this parameter is not set, the mv_ddr
-        sources are expected to be located at: drivers/marvell/mv_ddr. However, the parameter
-        is necessary for A37x0.
+        Do not remove any parts of git checkout becuase build process and other
+        applications need them for correct building and version determination.
 
-        For the mv_ddr source location, check the section "Tools and external components installation"
+
+CN913x specific build options:
 
 - CP_NUM
 
@@ -117,34 +129,121 @@
         family (PLAT=t9130), which can have external CPs connected to the MCI ports. Valid
         values with CP_NUM are in a range of 1 to 3.
 
+
+A7K/8K/CN913x specific build options:
+
+- BLE_PATH
+
+        Points to BLE (Binary ROM extension) sources folder.
+        The parameter is optional, its default value is ``plat/marvell/armada/a8k/common/ble``
+        which uses TF-A in-tree BLE implementation.
+
+- MSS_SUPPORT
+
+        When ``MSS_SUPPORT=1``, then TF-A includes support for Management SubSystem (MSS).
+        When enabled it is required to specify path to the MSS firmware image via ``SCP_BL2``
+        option.
+
+        This option is by default enabled.
+
+- SCP_BL2
+
+        Specify path to the MSS fimware image binary which will run on Cortex-M3 coprocessor.
+        It is available in Marvell binaries-marvell git repository. Required when ``MSS_SUPPORT=1``.
+
+Globalscale MOCHAbin specific build options:
+
 - DDR_TOPOLOGY
 
-        For Armada37x0 only, the DDR topology map index/name, default is 0.
+        The DDR topology map index/name, default is 0.
 
         Supported Options:
-            - DDR3 1CS (0): DB-88F3720-DDR3-Modular (512MB); EspressoBIN (512MB)
-            - DDR4 1CS (1): DB-88F3720-DDR4-Modular (512MB)
-            - DDR3 2CS (2): EspressoBIN V3-V5 (1GB 2CS)
-            - DDR4 2CS (3): DB-88F3720-DDR4-Modular (4GB)
-            - DDR3 1CS (4): DB-88F3720-DDR3-Modular (1GB); EspressoBIN V3-V5 (1GB 1CS)
-            - DDR4 1CS (5): EspressoBin V7 (1GB)
-            - DDR4 2CS (6): EspressoBin V7 (2GB)
-            - DDR3 2CS (7): EspressoBin V3-V5 (2GB)
-            - CUSTOMER (CUST): Customer board, DDR3 1CS 512MB
+            -    0 - DDR4 1CS 2GB
+            -    1 - DDR4 1CS 4GB
+            -    2 - DDR4 2CS 8GB
+
+Armada37x0 specific build options:
+
+- HANDLE_EA_EL3_FIRST
+
+        When ``HANDLE_EA_EL3_FIRST=1``, External Aborts and SError Interrupts will be always trapped
+        in TF-A. TF-A in this case enables dirty hack / workaround for a bug found in U-Boot and
+        Linux kernel PCIe controller driver pci-aardvark.c, traps and then masks SError interrupt
+        caused by AXI SLVERR on external access (syndrome 0xbf000002).
+
+        Otherwise when ``HANDLE_EA_EL3_FIRST=0``, these exceptions will be trapped in the current
+        exception level (or in EL1 if the current exception level is EL0). So exceptions caused by
+        U-Boot will be trapped in U-Boot, exceptions caused by Linux kernel (or user applications)
+        will be trapped in Linux kernel.
+
+        Mentioned bug in pci-aardvark.c driver is fixed in U-Boot version v2021.07 and Linux kernel
+        version v5.13 (workarounded since Linux kernel version 5.9) and also backported in Linux
+        kernel stable releases since versions v5.12.13, v5.10.46, v5.4.128, v4.19.198, v4.14.240.
+
+        If target system has already patched version of U-Boot and Linux kernel then it is strongly
+        recommended to not enable this workaround as it disallows propagating of all External Aborts
+        to running Linux kernel and makes correctable errors as fatal aborts.
+
+        This option is now disabled by default. In past this option was enabled by default in
+        TF-A versions v2.2, v2.3, v2.4 and v2.5.
+
+- CM3_SYSTEM_RESET
+
+        When ``CM3_SYSTEM_RESET=1``, the Cortex-M3 secure coprocessor will be used for system reset.
+
+        TF-A will send command 0x0009 with a magic value via the rWTM mailbox interface to the
+        Cortex-M3 secure coprocessor.
+        The firmware running in the coprocessor must either implement this functionality or
+        ignore the 0x0009 command (which is true for the firmware from A3700-utils-marvell
+        repository). If this option is enabled but the firmware does not support this command,
+        an error message will be printed prior trying to reboot via the usual way.
+
+        This option is needed on Turris MOX as a workaround to a HW bug which causes reset to
+        sometime hang the board.
+
+- A3720_DB_PM_WAKEUP_SRC
+
+        For Armada 3720 Development Board only, when ``A3720_DB_PM_WAKEUP_SRC=1``,
+        TF-A will setup PM wake up src configuration. This option is disabled by default.
+
+
+Armada37x0 specific build options for ``mrvl_flash`` and ``mrvl_uart`` targets:
+
+- DDR_TOPOLOGY
+
+        The DDR topology map index/name, default is 0.
+
+        Supported Options:
+            -    0 - DDR3 1CS 512MB (DB-88F3720-DDR3-Modular, EspressoBin V3-V5)
+            -    1 - DDR4 1CS 512MB (DB-88F3720-DDR4-Modular)
+            -    2 - DDR3 2CS   1GB (EspressoBin V3-V5)
+            -    3 - DDR4 2CS   4GB (DB-88F3720-DDR4-Modular)
+            -    4 - DDR3 1CS   1GB (DB-88F3720-DDR3-Modular, EspressoBin V3-V5)
+            -    5 - DDR4 1CS   1GB (EspressoBin V7, EspressoBin-Ultra)
+            -    6 - DDR4 2CS   2GB (EspressoBin V7)
+            -    7 - DDR3 2CS   2GB (EspressoBin V3-V5)
+            - CUST - CUSTOMER BOARD (Customer board settings)
 
 - CLOCKSPRESET
 
-        For Armada37x0 only, the clock tree configuration preset including CPU and DDR frequency,
+        The clock tree configuration preset including CPU and DDR frequency,
         default is CPU_800_DDR_800.
 
-            - CPU_600_DDR_600	-	CPU at 600 MHz, DDR at 600 MHz
-            - CPU_800_DDR_800	-	CPU at 800 MHz, DDR at 800 MHz
-            - CPU_1000_DDR_800	-	CPU at 1000 MHz, DDR at 800 MHz
-            - CPU_1200_DDR_750	-	CPU at 1200 MHz, DDR at 750 MHz
+            - CPU_600_DDR_600  - CPU at 600 MHz, DDR at 600 MHz
+            - CPU_800_DDR_800  - CPU at 800 MHz, DDR at 800 MHz
+            - CPU_1000_DDR_800 - CPU at 1000 MHz, DDR at 800 MHz
+            - CPU_1200_DDR_750 - CPU at 1200 MHz, DDR at 750 MHz
+
+        Look at Armada37x0 chip package marking on board to identify correct CPU frequency.
+        The last line on package marking (next line after the 88F37x0 line) should contain:
+
+            - C080 or I080 - chip with  800 MHz CPU - use ``CLOCKSPRESET=CPU_800_DDR_800``
+            - C100 or I100 - chip with 1000 MHz CPU - use ``CLOCKSPRESET=CPU_1000_DDR_800``
+            - C120         - chip with 1200 MHz CPU - use ``CLOCKSPRESET=CPU_1200_DDR_750``
 
 - BOOTDEV
 
-        For Armada37x0 only, the flash boot device, default is ``SPINOR``.
+        The flash boot device, default is ``SPINOR``.
 
         Currently, Armada37x0 only supports ``SPINOR``, ``SPINAND``, ``EMMCNORM`` and ``SATA``:
 
@@ -157,9 +256,13 @@
 
             - SATA - SATA device boot
 
+                Image needs to be stored at disk LBA 0 or at disk partition with
+                MBR type 0x4d (ASCII 'M' as in Marvell) or at disk partition with
+                GPT name ``MARVELL BOOT PARTITION``.
+
 - PARTNUM
 
-        For Armada37x0 only, the boot partition number, default is 0.
+        The boot partition number, default is 0.
 
         To boot from eMMC, the value should be aligned with the parameter in
         U-Boot with name of ``CONFIG_SYS_MMC_ENV_PART``, whose value by default is
@@ -168,41 +271,106 @@
 
 - WTMI_IMG
 
-        For Armada37x0 only, the path of the WTMI image can point to an image which
+        The path of the binary can point to an image which
         does nothing, an image which supports EFUSE or a customized CM3 firmware
-        binary. The default image is wtmi.bin that built from sources in WTP
+        binary. The default image is ``fuse.bin`` that built from sources in WTP
         folder, which is the next option. If the default image is OK, then this
         option should be skipped.
 
+        Please note that this is not a full WTMI image, just a main loop without
+        hardware initialization code. Final WTMI image is built from this WTMI_IMG
+        binary and sys-init code from the WTP directory which sets DDR and CPU
+        clocks according to DDR_TOPOLOGY and CLOCKSPRESET options.
+
+        CZ.NIC as part of Turris project released free and open source WTMI
+        application firmware ``wtmi_app.bin`` for all Armada 3720 devices.
+        This firmware includes additional features like access to Hardware
+        Random Number Generator of Armada 3720 SoC which original Marvell's
+        ``fuse.bin`` image does not have.
+
+        CZ.NIC's Armada 3720 Secure Firmware is available at website:
+
+            https://gitlab.nic.cz/turris/mox-boot-builder/
+
 - WTP
 
-    For Armada37x0 only, use this parameter to point to wtptools source code
-    directory, which can be found as a3700_utils.zip in the release. Usage
-    example: ``WTP=/path/to/a3700_utils``
+        Specify path to the full checkout of Marvell A3700-utils-marvell git
+        repository. Checkout must contain also .git subdirectory because WTP
+        build process calls git commands.
 
-    For example, in order to build the image in debug mode with log level up to 'notice' level run
+        WTP build process uses also Marvell mv-ddr-marvell git repository
+        specified in MV_DDR_PATH option.
 
-    .. code:: shell
+        Do not remove any parts of git checkout becuase build process and other
+        applications need them for correct building and version determination.
 
-        > make DEBUG=1 USE_COHERENT_MEM=0 LOG_LEVEL=20 PLAT=<MARVELL_PLATFORM> all fip
+- CRYPTOPP_PATH
 
-    And if we want to build a Armada37x0 image in debug mode with log level up to 'notice' level,
-    the image has the preset CPU at 1000 MHz, preset DDR3 at 800 MHz, the DDR topology of DDR4 2CS,
-    the image boot from SPI NOR flash partition 0, and the image is non trusted in WTP, the command
-    line is as following
+        Use this parameter to point to Crypto++ source code
+        directory. If this option is specified then Crypto++ source code in
+        CRYPTOPP_PATH directory will be automatically compiled. Crypto++ library
+        is required for building WTP image tool. Either CRYPTOPP_PATH or
+        CRYPTOPP_LIBDIR with CRYPTOPP_INCDIR needs to be specified for Armada37x0.
 
-    .. code:: shell
+- CRYPTOPP_LIBDIR
 
-        > make DEBUG=1 USE_COHERENT_MEM=0 LOG_LEVEL=20 CLOCKSPRESET=CPU_1000_DDR_800 \
-            MARVELL_SECURE_BOOT=0 DDR_TOPOLOGY=3 BOOTDEV=SPINOR PARTNUM=0 PLAT=a3700 all fip
+        Use this parameter to point to the directory with
+        compiled Crypto++ library. By default it points to the CRYPTOPP_PATH.
 
-    Supported MARVELL_PLATFORM are:
-        - a3700 (for both A3720 DB and EspressoBin)
-        - a70x0
-        - a70x0_amc (for AMC board)
-        - a80x0
-        - a80x0_mcbin (for MacchiatoBin)
-        - t9130 (OcteonTX2 CN913x)
+- CRYPTOPP_INCDIR
+
+        Use this parameter to point to the directory with
+        header files of Crypto++ library. By default it points to the CRYPTOPP_PATH.
+
+
+For example, in order to build the image in debug mode with log level up to 'notice' level run
+
+.. code:: shell
+
+    > make DEBUG=1 USE_COHERENT_MEM=0 LOG_LEVEL=20 PLAT=<MARVELL_PLATFORM> mrvl_flash
+
+And if we want to build a Armada37x0 image in debug mode with log level up to 'notice' level,
+the image has the preset CPU at 1000 MHz, preset DDR3 at 800 MHz, the DDR topology of DDR4 2CS,
+the image boot from SPI NOR flash partition 0, and the image is non trusted in WTP, the command
+line is as following
+
+.. code:: shell
+
+    > make DEBUG=1 USE_COHERENT_MEM=0 LOG_LEVEL=20 CLOCKSPRESET=CPU_1000_DDR_800 \
+        MARVELL_SECURE_BOOT=0 DDR_TOPOLOGY=3 BOOTDEV=SPINOR PARTNUM=0 PLAT=a3700 \
+        MV_DDR_PATH=/path/to/mv-ddr-marvell/ WTP=/path/to/A3700-utils-marvell/ \
+        CRYPTOPP_PATH=/path/to/cryptopp/ BL33=/path/to/u-boot.bin \
+        all fip mrvl_bootimage mrvl_flash mrvl_uart
+
+To build just TF-A without WTMI image (useful for A3720 Turris MOX board), run following command:
+
+.. code:: shell
+
+    > make USE_COHERENT_MEM=0 PLAT=a3700 CM3_SYSTEM_RESET=1 BL33=/path/to/u-boot.bin \
+        CROSS_COMPILE=aarch64-linux-gnu- mrvl_bootimage
+
+Here is full example how to build production release of Marvell firmware image (concatenated
+binary of Marvell's A3720 sys-init, CZ.NIC's Armada 3720 Secure Firmware, TF-A and U-Boot) for
+EspressoBin board (PLAT=a3700) with 1GHz CPU (CLOCKSPRESET=CPU_1000_DDR_800) and
+1GB DDR4 RAM (DDR_TOPOLOGY=5):
+
+.. code:: shell
+
+    > git clone https://git.trustedfirmware.org/TF-A/trusted-firmware-a.git
+    > git clone https://source.denx.de/u-boot/u-boot.git
+    > git clone https://github.com/weidai11/cryptopp.git
+    > git clone https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell.git
+    > git clone https://github.com/MarvellEmbeddedProcessors/A3700-utils-marvell.git
+    > git clone https://gitlab.nic.cz/turris/mox-boot-builder.git
+    > make -C u-boot CROSS_COMPILE=aarch64-linux-gnu- mvebu_espressobin-88f3720_defconfig u-boot.bin
+    > make -C mox-boot-builder CROSS_CM3=arm-linux-gnueabi- wtmi_app.bin
+    > make -C trusted-firmware-a CROSS_COMPILE=aarch64-linux-gnu- CROSS_CM3=arm-linux-gnueabi- \
+        USE_COHERENT_MEM=0 PLAT=a3700 CLOCKSPRESET=CPU_1000_DDR_800 DDR_TOPOLOGY=5 \
+        MV_DDR_PATH=$PWD/mv-ddr-marvell/ WTP=$PWD/A3700-utils-marvell/ \
+        CRYPTOPP_PATH=$PWD/cryptopp/ BL33=$PWD/u-boot/u-boot.bin \
+        WTMI_IMG=$PWD/mox-boot-builder/wtmi_app.bin FIP_ALIGN=0x100 mrvl_flash
+
+Produced Marvell firmware flash image: ``trusted-firmware-a/build/a3700/release/flash-image.bin``
 
 Special Build Flags
 --------------------
@@ -224,23 +392,31 @@
 
 Build output
 ------------
-Marvell's TF-A compilation generates 7 files:
+Marvell's TF-A compilation generates 8 files:
 
-    - ble.bin		- BLe image
+    - ble.bin		- BLe image (not available for Armada37x0)
     - bl1.bin		- BL1 image
     - bl2.bin		- BL2 image
     - bl31.bin		- BL31 image
     - fip.bin		- FIP image (contains BL2, BL31 & BL33 (U-Boot) images)
     - boot-image.bin	- TF-A image (contains BL1 and FIP images)
-    - flash-image.bin	- Image which contains boot-image.bin and SPL image.
-      Should be placed on the boot flash/device.
+    - flash-image.bin	- Flashable Marvell firmware image. For Armada37x0 it
+      contains TIM, WTMI and boot-image.bin images. For other platforms it contains
+      BLe and boot-image.bin images. Should be placed on the boot flash/device.
+    - uart-images.tgz.bin - GZIPed TAR archive which contains Armada37x0 images
+      for booting via UART. Could be loaded via Marvell's WtpDownload tool from
+      A3700-utils-marvell repository.
+
+Additional make target ``mrvl_bootimage`` produce ``boot-image.bin`` file. Target
+``mrvl_flash`` produce final ``flash-image.bin`` file and target ``mrvl_uart``
+produce ``uart-images.tgz.bin`` file.
 
 
 Tools and external components installation
 ------------------------------------------
 
-Armada37x0 Builds require installation of 3 components
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Armada37x0 Builds require installation of additional components
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 (1) ARM cross compiler capable of building images for the service CPU (CM3).
     This component is usually included in the Linux host packages.
@@ -260,19 +436,32 @@
         > export CROSS_CM3=/opt/arm-cross/bin/arm-linux-gnueabi
 
 (2) DDR initialization library sources (mv_ddr) available at the following repository
-    (use the "mv-ddr-devel" branch):
+    (use the "master" branch):
 
     https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell.git
 
 (3) Armada3700 tools available at the following repository
-    (use the "A3700_utils-armada-18.12-fixed" branch):
+    (use the "master" branch):
 
     https://github.com/MarvellEmbeddedProcessors/A3700-utils-marvell.git
 
-Armada70x0 and Armada80x0 Builds require installation of an additional component
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+(4) Crypto++ library available at the following repository:
+
+    https://github.com/weidai11/cryptopp.git
+
+(5) Optional CZ.NIC's Armada 3720 Secure Firmware:
+
+    https://gitlab.nic.cz/turris/mox-boot-builder.git
+
+Armada70x0, Armada80x0 and CN913x Builds require installation of additional components
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 (1) DDR initialization library sources (mv_ddr) available at the following repository
-    (use the "mv-ddr-devel" branch):
+    (use the "master" branch):
 
     https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell.git
+
+(2) MSS Management SubSystem Firmware available at the following repository
+    (use the "binaries-marvell-armada-SDK10.0.1.0" branch):
+
+    https://github.com/MarvellEmbeddedProcessors/binaries-marvell.git
diff --git a/docs/plat/marvell/armada/misc/mvebu-ccu.rst b/docs/plat/marvell/armada/misc/mvebu-ccu.rst
index 5bac11f..12118e9 100644
--- a/docs/plat/marvell/armada/misc/mvebu-ccu.rst
+++ b/docs/plat/marvell/armada/misc/mvebu-ccu.rst
@@ -1,7 +1,7 @@
 Marvell CCU address decoding bindings
 =====================================
 
-CCU configration driver (1st stage address translation) for Marvell Armada 8K and 8K+ SoCs.
+CCU configuration driver (1st stage address translation) for Marvell Armada 8K and 8K+ SoCs.
 
 The CCU node includes a description of the address decoding configuration.
 
diff --git a/docs/plat/marvell/armada/misc/mvebu-io-win.rst b/docs/plat/marvell/armada/misc/mvebu-io-win.rst
index 52845ca..7498291 100644
--- a/docs/plat/marvell/armada/misc/mvebu-io-win.rst
+++ b/docs/plat/marvell/armada/misc/mvebu-io-win.rst
@@ -1,7 +1,7 @@
 Marvell IO WIN address decoding bindings
 ========================================
 
-IO Window configration driver (2nd stage address translation) for Marvell Armada 8K and 8K+ SoCs.
+IO Window configuration driver (2nd stage address translation) for Marvell Armada 8K and 8K+ SoCs.
 
 The IO WIN includes a description of the address decoding configuration.
 
diff --git a/docs/plat/marvell/armada/misc/mvebu-iob.rst b/docs/plat/marvell/armada/misc/mvebu-iob.rst
index d02a7e8..aa41822 100644
--- a/docs/plat/marvell/armada/misc/mvebu-iob.rst
+++ b/docs/plat/marvell/armada/misc/mvebu-iob.rst
@@ -1,7 +1,7 @@
 Marvell IOB address decoding bindings
 =====================================
 
-IO bridge configration driver (3rd stage address translation) for Marvell Armada 8K and 8K+ SoCs.
+IO bridge configuration driver (3rd stage address translation) for Marvell Armada 8K and 8K+ SoCs.
 
 The IOB includes a description of the address decoding configuration.
 
diff --git a/docs/plat/mt8195.rst b/docs/plat/mt8195.rst
new file mode 100644
index 0000000..b2aeea2
--- /dev/null
+++ b/docs/plat/mt8195.rst
@@ -0,0 +1,21 @@
+MediaTek 8195
+=============
+
+MediaTek 8195 (MT8195) is a 64-bit ARM SoC introduced by MediaTek in 2021.
+The chip incorporates eight cores - four Cortex-A55 little cores and Cortex-A76.
+Cortex-A76 can operate at up to 2.2 GHz.
+Cortex-A55 can operate at up to 2.0 GHz.
+
+Boot Sequence
+-------------
+
+::
+
+    Boot Rom --> Coreboot --> TF-A BL31 --> Depthcharge --> Linux Kernel
+
+How to Build
+------------
+
+.. code:: shell
+
+    make CROSS_COMPILE=aarch64-linux-gnu- PLAT=mt8195 DEBUG=1 COREBOOT=1
diff --git a/docs/plat/nvidia-tegra.rst b/docs/plat/nvidia-tegra.rst
index 02ff38b..391c7c8 100644
--- a/docs/plat/nvidia-tegra.rst
+++ b/docs/plat/nvidia-tegra.rst
@@ -19,7 +19,7 @@
 multi-processing (HMP) solution designed to optimize performance and
 efficiency.
 
-T186 has Dual NVIDIA Denver 2 ARM® CPU cores, plus Quad ARM Cortex®-A57 cores,
+T186 has Dual NVIDIA Denver2 ARM® CPU cores, plus Quad ARM Cortex®-A57 cores,
 in a coherent multiprocessor configuration. The Denver 2 and Cortex-A57 cores
 support ARMv8, executing both 64-bit Aarch64 code, and 32-bit Aarch32 code
 including legacy ARMv7 applications. The Denver 2 processors each have 128 KB
@@ -29,20 +29,6 @@
 high speed coherency fabric connects these two processor complexes and allows
 heterogeneous multi-processing with all six cores if required.
 
--  .. rubric:: T210
-      :name: t210
-
-T210 has Quad Arm® Cortex®-A57 cores in a switched configuration with a
-companion set of quad Arm Cortex-A53 cores. The Cortex-A57 and A53 cores
-support Armv8-A, executing both 64-bit Aarch64 code, and 32-bit Aarch32 code
-including legacy Armv7-A applications. The Cortex-A57 processors each have
-48 KB Instruction and 32 KB Data Level 1 caches; and have a 2 MB shared
-Level 2 unified cache. The Cortex-A53 processors each have 32 KB Instruction
-and 32 KB Data Level 1 caches; and have a 512 KB shared Level 2 unified cache.
-
--  .. rubric:: T132
-      :name: t132
-
 Denver is NVIDIA's own custom-designed, 64-bit, dual-core CPU which is
 fully Armv8-A architecture compatible. Each of the two Denver cores
 implements a 7-way superscalar microarchitecture (up to 7 concurrent
@@ -68,6 +54,17 @@
 to extensive power-gating and dynamic voltage and clock scaling based on
 workloads.
 
+-  .. rubric:: T210
+      :name: t210
+
+T210 has Quad Arm® Cortex®-A57 cores in a switched configuration with a
+companion set of quad Arm Cortex-A53 cores. The Cortex-A57 and A53 cores
+support Armv8-A, executing both 64-bit Aarch64 code, and 32-bit Aarch32 code
+including legacy Armv7-A applications. The Cortex-A57 processors each have
+48 KB Instruction and 32 KB Data Level 1 caches; and have a 2 MB shared
+Level 2 unified cache. The Cortex-A53 processors each have 32 KB Instruction
+and 32 KB Data Level 1 caches; and have a 512 KB shared Level 2 unified cache.
+
 Directory structure
 -------------------
 
@@ -89,7 +86,6 @@
 
 These are the supported Trusted OS' by Tegra platforms.
 
-- Tegra132: TLK
 - Tegra210: TLK and Trusty
 - Tegra186: Trusty
 - Tegra194: Trusty
@@ -110,7 +106,7 @@
 .. code:: shell
 
     CROSS_COMPILE=<path-to-aarch64-gcc>/bin/aarch64-none-elf- make PLAT=tegra \
-    TARGET_SOC=<target-soc e.g. t194|t186|t210|t132> SPD=<dispatcher e.g. trusty|tlkd>
+    TARGET_SOC=<target-soc e.g. t194|t186|t210> SPD=<dispatcher e.g. trusty|tlkd>
     bl31
 
 Platforms wanting to use different TZDRAM\_BASE, can add ``TZDRAM_BASE=<value>``
diff --git a/docs/plat/nxp/index.rst b/docs/plat/nxp/index.rst
new file mode 100644
index 0000000..8546887
--- /dev/null
+++ b/docs/plat/nxp/index.rst
@@ -0,0 +1,17 @@
+NXP Reference Development Platforms
+===================================
+
+.. toctree::
+   :maxdepth: 1
+   :caption: Contents
+
+   nxp-layerscape
+   nxp-ls-fuse-prov
+   nxp-ls-tbbr
+
+This chapter holds documentation related to NXP reference development platforms.
+It includes details on image flashing, fuse provisioning and trusted board boot-up.
+
+--------------
+
+*Copyright (c) 2021, NXP Limited. All rights reserved.*
diff --git a/docs/plat/nxp/nxp-layerscape.rst b/docs/plat/nxp/nxp-layerscape.rst
new file mode 100644
index 0000000..9a470e6
--- /dev/null
+++ b/docs/plat/nxp/nxp-layerscape.rst
@@ -0,0 +1,301 @@
+NXP SoCs - Overview
+=====================
+.. section-numbering::
+    :suffix: .
+
+The QorIQ family of ARM based SoCs that are supported on TF-A are:
+
+1. LX2160A
+
+- SoC Overview:
+
+The LX2160A multicore processor, the highest-performance member of the
+Layerscape family, combines FinFET process technology's low power and
+sixteen Arm® Cortex®-A72 cores with datapath acceleration optimized for
+L2/3 packet processing, together with security offload, robust traffic
+management and quality of service.
+
+Details about LX2160A can be found at `lx2160a`_.
+
+- LX2160ARDB Board:
+
+The LX2160A reference design board provides a comprehensive platform
+that enables design and evaluation of the LX2160A or LX2162A processors. It
+comes preloaded with a board support package (BSP) based on a standard Linux
+kernel.
+
+Board details can be fetched from the link: `lx2160ardb`_.
+
+2. LS1028A
+
+- SoC Overview:
+
+The Layerscape LS1028A applications processor for industrial and
+automotive includes a time-sensitive networking (TSN) -enabled Ethernet
+switch and Ethernet controllers to support converged IT and OT networks.
+Two powerful 64-bit Arm®v8 cores support real-time processing for
+industrial control and virtual machines for edge computing in the IoT.
+The integrated GPU and LCD controller enable Human-Machine Interface
+(HMI) systems with next-generation interfaces.
+
+Details about LS1028A can be found at `ls1028a`_.
+
+- LS1028ARDB Boards:
+
+The LS1028A reference design board (RDB) is a computing, evaluation,
+and development platform that supports industrial IoT applications, human
+machine interface solutions, and industrial networking.
+
+Details about LS1028A RDB board can be found at `ls1028ardb`_.
+
+Table of supported boot-modes by each platform & platform that needs FIP-DDR:
+-----------------------------------------------------------------------------
+
++---------------------+---------------------------------------------------------------------+-----------------+
+|                     |                            BOOT_MODE                                |                 |
+|       PLAT          +-------+--------+-------+-------+-------+-------------+--------------+ fip_ddr_needed  |
+|                     |  sd   |  qspi  |  nor  | nand  | emmc  | flexspi_nor | flexspi_nand |                 |
++=====================+=======+========+=======+=======+=======+=============+==============+=================+
+|     lx2160ardb      |  yes  |        |       |       |  yes  |   yes       |              |       yes       |
++---------------------+-------+--------+-------+-------+-------+-------------+--------------+-----------------+
+|     ls1028ardb      |  yes  |        |       |       |  yes  |   yes       |              |       no        |
++---------------------+-------+--------+-------+-------+-------+-------------+--------------+-----------------+
+
+
+Boot Sequence
+-------------
+::
+
++                           Secure World        |     Normal World
++ EL0                                           |
++                                               |
++ EL1                           BL32(Tee OS)    |     kernel
++                                ^ |            |       ^
++                                | |            |       |
++ EL2                            | |            |     BL33(u-boot)
++                                | |            |      ^
++                                | v            |     /
++ EL3        BootROM --> BL2 --> BL31 ---------------/
++
+
+Boot Sequence with FIP-DDR
+--------------------------
+::
+
++                           Secure World        |     Normal World
++ EL0                                           |
++                                               |
++ EL1               fip-ddr     BL32(Tee OS)    |     kernel
++                     ^ |         ^ |           |       ^
++                     | |         | |           |       |
++ EL2                 | |         | |           |     BL33(u-boot)
++                     | |         | |           |      ^
++                     | v         | v           |     /
++ EL3     BootROM --> BL2 -----> BL31 ---------------/
++
+
+DDR Memory Layout
+--------------------------
+
+NXP Platforms divide DRAM into banks:
+
+- DRAM0 Bank:  Maximum size of this bank is fixed to 2GB, DRAM0 size is defined in platform_def.h if it is less than 2GB.
+
+- DRAM1 ~ DRAMn Bank:  Greater than 2GB belongs to DRAM1 and following banks, and size of DRAMn Bank varies for one platform to others.
+
+The following diagram is default DRAM0 memory layout in which secure memory is at top of DRAM0.
+
+::
+
+  high  +---------------------------------------------+
+        |                                             |
+        |   Secure EL1 Payload Shared Memory (2 MB)   |
+        |                                             |
+        +---------------------------------------------+
+        |                                             |
+        |            Secure Memory (64 MB)            |
+        |                                             |
+        +---------------------------------------------+
+        |                                             |
+        |             Non Secure Memory               |
+        |                                             |
+  low   +---------------------------------------------+
+
+How to build
+=============
+
+Code Locations
+--------------
+
+-  OP-TEE:
+   `link <https://source.codeaurora.org/external/qoriq/qoriq-components/optee_os>`__
+
+-  U-Boot:
+   `link <https://source.codeaurora.org/external/qoriq/qoriq-components/u-boot>`__
+
+-  RCW:
+   `link <https://source.codeaurora.org/external/qoriq/qoriq-components/rcw>`__
+
+-  ddr-phy-binary: Required by platforms that need fip-ddr.
+   `link <https:://github.com/NXP/ddr-phy-binary>`__
+
+-  cst: Required for TBBR.
+   `link <https:://source.codeaurora.org/external/qoriq/qoriq-components/cst>`__
+
+Build Procedure
+---------------
+
+-  Fetch all the above repositories into local host.
+
+-  Prepare AARCH64 toolchain and set the environment variable "CROSS_COMPILE".
+
+   .. code:: shell
+
+       export CROSS_COMPILE=.../bin/aarch64-linux-gnu-
+
+-  Build RCW. Refer README from the respective cloned folder for more details.
+
+-  Build u-boot and OPTee firstly, and get binary images: u-boot.bin and tee.bin.
+   For u-boot you can use the <platform>_tfa_defconfig for build.
+
+-  Copy/clone the repo "ddr-phy-binary" to the tfa directory for platform needing ddr-fip.
+
+-  Below are the steps to build TF-A images for the supported platforms.
+
+Compilation steps without BL32
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+BUILD BL2:
+
+-To compile
+   .. code:: shell
+
+       make PLAT=$PLAT \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       pbl
+
+BUILD FIP:
+
+   .. code:: shell
+
+       make PLAT=$PLAT \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL33=$UBOOT_SECURE_BIN \
+       pbl \
+       fip
+
+Compilation steps with BL32
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+BUILD BL2:
+
+-To compile
+   .. code:: shell
+
+       make PLAT=$PLAT \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL32=$TEE_BIN SPD=opteed\
+       pbl
+
+BUILD FIP:
+
+   .. code:: shell
+
+       make PLAT=$PLAT \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL32=$TEE_BIN SPD=opteed\
+       BL33=$UBOOT_SECURE_BIN \
+       pbl \
+       fip
+
+
+BUILD fip-ddr (Mandatory for certain platforms, refer table above):
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+-To compile additional fip-ddr for selected platforms(Refer above table if the platform needs fip-ddr).
+   .. code:: shell
+
+	make PLAT=<platform_name> fip-ddr
+
+
+Deploy ATF Images
+=================
+
+Note: The size in the standard uboot commands for copy to nor, qspi, nand or sd
+should be modified based on the binary size of the image to be copied.
+
+-  Deploy ATF images on flexspi-Nor flash Alt Bank from U-Boot prompt.
+   --  Commands to flash images for bl2_xxx.pbl and fip.bin.
+
+   .. code:: shell
+
+        tftp 82000000  $path/bl2_flexspi_nor.pbl;
+        i2c mw 66 50 20;sf probe 0:0; sf erase 0 +$filesize; sf write 0x82000000 0x0 $filesize;
+
+        tftp 82000000  $path/fip.bin;
+        i2c mw 66 50 20;sf probe 0:0; sf erase 0x100000 +$filesize; sf write 0x82000000 0x100000 $filesize;
+
+   --  Next step is valid for platform where FIP-DDR is needed.
+
+   .. code:: shell
+
+        tftp 82000000  $path/ddr_fip.bin;
+        i2c mw 66 50 20;sf probe 0:0; sf erase 0x800000 +$filesize; sf write 0x82000000 0x800000 $filesize;
+
+   --  Then reset to alternate bank to boot up ATF.
+
+   .. code:: shell
+
+        qixisreset altbank;
+
+-  Deploy ATF images on SD/eMMC from U-Boot prompt.
+   -- file_size_in_block_sizeof_512 = (Size_of_bytes_tftp / 512)
+
+   .. code:: shell
+
+        mmc dev <idx>; (idx = 1 for eMMC; idx = 0 for SD)
+
+        tftp 82000000  $path/bl2_<sd>_or_<emmc>.pbl;
+        mmc write 82000000 8 <file_size_in_block_sizeof_512>;
+
+        tftp 82000000  $path/fip.bin;
+        mmc write 82000000 0x800 <file_size_in_block_sizeof_512>;
+
+    --  Next step is valid for platform that needs FIP-DDR.
+
+   .. code:: shell
+
+        tftp 82000000  $path/ddr_fip.bin;
+        mmc write 82000000 0x4000 <file_size_in_block_sizeof_512>;
+
+   --  Then reset to sd/emmc to boot up ATF from sd/emmc as boot-source.
+
+   .. code:: shell
+
+        qixisreset <sd or emmc>;
+
+Trusted Board Boot:
+===================
+
+For TBBR, the binary name changes:
+
++-------------+--------------------------+---------+-------------------+
+|  Boot Type  |           BL2            |   FIP   |      FIP-DDR      |
++=============+==========================+=========+===================+
+| Normal Boot |  bl2_<boot_mode>.pbl     | fip.bin | ddr_fip.bin       |
++-------------+--------------------------+---------+-------------------+
+| TBBR Boot   |  bl2_<boot_mode>_sec.pbl | fip.bin | ddr_fip_sec.bin   |
++-------------+--------------------------+---------+-------------------+
+
+Refer `nxp-ls-tbbr.rst`_ for detailed user steps.
+
+
+.. _lx2160a: https://www.nxp.com/products/processors-and-microcontrollers/arm-processors/layerscape-processors/layerscape-lx2160a-lx2120a-lx2080a-processors:LX2160A
+.. _lx2160ardb: https://www.nxp.com/products/processors-and-microcontrollers/arm-processors/layerscape-communication-process/layerscape-lx2160a-multicore-communications-processor:LX2160A
+.. _ls1028a: https://www.nxp.com/products/processors-and-microcontrollers/arm-processors/layerscape-processors/layerscape-1028a-applications-processor:LS1028A
+.. _ls1028ardb: https://www.nxp.com/design/qoriq-developer-resources/layerscape-ls1028a-reference-design-board:LS1028ARDB
+.. _nxp-ls-tbbr.rst: ./nxp-ls-tbbr.rst
diff --git a/docs/plat/nxp/nxp-ls-fuse-prov.rst b/docs/plat/nxp/nxp-ls-fuse-prov.rst
new file mode 100644
index 0000000..64e1c6f
--- /dev/null
+++ b/docs/plat/nxp/nxp-ls-fuse-prov.rst
@@ -0,0 +1,271 @@
+
+Steps to blow fuses on NXP LS SoC:
+==================================
+
+
+- Enable POVDD
+  -- Refer board GSG(Getting Started Guide) for the steps to enable POVDD.
+  -- Once the POVDD is enabled, make sure to set variable POVDD_ENABLE := yes, in the platform.mk.
+
++---+-----------------+-----------+------------+-----------------+-----------------------------+
+|   |   Platform      |  Jumper   |  Switch    | LED to Verify   |  Through GPIO Pin (=number) |
++===+=================+===========+============+=================+=============================+
+| 1.| lx2160ardb      |  J9       |            |                 |             no              |
++---+-----------------+-----------+------------+-----------------+-----------------------------+
+| 2.| lx2160aqds      |  J35      |            |                 |             no              |
++---+-----------------+-----------+------------+-----------------+-----------------------------+
+| 3.| lx2162aqds      |  J35      | SW9[4] = 1 |    D15          |             no              |
++---+-----------------+-----------+------------+-----------------+-----------------------------+
+
+- SFP registers to be written to:
+
++---+----------------------------------+----------------------+----------------------+
+|   |   Platform                       |   OTPMKR0..OTPMKR7   |   SRKHR0..SRKHR7     |
++===+==================================+======================+======================+
+| 1.| lx2160ardb/lx2160aqds/lx2162aqds | 0x1e80234..0x1e80250 | 0x1e80254..0x1e80270 |
++---+----------------------------------+----------------------+----------------------+
+
+- At U-Boot prompt, verify that SNVS register - HPSR, whether OTPMK was written, already:
+
++---+----------------------------------+-------------------------------------------+---------------+
+|   |   Platform                       |           OTPMK_ZERO_BIT(=value)          | SNVS_HPSR_REG |
++===+==================================+===========================================+===============+
+| 1.| lx2160ardb/lx2160aqds/lx2162aqds | 27 (= 1 means not blown, =0 means blown)  | 0x01E90014    |
++---+----------------------------------+-------------------------------------------+---------------+
+
+From u-boot prompt:
+
+  --  Check for the OTPMK.
+   .. code:: shell
+
+        md $SNVS_HPSR_REG
+
+      Command Output:
+          01e90014: 88000900
+
+          In case it is read as 00000000, then read this register using jtag (in development mode only through CW tap).
+                       +0       +4       +8       +C
+          [0x01E90014] 88000900
+
+          Note: OTPMK_ZERO_BIT is 1, indicating that the OTPMK is not blown.
+
+  --  Check for the SRK Hash.
+   .. code:: shell
+
+        md $SRKHR0 0x10
+
+      Command Output:
+          01e80254: 00000000 00000000 00000000 00000000    ................
+          01e80264: 00000000 00000000 00000000 00000000    ................
+
+          Note: Zero means that SRK hash is not blown.
+
+- If not blown, then from the U-Boot prompt, using following commands:
+  --  Provision the OTPMK.
+
+   .. code:: shell
+
+        mw.l $OTPMKR0  <OTMPKR_0_32Bit_val>
+        mw.l $OTPMKR1  <OTMPKR_1_32Bit_val>
+        mw.l $OTPMKR2  <OTMPKR_2_32Bit_val>
+        mw.l $OTPMKR3  <OTMPKR_3_32Bit_val>
+        mw.l $OTPMKR4  <OTMPKR_4_32Bit_val>
+        mw.l $OTPMKR5  <OTMPKR_5_32Bit_val>
+        mw.l $OTPMKR6  <OTMPKR_6_32Bit_val>
+        mw.l $OTPMKR7  <OTMPKR_7_32Bit_val>
+
+  --  Provision the SRK Hash.
+
+   .. code:: shell
+
+        mw.l $SRKHR0  <SRKHR_0_32Bit_val>
+        mw.l $SRKHR1  <SRKHR_1_32Bit_val>
+        mw.l $SRKHR2  <SRKHR_2_32Bit_val>
+        mw.l $SRKHR3  <SRKHR_3_32Bit_val>
+        mw.l $SRKHR4  <SRKHR_4_32Bit_val>
+        mw.l $SRKHR5  <SRKHR_5_32Bit_val>
+        mw.l $SRKHR6  <SRKHR_6_32Bit_val>
+        mw.l $SRKHR7  <SRKHR_7_32Bit_val>
+
+      Note: SRK Hash should be carefully written keeping in mind the SFP Block Endianness.
+
+- At U-Boot prompt, verify that SNVS registers for OTPMK are correctly written:
+
+  --  Check for the OTPMK.
+   .. code:: shell
+
+        md $SNVS_HPSR_REG
+
+      Command Output:
+          01e90014: 80000900
+
+          OTPMK_ZERO_BIT is zero, indicating that the OTPMK is blown.
+
+          Note: In case it is read as 00000000, then read this register using jtag (in development mode only through CW tap).
+
+   .. code:: shell
+
+        md $OTPMKR0 0x10
+
+      Command Output:
+          01e80234: ffffffff ffffffff ffffffff ffffffff    ................
+          01e80244: ffffffff ffffffff ffffffff ffffffff    ................
+
+          Note: OTPMK will never be visible in plain.
+
+  --  Check for the SRK Hash. For example, if following SRK hash is written:
+
+       SFP SRKHR0 = fdc2fed4
+       SFP SRKHR1 = 317f569e
+       SFP SRKHR2 = 1828425c
+       SFP SRKHR3 = e87b5cfd
+       SFP SRKHR4 = 34beab8f
+       SFP SRKHR5 = df792a70
+       SFP SRKHR6 = 2dff85e1
+       SFP SRKHR7 = 32a29687,
+
+       then following would be the value on dumping SRK hash.
+
+   .. code:: shell
+
+        md $SRKHR0 0x10
+
+      Command Output:
+          01e80254: d4fec2fd 9e567f31 5c422818 fd5c7be8    ....1.V..(B\.{\.
+          01e80264: 8fabbe34 702a79df e185ff2d 8796a232    4....y*p-...2...
+
+          Note: SRK Hash is visible in plain based on the SFP Block Endianness.
+
+- Caution: Donot proceed to the next step, until you are sure that OTPMK and SRKH are correctly blown from above steps.
+  -- After the next step, there is no turning back.
+  -- Fuses will be burnt, which cannot be undo.
+
+- Write SFP_INGR[INST] with the PROGFB(0x2) instruction to blow the fuses.
+  -- User need to save the SRK key pair and OTPMK Key forever, to continue using this board.
+
++---+----------------------------------+-------------------------------------------+-----------+
+|   |   Platform                       | SFP_INGR_REG | SFP_WRITE_DATE_FRM_MIRROR_REG_TO_FUSE  |
++===+==================================+=======================================================+
+| 1.| lx2160ardb/lx2160aqds/lx2162aqds | 0x01E80020   |    0x2                                 |
++---+----------------------------------+--------------+----------------------------------------+
+
+   .. code:: shell
+
+        md $SFP_INGR_REG  $SFP_WRITE_DATE_FRM_MIRROR_REG_TO_FUSE
+
+- On reset, if the SFP register were read from u-boot, it will show the following:
+  --  Check for the OTPMK.
+
+   .. code:: shell
+
+        md $SNVS_HPSR_REG
+
+      Command Output:
+          01e90014: 80000900
+
+          In case it is read as 00000000, then read this register using jtag (in development mode only through CW tap).
+                       +0       +4       +8       +C
+          [0x01E90014] 80000900
+
+          Note: OTPMK_ZERO_BIT is zero, indicating that the OTPMK is blown.
+
+   .. code:: shell
+
+        md $OTPMKR0 0x10
+
+      Command Output:
+          01e80234: ffffffff ffffffff ffffffff ffffffff    ................
+          01e80244: ffffffff ffffffff ffffffff ffffffff    ................
+
+          Note: OTPMK will never be visible in plain.
+
+  -- SRK Hash
+
+   .. code:: shell
+
+        md $SRKHR0 0x10
+
+      Command Output:
+          01e80254: d4fec2fd 9e567f31 5c422818 fd5c7be8    ....1.V..(B\.{\.
+          01e80264: 8fabbe34 702a79df e185ff2d 8796a232    4....y*p-...2...
+
+          Note: SRK Hash is visible in plain based on the SFP Block Endianness.
+
+Second method to do the fuse provsioning:
+=========================================
+
+This method is used for quick way to provision fuses.
+Typically used by those who needs to provision number of boards.
+
+- Enable POVDD:
+  -- Refer the table above to enable POVDD.
+
+     Note: If GPIO Pin supports enabling POVDD, it can be done through the below input_fuse_file.
+
+  -- Once the POVDD is enabled, make sure to set variable POVDD_ENABLE := yes, in the platform.mk.
+
+- User need to populate the "input_fuse_file", corresponding to the platform for:
+
+  -- OTPMK
+  -- SRKH
+
+  Table of fuse provisioning input file for every supported platform:
+
++---+----------------------------------+-----------------------------------------------------------------+
+|   |   Platform                       |                        FUSE_PROV_FILE                           |
++===+==================================+=================================================================+
+| 1.| lx2160ardb/lx2160aqds/lx2162aqds | ${CST_DIR}/input_files/gen_fusescr/ls2088_1088/input_fuse_file  |
++---+----------------------------------+--------------+--------------------------------------------------+
+
+- Create the TF-A binary with FUSE_PROG=1.
+
+   .. code:: shell
+
+        make PLAT=$PLAT FUSE_PROG=1\
+          BOOT_MODE=<platform_supported_boot_mode> \
+          RCW=$RCW_BIN \
+          BL32=$TEE_BIN SPD=opteed\
+          BL33=$UBOOT_SECURE_BIN \
+          pbl \
+          fip \
+          fip_fuse \
+          FUSE_PROV_FILE=../../apps/security/cst/input_files/gen_fusescr/ls2088_1088/input_fuse_file
+
+- Deployment:
+  -- Refer the nxp-layerscape.rst for deploying TF-A images.
+  -- Deploying fip_fuse.bin:
+
+       For Flexspi-Nor:
+
+   .. code:: shell
+
+        tftp 82000000  $path/fuse_fip.bin;
+        i2c mw 66 50 20;sf probe 0:0; sf erase 0x880000 +$filesize; sf write 0x82000000 0x880000 $filesize;
+
+      For SD or eMMC [file_size_in_block_sizeof_512 = (Size_of_bytes_tftp / 512)]:
+
+   .. code:: shell
+
+        tftp 82000000  $path/fuse_fip.bin;
+        mmc write 82000000 0x4408 <file_size_in_block_sizeof_512>;
+
+- Valiation:
+
++---+----------------------------------+---------------------------------------------------+
+|   |   Platform                       |    Error_Register        | Error_Register_Address |
++===+==================================+===================================================+
+| 1.| lx2160ardb/lx2160aqds/lx2162aqds | DCFG scratch 4 register  |     0x01EE020C         |
++---+----------------------------------+---------------------------------------------------+
+
+   At the U-Boot prompt, check DCFG scratch 4 register for any error.
+
+   .. code:: shell
+
+        md $Error_Register_Address 1
+
+      Command Ouput:
+          01ee020c: 00000000
+
+      Note:
+       - 0x00000000 shows no error, then fuse provisioning is successful.
+       - For non-zero value, refer the code header file ".../drivers/nxp/sfp/sfp_error_codes.h"
diff --git a/docs/plat/nxp/nxp-ls-tbbr.rst b/docs/plat/nxp/nxp-ls-tbbr.rst
new file mode 100644
index 0000000..43e15f7
--- /dev/null
+++ b/docs/plat/nxp/nxp-ls-tbbr.rst
@@ -0,0 +1,210 @@
+
+--------------
+NXP Platforms:
+--------------
+TRUSTED_BOARD_BOOT option can be enabled by specifying TRUSTED_BOARD_BOOT=1 on command line during make.
+
+
+
+Bare-Minimum Preparation to run  TBBR on NXP Platforms:
+=======================================================
+- OTPMK(One Time Programable Key) needs to be burnt in fuses.
+  -- It is the 256 bit key that stores a secret value used by the NXP SEC 4.0 IP in Trusted or Secure mode.
+
+     Note: It is primarily for the purpose of decrypting additional secrets stored in system non-volatile memory.
+
+  -- NXP CST tool gives an option to generate it.
+
+   Use the below command from directory 'cst', with correct options.
+
+   .. code:: shell
+
+     ./gen_otpmk_drbg
+
+- SRKH (Super Root Key Hash) needs to be burnt in fuses.
+  -- It is the 256 bit hash of the list of the public keys of the SRK key pair.
+  -- NXP CST tool gives an option to generate the RSA key pair and its hash.
+
+   Use the below command from directory 'cst', with correct options.
+
+   .. code:: shell
+
+     ./gen_keys
+
+Refer fuse frovisioning readme 'nxp-ls-fuse-prov.rst' for steps to blow these keys.
+
+
+
+Two options are provided for TRUSTED_BOARD_BOOT:
+================================================
+
+-------------------------------------------------------------------------
+Option 1: CoT using X 509 certificates
+-------------------------------------------------------------------------
+
+- This CoT is as provided by ARM.
+
+- To use this option user needs to specify mbedtld dir path in MBEDTLS_DIR.
+
+- To generate CSF header, path of CST repository needs to be specified as CST_DIR
+
+- CSF header is embedded to each of the BL2 image.
+
+- GENERATE_COT=1 adds the tool 'cert_create' to the build environment to generate:
+  -- X509 Certificates as (.crt) files.
+  -- X509 Pem key file as (.pem) files.
+
+- SAVE_KEYS=1 saves the keys and certificates, if GENERATE_COT=1.
+  -- For this to work, file name for cert and keys are provided as part of  compilation or build command.
+
+     --- default file names will be used, incase not provided as part compilation or build command.
+     --- default folder 'BUILD_PLAT' will be used to store them.
+
+- ROTPK for x.509 certificates is generated and embedded in bl2.bin and
+  verified as part of CoT by Boot ROM during secure boot.
+
+- Compilation steps:
+
+All Images
+   .. code:: shell
+
+       make PLAT=$PLAT TRUSTED_BOARD_BOOT=1 GENERATE_COT=1 MBEDTLS_DIR=$MBEDTLS_PATH CST_DIR=$CST_DIR_PATH \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL32=$TEE_BIN SPD=opteed\
+       BL33=$UBOOT_SECURE_BIN \
+       pbl \
+       fip
+
+Additional FIP_DDR Image (For NXP platforms like lx2160a)
+   .. code:: shell
+
+       make PLAT=$PLAT TRUSTED_BOARD_BOOT=1 GENERATE_COT=1 MBEDTLS_DIR=$MBEDTLS_PATH fip_ddr
+
+      Note: make target 'fip_ddr' should never be combine with other make target 'fip', 'pbl' & 'bl2'.
+
+-------------------------------------------------------------------------
+Option 2: CoT using NXP CSF headers.
+-------------------------------------------------------------------------
+
+- This option is automatically selected when TRUSTED_BOARD_BOOT is set but MBEDTLS_DIR path is not specified.
+
+- CSF header is embedded to each of the BL31, BL32 and  BL33 image.
+
+- To generate CSF header, path of CST repository needs to be specified as CST_DIR
+
+- Default input files for CSF header generation is added in this repo.
+
+- Default input file requires user to generate RSA key pair named
+  -- srk.pri, and
+  -- srk.pub, and add them in ATF repo.
+  -- These keys can be generated using gen_keys tool of CST.
+
+- To change the input file , user can use the options BL33_INPUT_FILE, BL32_INPUT_FILE, BL31_INPUT_FILE
+
+- There are 2 paths in secure boot flow :
+  -- Development Mode (sb_en in RCW = 1, SFP->OSPR, ITS = 0)
+
+     --- In this flow , even on ROTPK comparison failure, flow would continue.
+     --- However SNVS is transitioned to non-secure state
+
+  -- Production mode (SFP->OSPR, ITS = 1)
+
+     --- Any failure is fatal failure
+
+- Compilation steps:
+
+All Images
+   .. code:: shell
+
+       make PLAT=$PLAT TRUSTED_BOARD_BOOT=1 CST_DIR=$CST_DIR_PATH \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL32=$TEE_BIN SPD=opteed\
+       BL33=$UBOOT_SECURE_BIN \
+       pbl \
+       fip
+
+Additional FIP_DDR Image (For NXP platforms like lx2160a)
+   .. code:: shell
+
+       make PLAT=$PLAT TRUSTED_BOARD_BOOT=1 CST_DIR=$CST_DIR_PATH fip_ddr
+
+- Compilation Steps with build option for generic image processing filters to prepend CSF header:
+  --  Generic image processing filters to prepend CSF header
+
+      BL32_INPUT_FILE = < file name>
+      BL33_INPUT_FILE = <file name>
+
+   .. code:: shell
+
+       make PLAT=$PLAT TRUSTED_BOARD_BOOT=1 CST_DIR=$CST_DIR_PATH \
+       BOOT_MODE=<platform_supported_boot_mode> \
+       RCW=$RCW_BIN \
+       BL32=$TEE_BIN SPD=opteed\
+       BL33=$UBOOT_SECURE_BIN \
+       BL33_INPUT_FILE = <ip file> \
+       BL32_INPUT_FILE = <ip_file> \
+       BL31_INPUT_FILE = <ip file> \
+       pbl \
+       fip
+
+
+Deploy ATF Images
+=================
+Same steps as mentioned in the readme "nxp-layerscape.rst".
+
+
+
+Verification to check if Secure state is achieved:
+==================================================
+
++---+----------------+-----------------+------------------------+----------------------------------+-------------------------------+
+|   |   Platform     |  SNVS_HPSR_REG  | SYS_SECURE_BIT(=value) | SYSTEM_SECURE_CONFIG_BIT(=value) | SSM_STATE                     |
++===+================+=================+========================+==================================+===============================+
+| 1.| lx2160ardb  or |    0x01E90014   | 15                     | 14-12                            | 11-8                          |
+|   | lx2160aqds  or |                 | ( = 1, BootROM Booted) | ( = 010 means Intent to Secure,  | (=1111 means secure boot)     |
+|   | lx2162aqds     |                 |                        | ( = 000 Unsecure)                | (=1011 means Non-secure Boot) |
++---+----------------+-----------------+------------------------+----------------------------------+-------------------------------+
+
+- Production mode (SFP->OSPR, ITS = 1)
+  -- Linux prompt will successfully come. if the TBBR is successful.
+
+     --- Else, Linux boot will be successful.
+
+  -- For secure-boot status, read SNVS Register $SNVS_HPSR_REG from u-boot prompt:
+
+   .. code:: shell
+
+        md $SNVS_HPSR_REG
+
+      Command Output:
+          1e90014: 8000AF00
+
+          In case it is read as 00000000, then read this register using jtag (in development mode only through CW tap).
+                       +0       +4       +8       +C
+          [0x01E90014] 8000AF00
+
+
+- Development Mode (sb_en in RCW = 1, SFP->OSPR, ITS = 0)
+  -- Refer the SoC specific table to read the register to interpret whether the secure boot is achieved or not.
+  -- Using JTAG (in development environment only, using CW tap):
+
+     --- For secure-boot status, read SNVS Register $SNVS_HPSR_REG
+
+   .. code:: shell
+
+        ccs::display_regs 86 0x01E90014 4 0 1
+
+      Command Output:
+          Using the SAP chain position number 86, following is the output.
+
+                       +0       +4       +8       +C
+          [0x01E90014] 8000AF00
+
+          Note: Chain position number will vary from one SoC to other SoC.
+
+- Interpretation of the value:
+
+  -- 0xA indicates BootROM booted, with intent to secure.
+  -- 0xF = secure boot, as SSM_STATE.
diff --git a/docs/plat/qti.rst b/docs/plat/qti.rst
index 814e672..1d483e7 100644
--- a/docs/plat/qti.rst
+++ b/docs/plat/qti.rst
@@ -1,8 +1,8 @@
 Qualcomm Technologies, Inc.
 ===========================
 
-Trusted Firmware-A (TF-A) implements the EL3 firmware layer for QTI SC7180.
-
+Trusted Firmware-A (TF-A) implements the EL3 firmware layer for QTI SC7180,
+SC7280.
 
 Boot Trace
 -------------
@@ -38,4 +38,6 @@
 added to satisfy compilation.
 
 QTISELIB for SC7180 is available at
-`link <https://review.coreboot.org/cgit/qc_blobs.git/plain/sc7180/qtiseclib/libqtisec.a>`__
+`link <https://github.com/coreboot/qc_blobs/blob/master/sc7180/qtiseclib/libqtisec.a?raw=true>`__
+QTISELIB for SC7280 is available at
+`link <https://github.com/coreboot/qc_blobs/blob/master/sc7280/qtiseclib/libqtisec.a?raw=true>`__
diff --git a/docs/plat/rpi4.rst b/docs/plat/rpi4.rst
index beb0227..6e83fd7 100644
--- a/docs/plat/rpi4.rst
+++ b/docs/plat/rpi4.rst
@@ -60,7 +60,7 @@
 run after the SoC gets its power. The on-chip Boot ROM loads the next stage
 (bootcode.bin) from flash (EEPROM), which is again GPU code.
 This part knows how to access the MMC controller and how to parse a FAT
-filesystem, so it will load further compononents and configuration files
+filesystem, so it will load further components and configuration files
 from the first FAT partition on the SD card.
 
 To accommodate this existing way of configuring and setting up the board,
diff --git a/docs/plat/rz-g2.rst b/docs/plat/rz-g2.rst
new file mode 100644
index 0000000..e7ae620
--- /dev/null
+++ b/docs/plat/rz-g2.rst
@@ -0,0 +1,228 @@
+Renesas RZ/G
+============
+
+The "RZ/G" Family of high-end 64-bit Arm®-based microprocessors (MPUs)
+enables the solutions required for the smart society of the future.
+Through a variety of Arm Cortex®-A53 and A57-based devices, engineers can
+easily implement high-resolution human machine interfaces (HMI), embedded
+vision, embedded artificial intelligence (e-AI) and real-time control and
+industrial ethernet connectivity.
+
+The scalable RZ/G hardware platform and flexible software platform
+cover the full product range, from the premium class to the entry
+level. Plug-ins are available for multiple open-source software tools.
+
+
+Renesas RZ/G2 reference platforms:
+----------------------------------
+
++--------------+----------------------------------------------------------------------------------+
+| Board        |      Details                                                                     |
++==============+===============+==================================================================+
+| hihope-rzg2h | "96 boards" compatible board from Hoperun equipped with Renesas RZ/G2H SoC       |
+|              +----------------------------------------------------------------------------------+
+|              | http://hihope.org/product/musashi                                                |
++--------------+----------------------------------------------------------------------------------+
+| hihope-rzg2m | "96 boards" compatible board from Hoperun equipped with Renesas RZ/G2M SoC       |
+|              +----------------------------------------------------------------------------------+
+|              | http://hihope.org/product/musashi                                                |
++--------------+----------------------------------------------------------------------------------+
+| hihope-rzg2n | "96 boards" compatible board from Hoperun equipped with Renesas RZ/G2N SoC       |
+|              +----------------------------------------------------------------------------------+
+|              | http://hihope.org/product/musashi                                                |
++--------------+----------------------------------------------------------------------------------+
+| ek874        | "96 boards" compatible board from Silicon Linux equipped with Renesas RZ/G2E SoC |
+|              +----------------------------------------------------------------------------------+
+|              | https://www.si-linux.co.jp/index.php?CAT%2FCAT874                                |
++--------------+----------------------------------------------------------------------------------+
+
+`boards info <https://www.renesas.com/us/en/products/rzg-linux-platform/rzg-marcketplace/board-solutions.html#rzg2>`__
+
+The current TF-A port has been tested on the HiHope RZ/G2M
+SoC_id r8a774a1 revision ES1.3.
+
+
+::
+
+    ARM CA57 (ARMv8) 1.5 GHz dual core, with NEON/VFPv4, L1$ I/D 48K/32K, L2$ 1MB
+    ARM CA53 (ARMv8) 1.2 GHz quad core, with NEON/VFPv4, L1$ I/D 32K/32K, L2$ 512K
+    Memory controller for LPDDR4-3200 4GB in 2 channels(32-bit bus mode)
+    Two- and three-dimensional graphics engines,
+    Video processing units,
+    Display Output,
+    Video Input,
+    SD card host interface,
+    USB3.0 and USB2.0 interfaces,
+    CAN interfaces,
+    Ethernet AVB,
+    Wi-Fi + BT,
+    PCI Express Interfaces,
+    Memories
+        INTERNAL 384KB SYSTEM RAM
+        DDR 4 GB LPDDR4
+        QSPI FLASH 64MB
+        EMMC 32 GB EMMC (HS400 240 MBYTES/S)
+        MICROSD-CARD SLOT (SDR104 100 MBYTES/S)
+
+Overview
+--------
+On RZ/G2 SoCs the BOOTROM starts the cpu at EL3; for this port BL2
+will therefore be entered at this exception level (the Renesas' ATF
+reference tree [1] resets into EL1 before entering BL2 - see its
+bl2.ld.S)
+
+BL2 initializes DDR before determining the boot reason (cold or warm).
+
+Once BL2 boots, it determines the boot reason, writes it to shared
+memory (BOOT_KIND_BASE) together with the BL31 parameters
+(PARAMS_BASE) and jumps to BL31.
+
+To all effects, BL31 is as if it is being entered in reset mode since
+it still needs to initialize the rest of the cores; this is the reason
+behind using direct shared memory access to  BOOT_KIND_BASE _and_
+PARAMS_BASE instead of using registers to get to those locations (see
+el3_common_macros.S and bl31_entrypoint.S for the RESET_TO_BL31 use
+case).
+
+[1] https://github.com/renesas-rz/meta-rzg2/tree/BSP-1.0.5/recipes-bsp/arm-trusted-firmware/files
+
+
+How to build
+------------
+
+The TF-A build options depend on the target board so you will have to
+refer to those specific instructions. What follows is customized to
+the HiHope RZ/G2M development kit used in this port.
+
+Build Tested:
+~~~~~~~~~~~~~
+
+.. code:: bash
+
+       make bl2 bl31 rzg LOG_LEVEL=40 PLAT=rzg LSI=G2M RCAR_DRAM_SPLIT=2\
+       RCAR_LOSSY_ENABLE=1 SPD="none" MBEDTLS_DIR=$mbedtls
+
+System Tested:
+~~~~~~~~~~~~~~
+* mbed_tls:
+  git@github.com:ARMmbed/mbedtls.git [devel]
+
+|  commit 72ca39737f974db44723760623d1b29980c00a88
+|  Merge: ef94c4fcf dd9ec1c57
+|  Author: Janos Follath <janos.follath@arm.com>
+|  Date:   Wed Oct 7 09:21:01 2020 +0100
+
+* u-boot:
+  The port has beent tested using mainline uboot with HiHope RZ/G2M board
+  specific patches.
+
+|  commit 46ce9e777c1314ccb78906992b94001194eaa87b
+|  Author: Heiko Schocher <hs@denx.de>
+|  Date:   Tue Nov 3 15:22:36 2020 +0100
+
+* linux:
+  The port has beent tested using mainline kernel.
+
+|  commit f8394f232b1eab649ce2df5c5f15b0e528c92091
+|  Author: Linus Torvalds <torvalds@linux-foundation.org>
+|  Date:   Sun Nov 8 16:10:16 2020 -0800
+|  Linux 5.10-rc3
+
+TF-A Build Procedure
+~~~~~~~~~~~~~~~~~~~~
+
+-  Fetch all the above 3 repositories.
+
+-  Prepare the AARCH64 toolchain.
+
+-  Build u-boot using hihope_rzg2_defconfig.
+
+   Result: u-boot-elf.srec
+
+.. code:: bash
+
+       make CROSS_COMPILE=aarch64-linux-gnu-
+	  hihope_rzg2_defconfig
+
+       make CROSS_COMPILE=aarch64-linux-gnu-
+
+-  Build TF-A
+
+   Result: bootparam_sa0.srec, cert_header_sa6.srec, bl2.srec, bl31.srec
+
+.. code:: bash
+
+       make bl2 bl31 rzg LOG_LEVEL=40 PLAT=rzg LSI=G2M RCAR_DRAM_SPLIT=2\
+       RCAR_LOSSY_ENABLE=1 SPD="none" MBEDTLS_DIR=$mbedtls
+
+
+Install Procedure
+~~~~~~~~~~~~~~~~~
+
+- Boot the board in Mini-monitor mode and enable access to the
+  QSPI flash.
+
+
+- Use the flash_writer utility[2] to flash all the SREC files.
+
+[2] https://github.com/renesas-rz/rzg2_flash_writer
+
+
+Boot trace
+----------
+::
+
+   INFO:    ARM GICv2 driver initialized
+   NOTICE:  BL2: RZ/G2 Initial Program Loader(CA57) Rev.2.0.6
+   NOTICE:  BL2: PRR is RZ/G2M Ver.1.3
+   NOTICE:  BL2: Board is HiHope RZ/G2M Rev.4.0
+   NOTICE:  BL2: Boot device is QSPI Flash(40MHz)
+   NOTICE:  BL2: LCM state is unknown
+   NOTICE:  BL2: DDR3200(rev.0.40)
+   NOTICE:  BL2: [COLD_BOOT]
+   NOTICE:  BL2: DRAM Split is 2ch
+   NOTICE:  BL2: QoS is default setting(rev.0.19)
+   NOTICE:  BL2: DRAM refresh interval 1.95 usec
+   NOTICE:  BL2: Periodic Write DQ Training
+   NOTICE:  BL2: CH0: 400000000 - 47fffffff, 2 GiB
+   NOTICE:  BL2: CH2: 600000000 - 67fffffff, 2 GiB
+   NOTICE:  BL2: Lossy Decomp areas
+   NOTICE:       Entry 0: DCMPAREACRAx:0x80000540 DCMPAREACRBx:0x570
+   NOTICE:       Entry 1: DCMPAREACRAx:0x40000000 DCMPAREACRBx:0x0
+   NOTICE:       Entry 2: DCMPAREACRAx:0x20000000 DCMPAREACRBx:0x0
+   NOTICE:  BL2: FDT at 0xe631db30
+   NOTICE:  BL2: v2.3(release):v2.4-rc0-2-g1433701e5
+   NOTICE:  BL2: Built : 13:45:26, Nov  7 2020
+   NOTICE:  BL2: Normal boot
+   INFO:    BL2: Doing platform setup
+   INFO:    BL2: Loading image id 3
+   NOTICE:  BL2: dst=0xe631d200 src=0x8180000 len=512(0x200)
+   NOTICE:  BL2: dst=0x43f00000 src=0x8180400 len=6144(0x1800)
+   WARNING: r-car ignoring the BL31 size from certificate,using RCAR_TRUSTED_SRAM_SIZE instead
+   INFO:    Loading image id=3 at address 0x44000000
+   NOTICE:  rcar_file_len: len: 0x0003e000
+   NOTICE:  BL2: dst=0x44000000 src=0x81c0000 len=253952(0x3e000)
+   INFO:    Image id=3 loaded: 0x44000000 - 0x4403e000
+   INFO:    BL2: Loading image id 5
+   INFO:    Loading image id=5 at address 0x50000000
+   NOTICE:  rcar_file_len: len: 0x00100000
+   NOTICE:  BL2: dst=0x50000000 src=0x8300000 len=1048576(0x100000)
+   INFO:    Image id=5 loaded: 0x50000000 - 0x50100000
+   NOTICE:  BL2: Booting BL31
+   INFO:    Entry point address = 0x44000000
+   INFO:    SPSR = 0x3cd
+
+
+   U-Boot 2021.01-rc1-00244-gac37e14fbd (Nov 04 2020 - 20:03:34 +0000)
+
+   CPU: Renesas Electronics R8A774A1 rev 1.3
+   Model: HopeRun HiHope RZ/G2M with sub board
+   DRAM:  3.9 GiB
+   MMC:   mmc@ee100000: 0, mmc@ee160000: 1
+   Loading Environment from MMC... OK
+   In:    serial@e6e88000
+   Out:   serial@e6e88000
+   Err:   serial@e6e88000
+   Net:   eth0: ethernet@e6800000
+   Hit any key to stop autoboot:  0
+   =>
diff --git a/docs/plat/stm32mp1.rst b/docs/plat/stm32mp1.rst
index f597460..af302c6 100644
--- a/docs/plat/stm32mp1.rst
+++ b/docs/plat/stm32mp1.rst
@@ -37,6 +37,17 @@
 for ROM code is able to load this image.
 Tool stm32image can be used to prepend this header to the generated TF-A binary.
 
+Boot with FIP
+~~~~~~~~~~~~~
+The use of FIP is now the recommended way to boot STM32MP1 platform.
+Only BL2 (with STM32 header) is loaded by ROM code. The other binaries are
+inside the FIP binary: BL32 (SP_min or OP-TEE), U-Boot and their respective
+device tree blobs.
+
+STM32IMAGE bootchain
+~~~~~~~~~~~~~~~~~~~~
+Although still supported, this way of booting is not recommended.
+Pease use FIP instead.
 At compilation step, BL2, BL32 and DTB file are linked together in a single
 binary. The stm32image tool is also generated and the header is added to TF-A
 binary. This binary file with header is named tf-a-stm32mp157c-ev1.stm32.
@@ -55,15 +66,17 @@
                |       ...       |
                |                 |
     0x2FFC0000 +-----------------+ \
-               |                 | |
-               |       ...       | |
-               |                 | |
-    0x2FFD8000 +-----------------+ |
-               |    TF-A DTB     | | Embedded SRAM
-    0x2FFDC000 +-----------------+ |
-               |       BL2       | |
-    0x2FFEF000 +-----------------+ |
+               |     BL32 DTB    | |
+    0x2FFC5000 +-----------------+ |
                |       BL32      | |
+    0x2FFDF000 +-----------------+ |
+               |       ...       | |
+    0x2FFE3000 +-----------------+ |
+               |     BL2 DTB     | | Embedded SRAM
+    0x2FFEA000 +-----------------+ |
+               |       BL2       | |
+    0x2FFFF000 +-----------------+ |
+               |  SCMI mailbox   | |
     0x30000000 +-----------------+ /
                |                 |
                |       ...       |
@@ -95,28 +108,118 @@
 ------------------
 Boot media(s) supported by BL2 must be specified in the build command.
 Available storage medias are:
+
 - ``STM32MP_SDMMC``
 - ``STM32MP_EMMC``
 - ``STM32MP_RAW_NAND``
 - ``STM32MP_SPI_NAND``
 - ``STM32MP_SPI_NOR``
 
-To build with SP_min and support for all bootable devices:
+Boot with FIP
+~~~~~~~~~~~~~
+You need to build BL2, BL32 (SP_min or OP-TEE) and BL33 (U-Boot) before building FIP binary.
+
+U-Boot
+______
 
 .. code:: bash
 
-    make CROSS_COMPILE=arm-linux-gnueabihf- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 AARCH32_SP=sp_min STM32MP_SDMMC=1 STM32MP_EMMC=1 STM32MP_RAW_NAND=1 STM32MP_SPI_NAND=1
-    STM32MP_SPI_NOR=1 DTB_FILE_NAME=stm32mp157c-ev1.dtb
     cd <u-boot_directory>
     make stm32mp15_trusted_defconfig
     make DEVICE_TREE=stm32mp157c-ev1 all
 
-To build TF-A with OP-TEE support for all bootable devices:
+OP-TEE (optional)
+_________________
+
 .. code:: bash
 
-    make CROSS_COMPILE=arm-linux-gnueabihf- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 AARCH32_SP=optee STM32MP_SDMMC=1 STM32MP_EMMC=1 STM32MP_RAW_NAND=1 STM32MP_SPI_NAND=1 STM32MP_SPI_NOR=1 DTB_FILE_NAME=stm32mp157c-ev1.dtb
     cd <optee_directory>
-    make CROSS_COMPILE=arm-linux-gnueabihf- ARCH=arm PLATFORM=stm32mp1 CFG_EMBED_DTB_SOURCE_FILE=stm32mp157c-ev1.dts
+    make CROSS_COMPILE=arm-linux-gnueabihf- ARCH=arm PLATFORM=stm32mp1 \
+        CFG_EMBED_DTB_SOURCE_FILE=stm32mp157c-ev1.dts
+
+
+TF-A BL32 (SP_min)
+__________________
+If you choose not to use OP-TEE, you can use TF-A SP_min.
+To build TF-A BL32, and its device tree file:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-none-eabi- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        AARCH32_SP=sp_min DTB_FILE_NAME=stm32mp157c-ev1.dtb bl32 dtbs
+
+TF-A BL2
+________
+To build TF-A BL2 with its STM32 header for SD-card boot:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-none-eabi- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        DTB_FILE_NAME=stm32mp157c-ev1.dtb STM32MP_SDMMC=1
+
+For other boot devices, you have to replace STM32MP_SDMMC in the previous command
+with the desired device flag.
+
+This BL2 is independent of the BL32 used (SP_min or OP-TEE)
+
+
+FIP
+___
+With BL32 SP_min:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-none-eabi- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        AARCH32_SP=sp_min \
+        DTB_FILE_NAME=stm32mp157c-ev1.dtb \
+        BL33=<u-boot_directory>/u-boot-nodtb.bin \
+        BL33_CFG=<u-boot_directory>/u-boot.dtb \
+        fip
+
+With OP-TEE:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-none-eabi- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        AARCH32_SP=optee \
+        DTB_FILE_NAME=stm32mp157c-ev1.dtb \
+        BL33=<u-boot_directory>/u-boot-nodtb.bin \
+        BL33_CFG=<u-boot_directory>/u-boot.dtb \
+        BL32=<optee_directory>/tee-header_v2.bin \
+        BL32_EXTRA1=<optee_directory>/tee-pager_v2.bin
+        BL32_EXTRA2=<optee_directory>/tee-pageable_v2.bin
+        fip
+
+
+STM32IMAGE bootchain
+~~~~~~~~~~~~~~~~~~~~
+You need to add the following flag to the make command:
+``STM32MP_USE_STM32IMAGE=1``
+
+To build with SP_min and support for SD-card boot:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-linux-gnueabihf- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        AARCH32_SP=sp_min STM32MP_SDMMC=1 DTB_FILE_NAME=stm32mp157c-ev1.dtb \
+        STM32MP_USE_STM32IMAGE=1
+
+    cd <u-boot_directory>
+    make stm32mp15_trusted_defconfig
+    make DEVICE_TREE=stm32mp157c-ev1 all
+
+To build TF-A with OP-TEE support for SD-card boot:
+
+.. code:: bash
+
+    make CROSS_COMPILE=arm-linux-gnueabihf- PLAT=stm32mp1 ARCH=aarch32 ARM_ARCH_MAJOR=7 \
+        AARCH32_SP=optee STM32MP_SDMMC=1 DTB_FILE_NAME=stm32mp157c-ev1.dtb \
+        STM32MP_USE_STM32IMAGE=1
+
+    cd <optee_directory>
+    make CROSS_COMPILE=arm-linux-gnueabihf- ARCH=arm PLATFORM=stm32mp1 \
+        CFG_EMBED_DTB_SOURCE_FILE=stm32mp157c-ev1.dts
+
     cd <u-boot_directory>
     make stm32mp15_trusted_defconfig
     make DEVICE_TREE=stm32mp157c-ev1 all
@@ -130,7 +233,19 @@
 Populate SD-card
 ----------------
 
-The SD-card has to be formated with GPT.
+Boot with FIP
+~~~~~~~~~~~~~
+The SD-card has to be formatted with GPT.
+It should contain at least those partitions:
+
+- fsbl: to copy the tf-a-stm32mp157c-ev1.stm32 binary (BL2)
+- fip: which contains the FIP binary
+
+Usually, two copies of fsbl are used (fsbl1 and fsbl2) instead of one partition fsbl.
+
+STM32IMAGE bootchain
+~~~~~~~~~~~~~~~~~~~~
+The SD-card has to be formatted with GPT.
 It should contain at least those partitions:
 
 - fsbl: to copy the tf-a-stm32mp157c-ev1.stm32 binary
diff --git a/docs/plat/xilinx-versal.rst b/docs/plat/xilinx-versal.rst
index 57a363b..d65b048 100644
--- a/docs/plat/xilinx-versal.rst
+++ b/docs/plat/xilinx-versal.rst
@@ -19,6 +19,16 @@
 make RESET_TO_BL31=1 CROSS_COMPILE=aarch64-none-elf- PLAT=versal VERSAL_PLATFORM=versal_virt bl31
 ```
 
+To build TF-A for JTAG DCC console
+```bash
+make RESET_TO_BL31=1 CROSS_COMPILE=aarch64-none-elf- PLAT=versal bl31 VERSAL_CONSOLE=dcc
+```
+
+To build TF-A with Straight-Line Speculation(SLS)
+```bash
+make RESET_TO_BL31=1 CROSS_COMPILE=aarch64-none-elf- PLAT=versal bl31 HARDEN_SLS_ALL=1
+```
+
 Xilinx Versal platform specific build options
 ---------------------------------------------
 
diff --git a/docs/plat/xilinx-zynqmp.rst b/docs/plat/xilinx-zynqmp.rst
index 5db4488..79c2535 100644
--- a/docs/plat/xilinx-zynqmp.rst
+++ b/docs/plat/xilinx-zynqmp.rst
@@ -22,6 +22,12 @@
 
     make CROSS_COMPILE=aarch64-none-elf- PLAT=zynqmp SPD=tspd bl31 bl32
 
+To build TF-A for JTAG DCC console:
+
+.. code:: bash
+
+    make CROSS_COMPILE=aarch64-none-elf- PLAT=zynqmp RESET_TO_BL31=1 bl31 ZYNQMP_CONSOLE=dcc
+
 ZynqMP platform specific build options
 --------------------------------------
 
diff --git a/docs/process/coding-style.rst b/docs/process/coding-style.rst
index 94fd85e..be13b14 100644
--- a/docs/process/coding-style.rst
+++ b/docs/process/coding-style.rst
@@ -101,7 +101,7 @@
 parentheses.
 
 Control statements (``if``, ``for``, ``switch``, ``while``, etc) must be
-separated from the following open paranthesis by a single space. The previous
+separated from the following open parenthesis by a single space. The previous
 example illustrates this for an ``if`` statement.
 
 Line Length
diff --git a/docs/process/contributing.rst b/docs/process/contributing.rst
index 15c2b45..aa050da 100644
--- a/docs/process/contributing.rst
+++ b/docs/process/contributing.rst
@@ -29,6 +29,20 @@
 -  Make commits of logical units. See these general `Git guidelines`_ for
    contributing to a project.
 
+-  Ensure your commit messages comply with the `Conventional Commits`_
+   specification:
+
+   .. code::
+
+       <type>[optional scope]: <description>
+
+       [optional body]
+
+       [optional footer(s)]
+
+   You can use the tooling installed by the optional steps in the
+   :ref:`prerequisites <Prerequisites>` guide to validate this locally.
+
 -  Keep the commits on topic. If you need to fix another bug or make another
    enhancement, please address it on a separate topic branch.
 
@@ -195,6 +209,65 @@
       revert your patches and ask you to resubmit a reworked version of them or
       they may ask you to provide a fix-up patch.
 
+Add Build Configurations
+------------------------
+
+-  TF-A uses Jenkins tool for Continuous Integration and testing activities.
+   Various CI Jobs are deployed which run tests on every patch before being
+   merged. So each of your patches go through a series of checks before they
+   get merged on to the master branch.
+
+-  ``Coverity Scan analysis`` is one of the tests we perform on our source code
+   at regular intervals. We maintain a build script ``tf-cov-make`` which contains the
+   build configurations of various platforms in order to cover the entire source
+   code being analysed by Coverity.
+
+-  When you submit your patches for review containing new source files, please
+   ensure to include them for the ``Coverity Scan analysis`` by adding the
+   respective build configurations in the ``tf-cov-make`` build script.
+
+-  In this section you find the details on how to append your new build
+   configurations for Coverity Scan analysis:
+
+#. We maintain a separate repository named `tf-a-ci-scripts repository`_
+   for placing all the test scripts which will be executed by the CI Jobs.
+
+#. In this repository, ``tf-cov-make`` script is located at
+   ``tf-a-ci-scripts/script/tf-coverity/tf-cov-make``
+
+#. Edit `tf-cov-make`_ script by appending all the possible build configurations with
+   the specific ``build-flags`` relevant to your platform, so that newly added
+   source files get built and analysed by Coverity.
+
+#. For better understanding follow the below specified examples listed in the
+   ``tf-cov-make`` script.
+
+.. code:: shell
+
+    Example 1:
+    #Intel
+    make PLAT=stratix10 $(common_flags) all
+    make PLAT=agilex $(common_flags) all
+
+-  In the above example there are two different SoCs ``stratix`` and ``agilex``
+   under the Intel platform and the build configurations has been added suitably
+   to include most of their source files.
+
+.. code:: shell
+
+    Example 2:
+    #Hikey
+    make PLAT=hikey $(common_flags) ${TBB_OPTIONS} ENABLE_PMF=1 all
+    make PLAT=hikey960 $(common_flags) ${TBB_OPTIONS} all
+    make PLAT=poplar $(common_flags) all
+
+-  In this case for ``Hikey`` boards additional ``build-flags`` has been included
+   along with the ``commom_flags`` to cover most of the files relevant to it.
+
+-  Similar to this you can still find many other different build configurations
+   of various other platforms listed in the ``tf-cov-make`` script. Kindly refer
+   them and append your build configurations respectively.
+
 Binary Components
 -----------------
 
@@ -214,8 +287,9 @@
 
 --------------
 
-*Copyright (c) 2013-2020, Arm Limited and Contributors. All rights reserved.*
+*Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.*
 
+.. _Conventional Commits: https://www.conventionalcommits.org/en/v1.0.0
 .. _developer.trustedfirmware.org: https://developer.trustedfirmware.org
 .. _review.trustedfirmware.org: https://review.trustedfirmware.org
 .. _issue: https://developer.trustedfirmware.org/project/board/1/
@@ -228,3 +302,5 @@
 .. _Trusted Firmware binary repository: https://review.trustedfirmware.org/admin/repos/tf-binaries
 .. _tf-binaries-readme: https://git.trustedfirmware.org/tf-binaries.git/tree/readme.rst
 .. _TF-A mailing list: https://lists.trustedfirmware.org/mailman/listinfo/tf-a
+.. _tf-a-ci-scripts repository: https://git.trustedfirmware.org/ci/tf-a-ci-scripts.git/
+.. _tf-cov-make: https://git.trustedfirmware.org/ci/tf-a-ci-scripts.git/tree/script/tf-coverity/tf-cov-make
diff --git a/docs/resources/diagrams/FIP_in_a_GPT_image.png b/docs/resources/diagrams/FIP_in_a_GPT_image.png
new file mode 100644
index 0000000..4bafed9
--- /dev/null
+++ b/docs/resources/diagrams/FIP_in_a_GPT_image.png
Binary files differ
diff --git a/docs/resources/diagrams/MMU-600.png b/docs/resources/diagrams/MMU-600.png
new file mode 100644
index 0000000..9cbc243
--- /dev/null
+++ b/docs/resources/diagrams/MMU-600.png
Binary files differ
diff --git a/docs/resources/diagrams/arm-cca-software-arch.png b/docs/resources/diagrams/arm-cca-software-arch.png
new file mode 100755
index 0000000..979e083
--- /dev/null
+++ b/docs/resources/diagrams/arm-cca-software-arch.png
Binary files differ
diff --git a/docs/resources/diagrams/ff-a-spm-sel2.png b/docs/resources/diagrams/ff-a-spm-sel2.png
index 6479ff5..605fd9b 100644
--- a/docs/resources/diagrams/ff-a-spm-sel2.png
+++ b/docs/resources/diagrams/ff-a-spm-sel2.png
Binary files differ
diff --git a/docs/resources/diagrams/ffa-ns-interrupt-handling-managed-exit.png b/docs/resources/diagrams/ffa-ns-interrupt-handling-managed-exit.png
new file mode 100644
index 0000000..0619cf2
--- /dev/null
+++ b/docs/resources/diagrams/ffa-ns-interrupt-handling-managed-exit.png
Binary files differ
diff --git a/docs/resources/diagrams/ffa-ns-interrupt-handling-sp-preemption.png b/docs/resources/diagrams/ffa-ns-interrupt-handling-sp-preemption.png
new file mode 100644
index 0000000..f110028
--- /dev/null
+++ b/docs/resources/diagrams/ffa-ns-interrupt-handling-sp-preemption.png
Binary files differ
diff --git a/docs/resources/diagrams/ffa-secure-interrupt-handling-nwd.png b/docs/resources/diagrams/ffa-secure-interrupt-handling-nwd.png
new file mode 100755
index 0000000..c318610
--- /dev/null
+++ b/docs/resources/diagrams/ffa-secure-interrupt-handling-nwd.png
Binary files differ
diff --git a/docs/resources/diagrams/ffa-secure-interrupt-handling-swd.png b/docs/resources/diagrams/ffa-secure-interrupt-handling-swd.png
new file mode 100755
index 0000000..b62000d
--- /dev/null
+++ b/docs/resources/diagrams/ffa-secure-interrupt-handling-swd.png
Binary files differ
diff --git a/docs/resources/diagrams/plantuml/fip-secure-partitions.puml b/docs/resources/diagrams/plantuml/fip-secure-partitions.puml
index 40621db..9457e32 100644
--- a/docs/resources/diagrams/plantuml/fip-secure-partitions.puml
+++ b/docs/resources/diagrams/plantuml/fip-secure-partitions.puml
@@ -13,6 +13,7 @@
  ===
  UUID = xxx
  load_address = 0xaaa
+ owner = "Sip"
  ...
  ]
 }
@@ -24,9 +25,26 @@
  ===
  UUID = yyy
  load_address = 0xbbb
+ owner = "Plat"
  ]
 }
 
+artifact tb_fw_config.dts [
+ tb_fw_config.dts
+ ----
+ secure-partitions
+ ===
+ spkg_1 UUID
+ spkg_1 load_address
+ ---
+ spkg_2 UUID
+ spkg_2 load_address
+ ---
+ ...
+ ===
+ ...<rest of the nodes>
+]
+
 artifact config.json [
  SP_LAYOUT.json
  ===
@@ -41,31 +59,22 @@
 
 control sp_mk_generator
 
-artifact fconf_node [
- fconf_sp.dts
- ===
- spkg_1 UUID
- spkg_1 load_address
- ---
- spkg_2 UUID
- spkg_2 load_address
-]
-
 artifact sp_gen [
  sp_gen.mk
  ===
  FDT_SOURCE = ...
  SPTOOL_ARGS = ...
- FIP_ARG = ...
+ FIP_ARGS = ...
+ CRT_ARGS = ...
 ]
 
 control dtc
 control sptool
 
-artifact FW_CONFIG
+artifact tb_fw_config.dtb
 
 artifact spkg_1 [
- spkg_1.bin
+ sp1.pkg
  ===
  <i>header</i>
  ---
@@ -75,7 +84,7 @@
 ]
 
 artifact spkg_2 [
- spkg_2.bin
+ sp2.pkg
  ===
  <i>header</i>
  ---
@@ -84,18 +93,47 @@
  binary
 ]
 
+artifact signed_tb_fw_config.dtb [
+ tb_fw_config.dtb (signed)
+]
+
+artifact signed_spkg_1 [
+ sp1.pkg (signed)
+ ===
+ <i>header</i>
+ ---
+ manifest
+ ---
+ binary
+ ---
+ <i>signature</I>
+]
+
+artifact signed_spkg_2 [
+ sp2.pkg (signed)
+ ===
+ <i>header</i>
+ ---
+ manifest
+ ---
+ binary
+ ---
+ <i>signature</I>
+]
+
+control crttool
 control fiptool
 
 artifact fip [
  fip.bin
  ===
- FW_CONFIG.dtb
+ tb_fw_config.dtb (signed)
  ---
  ...
  ---
- SPKG1
+ sp1.pkg  (signed & SiP owned)
  ---
- SPKG2
+ sp2.pkg  (signed & Platform owned)
  ---
  ...
 ]
@@ -103,20 +141,27 @@
 config.json .up.> SP_vendor_1
 config.json .up.> SP_vendor_2
 config.json --> sp_mk_generator
-sp_mk_generator --> fconf_node
 sp_mk_generator --> sp_gen
-
+sp_gen --> fiptool
+sp_gen --> cert_create
 sp_gen --> sptool
+
 sptool --> spkg_1
 sptool --> spkg_2
 
-fconf_node -down-> dtc
-dtc --> FW_CONFIG
+spkg_1 --> cert_create
+spkg_2 --> cert_create
+cert_create --> signed_spkg_1
+cert_create --> signed_spkg_2
 
-sp_gen --> fiptool
-FW_CONFIG --> fiptool
-spkg_1 -down-> fiptool
-spkg_2 -down-> fiptool
+tb_fw_config.dts --> dtc
+dtc --> tb_fw_config.dtb
+tb_fw_config.dtb --> cert_create
+cert_create --> signed_tb_fw_config.dtb
+
+signed_tb_fw_config.dtb --> fiptool
+signed_spkg_1 -down-> fiptool
+signed_spkg_2 -down-> fiptool
 fiptool -down-> fip
 
 @enduml
diff --git a/docs/resources/diagrams/plantuml/spm_dfd.puml b/docs/resources/diagrams/plantuml/spm_dfd.puml
new file mode 100644
index 0000000..ad4996e
--- /dev/null
+++ b/docs/resources/diagrams/plantuml/spm_dfd.puml
@@ -0,0 +1,82 @@
+/'
+ ' Copyright (c) 2021, Arm Limited. All rights reserved.
+ '
+ ' SPDX-License-Identifier: BSD-3-Clause
+ '/
+
+/'
+TF-A SPMC Data Flow Diagram
+'/
+
+@startuml
+digraph tfa_dfd {
+
+    # Allow arrows to end on cluster boundaries
+    compound=true
+
+    # Default settings for edges and nodes
+    edge [minlen=2 color="#8c1b07"]
+    node [fillcolor="#ffb866" style=filled shape=box fixedsize=true width=1.6 height=0.7]
+
+    # Nodes outside of the trust boundary
+    nsec [label="NS Client"]
+    ddr  [label="External memory (DDR)"]
+
+    # Trust boundary cluster
+    subgraph cluster_trusted {
+        graph [style=dashed color="#f22430"]
+
+        # HW IPs cluster
+        subgraph cluster_ip {
+            label ="Hardware IPs";
+            graph [style=filled color="#000000" fillcolor="#ffd29e"]
+
+            rank="same"
+            gic [label="GIC" width=1.2 height=0.5]
+            smmu [label="SMMU" width=1.2 height=0.5]
+            uart [label="UART" width=1.2 height=0.5]
+	    pe [label="PE" width=1.2 height=0.5]
+        }
+
+        # TF-A cluster
+        subgraph cluster_tfa {
+            label ="EL3 monitor";
+            graph [style=filled color="#000000" fillcolor="#faf9cd"]
+
+            bl31 [label="BL31" fillcolor="#ddffb3"];
+            spmd [label="SPMD" fillcolor="#ddffb3" height=1]
+        }
+
+        # SPMC cluster
+        subgraph cluster_spmc {
+            label ="SPMC";
+            graph [style=filled color="#000000" fillcolor="#faf9cd"]
+
+            spmc [label="SPMC" fillcolor="#ddffb3" height=1]
+        }
+	bl2 [label="BL2" width=1.2 height=0.5]
+    }
+
+    # Secure Partitions cluster
+    subgraph cluster_sp {
+        label ="Secure Partitions";
+        graph [style=filled color="#000000" fillcolor="#faf9cd"]
+
+        sp1 [label="SP1" fillcolor="#ddffb3" height=1]
+        sp2 [label="SP2" fillcolor="#ddffb3" height=1]
+        spn [label="SP..." fillcolor="#ddffb3" height=1]
+    }
+
+    # Interactions between nodes
+    sp1 -> spmc [dir="both" label="DF1"]
+    spmc -> spmd [dir="both" label="DF2"]
+    spmd -> nsec [dir="both" label="DF3"]
+    sp1 -> sp2 [dir="both" label="DF4"]
+    spmc -> smmu [lhead=cluster_spmc label="DF5"]
+    bl2 -> spmc [lhead=cluster_spmc label="DF6"]
+    bl2 -> spn [lhead=cluster_spmc label="DF6"]
+    sp1 -> ddr [dir="both"  label="DF7"]
+    spmc -> ddr [dir="both"  label="DF7"]
+}
+
+@enduml
diff --git a/docs/resources/diagrams/plantuml/tfa_dfd.puml b/docs/resources/diagrams/plantuml/tfa_dfd.puml
new file mode 100644
index 0000000..0007911
--- /dev/null
+++ b/docs/resources/diagrams/plantuml/tfa_dfd.puml
@@ -0,0 +1,66 @@
+/'
+ ' Copyright (c) 2021, Arm Limited. All rights reserved.
+ '
+ ' SPDX-License-Identifier: BSD-3-Clause
+ '/
+
+/'
+TF-A Data Flow Diagram
+'/
+
+@startuml
+digraph tfa_dfd {
+
+    # Arrange nodes from left to right
+    rankdir="LR"
+
+    # Allow arrows to end on cluster boundaries
+    compound=true
+
+    # Default settings for edges and nodes
+    edge [minlen=2 color="#8c1b07"]
+    node [fillcolor="#ffb866" style=filled shape=box fixedsize=true width=1.6 height=0.7]
+
+    # Nodes outside of the trust boundary
+    nsec [label="Non-secure\nClients"]
+    sec [label="Secure\nClients"]
+    dbg [label="Debug & Trace"]
+    logs [label="Logs\n(UART)"]
+    nvm [label="Non-volatile\nMemory"]
+
+    # Trust boundary cluster
+    subgraph cluster_trusted{
+        graph [style=dashed color="#f22430"]
+
+        # HW IPs cluster
+        subgraph cluster_ip{
+            label ="Hardware IPs";
+            graph [style=filled color="#000000" fillcolor="#ffd29e"]
+
+            rank="same"
+            gic [label="GIC" width=1.2 height=0.5]
+            tzc [label="TZ\nController" width=1.2 height=0.5]
+            etc [label="..." shape=none style=none height=0.5]
+        }
+
+        # TF-A cluster
+        subgraph cluster_tfa{
+            label ="TF-A";
+            graph [style=filled color="#000000" fillcolor="#faf9cd"]
+
+            bl1 [label="Boot ROM\n(BL1)" fillcolor="#ddffb3"];
+            bl2 [label="Trusted Boot\nFirmware\n(BL2)" fillcolor="#ddffb3" height=1]
+            bl31 [label="TF-A Runtime\n(BL31)" fillcolor="#ddffb3"]
+        }
+    }
+
+    # Interactions between nodes
+    nvm -> bl31 [lhead=cluster_tfa label="DF1"]
+    logs -> bl31 [dir="back" lhead=cluster_tfa label="DF2"]
+    dbg -> bl2 [dir="both" lhead=cluster_tfa label="DF3"]
+    sec -> bl2 [dir="both" lhead=cluster_tfa label="DF4"]
+    nsec -> bl1 [dir="both" lhead=cluster_tfa, label="DF5"]
+    bl2 ->  tzc [dir="both" ltail=cluster_tfa lhead=cluster_ip label="DF6" minlen=1]
+}
+
+@enduml
diff --git a/docs/resources/diagrams/spm-threat-model-trust-boundaries.png b/docs/resources/diagrams/spm-threat-model-trust-boundaries.png
new file mode 100644
index 0000000..58898c5
--- /dev/null
+++ b/docs/resources/diagrams/spm-threat-model-trust-boundaries.png
Binary files differ
diff --git a/docs/threat_model/index.rst b/docs/threat_model/index.rst
new file mode 100644
index 0000000..b5ede69
--- /dev/null
+++ b/docs/threat_model/index.rst
@@ -0,0 +1,21 @@
+Threat Model
+============
+
+Threat modeling is an important part of Secure Development Lifecycle (SDL)
+that helps us identify potential threats and mitigations affecting a system.
+
+In the next sections, we first give a description of the target of evaluation
+using a data flow diagram. Then we provide a list of threats we have identified
+based on the data flow diagram and potential threat mitigations.
+
+.. toctree::
+   :maxdepth: 1
+   :caption: Contents
+   :numbered:
+
+   threat_model
+   threat_model_spm
+
+--------------
+
+*Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.*
diff --git a/docs/threat_model/threat_model.rst b/docs/threat_model/threat_model.rst
new file mode 100644
index 0000000..4a31e79
--- /dev/null
+++ b/docs/threat_model/threat_model.rst
@@ -0,0 +1,788 @@
+Generic threat model
+********************
+
+************************
+Introduction
+************************
+This document provides a generic threat model for TF-A firmware.
+
+.. note::
+
+ This threat model doesn't consider Root and Realm worlds introduced by
+ :ref:`Realm Management Extension (RME)`.
+
+************************
+Target of Evaluation
+************************
+In this threat model, the target of evaluation is the Trusted
+Firmware for A-class Processors (TF-A). This includes the boot ROM (BL1),
+the trusted boot firmware (BL2) and the runtime EL3 firmware (BL31) as
+shown on Figure 1. Everything else on Figure 1 is outside of the scope of
+the evaluation.
+
+TF-A can be configured in various ways. In this threat model we consider
+only the most basic configuration. To that end we make the following
+assumptions:
+
+- All TF-A images are run from either ROM or on-chip trusted SRAM. This means
+  TF-A is not vulnerable to an attacker that can probe or tamper with off-chip
+  memory.
+
+- Trusted boot is enabled. This means an attacker can't boot arbitrary images
+  that are not approved by platform providers.
+
+- There is no Secure-EL2. We don't consider threats that may come with
+  Secure-EL2 software.
+
+Data Flow Diagram
+======================
+Figure 1 shows a high-level data flow diagram for TF-A. The diagram
+shows a model of the different components of a TF-A-based system and
+their interactions with TF-A. A description of each diagram element
+is given on Table 1. On the diagram, the red broken lines indicate
+trust boundaries. Components outside of the broken lines
+are considered untrusted by TF-A.
+
+.. uml:: ../resources/diagrams/plantuml/tfa_dfd.puml
+  :caption: Figure 1: TF-A Data Flow Diagram
+
+.. table:: Table 1: TF-A Data Flow Diagram Description
+
+  +-----------------+--------------------------------------------------------+
+  | Diagram Element | Description                                            |
+  +=================+========================================================+
+  |       ``DF1``   | | At boot time, images are loaded from non-volatile    |
+  |                 |   memory and verified by TF-A boot firmware. These     |
+  |                 |   images include TF-A BL2 and BL31 images, as well as  |
+  |                 |   other secure and non-secure images.                  |
+  +-----------------+--------------------------------------------------------+
+  |       ``DF2``   | | TF-A log system framework outputs debug messages     |
+  |                 |   over a UART interface.                               |
+  +-----------------+--------------------------------------------------------+
+  |       ``DF3``   | | Debug and trace IP on a platform can allow access    |
+  |                 |   to registers and memory of TF-A.                     |
+  +-----------------+--------------------------------------------------------+
+  |       ``DF4``   | | Secure world software (e.g. trusted OS) interact     |
+  |                 |   with TF-A through SMC call interface and/or shared   |
+  |                 |   memory.                                              |
+  +-----------------+--------------------------------------------------------+
+  |       ``DF5``   | | Non-secure world software (e.g. rich OS) interact    |
+  |                 |   with TF-A through SMC call interface and/or shared   |
+  |                 |   memory.                                              |
+  +-----------------+--------------------------------------------------------+
+  |       ``DF6``   | | This path represents the interaction between TF-A and|
+  |                 |   various hardware IPs such as TrustZone controller    |
+  |                 |   and GIC. At boot time TF-A configures/initializes the|
+  |                 |   IPs and interacts with them at runtime through       |
+  |                 |   interrupts and registers.                            |
+  +-----------------+--------------------------------------------------------+
+
+
+*********************
+Threat Analysis
+*********************
+In this section we identify and provide assessment of potential threats to TF-A
+firmware. The threats are identified for each diagram element on the
+data flow diagram above.
+
+For each threat, we identify the *asset* that is under threat, the
+*threat agent* and the *threat type*. Each threat is given a *risk rating*
+that represents the impact and likelihood of that threat. We also discuss
+potential mitigations.
+
+Assets
+==================
+We have identified the following assets for TF-A:
+
+.. table:: Table 2: TF-A Assets
+
+  +--------------------+---------------------------------------------------+
+  | Asset              | Description                                       |
+  +====================+===================================================+
+  | ``Sensitive Data`` | | These include sensitive data that an attacker   |
+  |                    |   must not be able to tamper with (e.g. the Root  |
+  |                    |   of Trust Public Key) or see (e.g. secure logs,  |
+  |                    |   debugging information such as crash reports).   |
+  +--------------------+---------------------------------------------------+
+  | ``Code Execution`` | | This represents the requirement that the        |
+  |                    |   platform should run only TF-A code approved by  |
+  |                    |   the platform provider.                          |
+  +--------------------+---------------------------------------------------+
+  | ``Availability``   | | This represents the requirement that TF-A       |
+  |                    |   services should always be available for use.    |
+  +--------------------+---------------------------------------------------+
+
+Threat Agents
+=====================
+To understand the attack surface, it is important to identify potential
+attackers, i.e. attack entry points. The following threat agents are
+in scope of this threat model.
+
+.. table:: Table 3: Threat Agents
+
+  +-------------------+-------------------------------------------------------+
+  | Threat Agent      | Description                                           |
+  +===================+=======================================================+
+  |   ``NSCode``      | | Malicious or faulty code running in the Non-secure  |
+  |                   |   world, including NS-EL0 NS-EL1 and NS-EL2 levels    |
+  +-------------------+-------------------------------------------------------+
+  |   ``SecCode``     | | Malicious or faulty code running in the secure      |
+  |                   |   world, including S-EL0 and S-EL1 levels             |
+  +-------------------+-------------------------------------------------------+
+  |   ``AppDebug``    | | Physical attacker using  debug signals to access    |
+  |                   |   TF-A resources                                      |
+  +-------------------+-------------------------------------------------------+
+  | ``PhysicalAccess``| | Physical attacker having access to external device  |
+  |                   |   communication bus and to external flash             |
+  |                   |   communication bus using common hardware             |
+  +-------------------+-------------------------------------------------------+
+
+.. note::
+
+  In this threat model an advanced physical attacker that has the capability
+  to tamper with a hardware (e.g. "rewiring" a chip using a focused
+  ion beam (FIB) workstation or decapsulate the chip using chemicals) is
+  considered out-of-scope.
+
+Threat Types
+========================
+In this threat model we categorize threats using the `STRIDE threat
+analysis technique`_. In this technique a threat is categorized as one
+or more of these types: ``Spoofing``, ``Tampering``, ``Repudiation``,
+``Information disclosure``, ``Denial of service`` or
+``Elevation of privilege``.
+
+Threat Risk Ratings
+========================
+For each threat identified, a risk rating that ranges
+from *informational* to *critical* is given based on the likelihood of the
+threat occuring if a mitigation is not in place, and the impact of the
+threat (i.e. how severe the consequences could be). Table 4 explains each
+rating in terms of score, impact and likelihood.
+
+.. table:: Table 4: Rating and score as applied to impact and likelihood
+
+  +-----------------------+-------------------------+---------------------------+
+  | **Rating (Score)**    | **Impact**              | **Likelihood**            |
+  +=======================+=========================+===========================+
+  | ``Critical (5)``      | | Extreme impact to     | | Threat is almost        |
+  |                       |   entire organization   |   certain to be exploited.|
+  |                       |   if exploited.         |                           |
+  |                       |                         | | Knowledge of the threat |
+  |                       |                         |   and how to exploit it   |
+  |                       |                         |   are in the public       |
+  |                       |                         |   domain.                 |
+  +-----------------------+-------------------------+---------------------------+
+  | ``High (4)``          | | Major impact to entire| | Threat is relatively    |
+  |                       |   organization or single|   easy to detect and      |
+  |                       |   line of business if   |   exploit by an attacker  |
+  |                       |   exploited             |   with little skill.      |
+  +-----------------------+-------------------------+---------------------------+
+  | ``Medium (3)``        | | Noticeable impact to  | | A knowledgeable insider |
+  |                       |   line of business if   |   or expert attacker could|
+  |                       |   exploited.            |   exploit the threat      |
+  |                       |                         |   without much difficulty.|
+  +-----------------------+-------------------------+---------------------------+
+  | ``Low (2)``           | | Minor damage if       | | Exploiting the threat   |
+  |                       |   exploited or could    |   would require           |
+  |                       |   be used in conjunction|   considerable expertise  |
+  |                       |   with other            |   and resources           |
+  |                       |   vulnerabilities to    |                           |
+  |                       |   perform a more serious|                           |
+  |                       |   attack                |                           |
+  +-----------------------+-------------------------+---------------------------+
+  | ``Informational (1)`` | | Poor programming      | | Threat is not likely    |
+  |                       |   practice or poor      |   to be exploited on its  |
+  |                       |   design decision that  |   own, but may be used to |
+  |                       |   may not represent an  |   gain information for    |
+  |                       |   immediate risk on its |   launching another       |
+  |                       |   own, but may have     |   attack                  |
+  |                       |   security implications |                           |
+  |                       |   if multiplied and/or  |                           |
+  |                       |   combined with other   |                           |
+  |                       |   threats.              |                           |
+  +-----------------------+-------------------------+---------------------------+
+
+Aggregate risk scores are assigned to identified threats;
+specifically, the impact score multiplied by the likelihood score.
+For example, a threat with high likelihood and low impact would have an
+aggregate risk score of eight (8); that is, four (4) for high likelihood
+multiplied by two (2) for low impact. The aggregate risk score determines
+the finding's overall risk level, as shown in the following table.
+
+.. table:: Table 5: Overall risk levels and corresponding aggregate scores
+
+  +---------------------+-----------------------------------+
+  | Overall Risk Level  | Aggregate Risk Score              |
+  |                     | (Impact multiplied by Likelihood) |
+  +=====================+===================================+
+  | Critical            | 20–25                             |
+  +---------------------+-----------------------------------+
+  | High                | 12–19                             |
+  +---------------------+-----------------------------------+
+  | Medium              | 6–11                              |
+  +---------------------+-----------------------------------+
+  | Low                 | 2–5                               |
+  +---------------------+-----------------------------------+
+  | Informational       | 1                                 |
+  +---------------------+-----------------------------------+
+
+The likelihood and impact of a threat depends on the
+target environment in which TF-A is running. For example, attacks
+that require physical access are unlikely in server environments while
+they are more common in Internet of Things(IoT) environments.
+In this threat model we consider three target environments:
+``Internet of Things(IoT)``, ``Mobile`` and ``Server``.
+
+Threat Assessment
+============================
+The following threats were identified by applying STRIDE analysis on
+each diagram element of the data flow diagram.
+
++------------------------+----------------------------------------------------+
+| ID                     | 01                                                 |
++========================+====================================================+
+| ``Threat``             | | **An attacker can mangle firmware images to      |
+|                        |   execute arbitrary code**                         |
+|                        |                                                    |
+|                        | | Some TF-A images are loaded from external        |
+|                        |   storage. It is possible for an attacker to access|
+|                        |   the external flash memory and change its contents|
+|                        |   physically, through the Rich OS, or using the    |
+|                        |   updating mechanism to modify the non-volatile    |
+|                        |   images to execute arbitrary code.                |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF4, DF5                                      |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | BL2, BL31                                          |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Code Execution                                     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | PhysicalAccess, NSCode, SecCode                    |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering, Elevation of Privilege                  |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        | ``Server``       | ``IoT``         | ``Mobile``    |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | Critical (5)     | Critical (5)    | Critical (5)  |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Critical (5)     | Critical (5)    | Critical (5)  |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | Critical (25)    | Critical (25)   | Critical (25) |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | | TF-A implements the `Trusted Board Boot (TBB)`_  |
+|                        |   feature which prevents malicious firmware from   |
+|                        |   running on the platform by authenticating all    |
+|                        |   firmware images. In addition to this, the TF-A   |
+|                        |   boot firmware performs extra checks on           |
+|                        |   unauthenticated data, such as FIP metadata, prior|
+|                        |   to use.                                          |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 02                                                 |
++========================+====================================================+
+| ``Threat``             | | **An attacker may attempt to boot outdated,      |
+|                        |   potentially vulnerable firmware image**          |
+|                        |                                                    |
+|                        | | When updating firmware, an attacker may attempt  |
+|                        |   to rollback to an older version that has unfixed |
+|                        |   vulnerabilities.                                 |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF4, DF5                                      |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | BL2, BL31                                          |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Code Execution                                     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | PhysicalAccess, NSCode, SecCode                    |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering                                          |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        | ``Server``       | ``IoT``         | ``Mobile``    |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | Critical (5)     | Critical (5)    | Critical (5)  |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Critical (5)     | Critical (5)    | Critical (5)  |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | Critical (25)    | Critical (25)   | Critical (25) |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | | TF-A supports anti-rollback protection using     |
+|                        |   non-volatile counters (NV counters) as required  |
+|                        |   by `TBBR-Client specification`_. After a firmware|
+|                        |   image is validated, the image revision number    |
+|                        |   taken from a certificate extension field is      |
+|                        |   compared with the corresponding NV counter stored|
+|                        |   in hardware to make sure the new counter value is|
+|                        |   larger or equal to the current counter value.    |
+|                        |   Platforms must implement this protection using   |
+|                        |   platform specific hardware NV counters.          |
++------------------------+----------------------------------------------------+
+
++------------------------+-------------------------------------------------------+
+| ID                     | 03                                                    |
++========================+=======================================================+
+| ``Threat``             | |  **An attacker can use Time-of-Check-Time-of-Use    |
+|                        |   (TOCTOU) attack to bypass image authentication      |
+|                        |   during the boot process**                           |
+|                        |                                                       |
+|                        | | Time-of-Check-Time-of-Use (TOCTOU) threats occur    |
+|                        |   when the security check is produced before the time |
+|                        |   the resource is accessed. If an attacker is sitting |
+|                        |   in the middle of the off-chip images, they could    |
+|                        |   change the binary containing executable code right  |
+|                        |   after the integrity and authentication check has    |
+|                        |   been performed.                                     |
++------------------------+-------------------------------------------------------+
+| ``Diagram Elements``   | DF1                                                   |
++------------------------+-------------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2                                              |
+| Components``           |                                                       |
++------------------------+-------------------------------------------------------+
+| ``Assets``             | Code Execution, Sensitive Data                        |
++------------------------+-------------------------------------------------------+
+| ``Threat Agent``       | PhysicalAccess                                        |
++------------------------+-------------------------------------------------------+
+| ``Threat Type``        | Elevation of Privilege                                |
++------------------------+---------------------+-----------------+---------------+
+| ``Application``        | ``Server``          | ``IoT``         | ``Mobile``    |
++------------------------+---------------------+-----------------+---------------+
+| ``Impact``             | N/A                 | Critical (5)    | Critical (5)  |
++------------------------+---------------------+-----------------+---------------+
+| ``Likelihood``         | N/A                 | Medium (3)      | Medium (3)    |
++------------------------+---------------------+-----------------+---------------+
+| ``Total Risk Rating``  | N/A                 | High (15)       | High (15)     |
++------------------------+---------------------+-----------------+---------------+
+| ``Mitigations``        | | TF-A boot firmware copies image to on-chip          |
+|                        |   memory before authenticating an image.              |
++------------------------+-------------------------------------------------------+
+
++------------------------+-------------------------------------------------------+
+| ID                     | 04                                                    |
++========================+=======================================================+
+| ``Threat``             | | **An attacker with physical access can execute      |
+|                        |   arbitrary image by bypassing the signature          |
+|                        |   verification stage using glitching techniques**     |
+|                        |                                                       |
+|                        | | Glitching (Fault injection) attacks attempt to put  |
+|                        |   a hardware into a undefined state by manipulating an|
+|                        |   environmental variable such as power supply.        |
+|                        |                                                       |
+|                        | | TF-A relies on a chain of trust that starts with the|
+|                        |   ROTPK, which is the key stored inside the chip and  |
+|                        |   the root of all validation processes. If an attacker|
+|                        |   can break this chain of trust, they could execute   |
+|                        |   arbitrary code on the device. This could be         |
+|                        |   achieved with physical access to the device by      |
+|                        |   attacking the normal execution flow of the          |
+|                        |   process using glitching techniques that target      |
+|                        |   points where the image is validated against the     |
+|                        |   signature.                                          |
++------------------------+-------------------------------------------------------+
+| ``Diagram Elements``   | DF1                                                   |
++------------------------+-------------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2                                              |
+| Components``           |                                                       |
++------------------------+-------------------------------------------------------+
+| ``Assets``             | Code Execution                                        |
++------------------------+-------------------------------------------------------+
+| ``Threat Agent``       | PhysicalAccess                                        |
++------------------------+-------------------------------------------------------+
+| ``Threat Type``        | Tampering, Elevation of Privilege                     |
++------------------------+---------------------+-----------------+---------------+
+| ``Application``        | ``Server``          | ``IoT``         | ``Mobile``    |
++------------------------+---------------------+-----------------+---------------+
+| ``Impact``             | N/A                 | Critical (5)    | Critical (5)  |
++------------------------+---------------------+-----------------+---------------+
+| ``Likelihood``         | N/A                 | Medium (3)      | Medium (3)    |
++------------------------+---------------------+-----------------+---------------+
+| ``Total Risk Rating``  | N/A                 | High (15)       | High (15)     |
++------------------------+---------------------+-----------------+---------------+
+| ``Mitigations``        | | The most effective mitigation is adding glitching   |
+|                        |   detection and mitigation circuit at the hardware    |
+|                        |   level. However, software techniques,                |
+|                        |   such as adding redundant checks when performing     |
+|                        |   conditional branches that are security sensitive,   |
+|                        |   can be used to harden TF-A against such attacks.    |
+|                        |   **At the moment TF-A doesn't implement such         |
+|                        |   mitigations.**                                      |
++------------------------+-------------------------------------------------------+
+
++------------------------+---------------------------------------------------+
+| ID                     | 05                                                |
++========================+===================================================+
+| ``Threat``             | | **Information leak via UART logs such as        |
+|                        |   crashes**                                       |
+|                        |                                                   |
+|                        | | During the development stages of software it is |
+|                        |   common to include crash reports with detailed   |
+|                        |   information of the CPU state including current  |
+|                        |   values of the registers, privilege level and    |
+|                        |   stack dumps. This information is useful when    |
+|                        |   debugging problems before releasing the         |
+|                        |   production version, but it could be used by an  |
+|                        |   attacker to develop a working exploit if left   |
+|                        |   in the production version.                      |
++------------------------+---------------------------------------------------+
+| ``Diagram Elements``   | DF2                                               |
++------------------------+---------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2, BL31                                    |
+| Components``           |                                                   |
++------------------------+---------------------------------------------------+
+| ``Assets``             | Sensitive Data                                    |
++------------------------+---------------------------------------------------+
+| ``Threat Agent``       | AppDebug                                          |
++------------------------+---------------------------------------------------+
+| ``Threat Type``        | Information Disclosure                            |
++------------------------+------------------+----------------+---------------+
+| ``Application``        | ``Server``       | ``IoT``        | ``Mobile``    |
++------------------------+------------------+----------------+---------------+
+| ``Impact``             | N/A              | Low (2)        | Low (2)       |
++------------------------+------------------+----------------+---------------+
+| ``Likelihood``         | N/A              | High (4)       | High (4)      |
++------------------------+------------------+----------------+---------------+
+| ``Total Risk Rating``  | N/A              | Medium (8)     | Medium (8)    |
++------------------------+------------------+----------------+---------------+
+| ``Mitigations``        | | In TF-A, crash reporting is only enabled for    |
+|                        |   debug builds by default. Alternatively, the log |
+|                        |   level can be tuned at build time (from verbose  |
+|                        |   to no output at all), independently of the      |
+|                        |   build type.                                     |
++------------------------+---------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 06                                                 |
++========================+====================================================+
+| ``Threat``             | | **An attacker can read sensitive data and        |
+|                        |   execute arbitrary code through the external      |
+|                        |   debug and trace interface**                      |
+|                        |                                                    |
+|                        | | Arm processors include hardware-assisted debug   |
+|                        |   and trace features that can be controlled without|
+|                        |   the need for software operating on the platform. |
+|                        |   If left enabled without authentication, this     |
+|                        |   feature can be used by an attacker to inspect and|
+|                        |   modify TF-A registers and memory allowing the    |
+|                        |   attacker to read sensitive data and execute      |
+|                        |   arbitrary code.                                  |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF3                                                |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2, BL31                                     |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Code Execution, Sensitive Data                     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | AppDebug                                           |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering, Information Disclosure,                 |
+|                        | Elevation of privilege                             |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        | ``Server``       | ``IoT``       | ``Mobile``      |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | N/A              | High (4)      | High (4)        |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | N/A              | Critical (5)  | Critical (5)    |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | N/A              | Critical (20) | Critical (20)   |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | | Configuration of debug and trace capabilities is |
+|                        |   platform specific. Therefore, platforms must     |
+|                        |   disable the debug and trace capability for       |
+|                        |   production releases or enable proper debug       |
+|                        |   authentication as recommended by [`DEN0034`_].   |
++------------------------+----------------------------------------------------+
+
++------------------------+------------------------------------------------------+
+| ID                     | 07                                                   |
++========================+======================================================+
+| ``Threat``             | | **An attacker can perform a denial-of-service      |
+|                        |   attack by using a broken SMC call that causes the  |
+|                        |   system to reboot or enter into unknown state.**    |
+|                        |                                                      |
+|                        | | Secure and non-secure clients access TF-A services |
+|                        |   through SMC calls. Malicious code can attempt to   |
+|                        |   place the TF-A runtime into an inconsistent state  |
+|                        |   by calling unimplemented SMC call or by passing    |
+|                        |   invalid arguments.                                 |
++------------------------+------------------------------------------------------+
+| ``Diagram Elements``   | DF4, DF5                                             |
++------------------------+------------------------------------------------------+
+| ``Affected TF-A        | BL31                                                 |
+| Components``           |                                                      |
++------------------------+------------------------------------------------------+
+| ``Assets``             | Availability                                         |
++------------------------+------------------------------------------------------+
+| ``Threat Agent``       | NSCode, SecCode                                      |
++------------------------+------------------------------------------------------+
+| ``Threat Type``        | Denial of Service                                    |
++------------------------+-------------------+----------------+-----------------+
+| ``Application``        | ``Server``        | ``IoT``        | ``Mobile``      |
++------------------------+-------------------+----------------+-----------------+
+| ``Impact``             | Medium (3)        | Medium (3)     | Medium (3)      |
++------------------------+-------------------+----------------+-----------------+
+| ``Likelihood``         | High (4)          | High (4)       | High (4)        |
++------------------------+-------------------+----------------+-----------------+
+| ``Total Risk Rating``  | High (12)         | High (12)      | High (12)       |
++------------------------+-------------------+----------------+-----------------+
+| ``Mitigations``        | | The generic TF-A code validates SMC function ids   |
+|                        |   and arguments before using them.                   |
+|                        |   Platforms that implement SiP services must also    |
+|                        |   validate SMC call arguments.                       |
++------------------------+------------------------------------------------------+
+
++------------------------+------------------------------------------------------+
+| ID                     | 08                                                   |
++========================+======================================================+
+| ``Threat``             | | **Memory corruption due to memory overflows and    |
+|                        |   lack of boundary checking when accessing resources |
+|                        |   could allow an attacker to execute arbitrary code, |
+|                        |   modify some state variable to change the normal    |
+|                        |   flow of the program, or leak sensitive             |
+|                        |   information**                                      |
+|                        |                                                      |
+|                        | | Like in other software, the Trusted Firmware has   |
+|                        |   multiple points where memory corruption security   |
+|                        |   errors can arise. Memory corruption is a dangerous |
+|                        |   security issue since it could allow an attacker    |
+|                        |   to execute arbitrary code, modify some state       |
+|                        |   variable to change the normal flow of the program, |
+|                        |   or leak sensitive information.                     |
+|                        |                                                      |
+|                        | | Some of the errors include integer overflow,       |
+|                        |   buffer overflow, incorrect array boundary checks,  |
+|                        |   and incorrect error management.                    |
+|                        |   Improper use of asserts instead of proper input    |
+|                        |   validations might also result in these kinds of    |
+|                        |   errors in release builds.                          |
++------------------------+------------------------------------------------------+
+| ``Diagram Elements``   | DF4, DF5                                             |
++------------------------+------------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2, BL31                                       |
+| Components``           |                                                      |
++------------------------+------------------------------------------------------+
+| ``Assets``             | Code Execution, Sensitive Data                       |
++------------------------+------------------------------------------------------+
+| ``Threat Agent``       | NSCode, SecCode                                      |
++------------------------+------------------------------------------------------+
+| ``Threat Type``        | Tampering, Information Disclosure,                   |
+|                        | Elevation of Privilege                               |
++------------------------+-------------------+-----------------+----------------+
+| ``Application``        | ``Server``        | ``IoT``         | ``Mobile``     |
++------------------------+-------------------+-----------------+----------------+
+| ``Impact``             | Critical (5)      | Critical (5)    | Critical (5)   |
++------------------------+-------------------+-----------------+----------------+
+| ``Likelihood``         | Medium (3         | Medium (3)      | Medium (3)     |
++------------------------+-------------------+-----------------+----------------+
+| ``Total Risk Rating``  | High (15)         | High (15)       | High (15)      |
++------------------------+-------------------+-----------------+----------------+
+| ``Mitigations``        | | TF-A uses a combination of manual code reviews and |
+|                        |   automated program analysis and testing to detect   |
+|                        |   and fix memory corruption bugs. All TF-A code      |
+|                        |   including platform code go through manual code     |
+|                        |   reviews. Additionally, static code analysis is     |
+|                        |   performed using Coverity Scan on all TF-A code.    |
+|                        |   The code is also tested  with                      |
+|                        |   `Trusted Firmware-A Tests`_ on Juno and FVP        |
+|                        |   platforms.                                         |
+|                        |                                                      |
+|                        | | Data received from normal world, such as addresses |
+|                        |   and sizes identifying memory regions, are          |
+|                        |   sanitized before being used. These security checks |
+|                        |   make sure that the normal world software does not  |
+|                        |   access memory beyond its limit.                    |
+|                        |                                                      |
+|                        | | By default *asserts* are only used to check for    |
+|                        |   programming errors in debug builds. Other types of |
+|                        |   errors are handled through condition checks that   |
+|                        |   remain enabled in release builds. See              |
+|                        |   `TF-A error handling policy`_. TF-A provides an    |
+|                        |   option to use *asserts* in release builds, however |
+|                        |   we recommend using proper runtime checks instead   |
+|                        |   of relying on asserts in release builds.           |
++------------------------+------------------------------------------------------+
+
++------------------------+------------------------------------------------------+
+| ID                     | 09                                                   |
++========================+======================================================+
+| ``Threat``             | | **Improperly handled SMC calls can leak register   |
+|                        |   contents**                                         |
+|                        |                                                      |
+|                        | | When switching between secure and non-secure       |
+|                        |   states, register contents of Secure world or       |
+|                        |   register contents of other normal world clients    |
+|                        |   can be leaked.                                     |
++------------------------+------------------------------------------------------+
+| ``Diagram Elements``   | DF5                                                  |
++------------------------+------------------------------------------------------+
+| ``Affected TF-A        | BL31                                                 |
+| Components``           |                                                      |
++------------------------+------------------------------------------------------+
+| ``Assets``             | Sensitive Data                                       |
++------------------------+------------------------------------------------------+
+| ``Threat Agent``       | NSCode                                               |
++------------------------+------------------------------------------------------+
+| ``Threat Type``        | Information Disclosure                               |
++------------------------+-------------------+----------------+-----------------+
+| ``Application``        | ``Server``        | ``IoT``        | ``Mobile``      |
++------------------------+-------------------+----------------+-----------------+
+| ``Impact``             | Medium (3)        | Medium (3)     | Medium (3)      |
++------------------------+-------------------+----------------+-----------------+
+| ``Likelihood``         | High (4)          | High (4)       | High (4)        |
++------------------------+-------------------+----------------+-----------------+
+| ``Total Risk Rating``  | High (12)         | High (12)      | High (12)       |
++------------------------+-------------------+----------------+-----------------+
+| ``Mitigations``        | | TF-A saves and restores registers                  |
+|                        |   by default when switching contexts. Build options  |
+|                        |   are also provided to save/restore additional       |
+|                        |   registers such as floating-point registers.        |
++------------------------+------------------------------------------------------+
+
++------------------------+-----------------------------------------------------+
+| ID                     | 10                                                  |
++========================+=====================================================+
+| ``Threat``             | | **SMC calls can leak sensitive information from   |
+|                        |   TF-A memory via microarchitectural side channels**|
+|                        |                                                     |
+|                        | | Microarchitectural side-channel attacks such as   |
+|                        |   `Spectre`_ can be used to leak data across        |
+|                        |   security boundaries. An attacker might attempt to |
+|                        |   use this kind of attack to leak sensitive         |
+|                        |   data from TF-A memory.                            |
++------------------------+-----------------------------------------------------+
+| ``Diagram Elements``   | DF4, DF5                                            |
++------------------------+-----------------------------------------------------+
+| ``Affected TF-A        | BL31                                                |
+| Components``           |                                                     |
++------------------------+-----------------------------------------------------+
+| ``Assets``             | Sensitive Data                                      |
++------------------------+-----------------------------------------------------+
+| ``Threat Agent``       | SecCode, NSCode                                     |
++------------------------+-----------------------------------------------------+
+| ``Threat Type``        | Information Disclosure                              |
++------------------------+-------------------+----------------+----------------+
+| ``Application``        | ``Server``        | ``IoT``        | ``Mobile``     |
++------------------------+-------------------+----------------+----------------+
+| ``Impact``             | Medium (3)        | Medium (3)     | Medium (3)     |
++------------------------+-------------------+----------------+----------------+
+| ``Likelihood``         | Medium (3)        | Medium (3)     | Medium (3)     |
++------------------------+-------------------+----------------+----------------+
+| ``Total Risk Rating``  | Medium (9)        | Medium (9)     | Medium (9)     |
++------------------------+-------------------+----------------+----------------+
+| ``Mitigations``        | | TF-A implements software mitigations for Spectre  |
+|                        |   type attacks as recommended by `Cache Speculation |
+|                        |   Side-channels`_ for the generic code. SiPs should |
+|                        |   implement similar mitigations for code that is    |
+|                        |   deemed to be vulnerable to such attacks.          |
++------------------------+-----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 11                                                 |
++========================+====================================================+
+| ``Threat``             | | **Misconfiguration of the Memory Management Unit |
+|                        |   (MMU) may allow a normal world software to       |
+|                        |   access sensitive data or execute arbitrary       |
+|                        |   code**                                           |
+|                        |                                                    |
+|                        | | A misconfiguration of the MMU could              |
+|                        |   lead to an open door for software running in the |
+|                        |   normal world to access sensitive data or even    |
+|                        |   execute code if the proper security mechanisms   |
+|                        |   are not in place.                                |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF5, DF6                                           |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | BL1, BL2, BL31                                     |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Sensitive Data, Code execution                     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NSCode                                             |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Information Disclosure, Elevation of Privilege     |
++------------------------+-----------------+-----------------+----------------+
+| ``Application``        | ``Server``      | ``IoT``         | ``Mobile``     |
++------------------------+-----------------+-----------------+----------------+
+| ``Impact``             | Critical (5)    | Critical (5)    | Critical (5)   |
++------------------------+-----------------+-----------------+----------------+
+| ``Likelihood``         | High (4)        | High (4)        | High (4)       |
++------------------------+-----------------+-----------------+----------------+
+| ``Total Risk Rating``  | Critical (20)   | Critical (20)   | Critical (20)  |
++------------------------+-----------------+-----------------+----------------+
+| ``Mitigations``        | | In TF-A, configuration of the MMU is done        |
+|                        |   through a translation tables library. The        |
+|                        |   library provides APIs to define memory regions   |
+|                        |   and assign attributes including memory types and |
+|                        |   access permissions. Memory configurations are    |
+|                        |   platform specific, therefore platforms need make |
+|                        |   sure the correct attributes are assigned to      |
+|                        |   memory regions. When assigning access            |
+|                        |   permissions, principle of least privilege ought  |
+|                        |   to be enforced, i.e. we should not grant more    |
+|                        |   privileges than strictly needed, e.g. code       |
+|                        |   should be read-only executable, RO data should   |
+|                        |   be read-only XN, and so on.                      |
++------------------------+----------------------------------------------------+
+
++------------------------+-----------------------------------------------------+
+| ID                     | 12                                                  |
++========================+=====================================================+
+| ``Threat``             | | **Incorrect configuration of Performance Monitor  |
+|                        |   Unit (PMU) counters can allow an attacker to      |
+|                        |   mount side-channel attacks using information      |
+|                        |   exposed by the counters**                         |
+|                        |                                                     |
+|                        | | Non-secure software can configure PMU registers   |
+|                        |   to count events at any exception level and in     |
+|                        |   both Secure and Non-secure states. This allows    |
+|                        |   a Non-secure software (or a lower-level Secure    |
+|                        |   software) to potentially  carry out               |
+|                        |   side-channel timing attacks against TF-A.         |
++------------------------+-----------------------------------------------------+
+| ``Diagram Elements``   | DF5, DF6                                            |
++------------------------+-----------------------------------------------------+
+| ``Affected TF-A        | BL31                                                |
+| Components``           |                                                     |
++------------------------+-----------------------------------------------------+
+| ``Assets``             | Sensitive Data                                      |
++------------------------+-----------------------------------------------------+
+| ``Threat Agent``       | NSCode                                              |
++------------------------+-----------------------------------------------------+
+| ``Threat Type``        | Information Disclosure                              |
++------------------------+-------------------+----------------+----------------+
+| ``Impact``             | Medium (3)        | Medium (3)     | Medium (3)     |
++------------------------+-------------------+----------------+----------------+
+| ``Likelihood``         | Low (2)           | Low (2)        | Low (2)        |
++------------------------+-------------------+----------------+----------------+
+| ``Total Risk Rating``  | Medium (6)        | Medium (6)     | Medium (6)     |
++------------------------+-------------------+----------------+----------------+
+| ``Mitigations``        | | TF-A follows mitigation strategies as described   |
+|                        |   in `Secure Development Guidelines`_. General      |
+|                        |   events and cycle counting in the Secure world is  |
+|                        |   prohibited by default when applicable. However,   |
+|                        |   on some implementations (e.g. PMUv3) Secure world |
+|                        |   event counting depends on external debug interface|
+|                        |   signals, i.e. Secure world event counting is      |
+|                        |   enabled if external debug is enabled.             |
+|                        |   Configuration of debug signals is platform        |
+|                        |   specific, therefore platforms need to make sure   |
+|                        |   that external debug is disabled in production or  |
+|                        |   proper debug authentication is in place.          |
++------------------------+-----------------------------------------------------+
+
+--------------
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
+
+
+.. _STRIDE threat analysis technique: https://docs.microsoft.com/en-us/azure/security/develop/threat-modeling-tool-threats#stride-model
+.. _DEN0034: https://developer.arm.com/documentation/den0034/latest
+.. _Cache Speculation Side-channels: https://developer.arm.com/support/arm-security-updates/speculative-processor-vulnerability
+.. _Spectre: https://developer.arm.com/support/arm-security-updates/speculative-processor-vulnerability
+.. _TBBR-Client specification: https://developer.arm.com/documentation/den0006/d/
+.. _Trusted Board Boot (TBB): https://trustedfirmware-a.readthedocs.io/en/latest/design/trusted-board-boot.html
+.. _TF-A error handling policy: https://trustedfirmware-a.readthedocs.io/en/latest/process/coding-guidelines.html#error-handling-and-robustness
+.. _Secure Development Guidelines: https://trustedfirmware-a.readthedocs.io/en/latest/process/security-hardening.html#secure-development-guidelines
+.. _Trusted Firmware-A Tests: https://git.trustedfirmware.org/TF-A/tf-a-tests.git/about/
diff --git a/docs/threat_model/threat_model_spm.rst b/docs/threat_model/threat_model_spm.rst
new file mode 100644
index 0000000..82f9916
--- /dev/null
+++ b/docs/threat_model/threat_model_spm.rst
@@ -0,0 +1,617 @@
+SPMC threat model
+*****************
+
+************************
+Introduction
+************************
+This document provides a threat model for the TF-A `Secure Partition Manager`_
+(SPM) implementation or more generally the S-EL2 reference firmware running on
+systems implementing the FEAT_SEL2 (formerly Armv8.4 Secure EL2) architecture
+extension. The SPM implementation is based on the `Arm Firmware Framework for
+Arm A-profile`_ specification.
+
+In brief, the broad FF-A specification and S-EL2 firmware implementation
+provide:
+
+- Isolation of mutually mistrusting SW components, or endpoints in the FF-A
+  terminology.
+- Distinct sandboxes in the secure world called secure partitions. This permits
+  isolation of services from multiple vendors.
+- A standard protocol for communication and memory sharing between FF-A
+  endpoints.
+- Mutual isolation of the normal world and the secure world (e.g. a Trusted OS
+  is prevented to map an arbitrary NS physical memory region such as the kernel
+  or the Hypervisor).
+
+************************
+Target of Evaluation
+************************
+In this threat model, the target of evaluation is the S-EL2 firmware or the
+``Secure Partition Manager Core`` component (SPMC).
+The monitor and SPMD at EL3 are covered by the `Generic TF-A threat model`_.
+
+The scope for this threat model is:
+
+- The TF-A implementation for the S-EL2 SPMC based on the Hafnium hypervisor
+  running in the secure world of TrustZone (at S-EL2 exception level).
+  The threat model is not related to the normal world Hypervisor or VMs.
+  The S-EL1 SPMC solution is not covered.
+- The implementation complies with the FF-A v1.0 specification.
+- Secure partitions are statically provisioned at boot time.
+- Focus on the run-time part of the life-cycle (no specific emphasis on boot
+  time, factory firmware provisioning, firmware udpate etc.)
+- Not covering advanced or invasive physical attacks such as decapsulation,
+  FIB etc.
+- Assumes secure boot or in particular TF-A trusted boot (TBBR or dual CoT) is
+  enabled. An attacker cannot boot arbitrary images that are not approved by the
+  SiP or platform providers.
+
+Data Flow Diagram
+======================
+Figure 1 shows a high-level data flow diagram for the SPM split into an SPMD
+component at EL3 and an SPMC component at S-EL2. The SPMD mostly acts as a
+relayer/pass-through between the normal world and the secure world. It is
+assumed to expose small attack surface.
+
+A description of each diagram element is given in Table 1. In the diagram, the
+red broken lines indicate trust boundaries.
+
+Components outside of the broken lines are considered untrusted.
+
+.. uml:: ../resources/diagrams/plantuml/spm_dfd.puml
+  :caption: Figure 1: SPMC Data Flow Diagram
+
+.. table:: Table 1: SPMC Data Flow Diagram Description
+
+  +---------------------+--------------------------------------------------------+
+  | Diagram Element     | Description                                            |
+  +=====================+========================================================+
+  | ``DF1``             | SP to SPMC communication. FF-A function invocation or  |
+  |                     | implementation-defined Hypervisor call.                |
+  +---------------------+--------------------------------------------------------+
+  | ``DF2``             | SPMC to SPMD FF-A call.                                |
+  +---------------------+--------------------------------------------------------+
+  | ``DF3``             | SPMD to NS forwarding.                                 |
+  +---------------------+--------------------------------------------------------+
+  | ``DF4``             | SP to SP FF-A direct message request/response.         |
+  |                     | Note as a matter of simplifying the diagram            |
+  |                     | the SP to SP communication happens through the SPMC    |
+  |                     | (SP1 performs a direct message request to the          |
+  |                     | SPMC targeting SP2 as destination. And similarly for   |
+  |                     | the direct message response from SP2 to SP1).          |
+  +---------------------+--------------------------------------------------------+
+  | ``DF5``             | HW control.                                            |
+  +---------------------+--------------------------------------------------------+
+  | ``DF6``             | Bootloader image loading.                              |
+  +---------------------+--------------------------------------------------------+
+  | ``DF7``             | External memory access.                                |
+  +---------------------+--------------------------------------------------------+
+
+*********************
+Threat Analysis
+*********************
+
+This threat model follows a similar methodology to the `Generic TF-A threat model`_.
+The following sections define:
+
+- Trust boundaries
+- Assets
+- Theat agents
+- Threat types
+
+Trust boundaries
+============================
+
+- Normal world is untrusted.
+- Secure world and normal world are separate trust boundaries.
+- EL3 monitor, SPMD and SPMC are trusted.
+- Bootloaders (in particular BL1/BL2 if using TF-A) and run-time BL31 are
+  implicitely trusted by the usage of secure boot.
+- EL3 monitor, SPMD, SPMC do not trust SPs.
+
+.. figure:: ../resources/diagrams/spm-threat-model-trust-boundaries.png
+
+    Figure 2: Trust boundaries
+
+Assets
+============================
+
+The following assets are identified:
+
+- SPMC state.
+- SP state.
+- Information exchange between endpoints (partition messages).
+- SPMC secrets (e.g. pointer authentication key when enabled)
+- SP secrets (e.g. application keys).
+- Scheduling cycles.
+- Shared memory.
+
+Threat Agents
+============================
+
+The following threat agents are identified:
+
+- NS-Endpoint identifies a non-secure endpoint: normal world client at NS-EL2
+  (Hypervisor) or NS-EL1 (VM or OS kernel).
+- S-Endpoint identifies a secure endpoint typically a secure partition.
+- Hardware attacks (non-invasive) requiring a physical access to the device,
+  such as bus probing or DRAM stress.
+
+Threat types
+============================
+
+The following threat categories as exposed in the `Generic TF-A threat model`_
+are re-used:
+
+- Spoofing
+- Tampering
+- Repudiation
+- Information disclosure
+- Denial of service
+- Elevation of privileges
+
+Similarly this threat model re-uses the same threat risk ratings. The risk
+analysis is evaluated based on the environment being ``Server`` or ``Mobile``.
+
+Threat Assessment
+============================
+
+The following threats are identified by applying STRIDE analysis on each diagram
+element of the data flow diagram.
+
++------------------------+----------------------------------------------------+
+| ID                     | 01                                                 |
++========================+====================================================+
+| ``Threat``             | **An endpoint impersonates the sender or receiver  |
+|                        | FF-A ID in a direct request/response invocation.** |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF2, DF3, DF4                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMD, SPMC                                         |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP state                                           |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Spoofing                                           |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------++----------------+---------------+
+| ``Impact``             | Critical(5)      | Critical(5)     |               |
++------------------------+------------------++----------------+---------------+
+| ``Likelihood``         | Critical(5)      | Critical(5)     |               |
++------------------------+------------------++----------------+---------------+
+| ``Total Risk Rating``  | Critical(25)     | Critical(25)    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | The TF-A SPMC does not mitigate this threat.       |
+|                        | The guidance below is left for a system integrator |
+|                        | to implemented as necessary.                       |
+|                        | The SPMC must enforce checks in the direct message |
+|                        | request/response interfaces such an endpoint cannot|
+|                        | spoof the origin and destination worlds (e.g. a NWd|
+|                        | originated message directed to the SWd cannot use a|
+|                        | SWd ID as the sender ID).                          |
+|                        | Additionally a software component residing in the  |
+|                        | SPMC can be added for the purpose of direct        |
+|                        | request/response filtering.                        |
+|                        | It can be configured with the list of known IDs    |
+|                        | and about which interaction can occur between one  |
+|                        | and another endpoint (e.g. which NWd endpoint ID   |
+|                        | sends a direct request to which SWd endpoint ID).  |
+|                        | This component checks the sender/receiver fields   |
+|                        | for a legitimate communication between endpoints.  |
+|                        | A similar component can exist in the OS kernel     |
+|                        | driver, or Hypervisor although it remains untrusted|
+|                        | by the SPMD/SPMC.                                  |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 02                                                 |
++========================+====================================================+
+| ``Threat``             | **Tampering with memory shared between an endpoint |
+|                        | and the SPMC.**                                    |
+|                        | A malicious endpoint may attempt tampering with its|
+|                        | RX/TX buffer contents while the SPMC is processing |
+|                        | it (TOCTOU).                                       |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF3, DF4, DF7                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Shared memory, Information exchange                |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering                                          |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | High (4)         | High (4)        |               |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | High (4)         | High (4)        |               |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | High (16)        | High (16)       |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | In context of FF-A v1.0 this is the case of sharing|
+|                        | the RX/TX buffer pair and usage in the             |
+|                        | PARTITION_INFO_GET or mem sharing primitives.      |
+|                        | The SPMC must copy the contents of the TX buffer   |
+|                        | to an internal temporary buffer before processing  |
+|                        | its contents. The SPMC must implement hardened     |
+|                        | input validation on data transmitted through the TX|
+|                        | buffer by an untrusted endpoint.                   |
+|                        | The TF-A SPMC mitigates this threat by enforcing   |
+|                        | checks on data transmitted through RX/TX buffers.  |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 03                                                 |
++========================+====================================================+
+| ``Threat``             | **An endpoint may tamper with its own state or the |
+|                        | state of another endpoint.**                       |
+|                        | A malicious endpoint may attempt violating:        |
+|                        | - its own or another SP state by using an unusual  |
+|                        | combination (or out-of-order) FF-A function        |
+|                        | invocations.                                       |
+|                        | This can also be an endpoint emitting              |
+|                        | FF-A function invocations to another endpoint while|
+|                        | the latter in not in a state to receive it (e.g. a |
+|                        | SP sends a direct request to the normal world early|
+|                        | while the normal world is not booted yet).         |
+|                        | - the SPMC state itself by employing unexpected    |
+|                        | transitions in FF-A memory sharing, direct requests|
+|                        | and responses, or handling of interrupts.          |
+|                        | This can be led by random stimuli injection or     |
+|                        | fuzzing.                                           |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF2, DF3, DF4                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMD, SPMC                                         |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP state, SPMC state                               |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering                                          |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | High (4)         | High (4)        |               |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Medium (3)       | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | High (12)        | High (12)       |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | The SPMC may be vulnerable to invalid state        |
+|                        | transitions for itself or while handling an SP     |
+|                        | state. The FF-A v1.1 specification provides a      |
+|                        | guidance on those state transitions (run-time      |
+|                        | model). The TF-A SPMC will be hardened in future   |
+|                        | releases to follow this guidance.                  |
+|                        | Additionally The TF-A SPMC mitigates the threat by |
+|                        | runs of the Arm `FF-A ACS`_ compliance test suite. |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 04                                                 |
++========================+====================================================+
+| ``Threat``             | *An attacker may attempt injecting errors by the   |
+|                        | use of external DRAM stress techniques.**          |
+|                        | A malicious agent may attempt toggling an SP       |
+|                        | Stage-2 MMU descriptor bit within the page tables  |
+|                        | that the SPMC manages. This can happen in Rowhammer|
+|                        | types of attack.                                   |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF7                                                |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP or SPMC state                                   |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | Hardware attack                                    |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering                                          |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        |   ``Server``     |  ``Mobile``   |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | High (4)         | High (4)	    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | Low (2)          | Medium (3)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | Medium (8)       | High (12)	    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | The TF-A SPMC does not provide mitigations to this |
+|                        | type of attack. It can be addressed by the use of  |
+|                        | dedicated HW circuity or hardening at the chipset  |
+|                        | or platform level left to the integrator.          |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 05                                                 |
++========================+====================================================+
+| ``Threat``             | **Protection of the SPMC from a DMA capable device |
+|                        | upstream to an SMMU.**                             |
+|                        | A device may attempt to tamper with the internal   |
+|                        | SPMC code/data sections.                           |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF5                                                |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SPMC or SP state                                   |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Tampering, Elevation of privileges                 |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        |   ``Server``     |  ``Mobile``   |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | High (4)         | High (4)      |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | Medium (3)       | Medium (3)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | High (12)        | High (12)     |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | A platform may prefer assigning boot time,         |
+|                        | statically alocated memory regions through the SMMU|
+|                        | configuration and page tables. The FF-A v1.1       |
+|                        | specification provisions this capability through   |
+|                        | static DMA isolation.                              |
+|                        | The TF-A SPMC does not mitigate this threat.       |
+|                        | It will adopt the static DMA isolation approach in |
+|                        | a future release.                                  |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 06                                                 |
++========================+====================================================+
+| ``Threat``             | **Replay fragments of past communication between   |
+|                        | endpoints.**                                       |
+|                        | A malicious endpoint may replay a message exchange |
+|                        | that occured between two legitimate endpoint as    |
+|                        | a matter of triggering a malfunction or extracting |
+|                        | secrets from the receiving endpoint. In particular |
+|                        | the memory sharing operation with fragmented       |
+|                        | messages between an endpoint and the SPMC may be   |
+|                        | replayed by a malicious agent as a matter of       |
+|                        | getting access or gaining permissions to a memory  |
+|                        | region which does not belong to this agent.        |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF2, DF3                                           |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | Information exchange                               |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Repdudiation                                       |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        |   ``Server``     |  ``Mobile``   |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | Medium (3)       | Medium (3)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | High (4)         | High (4)	    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | High (12)        | High (12)     |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | The TF-A SPMC does not mitigate this threat.       |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 07                                                 |
++========================+====================================================+
+| ``Threat``             | **A malicious endpoint may attempt to extract data |
+|                        | or state information by the use of invalid or      |
+|                        | incorrect input arguments.**                       |
+|                        | Lack of input parameter validation or side effects |
+|                        | of maliciously forged input parameters might affect|
+|                        | the SPMC.                                          |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF2, DF3, DF4                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMD, SPMC                                         |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP secrets, SPMC secrets, SP state, SPMC state     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Information discolure                              |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        |   ``Server``     |  ``Mobile``   |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | High (4)         | High (4)      |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | Medium (3)       | Medium (3)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | High (12)        | High (12)     |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | Secure Partitions must follow security standards   |
+|                        | and best practises as a way to mitigate the risk   |
+|                        | of common vulnerabilities to be exploited.         |
+|                        | The use of software (canaries) or hardware         |
+|                        | hardening techniques (XN, WXN, BTI, pointer        |
+|                        | authentication, MTE) helps detecting and stopping  |
+|                        | an exploitation early.                             |
+|                        | The TF-A SPMC mitigates this threat by implementing|
+|                        | stack protector, pointer authentication, BTI, XN,  |
+|                        | WXN, security hardening techniques.                |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 08                                                 |
++========================+====================================================+
+| ``Threat``             | **A malicious endpoint may forge a direct message  |
+|                        | request such that it reveals the internal state of |
+|                        | another endpoint through the direct message        |
+|                        | response.**                                        |
+|                        | The secure partition or SPMC replies to a partition|
+|                        | message by a direct message response with          |
+|                        | information which may reveal its internal state    |
+|                        | (.e.g. partition message response outside of       |
+|                        | allowed bounds).                                   |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF2, DF3, DF4                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SPMC or SP state                                   |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Information discolure                              |
++------------------------+------------------+---------------+-----------------+
+| ``Application``        |   ``Server``     |  ``Mobile``   |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Impact``             | Medium (3)       | Medium (3)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Likelihood``         | Low (2)          | Low (2)	    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Total Risk Rating``  | Medium (6)       | Medium (6)    |                 |
++------------------------+------------------+---------------+-----------------+
+| ``Mitigations``        | For the specific case of direct requests targetting|
+|                        | the SPMC, the latter is hardened to prevent        |
+|                        | its internal state or the state of an SP to be     |
+|                        | revealed through a direct message response.        |
+|                        | Further FF-A v1.1 guidance about run time models   |
+|                        | and partition states will be implemented in future |
+|                        | TF-A SPMC releases.                                |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 09                                                 |
++========================+====================================================+
+| ``Threat``             | **Probing the FF-A communication between           |
+|                        | endpoints.**                                       |
+|                        | SPMC and SPs are typically loaded to external      |
+|                        | memory (protected by a TrustZone memory            |
+|                        | controller). A malicious agent may use non invasive|
+|                        | methods to probe the external memory bus and       |
+|                        | extract the traffic between an SP and the SPMC or  |
+|                        | among SPs when shared buffers are held in external |
+|                        | memory.                                            |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF7                                                |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP/SPMC state, SP/SPMC secrets                     |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | Hardware attack                                    |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Information disclosure                             |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | Medium (3)       | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Low (2)          | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | Medium (6)       | Medium (9)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | It is expected the platform or chipset provides    |
+|                        | guarantees in protecting the DRAM contents.        |
+|                        | The TF-A SPMC does not mitigate this class of      |
+|                        | attack and this is left to the integrator.         |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 10                                                 |
++========================+====================================================+
+| ``Threat``             | **A malicious agent may attempt revealing the SPMC |
+|                        | state or secrets by the use of software-based cache|
+|                        | side-channel attack techniques.**                  |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF7                                                |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SP or SPMC state                                   |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Information disclosure                             |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | Medium (3)       | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Low (2)          | Low (2)         |               |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | Medium (6)       | Medium (6)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | From an integration perspective it is assumed      |
+|                        | platforms consuming the SPMC component at S-EL2    |
+|                        | (hence implementing the Armv8.4 FEAT_SEL2          |
+|                        | architecture extension) implement mitigations to   |
+|                        | Spectre, Meltdown or other cache timing            |
+|                        | side-channel type of attacks.                      |
+|                        | The TF-A SPMC implements one mitigation (barrier   |
+|                        | preventing speculation past exeception returns).   |
+|                        | The SPMC may be hardened further with SW           |
+|                        | mitigations (e.g. speculation barriers) for the    |
+|                        | cases not covered in HW. Usage of hardened         |
+|                        | compilers and appropriate options, code inspection |
+|                        | are recommended ways to mitigate Spectre types of  |
+|                        | attacks. For non-hardened cores, the usage of      |
+|                        | techniques such a kernel page table isolation can  |
+|                        | help mitigating Meltdown type of attacks.          |
++------------------------+----------------------------------------------------+
+
++------------------------+----------------------------------------------------+
+| ID                     | 11                                                 |
++========================+====================================================+
+| ``Threat``             | **A malicious endpoint may attempt flooding the    |
+|                        | SPMC with requests targetting a service within an  |
+|                        | endpoint such that it denies another endpoint to   |
+|                        | access this service.**                             |
+|                        | Similarly, the malicious endpoint may target a     |
+|                        | a service within an endpoint such that the latter  |
+|                        | is unable to request services from another         |
+|                        | endpoint.                                          |
++------------------------+----------------------------------------------------+
+| ``Diagram Elements``   | DF1, DF2, DF3, DF4                                 |
++------------------------+----------------------------------------------------+
+| ``Affected TF-A        | SPMC                                               |
+| Components``           |                                                    |
++------------------------+----------------------------------------------------+
+| ``Assets``             | SPMC state                                         |
++------------------------+----------------------------------------------------+
+| ``Threat Agent``       | NS-Endpoint, S-Endpoint                            |
++------------------------+----------------------------------------------------+
+| ``Threat Type``        | Denial of service                                  |
++------------------------+------------------+-----------------+---------------+
+| ``Application``        |   ``Server``     |   ``Mobile``    |               |
++------------------------+------------------+-----------------+---------------+
+| ``Impact``             | Medium (3)       | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Likelihood``         | Medium (3)       | Medium (3)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Total Risk Rating``  | Medium (9)       | Medium (9)      |               |
++------------------------+------------------+-----------------+---------------+
+| ``Mitigations``        | The TF-A SPMC does not mitigate this threat.       |
+|                        | Bounding the time for operations to complete can   |
+|                        | be achieved by the usage of a trusted watchdog.    |
+|                        | Other quality of service monitoring can be achieved|
+|                        | in the SPMC such as counting a number of operations|
+|                        | in a limited timeframe.                            |
++------------------------+----------------------------------------------------+
+
+--------------
+
+*Copyright (c) 2021, Arm Limited. All rights reserved.*
+
+.. _Arm Firmware Framework for Arm A-profile: https://developer.arm.com/docs/den0077/latest
+.. _Secure Partition Manager: ../components/secure-partition-manager.html
+.. _Generic TF-A threat model: ./threat_model.html#threat-analysis
+.. _FF-A ACS: https://github.com/ARM-software/ff-a-acs/releases
diff --git a/drivers/allwinner/axp/common.c b/drivers/allwinner/axp/common.c
index e98b16f..143fb0f 100644
--- a/drivers/allwinner/axp/common.c
+++ b/drivers/allwinner/axp/common.c
@@ -96,12 +96,27 @@
 	return 0;
 }
 
+static bool is_node_disabled(const void *fdt, int node)
+{
+	const char *cell;
+	cell = fdt_getprop(fdt, node, "status", NULL);
+	if (cell == NULL) {
+		return false;
+	}
+	return strcmp(cell, "okay") != 0;
+}
+
 static bool should_enable_regulator(const void *fdt, int node)
 {
-	if (fdt_getprop(fdt, node, "phandle", NULL) != NULL)
+	if (is_node_disabled(fdt, node)) {
+		return false;
+	}
+	if (fdt_getprop(fdt, node, "phandle", NULL) != NULL) {
 		return true;
-	if (fdt_getprop(fdt, node, "regulator-always-on", NULL) != NULL)
+	}
+	if (fdt_getprop(fdt, node, "regulator-always-on", NULL) != NULL) {
 		return true;
+	}
 	return false;
 }
 
diff --git a/drivers/arm/css/scmi/scmi_common.c b/drivers/arm/css/scmi/scmi_common.c
index 5b3724a..ec749fb 100644
--- a/drivers/arm/css/scmi/scmi_common.c
+++ b/drivers/arm/css/scmi/scmi_common.c
@@ -173,12 +173,12 @@
 
 	ret = scmi_proto_version(ch, SCMI_PWR_DMN_PROTO_ID, &version);
 	if (ret != SCMI_E_SUCCESS) {
-		WARN("SCMI power domain protocol version message failed");
+		WARN("SCMI power domain protocol version message failed\n");
 		goto error;
 	}
 
 	if (!is_scmi_version_compatible(SCMI_PWR_DMN_PROTO_VER, version)) {
-		WARN("SCMI power domain protocol version 0x%x incompatible with driver version 0x%x",
+		WARN("SCMI power domain protocol version 0x%x incompatible with driver version 0x%x\n",
 			version, SCMI_PWR_DMN_PROTO_VER);
 		goto error;
 	}
@@ -187,12 +187,12 @@
 
 	ret = scmi_proto_version(ch, SCMI_SYS_PWR_PROTO_ID, &version);
 	if ((ret != SCMI_E_SUCCESS)) {
-		WARN("SCMI system power protocol version message failed");
+		WARN("SCMI system power protocol version message failed\n");
 		goto error;
 	}
 
 	if (!is_scmi_version_compatible(SCMI_SYS_PWR_PROTO_VER, version)) {
-		WARN("SCMI system power management protocol version 0x%x incompatible with driver version 0x%x",
+		WARN("SCMI system power management protocol version 0x%x incompatible with driver version 0x%x\n",
 			version, SCMI_SYS_PWR_PROTO_VER);
 		goto error;
 	}
diff --git a/drivers/arm/css/scp/css_pm_scmi.c b/drivers/arm/css/scp/css_pm_scmi.c
index aeb7eda..5de2604 100644
--- a/drivers/arm/css/scp/css_pm_scmi.c
+++ b/drivers/arm/css/scp/css_pm_scmi.c
@@ -357,7 +357,7 @@
 	unsigned int composite_id, idx;
 
 	for (idx = 0; idx < PLAT_ARM_SCMI_CHANNEL_COUNT; idx++) {
-		INFO("Initializing driver on Channel %d\n", idx);
+		INFO("Initializing SCMI driver on channel %d\n", idx);
 
 		scmi_channels[idx].info = plat_css_get_scmi_info(idx);
 		scmi_channels[idx].lock = ARM_SCMI_LOCK_GET_INSTANCE;
diff --git a/drivers/arm/dcc/dcc_console.c b/drivers/arm/dcc/dcc_console.c
new file mode 100644
index 0000000..0b7e541
--- /dev/null
+++ b/drivers/arm/dcc/dcc_console.c
@@ -0,0 +1,152 @@
+/*
+ * Copyright (c) 2015-2021, Xilinx Inc.
+ * Written by Michal Simek.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * 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 <errno.h>
+#include <stddef.h>
+#include <arch_helpers.h>
+#include <drivers/arm/dcc.h>
+#include <drivers/console.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+/* DCC Status Bits */
+#define DCC_STATUS_RX		BIT(30)
+#define DCC_STATUS_TX		BIT(29)
+#define TIMEOUT_COUNT_US	U(0x10624)
+
+struct dcc_console {
+	struct console console;
+};
+
+static inline uint32_t __dcc_getstatus(void)
+{
+	return read_mdccsr_el0();
+}
+
+static inline char __dcc_getchar(void)
+{
+	char c;
+
+	c = read_dbgdtrrx_el0();
+
+	return c;
+}
+
+static inline void __dcc_putchar(char c)
+{
+	/*
+	 * The typecast is to make absolutely certain that 'c' is
+	 * zero-extended.
+	 */
+	write_dbgdtrtx_el0((unsigned char)c);
+}
+
+static int32_t dcc_status_timeout(uint32_t mask)
+{
+	const unsigned int timeout_count = TIMEOUT_COUNT_US;
+	uint64_t timeout;
+	unsigned int status;
+
+	timeout = timeout_init_us(timeout_count);
+
+	do {
+		status = (__dcc_getstatus() & mask);
+		if (timeout_elapsed(timeout)) {
+			return -ETIMEDOUT;
+		}
+	} while ((status != 0U));
+
+	return 0;
+}
+
+static int32_t dcc_console_putc(int32_t ch, struct console *console)
+{
+	unsigned int status;
+
+	status = dcc_status_timeout(DCC_STATUS_TX);
+	if (status != 0U) {
+		return status;
+	}
+	__dcc_putchar(ch);
+
+	return ch;
+}
+
+static int32_t dcc_console_getc(struct console *console)
+{
+	unsigned int status;
+
+	status = dcc_status_timeout(DCC_STATUS_RX);
+	if (status != 0U) {
+		return status;
+	}
+
+	return __dcc_getchar();
+}
+
+int32_t dcc_console_init(unsigned long base_addr, uint32_t uart_clk,
+		      uint32_t baud_rate)
+{
+	return 0; /* No init needed */
+}
+
+/**
+ * dcc_console_flush() - Function to force a write of all buffered data
+ *		          that hasn't been output.
+ * @console		Console struct
+ *
+ */
+static void dcc_console_flush(struct console *console)
+{
+	unsigned int status;
+
+	status = dcc_status_timeout(DCC_STATUS_TX);
+	if (status != 0U) {
+		return;
+	}
+}
+
+static struct dcc_console dcc_console = {
+	.console = {
+		.flags = CONSOLE_FLAG_BOOT |
+			CONSOLE_FLAG_RUNTIME,
+		.putc = dcc_console_putc,
+		.getc = dcc_console_getc,
+		.flush = dcc_console_flush,
+	},
+};
+
+int console_dcc_register(void)
+{
+	return console_register(&dcc_console.console);
+}
diff --git a/drivers/arm/ethosn/ethosn_smc.c b/drivers/arm/ethosn/ethosn_smc.c
new file mode 100644
index 0000000..60364cd
--- /dev/null
+++ b/drivers/arm/ethosn/ethosn_smc.c
@@ -0,0 +1,170 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+#include <stdbool.h>
+
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <drivers/arm/ethosn.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+#include <plat/arm/common/fconf_ethosn_getter.h>
+
+/*
+ * Number of Arm Ethos-N NPU (NPU) cores available for a
+ * particular parent device
+ */
+#define ETHOSN_NUM_CORES \
+	FCONF_GET_PROPERTY(hw_config, ethosn_config, num_cores)
+
+/* Address to an NPU core  */
+#define ETHOSN_CORE_ADDR(core_idx) \
+	FCONF_GET_PROPERTY(hw_config, ethosn_core_addr, core_idx)
+
+/* NPU core sec registry address */
+#define ETHOSN_CORE_SEC_REG(core_addr, reg_offset) \
+	(core_addr + reg_offset)
+
+/* Reset timeout in us */
+#define ETHOSN_RESET_TIMEOUT_US		U(10 * 1000 * 1000)
+#define ETHOSN_RESET_WAIT_US		U(1)
+
+#define SEC_DEL_REG			U(0x0004)
+#define SEC_DEL_VAL			U(0x81C)
+#define SEC_DEL_EXCC_MASK		U(0x20)
+
+#define SEC_SECCTLR_REG			U(0x0010)
+#define SEC_SECCTLR_VAL			U(0x3)
+
+#define SEC_DEL_MMUSID_REG		U(0x2008)
+#define SEC_DEL_MMUSID_VAL		U(0x3FFFF)
+
+#define SEC_DEL_ADDR_EXT_REG		U(0x201C)
+#define SEC_DEL_ADDR_EXT_VAL		U(0x15)
+
+#define SEC_SYSCTRL0_REG		U(0x0018)
+#define SEC_SYSCTRL0_SOFT_RESET		U(3U << 29)
+#define SEC_SYSCTRL0_HARD_RESET		U(1U << 31)
+
+static bool ethosn_is_core_addr_valid(uintptr_t core_addr)
+{
+	for (uint32_t core_idx = 0U; core_idx < ETHOSN_NUM_CORES; core_idx++) {
+		if (ETHOSN_CORE_ADDR(core_idx) == core_addr) {
+			return true;
+		}
+	}
+
+	return false;
+}
+
+static void ethosn_delegate_to_ns(uintptr_t core_addr)
+{
+	mmio_setbits_32(ETHOSN_CORE_SEC_REG(core_addr, SEC_SECCTLR_REG),
+			SEC_SECCTLR_VAL);
+
+	mmio_setbits_32(ETHOSN_CORE_SEC_REG(core_addr, SEC_DEL_REG),
+			SEC_DEL_VAL);
+
+	mmio_setbits_32(ETHOSN_CORE_SEC_REG(core_addr, SEC_DEL_MMUSID_REG),
+			SEC_DEL_MMUSID_VAL);
+
+	mmio_setbits_32(ETHOSN_CORE_SEC_REG(core_addr, SEC_DEL_ADDR_EXT_REG),
+			SEC_DEL_ADDR_EXT_VAL);
+}
+
+static int ethosn_is_sec(uintptr_t core_addr)
+{
+	if ((mmio_read_32(ETHOSN_CORE_SEC_REG(core_addr, SEC_DEL_REG))
+		& SEC_DEL_EXCC_MASK) != 0U) {
+		return 0;
+	}
+
+	return 1;
+}
+
+static bool ethosn_reset(uintptr_t core_addr, int hard_reset)
+{
+	unsigned int timeout;
+	const uintptr_t sysctrl0_reg =
+		ETHOSN_CORE_SEC_REG(core_addr, SEC_SYSCTRL0_REG);
+	const uint32_t reset_val = (hard_reset != 0) ? SEC_SYSCTRL0_HARD_RESET
+						    : SEC_SYSCTRL0_SOFT_RESET;
+
+	mmio_write_32(sysctrl0_reg, reset_val);
+
+	/* Wait for reset to complete */
+	for (timeout = 0U; timeout < ETHOSN_RESET_TIMEOUT_US;
+			   timeout += ETHOSN_RESET_WAIT_US) {
+
+		if ((mmio_read_32(sysctrl0_reg) & reset_val) == 0U) {
+			break;
+		}
+
+		udelay(ETHOSN_RESET_WAIT_US);
+	}
+
+	return timeout < ETHOSN_RESET_TIMEOUT_US;
+}
+
+uintptr_t ethosn_smc_handler(uint32_t smc_fid,
+			     u_register_t core_addr,
+			     u_register_t x2,
+			     u_register_t x3,
+			     u_register_t x4,
+			     void *cookie,
+			     void *handle,
+			     u_register_t flags)
+{
+	int hard_reset = 0;
+	const uint32_t fid = smc_fid & FUNCID_NUM_MASK;
+
+	/* Only SiP fast calls are expected */
+	if ((GET_SMC_TYPE(smc_fid) != SMC_TYPE_FAST) ||
+		(GET_SMC_OEN(smc_fid) != OEN_SIP_START)) {
+		SMC_RET1(handle, SMC_UNK);
+	}
+
+	/* Truncate parameters to 32-bits for SMC32 */
+	if (GET_SMC_CC(smc_fid) == SMC_32) {
+		core_addr &= 0xFFFFFFFF;
+		x2 &= 0xFFFFFFFF;
+		x3 &= 0xFFFFFFFF;
+		x4 &= 0xFFFFFFFF;
+	}
+
+	if (!is_ethosn_fid(smc_fid)) {
+		SMC_RET1(handle, SMC_UNK);
+	}
+
+	/* Commands that do not require a valid core address */
+	switch (fid) {
+	case ETHOSN_FNUM_VERSION:
+		SMC_RET2(handle, ETHOSN_VERSION_MAJOR, ETHOSN_VERSION_MINOR);
+	}
+
+	if (!ethosn_is_core_addr_valid(core_addr)) {
+		WARN("ETHOSN: Unknown core address given to SMC call.\n");
+		SMC_RET1(handle, ETHOSN_UNKNOWN_CORE_ADDRESS);
+	}
+
+	/* Commands that require a valid addr */
+	switch (fid) {
+	case ETHOSN_FNUM_IS_SEC:
+		SMC_RET1(handle, ethosn_is_sec(core_addr));
+	case ETHOSN_FNUM_HARD_RESET:
+		hard_reset = 1;
+		/* Fallthrough */
+	case ETHOSN_FNUM_SOFT_RESET:
+		if (!ethosn_reset(core_addr, hard_reset)) {
+			SMC_RET1(handle, ETHOSN_FAILURE);
+		}
+		ethosn_delegate_to_ns(core_addr);
+		SMC_RET1(handle, ETHOSN_SUCCESS);
+	default:
+		SMC_RET1(handle, SMC_UNK);
+	}
+}
diff --git a/drivers/arm/gic/v3/gic-x00.c b/drivers/arm/gic/v3/gic-x00.c
index 6e106ba..aaef485 100644
--- a/drivers/arm/gic/v3/gic-x00.c
+++ b/drivers/arm/gic/v3/gic-x00.c
@@ -16,15 +16,13 @@
 #include <assert.h>
 
 #include <arch_helpers.h>
+#include <drivers/arm/arm_gicv3_common.h>
 #include <drivers/arm/gicv3.h>
 
 #include "gicv3_private.h"
 
 /* GIC-600 specific register offsets */
 #define GICR_PWRR			0x24U
-#define IIDR_MODEL_ARM_GIC_600		U(0x0200043b)
-#define IIDR_MODEL_ARM_GIC_600AE	U(0x0300043b)
-#define IIDR_MODEL_ARM_GIC_CLAYTON	U(0x0400043b)
 
 /* GICR_PWRR fields */
 #define PWRR_RDPD_SHIFT			0
@@ -46,7 +44,7 @@
 
 #if GICV3_SUPPORT_GIC600
 
-/* GIC-600/Clayton specific accessor functions */
+/* GIC-600/700 specific accessor functions */
 static void gicr_write_pwrr(uintptr_t base, unsigned int val)
 {
 	mmio_write_32(base + GICR_PWRR, val);
@@ -123,12 +121,12 @@
 	uint32_t reg = mmio_read_32(gicr_base + GICR_IIDR);
 
 	/*
-	 * The Arm GIC-600 and GIC-Clayton models have their redistributors
+	 * The Arm GIC-600 and GIC-700 models have their redistributors
 	 * powered down at reset.
 	 */
 	return (((reg & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_600) ||
 		((reg & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_600AE) ||
-		((reg & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_CLAYTON));
+		((reg & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_700));
 }
 
 #endif	/* GICV3_SUPPORT_GIC600 */
diff --git a/drivers/arm/gic/v3/gic600_multichip.c b/drivers/arm/gic/v3/gic600_multichip.c
index ca7c43b..5f42ad9 100644
--- a/drivers/arm/gic/v3/gic600_multichip.c
+++ b/drivers/arm/gic/v3/gic600_multichip.c
@@ -11,14 +11,13 @@
 #include <assert.h>
 
 #include <common/debug.h>
+#include <drivers/arm/arm_gicv3_common.h>
 #include <drivers/arm/gic600_multichip.h>
 #include <drivers/arm/gicv3.h>
 
 #include "../common/gic_common_private.h"
 #include "gic600_multichip_private.h"
 
-#warning "GIC-600 Multichip driver is currently experimental and the API may change in future."
-
 /*******************************************************************************
  * GIC-600 multichip operation related helper functions
  ******************************************************************************/
@@ -73,6 +72,7 @@
 				unsigned int spi_id_max)
 {
 	unsigned int spi_block_min, spi_blocks;
+	unsigned int gicd_iidr_val = gicd_read_iidr(base);
 	uint64_t chipr_n_val;
 
 	/*
@@ -100,8 +100,24 @@
 	spi_block_min = SPI_BLOCK_MIN_VALUE(spi_id_min);
 	spi_blocks    = SPI_BLOCKS_VALUE(spi_id_min, spi_id_max);
 
-	chipr_n_val = (GICD_CHIPR_VALUE(chip_addr, spi_block_min, spi_blocks)) |
-		GICD_CHIPRx_SOCKET_STATE;
+	switch ((gicd_iidr_val & IIDR_MODEL_MASK)) {
+	case IIDR_MODEL_ARM_GIC_600:
+		chipr_n_val = GICD_CHIPR_VALUE_GIC_600(chip_addr,
+						       spi_block_min,
+						       spi_blocks);
+		break;
+	case IIDR_MODEL_ARM_GIC_700:
+		chipr_n_val = GICD_CHIPR_VALUE_GIC_700(chip_addr,
+						       spi_block_min,
+						       spi_blocks);
+		break;
+	default:
+		ERROR("Unsupported GIC model 0x%x for multichip setup.\n",
+		      gicd_iidr_val);
+		panic();
+		break;
+	}
+	chipr_n_val |= GICD_CHIPRx_SOCKET_STATE;
 
 	/*
 	 * Wait for DCHIPR.PUP to be zero before commencing writes to
@@ -194,8 +210,6 @@
 
 	gic600_multichip_validate_data(multichip_data);
 
-	INFO("GIC-600 Multichip driver is experimental\n");
-
 	/*
 	 * Ensure that G0/G1S/G1NS interrupts are disabled. This also ensures
 	 * that GIC-600 Multichip configuration is done first.
diff --git a/drivers/arm/gic/v3/gic600_multichip_private.h b/drivers/arm/gic/v3/gic600_multichip_private.h
index fe4134c..5d1ff6a 100644
--- a/drivers/arm/gic/v3/gic600_multichip_private.h
+++ b/drivers/arm/gic/v3/gic600_multichip_private.h
@@ -27,17 +27,11 @@
 #define GICD_CHIPSR_RTS_SHIFT		4
 #define GICD_DCHIPR_RT_OWNER_SHIFT	4
 
-/*
- * If GIC v4 extension is enabled, then use SPI macros specific to GIC-Clayton.
- * Other shifts and mask remains same between GIC-600 and GIC-Clayton.
- */
-#if GIC_ENABLE_V4_EXTN
-#define GICD_CHIPRx_SPI_BLOCK_MIN_SHIFT	9
-#define GICD_CHIPRx_SPI_BLOCKS_SHIFT	3
-#else
-#define GICD_CHIPRx_SPI_BLOCK_MIN_SHIFT	10
-#define GICD_CHIPRx_SPI_BLOCKS_SHIFT	5
-#endif
+/* Other shifts and masks remain the same between GIC-600 and GIC-700. */
+#define GIC_700_SPI_BLOCK_MIN_SHIFT	9
+#define GIC_700_SPI_BLOCKS_SHIFT	3
+#define GIC_600_SPI_BLOCK_MIN_SHIFT	10
+#define GIC_600_SPI_BLOCKS_SHIFT	5
 
 #define GICD_CHIPSR_RTS_STATE_DISCONNECTED	U(0)
 #define GICD_CHIPSR_RTS_STATE_UPDATING		U(1)
@@ -59,10 +53,14 @@
 #define SPI_BLOCKS_VALUE(spi_id_min, spi_id_max) \
 			(((spi_id_max) - (spi_id_min) + 1) / \
 			GIC600_SPI_ID_MIN)
-#define GICD_CHIPR_VALUE(chip_addr, spi_block_min, spi_blocks) \
+#define GICD_CHIPR_VALUE_GIC_700(chip_addr, spi_block_min, spi_blocks) \
 			(((chip_addr) << GICD_CHIPRx_ADDR_SHIFT) | \
-			((spi_block_min) << GICD_CHIPRx_SPI_BLOCK_MIN_SHIFT) | \
-			((spi_blocks) << GICD_CHIPRx_SPI_BLOCKS_SHIFT))
+			((spi_block_min) << GIC_700_SPI_BLOCK_MIN_SHIFT) | \
+			((spi_blocks) << GIC_700_SPI_BLOCKS_SHIFT))
+#define GICD_CHIPR_VALUE_GIC_600(chip_addr, spi_block_min, spi_blocks) \
+			(((chip_addr) << GICD_CHIPRx_ADDR_SHIFT) | \
+			((spi_block_min) << GIC_600_SPI_BLOCK_MIN_SHIFT) | \
+			((spi_blocks) << GIC_600_SPI_BLOCKS_SHIFT))
 
 /*
  * Multichip data assertion macros
diff --git a/drivers/arm/gic/v3/gic600ae_fmu.c b/drivers/arm/gic/v3/gic600ae_fmu.c
new file mode 100644
index 0000000..13979fa
--- /dev/null
+++ b/drivers/arm/gic/v3/gic600ae_fmu.c
@@ -0,0 +1,244 @@
+/*
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/*
+ * Driver for GIC-600AE Fault Management Unit
+ */
+
+#include <assert.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/arm/gic600ae_fmu.h>
+#include <drivers/arm/gicv3.h>
+
+/* GIC-600 AE FMU specific register offsets */
+
+/* GIC-600 AE FMU specific macros */
+#define FMU_ERRIDR_NUM			U(44)
+#define FMU_ERRIDR_NUM_MASK		U(0xFFFF)
+
+/* Safety mechanisms for GICD block */
+static char *gicd_sm_info[] = {
+	"Reserved",
+	"GICD dual lockstep error",
+	"GICD AXI4 slave interface error",
+	"GICD-PPI AXI4-Stream interface error",
+	"GICD-ITS AXI4-Stream interface error",
+	"GICD-SPI-Collator AXI4-Stream interface error",
+	"GICD AXI4 master interface error",
+	"SPI RAM DED error",
+	"SGI RAM DED error",
+	"Reserved",
+	"LPI RAM DED error",
+	"GICD-remote-GICD AXI4-Stream interface error",
+	"GICD Q-Channel interface error",
+	"GICD P-Channel interface error",
+	"SPI RAM address decode error",
+	"SGI RAM address decode error",
+	"Reserved",
+	"LPI RAM address decode error",
+	"FMU dual lockstep error",
+	"FMU ping ACK error",
+	"FMU APB parity error",
+	"GICD-Wake AXI4-Stream interface error",
+	"GICD PageOffset or Chip ID error",
+	"MBIST REQ error",
+	"SPI RAM SEC error",
+	"SGI RAM SEC error",
+	"Reserved",
+	"LPI RAM SEC error",
+	"User custom SM0 error",
+	"User custom SM1 error",
+	"GICD-ITS Monolithic switch error",
+	"GICD-ITS Q-Channel interface error",
+	"GICD-ITS Monolithic interface error",
+	"GICD FMU ClkGate override"
+};
+
+/* Safety mechanisms for PPI block */
+static char *ppi_sm_info[] = {
+	"Reserved",
+	"PPI dual lockstep error",
+	"PPI-GICD AXI4-Stream interface error",
+	"PPI-CPU-IF AXI4-Stream interface error",
+	"PPI Q-Channel interface error",
+	"PPI RAM DED error",
+	"PPI RAM address decode error",
+	"PPI RAM SEC error",
+	"PPI User0 SM",
+	"PPI User1 SM",
+	"MBIST REQ error",
+	"PPI interrupt parity protection error",
+	"PPI FMU ClkGate override"
+};
+
+/* Safety mechanisms for ITS block */
+static char *its_sm_info[] = {
+	"Reserved",
+	"ITS dual lockstep error",
+	"ITS-GICD AXI4-Stream interface error",
+	"ITS AXI4 slave interface error",
+	"ITS AXI4 master interface error",
+	"ITS Q-Channel interface error",
+	"ITS RAM DED error",
+	"ITS RAM address decode error",
+	"Bypass ACE switch error",
+	"ITS RAM SEC error",
+	"ITS User0 SM",
+	"ITS User1 SM",
+	"ITS-GICD Monolithic interface error",
+	"MBIST REQ error",
+	"ITS FMU ClkGate override"
+};
+
+/* Safety mechanisms for SPI Collator block */
+static char *spicol_sm_info[] = {
+	"Reserved",
+	"SPI Collator dual lockstep error",
+	"SPI-Collator-GICD AXI4-Stream interface error",
+	"SPI Collator Q-Channel interface error",
+	"SPI Collator Q-Channel clock error",
+	"SPI interrupt parity error"
+};
+
+/* Safety mechanisms for Wake Request block */
+static char *wkrqst_sm_info[] = {
+	"Reserved",
+	"Wake dual lockstep error",
+	"Wake-GICD AXI4-Stream interface error"
+};
+
+/*
+ * Initialization sequence for the FMU
+ *
+ * 1. enable error detection for error records that are passed in the blk_present_mask
+ * 2. enable MBIST REQ and FMU Clk Gate override safety mechanisms for error records
+ *    that are present on the platform
+ *
+ * The platforms are expected to pass `errctlr_ce_en` and `errctlr_ue_en`.
+ */
+void gic600_fmu_init(uint64_t base, uint64_t blk_present_mask,
+		     bool errctlr_ce_en, bool errctlr_ue_en)
+{
+	unsigned int num_blk = gic_fmu_read_erridr(base) & FMU_ERRIDR_NUM_MASK;
+	uint64_t errctlr;
+	uint32_t smen;
+
+	INFO("GIC600-AE FMU supports %d error records\n", num_blk);
+
+	assert(num_blk == FMU_ERRIDR_NUM);
+
+	/* sanitize block present mask */
+	blk_present_mask &= FMU_BLK_PRESENT_MASK;
+
+	/* Enable error detection for all error records */
+	for (unsigned int i = 0U; i < num_blk; i++) {
+
+		/* Skip next steps if the block is not present */
+		if ((blk_present_mask & BIT(i)) == 0U) {
+			continue;
+		}
+
+		/* Read the error record control register */
+		errctlr = gic_fmu_read_errctlr(base, i);
+
+		/* Enable error reporting and logging, if it is disabled */
+		if ((errctlr & FMU_ERRCTLR_ED_BIT) == 0U) {
+			errctlr |= FMU_ERRCTLR_ED_BIT;
+		}
+
+		/* Enable client provided ERRCTLR settings */
+		errctlr |= (errctlr_ce_en ? (FMU_ERRCTLR_CI_BIT | FMU_ERRCTLR_CE_EN_BIT) : 0);
+		errctlr |= (errctlr_ue_en ? FMU_ERRCTLR_UI_BIT : 0U);
+
+		gic_fmu_write_errctlr(base, i, errctlr);
+	}
+
+	/*
+	 * Enable MBIST REQ error and FMU CLK gate override safety mechanisms for
+	 * all blocks
+	 *
+	 * GICD, SMID 23 and SMID 33
+	 * PPI, SMID 10 and SMID 12
+	 * ITS, SMID 13 and SMID 14
+	 */
+	if ((blk_present_mask & BIT(FMU_BLK_GICD)) != 0U) {
+		smen = (GICD_MBIST_REQ_ERROR << FMU_SMEN_SMID_SHIFT) |
+			(FMU_BLK_GICD << FMU_SMEN_BLK_SHIFT);
+		gic_fmu_write_smen(base, smen);
+
+		smen = (GICD_FMU_CLKGATE_ERROR << FMU_SMEN_SMID_SHIFT) |
+			(FMU_BLK_GICD << FMU_SMEN_BLK_SHIFT);
+		gic_fmu_write_smen(base, smen);
+	}
+
+	for (unsigned int i = FMU_BLK_PPI0; i < FMU_BLK_PPI31; i++) {
+		if ((blk_present_mask & BIT(i)) != 0U) {
+			smen = (PPI_MBIST_REQ_ERROR << FMU_SMEN_SMID_SHIFT) |
+				(i << FMU_SMEN_BLK_SHIFT);
+			gic_fmu_write_smen(base, smen);
+
+			smen = (PPI_FMU_CLKGATE_ERROR << FMU_SMEN_SMID_SHIFT) |
+				(i << FMU_SMEN_BLK_SHIFT);
+			gic_fmu_write_smen(base, smen);
+		}
+	}
+
+	for (unsigned int i = FMU_BLK_ITS0; i < FMU_BLK_ITS7; i++) {
+		if ((blk_present_mask & BIT(i)) != 0U) {
+			smen = (ITS_MBIST_REQ_ERROR << FMU_SMEN_SMID_SHIFT) |
+				(i << FMU_SMEN_BLK_SHIFT);
+			gic_fmu_write_smen(base, smen);
+
+			smen = (ITS_FMU_CLKGATE_ERROR << FMU_SMEN_SMID_SHIFT) |
+				(i << FMU_SMEN_BLK_SHIFT);
+			gic_fmu_write_smen(base, smen);
+		}
+	}
+}
+
+/*
+ * This function enable the GICD background ping engine. The GICD sends ping
+ * messages to each remote GIC block, and expects a PING_ACK back within the
+ * specified timeout. Pings need to be enabled after programming the timeout
+ * value.
+ */
+void gic600_fmu_enable_ping(uint64_t base, uint64_t blk_present_mask,
+		unsigned int timeout_val, unsigned int interval_diff)
+{
+	/*
+	 * Populate the PING Mask to skip a specific block while generating
+	 * background ping messages and enable the ping mechanism.
+	 */
+	gic_fmu_write_pingmask(base, ~blk_present_mask);
+	gic_fmu_write_pingctlr(base, (interval_diff << FMU_PINGCTLR_INTDIFF_SHIFT) |
+		(timeout_val << FMU_PINGCTLR_TIMEOUTVAL_SHIFT) | FMU_PINGCTLR_EN_BIT);
+}
+
+/* Print the safety mechanism description for a given block */
+void gic600_fmu_print_sm_info(uint64_t base, unsigned int blk, unsigned int smid)
+{
+	if (blk == FMU_BLK_GICD && smid <= FMU_SMID_GICD_MAX) {
+		INFO("GICD, SMID %d: %s\n", smid, gicd_sm_info[smid]);
+	}
+
+	if (blk == FMU_BLK_SPICOL && smid <= FMU_SMID_SPICOL_MAX) {
+		INFO("SPI Collator, SMID %d: %s\n", smid, spicol_sm_info[smid]);
+	}
+
+	if (blk == FMU_BLK_WAKERQ && (smid <= FMU_SMID_WAKERQ_MAX)) {
+		INFO("Wake Request, SMID %d: %s\n", smid, wkrqst_sm_info[smid]);
+	}
+
+	if (((blk >= FMU_BLK_ITS0) && (blk <= FMU_BLK_ITS7)) && (smid <= FMU_SMID_ITS_MAX)) {
+		INFO("ITS, SMID %d: %s\n", smid, its_sm_info[smid]);
+	}
+
+	if (((blk >= FMU_BLK_PPI0) && (blk <= FMU_BLK_PPI31)) && (smid <= FMU_SMID_PPI_MAX)) {
+		INFO("PPI, SMID %d: %s\n", smid, ppi_sm_info[smid]);
+	}
+}
diff --git a/drivers/arm/gic/v3/gic600ae_fmu_helpers.c b/drivers/arm/gic/v3/gic600ae_fmu_helpers.c
new file mode 100644
index 0000000..84f7292
--- /dev/null
+++ b/drivers/arm/gic/v3/gic600ae_fmu_helpers.c
@@ -0,0 +1,257 @@
+/*
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <drivers/arm/gic600ae_fmu.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#define GICFMU_IDLE_TIMEOUT_US		U(2000000)
+
+/* Macro to write 32-bit FMU registers */
+#define GIC_FMU_WRITE_32(base, reg, val) \
+	do { \
+		/* \
+		 * This register receives the unlock key that is required for \
+		 * writes to FMU registers to be successful. \
+		 */ \
+		mmio_write_32(base + GICFMU_KEY, 0xBE); \
+		/* Perform the actual write */ \
+		mmio_write_32((base) + (reg), (val)); \
+	} while (false)
+
+/* Macro to write 64-bit FMU registers */
+#define GIC_FMU_WRITE_64(base, reg, n, val) \
+	do { \
+		/* \
+		 * This register receives the unlock key that is required for \
+		 * writes to FMU registers to be successful. \
+		 */ \
+		mmio_write_32(base + GICFMU_KEY, 0xBE); \
+		/* \
+		 * APB bus is 32-bit wide; so split the 64-bit write into \
+		 * two 32-bit writes \
+		 */ \
+		mmio_write_32((base) + reg##_LO + (n * 64), (val)); \
+		mmio_write_32((base) + reg##_HI + (n * 64), (val)); \
+	} while (false)
+
+/* Helper function to wait until FMU is ready to accept the next command */
+static void wait_until_fmu_is_idle(uintptr_t base)
+{
+	uint64_t timeout_ref = timeout_init_us(GICFMU_IDLE_TIMEOUT_US);
+	uint64_t status;
+
+	/* wait until status is 'busy' */
+	do {
+		status = (gic_fmu_read_status(base) & BIT(0));
+
+		if (timeout_elapsed(timeout_ref)) {
+			ERROR("GIC600 AE FMU is not responding\n");
+			panic();
+		}
+	} while (status == U(0));
+}
+
+#define GIC_FMU_WRITE_ON_IDLE_32(base, reg, val) \
+	do { \
+		/* Wait until FMU is ready */ \
+		wait_until_fmu_is_idle(base); \
+		/* Actual register write */ \
+		GIC_FMU_WRITE_32(base, reg, val); \
+		/* Wait until FMU is ready */ \
+		wait_until_fmu_is_idle(base); \
+	} while (false)
+
+#define GIC_FMU_WRITE_ON_IDLE_64(base, reg, n, val) \
+	do { \
+		/* Wait until FMU is ready */ \
+		wait_until_fmu_is_idle(base); \
+		/* Actual register write */ \
+		GIC_FMU_WRITE_64(base, reg, n, val); \
+		/* Wait until FMU is ready */ \
+		wait_until_fmu_is_idle(base); \
+	} while (false)
+
+/*******************************************************************************
+ * GIC FMU functions for accessing the Fault Management Unit registers
+ ******************************************************************************/
+
+/*
+ * Accessors to read the Error Record Feature Register bits corresponding
+ * to an error record 'n'
+ */
+uint64_t gic_fmu_read_errfr(uintptr_t base, unsigned int n)
+{
+	/*
+	 * APB bus is 32-bit wide; so split the 64-bit read into
+	 * two 32-bit reads
+	 */
+	uint64_t reg_val = (uint64_t)mmio_read_32(base + GICFMU_ERRFR_LO + n * 64U);
+
+	reg_val |= ((uint64_t)mmio_read_32(base + GICFMU_ERRFR_HI + n * 64U) << 32);
+	return reg_val;
+}
+
+/*
+ * Accessors to read the Error Record Control Register bits corresponding
+ * to an error record 'n'
+ */
+uint64_t gic_fmu_read_errctlr(uintptr_t base, unsigned int n)
+{
+	/*
+	 * APB bus is 32-bit wide; so split the 64-bit read into
+	 * two 32-bit reads
+	 */
+	uint64_t reg_val = (uint64_t)mmio_read_32(base + GICFMU_ERRCTLR_LO + n * 64U);
+
+	reg_val |= ((uint64_t)mmio_read_32(base + GICFMU_ERRCTLR_HI + n * 64U) << 32);
+	return reg_val;
+}
+
+/*
+ * Accessors to read the Error Record Primary Status Register bits
+ * corresponding to an error record 'n'
+ */
+uint64_t gic_fmu_read_errstatus(uintptr_t base, unsigned int n)
+{
+	/*
+	 * APB bus is 32-bit wide; so split the 64-bit read into
+	 * two 32-bit reads
+	 */
+	uint64_t reg_val = (uint64_t)mmio_read_32(base + GICFMU_ERRSTATUS_LO + n * 64U);
+
+	reg_val |= ((uint64_t)mmio_read_32(base + GICFMU_ERRSTATUS_HI + n * 64U) << 32);
+	return reg_val;
+}
+
+/*
+ * Accessors to read the Error Group Status Register
+ */
+uint64_t gic_fmu_read_errgsr(uintptr_t base)
+{
+	/*
+	 * APB bus is 32-bit wide; so split the 64-bit read into
+	 * two 32-bit reads
+	 */
+	uint64_t reg_val = (uint64_t)mmio_read_32(base + GICFMU_ERRGSR_LO);
+
+	reg_val |= ((uint64_t)mmio_read_32(base + GICFMU_ERRGSR_HI) << 32);
+	return reg_val;
+}
+
+/*
+ * Accessors to read the Ping Control Register
+ */
+uint32_t gic_fmu_read_pingctlr(uintptr_t base)
+{
+	return mmio_read_32(base + GICFMU_PINGCTLR);
+}
+
+/*
+ * Accessors to read the Ping Now Register
+ */
+uint32_t gic_fmu_read_pingnow(uintptr_t base)
+{
+	return mmio_read_32(base + GICFMU_PINGNOW);
+}
+
+/*
+ * Accessors to read the Ping Mask Register
+ */
+uint64_t gic_fmu_read_pingmask(uintptr_t base)
+{
+	/*
+	 * APB bus is 32-bit wide; so split the 64-bit read into
+	 * two 32-bit reads
+	 */
+	uint64_t reg_val = (uint64_t)mmio_read_32(base + GICFMU_PINGMASK_LO);
+
+	reg_val |= ((uint64_t)mmio_read_32(base + GICFMU_PINGMASK_HI) << 32);
+	return reg_val;
+}
+
+/*
+ * Accessors to read the FMU Status Register
+ */
+uint32_t gic_fmu_read_status(uintptr_t base)
+{
+	return mmio_read_32(base + GICFMU_STATUS);
+}
+
+/*
+ * Accessors to read the Error Record ID Register
+ */
+uint32_t gic_fmu_read_erridr(uintptr_t base)
+{
+	return mmio_read_32(base + GICFMU_ERRIDR);
+}
+
+/*
+ * Accessors to write a 64 bit value to the Error Record Control Register
+ */
+void gic_fmu_write_errctlr(uintptr_t base, unsigned int n, uint64_t val)
+{
+	GIC_FMU_WRITE_64(base, GICFMU_ERRCTLR, n, val);
+}
+
+/*
+ * Accessors to write a 64 bit value to the Error Record Primary Status
+ * Register
+ */
+void gic_fmu_write_errstatus(uintptr_t base, unsigned int n, uint64_t val)
+{
+	/* Wait until FMU is ready before writing */
+	GIC_FMU_WRITE_ON_IDLE_64(base, GICFMU_ERRSTATUS, n, val);
+}
+
+/*
+ * Accessors to write a 32 bit value to the Ping Control Register
+ */
+void gic_fmu_write_pingctlr(uintptr_t base, uint32_t val)
+{
+	GIC_FMU_WRITE_32(base, GICFMU_PINGCTLR, val);
+}
+
+/*
+ * Accessors to write a 32 bit value to the Ping Now Register
+ */
+void gic_fmu_write_pingnow(uintptr_t base, uint32_t val)
+{
+	/* Wait until FMU is ready before writing */
+	GIC_FMU_WRITE_ON_IDLE_32(base, GICFMU_PINGNOW, val);
+}
+
+/*
+ * Accessors to write a 32 bit value to the Safety Mechanism Enable Register
+ */
+void gic_fmu_write_smen(uintptr_t base, uint32_t val)
+{
+	/* Wait until FMU is ready before writing */
+	GIC_FMU_WRITE_ON_IDLE_32(base, GICFMU_SMEN, val);
+}
+
+/*
+ * Accessors to write a 32 bit value to the Safety Mechanism Inject Error
+ * Register
+ */
+void gic_fmu_write_sminjerr(uintptr_t base, uint32_t val)
+{
+	/* Wait until FMU is ready before writing */
+	GIC_FMU_WRITE_ON_IDLE_32(base, GICFMU_SMINJERR, val);
+}
+
+/*
+ * Accessors to write a 64 bit value to the Ping Mask Register
+ */
+void gic_fmu_write_pingmask(uintptr_t base, uint64_t val)
+{
+	GIC_FMU_WRITE_64(base, GICFMU_PINGMASK, 0, val);
+}
diff --git a/drivers/arm/gic/v3/gicv3.mk b/drivers/arm/gic/v3/gicv3.mk
index a2fc16f..d7e3536 100644
--- a/drivers/arm/gic/v3/gicv3.mk
+++ b/drivers/arm/gic/v3/gicv3.mk
@@ -1,11 +1,13 @@
 #
 # Copyright (c) 2013-2020, Arm Limited and Contributors. All rights reserved.
+# Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
 # Default configuration values
 GICV3_SUPPORT_GIC600		?=	0
+GICV3_SUPPORT_GIC600AE_FMU	?=	0
 GICV3_IMPL_GIC600_MULTICHIP	?=	0
 GICV3_OVERRIDE_DISTIF_PWR_OPS	?=	0
 GIC_ENABLE_V4_EXTN		?=	0
@@ -16,6 +18,11 @@
 			drivers/arm/gic/v3/gicdv3_helpers.c	\
 			drivers/arm/gic/v3/gicrv3_helpers.c
 
+ifeq (${GICV3_SUPPORT_GIC600AE_FMU}, 1)
+GICV3_SOURCES	+=	drivers/arm/gic/v3/gic600ae_fmu.c	\
+			drivers/arm/gic/v3/gic600ae_fmu_helpers.c
+endif
+
 ifeq (${GICV3_OVERRIDE_DISTIF_PWR_OPS}, 0)
 GICV3_SOURCES	+=	drivers/arm/gic/v3/arm_gicv3_common.c
 endif
@@ -29,6 +36,10 @@
 $(eval $(call assert_boolean,GICV3_SUPPORT_GIC600))
 $(eval $(call add_define,GICV3_SUPPORT_GIC600))
 
+# Set GIC-600AE FMU support
+$(eval $(call assert_boolean,GICV3_SUPPORT_GIC600AE_FMU))
+$(eval $(call add_define,GICV3_SUPPORT_GIC600AE_FMU))
+
 # Set GICv4 extension
 $(eval $(call assert_boolean,GIC_ENABLE_V4_EXTN))
 $(eval $(call add_define,GIC_ENABLE_V4_EXTN))
diff --git a/drivers/arm/gic/v3/gicv3_helpers.c b/drivers/arm/gic/v3/gicv3_helpers.c
index ff346f9..753d995 100644
--- a/drivers/arm/gic/v3/gicv3_helpers.c
+++ b/drivers/arm/gic/v3/gicv3_helpers.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -86,12 +86,52 @@
 		if (proc_num < rdistif_num) {
 			rdistif_base_addrs[proc_num] = rdistif_base;
 		}
-
-		rdistif_base += (1U << GICR_PCPUBASE_SHIFT);
+		rdistif_base += gicv3_redist_size(typer_val);
 	} while ((typer_val & TYPER_LAST_BIT) == 0U);
 }
 
 /*******************************************************************************
+ * Helper function to get the maximum SPI INTID + 1.
+ ******************************************************************************/
+unsigned int gicv3_get_spi_limit(uintptr_t gicd_base)
+{
+	unsigned int spi_limit;
+	unsigned int typer_reg = gicd_read_typer(gicd_base);
+
+	/* (maximum SPI INTID + 1) is equal to 32 * (GICD_TYPER.ITLinesNumber+1) */
+	spi_limit = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5;
+
+	/* Filter out special INTIDs 1020-1023 */
+	if (spi_limit > (MAX_SPI_ID + 1U)) {
+		return MAX_SPI_ID + 1U;
+	}
+
+	return spi_limit;
+}
+
+#if GIC_EXT_INTID
+/*******************************************************************************
+ * Helper function to get the maximum ESPI INTID + 1.
+ ******************************************************************************/
+unsigned int gicv3_get_espi_limit(uintptr_t gicd_base)
+{
+	unsigned int typer_reg = gicd_read_typer(gicd_base);
+
+	/* Check if extended SPI range is implemented */
+	if ((typer_reg & TYPER_ESPI) != 0U) {
+		/*
+		 * (maximum ESPI INTID + 1) is equal to
+		 * 32 * (GICD_TYPER.ESPI_range + 1) + 4096
+		 */
+		return ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
+			TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID;
+	}
+
+	return 0U;
+}
+#endif /* GIC_EXT_INTID */
+
+/*******************************************************************************
  * Helper function to configure the default attributes of (E)SPIs.
  ******************************************************************************/
 void gicv3_spis_config_defaults(uintptr_t gicd_base)
@@ -100,10 +140,9 @@
 #if GIC_EXT_INTID
 	unsigned int num_eints;
 #endif
-	unsigned int typer_reg = gicd_read_typer(gicd_base);
 
-	/* Maximum SPI INTID is 32 * (GICD_TYPER.ITLinesNumber + 1) - 1 */
-	num_ints = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5;
+	num_ints = gicv3_get_spi_limit(gicd_base);
+	INFO("Maximum SPI INTID supported: %u\n", num_ints - 1);
 
 	/* Treat all (E)SPIs as G1NS by default. We do 32 at a time. */
 	for (i = MIN_SPI_ID; i < num_ints; i += (1U << IGROUPR_SHIFT)) {
@@ -111,20 +150,16 @@
 	}
 
 #if GIC_EXT_INTID
-	/* Check if extended SPI range is implemented */
-	if ((typer_reg & TYPER_ESPI) != 0U) {
-		/*
-		 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
-		 */
-		num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
-			TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1;
+	num_eints = gicv3_get_espi_limit(gicd_base);
+	if (num_eints != 0U) {
+		INFO("Maximum ESPI INTID supported: %u\n", num_eints - 1);
 
 		for (i = MIN_ESPI_ID; i < num_eints;
 					i += (1U << IGROUPR_SHIFT)) {
 			gicd_write_igroupr(gicd_base, i, ~0U);
 		}
 	} else {
-		num_eints = 0U;
+		INFO("ESPI range is not implemented.\n");
 	}
 #endif
 
@@ -347,12 +382,29 @@
 	uintptr_t rdistif_base = gicr_frame;
 	unsigned int count;
 
-	for (count = 1; count < PLATFORM_CORE_COUNT; count++) {
-		if ((gicr_read_typer(rdistif_base) & TYPER_LAST_BIT) != 0U) {
+	for (count = 1U; count < PLATFORM_CORE_COUNT; count++) {
+		uint64_t typer_val = gicr_read_typer(rdistif_base);
+
+		if ((typer_val & TYPER_LAST_BIT) != 0U) {
 			break;
 		}
-		rdistif_base += (1U << GICR_PCPUBASE_SHIFT);
+		rdistif_base += gicv3_redist_size(typer_val);
 	}
 
 	return count;
 }
+
+unsigned int gicv3_get_component_partnum(const uintptr_t gic_frame)
+{
+	unsigned int part_id;
+
+	/*
+	 * The lower 8 bits of PIDR0, complemented by the lower 4 bits of
+	 * PIDR1 contain a part number identifying the GIC component at a
+	 * particular base address.
+	 */
+	part_id = mmio_read_32(gic_frame + GICD_PIDR0_GICV3) & 0xff;
+	part_id |= (mmio_read_32(gic_frame + GICD_PIDR1_GICV3) << 8) & 0xf00;
+
+	return part_id;
+}
diff --git a/drivers/arm/gic/v3/gicv3_main.c b/drivers/arm/gic/v3/gicv3_main.c
index 22efd45..53a8fae 100644
--- a/drivers/arm/gic/v3/gicv3_main.c
+++ b/drivers/arm/gic/v3/gicv3_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -70,7 +70,8 @@
 		for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\
 				int_id += (1U << REG##R_SHIFT)) {	\
 			gicd_write_##reg((base), int_id,		\
-			(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - MIN_SPI_ID))\
+			(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID -	\
+			round_up(TOTAL_SPI_INTR_NUM, 1U << REG##R_SHIFT)))\
 						>> REG##R_SHIFT]);	\
 		}							\
 	} while (false)
@@ -79,7 +80,8 @@
 	do {								\
 		for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\
 				int_id += (1U << REG##R_SHIFT)) {	\
-			(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - MIN_SPI_ID))\
+			(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID -	\
+			round_up(TOTAL_SPI_INTR_NUM, 1U << REG##R_SHIFT)))\
 			>> REG##R_SHIFT] = gicd_read_##reg((base), int_id);\
 		}							\
 	} while (false)
@@ -121,13 +123,7 @@
 	gic_version &= PIDR2_ARCH_REV_MASK;
 
 	/* Check GIC version */
-#if GIC_ENABLE_V4_EXTN
-	assert(gic_version == ARCH_REV_GICV4);
-
-	/* GICv4 supports Direct Virtual LPI injection */
-	assert((gicd_read_typer(plat_driver_data->gicd_base)
-					& TYPER_DVIS) != 0);
-#else
+#if !GIC_ENABLE_V4_EXTN
 	assert(gic_version == ARCH_REV_GICV3);
 #endif
 	/*
@@ -330,6 +326,8 @@
 	write_icc_igrpen1_el3(read_icc_igrpen1_el3() |
 				IGRPEN1_EL3_ENABLE_G1S_BIT);
 	isb();
+	/* Add DSB to ensure visibility of System register writes */
+	dsb();
 }
 
 /*******************************************************************************
@@ -361,6 +359,8 @@
 
 	/* Synchronise accesses to group enable registers */
 	isb();
+	/* Add DSB to ensure visibility of System register writes */
+	dsb();
 
 	/* Mark the connected core as asleep */
 	gicr_base = gicv3_driver_data->rdistif_base_addrs[proc_num];
@@ -726,40 +726,17 @@
  *****************************************************************************/
 void gicv3_distif_save(gicv3_dist_ctx_t * const dist_ctx)
 {
-	unsigned int typer_reg, num_ints;
-#if GIC_EXT_INTID
-	unsigned int num_eints;
-#endif
-
 	assert(gicv3_driver_data != NULL);
 	assert(gicv3_driver_data->gicd_base != 0U);
 	assert(IS_IN_EL3());
 	assert(dist_ctx != NULL);
 
 	uintptr_t gicd_base = gicv3_driver_data->gicd_base;
-
-	typer_reg = gicd_read_typer(gicd_base);
-
-	/* Maximum SPI INTID is 32 * (GICD_TYPER.ITLinesNumber + 1) - 1 */
-	num_ints = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5;
-
-	/* Filter out special INTIDs 1020-1023 */
-	if (num_ints > (MAX_SPI_ID + 1U)) {
-		num_ints = MAX_SPI_ID + 1U;
-	}
-
+	unsigned int num_ints = gicv3_get_spi_limit(gicd_base);
 #if GIC_EXT_INTID
-	/* Check if extended SPI range is implemented */
-	if ((typer_reg & TYPER_ESPI) != 0U) {
-		/*
-		 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
-		 */
-		num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
-			TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1;
-	} else {
-		num_eints = 0U;
-	}
+	unsigned int num_eints = gicv3_get_espi_limit(gicd_base);
 #endif
+
 	/* Wait for pending write to complete */
 	gicd_wait_for_pending_write(gicd_base);
 
@@ -836,11 +813,6 @@
  *****************************************************************************/
 void gicv3_distif_init_restore(const gicv3_dist_ctx_t * const dist_ctx)
 {
-	unsigned int typer_reg, num_ints;
-#if GIC_EXT_INTID
-	unsigned int num_eints;
-#endif
-
 	assert(gicv3_driver_data != NULL);
 	assert(gicv3_driver_data->gicd_base != 0U);
 	assert(IS_IN_EL3());
@@ -862,27 +834,9 @@
 	/* Set the ARE_S and ARE_NS bit now that interrupts have been disabled */
 	gicd_set_ctlr(gicd_base, CTLR_ARE_S_BIT | CTLR_ARE_NS_BIT, RWP_TRUE);
 
-	typer_reg = gicd_read_typer(gicd_base);
-
-	/* Maximum SPI INTID is 32 * (GICD_TYPER.ITLinesNumber + 1) - 1 */
-	num_ints = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5;
-
-	/* Filter out special INTIDs 1020-1023 */
-	if (num_ints > (MAX_SPI_ID + 1U)) {
-		num_ints = MAX_SPI_ID + 1U;
-	}
-
+	unsigned int num_ints = gicv3_get_spi_limit(gicd_base);
 #if GIC_EXT_INTID
-	/* Check if extended SPI range is implemented */
-	if ((typer_reg & TYPER_ESPI) != 0U) {
-		/*
-		 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
-		 */
-		num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
-			TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1;
-	} else {
-		num_eints = 0U;
-	}
+	unsigned int num_eints = gicv3_get_espi_limit(gicd_base);
 #endif
 	/* Restore GICD_IGROUPR for INTIDs 32 - 1019 */
 	RESTORE_GICD_REGS(gicd_base, dist_ctx, num_ints, igroupr, IGROUP);
@@ -1299,8 +1253,8 @@
  ******************************************************************************/
 int gicv3_rdistif_probe(const uintptr_t gicr_frame)
 {
-	u_register_t mpidr;
-	unsigned int proc_num, proc_self;
+	u_register_t mpidr, mpidr_self;
+	unsigned int proc_num;
 	uint64_t typer_val;
 	uintptr_t rdistif_base;
 	bool gicr_frame_found = false;
@@ -1314,18 +1268,18 @@
 	assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
 #endif /* !__aarch64__ */
 
-	proc_self = gicv3_driver_data->mpidr_to_core_pos(read_mpidr_el1());
+	mpidr_self = read_mpidr_el1() & MPIDR_AFFINITY_MASK;
 	rdistif_base = gicr_frame;
 	do {
 		typer_val = gicr_read_typer(rdistif_base);
+		mpidr = mpidr_from_gicr_typer(typer_val);
 		if (gicv3_driver_data->mpidr_to_core_pos != NULL) {
-			mpidr = mpidr_from_gicr_typer(typer_val);
 			proc_num = gicv3_driver_data->mpidr_to_core_pos(mpidr);
 		} else {
 			proc_num = (unsigned int)(typer_val >>
 				TYPER_PROC_NUM_SHIFT) & TYPER_PROC_NUM_MASK;
 		}
-		if (proc_num == proc_self) {
+		if (mpidr == mpidr_self) {
 			/* The base address doesn't need to be initialized on
 			 * every warm boot.
 			 */
@@ -1338,7 +1292,7 @@
 			gicr_frame_found = true;
 			break;
 		}
-		rdistif_base += (uintptr_t)(ULL(1) << GICR_PCPUBASE_SHIFT);
+		rdistif_base += gicv3_redist_size(typer_val);
 	} while ((typer_val & TYPER_LAST_BIT) == 0U);
 
 	if (!gicr_frame_found) {
diff --git a/drivers/arm/gic/v3/gicv3_private.h b/drivers/arm/gic/v3/gicv3_private.h
index c5d027d..93ee1a1 100644
--- a/drivers/arm/gic/v3/gicv3_private.h
+++ b/drivers/arm/gic/v3/gicv3_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -48,7 +48,8 @@
 #define	GICD_OFFSET_64(REG, id)						\
 	(((id) <= MAX_SPI_ID) ?						\
 	GICD_##REG##R + (((uintptr_t)(id) >> REG##R_SHIFT) << 3) :	\
-	GICD_##REG##RE + (((uintptr_t)(id) - MIN_ESPI_ID) << 3))
+	GICD_##REG##RE + ((((uintptr_t)(id) - MIN_ESPI_ID) >>		\
+					REG##R_SHIFT) << 3))
 
 #else	/* GICv3 */
 #define	GICD_OFFSET_8(REG, id)	\
@@ -232,6 +233,8 @@
 /*******************************************************************************
  * Private GICv3 helper function prototypes
  ******************************************************************************/
+unsigned int gicv3_get_spi_limit(uintptr_t gicd_base);
+unsigned int gicv3_get_espi_limit(uintptr_t gicd_base);
 void gicv3_spis_config_defaults(uintptr_t gicd_base);
 void gicv3_ppi_sgi_config_defaults(uintptr_t gicr_base);
 unsigned int gicv3_secure_ppi_sgi_config_props(uintptr_t gicr_base,
diff --git a/drivers/arm/tzc/tzc400.c b/drivers/arm/tzc/tzc400.c
index 95a5e7f..e4fc8c9 100644
--- a/drivers/arm/tzc/tzc400.c
+++ b/drivers/arm/tzc/tzc400.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,6 +10,7 @@
 #include <common/debug.h>
 #include <drivers/arm/tzc400.h>
 #include <lib/mmio.h>
+#include <lib/utils_def.h>
 
 #include "tzc_common_private.h"
 
@@ -67,9 +68,81 @@
 DEFINE_TZC_COMMON_WRITE_REGION_TOP(400, 400)
 DEFINE_TZC_COMMON_WRITE_REGION_ATTRIBUTES(400, 400)
 DEFINE_TZC_COMMON_WRITE_REGION_ID_ACCESS(400, 400)
+DEFINE_TZC_COMMON_UPDATE_FILTERS(400, 400)
 DEFINE_TZC_COMMON_CONFIGURE_REGION0(400)
 DEFINE_TZC_COMMON_CONFIGURE_REGION(400)
 
+static void _tzc400_clear_it(uintptr_t base, uint32_t filter)
+{
+	mmio_write_32(base + INT_CLEAR, BIT_32(filter));
+}
+
+static uint32_t _tzc400_get_int_by_filter(uintptr_t base, uint32_t filter)
+{
+	return mmio_read_32(base + INT_STATUS) & BIT_32(filter);
+}
+
+#if DEBUG
+static unsigned long _tzc400_get_fail_address(uintptr_t base, uint32_t filter)
+{
+	unsigned long fail_address;
+
+	fail_address = mmio_read_32(base + FAIL_ADDRESS_LOW_OFF +
+				    (filter * FILTER_OFFSET));
+#ifdef __aarch64__
+	fail_address += (unsigned long)mmio_read_32(base + FAIL_ADDRESS_HIGH_OFF +
+						    (filter * FILTER_OFFSET)) << 32;
+#endif
+
+	return fail_address;
+}
+
+static uint32_t _tzc400_get_fail_id(uintptr_t base, uint32_t filter)
+{
+	return mmio_read_32(base + FAIL_ID + (filter * FILTER_OFFSET));
+}
+
+static uint32_t _tzc400_get_fail_control(uintptr_t base, uint32_t filter)
+{
+	return mmio_read_32(base + FAIL_CONTROL_OFF + (filter * FILTER_OFFSET));
+}
+
+static void _tzc400_dump_fail_filter(uintptr_t base, uint32_t filter)
+{
+	uint32_t control_fail;
+	uint32_t fail_id;
+	unsigned long address_fail;
+
+	address_fail = _tzc400_get_fail_address(base, filter);
+	ERROR("Illegal access to 0x%lx:\n", address_fail);
+
+	fail_id = _tzc400_get_fail_id(base, filter);
+	ERROR("\tFAIL_ID = 0x%x\n", fail_id);
+
+	control_fail = _tzc400_get_fail_control(base, filter);
+	if (((control_fail & BIT_32(FAIL_CONTROL_NS_SHIFT)) >> FAIL_CONTROL_NS_SHIFT) ==
+	    FAIL_CONTROL_NS_NONSECURE) {
+		ERROR("\tNon-Secure\n");
+	} else {
+		ERROR("\tSecure\n");
+	}
+
+	if (((control_fail & BIT_32(FAIL_CONTROL_PRIV_SHIFT)) >> FAIL_CONTROL_PRIV_SHIFT) ==
+	    FAIL_CONTROL_PRIV_PRIV) {
+		ERROR("\tPrivilege\n");
+	} else {
+		ERROR("\tUnprivilege\n");
+	}
+
+	if (((control_fail & BIT_32(FAIL_CONTROL_DIR_SHIFT)) >> FAIL_CONTROL_DIR_SHIFT) ==
+	    FAIL_CONTROL_DIR_WRITE) {
+		ERROR("\tWrite\n");
+	} else {
+		ERROR("\tRead\n");
+	}
+}
+#endif /* DEBUG */
+
 static unsigned int _tzc400_get_gate_keeper(uintptr_t base,
 				unsigned int filter)
 {
@@ -108,11 +181,6 @@
 	assert(tzc400.base != 0U);
 	assert(action <= TZC_ACTION_ERR_INT);
 
-	/*
-	 * - Currently no handler is provided to trap an error via interrupt
-	 *   or exception.
-	 * - The interrupt action has not been tested.
-	 */
 	_tzc400_write_action(tzc400.base, action);
 }
 
@@ -162,7 +230,9 @@
 /*
  * `tzc400_configure_region` is used to program regions into the TrustZone
  * controller. A region can be associated with more than one filter. The
- * associated filters are passed in as a bitmap (bit0 = filter0).
+ * associated filters are passed in as a bitmap (bit0 = filter0), except that
+ * the value TZC_400_REGION_ATTR_FILTER_BIT_ALL selects all filters, based on
+ * the value of tzc400.num_filters.
  * NOTE:
  * Region 0 is special; it is preferable to use tzc400_configure_region0
  * for this region (see comment for that function).
@@ -176,6 +246,11 @@
 {
 	assert(tzc400.base != 0U);
 
+	/* Adjust filter mask by real filter number */
+	if (filters == TZC_400_REGION_ATTR_FILTER_BIT_ALL) {
+		filters = (1U << tzc400.num_filters) - 1U;
+	}
+
 	/* Do range checks on filters and regions. */
 	assert(((filters >> tzc400.num_filters) == 0U) &&
 	       (region < tzc400.num_regions));
@@ -197,6 +272,15 @@
 						sec_attr, nsaid_permissions);
 }
 
+void tzc400_update_filters(unsigned int region, unsigned int filters)
+{
+	/* Do range checks on filters and regions. */
+	assert(((filters >> tzc400.num_filters) == 0U) &&
+	       (region < tzc400.num_regions));
+
+	_tzc400_update_filters(tzc400.base, region, tzc400.num_filters, filters);
+}
+
 void tzc400_enable_filters(void)
 {
 	unsigned int state;
@@ -207,6 +291,11 @@
 	for (filter = 0U; filter < tzc400.num_filters; filter++) {
 		state = _tzc400_get_gate_keeper(tzc400.base, filter);
 		if (state != 0U) {
+			/* Filter 0 is special and cannot be disabled.
+			 * So here we allow it being already enabled. */
+			if (filter == 0U) {
+				continue;
+			}
 			/*
 			 * The TZC filter is already configured. Changing the
 			 * programmer's view in an active system can cause
@@ -228,13 +317,44 @@
 void tzc400_disable_filters(void)
 {
 	unsigned int filter;
+	unsigned int state;
+	unsigned int start = 0U;
 
 	assert(tzc400.base != 0U);
 
-	/*
-	 * We don't do the same state check as above as the Gatekeepers are
-	 * disabled after reset.
-	 */
-	for (filter = 0; filter < tzc400.num_filters; filter++)
+	/* Filter 0 is special and cannot be disabled. */
+	state = _tzc400_get_gate_keeper(tzc400.base, 0);
+	if (state != 0U) {
+		start++;
+	}
+	for (filter = start; filter < tzc400.num_filters; filter++)
 		_tzc400_set_gate_keeper(tzc400.base, filter, 0);
 }
+
+int tzc400_it_handler(void)
+{
+	uint32_t filter;
+	uint32_t filter_it_pending = tzc400.num_filters;
+
+	assert(tzc400.base != 0U);
+
+	for (filter = 0U; filter < tzc400.num_filters; filter++) {
+		if (_tzc400_get_int_by_filter(tzc400.base, filter) != 0U) {
+			filter_it_pending = filter;
+			break;
+		}
+	}
+
+	if (filter_it_pending == tzc400.num_filters) {
+		ERROR("TZC-400: No interrupt pending!\n");
+		return -1;
+	}
+
+#if DEBUG
+	_tzc400_dump_fail_filter(tzc400.base, filter_it_pending);
+#endif
+
+	_tzc400_clear_it(tzc400.base, filter_it_pending);
+
+	return 0;
+}
diff --git a/drivers/arm/tzc/tzc_common_private.h b/drivers/arm/tzc/tzc_common_private.h
index 1d99077..2090944 100644
--- a/drivers/arm/tzc/tzc_common_private.h
+++ b/drivers/arm/tzc/tzc_common_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -90,6 +90,27 @@
 	}
 
 /*
+ * It is used to modify the filters status for a defined region.
+ */
+#define DEFINE_TZC_COMMON_UPDATE_FILTERS(fn_name, macro_name)		\
+	static inline void _tzc##fn_name##_update_filters(		\
+						uintptr_t base,		\
+						unsigned int region_no,	\
+						unsigned int nbfilters, \
+						unsigned int filters)	\
+	{								\
+		uint32_t filters_mask = GENMASK(nbfilters - 1U, 0);	\
+									\
+		mmio_clrsetbits_32(base +				\
+			TZC_REGION_OFFSET(				\
+				TZC_##macro_name##_REGION_SIZE,		\
+				region_no) +				\
+			TZC_##macro_name##_REGION_ATTR_0_OFFSET,	\
+			filters_mask << TZC_REGION_ATTR_F_EN_SHIFT,	\
+			filters << TZC_REGION_ATTR_F_EN_SHIFT);		\
+	}
+
+/*
  * It is used to program region 0 ATTRIBUTES and ACCESS register.
  */
 #define DEFINE_TZC_COMMON_CONFIGURE_REGION0(fn_name)			\
diff --git a/drivers/auth/auth_mod.c b/drivers/auth/auth_mod.c
index 91ee1be..917ee4a 100644
--- a/drivers/auth/auth_mod.c
+++ b/drivers/auth/auth_mod.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,6 +16,7 @@
 #include <drivers/auth/auth_mod.h>
 #include <drivers/auth/crypto_mod.h>
 #include <drivers/auth/img_parser_mod.h>
+#include <drivers/fwu/fwu.h>
 #include <lib/fconf/fconf_tbbr_getter.h>
 #include <plat/common/platform.h>
 
@@ -222,20 +223,27 @@
  * To protect the system against rollback, the platform includes a non-volatile
  * counter whose value can only be increased. All certificates include a counter
  * value that should not be lower than the value stored in the platform. If the
- * value is larger, the counter in the platform must be updated to the new
- * value.
+ * value is larger, the counter in the platform must be updated to the new value
+ * (provided it has been authenticated).
  *
  * Return: 0 = success, Otherwise = error
+ * Returns additionally,
+ * cert_nv_ctr -> NV counter value present in the certificate
+ * need_nv_ctr_upgrade = 0 -> platform NV counter upgrade is not needed
+ * need_nv_ctr_upgrade = 1 -> platform NV counter upgrade is needed
  */
 static int auth_nvctr(const auth_method_param_nv_ctr_t *param,
 		      const auth_img_desc_t *img_desc,
-		      void *img, unsigned int img_len)
+		      void *img, unsigned int img_len,
+		      unsigned int *cert_nv_ctr,
+		      bool *need_nv_ctr_upgrade)
 {
 	char *p;
 	void *data_ptr = NULL;
 	unsigned int data_len, len, i;
-	unsigned int cert_nv_ctr, plat_nv_ctr;
+	unsigned int plat_nv_ctr;
 	int rc = 0;
+	bool is_trial_run = false;
 
 	/* Get the counter value from current image. The AM expects the IPM
 	 * to return the counter value as a DER encoded integer */
@@ -265,22 +273,23 @@
 	}
 
 	/* Convert to unsigned int. This code is for a little-endian CPU */
-	cert_nv_ctr = 0;
+	*cert_nv_ctr = 0;
 	for (i = 0; i < len; i++) {
-		cert_nv_ctr = (cert_nv_ctr << 8) | *p++;
+		*cert_nv_ctr = (*cert_nv_ctr << 8) | *p++;
 	}
 
 	/* Get the counter from the platform */
 	rc = plat_get_nv_ctr(param->plat_nv_ctr->cookie, &plat_nv_ctr);
 	return_if_error(rc);
 
-	if (cert_nv_ctr < plat_nv_ctr) {
+	if (*cert_nv_ctr < plat_nv_ctr) {
 		/* Invalid NV-counter */
 		return 1;
-	} else if (cert_nv_ctr > plat_nv_ctr) {
-		rc = plat_set_nv_ctr2(param->plat_nv_ctr->cookie,
-			img_desc, cert_nv_ctr);
-		return_if_error(rc);
+	} else if (*cert_nv_ctr > plat_nv_ctr) {
+#if PSA_FWU_SUPPORT && IMAGE_BL2
+		is_trial_run = fwu_is_trial_run_state();
+#endif /* PSA_FWU_SUPPORT && IMAGE_BL2 */
+		*need_nv_ctr_upgrade = !is_trial_run;
 	}
 
 	return 0;
@@ -351,6 +360,10 @@
 	void *param_ptr;
 	unsigned int param_len;
 	int rc, i;
+	unsigned int cert_nv_ctr = 0;
+	bool need_nv_ctr_upgrade = false;
+	bool sig_auth_done = false;
+	const auth_method_param_nv_ctr_t *nv_ctr_param = NULL;
 
 	/* Get the image descriptor from the chain of trust */
 	img_desc = FCONF_GET_PROPERTY(tbbr, cot, img_id);
@@ -376,10 +389,13 @@
 		case AUTH_METHOD_SIG:
 			rc = auth_signature(&auth_method->param.sig,
 					img_desc, img_ptr, img_len);
+			sig_auth_done = true;
 			break;
 		case AUTH_METHOD_NV_CTR:
-			rc = auth_nvctr(&auth_method->param.nv_ctr,
-					img_desc, img_ptr, img_len);
+			nv_ctr_param = &auth_method->param.nv_ctr;
+			rc = auth_nvctr(nv_ctr_param,
+					img_desc, img_ptr, img_len,
+					&cert_nv_ctr, &need_nv_ctr_upgrade);
 			break;
 		default:
 			/* Unknown authentication method */
@@ -389,6 +405,16 @@
 		return_if_error(rc);
 	}
 
+	/*
+	 * Do platform NV counter upgrade only if the certificate gets
+	 * authenticated, and platform NV-counter upgrade is needed.
+	 */
+	if (need_nv_ctr_upgrade && sig_auth_done) {
+		rc = plat_set_nv_ctr2(nv_ctr_param->plat_nv_ctr->cookie,
+				      img_desc, cert_nv_ctr);
+		return_if_error(rc);
+	}
+
 	/* Extract the parameters indicated in the image descriptor to
 	 * authenticate the children images. */
 	if (img_desc->authenticated_data != NULL) {
diff --git a/drivers/auth/cryptocell/713/cryptocell_crypto.c b/drivers/auth/cryptocell/713/cryptocell_crypto.c
index 5f390a2..077317e 100644
--- a/drivers/auth/cryptocell/713/cryptocell_crypto.c
+++ b/drivers/auth/cryptocell/713/cryptocell_crypto.c
@@ -13,6 +13,7 @@
 #include <drivers/auth/crypto_mod.h>
 
 #include <mbedtls/oid.h>
+#include <mbedtls/x509.h>
 
 #define LIB_NAME		"CryptoCell 713 SBROM"
 #define RSA_SALT_LEN		32
diff --git a/drivers/auth/tbbr/tbbr_cot_bl1_r64.c b/drivers/auth/tbbr/tbbr_cot_bl1_r64.c
new file mode 100644
index 0000000..e8e017c
--- /dev/null
+++ b/drivers/auth/tbbr/tbbr_cot_bl1_r64.c
@@ -0,0 +1,177 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <drivers/auth/auth_mod.h>
+#include <drivers/auth/mbedtls/mbedtls_config.h>
+#include <drivers/auth/tbbr_cot_common.h>
+
+#if USE_TBBR_DEFS
+#include <tools_share/tbbr_oid.h>
+#else
+#include <platform_oid.h>
+#endif
+#include <platform_def.h>
+
+
+static unsigned char trusted_world_pk_buf[PK_DER_LEN];
+static unsigned char non_trusted_world_pk_buf[PK_DER_LEN];
+static unsigned char content_pk_buf[PK_DER_LEN];
+static unsigned char nt_fw_config_hash_buf[HASH_DER_LEN];
+
+static auth_param_type_desc_t non_trusted_nv_ctr = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_NV_CTR, NON_TRUSTED_FW_NVCOUNTER_OID);
+static auth_param_type_desc_t trusted_world_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, TRUSTED_WORLD_PK_OID);
+static auth_param_type_desc_t non_trusted_world_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, NON_TRUSTED_WORLD_PK_OID);
+static auth_param_type_desc_t nt_fw_content_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, NON_TRUSTED_FW_CONTENT_CERT_PK_OID);
+static auth_param_type_desc_t nt_world_bl_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, NON_TRUSTED_WORLD_BOOTLOADER_HASH_OID);
+static auth_param_type_desc_t nt_fw_config_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, NON_TRUSTED_FW_CONFIG_HASH_OID);
+/*
+ * Trusted key certificate
+ */
+static const auth_img_desc_t trusted_key_cert = {
+	.img_id = TRUSTED_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &subject_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &trusted_world_pk,
+			.data = {
+				.ptr = (void *)trusted_world_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &non_trusted_world_pk,
+			.data = {
+				.ptr = (void *)non_trusted_world_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+/*
+ * Non-Trusted Firmware
+ */
+static const auth_img_desc_t non_trusted_fw_key_cert = {
+	.img_id = NON_TRUSTED_FW_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &non_trusted_nv_ctr,
+				.plat_nv_ctr = &non_trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &nt_fw_content_pk,
+			.data = {
+				.ptr = (void *)content_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t non_trusted_fw_content_cert = {
+	.img_id = NON_TRUSTED_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &non_trusted_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &nt_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &non_trusted_nv_ctr,
+				.plat_nv_ctr = &non_trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &nt_world_bl_hash,
+			.data = {
+				.ptr = (void *)nt_world_bl_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &nt_fw_config_hash,
+			.data = {
+				.ptr = (void *)nt_fw_config_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl33_image = {
+	.img_id = BL33_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &non_trusted_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &nt_world_bl_hash
+			}
+		}
+	}
+};
+
+static const auth_img_desc_t * const cot_desc[] = {
+	[TRUSTED_KEY_CERT_ID]			=	&trusted_key_cert,
+	[NON_TRUSTED_FW_KEY_CERT_ID]		=	&non_trusted_fw_key_cert,
+	[NON_TRUSTED_FW_CONTENT_CERT_ID]	=	&non_trusted_fw_content_cert,
+	[BL33_IMAGE_ID]				=	&bl33_image,
+};
+
+/* Register the CoT in the authentication module */
+REGISTER_COT(cot_desc);
diff --git a/drivers/brcm/emmc/emmc_csl_sdcard.c b/drivers/brcm/emmc/emmc_csl_sdcard.c
index d6ad4bc..9e2c618 100644
--- a/drivers/brcm/emmc/emmc_csl_sdcard.c
+++ b/drivers/brcm/emmc/emmc_csl_sdcard.c
@@ -4,9 +4,11 @@
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <inttypes.h>
+#include <stddef.h>
+#include <stdint.h>
 #include <stdlib.h>
 #include <string.h>
-#include <stddef.h>
 
 #include <arch_helpers.h>
 #include <lib/mmio.h>
@@ -521,7 +523,7 @@
 {
 	int rc = SD_OK;
 
-	VERBOSE("XFER: dest: 0x%llx, addr: 0x%x, size: 0x%x bytes\n",
+	VERBOSE("XFER: dest: 0x%" PRIx64 ", addr: 0x%x, size: 0x%x bytes\n",
 		(uint64_t)base, addr, length);
 
 	if ((length / handle->device->cfg.blockSize) > 1) {
diff --git a/drivers/brcm/i2c/i2c.c b/drivers/brcm/i2c/i2c.c
new file mode 100644
index 0000000..2096a82
--- /dev/null
+++ b/drivers/brcm/i2c/i2c.c
@@ -0,0 +1,886 @@
+/*
+ * Copyright (c) 2016 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <i2c.h>
+#include <i2c_regs.h>
+#include <lib/mmio.h>
+
+#include <platform_def.h>
+
+/* Max instances */
+#define MAX_I2C					2U
+
+/* Transaction error codes defined in Master command register (0x30) */
+#define MSTR_STS_XACT_SUCCESS			0U
+#define MSTR_STS_LOST_ARB			1U
+#define MSTR_STS_NACK_FIRST_BYTE		2U
+ /* NACK on a byte other than the first byte */
+#define MSTR_STS_NACK_NON_FIRST_BYTE		3U
+
+#define MSTR_STS_TTIMEOUT_EXCEEDED		4U
+#define MSTR_STS_TX_TLOW_MEXT_EXCEEDED		5U
+#define MSTR_STS_RX_TLOW_MEXT_EXCEEDED		6U
+
+/* SMBUS protocol values defined in register 0x30 */
+#define SMBUS_PROT_QUICK_CMD			0U
+#define SMBUS_PROT_SEND_BYTE			1U
+#define SMBUS_PROT_RECV_BYTE			2U
+#define SMBUS_PROT_WR_BYTE			3U
+#define SMBUS_PROT_RD_BYTE			4U
+#define SMBUS_PROT_WR_WORD			5U
+#define SMBUS_PROT_RD_WORD			6U
+#define SMBUS_PROT_BLK_WR			7U
+#define SMBUS_PROT_BLK_RD			8U
+#define SMBUS_PROT_PROC_CALL			9U
+#define SMBUS_PROT_BLK_WR_BLK_RD_PROC_CALL	10U
+
+/* Number can be changed later */
+#define BUS_BUSY_COUNT				100000U
+
+#define IPROC_I2C_INVALID_ADDR			0xFFU
+
+#define I2C_SMBUS_BLOCK_MAX			32U
+
+/*
+ * Enum to specify clock speed. The user will provide it during initialization.
+ * If needed, it can be changed dynamically
+ */
+typedef enum iproc_smb_clk_freq {
+	IPROC_SMB_SPEED_100KHz = 0,
+	IPROC_SMB_SPEED_400KHz = 1,
+	IPROC_SMB_SPEED_INVALID = 255
+} smb_clk_freq_t;
+
+/* Structure used to pass information to read/write functions. */
+struct iproc_xact_info {
+	/* Bus Identifier */
+	uint32_t bus_id;
+	/* Device Address */
+	uint8_t devaddr;
+	/* Passed by caller to send SMBus command cod e*/
+	uint8_t command;
+	/* actual data passed by the caller */
+	uint8_t *data;
+	/* Size of data buffer passed */
+	uint32_t size;
+	/* Sent by caller specifying PEC, 10-bit addresses */
+	uint16_t flags;
+	/* SMBus protocol to use to perform transaction */
+	uint8_t smb_proto;
+	/* true if command field below is valid. Otherwise, false */
+	uint32_t cmd_valid;
+};
+
+static const uintptr_t smbus_base_reg_addr[MAX_I2C] = {
+	SMBUS0_REGS_BASE,
+	SMBUS1_REGS_BASE
+};
+
+/* Function to read a value from specified register. */
+static uint32_t iproc_i2c_reg_read(uint32_t bus_id, unsigned long reg_addr)
+{
+	uint32_t val;
+	uintptr_t smbus;
+
+	smbus = smbus_base_reg_addr[bus_id];
+
+	val = mmio_read_32(smbus + reg_addr);
+	VERBOSE("i2c %u: reg %p read 0x%x\n", bus_id,
+		(void *)(smbus + reg_addr), val);
+	return val;
+}
+
+/* Function to write a value ('val') in to a specified register. */
+static void iproc_i2c_reg_write(uint32_t bus_id,
+				unsigned long reg_addr,
+				uint32_t val)
+{
+	uintptr_t smbus;
+
+	smbus = smbus_base_reg_addr[bus_id];
+
+	mmio_write_32((smbus + reg_addr), val);
+	VERBOSE("i2c %u: reg %p wrote 0x%x\n", bus_id,
+		(void *)(smbus + reg_addr), val);
+}
+
+/* Function to clear and set bits in a specified register. */
+static void iproc_i2c_reg_clearset(uint32_t bus_id,
+				   unsigned long reg_addr,
+				   uint32_t clear,
+				   uint32_t set)
+{
+	uintptr_t smbus;
+
+	smbus = smbus_base_reg_addr[bus_id];
+
+	mmio_clrsetbits_32((smbus + reg_addr), clear, set);
+	VERBOSE("i2c %u: reg %p clear 0x%x, set 0x%x\n", bus_id,
+		(void *)(smbus + reg_addr), clear, set);
+}
+
+/* Function to dump all SMBUS register */
+#ifdef BCM_I2C_DEBUG
+static int iproc_dump_i2c_regs(uint32_t bus_id)
+{
+	uint32_t regval;
+
+	if (bus_id > MAX_I2C) {
+		return -1;
+	}
+
+	INFO("----------------------------------------------\n");
+	INFO("%s: Dumping SMBus %u registers...\n", __func__, bus_id);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_CFG_REG);
+	INFO("SMB_CFG_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_TIMGCFG_REG);
+	INFO("SMB_TIMGCFG_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_ADDR_REG);
+	INFO("SMB_ADDR_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_MSTRFIFOCTL_REG);
+	INFO("SMB_MSTRFIFOCTL_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_SLVFIFOCTL_REG);
+	INFO("SMB_SLVFIFOCTL_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_BITBANGCTL_REG);
+	INFO("SMB_BITBANGCTL_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_MSTRCMD_REG);
+	INFO("SMB_MSTRCMD_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_SLVCMD_REG);
+	INFO("SMB_SLVCMD_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_EVTEN_REG);
+	INFO("SMB_EVTEN_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_EVTSTS_REG);
+	INFO("SMB_EVTSTS_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_MSTRDATAWR_REG);
+	INFO("SMB_MSTRDATAWR_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_MSTRDATARD_REG);
+	INFO("SMB_MSTRDATARD_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_SLVDATAWR_REG);
+	INFO("SMB_SLVDATAWR_REG=0x%x\n", regval);
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_SLVDATARD_REG);
+	INFO("SMB_SLVDATARD_REG=0x%x\n", regval);
+
+	INFO("----------------------------------------------\n");
+	return 0;
+}
+#endif
+
+/*
+ * Function to ensure that the previous transaction was completed before
+ * initiating a new transaction. It can also be used in polling mode to
+ * check status of completion of a command
+ */
+static int iproc_i2c_startbusy_wait(uint32_t bus_id)
+{
+	uint32_t regval;
+	uint32_t retry = 0U;
+
+	/*
+	 * Check if an operation is in progress. During probe it won't be.
+	 * Want to make sure that the transaction in progress is completed.
+	 */
+	do {
+		udelay(1U);
+		regval = iproc_i2c_reg_read(bus_id, SMB_MSTRCMD_REG);
+		regval &= SMB_MSTRSTARTBUSYCMD_MASK;
+		if (retry++ > BUS_BUSY_COUNT) {
+			ERROR("%s: START_BUSY bit didn't clear, exiting\n",
+			      __func__);
+			return -1;
+		}
+
+	} while (regval != 0U);
+
+	return 0;
+}
+
+/*
+ * This function copies data to SMBus's Tx FIFO. Valid for write transactions
+ * info: Data to copy in to Tx FIFO. For read commands, the size should be
+ * set to zero by the caller
+ */
+static void iproc_i2c_write_trans_data(struct iproc_xact_info *info)
+{
+	uint32_t regval;
+	uint8_t devaddr;
+	uint32_t i;
+	uint32_t num_data_bytes = 0U;
+
+#ifdef BCM_I2C_DEBUG
+	INFO("%s:dev_addr=0x%x,cmd_valid=%d, cmd=0x%x, size=%u proto=%d\n",
+	     __func__, info->devaddr, info->cmd_valid, info->command,
+	     info->size, info->smb_proto);
+#endif
+	/* Shift devaddr by 1 bit since SMBus uses the low bit[0] for R/W_n */
+	devaddr = (info->devaddr << 1);
+
+	/*
+	 * Depending on the SMBus protocol, we need to write additional
+	 * transaction data in to Tx FIFO. Refer to section 5.5 of SMBus spec
+	 * for sequence for a transaction
+	 */
+	switch (info->smb_proto) {
+	case SMBUS_PROT_RECV_BYTE:
+		/* No additional data to be written */
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr | 0x1U | SMB_MSTRWRSTS_MASK);
+		break;
+	case SMBUS_PROT_SEND_BYTE:
+		num_data_bytes = info->size;
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr);
+		break;
+	case SMBUS_PROT_RD_BYTE:
+	case SMBUS_PROT_RD_WORD:
+	case SMBUS_PROT_BLK_RD:
+		/* Write slave address with R/W~ set (bit #0) */
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr | 0x1U);
+		break;
+	case SMBUS_PROT_BLK_WR_BLK_RD_PROC_CALL:
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr | 0x1U | SMB_MSTRWRSTS_MASK);
+		break;
+	case SMBUS_PROT_WR_BYTE:
+	case SMBUS_PROT_WR_WORD:
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr);
+		/*
+		 * No additional bytes to be written. Data portion is written
+		 * in the 'for' loop below
+		 */
+		num_data_bytes = info->size;
+		break;
+	case SMBUS_PROT_BLK_WR:
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    devaddr);
+		/* 3rd byte is byte count */
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    info->size);
+		num_data_bytes = info->size;
+		break;
+	default:
+		return;
+	}
+
+	/* If the protocol needs command code, copy it */
+	if (info->cmd_valid) {
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    info->command);
+	}
+
+	/*
+	 * Copy actual data from caller. In general, for reads,
+	 * no data is copied.
+	 */
+	for (i = 0U; num_data_bytes; --num_data_bytes, i++) {
+		/* For the last byte, set MASTER_WR_STATUS bit */
+		regval = (num_data_bytes == 1U) ?
+			 info->data[i] | SMB_MSTRWRSTS_MASK : info->data[i];
+		iproc_i2c_reg_write(info->bus_id, SMB_MSTRDATAWR_REG,
+				    regval);
+	}
+}
+
+/*
+ * This function writes to the master command register and
+ * then polls for completion
+ */
+static int iproc_i2c_write_master_command(uint32_t mastercmd,
+					  struct iproc_xact_info *info)
+{
+	uint32_t retry = 0U;
+	uint32_t regval;
+
+	iproc_i2c_reg_write(info->bus_id, SMB_MSTRCMD_REG, mastercmd);
+
+	/* Check for Master Busy status */
+	regval = iproc_i2c_reg_read(info->bus_id, SMB_MSTRCMD_REG);
+	while ((regval & SMB_MSTRSTARTBUSYCMD_MASK) != 0U) {
+		udelay(1U);
+		if (retry++ > BUS_BUSY_COUNT) {
+			ERROR("%s: START_BUSY bit didn't clear, exiting\n",
+				__func__);
+			return -1;
+		}
+		regval = iproc_i2c_reg_read(info->bus_id, SMB_MSTRCMD_REG);
+	}
+
+	/* If start_busy bit cleared, check if there are any errors */
+	if (!(regval & SMB_MSTRSTARTBUSYCMD_MASK)) {
+		/* start_busy bit cleared, check master_status field now */
+		regval &= SMB_MSTRSTS_MASK;
+		regval >>= SMB_MSTRSTS_SHIFT;
+		if (regval != MSTR_STS_XACT_SUCCESS) {
+			/* Error We can flush Tx FIFO here */
+			ERROR("%s: ERROR: %u exiting\n", __func__, regval);
+			return -1;
+		}
+	}
+	return 0;
+
+}
+/* Function to initiate data send and verify completion status */
+static int iproc_i2c_data_send(struct iproc_xact_info *info)
+{
+	int rc;
+	uint32_t mastercmd;
+
+	/* Make sure the previous transaction completed */
+	rc = iproc_i2c_startbusy_wait(info->bus_id);
+
+	if (rc < 0) {
+		WARN("%s: Send: bus is busy, exiting\n", __func__);
+		return rc;
+	}
+	/* Write transaction bytes to Tx FIFO */
+	iproc_i2c_write_trans_data(info);
+
+	/*
+	 * Program master command register (0x30) with protocol type and set
+	 * start_busy_command bit to initiate the write transaction
+	 */
+	mastercmd = (info->smb_proto << SMB_MSTRSMBUSPROTO_SHIFT) |
+	    SMB_MSTRSTARTBUSYCMD_MASK;
+
+	if (iproc_i2c_write_master_command(mastercmd, info)) {
+		return -1;
+	}
+
+	return 0;
+}
+
+/*
+ * Function to initiate data receive, verify completion status,
+ * and read from SMBUS Read FIFO
+ */
+static int iproc_i2c_data_recv(struct iproc_xact_info *info,
+			       uint32_t *num_bytes_read)
+{
+	int rc;
+	uint32_t mastercmd;
+	uint32_t regval;
+
+	/* Make sure the previous transaction completed */
+	rc = iproc_i2c_startbusy_wait(info->bus_id);
+
+	if (rc < 0) {
+		WARN("%s: Receive: Bus is busy, exiting\n", __func__);
+		return rc;
+	}
+
+	/* Program all transaction bytes into master Tx FIFO */
+	iproc_i2c_write_trans_data(info);
+
+	/*
+	 * Program master command register (0x30) with protocol type and set
+	 * start_busy_command bit to initiate the write transaction
+	 */
+	mastercmd = (info->smb_proto << SMB_MSTRSMBUSPROTO_SHIFT) |
+		     SMB_MSTRSTARTBUSYCMD_MASK | info->size;
+
+	if (iproc_i2c_write_master_command(mastercmd, info)) {
+		return -1;
+	}
+
+	/* Read received byte(s), after TX out address etc */
+	regval = iproc_i2c_reg_read(info->bus_id, SMB_MSTRDATARD_REG);
+
+	/* For block read, protocol (hw) returns byte count,as the first byte */
+	if (info->smb_proto == SMBUS_PROT_BLK_RD) {
+		uint32_t i;
+
+		*num_bytes_read = regval & SMB_MSTRRDDATA_MASK;
+		/*
+		 * Limit to reading a max of 32 bytes only; just a safeguard.
+		 * If # bytes read is a number > 32, check transaction set up,
+		 * and contact hw engg.
+		 * Assumption: PEC is disabled
+		 */
+		for (i = 0U; (i < *num_bytes_read) &&
+		     (i < I2C_SMBUS_BLOCK_MAX); i++) {
+			/* Read Rx FIFO for data bytes */
+			regval = iproc_i2c_reg_read(info->bus_id,
+						    SMB_MSTRDATARD_REG);
+			info->data[i] = regval & SMB_MSTRRDDATA_MASK;
+		}
+	} else {
+		/* 1 Byte data */
+		*info->data = regval & SMB_MSTRRDDATA_MASK;
+		*num_bytes_read = 1U;
+	}
+
+	return 0;
+}
+
+/*
+ * This function set clock frequency for SMBus block. As per hardware
+ * engineering, the clock frequency can be changed dynamically.
+ */
+static int iproc_i2c_set_clk_freq(uint32_t bus_id, smb_clk_freq_t freq)
+{
+	uint32_t val;
+
+	switch (freq) {
+	case IPROC_SMB_SPEED_100KHz:
+		val = 0U;
+		break;
+	case IPROC_SMB_SPEED_400KHz:
+		val = 1U;
+		break;
+	default:
+		return -1;
+	}
+
+	iproc_i2c_reg_clearset(bus_id, SMB_TIMGCFG_REG,
+			       SMB_TIMGCFG_MODE400_MASK,
+			       val << SMB_TIMGCFG_MODE400_SHIFT);
+
+	return 0;
+}
+
+/* Helper function to fill the iproc_xact_info structure */
+static void iproc_i2c_fill_info(struct iproc_xact_info *info, uint32_t bus_id,
+				uint8_t devaddr, uint8_t cmd, uint8_t *value,
+				uint8_t smb_proto, uint32_t cmd_valid)
+{
+	info->bus_id = bus_id;
+	info->devaddr = devaddr;
+	info->command = (uint8_t)cmd;
+	info->smb_proto = smb_proto;
+	info->data = value;
+	info->size = 1U;
+	info->flags = 0U;
+	info->cmd_valid = cmd_valid;
+}
+
+/* This function initializes the SMBUS */
+static void iproc_i2c_init(uint32_t bus_id, int speed)
+{
+	uint32_t regval;
+
+#ifdef BCM_I2C_DEBUG
+	INFO("%s: Enter Init\n", __func__);
+#endif
+
+	/* Put controller in reset */
+	regval = iproc_i2c_reg_read(bus_id, SMB_CFG_REG);
+	regval |= BIT(SMB_CFG_RST_SHIFT);
+	regval &= ~(BIT(SMB_CFG_SMBEN_SHIFT));
+	iproc_i2c_reg_write(bus_id, SMB_CFG_REG, regval);
+
+	/* Wait 100 usec per spec */
+	udelay(100U);
+
+	/* Bring controller out of reset */
+	regval &= ~(BIT(SMB_CFG_RST_SHIFT));
+	iproc_i2c_reg_write(bus_id, SMB_CFG_REG, regval);
+
+	/*
+	 * Flush Tx, Rx FIFOs. Note we are setting the Rx FIFO threshold to 0.
+	 * May be OK since we are setting RX_EVENT and RX_FIFO_FULL interrupts
+	 */
+	regval = SMB_MSTRRXFIFOFLSH_MASK | SMB_MSTRTXFIFOFLSH_MASK;
+	iproc_i2c_reg_write(bus_id, SMB_MSTRFIFOCTL_REG, regval);
+
+	/*
+	 * Enable SMbus block. Note, we are setting MASTER_RETRY_COUNT to zero
+	 * since there will be only one master
+	 */
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_CFG_REG);
+	regval |= SMB_CFG_SMBEN_MASK;
+	iproc_i2c_reg_write(bus_id, SMB_CFG_REG, regval);
+	/* Wait a minimum of 50 Usec, as per SMB hw doc. But we wait longer */
+	mdelay(10U);
+
+	/* If error then set default speed */
+	if (i2c_set_bus_speed(bus_id, speed)) {
+		i2c_set_bus_speed(bus_id, I2C_SPEED_DEFAULT);
+	}
+
+	/* Disable intrs */
+	regval = 0x0U;
+	iproc_i2c_reg_write(bus_id, SMB_EVTEN_REG, regval);
+
+	/* Clear intrs (W1TC) */
+	regval = iproc_i2c_reg_read(bus_id, SMB_EVTSTS_REG);
+	iproc_i2c_reg_write(bus_id, SMB_EVTSTS_REG, regval);
+
+#ifdef BCM_I2C_DEBUG
+	iproc_dump_i2c_regs(bus_id);
+
+	INFO("%s: Exit Init Successfully\n", __func__);
+#endif
+}
+
+/*
+ * Function Name:    i2c_init
+ *
+ * Description:
+ *	This function initializes the SMBUS.
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *	speed  - I2C bus speed in Hz
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_init(uint32_t bus_id, int speed)
+{
+	if (bus_id > MAX_I2C) {
+		WARN("%s: Invalid Bus %u\n", __func__, bus_id);
+		return -1;
+	}
+
+	iproc_i2c_init(bus_id, speed);
+	return 0U;
+}
+
+/*
+ * Function Name:    i2c_probe
+ *
+ * Description:
+ *	This function probes the I2C bus for the existence of the specified
+ *	device.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_probe(uint32_t bus_id, uint8_t devaddr)
+{
+	uint32_t regval;
+	int rc;
+
+	/*
+	 * i2c_init() Initializes internal regs, disable intrs (and then clear intrs),
+	 * set fifo thresholds, etc.
+	 * Shift devaddr by 1 bit since SMBus uses the low bit[0] for R/W_n
+	 */
+	regval = (devaddr << 1U);
+	iproc_i2c_reg_write(bus_id, SMB_MSTRDATAWR_REG, regval);
+
+	regval = ((SMBUS_PROT_QUICK_CMD << SMB_MSTRSMBUSPROTO_SHIFT) |
+		  SMB_MSTRSTARTBUSYCMD_MASK);
+	iproc_i2c_reg_write(bus_id, SMB_MSTRCMD_REG, regval);
+
+	rc = iproc_i2c_startbusy_wait(bus_id);
+
+	if (rc < 0) {
+		WARN("%s: Probe: bus is busy, exiting\n", __func__);
+		return rc;
+	}
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_MSTRCMD_REG);
+	if (((regval & SMB_MSTRSTS_MASK) >> SMB_MSTRSTS_SHIFT) == 0)
+		VERBOSE("i2c device address: 0x%x\n", devaddr);
+	else
+		return -1;
+
+#ifdef BCM_I2C_DEBUG
+	iproc_dump_i2c_regs(bus_id);
+#endif
+	return 0;
+}
+
+/*
+ * Function Name:    i2c_recv_byte
+ *
+ * Description:
+ *	This function reads I2C data from a device without specifying
+ *	a command regsiter.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	value   - Data Read
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_recv_byte(uint32_t bus_id, uint8_t devaddr, uint8_t *value)
+{
+	int rc;
+	struct iproc_xact_info info;
+	uint32_t num_bytes_read = 0;
+
+	iproc_i2c_fill_info(&info, bus_id, devaddr, 0U, value,
+			    SMBUS_PROT_RECV_BYTE, 0U);
+
+	/* Refer to i2c_smbus_read_byte for params passed. */
+	rc = iproc_i2c_data_recv(&info, &num_bytes_read);
+
+	if (rc < 0) {
+		printf("%s: %s error accessing device 0x%x\n",
+		__func__, "Read", devaddr);
+	}
+
+	return rc;
+}
+
+/*
+ * Function Name:    i2c_send_byte
+ *
+ * Description:
+ *	This function send I2C data to a device without specifying
+ *	a command regsiter.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	value   - Data Send
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_send_byte(uint32_t bus_id, uint8_t devaddr, uint8_t value)
+{
+	int rc;
+	struct iproc_xact_info info;
+
+	iproc_i2c_fill_info(&info, bus_id, devaddr, 0U, &value,
+			    SMBUS_PROT_SEND_BYTE, 0U);
+
+	/* Refer to i2c_smbus_write_byte params passed. */
+	rc = iproc_i2c_data_send(&info);
+
+	if (rc < 0) {
+		ERROR("%s: %s error accessing device 0x%x\n",
+		__func__, "Write", devaddr);
+	}
+
+	return rc;
+}
+
+/* Helper function to read a single byte */
+static int i2c_read_byte(uint32_t bus_id,
+			 uint8_t devaddr,
+			 uint8_t regoffset,
+			 uint8_t *value)
+{
+	int rc;
+	struct iproc_xact_info info;
+	uint32_t num_bytes_read = 0U;
+
+	iproc_i2c_fill_info(&info, bus_id, devaddr, regoffset, value,
+			    SMBUS_PROT_RD_BYTE, 1U);
+
+	/* Refer to i2c_smbus_read_byte for params passed. */
+	rc = iproc_i2c_data_recv(&info, &num_bytes_read);
+
+	if (rc < 0) {
+		ERROR("%s: %s error accessing device 0x%x\n",
+		       __func__, "Read", devaddr);
+	}
+	return rc;
+}
+
+/*
+ * Function Name:    i2c_read
+ *
+ * Description:
+ *	This function reads I2C data from a device with a designated
+ *	command register
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	addr    - Register Offset
+ *	alen    - Address Length, 1 for byte, 2 for word (not supported)
+ *	buffer  - Data Buffer
+ *	len     - Data Length in bytes
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_read(uint32_t bus_id,
+	     uint8_t devaddr,
+	     uint32_t addr,
+	     int alen,
+	     uint8_t *buffer,
+	     int len)
+{
+	uint32_t i;
+
+	if (alen > 1) {
+		WARN("I2C read: addr len %d not supported\n", alen);
+		return -1;
+	}
+
+	if (addr + len > 256) {
+		WARN("I2C read: address out of range\n");
+		return -1;
+	}
+
+	for (i = 0U; i < len; i++) {
+		if (i2c_read_byte(bus_id, devaddr, addr + i, &buffer[i])) {
+			ERROR("I2C read: I/O error\n");
+			iproc_i2c_init(bus_id, i2c_get_bus_speed(bus_id));
+			return -1;
+		}
+	}
+
+	return 0;
+}
+
+/* Helper function to write a single byte */
+static int i2c_write_byte(uint32_t bus_id,
+			  uint8_t devaddr,
+			  uint8_t regoffset,
+			  uint8_t value)
+{
+	int rc;
+	struct iproc_xact_info info;
+
+	iproc_i2c_fill_info(&info, bus_id, devaddr, regoffset, &value,
+			    SMBUS_PROT_WR_BYTE, 1U);
+
+	/* Refer to i2c_smbus_write_byte params passed. */
+	rc = iproc_i2c_data_send(&info);
+
+	if (rc < 0) {
+		ERROR("%s: %s error accessing device 0x%x\n",
+		       __func__, "Write", devaddr);
+		return -1;
+	}
+
+	return 0;
+}
+
+/*
+ * Function Name:    i2c_write
+ *
+ * Description:
+ *	This function write I2C data to a device with a designated
+ *	command register
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	addr    - Register Offset
+ *	alen    - Address Length, 1 for byte, 2 for word (not supported)
+ *	buffer  - Data Buffer
+ *	len     - Data Length in bytes
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_write(uint32_t bus_id,
+	      uint8_t devaddr,
+	      uint32_t addr,
+	      int alen,
+	      uint8_t *buffer,
+	      int len)
+{
+	uint32_t i;
+
+	if (alen > 1) {
+		WARN("I2C write: addr len %d not supported\n", alen);
+		return -1;
+	}
+
+	if (addr + len > 256U) {
+		WARN("I2C write: address out of range\n");
+		return -1;
+	}
+
+	for (i = 0U; i < len; i++) {
+		if (i2c_write_byte(bus_id, devaddr, addr + i, buffer[i])) {
+			ERROR("I2C write: I/O error\n");
+			iproc_i2c_init(bus_id, i2c_get_bus_speed(bus_id));
+			return -1;
+		}
+	}
+	return 0;
+}
+
+/*
+ * Function Name:    i2c_set_bus_speed
+ *
+ * Description:
+ *	This function configures the SMBUS speed
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *	speed  - I2C bus speed in Hz
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_set_bus_speed(uint32_t bus_id, uint32_t speed)
+{
+	switch (speed) {
+	case I2C_SPEED_100KHz:
+		iproc_i2c_set_clk_freq(bus_id, IPROC_SMB_SPEED_100KHz);
+		break;
+
+	case I2C_SPEED_400KHz:
+		iproc_i2c_set_clk_freq(bus_id, IPROC_SMB_SPEED_400KHz);
+		break;
+
+	default:
+		return -1;
+	}
+	return 0;
+}
+
+/*
+ * Function Name:    i2c_get_bus_speed
+ *
+ * Description:
+ *	This function returns the SMBUS speed.
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *
+ * Return:
+ *	Bus speed in Hz, 0 on failure
+ */
+uint32_t i2c_get_bus_speed(uint32_t bus_id)
+{
+	uint32_t regval;
+	uint32_t retval = 0U;
+
+	regval = iproc_i2c_reg_read(bus_id, SMB_TIMGCFG_REG);
+	regval &= SMB_TIMGCFG_MODE400_MASK;
+	regval >>= SMB_TIMGCFG_MODE400_SHIFT;
+
+	switch (regval) {
+	case IPROC_SMB_SPEED_100KHz:
+		retval = I2C_SPEED_100KHz;
+		break;
+
+	case IPROC_SMB_SPEED_400KHz:
+		retval = I2C_SPEED_400KHz;
+		break;
+
+	default:
+		break;
+	}
+	return retval;
+}
+
diff --git a/drivers/brcm/mdio/mdio.c b/drivers/brcm/mdio/mdio.c
new file mode 100644
index 0000000..1cf9d66
--- /dev/null
+++ b/drivers/brcm/mdio/mdio.c
@@ -0,0 +1,87 @@
+/*
+ * Copyright (c) 2016 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <string.h>
+
+#include <platform_def.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+#include <mdio.h>
+
+static int mdio_op_status(uint32_t result)
+{
+	uint32_t timeout = 1000000U; /* loop for 1s */
+	uint32_t val;
+
+	do {
+		val = mmio_read_32(CMIC_MIIM_STAT);
+		if ((val & MDIO_STAT_DONE) == result) {
+			return 0;
+		}
+
+		udelay(1U);
+	} while (timeout-- != 0U);
+	return -1;
+}
+
+static int mdio_op(uint16_t busid, uint16_t phyid, uint32_t reg,
+	       uint16_t val, uint8_t op)
+{
+	uint32_t param;
+	int ret;
+
+	mmio_write_32(CMIC_MIIM_CTRL, 0U);
+	ret = mdio_op_status(0U);
+	if (ret != 0) {
+		goto err;
+	}
+
+	param = 0U;
+	param |= 1U << MDIO_PARAM_INTERNAL_SEL;
+	param |= (busid & MDIO_PARAM_BUSID_MASK) << MDIO_PARAM_BUSID;
+	param |= (phyid & MDIO_PARAM_PHYID_MASK) << MDIO_PARAM_PHYID;
+	param |= (val & MDIO_PARAM_DATA_MASK) << MDIO_PARAM_DATA;
+
+	mmio_write_32(CMIC_MIIM_PARAM, param);
+
+	mmio_write_32(CMIC_MIIM_ADDRESS, reg);
+
+	mmio_write_32(CMIC_MIIM_CTRL, op);
+
+	ret = mdio_op_status(1U);
+	if (ret != 0) {
+		goto err;
+	}
+
+	if (op == MDIO_CTRL_READ_OP) {
+		ret = mmio_read_32(CMIC_MIIM_READ_DATA) & MDIO_READ_DATA_MASK;
+	}
+err:
+	return ret;
+}
+
+int mdio_write(uint16_t busid, uint16_t phyid, uint32_t reg, uint16_t val)
+{
+	int ret;
+
+	ret = mdio_op(busid, phyid, reg, val, MDIO_CTRL_WRITE_OP);
+	if (ret == -1) {
+		INFO("MDIO write fail\n");
+	}
+	return ret;
+}
+
+int mdio_read(uint16_t busid, uint16_t phyid, uint32_t reg)
+{
+	int ret;
+
+	ret = mdio_op(busid, phyid, reg, 0U, MDIO_CTRL_READ_OP);
+	if (ret == -1) {
+		INFO("MDIO read fail\n");
+	}
+	return ret;
+}
diff --git a/drivers/cadence/uart/aarch64/cdns_console.S b/drivers/cadence/uart/aarch64/cdns_console.S
index d1995e3..4c1a80e 100644
--- a/drivers/cadence/uart/aarch64/cdns_console.S
+++ b/drivers/cadence/uart/aarch64/cdns_console.S
@@ -105,15 +105,15 @@
 	cmp	w0, #0xA
 	b.ne	2f
 1:
-	/* Check if the transmit FIFO is full */
+	/* Check if the transmit FIFO is empty */
 	ldr	w2, [x1, #R_UART_SR]
-	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 1b
+	tbz	w2, #UART_SR_INTR_TEMPTY_BIT, 1b
 	mov	w2, #0xD
 	str	w2, [x1, #R_UART_TX]
 2:
-	/* Check if the transmit FIFO is full */
+	/* Check if the transmit FIFO is empty */
 	ldr	w2, [x1, #R_UART_SR]
-	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 2b
+	tbz	w2, #UART_SR_INTR_TEMPTY_BIT, 2b
 	str	w0, [x1, #R_UART_TX]
 	ret
 endfunc console_cdns_core_putc
diff --git a/drivers/fwu/fwu.c b/drivers/fwu/fwu.c
new file mode 100644
index 0000000..7cb4c29
--- /dev/null
+++ b/drivers/fwu/fwu.c
@@ -0,0 +1,187 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <common/tf_crc32.h>
+#include <common/tbbr/tbbr_img_def.h>
+#include <drivers/fwu/fwu.h>
+#include <drivers/fwu/fwu_metadata.h>
+#include <drivers/io/io_storage.h>
+
+#include <plat/common/platform.h>
+
+/*
+ * Assert that crc_32 is the first member of fwu_metadata structure.
+ * It avoids accessing data outside of the metadata structure during
+ * CRC32 computation if the crc_32 field gets moved due the structure
+ * member(s) addition in the future.
+ */
+CASSERT((offsetof(struct fwu_metadata, crc_32) == 0),
+	crc_32_must_be_first_member_of_structure);
+
+static struct fwu_metadata metadata;
+static bool is_fwu_initialized;
+
+/*******************************************************************************
+ * Compute CRC32 of the FWU metadata, and check it against the CRC32 value
+ * present in the FWU metadata.
+ *
+ * return -1 on error, otherwise 0
+ ******************************************************************************/
+static int fwu_metadata_crc_check(void)
+{
+	unsigned char *data = (unsigned char *)&metadata;
+
+	uint32_t calc_crc = tf_crc32(0U, data + sizeof(metadata.crc_32),
+				     (sizeof(metadata) -
+				      sizeof(metadata.crc_32)));
+
+	if (metadata.crc_32 != calc_crc) {
+		return -1;
+	}
+
+	return 0;
+}
+
+/*******************************************************************************
+ * Check the sanity of FWU metadata.
+ *
+ * return -1 on error, otherwise 0
+ ******************************************************************************/
+static int fwu_metadata_sanity_check(void)
+{
+	/* ToDo: add more conditions for sanity check */
+	if ((metadata.active_index >= NR_OF_FW_BANKS) ||
+	    (metadata.previous_active_index >= NR_OF_FW_BANKS)) {
+		return -1;
+	}
+
+	return 0;
+}
+
+/*******************************************************************************
+ * Verify and load specified FWU metadata image to local FWU metadata structure.
+ *
+ * @image_id: FWU metadata image id (either FWU_METADATA_IMAGE_ID or
+ *				     BKUP_FWU_METADATA_IMAGE_ID)
+ *
+ * return a negative value on error, otherwise 0
+ ******************************************************************************/
+static int fwu_metadata_load(unsigned int image_id)
+{
+	int result;
+	uintptr_t dev_handle, image_handle, image_spec;
+	size_t bytes_read;
+
+	assert((image_id == FWU_METADATA_IMAGE_ID) ||
+	       (image_id == BKUP_FWU_METADATA_IMAGE_ID));
+
+	result = plat_fwu_set_metadata_image_source(image_id,
+						    &dev_handle,
+						    &image_spec);
+	if (result != 0) {
+		WARN("Failed to set reference to image id=%u (%i)\n",
+		     image_id, result);
+		return result;
+	}
+
+	result = io_open(dev_handle, image_spec, &image_handle);
+	if (result != 0) {
+		WARN("Failed to load image id id=%u (%i)\n",
+		     image_id, result);
+		return result;
+	}
+
+	result = io_read(image_handle, (uintptr_t)&metadata,
+			 sizeof(struct fwu_metadata), &bytes_read);
+
+	if (result != 0) {
+		WARN("Failed to read image id=%u (%i)\n", image_id, result);
+		goto exit;
+	}
+
+	if (sizeof(struct fwu_metadata) != bytes_read) {
+		/* return -1 in case of partial/no read */
+		result = -1;
+		WARN("Read bytes (%zu) instead of expected (%zu) bytes\n",
+		     bytes_read, sizeof(struct fwu_metadata));
+		goto exit;
+	}
+
+	/* sanity check on loaded parameters */
+	result = fwu_metadata_sanity_check();
+	if (result != 0) {
+		WARN("Sanity %s\n", "check failed on FWU metadata");
+		goto exit;
+	}
+
+	/* CRC check on loaded parameters */
+	result = fwu_metadata_crc_check();
+	if (result != 0) {
+		WARN("CRC %s\n", "check failed on FWU metadata");
+	}
+
+exit:
+	(void)io_close(image_handle);
+
+	return result;
+}
+
+/*******************************************************************************
+ * The system runs in the trial run state if any of the images in the active
+ * firmware bank has not been accepted yet.
+ *
+ * Returns true if the system is running in the trial state.
+ ******************************************************************************/
+bool fwu_is_trial_run_state(void)
+{
+	bool trial_run = false;
+
+	assert(is_fwu_initialized == true);
+
+	for (unsigned int i = 0U; i < NR_OF_IMAGES_IN_FW_BANK; i++) {
+		struct fwu_image_entry *entry = &metadata.img_entry[i];
+		struct fwu_image_properties *img_props =
+			&entry->img_props[metadata.active_index];
+		if (img_props->accepted == 0) {
+			trial_run = true;
+			break;
+		}
+	}
+
+	return trial_run;
+}
+
+/*******************************************************************************
+ * Load verified copy of FWU metadata image kept in the platform NV storage
+ * into local FWU metadata structure.
+ * Also, update platform I/O policies with the offset address and length of
+ * firmware-updated images kept in the platform NV storage.
+ ******************************************************************************/
+void fwu_init(void)
+{
+	/* Load FWU metadata which will be used to load the images in the
+	 * active bank as per PSA FWU specification
+	 */
+	int result = fwu_metadata_load(FWU_METADATA_IMAGE_ID);
+
+	if (result != 0) {
+		WARN("loading of FWU-Metadata failed, "
+		     "using Bkup-FWU-Metadata\n");
+
+		result = fwu_metadata_load(BKUP_FWU_METADATA_IMAGE_ID);
+		if (result != 0) {
+			ERROR("loading of Bkup-FWU-Metadata failed\n");
+			panic();
+		}
+	}
+
+	plat_fwu_set_images_source(&metadata);
+
+	is_fwu_initialized = true;
+}
diff --git a/drivers/fwu/fwu.mk b/drivers/fwu/fwu.mk
new file mode 100644
index 0000000..f4452e0
--- /dev/null
+++ b/drivers/fwu/fwu.mk
@@ -0,0 +1,11 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+FWU_SRC_DIR	:= drivers/fwu/
+
+FWU_SRCS	:= ${FWU_SRC_DIR}fwu.c
+
+BL2_SOURCES	+= ${FWU_SRCS}
diff --git a/drivers/io/io_mtd.c b/drivers/io/io_mtd.c
index 7575fa2..ba8cecd 100644
--- a/drivers/io/io_mtd.c
+++ b/drivers/io/io_mtd.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -18,8 +18,9 @@
 typedef struct {
 	io_mtd_dev_spec_t	*dev_spec;
 	uintptr_t		base;
-	unsigned long long	offset;		/* Offset in bytes */
-	unsigned long long	size;	/* Size of device in bytes */
+	unsigned long long	pos;		/* Offset in bytes */
+	unsigned long long	size;		/* Size of device in bytes */
+	unsigned long long	extra_offset;	/* Extra offset in bytes */
 } mtd_dev_state_t;
 
 io_type_t device_type_mtd(void);
@@ -110,16 +111,47 @@
 	return 0;
 }
 
+static int mtd_add_extra_offset(mtd_dev_state_t *cur, size_t *extra_offset)
+{
+	io_mtd_ops_t *ops = &cur->dev_spec->ops;
+	int ret;
+
+	if (ops->seek == NULL) {
+		return 0;
+	}
+
+	ret = ops->seek(cur->base, cur->pos, extra_offset);
+	if (ret != 0) {
+		ERROR("%s: Seek error %d\n", __func__, ret);
+		return ret;
+	}
+
+	return 0;
+}
+
 static int mtd_open(io_dev_info_t *dev_info, const uintptr_t spec,
 		    io_entity_t *entity)
 {
 	mtd_dev_state_t *cur;
+	io_block_spec_t *region;
+	size_t extra_offset = 0U;
+	int ret;
 
 	assert((dev_info->info != 0UL) && (entity->info == 0UL));
 
+	region = (io_block_spec_t *)spec;
 	cur = (mtd_dev_state_t *)dev_info->info;
 	entity->info = (uintptr_t)cur;
-	cur->offset = 0U;
+	cur->base = region->offset;
+	cur->pos = 0U;
+	cur->extra_offset = 0U;
+
+	ret = mtd_add_extra_offset(cur, &extra_offset);
+	if (ret != 0) {
+		return ret;
+	}
+
+	cur->base += extra_offset;
 
 	return 0;
 }
@@ -128,6 +160,8 @@
 static int mtd_seek(io_entity_t *entity, int mode, signed long long offset)
 {
 	mtd_dev_state_t *cur;
+	size_t extra_offset = 0U;
+	int ret;
 
 	assert((entity->info != (uintptr_t)NULL) && (offset >= 0));
 
@@ -140,22 +174,29 @@
 			return -EINVAL;
 		}
 
-		cur->offset = offset;
+		cur->pos = offset;
 		break;
 	case IO_SEEK_CUR:
-		if (((cur->offset + (unsigned long long)offset) >=
+		if (((cur->base + cur->pos + (unsigned long long)offset) >=
 		     cur->size) ||
-		    ((cur->offset + (unsigned long long)offset) <
-		     cur->offset)) {
+		    ((cur->base + cur->pos + (unsigned long long)offset) <
+		     cur->base + cur->pos)) {
 			return -EINVAL;
 		}
 
-		cur->offset += (unsigned long long)offset;
+		cur->pos += (unsigned long long)offset;
 		break;
 	default:
 		return -EINVAL;
 	}
 
+	ret = mtd_add_extra_offset(cur, &extra_offset);
+	if (ret != 0) {
+		return ret;
+	}
+
+	cur->extra_offset = extra_offset;
+
 	return 0;
 }
 
@@ -174,18 +215,19 @@
 	assert(ops->read != NULL);
 
 	VERBOSE("Read at %llx into %lx, length %zi\n",
-		cur->offset, buffer, length);
-	if ((cur->offset + length) > cur->dev_spec->device_size) {
+		cur->base + cur->pos, buffer, length);
+	if ((cur->base + cur->pos + length) > cur->dev_spec->device_size) {
 		return -EINVAL;
 	}
 
-	ret = ops->read(cur->offset, buffer, length, out_length);
+	ret = ops->read(cur->base + cur->pos + cur->extra_offset, buffer,
+			length, out_length);
 	if (ret < 0) {
 		return ret;
 	}
 
 	assert(*out_length == length);
-	cur->offset += *out_length;
+	cur->pos += *out_length;
 
 	return 0;
 }
diff --git a/drivers/marvell/amb_adec.c b/drivers/marvell/amb_adec.c
index 1f67105..d78fa25 100644
--- a/drivers/marvell/amb_adec.c
+++ b/drivers/marvell/amb_adec.c
@@ -7,6 +7,9 @@
 
 /* AXI to M-Bridge decoding unit driver for Marvell Armada 8K and 8K+ SoCs */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <lib/mmio.h>
 
@@ -44,10 +47,10 @@
 
 	/* make sure the base address is in 16-bit range */
 	if (win->base_addr > AMB_BASE_ADDR_MASK) {
-		WARN("Window %d: base address is too big 0x%llx\n",
+		WARN("Window %d: base address is too big 0x%" PRIx64 "\n",
 		       win_num, win->base_addr);
 		win->base_addr = AMB_BASE_ADDR_MASK;
-		WARN("Set the base address to 0x%llx\n", win->base_addr);
+		WARN("Set the base address to 0x%" PRIx64 "\n", win->base_addr);
 	}
 
 	base_addr  = win->base_addr << AMB_BASE_OFFSET;
@@ -57,15 +60,15 @@
 		win->base_addr = ALIGN_UP(base_addr, AMB_WIN_ALIGNMENT_1M);
 		WARN("Window %d: base address unaligned to 0x%x\n",
 		       win_num, AMB_WIN_ALIGNMENT_1M);
-		WARN("Align up the base address to 0x%llx\n", win->base_addr);
+		WARN("Align up the base address to 0x%" PRIx64 "\n", win->base_addr);
 	}
 
 	/* size parameter validity check */
 	if (!IS_POWER_OF_2(win->win_size)) {
-		WARN("Window %d: window size is not power of 2 (0x%llx)\n",
+		WARN("Window %d: window size is not power of 2 (0x%" PRIx64 ")\n",
 		       win_num, win->win_size);
 		win->win_size = ROUND_UP_TO_POW_OF_2(win->win_size);
-		WARN("Rounding size to 0x%llx\n", win->win_size);
+		WARN("Rounding size to 0x%" PRIx64 "\n", win->win_size);
 	}
 }
 
diff --git a/drivers/marvell/ccu.c b/drivers/marvell/ccu.c
index b4251f4..c206f11 100644
--- a/drivers/marvell/ccu.c
+++ b/drivers/marvell/ccu.c
@@ -7,6 +7,9 @@
 
 /* CCU unit device driver for Marvell AP807, AP807 and AP810 SoCs */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <drivers/marvell/ccu.h>
 #include <lib/mmio.h>
@@ -84,7 +87,7 @@
 							      win_id));
 			start = ((uint64_t)alr << ADDRESS_SHIFT);
 			end = (((uint64_t)ahr + 0x10) << ADDRESS_SHIFT);
-			printf("\tccu%d    %02x     0x%016llx 0x%016llx\n",
+			printf("\tccu%d    %02x     0x%016" PRIx64 " 0x%016" PRIx64 "\n",
 			       win_id, target_id, start, end);
 		}
 	}
@@ -99,14 +102,14 @@
 	/* check if address is aligned to 1M */
 	if (IS_NOT_ALIGN(win->base_addr, CCU_WIN_ALIGNMENT)) {
 		win->base_addr = ALIGN_UP(win->base_addr, CCU_WIN_ALIGNMENT);
-		NOTICE("%s: Align up the base address to 0x%llx\n",
+		NOTICE("%s: Align up the base address to 0x%" PRIx64 "\n",
 		       __func__, win->base_addr);
 	}
 
 	/* size parameter validity check */
 	if (IS_NOT_ALIGN(win->win_size, CCU_WIN_ALIGNMENT)) {
 		win->win_size = ALIGN_UP(win->win_size, CCU_WIN_ALIGNMENT);
-		NOTICE("%s: Aligning size to 0x%llx\n",
+		NOTICE("%s: Aligning size to 0x%" PRIx64 "\n",
 		       __func__, win->win_size);
 	}
 }
diff --git a/drivers/marvell/comphy/comphy-cp110.h b/drivers/marvell/comphy/comphy-cp110.h
index 9b10619..af5c715 100644
--- a/drivers/marvell/comphy/comphy-cp110.h
+++ b/drivers/marvell/comphy/comphy-cp110.h
@@ -54,7 +54,7 @@
 #define COMMON_SELECTOR_PIPE_COMPHY_USBH	0x1
 #define COMMON_SELECTOR_PIPE_COMPHY_USBD	0x2
 
-/* SGMII/HS-SGMII/SFI/RXAUI */
+/* SGMII/Base-X/SFI/RXAUI */
 #define COMMON_SELECTOR_COMPHY0_1_2_NETWORK	0x1
 #define COMMON_SELECTOR_COMPHY3_RXAUI		0x1
 #define COMMON_SELECTOR_COMPHY3_SGMII		0x2
diff --git a/drivers/marvell/comphy/phy-comphy-3700.c b/drivers/marvell/comphy/phy-comphy-3700.c
index f6a40a5..a3e414c 100644
--- a/drivers/marvell/comphy/phy-comphy-3700.c
+++ b/drivers/marvell/comphy/phy-comphy-3700.c
@@ -14,6 +14,7 @@
 
 #include <mvebu.h>
 #include <mvebu_def.h>
+#include <plat_marvell.h>
 
 #include "phy-comphy-3700.h"
 #include "phy-comphy-common.h"
@@ -29,15 +30,6 @@
 #define USB3_GBE1_PHY		(MVEBU_REGS_BASE + 0x5C000)
 #define COMPHY_SD_ADDR		(MVEBU_REGS_BASE + 0x1F000)
 
-/*
- * Below address in used only for reading, therefore no problem with concurrent
- * Linux access.
- */
-#define MVEBU_TEST_PIN_LATCH_N (MVEBU_NB_GPIO_REG_BASE + 0x8)
- #define MVEBU_XTAL_MODE_MASK		BIT(9)
- #define MVEBU_XTAL_MODE_OFFS		9
- #define MVEBU_XTAL_CLOCK_25MHZ		0x0
-
 struct sgmii_phy_init_data_fix {
 	uint16_t addr;
 	uint16_t value;
@@ -125,22 +117,8 @@
 	0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000	/*1F8 */
 };
 
-/* returns reference clock in MHz (25 or 40) */
-static uint32_t get_ref_clk(void)
-{
-	uint32_t val;
-
-	val = (mmio_read_32(MVEBU_TEST_PIN_LATCH_N) & MVEBU_XTAL_MODE_MASK) >>
-		MVEBU_XTAL_MODE_OFFS;
-
-	if (val == MVEBU_XTAL_CLOCK_25MHZ)
-		return 25;
-	else
-		return 40;
-}
-
 /* PHY selector configures with corresponding modes */
-static void mvebu_a3700_comphy_set_phy_selector(uint8_t comphy_index,
+static int mvebu_a3700_comphy_set_phy_selector(uint8_t comphy_index,
 						uint32_t comphy_mode)
 {
 	uint32_t reg;
@@ -157,7 +135,7 @@
 		break;
 
 	case (COMPHY_SGMII_MODE):
-	case (COMPHY_HS_SGMII_MODE):
+	case (COMPHY_2500BASEX_MODE):
 		if (comphy_index == COMPHY_LANE0)
 			reg &= ~COMPHY_SELECTOR_USB3_GBE1_SEL_BIT;
 		else if (comphy_index == COMPHY_LANE1)
@@ -190,9 +168,10 @@
 	}
 
 	mmio_write_32(MVEBU_COMPHY_REG_BASE + COMPHY_SELECTOR_PHY_REG, reg);
-	return;
+	return 0;
 error:
 	ERROR("COMPHY[%d] mode[%d] is invalid\n", comphy_index, mode);
+	return -EINVAL;
 }
 
 /*
@@ -205,7 +184,7 @@
  * with COMPHY_USB3D_MODE or COMPHY_USB3H_MODE. (The usb3 phy initialization
  * code does not differentiate between these modes.)
  * Also it returns COMPHY_SGMII_MODE even if the phy was configures with
- * COMPHY_HS_SGMII_MODE. (The sgmii phy initialization code does differentiate
+ * COMPHY_2500BASEX_MODE. (The sgmii phy initialization code does differentiate
  * between these modes, but it is irrelevant when powering the phy off.)
  */
 static int mvebu_a3700_comphy_get_mode(uint8_t comphy_index)
@@ -236,7 +215,7 @@
 
 /* It is only used for SATA and USB3 on comphy lane2. */
 static void comphy_set_indirect(uintptr_t addr, uint32_t offset, uint16_t data,
-				uint16_t mask, int mode)
+				uint16_t mask, bool is_sata)
 {
 	/*
 	 * When Lane 2 PHY is for USB3, access the PHY registers
@@ -246,27 +225,38 @@
 	 * within the SATA Host Controller registers, Lane 2 base register
 	 * offset is 0x200
 	 */
-	if (mode == COMPHY_UNUSED)
-		return;
-
-	if (mode == COMPHY_SATA_MODE)
+	if (is_sata) {
 		mmio_write_32(addr + COMPHY_LANE2_INDIR_ADDR_OFFSET, offset);
-	else
+	} else {
 		mmio_write_32(addr + COMPHY_LANE2_INDIR_ADDR_OFFSET,
 			      offset + USB3PHY_LANE2_REG_BASE_OFFSET);
+	}
 
 	reg_set(addr + COMPHY_LANE2_INDIR_DATA_OFFSET, data, mask);
 }
 
-/* It is only used USB3 direct access not on comphy lane2. */
+/* It is only used for SATA on comphy lane2. */
+static void comphy_sata_set_indirect(uintptr_t addr, uint32_t reg_offset,
+				     uint16_t data, uint16_t mask)
+{
+	comphy_set_indirect(addr, reg_offset, data, mask, true);
+}
+
+/* It is only used for USB3 indirect access on comphy lane2. */
+static void comphy_usb3_set_indirect(uintptr_t addr, uint32_t reg_offset,
+				     uint16_t data, uint16_t mask)
+{
+	comphy_set_indirect(addr, reg_offset, data, mask, false);
+}
+
+/* It is only used for USB3 direct access not on comphy lane2. */
 static void comphy_usb3_set_direct(uintptr_t addr, uint32_t reg_offset,
-				   uint16_t data, uint16_t mask, int mode)
+				   uint16_t data, uint16_t mask)
 {
 	reg_set16((reg_offset * PHY_SHFT(USB3) + addr), data, mask);
 }
 
-static void comphy_sgmii_phy_init(uint32_t comphy_index, uint32_t mode,
-				  uintptr_t sd_ip_addr)
+static void comphy_sgmii_phy_init(uintptr_t sd_ip_addr, bool is_1gbps)
 {
 	const int fix_arr_sz = ARRAY_SIZE(sgmii_phy_init_fix);
 	int addr, fix_idx;
@@ -281,8 +271,7 @@
 		 * comparison to 3.125 Gbps values. These register values are
 		 * stored in "sgmii_phy_init_fix" array.
 		 */
-		if ((mode != COMPHY_SGMII_MODE) &&
-		    (sgmii_phy_init_fix[fix_idx].addr == addr)) {
+		if (!is_1gbps && sgmii_phy_init_fix[fix_idx].addr == addr) {
 			/* Use new value */
 			val = sgmii_phy_init_fix[fix_idx].value;
 			if (fix_idx < fix_arr_sz)
@@ -298,21 +287,22 @@
 static int mvebu_a3700_comphy_sata_power_on(uint8_t comphy_index,
 					    uint32_t comphy_mode)
 {
-	int ret = 0;
+	int ret;
 	uint32_t offset, data = 0, ref_clk;
 	uintptr_t comphy_indir_regs = COMPHY_INDIRECT_REG;
-	int mode = COMPHY_GET_MODE(comphy_mode);
 	int invert = COMPHY_GET_POLARITY_INVERT(comphy_mode);
 
 	debug_enter();
 
 	/* Configure phy selector for SATA */
-	mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	ret = mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	if (ret) {
+		return ret;
+	}
 
 	/* Clear phy isolation mode to make it work in normal mode */
 	offset =  COMPHY_ISOLATION_CTRL_REG + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, 0, PHY_ISOLATE_MODE,
-			    mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, 0, PHY_ISOLATE_MODE);
 
 	/* 0. Check the Polarity invert bits */
 	if (invert & COMPHY_POLARITY_TXD_INVERT)
@@ -321,13 +311,13 @@
 		data |= RXD_INVERT_BIT;
 
 	offset = COMPHY_SYNC_PATTERN_REG + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, data, TXD_INVERT_BIT |
-			    RXD_INVERT_BIT, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, data, TXD_INVERT_BIT |
+				 RXD_INVERT_BIT);
 
 	/* 1. Select 40-bit data width width */
 	offset = COMPHY_LOOPBACK_REG0 + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, DATA_WIDTH_40BIT,
-			    SEL_DATA_WIDTH_MASK, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, DATA_WIDTH_40BIT,
+				 SEL_DATA_WIDTH_MASK);
 
 	/* 2. Select reference clock(25M) and PHY mode (SATA) */
 	offset = COMPHY_POWER_PLL_CTRL + SATAPHY_LANE2_REG_BASE_OFFSET;
@@ -336,17 +326,17 @@
 	else
 		ref_clk = REF_CLOCK_SPEED_25M;
 
-	comphy_set_indirect(comphy_indir_regs, offset, ref_clk | PHY_MODE_SATA,
-			    REF_FREF_SEL_MASK | PHY_MODE_MASK, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, ref_clk | PHY_MODE_SATA,
+				 REF_FREF_SEL_MASK | PHY_MODE_MASK);
 
 	/* 3. Use maximum PLL rate (no power save) */
 	offset = COMPHY_KVCO_CAL_CTRL + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, USE_MAX_PLL_RATE_BIT,
-			    USE_MAX_PLL_RATE_BIT, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, USE_MAX_PLL_RATE_BIT,
+				 USE_MAX_PLL_RATE_BIT);
 
 	/* 4. Reset reserved bit */
-	comphy_set_indirect(comphy_indir_regs, COMPHY_RESERVED_REG, 0,
-			    PHYCTRL_FRM_PIN_BIT, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, COMPHY_RESERVED_REG, 0,
+				 PHYCTRL_FRM_PIN_BIT);
 
 	/* 5. Set vendor-specific configuration (It is done in sata driver) */
 	/* XXX: in U-Boot below sequence was executed in this place, in Linux
@@ -368,17 +358,21 @@
 				   COMPHY_LANE2_INDIR_DATA_OFFSET,
 				   PLL_READY_TX_BIT, PLL_READY_TX_BIT,
 				   COMPHY_PLL_TIMEOUT, REG_32BIT);
+	if (ret) {
+		return -ETIMEDOUT;
+	}
 
 	debug_exit();
 
-	return ret;
+	return 0;
 }
 
 static int mvebu_a3700_comphy_sgmii_power_on(uint8_t comphy_index,
 					     uint32_t comphy_mode)
 {
-	int ret = 0;
-	uint32_t mask, data, offset;
+	int ret;
+	uint32_t mask, data;
+	uintptr_t offset;
 	uintptr_t sd_ip_addr;
 	int mode = COMPHY_GET_MODE(comphy_mode);
 	int invert = COMPHY_GET_POLARITY_INVERT(comphy_mode);
@@ -386,7 +380,10 @@
 	debug_enter();
 
 	/* Set selector */
-	mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	ret = mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	if (ret) {
+		return ret;
+	}
 
 	/* Serdes IP Base address
 	 * COMPHY Lane0 -- USB3/GBE1
@@ -423,8 +420,8 @@
 		/* SGMII 1G, SerDes speed 1.25G */
 		data |= SD_SPEED_1_25_G << GEN_RX_SEL_OFFSET;
 		data |= SD_SPEED_1_25_G << GEN_TX_SEL_OFFSET;
-	} else if (mode == COMPHY_HS_SGMII_MODE) {
-		/* HS SGMII (2.5G), SerDes speed 3.125G */
+	} else if (mode == COMPHY_2500BASEX_MODE) {
+		/* 2500Base-X, SerDes speed 3.125G */
 		data |= SD_SPEED_2_5_G << GEN_RX_SEL_OFFSET;
 		data |= SD_SPEED_2_5_G << GEN_TX_SEL_OFFSET;
 	} else {
@@ -501,9 +498,9 @@
 	 * 25 MHz the default values stored in PHY registers are OK.
 	 */
 	debug("Running C-DPI phy init %s mode\n",
-	      mode == COMPHY_HS_SGMII_MODE ? "2G5" : "1G");
+	      mode == COMPHY_2500BASEX_MODE ? "2G5" : "1G");
 	if (get_ref_clk() == 40)
-		comphy_sgmii_phy_init(comphy_index, mode, sd_ip_addr);
+		comphy_sgmii_phy_init(sd_ip_addr, mode != COMPHY_2500BASEX_MODE);
 
 	/*
 	 * 14. [Simulation Only] should not be used for real chip.
@@ -525,7 +522,8 @@
 		data |= TXD_INVERT_BIT;
 	if (invert & COMPHY_POLARITY_RXD_INVERT)
 		data |= RXD_INVERT_BIT;
-	reg_set16(SGMIIPHY_ADDR(COMPHY_SYNC_PATTERN_REG, sd_ip_addr), data, 0);
+	mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
+	reg_set16(SGMIIPHY_ADDR(COMPHY_SYNC_PATTERN_REG, sd_ip_addr), data, mask);
 
 	/*
 	 * 17. Set PHY input ports PIN_PU_PLL, PIN_PU_TX and PIN_PU_RX to 1 to
@@ -546,8 +544,10 @@
 				   PHY_PLL_READY_TX_BIT | PHY_PLL_READY_RX_BIT,
 				   PHY_PLL_READY_TX_BIT | PHY_PLL_READY_RX_BIT,
 				   COMPHY_PLL_TIMEOUT, REG_32BIT);
-	if (ret)
+	if (ret) {
 		ERROR("Failed to lock PLL for SGMII PHY %d\n", comphy_index);
+		return -ETIMEDOUT;
+	}
 
 	/*
 	 * 19. Set COMPHY input port PIN_TX_IDLE=0
@@ -563,65 +563,71 @@
 	 * refer to RX initialization part for details.
 	 */
 	reg_set(MVEBU_COMPHY_REG_BASE + COMPHY_PHY_CFG1_OFFSET(comphy_index),
-		PHY_RX_INIT_BIT, 0x0);
+		PHY_RX_INIT_BIT, PHY_RX_INIT_BIT);
 
 	ret = polling_with_timeout(MVEBU_COMPHY_REG_BASE +
 				   COMPHY_PHY_STATUS_OFFSET(comphy_index),
 				   PHY_PLL_READY_TX_BIT | PHY_PLL_READY_RX_BIT,
 				   PHY_PLL_READY_TX_BIT | PHY_PLL_READY_RX_BIT,
 				   COMPHY_PLL_TIMEOUT, REG_32BIT);
-	if (ret)
+	if (ret) {
 		ERROR("Failed to lock PLL for SGMII PHY %d\n", comphy_index);
-
+		return -ETIMEDOUT;
+	}
 
 	ret = polling_with_timeout(MVEBU_COMPHY_REG_BASE +
 				   COMPHY_PHY_STATUS_OFFSET(comphy_index),
 				   PHY_RX_INIT_DONE_BIT, PHY_RX_INIT_DONE_BIT,
 				   COMPHY_PLL_TIMEOUT, REG_32BIT);
-	if (ret)
+	if (ret) {
 		ERROR("Failed to init RX of SGMII PHY %d\n", comphy_index);
+		return -ETIMEDOUT;
+	}
 
 	debug_exit();
 
-	return ret;
+	return 0;
 }
 
 static int mvebu_a3700_comphy_sgmii_power_off(uint8_t comphy_index)
 {
-	int ret = 0;
-	uint32_t mask, data, offset;
+	uintptr_t offset;
+	uint32_t mask, data;
 
 	debug_enter();
 
 	data = PIN_RESET_CORE_BIT | PIN_RESET_COMPHY_BIT;
-	mask = 0;
+	mask = data;
 	offset = MVEBU_COMPHY_REG_BASE + COMPHY_PHY_CFG1_OFFSET(comphy_index);
 	reg_set(offset, data, mask);
 
 	debug_exit();
 
-	return ret;
+	return 0;
 }
 
 static int mvebu_a3700_comphy_usb3_power_on(uint8_t comphy_index,
 					    uint32_t comphy_mode)
 {
-	int ret = 0;
+	int ret;
 	uintptr_t reg_base = 0;
-	uint32_t mask, data, addr, cfg, ref_clk;
+	uintptr_t addr;
+	uint32_t mask, data, cfg, ref_clk;
 	void (*usb3_reg_set)(uintptr_t addr, uint32_t reg_offset, uint16_t data,
-			     uint16_t mask, int mode);
-	int mode = COMPHY_GET_MODE(comphy_mode);
+			     uint16_t mask);
 	int invert = COMPHY_GET_POLARITY_INVERT(comphy_mode);
 
 	debug_enter();
 
 	/* Set phy seclector */
-	mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	ret = mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	if (ret) {
+		return ret;
+	}
 
 	/* Set usb3 reg access func, Lane2 is indirect access */
 	if (comphy_index == COMPHY_LANE2) {
-		usb3_reg_set = &comphy_set_indirect;
+		usb3_reg_set = &comphy_usb3_set_indirect;
 		reg_base = COMPHY_INDIRECT_REG;
 	} else {
 		/* Get the direct access register resource and map */
@@ -640,7 +646,7 @@
 	mask = PRD_TXDEEMPH0_MASK | PRD_TXMARGIN_MASK | PRD_TXSWING_MASK |
 		CFG_TX_ALIGN_POS_MASK;
 	usb3_reg_set(reg_base, COMPHY_REG_LANE_CFG0_ADDR, PRD_TXDEEMPH0_MASK,
-		     mask, mode);
+		     mask);
 
 	/*
 	 * 2. Set BIT0: enable transmitter in high impedance mode
@@ -652,20 +658,20 @@
 	mask = PRD_TXDEEMPH1_MASK | TX_DET_RX_MODE | GEN2_TX_DATA_DLY_MASK |
 		TX_ELEC_IDLE_MODE_EN;
 	data = TX_DET_RX_MODE | GEN2_TX_DATA_DLY_DEFT | TX_ELEC_IDLE_MODE_EN;
-	usb3_reg_set(reg_base, COMPHY_REG_LANE_CFG1_ADDR, data, mask, mode);
+	usb3_reg_set(reg_base, COMPHY_REG_LANE_CFG1_ADDR, data, mask);
 
 	/*
 	 * 3. Set Spread Spectrum Clock Enabled
 	 */
 	usb3_reg_set(reg_base, COMPHY_REG_LANE_CFG4_ADDR,
-		     SPREAD_SPECTRUM_CLK_EN, SPREAD_SPECTRUM_CLK_EN, mode);
+		     SPREAD_SPECTRUM_CLK_EN, SPREAD_SPECTRUM_CLK_EN);
 
 	/*
 	 * 4. Set Override Margining Controls From the MAC:
 	 *    Use margining signals from lane configuration
 	 */
 	usb3_reg_set(reg_base, COMPHY_REG_TEST_MODE_CTRL_ADDR,
-		     MODE_MARGIN_OVERRIDE, REG_16_BIT_MASK, mode);
+		     MODE_MARGIN_OVERRIDE, REG_16_BIT_MASK);
 
 	/*
 	 * 5. Set Lane-to-Lane Bundle Clock Sampling Period = per PCLK cycles
@@ -673,13 +679,13 @@
 	 */
 	usb3_reg_set(reg_base, COMPHY_REG_GLOB_CLK_SRC_LO_ADDR, 0x0,
 		     (MODE_CLK_SRC | BUNDLE_PERIOD_SEL | BUNDLE_PERIOD_SCALE |
-		      BUNDLE_SAMPLE_CTRL | PLL_READY_DLY), mode);
+		      BUNDLE_SAMPLE_CTRL | PLL_READY_DLY));
 
 	/*
 	 * 6. Set G2 Spread Spectrum Clock Amplitude at 4K
 	 */
 	usb3_reg_set(reg_base, COMPHY_REG_GEN2_SET_2,
-		     G2_TX_SSC_AMP_VALUE_20, G2_TX_SSC_AMP_MASK, mode);
+		     G2_TX_SSC_AMP_VALUE_20, G2_TX_SSC_AMP_MASK);
 
 	/*
 	 * 7. Unset G3 Spread Spectrum Clock Amplitude
@@ -688,7 +694,7 @@
 	mask = G3_TX_SSC_AMP_MASK | G3_VREG_RXTX_MAS_ISET_MASK |
 		RSVD_PH03FH_6_0_MASK;
 	usb3_reg_set(reg_base, COMPHY_REG_GEN2_SET_3,
-		     G3_VREG_RXTX_MAS_ISET_60U, mask, mode);
+		     G3_VREG_RXTX_MAS_ISET_60U, mask);
 
 	/*
 	 * 8. Check crystal jumper setting and program the Power and PLL Control
@@ -709,69 +715,69 @@
 		REF_FREF_SEL_MASK;
 	data = PU_IVREF_BIT | PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT |
 		PU_TX_INTP_BIT | PU_DFE_BIT | PHY_MODE_USB3 | ref_clk;
-	usb3_reg_set(reg_base, COMPHY_POWER_PLL_CTRL, data,  mask, mode);
+	usb3_reg_set(reg_base, COMPHY_POWER_PLL_CTRL, data,  mask);
 
 	mask = CFG_PM_OSCCLK_WAIT_MASK | CFG_PM_RXDEN_WAIT_MASK |
 		CFG_PM_RXDLOZ_WAIT_MASK;
 	data = CFG_PM_RXDEN_WAIT_1_UNIT  | cfg;
-	usb3_reg_set(reg_base, COMPHY_REG_PWR_MGM_TIM1_ADDR, data, mask, mode);
+	usb3_reg_set(reg_base, COMPHY_REG_PWR_MGM_TIM1_ADDR, data, mask);
 
 	/*
 	 * 9. Enable idle sync
 	 */
 	data = UNIT_CTRL_DEFAULT_VALUE | IDLE_SYNC_EN;
-	usb3_reg_set(reg_base, COMPHY_REG_UNIT_CTRL_ADDR, data, REG_16_BIT_MASK,
-		     mode);
+	usb3_reg_set(reg_base, COMPHY_REG_UNIT_CTRL_ADDR, data, REG_16_BIT_MASK);
 
 	/*
 	 * 10. Enable the output of 500M clock
 	 */
 	data = MISC_REG0_DEFAULT_VALUE | CLK500M_EN;
-	usb3_reg_set(reg_base, COMPHY_MISC_REG0_ADDR, data, REG_16_BIT_MASK,
-		     mode);
+	usb3_reg_set(reg_base, COMPHY_MISC_REG0_ADDR, data, REG_16_BIT_MASK);
 
 	/*
 	 * 11. Set 20-bit data width
 	 */
 	usb3_reg_set(reg_base, COMPHY_LOOPBACK_REG0, DATA_WIDTH_20BIT,
-		     REG_16_BIT_MASK, mode);
+		     REG_16_BIT_MASK);
 
 	/*
 	 * 12. Override Speed_PLL value and use MAC PLL
 	 */
 	usb3_reg_set(reg_base, COMPHY_KVCO_CAL_CTRL,
 		     (SPEED_PLL_VALUE_16 | USE_MAX_PLL_RATE_BIT),
-		     REG_16_BIT_MASK, mode);
+		     REG_16_BIT_MASK);
 
 	/*
 	 * 13. Check the Polarity invert bit
 	 */
-	if (invert & COMPHY_POLARITY_TXD_INVERT)
-		usb3_reg_set(reg_base, COMPHY_SYNC_PATTERN_REG, TXD_INVERT_BIT,
-			     TXD_INVERT_BIT, mode);
-	if (invert & COMPHY_POLARITY_RXD_INVERT)
-		usb3_reg_set(reg_base, COMPHY_SYNC_PATTERN_REG, RXD_INVERT_BIT,
-			     RXD_INVERT_BIT, mode);
+	data = 0U;
+	if (invert & COMPHY_POLARITY_TXD_INVERT) {
+		data |= TXD_INVERT_BIT;
+	}
+	if (invert & COMPHY_POLARITY_RXD_INVERT) {
+		data |= RXD_INVERT_BIT;
+	}
+	mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
+	usb3_reg_set(reg_base, COMPHY_SYNC_PATTERN_REG, data, mask);
 
 	/*
 	 * 14. Set max speed generation to USB3.0 5Gbps
 	 */
 	usb3_reg_set(reg_base, COMPHY_SYNC_MASK_GEN_REG, PHY_GEN_USB3_5G,
-		     PHY_GEN_MAX_MASK, mode);
+		     PHY_GEN_MAX_MASK);
 
 	/*
 	 * 15. Set capacitor value for FFE gain peaking to 0xF
 	 */
 	usb3_reg_set(reg_base, COMPHY_REG_GEN3_SETTINGS_3,
-		     COMPHY_GEN_FFE_CAP_SEL_VALUE, COMPHY_GEN_FFE_CAP_SEL_MASK,
-		     mode);
+		     COMPHY_GEN_FFE_CAP_SEL_VALUE, COMPHY_GEN_FFE_CAP_SEL_MASK);
 
 	/*
 	 * 16. Release SW reset
 	 */
 	data = MODE_CORE_CLK_FREQ_SEL | MODE_PIPE_WIDTH_32 | MODE_REFDIV_BY_4;
 	usb3_reg_set(reg_base, COMPHY_REG_GLOB_PHY_CTRL0_ADDR, data,
-		     REG_16_BIT_MASK, mode);
+		     REG_16_BIT_MASK);
 
 	/* Wait for > 55 us to allow PCLK be enabled */
 	udelay(PLL_SET_DELAY_US);
@@ -789,12 +795,14 @@
 					   TXDCLK_PCLK_EN, TXDCLK_PCLK_EN,
 					   COMPHY_PLL_TIMEOUT, REG_16BIT);
 	}
-	if (ret)
+	if (ret) {
 		ERROR("Failed to lock USB3 PLL\n");
+		return -ETIMEDOUT;
+	}
 
 	debug_exit();
 
-	return ret;
+	return 0;
 }
 
 static int mvebu_a3700_comphy_pcie_power_on(uint8_t comphy_index,
@@ -802,21 +810,28 @@
 {
 	int ret;
 	uint32_t ref_clk;
+	uint32_t mask, data;
 	int invert = COMPHY_GET_POLARITY_INVERT(comphy_mode);
 
 	debug_enter();
 
+	/* Configure phy selector for PCIe */
+	ret = mvebu_a3700_comphy_set_phy_selector(comphy_index, comphy_mode);
+	if (ret) {
+		return ret;
+	}
+
 	/* 1. Enable max PLL. */
 	reg_set16(LANE_CFG1_ADDR(PCIE) + COMPHY_SD_ADDR,
-		  USE_MAX_PLL_RATE_EN, 0x0);
+		  USE_MAX_PLL_RATE_EN, USE_MAX_PLL_RATE_EN);
 
 	/* 2. Select 20 bit SERDES interface. */
 	reg_set16(GLOB_CLK_SRC_LO_ADDR(PCIE) + COMPHY_SD_ADDR,
-		  CFG_SEL_20B, 0);
+		  CFG_SEL_20B, CFG_SEL_20B);
 
 	/* 3. Force to use reg setting for PCIe mode */
 	reg_set16(MISC_REG1_ADDR(PCIE) + COMPHY_SD_ADDR,
-		  SEL_BITS_PCIE_FORCE, 0);
+		  SEL_BITS_PCIE_FORCE, SEL_BITS_PCIE_FORCE);
 
 	/* 4. Change RX wait */
 	reg_set16(PWR_MGM_TIM1_ADDR(PCIE) + COMPHY_SD_ADDR,
@@ -830,7 +845,7 @@
 
 	/* 6. Enable the output of 100M/125M/500M clock */
 	reg_set16(MISC_REG0_ADDR(PCIE) + COMPHY_SD_ADDR,
-		  MISC_REG0_DEFAULT_VALUE | CLK500M_EN | CLK100M_125M_EN,
+		  MISC_REG0_DEFAULT_VALUE | CLK500M_EN | TXDCLK_2X_SEL | CLK100M_125M_EN,
 		  REG_16_BIT_MASK);
 
 	/*
@@ -858,13 +873,15 @@
 		  SPEED_PLL_VALUE_16 | USE_MAX_PLL_RATE_BIT, REG_16_BIT_MASK);
 
 	/* 10. Check the Polarity invert bit */
-	if (invert & COMPHY_POLARITY_TXD_INVERT)
-		reg_set16(SYNC_PATTERN_REG_ADDR(PCIE) + COMPHY_SD_ADDR,
-			  TXD_INVERT_BIT, 0x0);
-
-	if (invert & COMPHY_POLARITY_RXD_INVERT)
-		reg_set16(SYNC_PATTERN_REG_ADDR(PCIE) + COMPHY_SD_ADDR,
-			  RXD_INVERT_BIT, 0x0);
+	data = 0U;
+	if (invert & COMPHY_POLARITY_TXD_INVERT) {
+		data |= TXD_INVERT_BIT;
+	}
+	if (invert & COMPHY_POLARITY_RXD_INVERT) {
+		data |= RXD_INVERT_BIT;
+	}
+	mask = TXD_INVERT_BIT | RXD_INVERT_BIT;
+	reg_set16(SYNC_PATTERN_REG_ADDR(PCIE) + COMPHY_SD_ADDR, data, mask);
 
 	/* 11. Release SW reset */
 	reg_set16(GLOB_PHY_CTRL0_ADDR(PCIE) + COMPHY_SD_ADDR,
@@ -877,12 +894,14 @@
 	ret = polling_with_timeout(LANE_STATUS1_ADDR(PCIE) + COMPHY_SD_ADDR,
 				   TXDCLK_PCLK_EN, TXDCLK_PCLK_EN,
 				   COMPHY_PLL_TIMEOUT, REG_16BIT);
-	if (ret)
+	if (ret) {
 		ERROR("Failed to lock PCIE PLL\n");
+		return -ETIMEDOUT;
+	}
 
 	debug_exit();
 
-	return ret;
+	return 0;
 }
 
 int mvebu_3700_comphy_power_on(uint8_t comphy_index, uint32_t comphy_mode)
@@ -898,7 +917,7 @@
 						       comphy_mode);
 		break;
 	case(COMPHY_SGMII_MODE):
-	case(COMPHY_HS_SGMII_MODE):
+	case(COMPHY_2500BASEX_MODE):
 		ret = mvebu_a3700_comphy_sgmii_power_on(comphy_index,
 							comphy_mode);
 		break;
@@ -934,23 +953,22 @@
 	return 0;
 }
 
-static int mvebu_a3700_comphy_sata_power_off(uint32_t comphy_mode)
+static int mvebu_a3700_comphy_sata_power_off(void)
 {
 	uintptr_t comphy_indir_regs = COMPHY_INDIRECT_REG;
-	int mode = COMPHY_GET_MODE(comphy_mode);
 	uint32_t offset;
 
 	debug_enter();
 
 	/* Set phy isolation mode */
 	offset = COMPHY_ISOLATION_CTRL_REG + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, PHY_ISOLATE_MODE,
-			    PHY_ISOLATE_MODE, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, PHY_ISOLATE_MODE,
+				 PHY_ISOLATE_MODE);
 
 	/* Power off PLL, Tx, Rx */
 	offset = COMPHY_POWER_PLL_CTRL + SATAPHY_LANE2_REG_BASE_OFFSET;
-	comphy_set_indirect(comphy_indir_regs, offset, 0,
-			    PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT, mode);
+	comphy_sata_set_indirect(comphy_indir_regs, offset, 0,
+				 PU_PLL_BIT | PU_RX_BIT | PU_TX_BIT);
 
 	debug_exit();
 
@@ -975,7 +993,7 @@
 
 	switch (mode) {
 	case(COMPHY_SGMII_MODE):
-	case(COMPHY_HS_SGMII_MODE):
+	case(COMPHY_2500BASEX_MODE):
 		err = mvebu_a3700_comphy_sgmii_power_off(comphy_index);
 		break;
 	case (COMPHY_USB3_MODE):
@@ -983,7 +1001,7 @@
 		err = mvebu_a3700_comphy_usb3_power_off();
 		break;
 	case (COMPHY_SATA_MODE):
-		err = mvebu_a3700_comphy_sata_power_off(comphy_mode);
+		err = mvebu_a3700_comphy_sata_power_off();
 		break;
 
 	default:
diff --git a/drivers/marvell/comphy/phy-comphy-3700.h b/drivers/marvell/comphy/phy-comphy-3700.h
index 1628e36..94056f1 100644
--- a/drivers/marvell/comphy/phy-comphy-3700.h
+++ b/drivers/marvell/comphy/phy-comphy-3700.h
@@ -104,6 +104,7 @@
 #define COMPHY_MISC_REG0_ADDR		0x4F
 #define MISC_REG0_ADDR(unit)		(COMPHY_MISC_REG0_ADDR * PHY_SHFT(unit))
 #define CLK100M_125M_EN			BIT(4)
+#define TXDCLK_2X_SEL			BIT(6)
 #define CLK500M_EN			BIT(7)
 #define PHY_REF_CLK_SEL			BIT(10)
 #define MISC_REG0_DEFAULT_VALUE		0xA00D
diff --git a/drivers/marvell/comphy/phy-comphy-common.h b/drivers/marvell/comphy/phy-comphy-common.h
index e3b430a..c599437 100644
--- a/drivers/marvell/comphy/phy-comphy-common.h
+++ b/drivers/marvell/comphy/phy-comphy-common.h
@@ -87,7 +87,7 @@
 
 #define COMPHY_SATA_MODE	0x1
 #define COMPHY_SGMII_MODE	0x2	/* SGMII 1G */
-#define COMPHY_HS_SGMII_MODE	0x3	/* SGMII 2.5G */
+#define COMPHY_2500BASEX_MODE	0x3	/* 2500Base-X */
 #define COMPHY_USB3H_MODE	0x4
 #define COMPHY_USB3D_MODE	0x5
 #define COMPHY_PCIE_MODE	0x6
diff --git a/drivers/marvell/comphy/phy-comphy-cp110.c b/drivers/marvell/comphy/phy-comphy-cp110.c
index d1c26f8..fa9fe41 100644
--- a/drivers/marvell/comphy/phy-comphy-cp110.c
+++ b/drivers/marvell/comphy/phy-comphy-cp110.c
@@ -8,6 +8,8 @@
 /* Marvell CP110 SoC COMPHY unit driver */
 
 #include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <common/debug.h>
 #include <drivers/delay_timer.h>
@@ -30,7 +32,7 @@
 /* COMPHY speed macro */
 #define COMPHY_SPEED_1_25G		0 /* SGMII 1G */
 #define COMPHY_SPEED_2_5G		1
-#define COMPHY_SPEED_3_125G		2 /* SGMII 2.5G */
+#define COMPHY_SPEED_3_125G		2 /* 2500Base-X */
 #define COMPHY_SPEED_5G			3
 #define COMPHY_SPEED_5_15625G		4 /* XFI 5G */
 #define COMPHY_SPEED_6G			5
@@ -53,14 +55,19 @@
 #define SYS_CTRL_FROM_COMPHY_ADDR(x)	((x & ~0xffffff) + 0x440000)
 
 /* DFX register spaces */
-#define SAR_RST_PCIE0_CLOCK_CONFIG_CP1_OFFSET	(0)
-#define SAR_RST_PCIE0_CLOCK_CONFIG_CP1_MASK	(0x1 << \
-					SAR_RST_PCIE0_CLOCK_CONFIG_CP1_OFFSET)
-#define SAR_RST_PCIE1_CLOCK_CONFIG_CP1_OFFSET	(1)
-#define SAR_RST_PCIE1_CLOCK_CONFIG_CP1_MASK	(0x1 << \
-					SAR_RST_PCIE1_CLOCK_CONFIG_CP1_OFFSET)
-#define SAR_STATUS_0_REG			200
+#define SAR_RST_PCIE0_CLOCK_CONFIG_CP0_OFFSET	(30)
+#define SAR_RST_PCIE0_CLOCK_CONFIG_CP0_MASK	(0x1UL << \
+					SAR_RST_PCIE0_CLOCK_CONFIG_CP0_OFFSET)
+#define SAR_RST_PCIE1_CLOCK_CONFIG_CP0_OFFSET	(31)
+#define SAR_RST_PCIE1_CLOCK_CONFIG_CP0_MASK	(0x1UL << \
+					SAR_RST_PCIE1_CLOCK_CONFIG_CP0_OFFSET)
+#define SAR_STATUS_0_REG			0x40600
 #define DFX_FROM_COMPHY_ADDR(x)			((x & ~0xffffff) + DFX_BASE)
+/* Common Phy training  */
+#define COMPHY_TRX_TRAIN_COMPHY_OFFS		0x1000
+#define COMPHY_TRX_TRAIN_RX_TRAIN_ENABLE	0x1
+#define COMPHY_TRX_RELATIVE_ADDR(comphy_index)	(comphy_train_base + \
+			(comphy_index) * COMPHY_TRX_TRAIN_COMPHY_OFFS)
 
 /* The same Units Soft Reset Config register are accessed in all PCIe ports
  * initialization, so a spin lock is defined in case when more than 1 CPUs
@@ -97,7 +104,7 @@
 	*cp_nr = (((comphy_base & ~0xffffff) - MVEBU_AP_IO_BASE(*ap_nr)) /
 		 MVEBU_CP_OFFSET);
 
-	debug("cp_base 0x%llx, ap_io_base 0x%lx, cp_offset 0x%lx\n",
+	debug("cp_base 0x%" PRIx64 ", ap_io_base 0x%lx, cp_offset 0x%lx\n",
 	       comphy_base, (unsigned long)MVEBU_AP_IO_BASE(*ap_nr),
 	       (unsigned long)MVEBU_CP_OFFSET);
 }
@@ -186,7 +193,7 @@
 		case(3):
 			/* For comphy 3:
 			 * 0x1 = RXAUI_Lane1
-			 * 0x2 = SGMII/HS-SGMII Port1
+			 * 0x2 = SGMII/Base-X Port1
 			 */
 			if (mode == COMPHY_RXAUI_MODE)
 				reg |= COMMON_SELECTOR_COMPHY3_RXAUI <<
@@ -197,20 +204,20 @@
 			break;
 		case(4):
 			 /* For comphy 4:
-			  * 0x1 = SGMII/HS-SGMII Port1, XFI1/SFI1
-			  * 0x2 = SGMII/HS-SGMII Port0: XFI0/SFI0, RXAUI_Lane0
+			  * 0x1 = SGMII/Base-X Port1, XFI1/SFI1
+			  * 0x2 = SGMII/Base-X Port0: XFI0/SFI0, RXAUI_Lane0
 			  *
-			  * We want to check if SGMII1/HS_SGMII1 is the
+			  * We want to check if SGMII1 is the
 			  * requested mode in order to determine which value
 			  * should be set (all other modes use the same value)
 			  * so we need to strip the mode, and check the ID
-			  * because we might handle SGMII0/HS_SGMII0 too.
+			  * because we might handle SGMII0 too.
 			  */
 			  /* TODO: need to distinguish between CP110 and CP115
 			   * as SFI1/XFI1 available only for CP115.
 			   */
 			if ((mode == COMPHY_SGMII_MODE ||
-			     mode == COMPHY_HS_SGMII_MODE ||
+			     mode == COMPHY_2500BASEX_MODE ||
 			     mode == COMPHY_SFI_MODE ||
 			     mode == COMPHY_XFI_MODE ||
 			     mode == COMPHY_AP_MODE)
@@ -223,7 +230,7 @@
 			break;
 		case(5):
 			/* For comphy 5:
-			 * 0x1 = SGMII/HS-SGMII Port2
+			 * 0x1 = SGMII/Base-X Port2
 			 * 0x2 = RXAUI Lane1
 			 */
 			if (mode == COMPHY_RXAUI_MODE)
@@ -708,7 +715,7 @@
 		data |= 0x6 << SD_EXTERNAL_CONFIG0_SD_PHY_GEN_RX_OFFSET;
 		data |= 0x6 << SD_EXTERNAL_CONFIG0_SD_PHY_GEN_TX_OFFSET;
 	} else if (sgmii_speed == COMPHY_SPEED_3_125G) {
-		/* HS SGMII (2.5G), SerDes speed 3.125G */
+		/* 2500Base-X, SerDes speed 3.125G */
 		data |= 0x8 << SD_EXTERNAL_CONFIG0_SD_PHY_GEN_RX_OFFSET;
 		data |= 0x8 << SD_EXTERNAL_CONFIG0_SD_PHY_GEN_TX_OFFSET;
 	} else {
@@ -829,7 +836,8 @@
 
 static int mvebu_cp110_comphy_xfi_power_on(uint64_t comphy_base,
 					   uint8_t comphy_index,
-					   uint32_t comphy_mode)
+					   uint32_t comphy_mode,
+					   uint64_t comphy_train_base)
 {
 	uintptr_t hpipe_addr, sd_ip_addr, comphy_addr, addr;
 	uint32_t mask, data, speed = COMPHY_GET_SPEED(comphy_mode);
@@ -837,7 +845,6 @@
 	uint8_t ap_nr, cp_nr;
 
 	debug_enter();
-
 	mvebu_cp110_get_ap_and_cp_nr(&ap_nr, &cp_nr, comphy_base);
 
 	if (rx_trainng_done[ap_nr][cp_nr][comphy_index]) {
@@ -1234,6 +1241,14 @@
 	data |= 0x1 << SD_EXTERNAL_CONFIG1_RF_RESET_IN_OFFSET;
 	reg_set(sd_ip_addr + SD_EXTERNAL_CONFIG1_REG, data, mask);
 
+	/* Force rx training on 10G port */
+	data = mmio_read_32(COMPHY_TRX_RELATIVE_ADDR(comphy_index));
+	data |= COMPHY_TRX_TRAIN_RX_TRAIN_ENABLE;
+	mmio_write_32(COMPHY_TRX_RELATIVE_ADDR(comphy_index), data);
+	mdelay(200);
+	data &= ~COMPHY_TRX_TRAIN_RX_TRAIN_ENABLE;
+	mmio_write_32(COMPHY_TRX_RELATIVE_ADDR(comphy_index), data);
+
 	debug_exit();
 
 	return ret;
@@ -1305,11 +1320,11 @@
 	reg = mmio_read_32(DFX_FROM_COMPHY_ADDR(comphy_base) +
 			   SAR_STATUS_0_REG);
 	if (comphy_index == COMPHY_LANE4 || comphy_index == COMPHY_LANE5)
-		clk_dir = (reg & SAR_RST_PCIE1_CLOCK_CONFIG_CP1_MASK) >>
-					  SAR_RST_PCIE1_CLOCK_CONFIG_CP1_OFFSET;
+		clk_dir = (reg & SAR_RST_PCIE1_CLOCK_CONFIG_CP0_MASK) >>
+					  SAR_RST_PCIE1_CLOCK_CONFIG_CP0_OFFSET;
 	else
-		clk_dir = (reg & SAR_RST_PCIE0_CLOCK_CONFIG_CP1_MASK) >>
-					  SAR_RST_PCIE0_CLOCK_CONFIG_CP1_OFFSET;
+		clk_dir = (reg & SAR_RST_PCIE0_CLOCK_CONFIG_CP0_MASK) >>
+					  SAR_RST_PCIE0_CLOCK_CONFIG_CP0_OFFSET;
 
 	debug("On lane %d\n", comphy_index);
 	debug("PCIe clock direction = %x\n", clk_dir);
@@ -1717,11 +1732,13 @@
 				HPIPE_LANE_STATUS1_REG;
 			data = HPIPE_LANE_STATUS1_PCLK_EN_MASK;
 			mask = data;
-			ret = polling_with_timeout(addr, data, mask,
+			data = polling_with_timeout(addr, data, mask,
 						   PLL_LOCK_TIMEOUT,
 						   REG_32BIT);
-			if (ret)
+			if (data) {
 				ERROR("Failed to lock PCIE PLL\n");
+				ret = -ETIMEDOUT;
+			}
 		}
 	}
 
@@ -2284,7 +2301,6 @@
 					  uint32_t comphy_mode)
 {
 	uint32_t mask, data;
-	uint8_t ap_nr, cp_nr;
 	uintptr_t comphy_addr = comphy_addr =
 				COMPHY_ADDR(comphy_base, comphy_index);
 
@@ -2301,10 +2317,16 @@
 	reg_set(comphy_addr + COMMON_PHY_CFG1_REG, data, mask);
 	debug_exit();
 
-	/* Start AP Firmware */
-	mvebu_cp110_get_ap_and_cp_nr(&ap_nr, &cp_nr, comphy_base);
-	mg_start_ap_fw(cp_nr, comphy_index);
+#if MSS_SUPPORT
+	do {
+		uint8_t ap_nr, cp_nr;
 
+		/* start ap fw */
+		mvebu_cp110_get_ap_and_cp_nr(&ap_nr, &cp_nr, comphy_base);
+		mg_start_ap_fw(cp_nr, comphy_index);
+
+	} while (0);
+#endif
 	return 0;
 }
 
@@ -2325,7 +2347,7 @@
 
 	switch (mode) {
 	case (COMPHY_SGMII_MODE):
-	case (COMPHY_HS_SGMII_MODE):
+	case (COMPHY_2500BASEX_MODE):
 	case (COMPHY_XFI_MODE):
 	case (COMPHY_SFI_MODE):
 	case (COMPHY_RXAUI_MODE):
@@ -2343,8 +2365,10 @@
 	return 0;
 }
 
-int mvebu_cp110_comphy_power_on(uint64_t comphy_base, uint8_t comphy_index,
-				uint64_t comphy_mode)
+int mvebu_cp110_comphy_power_on(uint64_t comphy_base,
+				uint8_t comphy_index,
+				uint64_t comphy_mode,
+				uint64_t comphy_train_base)
 {
 	int mode = COMPHY_GET_MODE(comphy_mode);
 	int err = 0;
@@ -2358,7 +2382,7 @@
 						       comphy_mode);
 		break;
 	case(COMPHY_SGMII_MODE):
-	case(COMPHY_HS_SGMII_MODE):
+	case(COMPHY_2500BASEX_MODE):
 		err = mvebu_cp110_comphy_sgmii_power_on(comphy_base,
 							comphy_index,
 							comphy_mode);
@@ -2368,7 +2392,8 @@
 	case (COMPHY_SFI_MODE):
 		err = mvebu_cp110_comphy_xfi_power_on(comphy_base,
 						      comphy_index,
-						      comphy_mode);
+						      comphy_mode,
+						      comphy_train_base);
 		break;
 	case (COMPHY_PCIE_MODE):
 		err = mvebu_cp110_comphy_pcie_power_on(comphy_base,
diff --git a/drivers/marvell/comphy/phy-comphy-cp110.h b/drivers/marvell/comphy/phy-comphy-cp110.h
index b4a2102..0be6c26 100644
--- a/drivers/marvell/comphy/phy-comphy-cp110.h
+++ b/drivers/marvell/comphy/phy-comphy-cp110.h
@@ -89,8 +89,9 @@
 				     uint8_t comphy_index);
 int mvebu_cp110_comphy_power_off(uint64_t comphy_base,
 				 uint8_t comphy_index, uint64_t comphy_mode);
-int mvebu_cp110_comphy_power_on(uint64_t comphy_base,
-				uint8_t comphy_index, uint64_t comphy_mode);
+int mvebu_cp110_comphy_power_on(uint64_t comphy_base, uint8_t comphy_index,
+				uint64_t comphy_mode,
+				uint64_t comphy_train_base);
 int mvebu_cp110_comphy_xfi_rx_training(uint64_t comphy_base,
 				       uint8_t comphy_index);
 int mvebu_cp110_comphy_digital_reset(uint64_t comphy_base, uint8_t comphy_index,
diff --git a/drivers/marvell/ddr_phy_access.c b/drivers/marvell/ddr_phy_access.c
new file mode 100644
index 0000000..352d1ef
--- /dev/null
+++ b/drivers/marvell/ddr_phy_access.c
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include "ddr_phy_access.h"
+#include <lib/mmio.h>
+#include <drivers/marvell/ccu.h>
+#include <errno.h>
+
+#define DDR_PHY_END_ADDRESS	0x100000
+
+#ifdef DDR_PHY_DEBUG
+#define debug_printf(...) printf(__VA_ARGS__)
+#else
+#define debug_printf(...)
+#endif
+
+
+/*
+ * This routine writes 'data' to specified 'address' offset,
+ * with optional debug print support
+ */
+int snps_fw_write(uintptr_t offset, uint16_t data)
+{
+	debug_printf("In %s\n", __func__);
+
+	if (offset < DDR_PHY_END_ADDRESS) {
+		mmio_write_16(DDR_PHY_BASE_ADDR + (2 * offset), data);
+		return 0;
+	}
+	debug_printf("%s: illegal offset value: 0x%x\n", __func__, offset);
+	return -EINVAL;
+}
+
+int snps_fw_read(uintptr_t offset, uint16_t *read)
+{
+	debug_printf("In %s\n", __func__);
+
+	if (offset < DDR_PHY_END_ADDRESS) {
+		*read = mmio_read_16(DDR_PHY_BASE_ADDR + (2 * offset));
+		return 0;
+	}
+	debug_printf("%s: illegal offset value: 0x%x\n", __func__, offset);
+	return -EINVAL;
+}
+
+int mvebu_ddr_phy_write(uintptr_t offset, uint16_t data)
+{
+	return snps_fw_write(offset, data);
+}
+
+int mvebu_ddr_phy_read(uintptr_t offset, uint16_t *read)
+{
+	return snps_fw_read(offset, read);
+}
diff --git a/drivers/marvell/ddr_phy_access.h b/drivers/marvell/ddr_phy_access.h
new file mode 100644
index 0000000..5f9a668
--- /dev/null
+++ b/drivers/marvell/ddr_phy_access.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <plat_marvell.h>
+
+#define DEVICE_BASE		0xF0000000
+#define DDR_PHY_OFFSET		0x1000000
+#define DDR_PHY_BASE_ADDR	(DEVICE_BASE + DDR_PHY_OFFSET)
+
+int mvebu_ddr_phy_write(uintptr_t offset, uint16_t data);
+int mvebu_ddr_phy_read(uintptr_t offset, uint16_t *read);
diff --git a/drivers/marvell/gwin.c b/drivers/marvell/gwin.c
index 9d94308..fa59cb0 100644
--- a/drivers/marvell/gwin.c
+++ b/drivers/marvell/gwin.c
@@ -7,6 +7,9 @@
 
 /* GWIN unit device driver for Marvell AP810 SoC */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <drivers/marvell/gwin.h>
 #include <lib/mmio.h>
@@ -49,14 +52,14 @@
 	/* The base is always 64M aligned */
 	if (IS_NOT_ALIGN(win->base_addr, GWIN_ALIGNMENT_64M)) {
 		win->base_addr &= ~(GWIN_ALIGNMENT_64M - 1);
-		NOTICE("%s: Align the base address to 0x%llx\n",
+		NOTICE("%s: Align the base address to 0x%" PRIx64 "\n",
 		       __func__, win->base_addr);
 	}
 
 	/* size parameter validity check */
 	if (IS_NOT_ALIGN(win->win_size, GWIN_ALIGNMENT_64M)) {
 		win->win_size = ALIGN_UP(win->win_size, GWIN_ALIGNMENT_64M);
-		NOTICE("%s: Aligning window size to 0x%llx\n",
+		NOTICE("%s: Aligning window size to 0x%" PRIx64 "\n",
 		       __func__, win->win_size);
 	}
 }
@@ -167,7 +170,7 @@
 			alr = (alr >> ADDRESS_LSHIFT) << ADDRESS_RSHIFT;
 			ahr = mmio_read_32(GWIN_AHR_OFFSET(ap_index, win_num));
 			ahr = (ahr >> ADDRESS_LSHIFT) << ADDRESS_RSHIFT;
-			printf("\tgwin   %d     0x%016llx 0x%016llx\n",
+			printf("\tgwin   %d     0x%016" PRIx64 " 0x%016" PRIx64 "\n",
 			       (cr >> 8) & 0xF, alr, ahr);
 		}
 	}
diff --git a/drivers/marvell/io_win.c b/drivers/marvell/io_win.c
index c4257fa..124382a 100644
--- a/drivers/marvell/io_win.c
+++ b/drivers/marvell/io_win.c
@@ -7,6 +7,9 @@
 
 /* IO Window unit device driver for Marvell AP807, AP807 and AP810 SoCs */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <drivers/marvell/io_win.h>
 #include <lib/mmio.h>
@@ -44,14 +47,14 @@
 	/* check if address is aligned to 1M */
 	if (IS_NOT_ALIGN(win->base_addr, IO_WIN_ALIGNMENT_1M)) {
 		win->base_addr = ALIGN_UP(win->base_addr, IO_WIN_ALIGNMENT_1M);
-		NOTICE("%s: Align up the base address to 0x%llx\n",
+		NOTICE("%s: Align up the base address to 0x%" PRIx64 "\n",
 		       __func__, win->base_addr);
 	}
 
 	/* size parameter validity check */
 	if (IS_NOT_ALIGN(win->win_size, IO_WIN_ALIGNMENT_1M)) {
 		win->win_size = ALIGN_UP(win->win_size, IO_WIN_ALIGNMENT_1M);
-		NOTICE("%s: Aligning size to 0x%llx\n",
+		NOTICE("%s: Aligning size to 0x%" PRIx64 "\n",
 		       __func__, win->win_size);
 	}
 }
@@ -170,7 +173,7 @@
 								win_id));
 			start = ((uint64_t)alr << ADDRESS_SHIFT);
 			end = (((uint64_t)ahr + 0x10) << ADDRESS_SHIFT);
-			printf("\tio-win %d     0x%016llx 0x%016llx\n",
+			printf("\tio-win %d     0x%016" PRIx64 " 0x%016" PRIx64 "\n",
 			       trgt_id, start, end);
 		}
 	}
diff --git a/drivers/marvell/iob.c b/drivers/marvell/iob.c
index 87f147a..1f39395 100644
--- a/drivers/marvell/iob.c
+++ b/drivers/marvell/iob.c
@@ -7,6 +7,9 @@
 
 /* IOW unit device driver for Marvell CP110 and CP115 SoCs */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <arch_helpers.h>
 #include <common/debug.h>
 #include <drivers/marvell/iob.h>
@@ -44,6 +47,10 @@
 #define IOB_WIN_ALR_OFFSET(win)		(iob_base + 0x8 + (0x20 * win))
 #define IOB_WIN_AHR_OFFSET(win)		(iob_base + 0xC + (0x20 * win))
 
+#define IOB_WIN_DIOB_CR_OFFSET(win)	(iob_base + 0x10 + (0x20 * win))
+#define IOB_WIN_XOR0_DIOB_EN		BIT(0)
+#define IOB_WIN_XOR1_DIOB_EN		BIT(1)
+
 uintptr_t iob_base;
 
 static void iob_win_check(struct addr_map_win *win, uint32_t win_num)
@@ -53,7 +60,7 @@
 		win->base_addr = ALIGN_UP(win->base_addr, IOB_WIN_ALIGNMENT);
 		ERROR("Window %d: base address unaligned to 0x%x\n",
 		      win_num, IOB_WIN_ALIGNMENT);
-		printf("Align up the base address to 0x%llx\n",
+		printf("Align up the base address to 0x%" PRIx64 "\n",
 		       win->base_addr);
 	}
 
@@ -62,7 +69,7 @@
 		win->win_size = ALIGN_UP(win->win_size, IOB_WIN_ALIGNMENT);
 		ERROR("Window %d: window size unaligned to 0x%x\n", win_num,
 		      IOB_WIN_ALIGNMENT);
-		printf("Aligning size to 0x%llx\n", win->win_size);
+		printf("Aligning size to 0x%" PRIx64 "\n", win->win_size);
 	}
 }
 
@@ -71,6 +78,17 @@
 	uint32_t iob_win_reg;
 	uint32_t alr, ahr;
 	uint64_t end_addr;
+	uint32_t reg_en;
+
+	/* move XOR (DMA) to use WIN1 which is used for PCI-EP address space */
+	reg_en = IOB_WIN_XOR0_DIOB_EN | IOB_WIN_XOR1_DIOB_EN;
+	iob_win_reg = mmio_read_32(IOB_WIN_DIOB_CR_OFFSET(0));
+	iob_win_reg &= ~reg_en;
+	mmio_write_32(IOB_WIN_DIOB_CR_OFFSET(0), iob_win_reg);
+
+	iob_win_reg = mmio_read_32(IOB_WIN_DIOB_CR_OFFSET(1));
+	iob_win_reg |= reg_en;
+	mmio_write_32(IOB_WIN_DIOB_CR_OFFSET(1), iob_win_reg);
 
 	end_addr = (win->base_addr + win->win_size - 1);
 	alr = (uint32_t)((win->base_addr >> ADDRESS_SHIFT) & ADDRESS_MASK);
@@ -115,7 +133,7 @@
 				 */
 				end = start + (16 << 20);
 			}
-			printf("iob   %02d %s   0x%016llx 0x%016llx\n",
+			printf("iob   %02d %s   0x%016" PRIx64 " 0x%016" PRIx64 "\n",
 			       win_id, iob_target_name[target_id],
 			       start, end);
 		}
diff --git a/drivers/marvell/mc_trustzone/mc_trustzone.c b/drivers/marvell/mc_trustzone/mc_trustzone.c
index 52b3006..648bd0e 100644
--- a/drivers/marvell/mc_trustzone/mc_trustzone.c
+++ b/drivers/marvell/mc_trustzone/mc_trustzone.c
@@ -5,6 +5,9 @@
  * https://spdx.org/licenses
  */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <drivers/marvell/addr_map.h>
 #include <lib/mmio.h>
@@ -39,7 +42,7 @@
 	/* map the window size to trustzone register convention */
 	tz_size = fls(TZ_SIZE(win->win_size));
 
-	VERBOSE("%s: window size = 0x%llx maps to tz_size %d\n",
+	VERBOSE("%s: window size = 0x%" PRIx64 " maps to tz_size %d\n",
 		__func__, win->win_size, tz_size);
 	if (tz_size < 0 || tz_size > 31) {
 		ERROR("Using not allowed size for MC TrustZone window %d!\n",
@@ -49,7 +52,7 @@
 
 	if (base & 0xfff) {
 		base = base & ~0xfff;
-		WARN("Attempt to open MC TZ win. at 0x%llx, truncate to 0x%x\n",
+		WARN("Attempt to open MC TZ win. at 0x%" PRIx64 ", truncate to 0x%x\n",
 		     win->base_addr, base);
 	}
 
diff --git a/drivers/marvell/mochi/ap807_setup.c b/drivers/marvell/mochi/ap807_setup.c
index 1069f8c..75e9654 100644
--- a/drivers/marvell/mochi/ap807_setup.c
+++ b/drivers/marvell/mochi/ap807_setup.c
@@ -15,8 +15,9 @@
 #include <drivers/marvell/mci.h>
 #include <drivers/marvell/mochi/ap_setup.h>
 #include <lib/mmio.h>
+#include <lib/utils_def.h>
 
-#include <mvebu_def.h>
+#include <a8k_plat_def.h>
 
 #define SMMU_sACR				(MVEBU_SMMU_BASE + 0x10)
 #define SMMU_sACR_PG_64K			(1 << 16)
@@ -71,6 +72,23 @@
 #define MVEBU_AXI_ATTR_REG(index)		(MVEBU_AXI_ATTR_BASE + \
 							0x4 * index)
 
+#define XOR_STREAM_ID_REG(ch)	(MVEBU_REGS_BASE + 0x410010 + (ch) * 0x20000)
+#define XOR_STREAM_ID_MASK	0xFFFF
+#define SDIO_STREAM_ID_REG	(MVEBU_RFU_BASE + 0x4600)
+#define SDIO_STREAM_ID_MASK	0xFF
+
+/* Do not use the default Stream ID 0 */
+#define A807_STREAM_ID_BASE	(0x1)
+
+static uintptr_t stream_id_reg[] = {
+	XOR_STREAM_ID_REG(0),
+	XOR_STREAM_ID_REG(1),
+	XOR_STREAM_ID_REG(2),
+	XOR_STREAM_ID_REG(3),
+	SDIO_STREAM_ID_REG,
+	0
+};
+
 enum axi_attr {
 	AXI_SDIO_ATTR = 0,
 	AXI_DFX_ATTR,
@@ -162,6 +180,21 @@
 				  MCI_REMAP_OFF_SHIFT);
 }
 
+/* Set a unique stream id for all DMA capable devices */
+static void ap807_stream_id_init(void)
+{
+	uint32_t i;
+
+	for (i = 0;
+	     stream_id_reg[i] != 0 && i < ARRAY_SIZE(stream_id_reg); i++) {
+		uint32_t mask = stream_id_reg[i] == SDIO_STREAM_ID_REG ?
+				SDIO_STREAM_ID_MASK : XOR_STREAM_ID_MASK;
+
+		mmio_clrsetbits_32(stream_id_reg[i], mask,
+				   i + A807_STREAM_ID_BASE);
+	}
+}
+
 static void ap807_axi_attr_init(void)
 {
 	uint32_t index, data;
@@ -265,6 +298,9 @@
 	/* configure CCU windows */
 	init_ccu(MVEBU_AP0);
 
+	/* Set the stream IDs for DMA masters */
+	ap807_stream_id_init();
+
 	/* configure the SMMU */
 	setup_smmu();
 
diff --git a/drivers/marvell/mochi/apn806_setup.c b/drivers/marvell/mochi/apn806_setup.c
index 8c3ba92..5c71fed 100644
--- a/drivers/marvell/mochi/apn806_setup.c
+++ b/drivers/marvell/mochi/apn806_setup.c
@@ -15,7 +15,7 @@
 #include <drivers/marvell/mochi/ap_setup.h>
 #include <lib/mmio.h>
 
-#include <mvebu_def.h>
+#include <a8k_plat_def.h>
 
 #define SMMU_sACR				(MVEBU_SMMU_BASE + 0x10)
 #define SMMU_sACR_PG_64K			(1 << 16)
@@ -67,6 +67,23 @@
 #define MVEBU_AXI_ATTR_REG(index)		(MVEBU_AXI_ATTR_BASE + \
 							0x4 * index)
 
+#define XOR_STREAM_ID_REG(ch)	(MVEBU_REGS_BASE + 0x410010 + (ch) * 0x20000)
+#define XOR_STREAM_ID_MASK	0xFFFF
+#define SDIO_STREAM_ID_REG	(MVEBU_RFU_BASE + 0x4600)
+#define SDIO_STREAM_ID_MASK	0xFF
+
+/* Do not use the default Stream ID 0 */
+#define A806_STREAM_ID_BASE	(0x1)
+
+static uintptr_t stream_id_reg[] = {
+	XOR_STREAM_ID_REG(0),
+	XOR_STREAM_ID_REG(1),
+	XOR_STREAM_ID_REG(2),
+	XOR_STREAM_ID_REG(3),
+	SDIO_STREAM_ID_REG,
+	0
+};
+
 enum axi_attr {
 	AXI_SDIO_ATTR = 0,
 	AXI_DFX_ATTR,
@@ -158,6 +175,20 @@
 			      MCI_REMAP_OFF_SHIFT);
 }
 
+/* Set a unique stream id for all DMA capable devices */
+static void ap806_stream_id_init(void)
+{
+	int i;
+
+	for (i = 0; stream_id_reg[i] != 0; i++) {
+		uint32_t mask = stream_id_reg[i] == SDIO_STREAM_ID_REG ?
+				SDIO_STREAM_ID_MASK : XOR_STREAM_ID_MASK;
+
+		mmio_clrsetbits_32(stream_id_reg[i], mask,
+				   i + A806_STREAM_ID_BASE);
+	}
+}
+
 static void apn806_axi_attr_init(void)
 {
 	uint32_t index, data;
@@ -236,6 +267,9 @@
 	/* configure DSS */
 	dss_setup();
 
+	/* Set the stream IDs for DMA masters */
+	ap806_stream_id_init();
+
 	/* configure the SMMU */
 	setup_smmu();
 
diff --git a/drivers/marvell/mochi/cp110_setup.c b/drivers/marvell/mochi/cp110_setup.c
index 0fa0497..f12da0e 100644
--- a/drivers/marvell/mochi/cp110_setup.c
+++ b/drivers/marvell/mochi/cp110_setup.c
@@ -12,7 +12,9 @@
 #include <drivers/marvell/amb_adec.h>
 #include <drivers/marvell/iob.h>
 #include <drivers/marvell/mochi/cp110_setup.h>
+#include <drivers/rambus/trng_ip_76.h>
 
+#include <efuse_def.h>
 #include <plat_marvell.h>
 
 /*
@@ -105,6 +107,13 @@
 #define MVEBU_RTC_READ_OUTPUT_DELAY_MASK		0xFFFF
 #define MVEBU_RTC_READ_OUTPUT_DELAY_DEFAULT		0x1F
 
+/*******************************************************************************
+ * TRNG Configuration
+ ******************************************************************************/
+#define MVEBU_TRNG_BASE					(0x760000)
+#define MVEBU_EFUSE_TRNG_ENABLE_EFUSE_WORD		MVEBU_AP_LDX_220_189_EFUSE_OFFS
+#define MVEBU_EFUSE_TRNG_ENABLE_BIT_OFFSET		13	/* LD0[202] */
+
 enum axi_attr {
 	AXI_ADUNIT_ATTR = 0,
 	AXI_COMUNIT_ATTR,
@@ -130,7 +139,7 @@
 #define USB3H_1_STREAM_ID_REG	(RFU_STREAM_ID_BASE + 0x10)
 #define SATA_0_STREAM_ID_REG	(RFU_STREAM_ID_BASE + 0x14)
 #define SATA_1_STREAM_ID_REG	(RFU_STREAM_ID_BASE + 0x18)
-#define SDIO_0_STREAM_ID_REG	(RFU_STREAM_ID_BASE + 0x28)
+#define SDIO_STREAM_ID_REG	(RFU_STREAM_ID_BASE + 0x28)
 
 #define CP_DMA_0_STREAM_ID_REG  (0x6B0010)
 #define CP_DMA_1_STREAM_ID_REG  (0x6D0010)
@@ -138,14 +147,14 @@
 /* We allocate IDs 128-255 for PCIe */
 #define MAX_STREAM_ID		(0x80)
 
-uintptr_t stream_id_reg[] = {
+static uintptr_t stream_id_reg[] = {
 	USB3H_0_STREAM_ID_REG,
 	USB3H_1_STREAM_ID_REG,
 	CP_DMA_0_STREAM_ID_REG,
 	CP_DMA_1_STREAM_ID_REG,
 	SATA_0_STREAM_ID_REG,
 	SATA_1_STREAM_ID_REG,
-	SDIO_0_STREAM_ID_REG,
+	SDIO_STREAM_ID_REG,
 	0
 };
 
@@ -180,8 +189,9 @@
 	pcie0_clk = (reg & SAR_PCIE0_CLK_CFG_MASK) >> SAR_PCIE0_CLK_CFG_OFFSET;
 	pcie1_clk = (reg & SAR_PCIE1_CLK_CFG_MASK) >> SAR_PCIE1_CLK_CFG_OFFSET;
 
-	/* CP110 revision A2 */
-	if (cp110_rev_id_get(base) == MVEBU_CP110_REF_ID_A2) {
+	/* CP110 revision A2 or CN913x */
+	if (cp110_rev_id_get(base) == MVEBU_CP110_REF_ID_A2 ||
+	    cp110_device_id_get(base) == MVEBU_CN9130_DEV_ID) {
 		/*
 		 * PCIe Reference Clock Buffer Control register must be
 		 * set according to the clock direction (input/output)
@@ -378,6 +388,36 @@
 	init_amb_adec(base);
 }
 
+static void cp110_trng_init(uintptr_t base)
+{
+	static bool done;
+	int ret;
+	uint32_t reg_val, efuse;
+
+	/* Set access to LD0 */
+	reg_val = mmio_read_32(MVEBU_AP_EFUSE_SRV_CTRL_REG);
+	reg_val &= ~EFUSE_SRV_CTRL_LD_SELECT_MASK;
+	mmio_write_32(MVEBU_AP_EFUSE_SRV_CTRL_REG, reg_val);
+
+	/* Obtain the AP LD0 bit defining TRNG presence */
+	efuse = mmio_read_32(MVEBU_EFUSE_TRNG_ENABLE_EFUSE_WORD);
+	efuse >>= MVEBU_EFUSE_TRNG_ENABLE_BIT_OFFSET;
+	efuse &= 1;
+
+	if (efuse == 0) {
+		VERBOSE("TRNG is not present, skipping");
+		return;
+	}
+
+	if (!done) {
+		ret = eip76_rng_probe(base + MVEBU_TRNG_BASE);
+		if (ret != 0) {
+			ERROR("Failed to init TRNG @ 0x%lx\n", base);
+			return;
+		}
+		done = true;
+	}
+}
 void cp110_init(uintptr_t cp110_base, uint32_t stream_id)
 {
 	INFO("%s: Initialize CPx - base = %lx\n", __func__, cp110_base);
@@ -405,6 +445,9 @@
 
 	/* Reset RTC if needed */
 	cp110_rtc_init(cp110_base);
+
+	/* TRNG init - for CP0 only */
+	cp110_trng_init(cp110_base);
 }
 
 /* Do the minimal setup required to configure the CP in BLE */
diff --git a/drivers/marvell/secure_dfx_access/armada_thermal.c b/drivers/marvell/secure_dfx_access/armada_thermal.c
new file mode 100644
index 0000000..4f7191b
--- /dev/null
+++ b/drivers/marvell/secure_dfx_access/armada_thermal.c
@@ -0,0 +1,253 @@
+/*
+ * Copyright (C) 2019 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <errno.h>
+#include <lib/mmio.h>
+#include <mvebu.h>
+#include <stdbool.h>
+#include "dfx.h"
+
+/* #define DEBUG_DFX */
+#ifdef DEBUG_DFX
+#define debug(format...) NOTICE(format)
+#else
+#define debug(format, arg...)
+#endif
+
+#define TSEN_CTRL0			0xf06f8084
+ #define TSEN_CTRL0_START		BIT(0)
+ #define TSEN_CTRL0_RESET		BIT(1)
+ #define TSEN_CTRL0_ENABLE		BIT(2)
+ #define TSEN_CTRL0_AVG_BYPASS		BIT(6)
+ #define TSEN_CTRL0_CHAN_SHIFT		13
+ #define TSEN_CTRL0_CHAN_MASK		0xF
+ #define TSEN_CTRL0_OSR_SHIFT		24
+ #define TSEN_CTRL0_OSR_MAX		0x3
+ #define TSEN_CTRL0_MODE_SHIFT		30
+ #define TSEN_CTRL0_MODE_EXTERNAL	0x2U
+ #define TSEN_CTRL0_MODE_MASK		0x3U
+
+#define TSEN_CTRL1			0xf06f8088
+ #define TSEN_CTRL1_INT_EN		BIT(25)
+ #define TSEN_CTRL1_HYST_SHIFT		19
+ #define TSEN_CTRL1_HYST_MASK		(0x3 << TSEN_CTRL1_HYST_SHIFT)
+ #define TSEN_CTRL1_THRESH_SHIFT	3
+ #define TSEN_CTRL1_THRESH_MASK		(0x3ff << TSEN_CTRL1_THRESH_SHIFT)
+
+#define TSEN_STATUS			0xf06f808c
+ #define TSEN_STATUS_VALID_OFFSET	16
+ #define TSEN_STATUS_VALID_MASK		(0x1 << TSEN_STATUS_VALID_OFFSET)
+ #define TSEN_STATUS_TEMP_OUT_OFFSET	0
+ #define TSEN_STATUS_TEMP_OUT_MASK	(0x3FF << TSEN_STATUS_TEMP_OUT_OFFSET)
+
+#define DFX_SERVER_IRQ_SUM_MASK_REG	0xf06f8104
+ #define DFX_SERVER_IRQ_EN		BIT(1)
+
+#define DFX_IRQ_CAUSE_REG		0xf06f8108
+
+#define DFX_IRQ_MASK_REG		0xf06f810c
+ #define DFX_IRQ_TSEN_OVERHEAT_OFFSET	BIT(22)
+
+#define THERMAL_SEN_OUTPUT_MSB		512
+#define THERMAL_SEN_OUTPUT_COMP		1024
+
+#define COEF_M 423
+#define COEF_B -150000LL
+
+static void armada_ap806_thermal_read(u_register_t *temp)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(TSEN_STATUS);
+
+	reg = ((reg & TSEN_STATUS_TEMP_OUT_MASK) >>
+	      TSEN_STATUS_TEMP_OUT_OFFSET);
+
+	/*
+	 * TSEN output format is signed as a 2s complement number
+	 * ranging from-512 to +511. when MSB is set, need to
+	 * calculate the complement number
+	 */
+	if (reg >= THERMAL_SEN_OUTPUT_MSB)
+		reg -= THERMAL_SEN_OUTPUT_COMP;
+
+	*temp = ((COEF_M * ((signed int)reg)) - COEF_B);
+}
+
+static void armada_ap806_thermal_irq(void)
+{
+	/* Dummy read, register ROC */
+	mmio_read_32(DFX_IRQ_CAUSE_REG);
+}
+
+static void armada_ap806_thermal_overheat_irq_init(void)
+{
+	uint32_t reg;
+
+	/* Clear DFX temperature IRQ cause */
+	reg = mmio_read_32(DFX_IRQ_CAUSE_REG);
+
+	/* Enable DFX Temperature IRQ */
+	reg = mmio_read_32(DFX_IRQ_MASK_REG);
+	reg |= DFX_IRQ_TSEN_OVERHEAT_OFFSET;
+	mmio_write_32(DFX_IRQ_MASK_REG, reg);
+
+	/* Enable DFX server IRQ */
+	reg = mmio_read_32(DFX_SERVER_IRQ_SUM_MASK_REG);
+	reg |= DFX_SERVER_IRQ_EN;
+	mmio_write_32(DFX_SERVER_IRQ_SUM_MASK_REG, reg);
+
+	/* Enable overheat interrupt */
+	reg = mmio_read_32(TSEN_CTRL1);
+	reg |= TSEN_CTRL1_INT_EN;
+	mmio_write_32(TSEN_CTRL1, reg);
+}
+
+static unsigned int armada_mc_to_reg_temp(unsigned int temp_mc)
+{
+	unsigned int sample;
+
+	sample = (temp_mc + COEF_B) / COEF_M;
+
+	return sample & 0x3ff;
+}
+
+/*
+ * The documentation states:
+ * high/low watermark = threshold +/- 0.4761 * 2^(hysteresis + 2)
+ * which is the mathematical derivation for:
+ * 0x0 <=> 1.9°C, 0x1 <=> 3.8°C, 0x2 <=> 7.6°C, 0x3 <=> 15.2°C
+ */
+static unsigned int hyst_levels_mc[] = {1900, 3800, 7600, 15200};
+
+static unsigned int armada_mc_to_reg_hyst(int hyst_mc)
+{
+	int i;
+
+	/*
+	 * We will always take the smallest possible hysteresis to avoid risking
+	 * the hardware integrity by enlarging the threshold by +8°C in the
+	 * worst case.
+	 */
+	for (i = ARRAY_SIZE(hyst_levels_mc) - 1; i > 0; i--)
+		if (hyst_mc >= hyst_levels_mc[i])
+			break;
+
+	return i;
+}
+
+static void armada_ap806_thermal_threshold(int thresh_mc, int hyst_mc)
+{
+	uint32_t ctrl1;
+	unsigned int threshold = armada_mc_to_reg_temp(thresh_mc);
+	unsigned int hysteresis = armada_mc_to_reg_hyst(hyst_mc);
+
+	ctrl1 = mmio_read_32(TSEN_CTRL1);
+	/* Set Threshold */
+	if (thresh_mc >= 0) {
+		ctrl1 &= ~(TSEN_CTRL1_THRESH_MASK);
+		ctrl1 |= threshold << TSEN_CTRL1_THRESH_SHIFT;
+	}
+
+	/* Set Hysteresis */
+	if (hyst_mc >= 0) {
+		ctrl1 &= ~(TSEN_CTRL1_HYST_MASK);
+		ctrl1 |= hysteresis << TSEN_CTRL1_HYST_SHIFT;
+	}
+
+	mmio_write_32(TSEN_CTRL1, ctrl1);
+}
+
+static void armada_select_channel(int channel)
+{
+	uint32_t ctrl0;
+
+	/* Stop the measurements */
+	ctrl0 = mmio_read_32(TSEN_CTRL0);
+	ctrl0 &= ~TSEN_CTRL0_START;
+	mmio_write_32(TSEN_CTRL0, ctrl0);
+
+	/* Reset the mode, internal sensor will be automatically selected */
+	ctrl0 &= ~(TSEN_CTRL0_MODE_MASK << TSEN_CTRL0_MODE_SHIFT);
+
+	/* Other channels are external and should be selected accordingly */
+	if (channel) {
+		/* Change the mode to external */
+		ctrl0 |= TSEN_CTRL0_MODE_EXTERNAL <<
+			 TSEN_CTRL0_MODE_SHIFT;
+		/* Select the sensor */
+		ctrl0 &= ~(TSEN_CTRL0_CHAN_MASK << TSEN_CTRL0_CHAN_SHIFT);
+		ctrl0 |= (channel - 1) << TSEN_CTRL0_CHAN_SHIFT;
+	}
+
+	/* Actually set the mode/channel */
+	mmio_write_32(TSEN_CTRL0, ctrl0);
+
+	/* Re-start the measurements */
+	ctrl0 |= TSEN_CTRL0_START;
+	mmio_write_32(TSEN_CTRL0, ctrl0);
+}
+
+static void armada_ap806_thermal_init(void)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(TSEN_CTRL0);
+	reg &= ~TSEN_CTRL0_RESET;
+	reg |= TSEN_CTRL0_START | TSEN_CTRL0_ENABLE;
+
+	/* Sample every ~2ms */
+	reg |= TSEN_CTRL0_OSR_MAX << TSEN_CTRL0_OSR_SHIFT;
+
+	/* Enable average (2 samples by default) */
+	reg &= ~TSEN_CTRL0_AVG_BYPASS;
+
+	mmio_write_32(TSEN_CTRL0, reg);
+
+	debug("thermal: Initialization done\n");
+}
+
+static void armada_is_valid(u_register_t *read)
+{
+	*read = (mmio_read_32(TSEN_STATUS) & TSEN_STATUS_VALID_MASK);
+}
+
+int mvebu_dfx_thermal_handle(u_register_t func, u_register_t *read,
+			     u_register_t x2, u_register_t x3)
+{
+	debug_enter();
+
+	switch (func) {
+	case MV_SIP_DFX_THERMAL_INIT:
+		armada_ap806_thermal_init();
+		break;
+	case MV_SIP_DFX_THERMAL_READ:
+		armada_ap806_thermal_read(read);
+		break;
+	case MV_SIP_DFX_THERMAL_IRQ:
+		armada_ap806_thermal_irq();
+		break;
+	case MV_SIP_DFX_THERMAL_THRESH:
+		armada_ap806_thermal_threshold(x2, x3);
+		armada_ap806_thermal_overheat_irq_init();
+		break;
+	case MV_SIP_DFX_THERMAL_IS_VALID:
+		armada_is_valid(read);
+		break;
+	case MV_SIP_DFX_THERMAL_SEL_CHANNEL:
+		armada_select_channel(x2);
+		break;
+	default:
+		ERROR("unsupported dfx func\n");
+		return -EINVAL;
+	}
+
+	debug_exit();
+
+	return 0;
+}
diff --git a/drivers/marvell/secure_dfx_access/dfx.h b/drivers/marvell/secure_dfx_access/dfx.h
new file mode 100644
index 0000000..88c4de8
--- /dev/null
+++ b/drivers/marvell/secure_dfx_access/dfx.h
@@ -0,0 +1,22 @@
+/*
+ * Copyright (C) 2019 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+/* DFX sub-FID */
+#define MV_SIP_DFX_THERMAL_INIT		1
+#define MV_SIP_DFX_THERMAL_READ		2
+#define MV_SIP_DFX_THERMAL_IS_VALID	3
+#define MV_SIP_DFX_THERMAL_IRQ		4
+#define MV_SIP_DFX_THERMAL_THRESH	5
+#define MV_SIP_DFX_THERMAL_SEL_CHANNEL	6
+
+#define MV_SIP_DFX_SREAD		20
+#define MV_SIP_DFX_SWRITE		21
+
+int mvebu_dfx_thermal_handle(u_register_t func, u_register_t *read,
+			     u_register_t x2, u_register_t x3);
+int mvebu_dfx_misc_handle(u_register_t func, u_register_t *read,
+			  u_register_t addr, u_register_t val);
diff --git a/drivers/marvell/secure_dfx_access/misc_dfx.c b/drivers/marvell/secure_dfx_access/misc_dfx.c
new file mode 100644
index 0000000..189105f
--- /dev/null
+++ b/drivers/marvell/secure_dfx_access/misc_dfx.c
@@ -0,0 +1,123 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include "dfx.h"
+#include <mvebu_def.h>
+#include <mvebu.h>
+#include <errno.h>
+
+/* #define DEBUG_DFX */
+#ifdef DEBUG_DFX
+#define debug(format...) NOTICE(format)
+#else
+#define debug(format, arg...)
+#endif
+
+#define SAR_BASE			(MVEBU_REGS_BASE + 0x6F8200)
+#define SAR_SIZE			0x4
+#define AP_DEV_ID_STATUS_REG		(MVEBU_REGS_BASE + 0x6F8240)
+#define JTAG_DEV_ID_STATUS_REG		(MVEBU_REGS_BASE + 0x6F8244)
+#define EFUSE_CTRL			(MVEBU_REGS_BASE + 0x6F8008)
+#define EFUSE_LD_BASE			(MVEBU_REGS_BASE + 0x6F8F00)
+#define EFUSE_LD_SIZE			0x1C
+#define EFUSE_HD_BASE			(MVEBU_REGS_BASE + 0x6F9000)
+#define EFUSE_HD_SIZE			0x3F8
+
+/* AP806 CPU DFS register mapping*/
+#define AP806_CA72MP2_0_PLL_CR_0_BASE		(MVEBU_REGS_BASE + 0x6F8278)
+#define AP806_CA72MP2_0_PLL_CR_1_BASE		(MVEBU_REGS_BASE + 0x6F8280)
+#define AP806_CA72MP2_0_PLL_CR_2_BASE		(MVEBU_REGS_BASE + 0x6F8284)
+#define AP806_CA72MP2_0_PLL_SR_BASE		(MVEBU_REGS_BASE + 0x6F8C94)
+
+/* AP807 CPU DFS register mapping */
+#define AP807_DEVICE_GENERAL_CR_10_BASE		(MVEBU_REGS_BASE + 0x6F8278)
+#define AP807_DEVICE_GENERAL_CR_11_BASE		(MVEBU_REGS_BASE + 0x6F827C)
+#define AP807_DEVICE_GENERAL_STATUS_6_BASE	(MVEBU_REGS_BASE + 0x6F8C98)
+
+#ifdef MVEBU_SOC_AP807
+ #define CLUSTER_OFFSET		0x8
+ #define CLK_DIVIDER_REG	AP807_DEVICE_GENERAL_CR_10_BASE
+ #define CLK_FORCE_REG		AP807_DEVICE_GENERAL_CR_11_BASE
+ #define CLK_RATIO_REG		AP807_DEVICE_GENERAL_CR_11_BASE
+ #define CLK_RATIO_STATE_REG	AP807_DEVICE_GENERAL_STATUS_6_BASE
+#else
+ #define CLUSTER_OFFSET		0x14
+ #define CLK_DIVIDER_REG		AP806_CA72MP2_0_PLL_CR_0_BASE
+ #define CLK_FORCE_REG		AP806_CA72MP2_0_PLL_CR_1_BASE
+ #define CLK_RATIO_REG		AP806_CA72MP2_0_PLL_CR_2_BASE
+ #define CLK_RATIO_STATE_REG	AP806_CA72MP2_0_PLL_SR_BASE
+#endif /* MVEBU_SOC_AP807 */
+
+static _Bool is_valid(u_register_t addr)
+{
+	switch (addr) {
+	case AP_DEV_ID_STATUS_REG:
+	case JTAG_DEV_ID_STATUS_REG:
+	case SAR_BASE ... (SAR_BASE + SAR_SIZE):
+	case EFUSE_LD_BASE ... (EFUSE_LD_BASE + EFUSE_LD_SIZE):
+	case EFUSE_HD_BASE ... (EFUSE_HD_BASE + EFUSE_HD_SIZE):
+	case EFUSE_CTRL:
+	/* cpu-clk related registers */
+	case CLK_DIVIDER_REG:
+	case CLK_DIVIDER_REG + CLUSTER_OFFSET:
+	case CLK_FORCE_REG:
+	case CLK_FORCE_REG + CLUSTER_OFFSET:
+#ifndef MVEBU_SOC_AP807
+	case CLK_RATIO_REG:
+	case CLK_RATIO_REG + CLUSTER_OFFSET:
+#endif
+	case CLK_RATIO_STATE_REG:
+	case CLK_RATIO_STATE_REG + CLUSTER_OFFSET:
+		return true;
+	default:
+		return false;
+	}
+}
+
+static int armada_dfx_sread(u_register_t *read, u_register_t addr)
+{
+	if (!is_valid(addr))
+		return -EINVAL;
+
+	*read = mmio_read_32(addr);
+
+	return 0;
+}
+
+static int armada_dfx_swrite(u_register_t addr, u_register_t val)
+{
+	if (!is_valid(addr))
+		return -EINVAL;
+
+	mmio_write_32(addr, val);
+
+	return 0;
+}
+
+int mvebu_dfx_misc_handle(u_register_t func, u_register_t *read,
+			  u_register_t addr, u_register_t val)
+{
+	debug_enter();
+
+	debug("func %ld, addr 0x%lx, val 0x%lx\n", func, addr, val);
+
+	switch (func) {
+	case MV_SIP_DFX_SREAD:
+		return armada_dfx_sread(read, addr);
+	case MV_SIP_DFX_SWRITE:
+		return armada_dfx_swrite(addr, val);
+	default:
+		ERROR("unsupported dfx misc sub-func\n");
+		return -EINVAL;
+	}
+
+	debug_exit();
+
+	return 0;
+}
diff --git a/drivers/marvell/uart/a3700_console.S b/drivers/marvell/uart/a3700_console.S
index d184a2d..218fd86 100644
--- a/drivers/marvell/uart/a3700_console.S
+++ b/drivers/marvell/uart/a3700_console.S
@@ -45,40 +45,38 @@
 	cbz	w2, init_fail
 
 	/* Program the baudrate */
-	/* Divisor =  Uart clock / (16 * baudrate) */
+	/* Divisor = Round(Uartclock / (16 * baudrate)) */
 	lsl	w2, w2, #4
+	add	w1, w1, w2, lsr #1
 	udiv	w2, w1, w2
-	and	w2, w2, #0x3ff
+	and	w2, w2, #0x3ff /* clear all other bits to use default clock */
 
-	ldr	w3, [x0, #UART_BAUD_REG]
-	bic	w3, w3, 0x3ff
-	orr	w3, w3, w2
-	str	w3, [x0, #UART_BAUD_REG]/* set baud rate divisor */
+	str	w2, [x0, #UART_BAUD_REG]/* set baud rate divisor */
 
 	/* Set UART to default 16X scheme */
 	mov	w3, #0
 	str	w3, [x0, #UART_POSSR_REG]
 
 	/*
-	 * Wait for the TX FIFO to be empty. If wait for 20ms, the TX FIFO is
+	 * Wait for the TX (THR and TSR) to be empty. If wait for 3ms, the TX FIFO is
 	 * still not empty, TX FIFO will reset by all means.
 	 */
-	mov	w1, #20				/* max time out 20ms */
+	mov	w1, #30				/* max time out 30 * 100 us */
 2:
-	/* Check whether TX FIFO is empty */
+	/* Check whether TX (THR and TSR) is empty */
 	ldr	w3, [x0, #UART_STATUS_REG]
-	and	w3, w3, #UARTLSR_TXFIFOEMPTY
+	and	w3, w3, #UARTLSR_TXEMPTY
 	cmp	w3, #0
 	b.ne	4f
 
 	/* Delay */
-	mov	w2, #30000
+	mov	w2, #60000	/* 60000 cycles of below 3 instructions on 1200 MHz CPU ~~ 100 us */
 3:
 	sub     w2, w2, #1
 	cmp	w2, #0
 	b.ne	3b
 
-	/* Check whether 10ms is waited */
+	/* Check whether wait timeout expired */
 	sub     w1, w1, #1
 	cmp	w1, #0
 	b.ne	2b
@@ -196,14 +194,23 @@
 	 * int console_a3700_core_getc(void)
 	 * Function to get a character from the console.
 	 * It returns the character grabbed on success
-	 * or -1 on error.
+	 * or -1 if no character is available.
 	 * In : w0 - console base address
-	 * Out : return -1 on error else return character.
+	 * Out : w0 - character if available, else -1
 	 * Clobber list : x0, x1
 	 * ---------------------------------------------
 	 */
 func console_a3700_core_getc
-	mov	w0, #-1
+	/* Check if there is a pending character */
+	ldr	w1, [x0, #UART_STATUS_REG]
+	and	w1, w1, #UARTLSR_RXRDY
+	cmp	w1, #UARTLSR_RXRDY
+	b.ne	getc_no_char
+	ldr	w0, [x0, #UART_RX_REG]
+	and	w0, w0, #0xff
+	ret
+getc_no_char:
+	mov	w0, #ERROR_NO_PENDING_CHAR
 	ret
 endfunc console_a3700_core_getc
 
@@ -232,6 +239,11 @@
 	 * ---------------------------------------------
 	 */
 func console_a3700_core_flush
+	/* Wait for the TX (THR and TSR) to be empty */
+1:	ldr	w1, [x0, #UART_STATUS_REG]
+	and	w1, w1, #UARTLSR_TXEMPTY
+	cmp	w1, #UARTLSR_TXEMPTY
+	b.ne	1b
 	ret
 endfunc console_a3700_core_flush
 
diff --git a/drivers/measured_boot/event_log.c b/drivers/measured_boot/event_log.c
deleted file mode 100644
index 727bdf5..0000000
--- a/drivers/measured_boot/event_log.c
+++ /dev/null
@@ -1,410 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-#include <errno.h>
-#include <string.h>
-#include <arch_helpers.h>
-
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/auth/crypto_mod.h>
-#include <drivers/measured_boot/event_log.h>
-#include <mbedtls/md.h>
-
-#include <plat/common/platform.h>
-
-/* Event Log data */
-static uint8_t event_log[EVENT_LOG_SIZE];
-
-/* End of Event Log */
-#define	EVENT_LOG_END	((uintptr_t)event_log + sizeof(event_log) - 1U)
-
-CASSERT(sizeof(event_log) >= LOG_MIN_SIZE, assert_event_log_size);
-
-/* Pointer in event_log[] */
-static uint8_t *log_ptr = event_log;
-
-/* Pointer to measured_boot_data_t */
-const static measured_boot_data_t *plat_data_ptr;
-
-static uintptr_t tos_fw_config_base;
-static uintptr_t nt_fw_config_base;
-
-/* TCG_EfiSpecIdEvent */
-static const id_event_headers_t id_event_header = {
-	.header = {
-		.pcr_index = PCR_0,
-		.event_type = EV_NO_ACTION,
-		.digest = {0},
-		.event_size = (uint32_t)(sizeof(id_event_struct_t) +
-				(sizeof(id_event_algorithm_size_t) *
-				HASH_ALG_COUNT))
-	},
-
-	.struct_header = {
-		.signature = TCG_ID_EVENT_SIGNATURE_03,
-		.platform_class = PLATFORM_CLASS_CLIENT,
-		.spec_version_minor = TCG_SPEC_VERSION_MINOR_TPM2,
-		.spec_version_major = TCG_SPEC_VERSION_MAJOR_TPM2,
-		.spec_errata = TCG_SPEC_ERRATA_TPM2,
-		.uintn_size = (uint8_t)(sizeof(unsigned int) /
-					sizeof(uint32_t)),
-		.number_of_algorithms = HASH_ALG_COUNT
-	}
-};
-
-static const event2_header_t locality_event_header = {
-		/*
-		 * All EV_NO_ACTION events SHALL set
-		 * TCG_PCR_EVENT2.pcrIndex = 0, unless otherwise specified
-		 */
-		.pcr_index = PCR_0,
-
-		/*
-		 * All EV_NO_ACTION events SHALL set
-		 * TCG_PCR_EVENT2.eventType = 03h
-		 */
-		.event_type = EV_NO_ACTION,
-
-		/*
-		 * All EV_NO_ACTION events SHALL set
-		 * TCG_PCR_EVENT2.digests to all
-		 * 0x00's for each allocated Hash algorithm
-		 */
-		.digests = {
-			.count = HASH_ALG_COUNT
-		}
-};
-
-/* Platform's table with platform specific image IDs, names and PCRs */
-static const image_data_t plat_images_data[] = {
-	{ BL2_IMAGE_ID, BL2_STRING, PCR_0 },		/* Reserved for BL2 */
-	{ INVALID_ID, NULL, (unsigned int)(-1) }	/* Terminator */
-};
-
-static const measured_boot_data_t plat_measured_boot_data = {
-	plat_images_data,
-	NULL,	/* platform_set_nt_fw_info */
-	NULL	/* platform_set_tos_fw_info */
-};
-
-/*
- * Function retuns pointer to platform's measured_boot_data_t structure
- *
- * Must be overridden in the platform code
- */
-#pragma weak plat_get_measured_boot_data
-
-const measured_boot_data_t *plat_get_measured_boot_data(void)
-{
-	return &plat_measured_boot_data;
-}
-
-/*
- * Add TCG_PCR_EVENT2 event
- *
- * @param[in] hash	Pointer to hash data of TCG_DIGEST_SIZE bytes
- * @param[in] image_ptr	Pointer to image_data_t structure
- * @return:
- *	0 = success
- *    < 0 = error code
- */
-static int add_event2(const uint8_t *hash, const image_data_t *image_ptr)
-{
-	void *ptr = log_ptr;
-	uint32_t name_len;
-	uint32_t size_of_event;
-
-	assert(image_ptr != NULL);
-	assert(image_ptr->name != NULL);
-
-	name_len = (uint32_t)strlen(image_ptr->name) + 1U;
-	size_of_event = name_len + (uint32_t)EVENT2_HDR_SIZE;
-
-	/* Check for space in Event Log buffer */
-	if (((uintptr_t)ptr + size_of_event) > EVENT_LOG_END) {
-		ERROR("%s(): Event Log is short of memory", __func__);
-		return -ENOMEM;
-	}
-
-	/*
-	 * As per TCG specifications, firmware components that are measured
-	 * into PCR[0] must be logged in the event log using the event type
-	 * EV_POST_CODE.
-	 */
-	/* TCG_PCR_EVENT2.PCRIndex */
-	((event2_header_t *)ptr)->pcr_index = image_ptr->pcr;
-
-	/* TCG_PCR_EVENT2.EventType */
-	((event2_header_t *)ptr)->event_type = EV_POST_CODE;
-
-	/* TCG_PCR_EVENT2.Digests.Count */
-	ptr = (uint8_t *)ptr + offsetof(event2_header_t, digests);
-	((tpml_digest_values *)ptr)->count = HASH_ALG_COUNT;
-
-	/* TCG_PCR_EVENT2.Digests[] */
-	ptr = (uint8_t *)((uintptr_t)ptr +
-			offsetof(tpml_digest_values, digests));
-
-	/* TCG_PCR_EVENT2.Digests[].AlgorithmId */
-	((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
-
-	/* TCG_PCR_EVENT2.Digests[].Digest[] */
-	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(tpmt_ha, digest));
-
-	/* Check for space in Event Log buffer */
-	if (((uintptr_t)ptr + TCG_DIGEST_SIZE) > EVENT_LOG_END) {
-		ERROR("%s(): Event Log is short of memory", __func__);
-		return -ENOMEM;
-	}
-
-	if (hash == NULL) {
-		/* Get BL2 hash from DTB */
-		bl2_plat_get_hash(ptr);
-	} else {
-		/* Copy digest */
-		(void)memcpy(ptr, (const void *)hash, TCG_DIGEST_SIZE);
-	}
-
-	/* TCG_PCR_EVENT2.EventSize */
-	ptr = (uint8_t *)((uintptr_t)ptr + TCG_DIGEST_SIZE);
-	((event2_data_t *)ptr)->event_size = name_len;
-
-	/* Copy event data to TCG_PCR_EVENT2.Event */
-	(void)memcpy((void *)(((event2_data_t *)ptr)->event),
-			(const void *)image_ptr->name, name_len);
-
-	/* End of event data */
-	log_ptr = (uint8_t *)((uintptr_t)ptr +
-			offsetof(event2_data_t, event) + name_len);
-
-	return 0;
-}
-
-/*
- * Init Event Log
- *
- * Initialises Event Log by writing Specification ID and
- * Startup Locality events.
- */
-void event_log_init(void)
-{
-	const char locality_signature[] = TCG_STARTUP_LOCALITY_SIGNATURE;
-	const uint8_t *start_ptr;
-	void *ptr = event_log;
-
-	/* Get pointer to platform's measured_boot_data_t structure */
-	plat_data_ptr = plat_get_measured_boot_data();
-
-	/*
-	 * Add Specification ID Event first
-	 *
-	 * Copy TCG_EfiSpecIDEventStruct structure header
-	 */
-	(void)memcpy(ptr, (const void *)&id_event_header,
-			sizeof(id_event_header));
-	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_header));
-
-	/* TCG_EfiSpecIdEventAlgorithmSize structure */
-	((id_event_algorithm_size_t *)ptr)->algorithm_id = TPM_ALG_ID;
-	((id_event_algorithm_size_t *)ptr)->digest_size = TCG_DIGEST_SIZE;
-	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_algorithm_size_t));
-
-	/*
-	 * TCG_EfiSpecIDEventStruct.vendorInfoSize
-	 * No vendor data
-	 */
-	((id_event_struct_data_t *)ptr)->vendor_info_size = 0;
-	ptr = (uint8_t *)((uintptr_t)ptr +
-			offsetof(id_event_struct_data_t, vendor_info));
-	if ((uintptr_t)ptr != ((uintptr_t)event_log + ID_EVENT_SIZE)) {
-		panic();
-	}
-
-	start_ptr = (uint8_t *)ptr;
-
-	/*
-	 * The Startup Locality event should be placed in the log before
-	 * any event which extends PCR[0].
-	 *
-	 * Ref. TCG PC Client Platform Firmware Profile 9.4.5.3
-	 */
-
-	/* Copy Startup Locality Event Header */
-	(void)memcpy(ptr, (const void *)&locality_event_header,
-			sizeof(locality_event_header));
-	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(locality_event_header));
-
-	/* TCG_PCR_EVENT2.Digests[].AlgorithmId */
-	((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
-
-	/* TCG_PCR_EVENT2.Digests[].Digest[] */
-	(void)memset(&((tpmt_ha *)ptr)->digest, 0, TPM_ALG_ID);
-	ptr = (uint8_t *)((uintptr_t)ptr +
-			offsetof(tpmt_ha, digest) + TCG_DIGEST_SIZE);
-
-	/* TCG_PCR_EVENT2.EventSize */
-	((event2_data_t *)ptr)->event_size =
-		(uint32_t)sizeof(startup_locality_event_t);
-	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(event2_data_t, event));
-
-	/* TCG_EfiStartupLocalityEvent.Signature */
-	(void)memcpy(ptr, (const void *)locality_signature,
-		sizeof(TCG_STARTUP_LOCALITY_SIGNATURE));
-
-	/*
-	 * TCG_EfiStartupLocalityEvent.StartupLocality = 0:
-	 * the platform's boot firmware
-	 */
-	((startup_locality_event_t *)ptr)->startup_locality = 0U;
-	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(startup_locality_event_t));
-	if ((uintptr_t)ptr != ((uintptr_t)start_ptr + LOC_EVENT_SIZE)) {
-		panic();
-	}
-
-	log_ptr = (uint8_t *)ptr;
-
-	/* Add BL2 event */
-	if (add_event2(NULL, plat_data_ptr->images_data) != 0) {
-		panic();
-	}
-}
-
-/*
- * Calculate and write hash of image, configuration data, etc.
- * to Event Log.
- *
- * @param[in] data_base		Address of data
- * @param[in] data_size		Size of data
- * @param[in] data_id		Data ID
- * @return:
- *	0 = success
- *    < 0 = error
- */
-int tpm_record_measurement(uintptr_t data_base, uint32_t data_size,
-			   uint32_t data_id)
-{
-	const image_data_t *data_ptr = plat_data_ptr->images_data;
-	unsigned char hash_data[MBEDTLS_MD_MAX_SIZE];
-	int rc;
-
-	/* Check if image_id is supported */
-	while (data_ptr->id != data_id) {
-		if ((data_ptr++)->id == INVALID_ID) {
-			ERROR("%s(): image_id %u not supported\n",
-				__func__, data_id);
-			return -EINVAL;
-		}
-	}
-
-	if (data_id == TOS_FW_CONFIG_ID) {
-		tos_fw_config_base = data_base;
-	} else if (data_id == NT_FW_CONFIG_ID) {
-		nt_fw_config_base = data_base;
-	} else {
-		/* No action */
-	}
-
-	/* Calculate hash */
-	rc = crypto_mod_calc_hash((unsigned int)MBEDTLS_MD_ID,
-				(void *)data_base, data_size, hash_data);
-	if (rc != 0) {
-		return rc;
-	}
-
-	return add_event2(hash_data, data_ptr);
-}
-
-/*
- * Finalise Event Log
- *
- * @param[out] log_addr	Pointer to return Event Log address
- * @param[out] log_size	Pointer to return Event Log size
- * @return:
- *	0 = success
- *    < 0 = error code
- */
-int event_log_finalise(uint8_t **log_addr, size_t *log_size)
-{
-	/* Event Log size */
-	size_t num_bytes = (uintptr_t)log_ptr - (uintptr_t)event_log;
-	int rc;
-
-	assert(log_addr != NULL);
-	assert(log_size != NULL);
-
-	if (nt_fw_config_base == 0UL) {
-		ERROR("%s(): %s_FW_CONFIG not loaded\n", __func__, "NT");
-		return -ENOENT;
-	}
-
-	/*
-	 * Set Event Log data in NT_FW_CONFIG and
-	 * get Event Log address in Non-Secure memory
-	 */
-	if (plat_data_ptr->set_nt_fw_info != NULL) {
-
-		/* Event Log address in Non-Secure memory */
-		uintptr_t ns_log_addr;
-
-		rc = plat_data_ptr->set_nt_fw_info(
-				nt_fw_config_base,
-#ifdef SPD_opteed
-				(uintptr_t)event_log,
-#endif
-				num_bytes, &ns_log_addr);
-		if (rc != 0) {
-			ERROR("%s(): Unable to update %s_FW_CONFIG\n",
-						__func__, "NT");
-			return rc;
-		}
-
-		/* Copy Event Log to Non-secure memory */
-		(void)memcpy((void *)ns_log_addr, (const void *)event_log,
-				num_bytes);
-
-		/* Ensure that the Event Log is visible in Non-secure memory */
-		flush_dcache_range(ns_log_addr, num_bytes);
-
-		/* Return Event Log address in Non-Secure memory */
-		*log_addr = (uint8_t *)ns_log_addr;
-
-	} else {
-		INFO("%s(): set_%s_fw_info not set\n", __func__, "nt");
-
-		/* Return Event Log address in Secure memory */
-		*log_addr = event_log;
-	}
-
-	if (tos_fw_config_base != 0UL) {
-		if (plat_data_ptr->set_tos_fw_info != NULL) {
-
-			/* Set Event Log data in TOS_FW_CONFIG */
-			rc = plat_data_ptr->set_tos_fw_info(
-						tos_fw_config_base,
-						(uintptr_t)event_log,
-						num_bytes);
-			if (rc != 0) {
-				ERROR("%s(): Unable to update %s_FW_CONFIG\n",
-						__func__, "TOS");
-				return rc;
-			}
-		} else {
-			INFO("%s(): set_%s_fw_info not set\n", __func__, "tos");
-		}
-	} else {
-		INFO("%s(): %s_FW_CONFIG not loaded\n", __func__, "TOS");
-	}
-
-	/* Ensure that the Event Log is visible in Secure memory */
-	flush_dcache_range((uintptr_t)event_log, num_bytes);
-
-	/* Return Event Log size */
-	*log_size = num_bytes;
-
-	return 0;
-}
diff --git a/drivers/measured_boot/event_log/event_log.c b/drivers/measured_boot/event_log/event_log.c
new file mode 100644
index 0000000..1755dd9
--- /dev/null
+++ b/drivers/measured_boot/event_log/event_log.c
@@ -0,0 +1,284 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <string.h>
+#include <arch_helpers.h>
+
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/auth/crypto_mod.h>
+#include <drivers/measured_boot/event_log/event_log.h>
+#include <mbedtls/md.h>
+
+#include <plat/common/platform.h>
+
+/* Running Event Log Pointer */
+static uint8_t *log_ptr;
+
+/* Pointer to the first byte past end of the Event Log buffer */
+static uintptr_t log_end;
+
+/* Pointer to event_log_metadata_t */
+static const event_log_metadata_t *plat_metadata_ptr;
+
+/* TCG_EfiSpecIdEvent */
+static const id_event_headers_t id_event_header = {
+	.header = {
+		.pcr_index = PCR_0,
+		.event_type = EV_NO_ACTION,
+		.digest = {0},
+		.event_size = (uint32_t)(sizeof(id_event_struct_t) +
+				(sizeof(id_event_algorithm_size_t) *
+				HASH_ALG_COUNT))
+	},
+
+	.struct_header = {
+		.signature = TCG_ID_EVENT_SIGNATURE_03,
+		.platform_class = PLATFORM_CLASS_CLIENT,
+		.spec_version_minor = TCG_SPEC_VERSION_MINOR_TPM2,
+		.spec_version_major = TCG_SPEC_VERSION_MAJOR_TPM2,
+		.spec_errata = TCG_SPEC_ERRATA_TPM2,
+		.uintn_size = (uint8_t)(sizeof(unsigned int) /
+					sizeof(uint32_t)),
+		.number_of_algorithms = HASH_ALG_COUNT
+	}
+};
+
+static const event2_header_t locality_event_header = {
+	/*
+	 * All EV_NO_ACTION events SHALL set
+	 * TCG_PCR_EVENT2.pcrIndex = 0, unless otherwise specified
+	 */
+	.pcr_index = PCR_0,
+
+	/*
+	 * All EV_NO_ACTION events SHALL set
+	 * TCG_PCR_EVENT2.eventType = 03h
+	 */
+	.event_type = EV_NO_ACTION,
+
+	/*
+	 * All EV_NO_ACTION events SHALL set TCG_PCR_EVENT2.digests to all
+	 * 0x00's for each allocated Hash algorithm
+	 */
+	.digests = {
+		.count = HASH_ALG_COUNT
+	}
+};
+
+/*
+ * Record a measurement as a TCG_PCR_EVENT2 event
+ *
+ * @param[in] hash		Pointer to hash data of TCG_DIGEST_SIZE bytes
+ * @param[in] metadata_ptr	Pointer to event_log_metadata_t structure
+ *
+ * There must be room for storing this new event into the event log buffer.
+ */
+static void event_log_record(const uint8_t *hash,
+			     const event_log_metadata_t *metadata_ptr)
+{
+	void *ptr = log_ptr;
+	uint32_t name_len;
+
+	assert(hash != NULL);
+	assert(metadata_ptr != NULL);
+	assert(metadata_ptr->name != NULL);
+	/* event_log_init() must have been called prior to this. */
+	assert(log_ptr != NULL);
+
+	name_len = (uint32_t)strlen(metadata_ptr->name) + 1U;
+
+	/* Check for space in Event Log buffer */
+	assert(((uintptr_t)ptr + (uint32_t)EVENT2_HDR_SIZE + name_len) <
+	       log_end);
+
+	/*
+	 * As per TCG specifications, firmware components that are measured
+	 * into PCR[0] must be logged in the event log using the event type
+	 * EV_POST_CODE.
+	 */
+	/* TCG_PCR_EVENT2.PCRIndex */
+	((event2_header_t *)ptr)->pcr_index = metadata_ptr->pcr;
+
+	/* TCG_PCR_EVENT2.EventType */
+	((event2_header_t *)ptr)->event_type = EV_POST_CODE;
+
+	/* TCG_PCR_EVENT2.Digests.Count */
+	ptr = (uint8_t *)ptr + offsetof(event2_header_t, digests);
+	((tpml_digest_values *)ptr)->count = HASH_ALG_COUNT;
+
+	/* TCG_PCR_EVENT2.Digests[] */
+	ptr = (uint8_t *)((uintptr_t)ptr +
+			offsetof(tpml_digest_values, digests));
+
+	/* TCG_PCR_EVENT2.Digests[].AlgorithmId */
+	((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
+
+	/* TCG_PCR_EVENT2.Digests[].Digest[] */
+	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(tpmt_ha, digest));
+
+	/* Copy digest */
+	(void)memcpy(ptr, (const void *)hash, TCG_DIGEST_SIZE);
+
+	/* TCG_PCR_EVENT2.EventSize */
+	ptr = (uint8_t *)((uintptr_t)ptr + TCG_DIGEST_SIZE);
+	((event2_data_t *)ptr)->event_size = name_len;
+
+	/* Copy event data to TCG_PCR_EVENT2.Event */
+	(void)memcpy((void *)(((event2_data_t *)ptr)->event),
+			(const void *)metadata_ptr->name, name_len);
+
+	/* End of event data */
+	log_ptr = (uint8_t *)((uintptr_t)ptr +
+			offsetof(event2_data_t, event) + name_len);
+}
+
+/*
+ * Initialise Event Log global variables, used during the recording
+ * of various payload measurements into the Event Log buffer
+ *
+ * @param[in] event_log_start		Base address of Event Log buffer
+ * @param[in] event_log_finish		End address of Event Log buffer,
+ * 					it is a first byte past end of the
+ * 					buffer
+ */
+void event_log_init(uint8_t *event_log_start, uint8_t *event_log_finish)
+{
+	assert(event_log_start != NULL);
+	assert(event_log_finish > event_log_start);
+
+	log_ptr = event_log_start;
+	log_end = (uintptr_t)event_log_finish;
+
+	/* Get pointer to platform's event_log_metadata_t structure */
+	plat_metadata_ptr = plat_event_log_get_metadata();
+	assert(plat_metadata_ptr != NULL);
+}
+
+/*
+ * Initialises Event Log by writing Specification ID and
+ * Startup Locality events
+ */
+void event_log_write_header(void)
+{
+	const char locality_signature[] = TCG_STARTUP_LOCALITY_SIGNATURE;
+	void *ptr = log_ptr;
+
+	/* event_log_init() must have been called prior to this. */
+	assert(log_ptr != NULL);
+
+	/*
+	 * Add Specification ID Event first
+	 *
+	 * Copy TCG_EfiSpecIDEventStruct structure header
+	 */
+	(void)memcpy(ptr, (const void *)&id_event_header,
+			sizeof(id_event_header));
+	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_header));
+
+	/* TCG_EfiSpecIdEventAlgorithmSize structure */
+	((id_event_algorithm_size_t *)ptr)->algorithm_id = TPM_ALG_ID;
+	((id_event_algorithm_size_t *)ptr)->digest_size = TCG_DIGEST_SIZE;
+	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(id_event_algorithm_size_t));
+
+	/*
+	 * TCG_EfiSpecIDEventStruct.vendorInfoSize
+	 * No vendor data
+	 */
+	((id_event_struct_data_t *)ptr)->vendor_info_size = 0;
+	ptr = (uint8_t *)((uintptr_t)ptr +
+			offsetof(id_event_struct_data_t, vendor_info));
+
+	/*
+	 * The Startup Locality event should be placed in the log before
+	 * any event which extends PCR[0].
+	 *
+	 * Ref. TCG PC Client Platform Firmware Profile 9.4.5.3
+	 */
+
+	/* Copy Startup Locality Event Header */
+	(void)memcpy(ptr, (const void *)&locality_event_header,
+			sizeof(locality_event_header));
+	ptr = (uint8_t *)((uintptr_t)ptr + sizeof(locality_event_header));
+
+	/* TCG_PCR_EVENT2.Digests[].AlgorithmId */
+	((tpmt_ha *)ptr)->algorithm_id = TPM_ALG_ID;
+
+	/* TCG_PCR_EVENT2.Digests[].Digest[] */
+	(void)memset(&((tpmt_ha *)ptr)->digest, 0, TPM_ALG_ID);
+	ptr = (uint8_t *)((uintptr_t)ptr +
+			offsetof(tpmt_ha, digest) + TCG_DIGEST_SIZE);
+
+	/* TCG_PCR_EVENT2.EventSize */
+	((event2_data_t *)ptr)->event_size =
+		(uint32_t)sizeof(startup_locality_event_t);
+	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(event2_data_t, event));
+
+	/* TCG_EfiStartupLocalityEvent.Signature */
+	(void)memcpy(ptr, (const void *)locality_signature,
+		sizeof(TCG_STARTUP_LOCALITY_SIGNATURE));
+
+	/*
+	 * TCG_EfiStartupLocalityEvent.StartupLocality = 0:
+	 * the platform's boot firmware
+	 */
+	((startup_locality_event_t *)ptr)->startup_locality = 0U;
+	log_ptr = (uint8_t *)((uintptr_t)ptr + sizeof(startup_locality_event_t));
+}
+
+/*
+ * Calculate and write hash of image, configuration data, etc.
+ * to Event Log.
+ *
+ * @param[in] data_base		Address of data
+ * @param[in] data_size		Size of data
+ * @param[in] data_id		Data ID
+ * @return:
+ *	0 = success
+ *    < 0 = error
+ */
+int event_log_measure_and_record(uintptr_t data_base, uint32_t data_size,
+				 uint32_t data_id)
+{
+	unsigned char hash_data[MBEDTLS_MD_MAX_SIZE];
+	int rc;
+	const event_log_metadata_t *metadata_ptr = plat_metadata_ptr;
+
+	/* Get the metadata associated with this image. */
+	while ((metadata_ptr->id != INVALID_ID) &&
+		(metadata_ptr->id != data_id)) {
+		metadata_ptr++;
+	}
+	assert(metadata_ptr->id != INVALID_ID);
+
+	/* Calculate hash */
+	rc = crypto_mod_calc_hash((unsigned int)MBEDTLS_MD_ID,
+				(void *)data_base, data_size, hash_data);
+	if (rc != 0) {
+		return rc;
+	}
+
+	event_log_record(hash_data, metadata_ptr);
+
+	return 0;
+}
+
+/*
+ * Get current Event Log buffer size i.e. used space of Event Log buffer
+ *
+ * @param[in]  event_log_start		Base Pointer to Event Log buffer
+ *
+ * @return: current Size of Event Log buffer
+ */
+size_t event_log_get_cur_size(uint8_t *event_log_start)
+{
+	assert(event_log_start != NULL);
+	assert(log_ptr >= event_log_start);
+
+	return (size_t)((uintptr_t)log_ptr - (uintptr_t)event_log_start);
+}
diff --git a/drivers/measured_boot/event_log/event_log.mk b/drivers/measured_boot/event_log/event_log.mk
new file mode 100644
index 0000000..37e5e29
--- /dev/null
+++ b/drivers/measured_boot/event_log/event_log.mk
@@ -0,0 +1,50 @@
+#
+# Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Default log level to dump the event log (LOG_LEVEL_INFO)
+EVENT_LOG_LEVEL         ?= 40
+
+# TPM hash algorithm.
+# SHA-256 (or stronger) is required for all devices that are TPM 2.0 compliant.
+TPM_HASH_ALG			:=	sha256
+
+ifeq (${TPM_HASH_ALG}, sha512)
+    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA512
+    TPM_ALG_ID			:=	TPM_ALG_SHA512
+    TCG_DIGEST_SIZE		:=	64U
+else ifeq (${TPM_HASH_ALG}, sha384)
+    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA384
+    TPM_ALG_ID			:=	TPM_ALG_SHA384
+    TCG_DIGEST_SIZE		:=	48U
+else
+    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA256
+    TPM_ALG_ID			:=	TPM_ALG_SHA256
+    TCG_DIGEST_SIZE		:=	32U
+endif
+
+
+# Set definitions for mbed TLS library and Measured Boot driver
+$(eval $(call add_defines,\
+    $(sort \
+        MBEDTLS_MD_ID \
+        TPM_ALG_ID \
+        TCG_DIGEST_SIZE \
+        EVENT_LOG_LEVEL \
+)))
+
+ifeq (${HASH_ALG}, sha256)
+    ifneq (${TPM_HASH_ALG}, sha256)
+        $(eval $(call add_define,MBEDTLS_SHA512_C))
+    endif
+endif
+
+MEASURED_BOOT_SRC_DIR	:= drivers/measured_boot/event_log/
+
+MEASURED_BOOT_SOURCES	:= ${MEASURED_BOOT_SRC_DIR}event_log.c		\
+			   ${MEASURED_BOOT_SRC_DIR}event_print.c
+
+BL2_SOURCES		+= ${MEASURED_BOOT_SOURCES}
+BL1_SOURCES             += ${MEASURED_BOOT_SOURCES}
diff --git a/drivers/measured_boot/event_log/event_print.c b/drivers/measured_boot/event_log/event_print.c
new file mode 100644
index 0000000..e2ba174
--- /dev/null
+++ b/drivers/measured_boot/event_log/event_print.c
@@ -0,0 +1,265 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/measured_boot/event_log/event_log.h>
+
+#if LOG_LEVEL >= EVENT_LOG_LEVEL
+
+/*
+ * Print TCG_EfiSpecIDEventStruct
+ *
+ * @param[in/out] log_addr	Pointer to Event Log
+ * @param[in/out] log_size	Pointer to Event Log size
+ */
+static void id_event_print(uint8_t **log_addr, size_t *log_size)
+{
+	unsigned int i;
+	uint8_t info_size, *info_size_ptr;
+	void *ptr = *log_addr;
+	id_event_headers_t *event = (id_event_headers_t *)ptr;
+	id_event_algorithm_size_t *alg_ptr;
+	uint32_t event_size, number_of_algorithms;
+	size_t digest_len;
+#if ENABLE_ASSERTIONS
+	const uint8_t *end_ptr = (uint8_t *)((uintptr_t)*log_addr + *log_size);
+	bool valid = true;
+#endif
+
+	assert(*log_size >= sizeof(id_event_headers_t));
+
+	/* The fields of the event log header are defined to be PCRIndex of 0,
+	 * EventType of EV_NO_ACTION, Digest of 20 bytes of 0, and
+	 * Event content defined as TCG_EfiSpecIDEventStruct.
+	 */
+	LOG_EVENT("TCG_EfiSpecIDEvent:\n");
+	LOG_EVENT("  PCRIndex           : %u\n", event->header.pcr_index);
+	assert(event->header.pcr_index == (uint32_t)PCR_0);
+
+	LOG_EVENT("  EventType          : %u\n", event->header.event_type);
+	assert(event->header.event_type == EV_NO_ACTION);
+
+	LOG_EVENT("  Digest             :");
+	for (i = 0U; i < sizeof(event->header.digest); ++i) {
+		uint8_t val = event->header.digest[i];
+
+		(void)printf(" %02x", val);
+		if ((i & U(0xF)) == 0U) {
+			(void)printf("\n");
+			LOG_EVENT("\t\t      :");
+		}
+#if ENABLE_ASSERTIONS
+		if (val != 0U) {
+			valid = false;
+		}
+#endif
+	}
+	if ((i & U(0xF)) != 0U) {
+		(void)printf("\n");
+	}
+
+	assert(valid);
+
+	/* EventSize */
+	event_size = event->header.event_size;
+	LOG_EVENT("  EventSize          : %u\n", event_size);
+
+	LOG_EVENT("  Signature          : %s\n",
+			event->struct_header.signature);
+	LOG_EVENT("  PlatformClass      : %u\n",
+			event->struct_header.platform_class);
+	LOG_EVENT("  SpecVersion        : %u.%u.%u\n",
+			event->struct_header.spec_version_major,
+			event->struct_header.spec_version_minor,
+			event->struct_header.spec_errata);
+	LOG_EVENT("  UintnSize          : %u\n",
+			event->struct_header.uintn_size);
+
+	/* NumberOfAlgorithms */
+	number_of_algorithms = event->struct_header.number_of_algorithms;
+	LOG_EVENT("  NumberOfAlgorithms : %u\n", number_of_algorithms);
+
+	/* Address of DigestSizes[] */
+	alg_ptr = event->struct_header.digest_size;
+
+	/* Size of DigestSizes[] */
+	digest_len = number_of_algorithms * sizeof(id_event_algorithm_size_t);
+	assert(((uintptr_t)alg_ptr + digest_len) <= (uintptr_t)end_ptr);
+
+	LOG_EVENT("  DigestSizes        :\n");
+	for (i = 0U; i < number_of_algorithms; ++i) {
+		LOG_EVENT("    #%u AlgorithmId   : SHA", i);
+		uint16_t algorithm_id = alg_ptr[i].algorithm_id;
+
+		switch (algorithm_id) {
+		case TPM_ALG_SHA256:
+			(void)printf("256\n");
+			break;
+		case TPM_ALG_SHA384:
+			(void)printf("384\n");
+			break;
+		case TPM_ALG_SHA512:
+			(void)printf("512\n");
+			break;
+		default:
+			(void)printf("?\n");
+			ERROR("Algorithm 0x%x not found\n", algorithm_id);
+			assert(false);
+		}
+
+		LOG_EVENT("       DigestSize    : %u\n",
+					alg_ptr[i].digest_size);
+	}
+
+	/* Address of VendorInfoSize */
+	info_size_ptr = (uint8_t *)((uintptr_t)alg_ptr + digest_len);
+	assert((uintptr_t)info_size_ptr <= (uintptr_t)end_ptr);
+
+	info_size = *info_size_ptr++;
+	LOG_EVENT("  VendorInfoSize     : %u\n", info_size);
+
+	/* Check VendorInfo end address */
+	assert(((uintptr_t)info_size_ptr + info_size) <= (uintptr_t)end_ptr);
+
+	/* Check EventSize */
+	assert(event_size == (sizeof(id_event_struct_t) +
+				digest_len + info_size));
+	if (info_size != 0U) {
+		LOG_EVENT("  VendorInfo         :");
+		for (i = 0U; i < info_size; ++i) {
+			(void)printf(" %02x", *info_size_ptr++);
+		}
+		(void)printf("\n");
+	}
+
+	*log_size -= (uintptr_t)info_size_ptr - (uintptr_t)*log_addr;
+	*log_addr = info_size_ptr;
+}
+
+/*
+ * Print TCG_PCR_EVENT2
+ *
+ * @param[in/out] log_addr	Pointer to Event Log
+ * @param[in/out] log_size	Pointer to Event Log size
+ */
+static void event2_print(uint8_t **log_addr, size_t *log_size)
+{
+	uint32_t event_size, count;
+	size_t sha_size, digests_size = 0U;
+	void *ptr = *log_addr;
+#if ENABLE_ASSERTIONS
+	const uint8_t *end_ptr = (uint8_t *)((uintptr_t)*log_addr + *log_size);
+#endif
+
+	assert(*log_size >= sizeof(event2_header_t));
+
+	LOG_EVENT("PCR_Event2:\n");
+	LOG_EVENT("  PCRIndex           : %u\n",
+			((event2_header_t *)ptr)->pcr_index);
+	LOG_EVENT("  EventType          : %u\n",
+			((event2_header_t *)ptr)->event_type);
+
+	count = ((event2_header_t *)ptr)->digests.count;
+	LOG_EVENT("  Digests Count      : %u\n", count);
+
+	/* Address of TCG_PCR_EVENT2.Digests[] */
+	ptr = (uint8_t *)ptr + sizeof(event2_header_t);
+	assert(((uintptr_t)ptr <= (uintptr_t)end_ptr) && (count != 0U));
+
+	for (unsigned int i = 0U; i < count; ++i) {
+		/* Check AlgorithmId address */
+		assert(((uintptr_t)ptr +
+			offsetof(tpmt_ha, digest)) <= (uintptr_t)end_ptr);
+
+		LOG_EVENT("    #%u AlgorithmId   : SHA", i);
+		switch (((tpmt_ha *)ptr)->algorithm_id) {
+		case TPM_ALG_SHA256:
+			sha_size = SHA256_DIGEST_SIZE;
+			(void)printf("256\n");
+			break;
+		case TPM_ALG_SHA384:
+			sha_size = SHA384_DIGEST_SIZE;
+			(void)printf("384\n");
+			break;
+		case TPM_ALG_SHA512:
+			sha_size = SHA512_DIGEST_SIZE;
+			(void)printf("512\n");
+			break;
+		default:
+			(void)printf("?\n");
+			ERROR("Algorithm 0x%x not found\n",
+				((tpmt_ha *)ptr)->algorithm_id);
+			panic();
+		}
+
+		/* End of Digest[] */
+		ptr = (uint8_t *)((uintptr_t)ptr + offsetof(tpmt_ha, digest));
+		assert(((uintptr_t)ptr + sha_size) <= (uintptr_t)end_ptr);
+
+		/* Total size of all digests */
+		digests_size += sha_size;
+
+		LOG_EVENT("       Digest        :");
+		for (unsigned int j = 0U; j < sha_size; ++j) {
+			(void)printf(" %02x", *(uint8_t *)ptr++);
+			if ((j & U(0xF)) == U(0xF)) {
+				(void)printf("\n");
+				if (j < (sha_size - 1U)) {
+					LOG_EVENT("\t\t      :");
+				}
+			}
+		}
+	}
+
+	/* TCG_PCR_EVENT2.EventSize */
+	assert(((uintptr_t)ptr + offsetof(event2_data_t, event)) <= (uintptr_t)end_ptr);
+
+	event_size = ((event2_data_t *)ptr)->event_size;
+	LOG_EVENT("  EventSize          : %u\n", event_size);
+
+	/* Address of TCG_PCR_EVENT2.Event[EventSize] */
+	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(event2_data_t, event));
+
+	/* End of TCG_PCR_EVENT2.Event[EventSize] */
+	assert(((uintptr_t)ptr + event_size) <= (uintptr_t)end_ptr);
+
+	if ((event_size == sizeof(startup_locality_event_t)) &&
+	     (strcmp((const char *)ptr, TCG_STARTUP_LOCALITY_SIGNATURE) == 0)) {
+		LOG_EVENT("  Signature          : %s\n",
+			((startup_locality_event_t *)ptr)->signature);
+		LOG_EVENT("  StartupLocality    : %u\n",
+			((startup_locality_event_t *)ptr)->startup_locality);
+	} else {
+		LOG_EVENT("  Event              : %s\n", (uint8_t *)ptr);
+	}
+
+	*log_size -= (uintptr_t)ptr + event_size - (uintptr_t)*log_addr;
+	*log_addr = (uint8_t *)ptr + event_size;
+}
+#endif	/* LOG_LEVEL >= EVENT_LOG_LEVEL */
+
+/*
+ * Print Event Log
+ *
+ * @param[in]	log_addr	Pointer to Event Log
+ * @param[in]	log_size	Event Log size
+ */
+void dump_event_log(uint8_t *log_addr, size_t log_size)
+{
+#if LOG_LEVEL >= EVENT_LOG_LEVEL
+	assert(log_addr != NULL);
+
+	/* Print TCG_EfiSpecIDEvent */
+	id_event_print(&log_addr, &log_size);
+
+	while (log_size != 0U) {
+		event2_print(&log_addr, &log_size);
+	}
+#endif
+}
diff --git a/drivers/measured_boot/event_print.c b/drivers/measured_boot/event_print.c
deleted file mode 100644
index 84ed4b1..0000000
--- a/drivers/measured_boot/event_print.c
+++ /dev/null
@@ -1,265 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-#include <string.h>
-
-#include <common/debug.h>
-#include <drivers/measured_boot/event_log.h>
-
-#if LOG_LEVEL >= EVENT_LOG_LEVEL
-
-/*
- * Print TCG_EfiSpecIDEventStruct
- *
- * @param[in/out] log_addr	Pointer to Event Log
- * @param[in/out] log_size	Pointer to Event Log size
- */
-static void id_event_print(uint8_t **log_addr, size_t *log_size)
-{
-	unsigned int i;
-	uint8_t info_size, *info_size_ptr;
-	void *ptr = *log_addr;
-	id_event_headers_t *event = (id_event_headers_t *)ptr;
-	id_event_algorithm_size_t *alg_ptr;
-	uint32_t event_size, number_of_algorithms;
-	size_t digest_len;
-#if ENABLE_ASSERTIONS
-	const uint8_t *end_ptr = (uint8_t *)((uintptr_t)*log_addr + *log_size);
-	bool valid = true;
-#endif
-
-	assert(*log_size >= sizeof(id_event_headers_t));
-
-	/* The fields of the event log header are defined to be PCRIndex of 0,
-	 * EventType of EV_NO_ACTION, Digest of 20 bytes of 0, and
-	 * Event content defined as TCG_EfiSpecIDEventStruct.
-	 */
-	LOG_EVENT("TCG_EfiSpecIDEvent:\n");
-	LOG_EVENT("  PCRIndex           : %u\n", event->header.pcr_index);
-	assert(event->header.pcr_index == (uint32_t)PCR_0);
-
-	LOG_EVENT("  EventType          : %u\n", event->header.event_type);
-	assert(event->header.event_type == EV_NO_ACTION);
-
-	LOG_EVENT("  Digest             :");
-	for (i = 0U; i < sizeof(event->header.digest); ++i) {
-		uint8_t val = event->header.digest[i];
-
-		(void)printf(" %02x", val);
-		if ((i & U(0xF)) == 0U) {
-			(void)printf("\n");
-			LOG_EVENT("\t\t      :");
-		}
-#if ENABLE_ASSERTIONS
-		if (val != 0U) {
-			valid = false;
-		}
-#endif
-	}
-	if ((i & U(0xF)) != 0U) {
-		(void)printf("\n");
-	}
-
-	assert(valid);
-
-	/* EventSize */
-	event_size = event->header.event_size;
-	LOG_EVENT("  EventSize          : %u\n", event_size);
-
-	LOG_EVENT("  Signature          : %s\n",
-			event->struct_header.signature);
-	LOG_EVENT("  PlatformClass      : %u\n",
-			event->struct_header.platform_class);
-	LOG_EVENT("  SpecVersion        : %u.%u.%u\n",
-			event->struct_header.spec_version_major,
-			event->struct_header.spec_version_minor,
-			event->struct_header.spec_errata);
-	LOG_EVENT("  UintnSize          : %u\n",
-			event->struct_header.uintn_size);
-
-	/* NumberOfAlgorithms */
-	number_of_algorithms = event->struct_header.number_of_algorithms;
-	LOG_EVENT("  NumberOfAlgorithms : %u\n", number_of_algorithms);
-
-	/* Address of DigestSizes[] */
-	alg_ptr = event->struct_header.digest_size;
-
-	/* Size of DigestSizes[] */
-	digest_len = number_of_algorithms * sizeof(id_event_algorithm_size_t);
-	assert(((uintptr_t)alg_ptr + digest_len) <= (uintptr_t)end_ptr);
-
-	LOG_EVENT("  DigestSizes        :\n");
-	for (i = 0U; i < number_of_algorithms; ++i) {
-		LOG_EVENT("    #%u AlgorithmId   : SHA", i);
-		uint16_t algorithm_id = alg_ptr[i].algorithm_id;
-
-		switch (algorithm_id) {
-		case TPM_ALG_SHA256:
-			(void)printf("256\n");
-			break;
-		case TPM_ALG_SHA384:
-			(void)printf("384\n");
-			break;
-		case TPM_ALG_SHA512:
-			(void)printf("512\n");
-			break;
-		default:
-			(void)printf("?\n");
-			ERROR("Algorithm 0x%x not found\n", algorithm_id);
-			assert(false);
-		}
-
-		LOG_EVENT("       DigestSize    : %u\n",
-					alg_ptr[i].digest_size);
-	}
-
-	/* Address of VendorInfoSize */
-	info_size_ptr = (uint8_t *)((uintptr_t)alg_ptr + digest_len);
-	assert((uintptr_t)info_size_ptr <= (uintptr_t)end_ptr);
-
-	info_size = *info_size_ptr++;
-	LOG_EVENT("  VendorInfoSize     : %u\n", info_size);
-
-	/* Check VendorInfo end address */
-	assert(((uintptr_t)info_size_ptr + info_size) <= (uintptr_t)end_ptr);
-
-	/* Check EventSize */
-	assert(event_size == (sizeof(id_event_struct_t) +
-				digest_len + info_size));
-	if (info_size != 0U) {
-		LOG_EVENT("  VendorInfo         :");
-		for (i = 0U; i < info_size; ++i) {
-			(void)printf(" %02x", *info_size_ptr++);
-		}
-		(void)printf("\n");
-	}
-
-	*log_size -= (uintptr_t)info_size_ptr - (uintptr_t)*log_addr;
-	*log_addr = info_size_ptr;
-}
-
-/*
- * Print TCG_PCR_EVENT2
- *
- * @param[in/out] log_addr	Pointer to Event Log
- * @param[in/out] log_size	Pointer to Event Log size
- */
-static void event2_print(uint8_t **log_addr, size_t *log_size)
-{
-	uint32_t event_size, count;
-	size_t sha_size, digests_size = 0U;
-	void *ptr = *log_addr;
-#if ENABLE_ASSERTIONS
-	const uint8_t *end_ptr = (uint8_t *)((uintptr_t)*log_addr + *log_size);
-#endif
-
-	assert(*log_size >= sizeof(event2_header_t));
-
-	LOG_EVENT("PCR_Event2:\n");
-	LOG_EVENT("  PCRIndex           : %u\n",
-			((event2_header_t *)ptr)->pcr_index);
-	LOG_EVENT("  EventType          : %u\n",
-			((event2_header_t *)ptr)->event_type);
-
-	count = ((event2_header_t *)ptr)->digests.count;
-	LOG_EVENT("  Digests Count      : %u\n", count);
-
-	/* Address of TCG_PCR_EVENT2.Digests[] */
-	ptr = (uint8_t *)ptr + sizeof(event2_header_t);
-	assert(((uintptr_t)ptr <= (uintptr_t)end_ptr) && (count != 0U));
-
-	for (unsigned int i = 0U; i < count; ++i) {
-		/* Check AlgorithmId address */
-		assert(((uintptr_t)ptr +
-			offsetof(tpmt_ha, digest)) <= (uintptr_t)end_ptr);
-
-		LOG_EVENT("    #%u AlgorithmId   : SHA", i);
-		switch (((tpmt_ha *)ptr)->algorithm_id) {
-		case TPM_ALG_SHA256:
-			sha_size = SHA256_DIGEST_SIZE;
-			(void)printf("256\n");
-			break;
-		case TPM_ALG_SHA384:
-			sha_size = SHA384_DIGEST_SIZE;
-			(void)printf("384\n");
-			break;
-		case TPM_ALG_SHA512:
-			sha_size = SHA512_DIGEST_SIZE;
-			(void)printf("512\n");
-			break;
-		default:
-			(void)printf("?\n");
-			ERROR("Algorithm 0x%x not found\n",
-				((tpmt_ha *)ptr)->algorithm_id);
-			panic();
-		}
-
-		/* End of Digest[] */
-		ptr = (uint8_t *)((uintptr_t)ptr + offsetof(tpmt_ha, digest));
-		assert(((uintptr_t)ptr + sha_size) <= (uintptr_t)end_ptr);
-
-		/* Total size of all digests */
-		digests_size += sha_size;
-
-		LOG_EVENT("       Digest        :");
-		for (unsigned int j = 0U; j < sha_size; ++j) {
-			(void)printf(" %02x", *(uint8_t *)ptr++);
-			if ((j & U(0xF)) == U(0xF)) {
-				(void)printf("\n");
-				if (j < (sha_size - 1U)) {
-					LOG_EVENT("\t\t      :");
-				}
-			}
-		}
-	}
-
-	/* TCG_PCR_EVENT2.EventSize */
-	assert(((uintptr_t)ptr + offsetof(event2_data_t, event)) <= (uintptr_t)end_ptr);
-
-	event_size = ((event2_data_t *)ptr)->event_size;
-	LOG_EVENT("  EventSize          : %u\n", event_size);
-
-	/* Address of TCG_PCR_EVENT2.Event[EventSize] */
-	ptr = (uint8_t *)((uintptr_t)ptr + offsetof(event2_data_t, event));
-
-	/* End of TCG_PCR_EVENT2.Event[EventSize] */
-	assert(((uintptr_t)ptr + event_size) <= (uintptr_t)end_ptr);
-
-	if ((event_size == sizeof(startup_locality_event_t)) &&
-	     (strcmp((const char *)ptr, TCG_STARTUP_LOCALITY_SIGNATURE) == 0)) {
-		LOG_EVENT("  Signature          : %s\n",
-			((startup_locality_event_t *)ptr)->signature);
-		LOG_EVENT("  StartupLocality    : %u\n",
-			((startup_locality_event_t *)ptr)->startup_locality);
-	} else {
-		LOG_EVENT("  Event              : %s\n", (uint8_t *)ptr);
-	}
-
-	*log_size -= (uintptr_t)ptr + event_size - (uintptr_t)*log_addr;
-	*log_addr = (uint8_t *)ptr + event_size;
-}
-#endif	/* LOG_LEVEL >= EVENT_LOG_LEVEL */
-
-/*
- * Print Event Log
- *
- * @param[in]	log_addr	Pointer to Event Log
- * @param[in]	log_size	Event Log size
- */
-void dump_event_log(uint8_t *log_addr, size_t log_size)
-{
-#if LOG_LEVEL >= EVENT_LOG_LEVEL
-	assert(log_addr != NULL);
-
-	/* Print TCG_EfiSpecIDEvent */
-	id_event_print(&log_addr, &log_size);
-
-	while (log_size != 0U) {
-		event2_print(&log_addr, &log_size);
-	}
-#endif
-}
diff --git a/drivers/measured_boot/measured_boot.c b/drivers/measured_boot/measured_boot.c
deleted file mode 100644
index 37fddfb..0000000
--- a/drivers/measured_boot/measured_boot.c
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <common/debug.h>
-#include <drivers/measured_boot/measured_boot.h>
-
-/*
- * Init Measured Boot driver
- *
- * Initialises Event Log.
- */
-void measured_boot_init(void)
-{
-	event_log_init();
-}
-
-/*
- * Finish Measured Boot driver
- *
- * Finalises Event Log and dumps the records to the debug console.
- */
-void measured_boot_finish(void)
-{
-	uint8_t *log_addr;
-	size_t log_size;
-	int rc;
-
-	rc = event_log_finalise(&log_addr, &log_size);
-	if (rc != 0) {
-		panic();
-	}
-
-	dump_event_log(log_addr, log_size);
-}
diff --git a/drivers/measured_boot/measured_boot.mk b/drivers/measured_boot/measured_boot.mk
deleted file mode 100644
index 497fdba..0000000
--- a/drivers/measured_boot/measured_boot.mk
+++ /dev/null
@@ -1,52 +0,0 @@
-#
-# Copyright (c) 2020, Arm Limited. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-# Default log level to dump the event log (LOG_LEVEL_INFO)
-EVENT_LOG_LEVEL         ?= 40
-
-# TPM hash algorithm
-TPM_HASH_ALG			:=	sha256
-
-ifeq (${TPM_HASH_ALG}, sha512)
-    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA512
-    TPM_ALG_ID			:=	TPM_ALG_SHA512
-    TCG_DIGEST_SIZE		:=	64U
-else ifeq (${TPM_HASH_ALG}, sha384)
-    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA384
-    TPM_ALG_ID			:=	TPM_ALG_SHA384
-    TCG_DIGEST_SIZE		:=	48U
-else
-    MBEDTLS_MD_ID		:=	MBEDTLS_MD_SHA256
-    TPM_ALG_ID			:=	TPM_ALG_SHA256
-    TCG_DIGEST_SIZE		:=	32U
-endif
-
-# Event Log length in bytes
-EVENT_LOG_SIZE			:= 1024
-
-# Set definitions for mbed TLS library and Measured Boot driver
-$(eval $(call add_defines,\
-    $(sort \
-        MBEDTLS_MD_ID \
-        TPM_ALG_ID \
-        TCG_DIGEST_SIZE \
-        EVENT_LOG_SIZE \
-        EVENT_LOG_LEVEL \
-)))
-
-ifeq (${HASH_ALG}, sha256)
-ifneq (${TPM_HASH_ALG}, sha256)
-$(eval $(call add_define,MBEDTLS_SHA512_C))
-endif
-endif
-
-MEASURED_BOOT_SRC_DIR	:= drivers/measured_boot/
-
-MEASURED_BOOT_SOURCES	:= ${MEASURED_BOOT_SRC_DIR}measured_boot.c	\
-    			   ${MEASURED_BOOT_SRC_DIR}event_log.c		\
-    			   ${MEASURED_BOOT_SRC_DIR}event_print.c
-
-BL2_SOURCES		+= ${MEASURED_BOOT_SOURCES}
diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c
index b5f6a10..c327e71 100644
--- a/drivers/mmc/mmc.c
+++ b/drivers/mmc/mmc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -105,6 +105,36 @@
 	return MMC_GET_STATE(resp_data[0]);
 }
 
+static int mmc_send_part_switch_cmd(unsigned int part_config)
+{
+	int ret;
+	unsigned int part_time = 0;
+
+	ret = mmc_send_cmd(MMC_CMD(6),
+			   EXTCSD_WRITE_BYTES |
+			   EXTCSD_CMD(CMD_EXTCSD_PARTITION_CONFIG) |
+			   EXTCSD_VALUE(part_config) |
+			   EXTCSD_CMD_SET_NORMAL,
+			   MMC_RESPONSE_R1B, NULL);
+	if (ret != 0) {
+		return ret;
+	}
+
+	/* Partition switch timing is in 10ms units */
+	part_time = mmc_ext_csd[CMD_EXTCSD_PART_SWITCH_TIME] * 10;
+
+	mdelay(part_time);
+
+	do {
+		ret = mmc_device_state();
+		if (ret < 0) {
+			return ret;
+		}
+	} while (ret == MMC_STATE_PRG);
+
+	return 0;
+}
+
 static int mmc_set_ext_csd(unsigned int ext_cmd, unsigned int value)
 {
 	int ret;
@@ -392,7 +422,7 @@
 	ret = mmc_reset_to_idle();
 	if (ret != 0) {
 		return ret;
-	};
+	}
 
 	for (n = 0; n < SEND_OP_COND_MAX_RETRIES; n++) {
 		ret = mmc_send_cmd(MMC_CMD(1), OCR_SECTOR_MODE |
@@ -425,7 +455,7 @@
 	ret = mmc_reset_to_idle();
 	if (ret != 0) {
 		return ret;
-	};
+	}
 
 	if (mmc_dev_info->mmc_dev_type == MMC_IS_EMMC) {
 		ret = mmc_send_op_cond();
@@ -668,7 +698,7 @@
 {
 	mmc_set_ext_csd(CMD_EXTCSD_PARTITION_CONFIG,
 			PART_CFG_BOOT_PARTITION1_ENABLE |
-			PART_CFG_PARTITION1_ACCESS);
+			PART_CFG_BOOT_PARTITION1_ACCESS);
 }
 
 static inline void mmc_rpmb_disable(void)
@@ -710,6 +740,50 @@
 	return size_erased;
 }
 
+static int mmc_part_switch(unsigned int part_type)
+{
+	uint8_t part_config = mmc_ext_csd[CMD_EXTCSD_PARTITION_CONFIG];
+
+	part_config &= ~EXT_CSD_PART_CONFIG_ACC_MASK;
+	part_config |= part_type;
+
+	return mmc_send_part_switch_cmd(part_config);
+}
+
+static unsigned char mmc_current_boot_part(void)
+{
+	return PART_CFG_CURRENT_BOOT_PARTITION(mmc_ext_csd[CMD_EXTCSD_PARTITION_CONFIG]);
+}
+
+size_t mmc_boot_part_read_blocks(int lba, uintptr_t buf, size_t size)
+{
+	size_t size_read;
+	int ret;
+	unsigned char current_boot_part = mmc_current_boot_part();
+
+	if (current_boot_part != 1U &&
+	    current_boot_part != 2U) {
+		ERROR("Got unexpected value for active boot partition, %u\n", current_boot_part);
+		return 0;
+	}
+
+	ret = mmc_part_switch(current_boot_part);
+	if (ret < 0) {
+		ERROR("Failed to switch to boot partition, %d\n", ret);
+		return 0;
+	}
+
+	size_read = mmc_read_blocks(lba, buf, size);
+
+	ret = mmc_part_switch(0);
+	if (ret < 0) {
+		ERROR("Failed to switch back to user partition, %d\n", ret);
+		return 0;
+	}
+
+	return size_read;
+}
+
 int mmc_init(const struct mmc_ops *ops_ptr, unsigned int clk,
 	     unsigned int width, unsigned int flags,
 	     struct mmc_device_info *device_info)
diff --git a/drivers/mtd/nand/core.c b/drivers/mtd/nand/core.c
index 44b001e..9f0331a 100644
--- a/drivers/mtd/nand/core.c
+++ b/drivers/mtd/nand/core.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -112,6 +112,47 @@
 	return 0;
 }
 
+int nand_seek_bb(uintptr_t base, unsigned int offset, size_t *extra_offset)
+{
+	unsigned int block;
+	unsigned int offset_block;
+	unsigned int max_block;
+	int is_bad;
+	size_t count_bb = 0U;
+
+	block = base / nand_dev.block_size;
+
+	if (offset != 0U) {
+		offset_block = (base + offset - 1U) / nand_dev.block_size;
+	} else {
+		offset_block = block;
+	}
+
+	max_block = nand_dev.size / nand_dev.block_size;
+
+	while (block <= offset_block) {
+		if (offset_block >= max_block) {
+			return -EIO;
+		}
+
+		is_bad = nand_dev.mtd_block_is_bad(block);
+		if (is_bad < 0) {
+			return is_bad;
+		}
+
+		if (is_bad == 1) {
+			count_bb++;
+			offset_block++;
+		}
+
+		block++;
+	}
+
+	*extra_offset = count_bb * nand_dev.block_size;
+
+	return 0;
+}
+
 struct nand_device *get_nand_device(void)
 {
 	return &nand_dev;
diff --git a/drivers/mtd/nand/spi_nand.c b/drivers/mtd/nand/spi_nand.c
index d01a119..abb524d 100644
--- a/drivers/mtd/nand/spi_nand.c
+++ b/drivers/mtd/nand/spi_nand.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019,  STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021,  STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -286,6 +286,10 @@
 		return -EINVAL;
 	}
 
+	assert((spinand_dev.nand_dev->page_size != 0U) &&
+	       (spinand_dev.nand_dev->block_size != 0U) &&
+	       (spinand_dev.nand_dev->size != 0U));
+
 	ret = spi_nand_reset();
 	if (ret != 0) {
 		return ret;
@@ -301,12 +305,12 @@
 		return ret;
 	}
 
-	ret = spi_nand_quad_enable(id[0]);
+	ret = spi_nand_quad_enable(id[1]);
 	if (ret != 0) {
 		return ret;
 	}
 
-	VERBOSE("SPI_NAND Detected ID 0x%x 0x%x\n", id[0], id[1]);
+	VERBOSE("SPI_NAND Detected ID 0x%x\n", id[1]);
 
 	VERBOSE("Page size %i, Block size %i, size %lli\n",
 		spinand_dev.nand_dev->page_size,
diff --git a/drivers/mtd/nor/spi_nor.c b/drivers/mtd/nor/spi_nor.c
index 108f893..6b4643e 100644
--- a/drivers/mtd/nor/spi_nor.c
+++ b/drivers/mtd/nor/spi_nor.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -103,7 +103,7 @@
 			0 : 1;
 	}
 
-	return (((sr & SR_WIP) != 0U) ? 1 : 0);
+	return (((sr & SR_WIP) == 0U) ? 0 : 1);
 }
 
 static int spi_nor_wait_ready(void)
@@ -131,7 +131,7 @@
 		return ret;
 	}
 
-	if ((sr & SR_QUAD_EN_MX) == 0U) {
+	if ((sr & SR_QUAD_EN_MX) != 0U) {
 		return 0;
 	}
 
@@ -141,7 +141,7 @@
 	}
 
 	sr |= SR_QUAD_EN_MX;
-	ret = spi_nor_reg(SPI_NOR_OP_WRSR, &sr, 1, SPI_MEM_DATA_OUT);
+	ret = spi_nor_reg(SPI_NOR_OP_WRSR, &sr, 1U, SPI_MEM_DATA_OUT);
 	if (ret != 0) {
 		return ret;
 	}
@@ -168,7 +168,7 @@
 		return ret;
 	}
 
-	ret = spi_nor_reg(SPI_NOR_OP_WRSR, sr_cr, 2, SPI_MEM_DATA_OUT);
+	ret = spi_nor_reg(SPI_NOR_OP_WRSR, sr_cr, 2U, SPI_MEM_DATA_OUT);
 	if (ret != 0) {
 		return -EINVAL;
 	}
@@ -230,7 +230,7 @@
 	}
 
 	return spi_nor_reg(nor_dev.bank_write_cmd, &nor_dev.selected_bank,
-			   1, SPI_MEM_DATA_OUT);
+			   1U, SPI_MEM_DATA_OUT);
 }
 
 static int spi_nor_write_bar(uint32_t offset)
@@ -248,7 +248,7 @@
 	}
 
 	ret = spi_nor_reg(nor_dev.bank_write_cmd, &selected_bank,
-			  1, SPI_MEM_DATA_OUT);
+			  1U, SPI_MEM_DATA_OUT);
 	if (ret != 0) {
 		return ret;
 	}
@@ -260,11 +260,11 @@
 
 static int spi_nor_read_bar(void)
 {
-	uint8_t selected_bank = 0;
+	uint8_t selected_bank = 0U;
 	int ret;
 
 	ret = spi_nor_reg(nor_dev.bank_read_cmd, &selected_bank,
-			  1, SPI_MEM_DATA_IN);
+			  1U, SPI_MEM_DATA_IN);
 	if (ret != 0) {
 		return ret;
 	}
@@ -280,7 +280,7 @@
 	size_t remain_len;
 	int ret;
 
-	*length_read = 0;
+	*length_read = 0U;
 	nor_dev.read_op.addr.val = offset;
 	nor_dev.read_op.data.buf = (void *)buffer;
 
@@ -324,7 +324,7 @@
 
 int spi_nor_init(unsigned long long *size, unsigned int *erase_size)
 {
-	int ret = 0;
+	int ret;
 	uint8_t id;
 
 	/* Default read command used */
@@ -339,7 +339,7 @@
 		return -EINVAL;
 	}
 
-	assert(nor_dev.size != 0);
+	assert(nor_dev.size != 0U);
 
 	if (nor_dev.size > BANK_SIZE) {
 		nor_dev.flags |= SPI_NOR_USE_BANK;
diff --git a/drivers/mtd/spi-mem/spi_mem.c b/drivers/mtd/spi-mem/spi_mem.c
index 63ea769..010e8b6 100644
--- a/drivers/mtd/spi-mem/spi_mem.c
+++ b/drivers/mtd/spi-mem/spi_mem.c
@@ -5,6 +5,8 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <libfdt.h>
 
@@ -150,7 +152,7 @@
 	const struct spi_bus_ops *ops = spi_slave.ops;
 	int ret;
 
-	VERBOSE("%s: cmd:%x mode:%d.%d.%d.%d addqr:%llx len:%x\n",
+	VERBOSE("%s: cmd:%x mode:%d.%d.%d.%d addqr:%" PRIx64 " len:%x\n",
 		__func__, op->cmd.opcode, op->cmd.buswidth, op->addr.buswidth,
 		op->dummy.buswidth, op->data.buswidth,
 		op->addr.val, op->data.nbytes);
diff --git a/drivers/nxp/auth/csf_hdr_parser/cot.c b/drivers/nxp/auth/csf_hdr_parser/cot.c
new file mode 100644
index 0000000..4502ed6
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/cot.c
@@ -0,0 +1,284 @@
+/*
+ * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <drivers/auth/auth_mod.h>
+
+#if USE_TBBR_DEFS
+#include <tools_share/tbbr_oid.h>
+#else
+#include <platform_oid.h>
+#endif
+
+
+static auth_param_type_desc_t sig = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_SIG, 0);
+static auth_param_type_desc_t sig_alg = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_SIG_ALG, 0);
+static auth_param_type_desc_t sig_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, 0);
+
+static auth_param_type_desc_t non_trusted_world_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, NON_TRUSTED_WORLD_PK_OID);
+
+/*
+ * TBBR Chain of trust definition
+ */
+static const auth_img_desc_t bl31_image = {
+	.img_id = BL31_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t scp_bl2_image = {
+	.img_id = SCP_BL2_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl32_image = {
+	.img_id = BL32_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl33_image = {
+	.img_id = BL33_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+#ifdef POLICY_FUSE_PROVISION
+static const auth_img_desc_t fuse_prov_img = {
+	.img_id = FUSE_PROV_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t fuse_upgrade_img = {
+	.img_id = FUSE_UP_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+#endif
+#ifdef CONFIG_DDR_FIP_IMAGE
+static const auth_img_desc_t ddr_imem_udimm_1d_img = {
+	.img_id = DDR_IMEM_UDIMM_1D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_imem_udimm_2d_img = {
+	.img_id = DDR_IMEM_UDIMM_2D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_udimm_1d_img = {
+	.img_id = DDR_DMEM_UDIMM_1D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_udimm_2d_img = {
+	.img_id = DDR_DMEM_UDIMM_2D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_imem_rdimm_1d_img = {
+	.img_id = DDR_IMEM_RDIMM_1D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_imem_rdimm_2d_img = {
+	.img_id = DDR_IMEM_RDIMM_2D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_rdimm_1d_img = {
+	.img_id = DDR_DMEM_RDIMM_1D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_rdimm_2d_img = {
+	.img_id = DDR_DMEM_RDIMM_2D_IMAGE_ID,
+	.img_type = IMG_PLAT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &sig_hash
+			}
+		}
+	}
+};
+#endif
+
+static const auth_img_desc_t * const cot_desc[] = {
+	[BL31_IMAGE_ID]			=	&bl31_image,
+	[SCP_BL2_IMAGE_ID]		=	&scp_bl2_image,
+	[BL32_IMAGE_ID]			=	&bl32_image,
+	[BL33_IMAGE_ID]			=	&bl33_image,
+#ifdef POLICY_FUSE_PROVISION
+	[FUSE_PROV_IMAGE_ID]		=	&fuse_prov_img,
+	[FUSE_UP_IMAGE_ID]		=	&fuse_upgrade_img,
+#endif
+#ifdef CONFIG_DDR_FIP_IMAGE
+	[DDR_IMEM_UDIMM_1D_IMAGE_ID]	=	&ddr_imem_udimm_1d_img,
+	[DDR_IMEM_UDIMM_2D_IMAGE_ID]	=	&ddr_imem_udimm_2d_img,
+	[DDR_DMEM_UDIMM_1D_IMAGE_ID]	=	&ddr_dmem_udimm_1d_img,
+	[DDR_DMEM_UDIMM_2D_IMAGE_ID]	=	&ddr_dmem_udimm_2d_img,
+	[DDR_IMEM_RDIMM_1D_IMAGE_ID]	=	&ddr_imem_rdimm_1d_img,
+	[DDR_IMEM_RDIMM_2D_IMAGE_ID]	=	&ddr_imem_rdimm_2d_img,
+	[DDR_DMEM_RDIMM_1D_IMAGE_ID]	=	&ddr_dmem_rdimm_1d_img,
+	[DDR_DMEM_RDIMM_2D_IMAGE_ID]	=	&ddr_dmem_rdimm_2d_img,
+#endif
+};
+
+/* Register the CoT in the authentication module */
+REGISTER_COT(cot_desc);
diff --git a/drivers/nxp/auth/csf_hdr_parser/csf_hdr.mk b/drivers/nxp/auth/csf_hdr_parser/csf_hdr.mk
new file mode 100644
index 0000000..1af51f8
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/csf_hdr.mk
@@ -0,0 +1,64 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+CSF_HDR_SOURCES	:=  $(PLAT_DRIVERS_PATH)/auth/csf_hdr_parser/csf_hdr_parser.c
+
+CSF_HDR_SOURCES	+=  $(PLAT_DRIVERS_PATH)/auth/csf_hdr_parser/plat_img_parser.c
+
+PLAT_INCLUDES	+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/auth/csf_hdr_parser/
+
+$(eval $(call add_define, CSF_HEADER_PREPENDED))
+
+
+# Path to CST directory is required to generate the CSF header
+# and prepend it to image before fip image gets generated
+ifeq (${CST_DIR},)
+  $(error Error: CST_DIR not set)
+endif
+
+# Rules are created for generating and appending CSF header to images before
+# FIT image generation
+
+# CST_BL31
+define CST_BL31_RULE
+$(1): $(2)
+	@echo " Generating CSF Header for $$@ $$<"
+	$(Q)$(CST_DIR)/create_hdr_esbc --in $(2) --out $(1) --app_off ${CSF_HDR_SZ} \
+					--app $(2) ${BL31_INPUT_FILE}
+endef
+
+CST_BL31_SUFFIX := .cst
+
+# CST_BL32
+define CST_BL32_RULE
+$(1): $(2)
+	@echo " Generating CSF Header for $$@ $$<"
+	$(Q)$(CST_DIR)/create_hdr_esbc --in $(2) --out $(1) --app_off ${CSF_HDR_SZ} \
+					--app $(2) ${BL32_INPUT_FILE}
+endef
+
+CST_BL32_SUFFIX := .cst
+
+# CST_BL33
+define CST_BL33_RULE
+$(1): $(2)
+	@echo " Generating CSF Header for $$@ $$<"
+	$(Q)$(CST_DIR)/create_hdr_esbc --in $(2) --out $(1) --app_off ${CSF_HDR_SZ} \
+					--app $(2) ${BL33_INPUT_FILE}
+endef
+
+CST_BL33_SUFFIX := .cst
+
+# CST_SCP_BL2
+define CST_SCP_BL2_RULE
+$(1): $(2)
+	@echo " Generating CSF Header for $$@ $$<"
+	$(Q)$(CST_DIR)/create_hdr_esbc --in $(2) --out $(1) --app_off ${CSF_HDR_SZ} \
+					--app $(2) ${FUSE_INPUT_FILE}
+endef
+
+CST_SCP_BL2_SUFFIX := .cst
diff --git a/drivers/nxp/auth/csf_hdr_parser/csf_hdr_parser.c b/drivers/nxp/auth/csf_hdr_parser/csf_hdr_parser.c
new file mode 100644
index 0000000..b878082
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/csf_hdr_parser.c
@@ -0,0 +1,365 @@
+/*
+ * Copyright (c) 2014-2016, Freescale Semiconductor, Inc.
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <stddef.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <cassert.h>
+#include <common/debug.h>
+#include <csf_hdr.h>
+#include <dcfg.h>
+#include <drivers/auth/crypto_mod.h>
+#include <lib/utils.h>
+#include <sfp.h>
+
+/* Maximum OID string length ("a.b.c.d.e.f ...") */
+#define MAX_OID_STR_LEN			64
+
+#define LIB_NAME	"NXP CSFv2"
+
+#ifdef CSF_HDR_CH3
+/* Barker Code for LS Ch3 ESBC Header */
+static const uint8_t barker_code[CSF_BARKER_LEN] = { 0x12, 0x19, 0x20, 0x01 };
+#else
+static const uint8_t barker_code[CSF_BARKER_LEN] = { 0x68, 0x39, 0x27, 0x81 };
+#endif
+
+#define CHECK_KEY_LEN(key_len)	(((key_len) == 2 * RSA_1K_KEY_SZ_BYTES) || \
+				 ((key_len) == 2 * RSA_2K_KEY_SZ_BYTES) || \
+				 ((key_len) == 2 * RSA_4K_KEY_SZ_BYTES))
+
+/* Flag to indicate if values are there in rotpk_hash_table */
+bool rotpk_not_dpld =  true;
+uint8_t rotpk_hash_table[MAX_KEY_ENTRIES][SHA256_BYTES];
+uint32_t num_rotpk_hash_entries;
+
+/*
+ * This function deploys the hashes of the various platform keys in
+ * rotpk_hash_table. This is done in case of secure boot after comparison
+ * of table's hash with the hash in SFP fuses. This installation is done
+ * only in the first header parsing.
+ */
+static int deploy_rotpk_hash_table(void *srk_buffer, uint16_t num_srk)
+{
+	void *ctx;
+	int ret = 0;
+	int i, j = 0;
+	unsigned int digest_size = SHA256_BYTES;
+	enum hash_algo algo = SHA256;
+	uint8_t hash[SHA256_BYTES];
+	uint32_t srk_hash[SHA256_BYTES/4] __aligned(CACHE_WRITEBACK_GRANULE);
+	struct srk_table *srktbl = (void *)srk_buffer;
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(get_sfp_addr()
+							+ SFP_FUSE_REGS_OFFSET);
+
+
+	if (num_srk > MAX_KEY_ENTRIES) {
+		return -1;
+	}
+
+	ret = hash_init(algo, &ctx);
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Update hash with that of SRK table */
+	ret = hash_update(algo, ctx, (uint8_t *)((uint8_t *)srk_buffer),
+			  num_srk * sizeof(struct srk_table));
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Copy hash at destination buffer */
+	ret = hash_final(algo, ctx, hash, digest_size);
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Add comparison of hash with SFP hash here */
+	for (i = 0; i < SHA256_BYTES/4; i++) {
+		srk_hash[i] =
+			mmio_read_32((uintptr_t)&sfp_ccsr_regs->srk_hash[i]);
+	}
+
+	VERBOSE("SRK table HASH\n");
+	for (i = 0; i < 8; i++) {
+		VERBOSE("%x\n", *((uint32_t *)hash + i));
+	}
+
+	if (memcmp(hash, srk_hash, SHA256_BYTES) != 0) {
+		ERROR("Error in installing ROTPK table\n");
+		ERROR("SRK hash doesn't match the fuse hash\n");
+		return -1;
+	}
+
+	/* Hash table already deployed */
+	if (rotpk_not_dpld == false) {
+		return 0;
+	}
+
+	for (i = 0; i < num_srk; i++) {
+		ret = hash_init(algo, &ctx);
+		if (ret != 0) {
+			return -1;
+		}
+
+		/* Update hash with that of SRK table */
+		ret = hash_update(algo, ctx, srktbl[i].pkey, srktbl[i].key_len);
+		if (ret != 0) {
+			return -1;
+		}
+
+		/* Copy hash at destination buffer */
+		ret = hash_final(algo, ctx, rotpk_hash_table[i], digest_size);
+		if (ret != 0) {
+			return -1;
+		}
+		VERBOSE("Table key %d HASH\n", i);
+		for (j = 0; j < 8; j++) {
+			VERBOSE("%x\n", *((uint32_t *)rotpk_hash_table[i] + j));
+		}
+	}
+	rotpk_not_dpld = false;
+	num_rotpk_hash_entries = num_srk;
+
+	return 0;
+}
+
+/*
+ * Calculate hash of ESBC hdr and ESBC. This function calculates the
+ * single hash of ESBC header and ESBC image
+ */
+int calc_img_hash(struct csf_hdr *hdr,
+		  void *img_addr, uint32_t img_size,
+		  uint8_t *img_hash, uint32_t *hash_len)
+{
+	void *ctx;
+	int ret = 0;
+	unsigned int digest_size = SHA256_BYTES;
+	enum hash_algo algo = SHA256;
+
+	ret = hash_init(algo, &ctx);
+	/* Copy hash at destination buffer */
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Update hash for CSF Header */
+	ret = hash_update(algo, ctx, (uint8_t *)hdr, sizeof(struct csf_hdr));
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Update hash with that of SRK table */
+	ret = hash_update(algo, ctx,
+			  (uint8_t *)((uint8_t *)hdr + hdr->srk_tbl_off),
+			  hdr->len_kr.num_srk * sizeof(struct srk_table));
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Update hash for actual Image */
+	ret = hash_update(algo, ctx, (uint8_t *)(img_addr), img_size);
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* Copy hash at destination buffer */
+	ret = hash_final(algo, ctx, img_hash, digest_size);
+	if (ret != 0) {
+		return -1;
+	}
+
+	*hash_len = digest_size;
+
+	VERBOSE("IMG encoded HASH\n");
+	for (int i = 0; i < 8; i++) {
+		VERBOSE("%x\n", *((uint32_t *)img_hash + i));
+	}
+
+	return 0;
+}
+
+/* This function checks if selected key is revoked or not.*/
+static uint32_t is_key_revoked(uint32_t keynum, uint32_t rev_flag)
+{
+	if (keynum == UNREVOCABLE_KEY) {
+		return 0;
+	}
+
+	if (((uint32_t)(1 << (REVOC_KEY_ALIGN - keynum)) & rev_flag) != 0) {
+		return 1;
+	}
+
+	return 0;
+}
+
+/* Parse the header to extract the type of key,
+ * Check if key is not revoked
+ * and return the key , key length and key_type
+ */
+static int32_t get_key(struct csf_hdr *hdr, uint8_t **key, uint32_t *len,
+			enum sig_alg *key_type)
+{
+	int i = 0;
+	uint32_t ret = 0U;
+	uint32_t key_num, key_revoc_flag;
+	void *esbc = hdr;
+	struct srk_table *srktbl = (void *)((uint8_t *)esbc + hdr->srk_tbl_off);
+	bool sb;
+	uint32_t mode;
+
+	/* We currently support only RSA keys and signature */
+	*key_type = RSA;
+
+	/* Check for number of SRK entries */
+	if ((hdr->len_kr.num_srk == 0) ||
+	    (hdr->len_kr.num_srk > MAX_KEY_ENTRIES)) {
+		ERROR("Error in NUM entries in SRK Table\n");
+		return -1;
+	}
+
+	/*
+	 * Check the key number field. It should be not greater than
+	 * number of entries in SRK table.
+	 */
+	key_num = hdr->len_kr.srk_sel;
+	if ((key_num == 0) || (key_num > hdr->len_kr.num_srk)) {
+		ERROR("Invalid Key number\n");
+		return -1;
+	}
+
+	/* Get revoc key from sfp */
+	key_revoc_flag = get_key_revoc();
+
+	/* Check if selected key has been revoked */
+	ret = is_key_revoked(key_num, key_revoc_flag);
+	if (ret != 0) {
+		ERROR("Selected key has been revoked\n");
+		return -1;
+	}
+
+	/* Check for valid key length - allowed key sized 1k, 2k and 4K */
+	for (i = 0; i < hdr->len_kr.num_srk; i++) {
+		if (CHECK_KEY_LEN(srktbl[i].key_len) == 0) {
+			ERROR("Invalid key length\n");
+			return -1;
+		}
+	}
+
+	/* We don't return error from here. While parsing we just try to
+	 * install the srk table. Failure needs to be taken care of in
+	 * case of secure boot. This failure will be handled at the time
+	 * of rotpk comparison in plat_get_rotpk_info function
+	 */
+	sb = check_boot_mode_secure(&mode);
+	if (sb) {
+		ret = deploy_rotpk_hash_table(srktbl, hdr->len_kr.num_srk);
+		if (ret != 0) {
+			ERROR("ROTPK FAILURE\n");
+			/* For ITS =1 , return failure */
+			if (mode != 0) {
+				return -1;
+			}
+			ERROR("SECURE BOOT DEV-ENV MODE:\n");
+			ERROR("\tCHECK ROTPK !\n");
+			ERROR("\tCONTINUING ON FAILURE...\n");
+		}
+	}
+
+	/* Return the length of the selected key */
+	*len = srktbl[key_num - 1].key_len;
+
+	/* Point key to the selected key */
+	*key =  (uint8_t *)&(srktbl[key_num - 1].pkey);
+
+	return 0;
+}
+
+/*
+ * This function would parse the CSF header and do the following:
+ * 1. Basic integrity checks
+ * 2. Key checks and extract the key from SRK/IE Table
+ * 3. Key hash comparison with SRKH in fuses in case of SRK Table
+ * 4. OEM/UID checks - To be added
+ * 5. Hash calculation for various components used in signature
+ * 6. Signature integrity checks
+ * return -> 0 on success, -1 on failure
+ */
+int validate_esbc_header(void *img_hdr, void **img_key, uint32_t *key_len,
+			 void **img_sign, uint32_t *sign_len,
+			 enum sig_alg *algo)
+{
+	struct csf_hdr *hdr = img_hdr;
+	uint8_t *s;
+	int32_t ret = 0;
+	void *esbc = (uint8_t *)img_hdr;
+	uint8_t *key;
+	uint32_t klen;
+
+	/* check barker code */
+	if (memcmp(hdr->barker, barker_code, CSF_BARKER_LEN) != 0) {
+		ERROR("Wrong barker code in header\n");
+		return -1;
+	}
+
+	ret = get_key(hdr, &key, &klen, algo);
+	if (ret != 0) {
+		return -1;
+	}
+
+	/* check signaure */
+	if (klen == (2 * hdr->sign_len)) {
+		/* check signature length */
+		if (((hdr->sign_len == RSA_1K_KEY_SZ_BYTES) ||
+		    (hdr->sign_len == RSA_2K_KEY_SZ_BYTES) ||
+		    (hdr->sign_len == RSA_4K_KEY_SZ_BYTES)) == 0) {
+			ERROR("Wrong Signature length in header\n");
+			return -1;
+		}
+	} else {
+		ERROR("RSA key length not twice the signature length\n");
+		return -1;
+	}
+
+	/* modulus most significant bit should be set */
+
+	if ((key[0] & 0x80) == 0U) {
+		ERROR("RSA Public key MSB not set\n");
+		return -1;
+	}
+
+	/* modulus value should be odd */
+	if ((key[klen / 2 - 1] & 0x1) == 0U) {
+		ERROR("Public key Modulus in header not odd\n");
+		return -1;
+	}
+
+	/* Check signature value < modulus value */
+	s =  (uint8_t *)(esbc + hdr->psign);
+
+	if (!(memcmp(s, key, hdr->sign_len) < 0)) {
+		ERROR("Signature not less than modulus");
+		return -1;
+	}
+
+	/* Populate the return addresses */
+	*img_sign = (void *)(s);
+
+	/* Save the length of signature */
+	*sign_len = hdr->sign_len;
+
+	*img_key = (uint8_t *)key;
+
+	*key_len = klen;
+
+	return ret;
+}
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch2 b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch2
new file mode 100644
index 0000000..bf8934b
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch2
@@ -0,0 +1,89 @@
+/*
+ * Copyright (c) 2014-2016, Freescale Semiconductor, Inc.
+ * Copyright 2017-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform - 1010/1040/2041/3041/4080/5020/5040/9131/9132/9164/4240/C290/LS1
+PLATFORM=LS1043
+# ESBC Flag. Specify ESBC=0 to sign u-boot and ESBC=1 to sign ESBC images.(default is 0)
+ESBC=0
+---------------------------------------------------
+# Entry Point/Image start address field in the header.[Mandatory]
+# (default=ADDRESS of first file specified in images)
+ENTRY_POINT=10000000
+---------------------------------------------------
+# Specify the file name of the keys separated by comma.
+# The number of files and key select should lie between 1 and 4 for 1040 and C290.
+# For rest of the platforms only one key is required and key select should not be provided.
+
+# USAGE (for 4080/5020/5040/3041/2041/1010/913x): PRI_KEY = <key1.pri>
+# USAGE (for 1040/C290/9164/4240/LS1): PRI_KEY = <key1.pri>, <key2.pri>, <key3.pri>, <key4.pri>
+
+# PRI_KEY (Default private key :srk.pri) - [Optional]
+PRI_KEY=srk.pri
+# PUB_KEY (Default public key :srk.pub) - [Optional]
+PUB_KEY=srk.pub
+# Please provide KEY_SELECT(between 1 to 4) (Required for 1040/C290/9164/4240/LS1 only) - [Optional]
+KEY_SELECT=
+---------------------------------------------------
+# Specify SG table address, only for (2041/3041/4080/5020/5040) with ESBC=0 - [Optional]
+SG_TABLE_ADDR=
+---------------------------------------------------
+# Specify the target where image will be loaded. (Default is NOR_16B) - [Optional]
+# Only required for Non-PBL Devices (1010/1040/9131/9132i/C290)
+# Select from - NOR_8B/NOR_16B/NAND_8B_512/NAND_8B_2K/NAND_8B_4K/NAND_16B_512/NAND_16B_2K/NAND_16B_4K/SD/MMC/SPI
+IMAGE_TARGET=
+---------------------------------------------------
+# Specify IMAGE, Max 8 images are possible. DST_ADDR is required only for Non-PBL Platform. [Mandatory]
+# USAGE : IMAGE_NO = {IMAGE_NAME, SRC_ADDR, DST_ADDR}
+IMAGE_1={bl2.bin,10000000,ffffffff}
+IMAGE_2={,,}
+IMAGE_3={,,}
+IMAGE_4={,,}
+IMAGE_5={,,}
+IMAGE_6={,,}
+IMAGE_7={,,}
+IMAGE_8={,,}
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+---------------------------------------------------
+# Specify the file names of csf header and sg table. (Default :hdr.out) [Optional]
+OUTPUT_HDR_FILENAME=hdr_bl2.out
+
+# Specify the file names of hash file and sign file.
+HASH_FILENAME=img_hash.out
+INPUT_SIGN_FILENAME=sign.out
+
+# Specify the signature size.It is mandatory when neither public key nor private key is specified.
+# Signature size would be [0x80 for 1k key, 0x100 for 2k key, and 0x200 for 4k key].
+SIGN_SIZE=
+---------------------------------------------------
+# Specify the output file name of sg table. (Default :sg_table.out). [Optional]
+# Please note that OUTPUT SG BIN is only required for 2041/3041/4080/5020/5040 when ESBC flag is not set.
+OUTPUT_SG_BIN=
+---------------------------------------------------
+# Following fields are Required for 4240/9164/1040/C290 only
+
+# Specify House keeping Area
+# Required for 4240/9164/1040/C290 only when ESBC flag is not set. [Mandatory]
+HK_AREA_POINTER=
+HK_AREA_SIZE=
+---------------------------------------------------
+# Following field Required for 4240/9164/1040/C290 only
+# Specify Secondary Image Flag. (0 or 1) - [Optional]
+# (Default is 0)
+SEC_IMAGE=0
+# Specify Manufacturing Protection Flag. (0 or 1) - [Optional]
+# Required only for LS1(Default is 0)
+MP_FLAG=1
+---------------------------------------------------
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3 b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3
new file mode 100644
index 0000000..5fdad9c
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform -
+# TRUST 3.2: LX2160
+PLATFORM=LS2088
+---------------------------------------------------
+# Entry Point/Image start address field in the header.[Mandatory]
+# (default=ADDRESS of first file specified in images)
+# Address can be 64 bit
+ENTRY_POINT=1800A000
+---------------------------------------------------
+# Specify the Key Information.
+# PUB_KEY [Mandatory] Comma Separated List
+# Usage: <srk1.pub> <srk2.pub> .....
+PUB_KEY=srk.pub
+# KEY_SELECT [Mandatory]
+# USAGE (for TRUST 3.x): (between 1 to 8)
+KEY_SELECT=1
+# PRI_KEY [Mandatory] Single Key Used for Signing
+# USAGE: <srk.pri>
+PRI_KEY=srk.pri
+---------------------------------------------------
+# Specify IMAGE, Max 8 images are possible.
+# DST_ADDR is required only for Non-PBL Platform. [Mandatory]
+# USAGE : IMAGE_NO = {IMAGE_NAME, SRC_ADDR, DST_ADDR}
+# Address can be 64 bit
+IMAGE_1={bl2.bin,1800A000,ffffffff}
+IMAGE_2={,,}
+IMAGE_3={,,}
+IMAGE_4={,,}
+IMAGE_5={,,}
+IMAGE_6={,,}
+IMAGE_7={,,}
+IMAGE_8={,,}
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID_0=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+OEM_UID_2=
+OEM_UID_3=
+OEM_UID_4=
+---------------------------------------------------
+# Specify the output file names [Optional].
+# Default Values chosen in Tool
+OUTPUT_HDR_FILENAME=hdr_bl2.out
+IMAGE_HASH_FILENAME=
+RSA_SIGN_FILENAME=
+---------------------------------------------------
+# Specify The Flags. (0 or 1) - [Optional]
+MP_FLAG=0
+ISS_FLAG=1
+LW_FLAG=0
+---------------------------------------------------
+# Specify VERBOSE as 1, if you want to Display Header Information [Optional]
+VERBOSE=1
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3_2 b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3_2
new file mode 100644
index 0000000..cc7c07c
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_bl2_ch3_2
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform -
+# TRUST 3.2: LX2160
+PLATFORM=LX2160
+---------------------------------------------------
+# Entry Point/Image start address field in the header.[Mandatory]
+# (default=ADDRESS of first file specified in images)
+# Address can be 64 bit
+ENTRY_POINT=1800D000
+---------------------------------------------------
+# Specify the Key Information.
+# PUB_KEY [Mandatory] Comma Separated List
+# Usage: <srk1.pub> <srk2.pub> .....
+PUB_KEY=srk.pub
+# KEY_SELECT [Mandatory]
+# USAGE (for TRUST 3.x): (between 1 to 8)
+KEY_SELECT=1
+# PRI_KEY [Mandatory] Single Key Used for Signing
+# USAGE: <srk.pri>
+PRI_KEY=srk.pri
+---------------------------------------------------
+# Specify IMAGE, Max 8 images are possible.
+# DST_ADDR is required only for Non-PBL Platform. [Mandatory]
+# USAGE : IMAGE_NO = {IMAGE_NAME, SRC_ADDR, DST_ADDR}
+# Address can be 64 bit
+IMAGE_1={bl2.bin,1800D000,ffffffff}
+IMAGE_2={,,}
+IMAGE_3={,,}
+IMAGE_4={,,}
+IMAGE_5={,,}
+IMAGE_6={,,}
+IMAGE_7={,,}
+IMAGE_8={,,}
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID_0=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+OEM_UID_2=
+OEM_UID_3=
+OEM_UID_4=
+---------------------------------------------------
+# Specify the output file names [Optional].
+# Default Values chosen in Tool
+OUTPUT_HDR_FILENAME=hdr_bl2.out
+IMAGE_HASH_FILENAME=
+RSA_SIGN_FILENAME=
+---------------------------------------------------
+# Specify The Flags. (0 or 1) - [Optional]
+MP_FLAG=0
+ISS_FLAG=1
+LW_FLAG=0
+---------------------------------------------------
+# Specify VERBOSE as 1, if you want to Display Header Information [Optional]
+VERBOSE=1
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_blx_ch2 b/drivers/nxp/auth/csf_hdr_parser/input_blx_ch2
new file mode 100644
index 0000000..93b020b
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_blx_ch2
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2017-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform - 1010/1040/2041/3041/4080/5020/5040/9131/9132/9164/4240/C290/LS1
+PLATFORM=LS1043
+# ESBC Flag. Specify ESBC=0 to sign u-boot and ESBC=1 to sign ESBC images.(default is 0)
+ESBC=1
+---------------------------------------------------
+# Specify the file name of the keys separated by comma.
+
+# PRI_KEY (Default private key :srk.pri) - [Optional]
+PRI_KEY=srk.pri
+# PUB_KEY (Default public key :srk.pub) - [Optional]
+PUB_KEY=srk.pub
+# Please provide KEY_SELECT(between 1 to 4) (Required for 1040/C290/9164/4240 only) - [Optional]
+KEY_SELECT=1
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+---------------------------------------------------
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_blx_ch3 b/drivers/nxp/auth/csf_hdr_parser/input_blx_ch3
new file mode 100644
index 0000000..18e8e3b
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_blx_ch3
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2017-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+ESBC=1
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform -
+# TRUST 3.0: LS2085
+# TRUST 3.1: LS2088, LS1088
+PLATFORM=LS2088
+---------------------------------------------------
+# Specify the Key Information.
+# PUB_KEY [Mandatory] Comma Separated List
+# Usage: <srk1.pub> <srk2.pub> .....
+PUB_KEY=srk.pub
+# KEY_SELECT [Mandatory]
+# USAGE (for TRUST 3.x): (between 1 to 8)
+KEY_SELECT=1
+# PRI_KEY [Mandatory] Single Key Used for Signing
+# USAGE: <srk.pri>
+PRI_KEY=srk.pri
+
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID_0=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+OEM_UID_2=
+OEM_UID_3=
+OEM_UID_4=
+---------------------------------------------------
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3 b/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3
new file mode 100644
index 0000000..9111a2a
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2016-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform -
+# TRUST 3.0: LS2085
+# TRUST 3.1: LS2088, LS1088
+PLATFORM=LS2088
+---------------------------------------------------
+# Specify the Key Information.
+# PUB_KEY [Mandatory] Comma Separated List
+# Usage: <srk1.pub> <srk2.pub> .....
+PUB_KEY=srk.pub
+# KEY_SELECT [Mandatory]
+# USAGE (for TRUST 3.x): (between 1 to 8)
+KEY_SELECT=1
+# PRI_KEY [Mandatory] Single Key Used for Signing
+# USAGE: <srk.pri>
+PRI_KEY=srk.pri
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID_0=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+OEM_UID_2=
+OEM_UID_3=
+OEM_UID_4=
+---------------------------------------------------
+# Specify The Flags. (0 or 1) - [Optional]
+MP_FLAG=0
+ISS_FLAG=1
+LW_FLAG=0
+---------------------------------------------------
+# Specify VERBOSE as 1, if you want to Display Header Information [Optional]
+VERBOSE=1
+---------------------------------------------------
diff --git a/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3_2 b/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3_2
new file mode 100644
index 0000000..c2d7ce4
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/input_pbi_ch3_2
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2017-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+---------------------------------------------------
+# Specify the platform. [Mandatory]
+# Choose Platform -
+# TRUST 3.0: LS2085
+# TRUST 3.1: LS2088, LS1088
+PLATFORM=LX2160
+---------------------------------------------------
+# Specify the Key Information.
+# PUB_KEY [Mandatory] Comma Separated List
+# Usage: <srk1.pub> <srk2.pub> .....
+PUB_KEY=srk.pub
+# KEY_SELECT [Mandatory]
+# USAGE (for TRUST 3.x): (between 1 to 8)
+KEY_SELECT=1
+# PRI_KEY [Mandatory] Single Key Used for Signing
+# USAGE: <srk.pri>
+PRI_KEY=srk.pri
+---------------------------------------------------
+# Specify OEM AND FSL ID to be populated in header. [Optional]
+# e.g FSL_UID_0=11111111
+FSL_UID_0=
+FSL_UID_1=
+OEM_UID_0=
+OEM_UID_1=
+OEM_UID_2=
+OEM_UID_3=
+OEM_UID_4=
+---------------------------------------------------
+# Specify The Flags. (0 or 1) - [Optional]
+MP_FLAG=0
+ISS_FLAG=1
+LW_FLAG=0
+---------------------------------------------------
+# Specify VERBOSE as 1, if you want to Display Header Information [Optional]
+VERBOSE=1
+---------------------------------------------------
diff --git a/drivers/nxp/auth/csf_hdr_parser/plat_img_parser.c b/drivers/nxp/auth/csf_hdr_parser/plat_img_parser.c
new file mode 100644
index 0000000..43b78e5
--- /dev/null
+++ b/drivers/nxp/auth/csf_hdr_parser/plat_img_parser.c
@@ -0,0 +1,180 @@
+/*
+ * Copyright (c) 2014-2016, Freescale Semiconductor, Inc.
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <stddef.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <csf_hdr.h>
+#include <drivers/auth/crypto_mod.h>
+#include <drivers/auth/img_parser_mod.h>
+#include <lib/utils.h>
+#include <sfp.h>
+
+/* Temporary variables to speed up the authentication parameters search. These
+ * variables are assigned once during the integrity check and used any time an
+ * authentication parameter is requested, so we do not have to parse the image
+ * again.
+ */
+
+/* Hash of Image + CSF Header + SRK table */
+uint8_t img_hash[SHA256_BYTES] __aligned(CACHE_WRITEBACK_GRANULE);
+uint32_t hash_len;
+
+/* Key being used for authentication
+ * Points to the key in CSF header copied in DDR
+ * ESBC client key
+ */
+void *img_key;
+uint32_t key_len;
+
+/* ESBC client signature */
+void *img_sign;
+uint32_t sign_len;
+enum sig_alg alg;
+
+/* Maximum OID string length ("a.b.c.d.e.f ...") */
+#define MAX_OID_STR_LEN			64
+
+#define LIB_NAME	"NXP CSFv2"
+
+/*
+ * Clear all static temporary variables.
+ */
+static void clear_temp_vars(void)
+{
+#define ZERO_AND_CLEAN(x)					\
+	do {							\
+		zeromem(&x, sizeof(x));				\
+		clean_dcache_range((uintptr_t)&x, sizeof(x));	\
+	} while (0)
+
+	ZERO_AND_CLEAN(img_key);
+	ZERO_AND_CLEAN(img_sign);
+	ZERO_AND_CLEAN(img_hash);
+	ZERO_AND_CLEAN(key_len);
+	ZERO_AND_CLEAN(hash_len);
+	ZERO_AND_CLEAN(sign_len);
+
+#undef ZERO_AND_CLEAN
+}
+
+/* Exported functions */
+
+static void init(void)
+{
+	clear_temp_vars();
+}
+
+/*
+ * This function would check the integrity of the CSF header
+ */
+static int check_integrity(void *img, unsigned int img_len)
+{
+	int ret;
+
+	/*
+	 * The image file has been successfully loaded till here.
+	 *
+	 * Flush the image to main memory so that it can be authenticated
+	 * by CAAM, a HW accelerator regardless of cache and MMU state.
+	 */
+	flush_dcache_range((uintptr_t) img, img_len);
+
+	/*
+	 * Image is appended at an offset of 16K (IMG_OFFSET) to the header.
+	 * So the size in header should be equal to img_len - IMG_OFFSET
+	 */
+	VERBOSE("Barker code is %x\n", *(unsigned int *)img);
+	ret = validate_esbc_header(img, &img_key, &key_len, &img_sign,
+				   &sign_len, &alg);
+	if (ret < 0) {
+		ERROR("Header authentication failed\n");
+		clear_temp_vars();
+		return IMG_PARSER_ERR;
+	}
+	/* Calculate the hash of various components from the image */
+	ret = calc_img_hash(img, (uint8_t *)img + CSF_HDR_SZ,
+			    img_len - CSF_HDR_SZ, img_hash, &hash_len);
+	if (ret != 0) {
+		ERROR("Issue in hash calculation %d\n", ret);
+		clear_temp_vars();
+		return IMG_PARSER_ERR;
+	}
+
+	return IMG_PARSER_OK;
+}
+
+/*
+ * Extract an authentication parameter from CSF header
+ *
+ * CSF header has already been parsed and the required information like
+ * hash of data, signature, length stored in global variables has been
+ * extracted in chek_integrity function.  This data
+ * is returned back to the caller.
+ */
+static int get_auth_param(const auth_param_type_desc_t *type_desc,
+		void *img, unsigned int img_len,
+		void **param, unsigned int *param_len)
+{
+	int rc = IMG_PARSER_OK;
+
+	/* We do not use img because the check_integrity function has already
+	 * extracted the relevant data ( pk, sig_alg, etc)
+	 */
+
+	switch (type_desc->type) {
+
+	/* Hash will be returned for comparison with signature */
+	case AUTH_PARAM_HASH:
+		*param = (void *)img_hash;
+		*param_len = (unsigned int)SHA256_BYTES;
+		break;
+
+	/* Return the public key used for signature extracted from the SRK table
+	 * after checks with key revocation
+	 */
+	case AUTH_PARAM_PUB_KEY:
+		/* Get the subject public key */
+		/* For a 1K key - the length would be 2k/8 = 0x100 bytes
+		 * 2K RSA key - 0x200 , 4K RSA - 0x400
+		 */
+		*param = img_key;
+		*param_len = (unsigned int)key_len;
+		break;
+
+	/* Call a function to tell if signature is RSA or ECDSA. ECDSA to be
+	 * supported in later platforms like LX2 etc
+	 */
+	case AUTH_PARAM_SIG_ALG:
+		/* Algo will be signature - RSA or ECDSA  on hash */
+		*param = (void *)&alg;
+		*param_len = 4U;
+		break;
+
+	/* Return the signature */
+	case AUTH_PARAM_SIG:
+		*param = img_sign;
+		*param_len = (unsigned int)sign_len;
+		break;
+
+	case AUTH_PARAM_NV_CTR:
+
+	default:
+		rc = IMG_PARSER_ERR_NOT_FOUND;
+		break;
+	}
+
+	return rc;
+}
+
+REGISTER_IMG_PARSER_LIB(IMG_PLAT, LIB_NAME, init,
+			check_integrity, get_auth_param);
diff --git a/drivers/nxp/auth/tbbr/tbbr_cot.c b/drivers/nxp/auth/tbbr/tbbr_cot.c
new file mode 100644
index 0000000..bb21fa0
--- /dev/null
+++ b/drivers/nxp/auth/tbbr/tbbr_cot.c
@@ -0,0 +1,820 @@
+/*
+ * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <drivers/auth/auth_mod.h>
+
+#if USE_TBBR_DEFS
+#include <tools_share/tbbr_oid.h>
+#else
+#include <platform_oid.h>
+#endif
+
+
+#if TF_MBEDTLS_HASH_ALG_ID == TF_MBEDTLS_SHA256
+#define HASH_DER_LEN			51
+#elif TF_MBEDTLS_HASH_ALG_ID == TF_MBEDTLS_SHA384
+#define HASH_DER_LEN			67
+#elif TF_MBEDTLS_HASH_ALG_ID == TF_MBEDTLS_SHA512
+#define HASH_DER_LEN			83
+#else
+#error "Invalid value for TF_MBEDTLS_HASH_ALG_ID"
+#endif
+
+/*
+ * The platform must allocate buffers to store the authentication parameters
+ * extracted from the certificates. In this case, because of the way the CoT is
+ * established, we can reuse some of the buffers on different stages
+ */
+
+static unsigned char nt_world_bl_hash_buf[HASH_DER_LEN];
+
+static unsigned char soc_fw_hash_buf[HASH_DER_LEN];
+static unsigned char tos_fw_hash_buf[HASH_DER_LEN];
+static unsigned char tos_fw_extra1_hash_buf[HASH_DER_LEN];
+static unsigned char tos_fw_extra2_hash_buf[HASH_DER_LEN];
+static unsigned char trusted_world_pk_buf[PK_DER_LEN];
+static unsigned char non_trusted_world_pk_buf[PK_DER_LEN];
+static unsigned char content_pk_buf[PK_DER_LEN];
+static unsigned char soc_fw_config_hash_buf[HASH_DER_LEN];
+static unsigned char tos_fw_config_hash_buf[HASH_DER_LEN];
+static unsigned char nt_fw_config_hash_buf[HASH_DER_LEN];
+
+#ifdef CONFIG_DDR_FIP_IMAGE
+static unsigned char ddr_fw_content_pk_buf[PK_DER_LEN];
+static unsigned char ddr_imem_udimm_1d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_imem_udimm_2d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_dmem_udimm_1d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_dmem_udimm_2d_hash_buf[HASH_DER_LEN];
+
+static unsigned char ddr_imem_rdimm_1d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_imem_rdimm_2d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_dmem_rdimm_1d_hash_buf[HASH_DER_LEN];
+static unsigned char ddr_dmem_rdimm_2d_hash_buf[HASH_DER_LEN];
+#endif
+
+/*
+ * Parameter type descriptors
+ */
+static auth_param_type_desc_t trusted_nv_ctr = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_NV_CTR, TRUSTED_FW_NVCOUNTER_OID);
+
+static auth_param_type_desc_t subject_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, 0);
+static auth_param_type_desc_t sig = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_SIG, 0);
+static auth_param_type_desc_t sig_alg = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_SIG_ALG, 0);
+static auth_param_type_desc_t raw_data = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_RAW_DATA, 0);
+
+
+static auth_param_type_desc_t non_trusted_nv_ctr = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_NV_CTR, NON_TRUSTED_FW_NVCOUNTER_OID);
+static auth_param_type_desc_t trusted_world_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, TRUSTED_WORLD_PK_OID);
+static auth_param_type_desc_t non_trusted_world_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, NON_TRUSTED_WORLD_PK_OID);
+static auth_param_type_desc_t soc_fw_content_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, SOC_FW_CONTENT_CERT_PK_OID);
+static auth_param_type_desc_t tos_fw_content_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, TRUSTED_OS_FW_CONTENT_CERT_PK_OID);
+static auth_param_type_desc_t nt_fw_content_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, NON_TRUSTED_FW_CONTENT_CERT_PK_OID);
+static auth_param_type_desc_t soc_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, SOC_AP_FW_HASH_OID);
+static auth_param_type_desc_t soc_fw_config_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, SOC_FW_CONFIG_HASH_OID);
+static auth_param_type_desc_t tos_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, TRUSTED_OS_FW_HASH_OID);
+static auth_param_type_desc_t tos_fw_config_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, TRUSTED_OS_FW_CONFIG_HASH_OID);
+static auth_param_type_desc_t tos_fw_extra1_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, TRUSTED_OS_FW_EXTRA1_HASH_OID);
+static auth_param_type_desc_t tos_fw_extra2_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, TRUSTED_OS_FW_EXTRA2_HASH_OID);
+static auth_param_type_desc_t nt_world_bl_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, NON_TRUSTED_WORLD_BOOTLOADER_HASH_OID);
+static auth_param_type_desc_t nt_fw_config_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, NON_TRUSTED_FW_CONFIG_HASH_OID);
+
+#ifdef CONFIG_DDR_FIP_IMAGE
+static auth_param_type_desc_t ddr_fw_content_pk = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_PUB_KEY, DDR_FW_CONTENT_CERT_PK_OID);
+
+static auth_param_type_desc_t ddr_imem_udimm_1d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_IMEM_UDIMM_1D_HASH_OID);
+static auth_param_type_desc_t ddr_imem_udimm_2d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_IMEM_UDIMM_2D_HASH_OID);
+static auth_param_type_desc_t ddr_dmem_udimm_1d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_DMEM_UDIMM_1D_HASH_OID);
+static auth_param_type_desc_t ddr_dmem_udimm_2d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_DMEM_UDIMM_2D_HASH_OID);
+
+static auth_param_type_desc_t ddr_imem_rdimm_1d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_IMEM_RDIMM_1D_HASH_OID);
+static auth_param_type_desc_t ddr_imem_rdimm_2d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_IMEM_RDIMM_2D_HASH_OID);
+static auth_param_type_desc_t ddr_dmem_rdimm_1d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_DMEM_RDIMM_1D_HASH_OID);
+static auth_param_type_desc_t ddr_dmem_rdimm_2d_fw_hash = AUTH_PARAM_TYPE_DESC(
+		AUTH_PARAM_HASH, DDR_DMEM_RDIMM_2D_HASH_OID);
+#endif
+
+
+/*
+ * Trusted key certificate
+ */
+static const auth_img_desc_t trusted_key_cert = {
+	.img_id = TRUSTED_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = NULL,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &subject_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &trusted_world_pk,
+			.data = {
+				.ptr = (void *)trusted_world_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &non_trusted_world_pk,
+			.data = {
+				.ptr = (void *)non_trusted_world_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+
+/*
+ * SoC Firmware
+ */
+static const auth_img_desc_t soc_fw_key_cert = {
+	.img_id = SOC_FW_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &soc_fw_content_pk,
+			.data = {
+				.ptr = (void *)content_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t soc_fw_content_cert = {
+	.img_id = SOC_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &soc_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &soc_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &soc_fw_hash,
+			.data = {
+				.ptr = (void *)soc_fw_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &soc_fw_config_hash,
+			.data = {
+				.ptr = (void *)soc_fw_config_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl31_image = {
+	.img_id = BL31_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &soc_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &soc_fw_hash
+			}
+		}
+	}
+};
+/* SOC FW Config */
+static const auth_img_desc_t soc_fw_config = {
+	.img_id = SOC_FW_CONFIG_ID,
+	.img_type = IMG_RAW,
+	.parent = &soc_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &soc_fw_config_hash
+			}
+		}
+	}
+};
+/*
+ * Trusted OS Firmware
+ */
+static const auth_img_desc_t trusted_os_fw_key_cert = {
+	.img_id = TRUSTED_OS_FW_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &tos_fw_content_pk,
+			.data = {
+				.ptr = (void *)content_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t trusted_os_fw_content_cert = {
+	.img_id = TRUSTED_OS_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_os_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &tos_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &tos_fw_hash,
+			.data = {
+				.ptr = (void *)tos_fw_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &tos_fw_extra1_hash,
+			.data = {
+				.ptr = (void *)tos_fw_extra1_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[2] = {
+			.type_desc = &tos_fw_extra2_hash,
+			.data = {
+				.ptr = (void *)tos_fw_extra2_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[3] = {
+			.type_desc = &tos_fw_config_hash,
+			.data = {
+				.ptr = (void *)tos_fw_config_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl32_image = {
+	.img_id = BL32_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &trusted_os_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &tos_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl32_extra1_image = {
+	.img_id = BL32_EXTRA1_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &trusted_os_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &tos_fw_extra1_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl32_extra2_image = {
+	.img_id = BL32_EXTRA2_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &trusted_os_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &tos_fw_extra2_hash
+			}
+		}
+	}
+};
+/* TOS FW Config */
+static const auth_img_desc_t tos_fw_config = {
+	.img_id = TOS_FW_CONFIG_ID,
+	.img_type = IMG_RAW,
+	.parent = &trusted_os_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &tos_fw_config_hash
+			}
+		}
+	}
+};
+/*
+ * Non-Trusted Firmware
+ */
+static const auth_img_desc_t non_trusted_fw_key_cert = {
+	.img_id = NON_TRUSTED_FW_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &non_trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &non_trusted_nv_ctr,
+				.plat_nv_ctr = &non_trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &nt_fw_content_pk,
+			.data = {
+				.ptr = (void *)content_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t non_trusted_fw_content_cert = {
+	.img_id = NON_TRUSTED_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &non_trusted_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &nt_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &non_trusted_nv_ctr,
+				.plat_nv_ctr = &non_trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &nt_world_bl_hash,
+			.data = {
+				.ptr = (void *)nt_world_bl_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &nt_fw_config_hash,
+			.data = {
+				.ptr = (void *)nt_fw_config_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t bl33_image = {
+	.img_id = BL33_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &non_trusted_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &nt_world_bl_hash
+			}
+		}
+	}
+};
+/* NT FW Config */
+static const auth_img_desc_t nt_fw_config = {
+	.img_id = NT_FW_CONFIG_ID,
+	.img_type = IMG_RAW,
+	.parent = &non_trusted_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &nt_fw_config_hash
+			}
+		}
+	}
+};
+#ifdef CONFIG_DDR_FIP_IMAGE
+/*
+ * DDR Firmware
+ */
+static const auth_img_desc_t ddr_fw_key_cert = {
+	.img_id = DDR_FW_KEY_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &trusted_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &trusted_world_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &ddr_fw_content_pk,
+			.data = {
+				.ptr = (void *)ddr_fw_content_pk_buf,
+				.len = (unsigned int)PK_DER_LEN
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_udimm_fw_content_cert = {
+	.img_id = DDR_UDIMM_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &ddr_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &ddr_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &ddr_imem_udimm_1d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_imem_udimm_1d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &ddr_imem_udimm_2d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_imem_udimm_2d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[2] = {
+			.type_desc = &ddr_dmem_udimm_1d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_dmem_udimm_1d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[3] = {
+			.type_desc = &ddr_dmem_udimm_2d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_dmem_udimm_2d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+	}
+};
+
+static const auth_img_desc_t ddr_imem_udimm_1d_img = {
+	.img_id = DDR_IMEM_UDIMM_1D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_udimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_imem_udimm_1d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_imem_udimm_2d_img = {
+	.img_id = DDR_IMEM_UDIMM_2D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_udimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_imem_udimm_2d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_udimm_1d_img = {
+	.img_id = DDR_DMEM_UDIMM_1D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_udimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_dmem_udimm_1d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_udimm_2d_img = {
+	.img_id = DDR_DMEM_UDIMM_2D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_udimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_dmem_udimm_2d_fw_hash
+			}
+		}
+	}
+};
+
+static const auth_img_desc_t ddr_rdimm_fw_content_cert = {
+	.img_id = DDR_RDIMM_FW_CONTENT_CERT_ID,
+	.img_type = IMG_CERT,
+	.parent = &ddr_fw_key_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_SIG,
+			.param.sig = {
+				.pk = &ddr_fw_content_pk,
+				.sig = &sig,
+				.alg = &sig_alg,
+				.data = &raw_data
+			}
+		},
+		[1] = {
+			.type = AUTH_METHOD_NV_CTR,
+			.param.nv_ctr = {
+				.cert_nv_ctr = &trusted_nv_ctr,
+				.plat_nv_ctr = &trusted_nv_ctr
+			}
+		}
+	},
+	.authenticated_data = (const auth_param_desc_t[COT_MAX_VERIFIED_PARAMS]) {
+		[0] = {
+			.type_desc = &ddr_imem_rdimm_1d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_imem_rdimm_1d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[1] = {
+			.type_desc = &ddr_imem_rdimm_2d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_imem_rdimm_2d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[2] = {
+			.type_desc = &ddr_dmem_rdimm_1d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_dmem_rdimm_1d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+		[3] = {
+			.type_desc = &ddr_dmem_rdimm_2d_fw_hash,
+			.data = {
+				.ptr = (void *)ddr_dmem_rdimm_2d_hash_buf,
+				.len = (unsigned int)HASH_DER_LEN
+			}
+		},
+	}
+};
+
+static const auth_img_desc_t ddr_imem_rdimm_1d_img = {
+	.img_id = DDR_IMEM_RDIMM_1D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_rdimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_imem_rdimm_1d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_imem_rdimm_2d_img = {
+	.img_id = DDR_IMEM_RDIMM_2D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_rdimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_imem_rdimm_2d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_rdimm_1d_img = {
+	.img_id = DDR_DMEM_RDIMM_1D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_rdimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_dmem_rdimm_1d_fw_hash
+			}
+		}
+	}
+};
+static const auth_img_desc_t ddr_dmem_rdimm_2d_img = {
+	.img_id = DDR_DMEM_RDIMM_2D_IMAGE_ID,
+	.img_type = IMG_RAW,
+	.parent = &ddr_rdimm_fw_content_cert,
+	.img_auth_methods = (const auth_method_desc_t[AUTH_METHOD_NUM]) {
+		[0] = {
+			.type = AUTH_METHOD_HASH,
+			.param.hash = {
+				.data = &raw_data,
+				.hash = &ddr_dmem_rdimm_2d_fw_hash
+			}
+		}
+	}
+};
+#endif
+
+/*
+ * TBBR Chain of trust definition
+ */
+
+static const auth_img_desc_t * const cot_desc[] = {
+	[TRUSTED_KEY_CERT_ID]			=	&trusted_key_cert,
+	[SOC_FW_KEY_CERT_ID]			=	&soc_fw_key_cert,
+	[SOC_FW_CONTENT_CERT_ID]		=	&soc_fw_content_cert,
+	[BL31_IMAGE_ID]				=	&bl31_image,
+	[SOC_FW_CONFIG_ID]			=	&soc_fw_config,
+	[TRUSTED_OS_FW_KEY_CERT_ID]		=	&trusted_os_fw_key_cert,
+	[TRUSTED_OS_FW_CONTENT_CERT_ID]		=	&trusted_os_fw_content_cert,
+	[BL32_IMAGE_ID]				=	&bl32_image,
+	[BL32_EXTRA1_IMAGE_ID]			=	&bl32_extra1_image,
+	[BL32_EXTRA2_IMAGE_ID]			=	&bl32_extra2_image,
+	[TOS_FW_CONFIG_ID]			=	&tos_fw_config,
+	[NON_TRUSTED_FW_KEY_CERT_ID]		=	&non_trusted_fw_key_cert,
+	[NON_TRUSTED_FW_CONTENT_CERT_ID]	=	&non_trusted_fw_content_cert,
+	[BL33_IMAGE_ID]				=	&bl33_image,
+	[NT_FW_CONFIG_ID]			=	&nt_fw_config,
+#ifdef CONFIG_DDR_FIP_IMAGE
+	[DDR_FW_KEY_CERT_ID]			=	&ddr_fw_key_cert,
+	[DDR_UDIMM_FW_CONTENT_CERT_ID]		=	&ddr_udimm_fw_content_cert,
+	[DDR_RDIMM_FW_CONTENT_CERT_ID]		=	&ddr_rdimm_fw_content_cert,
+	[DDR_IMEM_UDIMM_1D_IMAGE_ID]		=	&ddr_imem_udimm_1d_img,
+	[DDR_IMEM_UDIMM_2D_IMAGE_ID]		=	&ddr_imem_udimm_2d_img,
+	[DDR_DMEM_UDIMM_1D_IMAGE_ID]		=	&ddr_dmem_udimm_1d_img,
+	[DDR_DMEM_UDIMM_2D_IMAGE_ID]		=	&ddr_dmem_udimm_2d_img,
+	[DDR_IMEM_RDIMM_1D_IMAGE_ID]		=	&ddr_imem_rdimm_1d_img,
+	[DDR_IMEM_RDIMM_2D_IMAGE_ID]		=	&ddr_imem_rdimm_2d_img,
+	[DDR_DMEM_RDIMM_1D_IMAGE_ID]		=	&ddr_dmem_rdimm_1d_img,
+	[DDR_DMEM_RDIMM_2D_IMAGE_ID]		=	&ddr_dmem_rdimm_2d_img,
+#endif
+};
+
+/* Register the CoT in the authentication module */
+REGISTER_COT(cot_desc);
diff --git a/drivers/nxp/console/16550_console.S b/drivers/nxp/console/16550_console.S
new file mode 100644
index 0000000..044d3d0
--- /dev/null
+++ b/drivers/nxp/console/16550_console.S
@@ -0,0 +1,319 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <assert_macros.S>
+#include <console_macros.S>
+
+/* UART16550 Registers */
+#define UARTTX			0x0
+#define UARTRX			0x0
+#define UARTDLL			0x0
+#define UARTIER			0x1
+#define UARTDLLM		0x1
+#define UARTFCR			0x2
+#define UARTLCR			0x3
+#define UARTLSR			0x5
+#define UARTMCR                 0x4
+
+/* FIFO Control Register bits */
+#define UARTFCR_FIFOMD_16450	(0 << 6)
+#define UARTFCR_FIFOMD_16550	(1 << 6)
+#define UARTFCR_RXTRIG_1	(0 << 6)
+#define UARTFCR_RXTRIG_4	(1 << 6)
+#define UARTFCR_RXTRIG_8	(2 << 6)
+#define UARTFCR_RXTRIG_16	(3 << 6)
+#define UARTFCR_TXTRIG_1	(0 << 4)
+#define UARTFCR_TXTRIG_4	(1 << 4)
+#define UARTFCR_TXTRIG_8	(2 << 4)
+#define UARTFCR_TXTRIG_16	(3 << 4)
+#define UARTFCR_DMAEN		(1 << 3)	/* Enable DMA mode */
+#define UARTFCR_TXCLR		(1 << 2)	/* Clear contents of Tx FIFO */
+#define UARTFCR_RXCLR		(1 << 1)	/* Clear contents of Rx FIFO */
+#define UARTFCR_FIFOEN		(1 << 0)	/* Enable the Tx/Rx FIFO */
+#define UARTFCR_64FIFO          (1 << 5)
+
+/* Line Control Register bits */
+#define UARTLCR_DLAB		(1 << 7)	/* Divisor Latch Access */
+#define UARTLCR_SETB		(1 << 6)	/* Set BREAK Condition */
+#define UARTLCR_SETP		(1 << 5)	/* Set Parity to LCR[4] */
+#define UARTLCR_EVEN		(1 << 4)	/* Even Parity Format */
+#define UARTLCR_PAR		(1 << 3)	/* Parity */
+#define UARTLCR_STOP		(1 << 2)	/* Stop Bit */
+#define UARTLCR_WORDSZ_5	0		/* Word Length of 5 */
+#define UARTLCR_WORDSZ_6	1		/* Word Length of 6 */
+#define UARTLCR_WORDSZ_7	2		/* Word Length of 7 */
+#define UARTLCR_WORDSZ_8	3		/* Word Length of 8 */
+
+/* Line Status Register bits */
+#define UARTLSR_RXFIFOEMT	(1 << 9)	/* Rx Fifo Empty */
+#define UARTLSR_TXFIFOFULL	(1 << 8)	/* Tx Fifo Full */
+#define UARTLSR_RXFIFOERR	(1 << 7)	/* Rx Fifo Error */
+#define UARTLSR_TEMT		(1 << 6)	/* Tx Shift Register Empty */
+#define UARTLSR_THRE		(1 << 5)	/* Tx Holding Register Empty */
+#define UARTLSR_BRK		(1 << 4)	/* Break Condition Detected */
+#define UARTLSR_FERR		(1 << 3)	/* Framing Error */
+#define UARTLSR_PERR		(1 << 3)	/* Parity Error */
+#define UARTLSR_OVRF		(1 << 2)	/* Rx Overrun Error */
+#define UARTLSR_RDR		(1 << 2)	/* Rx Data Ready */
+
+#define CONSOLE_T_16550_BASE	CONSOLE_T_BASE
+
+	/*
+	 * "core" functions are low-level implementations that don't require
+	 * writable memory and are thus safe to call in BL1 crash context.
+	 */
+	.globl nxp_console_16550_core_init
+	.globl nxp_console_16550_core_putc
+	.globl nxp_console_16550_core_getc
+	.globl nxp_console_16550_core_flush
+
+	.globl console_16550_putc
+	.globl console_16550_getc
+	.globl console_16550_flush
+
+	/* -----------------------------------------------
+	 * int nxp_console_16550_core_init(uintptr_t base_addr,
+	 * unsigned int uart_clk, unsigned int baud_rate)
+	 * Function to initialize the console without a
+	 * C Runtime to print debug information. This
+	 * function will be accessed by console_init and
+	 * crash reporting.
+	 * In: x0 - console base address
+	 *     w1 - Uart clock in Hz
+	 *     w2 - Baud rate
+	 * Out: return 1 on success, 0 on error
+	 * Clobber list : x1, x2, x3
+	 * -----------------------------------------------
+	 */
+func nxp_console_16550_core_init
+	/* Check the input base address */
+	cbz	x0, init_fail
+	/* Check baud rate and uart clock for sanity */
+	cbz	w1, init_fail
+	cbz	w2, init_fail
+
+	/* Program the baudrate */
+	/* Divisor =  Uart clock / (16 * baudrate) */
+	lsl	w2, w2, #4
+	udiv	w2, w1, w2
+	and	w1, w2, #0xff		/* w1 = DLL */
+	lsr	w2, w2, #8
+	and	w2, w2, #0xff		/* w2 = DLLM */
+	ldrb	w3, [x0, #UARTLCR]
+	orr	w3, w3, #UARTLCR_DLAB
+	strb	w3, [x0, #UARTLCR]	/* enable DLL, DLLM programming */
+	strb	w1, [x0, #UARTDLL]	/* program DLL */
+	strb	w2, [x0, #UARTDLLM]	/* program DLLM */
+	mov	w2, #~UARTLCR_DLAB
+	and	w3, w3, w2
+	strb	w3, [x0, #UARTLCR]	/* disable DLL, DLLM programming */
+
+	/* 8n1 */
+	mov	w3, #3
+	strb	w3, [x0, #UARTLCR]
+	/* no interrupt */
+	mov	w3, #0
+	strb	w3, [x0, #UARTIER]
+	/* enable fifo, DMA */
+	mov	w3, #(UARTFCR_FIFOEN |UARTFCR_TXCLR | UARTFCR_RXCLR)
+	strb	w3, [x0, #UARTFCR]
+	/* DTR + RTS */
+	mov	w3, #3
+	str	w3, [x0, #UARTMCR]
+	mov	w0, #1
+	ret
+init_fail:
+	mov	w0, #0
+	ret
+endfunc nxp_console_16550_core_init
+
+	.globl nxp_console_16550_register
+
+	/* -----------------------------------------------
+	 * int nxp_console_16550_register(uintptr_t baseaddr,
+	 *     uint32_t clock, uint32_t baud,
+	 *     console_t *console);
+	 * Function to initialize and register a new 16550
+	 * console. Storage passed in for the console struct
+	 * *must* be persistent (i.e. not from the stack).
+	 * If w1 (UART clock) is 0, initialisation will be
+	 * skipped, relying on previous code to have done
+	 * this already. w2 is ignored then as well.
+	 * In: x0 - UART register base address
+	 *     w1 - UART clock in Hz
+	 *     w2 - Baud rate (ignored if w1 is 0)
+	 *     x3 - pointer to empty console_t struct
+	 * Out: return 1 on success, 0 on error
+	 * Clobber list : x0, x1, x2, x6, x7, x14
+	 * -----------------------------------------------
+	 */
+func nxp_console_16550_register
+	mov	x7, x30
+	mov	x6, x3
+	cbz	x6, register_fail
+	str	x0, [x6, #CONSOLE_T_16550_BASE]
+
+	/* A clock rate of zero means to skip the initialisation. */
+	cbz	w1, register_16550
+
+	bl	nxp_console_16550_core_init
+	cbz	x0, register_fail
+
+register_16550:
+	mov	x0, x6
+	mov	x30, x7
+	finish_console_register 16550 putc=1, getc=1, flush=1
+
+register_fail:
+	ret	x7
+endfunc nxp_console_16550_register
+
+	/* --------------------------------------------------------
+	 * int console_16550_core_putc(int c, uintptr_t base_addr)
+	 * Function to output a character over the console. It
+	 * returns the character printed on success or -1 on error.
+	 * In : w0 - character to be printed
+	 *      x1 - console base address
+	 * Out : return -1 on error else return character.
+	 * Clobber list : x2
+	 * --------------------------------------------------------
+	 */
+func nxp_console_16550_core_putc
+#if ENABLE_ASSERTIONS
+	cmp	x1, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+
+	/* Prepend '\r' to '\n' */
+	cmp	w0, #'\n'
+	b.ne	2f
+	/* Check if the transmit FIFO is full */
+1:	ldrb	w2, [x1, #UARTLSR]
+	and	w2, w2, #UARTLSR_THRE        /* #(UARTLSR_TEMT | UARTLSR_THRE)*/
+	cmp	w2, #(UARTLSR_THRE)
+	b.ne	1b
+	mov	w2, #'\r'
+	strb	w2, [x1, #UARTTX]
+	ldrb	w2, [x1, #UARTFCR]
+	orr	w2, w2, #UARTFCR_TXCLR
+
+	/* Check if the transmit FIFO is full */
+2:	ldrb	w2, [x1, #UARTLSR]
+	and	w2, w2, #(UARTLSR_THRE)
+	cmp	w2, #(UARTLSR_THRE)
+	b.ne	2b
+	strb	w0, [x1, #UARTTX]
+	ret
+endfunc nxp_console_16550_core_putc
+
+	/* --------------------------------------------------------
+	 * int console_16550_putc(int c, console_t *console)
+	 * Function to output a character over the console. It
+	 * returns the character printed on success or -1 on error.
+	 * In : w0 - character to be printed
+	 *      x1 - pointer to console_t structure
+	 * Out : return -1 on error else return character.
+	 * Clobber list : x2
+	 * --------------------------------------------------------
+	 */
+func console_16550_putc
+#if ENABLE_ASSERTIONS
+	cmp	x1, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+	ldr	x1, [x1, #CONSOLE_T_16550_BASE]
+	b	nxp_console_16550_core_putc
+endfunc console_16550_putc
+
+	/* ---------------------------------------------
+	 * int console_16550_core_getc(uintptr_t base_addr)
+	 * Function to get a character from the console.
+	 * It returns the character grabbed on success
+	 * or -1 on if no character is available.
+	 * In :  x0 - console base address
+	 * Out : w0 - character if available, else -1
+	 * Clobber list : x0, x1
+	 * ---------------------------------------------
+	 */
+func nxp_console_16550_core_getc
+#if ENABLE_ASSERTIONS
+	cmp	x0, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+
+	/* Check if the receive FIFO is empty */
+1:	ldrb	w1, [x0, #UARTLSR]
+	tbz	w1, #UARTLSR_RDR, 1b
+	ldrb	w0, [x0, #UARTRX]
+	ret
+no_char:
+	mov	w0, #ERROR_NO_PENDING_CHAR
+	ret
+endfunc nxp_console_16550_core_getc
+
+	/* ---------------------------------------------
+	 * int console_16550_getc(console_t *console)
+	 * Function to get a character from the console.
+	 * It returns the character grabbed on success
+	 * or -1 on if no character is available.
+	 * In :  x0 - pointer to console_t structure
+	 * Out : w0 - character if available, else -1
+	 * Clobber list : x0, x1
+	 * ---------------------------------------------
+	 */
+func console_16550_getc
+#if ENABLE_ASSERTIONS
+	cmp	x1, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+	ldr	x0, [x0, #CONSOLE_T_16550_BASE]
+	b	nxp_console_16550_core_getc
+endfunc console_16550_getc
+
+	/* ---------------------------------------------
+	 * int console_16550_core_flush(uintptr_t base_addr)
+	 * Function to force a write of all buffered
+	 * data that hasn't been output.
+	 * In : x0 - console base address
+	 * Out : return -1 on error else return 0.
+	 * Clobber list : x0, x1
+	 * ---------------------------------------------
+	 */
+func nxp_console_16550_core_flush
+#if ENABLE_ASSERTIONS
+	cmp	x0, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+
+	/* Loop until the transmit FIFO is empty */
+1:	ldrb	w1, [x0, #UARTLSR]
+	and	w1, w1, #(UARTLSR_THRE)
+	cmp	w1, #(UARTLSR_THRE)
+	b.ne	1b
+
+	mov	w0, #0
+	ret
+endfunc nxp_console_16550_core_flush
+
+	/* ---------------------------------------------
+	 * int console_16550_flush(console_t *console)
+	 * Function to force a write of all buffered
+	 * data that hasn't been output.
+	 * In : x0 - pointer to console_t structure
+	 * Out : return -1 on error else return 0.
+	 * Clobber list : x0, x1
+	 * ---------------------------------------------
+	 */
+func console_16550_flush
+#if ENABLE_ASSERTIONS
+	cmp	x0, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+	ldr	x0, [x0, #CONSOLE_T_16550_BASE]
+	b	nxp_console_16550_core_flush
+endfunc console_16550_flush
diff --git a/drivers/nxp/console/console.mk b/drivers/nxp/console/console.mk
new file mode 100644
index 0000000..6174650
--- /dev/null
+++ b/drivers/nxp/console/console.mk
@@ -0,0 +1,46 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the CORE files
+#
+# -----------------------------------------------------------------------------
+
+ifeq (${ADD_CONSOLE},)
+
+ADD_CONSOLE		:= 1
+
+PLAT_INCLUDES		+=	-I$(PLAT_DRIVERS_INCLUDE_PATH)/console
+
+ifeq ($(CONSOLE), NS16550)
+NXP_CONSOLE		:=	NS16550
+
+$(eval $(call add_define_val,NXP_CONSOLE,${NXP_CONSOLE}))
+
+CONSOLE_SOURCES		:=	$(PLAT_DRIVERS_PATH)/console/16550_console.S	\
+				$(PLAT_DRIVERS_PATH)/console/console_16550.c
+else
+ifeq ($(CONSOLE), PL011)
+CONSOLE_SOURCES		:=	drivers/arm/pl011/aarch64/pl011_console.S	\
+				${PLAT_DRIVERS_PATH}/console/console_pl011.c
+else
+	$(error -> CONSOLE not set!)
+endif
+endif
+
+ifeq (${BL_COMM_CONSOLE_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${CONSOLE_SOURCES}
+else
+ifeq (${BL2_CONSOLE_NEEDED},yes)
+BL2_SOURCES		+= ${CONSOLE_SOURCES}
+endif
+ifeq (${BL31_CONSOLE_NEEDED},yes)
+BL31_SOURCES		+= ${CONSOLE_SOURCES}
+endif
+endif
+endif
+# -----------------------------------------------------------------------------
diff --git a/drivers/nxp/console/console_16550.c b/drivers/nxp/console/console_16550.c
new file mode 100644
index 0000000..fa5c5bb
--- /dev/null
+++ b/drivers/nxp/console/console_16550.c
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <dcfg.h>
+#include <lib/utils.h>
+#include <plat_console.h>
+
+/*
+ * Perform Arm specific early platform setup. At this moment we only initialize
+ * the console and the memory layout.
+ */
+void plat_console_init(uintptr_t nxp_console_addr, uint32_t uart_clk_div,
+			uint32_t baud)
+{
+	struct sysinfo sys;
+	static console_t nxp_console;
+
+	zeromem(&sys, sizeof(sys));
+	if (get_clocks(&sys)) {
+		ERROR("System clocks are not set\n");
+		panic();
+	}
+	nxp_console_16550_register(nxp_console_addr,
+			      (sys.freq_platform/uart_clk_div),
+			       baud, &nxp_console);
+}
diff --git a/drivers/nxp/console/console_pl011.c b/drivers/nxp/console/console_pl011.c
new file mode 100644
index 0000000..93f2fc2
--- /dev/null
+++ b/drivers/nxp/console/console_pl011.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <dcfg.h>
+#include <drivers/arm/pl011.h>
+#include <drivers/console.h>
+#include <lib/utils.h>
+
+/*
+ * Perform Arm specific early platform setup. At this moment we only initialize
+ * the console and the memory layout.
+ */
+void plat_console_init(uintptr_t nxp_console_addr, uint32_t uart_clk_div,
+			uint32_t baud)
+{
+	struct sysinfo sys;
+	static console_t nxp_console;
+
+	zeromem(&sys, sizeof(sys));
+	if (get_clocks(&sys)) {
+		ERROR("System clocks are not set\n");
+		panic();
+	}
+
+	console_pl011_register(nxp_console_addr,
+			      (sys.freq_platform/uart_clk_div),
+			       baud, &nxp_console);
+}
diff --git a/drivers/nxp/crypto/caam/caam.mk b/drivers/nxp/crypto/caam/caam.mk
new file mode 100644
index 0000000..f929f53
--- /dev/null
+++ b/drivers/nxp/crypto/caam/caam.mk
@@ -0,0 +1,27 @@
+#
+# Copyright 2020-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+ifeq (${ADD_CAAM},)
+
+ADD_CAAM		:= 1
+
+CAAM_DRIVER_SOURCES	+=  $(wildcard $(PLAT_DRIVERS_PATH)/crypto/caam/src/*.c)
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/crypto/caam
+
+ifeq (${BL_COMM_CRYPTO_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${CAAM_DRIVER_SOURCES}
+else
+ifeq (${BL2_CRYPTO_NEEDED},yes)
+BL2_SOURCES		+= ${CAAM_DRIVER_SOURCES}
+endif
+ifeq (${BL31_CRYPTO_NEEDED},yes)
+BL31_SOURCES		+= ${CAAM_DRIVER_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/nxp/crypto/caam/src/auth/auth.mk b/drivers/nxp/crypto/caam/src/auth/auth.mk
new file mode 100644
index 0000000..d1f8c75
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/auth/auth.mk
@@ -0,0 +1,12 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+SEC_DRIVERS_PATH	:=	drivers/nxp/crypto/caam
+
+ifeq (${TRUSTED_BOARD_BOOT},1)
+AUTH_SOURCES +=  $(wildcard $(SEC_DRIVERS_PATH)/src/auth/*.c)
+endif
diff --git a/drivers/nxp/crypto/caam/src/auth/hash.c b/drivers/nxp/crypto/caam/src/auth/hash.c
new file mode 100644
index 0000000..1665df1
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/auth/hash.c
@@ -0,0 +1,155 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include <drivers/auth/crypto_mod.h>
+
+#include "hash.h"
+#include "jobdesc.h"
+#include "sec_hw_specific.h"
+
+/* Since no Allocator is available . Taking a global static ctx.
+ * This would mean that only one active ctx can be there at a time.
+ */
+
+static struct hash_ctx glbl_ctx;
+
+static void hash_done(uint32_t *desc, uint32_t status, void *arg,
+		      void *job_ring)
+{
+	INFO("Hash Desc SUCCESS with status %x\n", status);
+}
+
+/***************************************************************************
+ * Function	: hash_init
+ * Arguments	: ctx - SHA context
+ * Return	: init,
+ * Description	: This function initializes the context for SHA calculation
+ ***************************************************************************/
+int hash_init(enum hash_algo algo, void **ctx)
+{
+	if (glbl_ctx.active == false) {
+		memset(&glbl_ctx, 0, sizeof(struct hash_ctx));
+		glbl_ctx.active = true;
+		glbl_ctx.algo = algo;
+		*ctx = &glbl_ctx;
+		return 0;
+	} else {
+		return -1;
+	}
+}
+
+/***************************************************************************
+ * Function	: hash_update
+ * Arguments	: ctx - SHA context
+ *		  buffer - Data
+ *		  length - Length
+ * Return	: -1 on error
+ *		  0 on SUCCESS
+ * Description	: This function creates SG entry of the data provided
+ ***************************************************************************/
+int hash_update(enum hash_algo algo, void *context, void *data_ptr,
+		unsigned int data_len)
+{
+	struct hash_ctx *ctx = context;
+	/* MAX_SG would be MAX_SG_ENTRIES + key + hdr + sg table */
+	if (ctx->sg_num >= MAX_SG) {
+		ERROR("Reached limit for calling %s\n", __func__);
+		ctx->active = false;
+		return -EINVAL;
+
+	}
+
+	if (ctx->algo != algo) {
+		ERROR("ctx for algo not correct\n");
+		ctx->active = false;
+		return -EINVAL;
+	}
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)data_ptr, data_len);
+	dmbsy();
+#endif
+
+#ifdef CONFIG_PHYS_64BIT
+	sec_out32(&ctx->sg_tbl[ctx->sg_num].addr_hi,
+		  (uint32_t) ((uintptr_t) data_ptr >> 32));
+#else
+	sec_out32(&ctx->sg_tbl[ctx->sg_num].addr_hi, 0x0);
+#endif
+	sec_out32(&ctx->sg_tbl[ctx->sg_num].addr_lo, (uintptr_t) data_ptr);
+
+	sec_out32(&ctx->sg_tbl[ctx->sg_num].len_flag,
+		  (data_len & SG_ENTRY_LENGTH_MASK));
+
+	ctx->sg_num++;
+
+	ctx->len += data_len;
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function	: hash_final
+ * Arguments	: ctx - SHA context
+ * Return	: SUCCESS or FAILURE
+ * Description	: This function sets the final bit and enqueues the decriptor
+ ***************************************************************************/
+int hash_final(enum hash_algo algo, void *context, void *hash_ptr,
+	       unsigned int hash_len)
+{
+	int ret = 0;
+	struct hash_ctx *ctx = context;
+	uint32_t final = 0U;
+
+	struct job_descriptor jobdesc __aligned(CACHE_WRITEBACK_GRANULE);
+
+	jobdesc.arg = NULL;
+	jobdesc.callback = hash_done;
+
+	if (ctx->algo != algo) {
+		ERROR("ctx for algo not correct\n");
+		ctx->active = false;
+		return -EINVAL;
+	}
+
+	final = sec_in32(&ctx->sg_tbl[ctx->sg_num - 1].len_flag) |
+	    SG_ENTRY_FINAL_BIT;
+	sec_out32(&ctx->sg_tbl[ctx->sg_num - 1].len_flag, final);
+
+	dsb();
+
+	/* create the hw_rng descriptor */
+	cnstr_hash_jobdesc(jobdesc.desc, (uint8_t *) ctx->sg_tbl,
+			   ctx->len, hash_ptr);
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)ctx->sg_tbl,
+			   (sizeof(struct sg_entry) * MAX_SG));
+	inv_dcache_range((uintptr_t)hash_ptr, hash_len);
+
+	dmbsy();
+#endif
+
+	/* Finally, generate the requested random data bytes */
+	ret = run_descriptor_jr(&jobdesc);
+	if (ret != 0) {
+		ERROR("Error in running descriptor\n");
+		ret = -1;
+	}
+	ctx->active = false;
+	return ret;
+}
diff --git a/drivers/nxp/crypto/caam/src/auth/nxp_crypto.c b/drivers/nxp/crypto/caam/src/auth/nxp_crypto.c
new file mode 100644
index 0000000..646e981
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/auth/nxp_crypto.c
@@ -0,0 +1,123 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stddef.h>
+#include <string.h>
+
+#include "caam.h"
+#include <common/debug.h>
+#include <drivers/auth/crypto_mod.h>
+
+#include "hash.h"
+#include "rsa.h"
+
+#define LIB_NAME		"NXP crypto"
+
+/*
+ * Initialize the library and export the descriptor
+ */
+static void init(void)
+{
+	/* Initialize NXP crypto library`:*/
+	NOTICE("Initializing & configuring SEC block.\n");
+
+	if (config_sec_block() < 0) {
+		ERROR("Init & config failure for caam.\n");
+	}
+}
+
+/*
+ * Verify a signature.
+ *
+ * For IMG_PLAT - data points to a PKCS#1.5 encoded HASH
+ * sig_alg will be RSA or ECC
+ * Parameters are passed using the DER encoding format following the ASN.1
+ * structures detailed above.
+ */
+static int verify_signature(void *data_ptr, unsigned int data_len,
+			    void *sig_ptr, unsigned int sig_len,
+			    void *sign_alg, unsigned int sig_alg_len,
+			    void *pk_ptr, unsigned int pk_len)
+{
+	int ret = CRYPTO_SUCCESS;
+
+	enum sig_alg alg = *(enum sig_alg *)sign_alg;
+
+	switch (alg) {
+	case RSA:
+		NOTICE("Verifying RSA\n");
+		ret = rsa_verify_signature(data_ptr, data_len, sig_ptr, sig_len,
+					   pk_ptr, pk_len);
+		break;
+	case ECC:
+	default:
+		ret = CRYPTO_ERR_SIGNATURE;
+		break;
+	}
+
+	if (ret != 0) {
+		ERROR("RSA verification Failed\n");
+	}
+	return ret;
+
+}
+
+/*
+ * Match a hash
+ *
+ * Digest info is passed as a table of SHA-26 hashes and digest_info_len
+ * is number of entries in the table
+ * This implementation is very specific to the CSF header parser ROTPK
+ * comparison.
+ */
+static int verify_hash(void *data_ptr, unsigned int data_len,
+		       void *digest_info_ptr, unsigned int digest_info_len)
+{
+	void *ctx = NULL;
+	int i = 0, ret = 0;
+	enum hash_algo algo = SHA256;
+	uint8_t hash[SHA256_BYTES] __aligned(CACHE_WRITEBACK_GRANULE) = {0};
+	uint32_t digest_size = SHA256_BYTES;
+	uint8_t *hash_tbl = digest_info_ptr;
+
+	NOTICE("Verifying hash\n");
+	ret = hash_init(algo, &ctx);
+	if (ret != 0) {
+		return CRYPTO_ERR_HASH;
+	}
+
+	/* Update hash with that of SRK table */
+	ret = hash_update(algo, ctx, data_ptr, data_len);
+	if (ret != 0) {
+		return CRYPTO_ERR_HASH;
+	}
+
+	/* Copy hash at destination buffer */
+	ret = hash_final(algo, ctx, hash, digest_size);
+	if (ret != 0) {
+		return CRYPTO_ERR_HASH;
+	}
+
+	VERBOSE("%s Calculated hash\n", __func__);
+	for (i = 0; i < SHA256_BYTES/4; i++) {
+		VERBOSE("%x\n", *((uint32_t *)hash + i));
+	}
+
+	for (i = 0; i < digest_info_len; i++) {
+		if (memcmp(hash, (hash_tbl + (i * digest_size)),
+			   digest_size) == 0) {
+			return CRYPTO_SUCCESS;
+		}
+	}
+
+	return CRYPTO_ERR_HASH;
+}
+
+/*
+ * Register crypto library descriptor
+ */
+REGISTER_CRYPTO_LIB(LIB_NAME, init, verify_signature, verify_hash, NULL);
diff --git a/drivers/nxp/crypto/caam/src/auth/rsa.c b/drivers/nxp/crypto/caam/src/auth/rsa.c
new file mode 100644
index 0000000..0c44462
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/auth/rsa.c
@@ -0,0 +1,179 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include <drivers/auth/crypto_mod.h>
+
+#include "jobdesc.h"
+#include "rsa.h"
+#include "sec_hw_specific.h"
+
+/* This array contains DER value for SHA-256 */
+static const uint8_t hash_identifier[] = {
+	0x30, 0x31, 0x30, 0x0d, 0x06, 0x09, 0x60,
+	0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00,
+	0x04, 0x20
+};
+
+static void rsa_done(uint32_t *desc, uint32_t status, void *arg,
+		     void *job_ring)
+{
+	INFO("RSA Desc SUCCESS with status %x\n", status);
+}
+
+static int rsa_public_verif_sec(uint8_t *sign, uint8_t *to,
+				uint8_t *rsa_pub_key, uint32_t klen)
+{
+	int ret = 0;
+	struct rsa_context ctx __aligned(CACHE_WRITEBACK_GRANULE);
+	struct job_descriptor jobdesc __aligned(CACHE_WRITEBACK_GRANULE);
+
+	jobdesc.arg = NULL;
+	jobdesc.callback = rsa_done;
+
+	memset(&ctx, 0, sizeof(struct rsa_context));
+
+	ctx.pkin.a = sign;
+	ctx.pkin.a_siz = klen;
+	ctx.pkin.n = rsa_pub_key;
+	ctx.pkin.n_siz = klen;
+	ctx.pkin.e = rsa_pub_key + klen;
+	ctx.pkin.e_siz = klen;
+
+	cnstr_jobdesc_pkha_rsaexp(jobdesc.desc, &ctx.pkin, to, klen);
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)sign, klen);
+	flush_dcache_range((uintptr_t)rsa_pub_key, 2 * klen);
+	flush_dcache_range((uintptr_t)&ctx.pkin, sizeof(ctx.pkin));
+	inv_dcache_range((uintptr_t)to, klen);
+
+	dmbsy();
+	dsbsy();
+	isb();
+#endif
+
+	/* Finally, generate the requested random data bytes */
+	ret = run_descriptor_jr(&jobdesc);
+	if (ret != 0) {
+		ERROR("Error in running descriptor\n");
+		ret = -1;
+	}
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	inv_dcache_range((uintptr_t)to, klen);
+	dmbsy();
+	dsbsy();
+	isb();
+#endif
+	return ret;
+}
+
+/*
+ * Construct encoded hash EM' wrt PKCSv1.5. This function calculates the
+ * pointers for padding, DER value and hash. And finally, constructs EM'
+ * which includes hash of complete CSF header and ESBC image. If SG flag
+ * is on, hash of SG table and entries is also included.
+ */
+static int construct_img_encoded_hash_second(uint8_t *hash, uint8_t hash_len,
+					     uint8_t *encoded_hash_second,
+					     unsigned int key_len)
+{
+	/*
+	 * RSA PKCSv1.5 encoding format for encoded message is below
+	 * EM = 0x0 || 0x1 || PS || 0x0 || DER || Hash
+	 * PS is Padding String
+	 * DER is DER value for SHA-256
+	 * Hash is SHA-256 hash
+	 * *********************************************************
+	 * representative points to first byte of EM initially and is
+	 * filled with 0x0
+	 * representative is incremented by 1 and second byte is filled
+	 * with 0x1
+	 * padding points to third byte of EM
+	 * digest points to full length of EM - 32 bytes
+	 * hash_id (DER value) points to 19 bytes before pDigest
+	 * separator is one byte which separates padding and DER
+	 */
+
+	unsigned int len;
+	uint8_t *representative;
+	uint8_t *padding, *digest;
+	uint8_t *hash_id, *separator;
+	int i;
+	int ret = 0;
+
+	if (hash_len != SHA256_BYTES) {
+		return -1;
+	}
+
+	/* Key length = Modulus length */
+	len = (key_len / 2U) - 1U;
+	representative = encoded_hash_second;
+	representative[0] = 0U;
+	representative[1] = 1U;	/* block type 1 */
+
+	padding = &representative[2];
+	digest = &representative[1] + len - 32;
+	hash_id = digest - sizeof(hash_identifier);
+	separator = hash_id - 1;
+
+	/* fill padding area pointed by padding with 0xff */
+	memset(padding, 0xff, separator - padding);
+
+	/* fill byte pointed by separator */
+	*separator = 0U;
+
+	/* fill SHA-256 DER value  pointed by HashId */
+	memcpy(hash_id, hash_identifier, sizeof(hash_identifier));
+
+	/* fill hash pointed by Digest */
+	for (i = 0; i < SHA256_BYTES; i++) {
+		digest[i] = hash[i];
+	}
+
+	return ret;
+}
+
+int rsa_verify_signature(void *hash_ptr, unsigned int hash_len,
+			 void *sig_ptr, unsigned int sig_len,
+			 void *pk_ptr, unsigned int pk_len)
+{
+	uint8_t img_encoded_hash_second[RSA_4K_KEY_SZ_BYTES];
+	uint8_t encoded_hash[RSA_4K_KEY_SZ_BYTES] __aligned(CACHE_WRITEBACK_GRANULE);
+	int ret = 0;
+
+	ret = construct_img_encoded_hash_second(hash_ptr, hash_len,
+						img_encoded_hash_second,
+						pk_len);
+	if (ret != 0) {
+		ERROR("Encoded Hash Failure\n");
+		return CRYPTO_ERR_SIGNATURE;
+	}
+
+	ret = rsa_public_verif_sec(sig_ptr, encoded_hash, pk_ptr, pk_len / 2);
+	if (ret != 0) {
+		ERROR("RSA signature Failure\n");
+		return CRYPTO_ERR_SIGNATURE;
+	}
+
+	ret = memcmp(img_encoded_hash_second, encoded_hash, sig_len);
+	if (ret != 0) {
+		ERROR("Comparison Failure\n");
+		return CRYPTO_ERR_SIGNATURE;
+	}
+
+	return CRYPTO_SUCCESS;
+}
diff --git a/drivers/nxp/crypto/caam/src/caam.c b/drivers/nxp/crypto/caam/src/caam.c
new file mode 100644
index 0000000..e594f7b
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/caam.c
@@ -0,0 +1,339 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "sec_hw_specific.h"
+
+static uintptr_t g_nxp_caam_addr;
+static void *job_ring;
+
+uintptr_t get_caam_addr(void)
+{
+	if (g_nxp_caam_addr == 0) {
+		ERROR("Sec Init is not done.\n");
+		panic();
+	}
+	return g_nxp_caam_addr;
+}
+
+/* This function sets the TZ bit for the Job ring number passed as @num */
+static void config_tz(int num)
+{
+	uint32_t jricid;
+
+	/* Setting TZ bit of job ring */
+	switch (num) {
+	case 0:
+		jricid = sec_in32(g_nxp_caam_addr + SEC_REG_JR0ICIDR_MS_OFFSET);
+		sec_out32(g_nxp_caam_addr + SEC_REG_JR0ICIDR_MS_OFFSET,
+			  jricid | JRICID_MS_TZ);
+		break;
+	case 1:
+		jricid = sec_in32(g_nxp_caam_addr + SEC_REG_JR1ICIDR_MS_OFFSET);
+		sec_out32(g_nxp_caam_addr + SEC_REG_JR1ICIDR_MS_OFFSET,
+			  jricid | JRICID_MS_TZ);
+		break;
+	case 2:
+		jricid = sec_in32(g_nxp_caam_addr + SEC_REG_JR2ICIDR_MS_OFFSET);
+		sec_out32(g_nxp_caam_addr + SEC_REG_JR2ICIDR_MS_OFFSET,
+			  jricid | JRICID_MS_TZ);
+		break;
+	case 3:
+		jricid = sec_in32(g_nxp_caam_addr + SEC_REG_JR3ICIDR_MS_OFFSET);
+		sec_out32(g_nxp_caam_addr + SEC_REG_JR3ICIDR_MS_OFFSET,
+			  jricid | JRICID_MS_TZ);
+		break;
+	default:
+		break;
+	}
+}
+
+/* This function checks if Virtualization is enabled for JR and
+ * accordingly sets the bot for starting JR<num> in JRSTARTR register
+ */
+static inline void start_jr(int num)
+{
+	uint32_t ctpr = sec_in32((g_nxp_caam_addr + SEC_REG_CTPR_MS_OFFSET));
+	uint32_t tmp = sec_in32((g_nxp_caam_addr + SEC_REG_JRSTARTR_OFFSET));
+	uint32_t scfgr = sec_in32((g_nxp_caam_addr + SEC_REG_SCFGR_OFFSET));
+	bool start = false;
+
+	if ((ctpr & CTPR_VIRT_EN_INC) != 0U) {
+		if (((ctpr & CTPR_VIRT_EN_POR) != 0U) ||
+		    ((scfgr & SCFGR_VIRT_EN) != 0U)) {
+			start = true;
+		}
+	} else {
+		if ((ctpr & CTPR_VIRT_EN_POR) != 0U) {
+			start = true;
+		}
+	}
+
+	if (start == true) {
+		switch (num) {
+		case 0:
+			tmp |= JRSTARTR_STARTJR0;
+			break;
+		case 1:
+			tmp |= JRSTARTR_STARTJR1;
+			break;
+		case 2:
+			tmp |= JRSTARTR_STARTJR2;
+			break;
+		case 3:
+			tmp |= JRSTARTR_STARTJR3;
+			break;
+		default:
+			break;
+		}
+	}
+	sec_out32((g_nxp_caam_addr + SEC_REG_JRSTARTR_OFFSET), tmp);
+}
+
+/* This functions configures the Job Ring
+ * JR3 is reserved for use by Secure world
+ */
+static int configure_jr(int num)
+{
+	int ret;
+	void *reg_base_addr;
+
+	switch (num) {
+	case 0:
+		reg_base_addr = (void *)(g_nxp_caam_addr + CAAM_JR0_OFFSET);
+		break;
+	case 1:
+		reg_base_addr = (void *)(g_nxp_caam_addr + CAAM_JR1_OFFSET);
+		break;
+	case 2:
+		reg_base_addr = (void *)(g_nxp_caam_addr + CAAM_JR2_OFFSET);
+		break;
+	case 3:
+		reg_base_addr = (void *)(g_nxp_caam_addr + CAAM_JR3_OFFSET);
+		break;
+	default:
+		break;
+	}
+
+	/* Initialize the JR library */
+	ret = sec_jr_lib_init();
+	if (ret != 0) {
+		ERROR("Error in sec_jr_lib_init");
+		return -1;
+	}
+
+	start_jr(num);
+
+	/* Do HW configuration of the JR */
+	job_ring = init_job_ring(SEC_NOTIFICATION_TYPE_POLL, 0, 0,
+				 reg_base_addr, 0);
+
+	if (job_ring == NULL) {
+		ERROR("Error in init_job_ring");
+		return -1;
+	}
+
+	return ret;
+}
+
+/* TBD - Configures and locks the ICID values for various JR */
+static inline void configure_icid(void)
+{
+}
+
+/* TBD configures the TZ settings of RTIC */
+static inline void configure_rtic(void)
+{
+}
+
+int sec_init(uintptr_t nxp_caam_addr)
+{
+	g_nxp_caam_addr = nxp_caam_addr;
+	return config_sec_block();
+}
+
+/* This function configure SEC block:
+ * - It does basic parameter setting
+ * - Configures the default Job ring assigned to TZ /secure world
+ * - Instantiates the RNG
+ */
+int config_sec_block(void)
+{
+	int ret = 0;
+	uint32_t mcfgr;
+
+	if (g_nxp_caam_addr == 0) {
+		ERROR("Sec Init is not done.\n");
+		return -1;
+	} else if (job_ring != NULL) {
+		NOTICE("Sec is already initialized and configured.\n");
+		return ret;
+	}
+
+	mcfgr = sec_in32(g_nxp_caam_addr + SEC_REG_MCFGR_OFFSET);
+
+	/* Modify CAAM Read/Write attributes
+	 * AXI Write - Cacheable, WB and WA
+	 * AXI Read - Cacheable, RA
+	 */
+#if defined(CONFIG_ARCH_LS2080A) || defined(CONFIG_ARCH_LS2088A)
+	mcfgr = (mcfgr & ~MCFGR_AWCACHE_MASK) | (0xb << MCFGR_AWCACHE_SHIFT);
+	mcfgr = (mcfgr & ~MCFGR_ARCACHE_MASK) | (0x6 << MCFGR_ARCACHE_SHIFT);
+#else
+	mcfgr = (mcfgr & ~MCFGR_AWCACHE_MASK) | (0x2 << MCFGR_AWCACHE_SHIFT);
+#endif
+
+	/* Set PS bit to 1 */
+#ifdef CONFIG_PHYS_64BIT
+	mcfgr |= (1 << MCFGR_PS_SHIFT);
+#endif
+	sec_out32(g_nxp_caam_addr + SEC_REG_MCFGR_OFFSET, mcfgr);
+
+	/* Asssign ICID to all Job rings and lock them for usage */
+	configure_icid();
+
+	/* Configure the RTIC */
+	configure_rtic();
+
+	/* Configure the default JR for usage */
+	ret = configure_jr(DEFAULT_JR);
+	if (ret != 0) {
+		ERROR("\nFSL_JR: configuration failure\n");
+		return -1;
+	}
+	/* Do TZ configuration of default JR for sec firmware */
+	config_tz(DEFAULT_JR);
+
+#ifdef CONFIG_RNG_INIT
+	/* Instantiate the RNG */
+	ret = hw_rng_instantiate();
+	if (ret != 0) {
+		ERROR("\nRNG Instantiation failure\n");
+		return -1;
+	}
+#endif
+
+	return ret;
+}
+
+/* This function is used for sumbitting job to the Job Ring
+ * [param] [in] - jobdesc to be submitted
+ * Return - -1 in case of error and 0 in case of SUCCESS
+ */
+int run_descriptor_jr(struct job_descriptor *jobdesc)
+{
+	int i = 0, ret = 0;
+	uint32_t *desc_addr = jobdesc->desc;
+	uint32_t desc_len = desc_length(jobdesc->desc);
+	uint32_t desc_word;
+
+	for (i = 0; i < desc_len; i++) {
+		desc_word = desc_addr[i];
+		VERBOSE("%x\n", desc_word);
+		sec_out32((uint32_t *)&desc_addr[i], desc_word);
+	}
+	dsb();
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)desc_addr, desc_len * 4);
+	dmbsy();
+	dsbsy();
+	isb();
+#endif
+
+	ret = enq_jr_desc(job_ring, jobdesc);
+	if (ret == 0) {
+		VERBOSE("JR enqueue done...\n");
+	} else {
+		ERROR("Error in Enqueue\n");
+		return ret;
+	}
+
+	VERBOSE("Dequeue in progress");
+
+	ret = dequeue_jr(job_ring, -1);
+	if (ret >= 0) {
+		VERBOSE("Dequeue of %x desc success\n", ret);
+		ret = 0;
+	} else {
+		ERROR("deq_ret %x\n", ret);
+		ret = -1;
+	}
+
+	return ret;
+}
+
+/* this function returns a random number using HW RNG Algo
+ * In case of failure, random number returned is 0
+ * prngWidth = 0 - 32 bit random number
+ * prngWidth > 0 means 64 bit random number
+ */
+unsigned long long get_random(int rngWidth)
+{
+	unsigned long long result = 0;
+	uint8_t rand_byte[64] __aligned(CACHE_WRITEBACK_GRANULE);
+	uint8_t rand_byte_swp[8];
+	int bytes = 0;
+	int i = 0;
+	int ret = 0;
+
+#ifdef CAAM_TEST
+	rand_byte[0] = U(0x12);
+	rand_byte[1] = U(0x34);
+	rand_byte[2] = U(0x56);
+	rand_byte[3] = U(0x78);
+	rand_byte[4] = U(0x9a);
+	rand_byte[5] = U(0xbc);
+	rand_byte[6] = U(0xde);
+	rand_byte[7] = U(0xf1);
+#endif
+
+	if (rngWidth == 0U) {
+		bytes = 4;
+	} else {
+		bytes = 8;
+	}
+
+	memset(rand_byte, 0, 64);
+
+	ret = get_rand_bytes_hw(rand_byte, bytes);
+
+	for (i = 0; i < bytes; i++) {
+		if (ret != 0) {
+			/* Return 0 in case of failure */
+			rand_byte_swp[i] = 0;
+		} else {
+			rand_byte_swp[i] = rand_byte[bytes - i - 1];
+			result = (result << 8) | rand_byte_swp[i];
+		}
+	}
+
+	INFO("result %llx\n", result);
+
+	return result;
+
+} /* _get_RNG() */
+
+unsigned int _get_hw_unq_key(uint64_t hw_key_phy_addr, unsigned int size)
+{
+	int ret = 0;
+	uint8_t *hw_key = (uint8_t *) ptov((phys_addr_t *) hw_key_phy_addr);
+
+	ret = get_hw_unq_key_blob_hw(hw_key, size);
+
+	return ret;
+}
diff --git a/drivers/nxp/crypto/caam/src/hw_key_blob.c b/drivers/nxp/crypto/caam/src/hw_key_blob.c
new file mode 100644
index 0000000..0720695
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/hw_key_blob.c
@@ -0,0 +1,81 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "sec_hw_specific.h"
+
+
+/* Callback function after Instantiation decsriptor is submitted to SEC
+ */
+static void blob_done(uint32_t *desc, uint32_t status, void *arg,
+		      void *job_ring)
+{
+	INFO("Blob Desc SUCCESS with status %x\n", status);
+}
+
+/* @brief Submit descriptor to create blob
+ * @retval 0 on success
+ * @retval -1 on error
+ */
+int get_hw_unq_key_blob_hw(uint8_t *hw_key, int size)
+{
+	int ret = 0;
+	int i = 0;
+
+	uint32_t key_sz = KEY_IDNFR_SZ_BYTES;
+	uint8_t key_data[KEY_IDNFR_SZ_BYTES];
+	uint8_t in_data[16];
+	uint8_t out_data[16 + KEY_BLOB_SIZE + MAC_SIZE];
+	struct job_descriptor desc __aligned(CACHE_WRITEBACK_GRANULE);
+	struct job_descriptor *jobdesc = &desc;
+	uint32_t in_sz = 16U;
+
+	/* Output blob will have 32 bytes key blob in beginning and
+	 * 16 byte HMAC identifier at end of data blob
+	 */
+	uint32_t out_sz = in_sz + KEY_BLOB_SIZE + MAC_SIZE;
+
+	uint32_t operation = CMD_OPERATION | OP_TYPE_ENCAP_PROTOCOL |
+	    OP_PCLID_BLOB | BLOB_PROTO_INFO;
+
+	memset(key_data, 0xff, KEY_IDNFR_SZ_BYTES);
+	memset(in_data, 0x00, in_sz);
+	memset(out_data, 0x00, in_sz);
+
+	jobdesc->arg = NULL;
+	jobdesc->callback = blob_done;
+
+	INFO("\nGenerating Master Key Verification Blob.\n");
+
+	/* Create the hw_rng descriptor */
+	ret = cnstr_hw_encap_blob_jobdesc(jobdesc->desc, key_data, key_sz,
+					  CLASS_2, in_data, in_sz, out_data,
+					  out_sz, operation);
+
+	/* Finally, generate the blob. */
+	ret = run_descriptor_jr(jobdesc);
+	if (ret != 0) {
+		ERROR("Error in running hw unq key blob descriptor\n");
+		return -1;
+	}
+	/* Copying alternate bytes of the Master Key Verification Blob.
+	 */
+	for (i = 0; i < size; i++) {
+		hw_key[i] = out_data[2 * i];
+	}
+
+	return ret;
+}
diff --git a/drivers/nxp/crypto/caam/src/jobdesc.c b/drivers/nxp/crypto/caam/src/jobdesc.c
new file mode 100644
index 0000000..9c235af
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/jobdesc.c
@@ -0,0 +1,236 @@
+/*
+ * Copyright 2017-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "rsa.h"
+#include "sec_hw_specific.h"
+
+
+/* Return Length of desctiptr from first word */
+uint32_t desc_length(uint32_t *desc)
+{
+	return desc[0] & DESC_LEN_MASK;
+}
+
+/*Update start index in first word of descriptor */
+void desc_update_start_index(uint32_t *desc, uint32_t index)
+{
+	desc[0] |= (index << DESC_START_SHIFT);
+}
+
+/* Initialize the descriptor */
+void desc_init(uint32_t *desc)
+{
+	*desc = 0;
+}
+
+/* Add word in the descriptor and increment the length */
+void desc_add_word(uint32_t *desc, uint32_t word)
+{
+	uint32_t len = desc_length(desc);
+
+	/* Add Word at Last */
+	uint32_t *last = desc + len;
+	*last = word;
+
+	/* Increase the length */
+	desc[0] += 1;
+}
+
+/* Add Pointer to the descriptor */
+void desc_add_ptr(uint32_t *desc, phys_addr_t *ptr)
+{
+	uint32_t len = desc_length(desc);
+
+	/* Add Word at Last */
+	phys_addr_t *last = (phys_addr_t *) (desc + len);
+
+#ifdef CONFIG_PHYS_64BIT
+	ptr_addr_t *ptr_addr = (ptr_addr_t *) last;
+
+	ptr_addr->m_halves.high = PHYS_ADDR_HI(ptr);
+	ptr_addr->m_halves.low = PHYS_ADDR_LO(ptr);
+#else
+	*last = ptr;
+#endif
+
+	/* Increase the length */
+	desc[0] += (uint32_t) (sizeof(phys_addr_t) / sizeof(uint32_t));
+}
+
+/* Descriptor to generate Random words */
+int cnstr_rng_jobdesc(uint32_t *desc, uint32_t state_handle,
+		      uint32_t *add_inp, uint32_t add_ip_len,
+		      uint8_t *out_data, uint32_t len)
+{
+	phys_addr_t *phys_addr_out = vtop(out_data);
+
+	/* Current descriptor support only 64K length */
+	if (len > U(0xffff))
+		return -1;
+	/* Additional Input not supported by current descriptor */
+	if (add_ip_len > 0U)
+		return -1;
+
+	VERBOSE("Constructing descriptor\n");
+	desc_init(desc);
+	/* Class1 Alg Operation,RNG Optype, Generate */
+	desc_add_word(desc, U(0xb0800000));
+	desc_add_word(desc, U(0x82500000) | (state_handle << ALG_AAI_SH_SHIFT));
+	desc_add_word(desc, U(0x60340000) | len);
+	desc_add_ptr(desc, phys_addr_out);
+
+	return 0;
+
+}
+
+/* Construct descriptor to instantiate RNG */
+int cnstr_rng_instantiate_jobdesc(uint32_t *desc)
+{
+	desc_init(desc);
+	desc_add_word(desc, U(0xb0800000));
+	/* Class1 Alg Operation,RNG Optype, Instantiate */
+	desc_add_word(desc, U(0x82500004));
+	/* Wait for done */
+	desc_add_word(desc, U(0xa2000001));
+	/*Load to clear written */
+	desc_add_word(desc, U(0x10880004));
+	/*Pri Mode Reg clear */
+	desc_add_word(desc, U(0x00000001));
+	/* Generate secure keys */
+	desc_add_word(desc, U(0x82501000));
+
+	return 0;
+}
+
+/* Construct descriptor to generate hw key blob */
+int cnstr_hw_encap_blob_jobdesc(uint32_t *desc,
+				uint8_t *key_idnfr, uint32_t key_sz,
+				uint32_t key_class, uint8_t *plain_txt,
+				uint32_t in_sz, uint8_t *enc_blob,
+				uint32_t out_sz, uint32_t operation)
+{
+	phys_addr_t *phys_key_idnfr, *phys_addr_in, *phys_addr_out;
+	int i = 0;
+
+	phys_key_idnfr = vtop((void *)key_idnfr);
+	phys_addr_in = vtop((void *)plain_txt);
+	phys_addr_out = vtop((void *)enc_blob);
+
+	desc_init(desc);
+
+	desc_add_word(desc, U(0xb0800000));
+
+	/* Key Identifier */
+	desc_add_word(desc, (key_class | key_sz));
+	desc_add_ptr(desc, phys_key_idnfr);
+
+	/* Source Address */
+	desc_add_word(desc, U(0xf0400000));
+	desc_add_ptr(desc, phys_addr_in);
+
+	/* In Size = 0x10 */
+	desc_add_word(desc, in_sz);
+
+	/* Out Address */
+	desc_add_word(desc, U(0xf8400000));
+	desc_add_ptr(desc, phys_addr_out);
+
+	/* Out Size = 0x10 */
+	desc_add_word(desc, out_sz);
+
+	/* Operation */
+	desc_add_word(desc, operation);
+
+	for (i = 0; i < 15; i++)
+		VERBOSE("desc word %x\n", desc[i]);
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function	: inline_cnstr_jobdesc_pkha_rsaexp
+ * Arguments	: desc - Pointer to Descriptor
+ *		  pkin - Pointer to Input Params
+ *		  out - Pointer to Output
+ *		  out_siz - Output Size
+ * Return	: Void
+ * Description	: Creates the descriptor for PKHA RSA
+ ***************************************************************************/
+void cnstr_jobdesc_pkha_rsaexp(uint32_t *desc,
+			       struct pk_in_params *pkin, uint8_t *out,
+			       uint32_t out_siz)
+{
+	phys_addr_t *ptr_addr_e, *ptr_addr_a, *ptr_addr_n, *ptr_addr_out;
+
+	ptr_addr_e = vtop((void *)(pkin->e));
+	ptr_addr_a = vtop((void *)(pkin->a));
+	ptr_addr_n = vtop((void *)(pkin->n));
+	ptr_addr_out = vtop((void *)(out));
+
+	desc_init(desc);
+	desc_add_word(desc, U(0xb0800000));
+	desc_add_word(desc, U(0x02010000) | pkin->e_siz);
+	desc_add_ptr(desc, ptr_addr_e);
+	desc_add_word(desc, U(0x220c0000) | pkin->a_siz);
+	desc_add_ptr(desc, ptr_addr_a);
+	desc_add_word(desc, U(0x22080000) | pkin->n_siz);
+	desc_add_ptr(desc, ptr_addr_n);
+	desc_add_word(desc, U(0x81800006));
+	desc_add_word(desc, U(0x620d0000) | out_siz);
+	desc_add_ptr(desc, ptr_addr_out);
+}
+
+/***************************************************************************
+ * Function	: inline_cnstr_jobdesc_sha256
+ * Arguments	: desc - Pointer to Descriptor
+ *		  msg - Pointer to SG Table
+ *		  msgsz - Size of SG Table
+ *		  digest - Pointer to Output Digest
+ * Return	: Void
+ * Description	: Creates the descriptor for SHA256 HASH calculation
+ ***************************************************************************/
+void cnstr_hash_jobdesc(uint32_t *desc, uint8_t *msg, uint32_t msgsz,
+			uint8_t *digest)
+{
+	/* SHA 256 , output is of length 32 words */
+	phys_addr_t *ptr_addr_in, *ptr_addr_out;
+
+	ptr_addr_in = (void *)vtop(msg);
+	ptr_addr_out = (void *)vtop(digest);
+
+	desc_init(desc);
+	desc_add_word(desc, U(0xb0800000));
+
+	/* Operation Command
+	 * OP_TYPE_CLASS2_ALG | OP_ALG_ALGSEL_SHA256 | OP_ALG_AAI_HASH |
+	 * OP_ALG_AS_INITFINAL | OP_ALG_ENCRYPT | OP_ALG_ICV_OFF)
+	 */
+	desc_add_word(desc, U(0x8443000d));
+
+	if (msgsz > U(0xffff)) {
+		desc_add_word(desc, U(0x25540000));	/* FIFO Load */
+		desc_add_ptr(desc, ptr_addr_in);	/* Pointer to msg */
+		desc_add_word(desc, msgsz);	/* Size */
+		desc_add_word(desc, U(0x54200020));	/* FIFO Store */
+		desc_add_ptr(desc, ptr_addr_out);	/* Pointer to Result */
+	} else {
+		desc_add_word(desc, U(0x25140000) | msgsz);
+		desc_add_ptr(desc, ptr_addr_in);
+		desc_add_word(desc, U(0x54200020));
+		desc_add_ptr(desc, ptr_addr_out);
+	}
+
+}
diff --git a/drivers/nxp/crypto/caam/src/rng.c b/drivers/nxp/crypto/caam/src/rng.c
new file mode 100644
index 0000000..0b9d87d
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/rng.c
@@ -0,0 +1,251 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "sec_hw_specific.h"
+
+
+/* Callback function after Instantiation decsriptor is submitted to SEC */
+static void rng_done(uint32_t *desc, uint32_t status, void *arg,
+		     void *job_ring)
+{
+	INFO("RNG Desc SUCCESS with status %x\n", status);
+}
+
+/* Is the HW RNG instantiated?
+ * Return code:
+ * 0 - Not in the instantiated state
+ * 1 - In the instantiated state
+ * state_handle - 0 for SH0, 1 for SH1
+ */
+static int is_hw_rng_instantiated(uint32_t *state_handle)
+{
+	int ret_code = 0;
+	uint32_t rdsta;
+
+	rdsta = sec_in32(get_caam_addr() + RNG_REG_RDSTA_OFFSET);
+
+	 /*Check if either of the two state handles has been instantiated */
+	if (rdsta & RNG_STATE0_HANDLE_INSTANTIATED) {
+		*state_handle = 0;
+		ret_code = 1;
+	} else if (rdsta & RNG_STATE0_HANDLE_INSTANTIATED) {
+		*state_handle = 1;
+		ret_code = 1;
+	}
+
+	return ret_code;
+}
+
+/* @brief Kick the TRNG block of the RNG HW Engine
+ * @param [in] ent_delay       Entropy delay to be used
+ *        By default, the TRNG runs for 200 clocks per sample;
+ *        1200 clocks per sample generates better entropy.
+ * @retval 0 on success
+ * @retval -1 on error
+ */
+static void kick_trng(int ent_delay)
+{
+	uint32_t val;
+
+	/* put RNG4 into program mode */
+	val = sec_in32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET);
+	val = val | RTMCTL_PRGM;
+	sec_out32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET, val);
+
+	/* rtsdctl bits 0-15 contain "Entropy Delay, which defines the
+	 *  length (in system clocks) of each Entropy sample taken
+	 */
+	val = sec_in32(get_caam_addr() + RNG_REG_RTSDCTL_OFFSET);
+	val = (val & ~RTSDCTL_ENT_DLY_MASK) |
+	    (ent_delay << RTSDCTL_ENT_DLY_SHIFT);
+	sec_out32(get_caam_addr() + RNG_REG_RTSDCTL_OFFSET, val);
+	/* min. freq. count, equal to 1/4 of the entropy sample length */
+	sec_out32(get_caam_addr() + RNG_REG_RTFRQMIN_OFFSET, ent_delay >> 2);
+	/* disable maximum frequency count */
+	sec_out32(get_caam_addr() + RNG_REG_RTFRQMAX_OFFSET, RTFRQMAX_DISABLE);
+
+	/* select raw sampling in both entropy shifter
+	 *  and statistical checker
+	 */
+	val = sec_in32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET);
+	val = val | RTMCTL_SAMP_MODE_RAW_ES_SC;
+	sec_out32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET, val);
+
+	/* put RNG4 into run mode */
+	val = sec_in32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET);
+	val = val & ~RTMCTL_PRGM;
+	sec_out32(get_caam_addr() + RNG_REG_RTMCTL_OFFSET, val);
+}
+
+/* @brief Submit descriptor to instantiate the RNG
+ * @retval 0 on success
+ * @retval -1 on error
+ */
+static int instantiate_rng(void)
+{
+	int ret = 0;
+	struct job_descriptor desc __aligned(CACHE_WRITEBACK_GRANULE);
+	struct job_descriptor *jobdesc = &desc;
+
+	jobdesc->arg = NULL;
+	jobdesc->callback = rng_done;
+
+	/* create the hw_rng descriptor */
+	cnstr_rng_instantiate_jobdesc(jobdesc->desc);
+
+	/* Finally, generate the requested random data bytes */
+	ret = run_descriptor_jr(jobdesc);
+	if (ret != 0) {
+		ERROR("Error in running descriptor\n");
+		ret = -1;
+	}
+	return ret;
+}
+
+/* Generate Random Data using HW RNG
+ * Parameters:
+ * uint8_t* add_input   - user specified optional input byte array
+ * uint32_t add_input_len - number of bytes of additional input
+ * uint8_t* out                   - user specified output byte array
+ * uint32_t out_len       - number of bytes to store in output byte array
+ * Return code:
+ * 0 - SUCCESS
+ * -1 - ERROR
+ */
+static int
+hw_rng_generate(uint32_t *add_input, uint32_t add_input_len,
+		uint8_t *out, uint32_t out_len, uint32_t state_handle)
+{
+	int ret = 0;
+	struct job_descriptor desc __aligned(CACHE_WRITEBACK_GRANULE);
+	struct job_descriptor *jobdesc = &desc;
+
+	jobdesc->arg = NULL;
+	jobdesc->callback = rng_done;
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	inv_dcache_range((uintptr_t)out, out_len);
+	dmbsy();
+#endif
+
+	/* create the hw_rng descriptor */
+	ret = cnstr_rng_jobdesc(jobdesc->desc, state_handle,
+				add_input, add_input_len, out, out_len);
+	if (ret != 0) {
+		ERROR("Descriptor construction failed\n");
+		ret = -1;
+		goto out;
+	}
+	/* Finally, generate the requested random data bytes */
+	ret = run_descriptor_jr(jobdesc);
+	if (ret != 0) {
+		ERROR("Error in running descriptor\n");
+		ret = -1;
+	}
+
+out:
+	return ret;
+}
+
+/* this function instantiates the rng
+ *
+ * Return code:
+ *  0 - All is well
+ * <0 - Error occurred somewhere
+ */
+int hw_rng_instantiate(void)
+{
+	int ret = 0;
+	int ent_delay = RTSDCTL_ENT_DLY_MIN;
+	uint32_t state_handle;
+
+	ret = is_hw_rng_instantiated(&state_handle);
+	if (ret != 0) {
+		NOTICE("RNG already instantiated\n");
+		return 0;
+	}
+	do {
+		kick_trng(ent_delay);
+		ent_delay += 400;
+		/*if instantiate_rng(...) fails, the loop will rerun
+		 *and the kick_trng(...) function will modify the
+		 *upper and lower limits of the entropy sampling
+		 *interval, leading to a sucessful initialization of
+		 */
+		ret = instantiate_rng();
+	} while ((ret == -1) && (ent_delay < RTSDCTL_ENT_DLY_MAX));
+	if (ret != 0) {
+		ERROR("RNG: Failed to instantiate RNG\n");
+		return ret;
+	}
+
+	NOTICE("RNG: INSTANTIATED\n");
+
+	/* Enable RDB bit so that RNG works faster */
+	// sec_setbits32(&sec->scfgr, SEC_SCFGR_RDBENABLE);
+
+	return ret;
+}
+
+/* Generate random bytes, and stuff them into the bytes buffer
+ *
+ * If the HW RNG has not already been instantiated,
+ *  it will be instantiated before data is generated.
+ *
+ * Parameters:
+ * uint8_t* bytes  - byte buffer large enough to hold the requested random date
+ * int byte_len - number of random bytes to generate
+ *
+ * Return code:
+ *  0 - All is well
+ *  ~0 - Error occurred somewhere
+ */
+int get_rand_bytes_hw(uint8_t *bytes, int byte_len)
+{
+	int ret_code = 0;
+	uint32_t state_handle;
+
+	/* If this is the first time this routine is called,
+	 *  then the hash_drbg will not already be instantiated.
+	 * Therefore, before generating data, instantiate the hash_drbg
+	 */
+	ret_code = is_hw_rng_instantiated(&state_handle);
+	if (ret_code == 0) {
+		INFO("Instantiating the HW RNG\n");
+
+		/* Instantiate the hw RNG */
+		ret_code = hw_rng_instantiate();
+		if (ret_code != 0) {
+			ERROR("HW RNG Instantiate failed\n");
+			return ret_code;
+		}
+	}
+	/* If  HW RNG is still not instantiated, something must have gone wrong,
+	 * it must be in the error state, we will not generate any random data
+	 */
+	if (is_hw_rng_instantiated(&state_handle) == 0) {
+		ERROR("HW RNG is in an Error state, and cannot be used\n");
+		return -1;
+	}
+	/* Generate a random 256-bit value, as 32 bytes */
+	ret_code = hw_rng_generate(0, 0, bytes, byte_len, state_handle);
+	if (ret_code != 0) {
+		ERROR("HW RNG Generate failed\n");
+		return ret_code;
+	}
+
+	return ret_code;
+}
diff --git a/drivers/nxp/crypto/caam/src/sec_hw_specific.c b/drivers/nxp/crypto/caam/src/sec_hw_specific.c
new file mode 100644
index 0000000..92b7762
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/sec_hw_specific.c
@@ -0,0 +1,635 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "sec_hw_specific.h"
+
+
+/* Job rings used for communication with SEC HW */
+extern struct sec_job_ring_t g_job_rings[MAX_SEC_JOB_RINGS];
+
+/* The current state of SEC user space driver */
+extern volatile sec_driver_state_t g_driver_state;
+
+/* The number of job rings used by SEC user space driver */
+extern int g_job_rings_no;
+
+/* LOCAL FUNCTIONS */
+static inline void hw_set_input_ring_start_addr(struct jobring_regs *regs,
+						phys_addr_t *start_addr)
+{
+#if defined(CONFIG_PHYS_64BIT)
+	sec_out32(&regs->irba_h, PHYS_ADDR_HI(start_addr));
+#else
+	sec_out32(&regs->irba_h, 0);
+#endif
+	sec_out32(&regs->irba_l, PHYS_ADDR_LO(start_addr));
+}
+
+static inline void hw_set_output_ring_start_addr(struct jobring_regs *regs,
+						 phys_addr_t *start_addr)
+{
+#if defined(CONFIG_PHYS_64BIT)
+	sec_out32(&regs->orba_h, PHYS_ADDR_HI(start_addr));
+#else
+	sec_out32(&regs->orba_h, 0);
+#endif
+	sec_out32(&regs->orba_l, PHYS_ADDR_LO(start_addr));
+}
+
+/* ORJR - Output Ring Jobs Removed Register shows how many jobs were
+ * removed from the Output Ring for processing by software. This is done after
+ * the software has processed the entries.
+ */
+static inline void hw_remove_entries(sec_job_ring_t *jr, int num)
+{
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)jr->register_base_addr;
+
+	sec_out32(&regs->orjr, num);
+}
+
+/* IRSA - Input Ring Slots Available register holds the number of entries in
+ * the Job Ring's input ring. Once a job is enqueued, the value returned is
+ * decremented by the hardware by the number of jobs enqueued.
+ */
+static inline int hw_get_available_slots(sec_job_ring_t *jr)
+{
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)jr->register_base_addr;
+
+	return sec_in32(&regs->irsa);
+}
+
+/* ORSFR - Output Ring Slots Full register holds the number of jobs which were
+ * processed by the SEC and can be retrieved by the software. Once a job has
+ * been processed by software, the user will call hw_remove_one_entry in order
+ * to notify the SEC that the entry was processed
+ */
+static inline int hw_get_no_finished_jobs(sec_job_ring_t *jr)
+{
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)jr->register_base_addr;
+
+	return sec_in32(&regs->orsf);
+}
+
+/* @brief Process Jump Halt Condition related errors
+ * @param [in]  error_code The error code in the descriptor status word
+ */
+static inline void hw_handle_jmp_halt_cond_err(union hw_error_code error_code)
+{
+	ERROR("JMP %x\n", error_code.error_desc.jmp_halt_cond_src.jmp);
+	ERROR("Descriptor Index: %d\n",
+	      error_code.error_desc.jmp_halt_cond_src.desc_idx);
+	ERROR(" Condition %x\n", error_code.error_desc.jmp_halt_cond_src.cond);
+}
+
+/* @brief Process DECO related errors
+ * @param [in]  error_code      The error code in the descriptor status word
+ */
+static inline void hw_handle_deco_err(union hw_error_code error_code)
+{
+	ERROR("JMP %x\n", error_code.error_desc.deco_src.jmp);
+	ERROR("Descriptor Index: 0x%x",
+	      error_code.error_desc.deco_src.desc_idx);
+
+	switch (error_code.error_desc.deco_src.desc_err) {
+	case SEC_HW_ERR_DECO_HFN_THRESHOLD:
+		WARN(" Descriptor completed but exceeds the Threshold");
+		break;
+	default:
+		ERROR("Error 0x%04x not implemented",
+		      error_code.error_desc.deco_src.desc_err);
+		break;
+	}
+}
+
+/* @brief Process  Jump Halt User Status related errors
+ * @param [in]  error_code      The error code in the descriptor status word
+ */
+static inline void hw_handle_jmp_halt_user_err(union hw_error_code error_code)
+{
+	WARN(" Not implemented");
+}
+
+/* @brief Process CCB related errors
+ * @param [in]  error_code      The error code in the descriptor status word
+ */
+static inline void hw_handle_ccb_err(union hw_error_code hw_error_code)
+{
+	WARN(" Not implemented");
+}
+
+/* @brief Process Job Ring related errors
+ * @param [in]  error_code      The error code in the descriptor status word
+ */
+static inline void hw_handle_jr_err(union hw_error_code hw_error_code)
+{
+	WARN(" Not implemented");
+}
+
+/* GLOBAL FUNCTIONS */
+
+int hw_reset_job_ring(sec_job_ring_t *job_ring)
+{
+	int ret = 0;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* First reset the job ring in hw */
+	ret = hw_shutdown_job_ring(job_ring);
+	if (ret != 0) {
+		ERROR("Failed resetting job ring in hardware");
+		return ret;
+	}
+	/* In order to have the HW JR in a workable state
+	 *after a reset, I need to re-write the input
+	 * queue size, input start address, output queue
+	 * size and output start address
+	 * Write the JR input queue size to the HW register
+	 */
+	sec_out32(&regs->irs, SEC_JOB_RING_SIZE);
+
+	/* Write the JR output queue size to the HW register */
+	sec_out32(&regs->ors, SEC_JOB_RING_SIZE);
+
+	/* Write the JR input queue start address */
+	hw_set_input_ring_start_addr(regs, vtop(job_ring->input_ring));
+
+	/* Write the JR output queue start address */
+	hw_set_output_ring_start_addr(regs, vtop(job_ring->output_ring));
+
+	return 0;
+}
+
+int hw_shutdown_job_ring(sec_job_ring_t *job_ring)
+{
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+	unsigned int timeout = SEC_TIMEOUT;
+	uint32_t tmp = 0U;
+
+	VERBOSE("Resetting Job ring\n");
+
+	/*
+	 * Mask interrupts since we are going to poll
+	 * for reset completion status
+	 * Also, at POR, interrupts are ENABLED on a JR, thus
+	 * this is the point where I can disable them without
+	 * changing the code logic too much
+	 */
+
+	jr_disable_irqs(job_ring);
+
+	/* initiate flush (required prior to reset) */
+	sec_out32(&regs->jrcr, JR_REG_JRCR_VAL_RESET);
+
+	/* dummy read */
+	tmp = sec_in32(&regs->jrcr);
+
+	do {
+		tmp = sec_in32(&regs->jrint);
+	} while (((tmp & JRINT_ERR_HALT_MASK) ==
+		  JRINT_ERR_HALT_INPROGRESS) && ((--timeout) != 0U));
+
+	if ((tmp & JRINT_ERR_HALT_MASK) != JRINT_ERR_HALT_COMPLETE ||
+	    timeout == 0U) {
+		ERROR("Failed to flush hw job ring %x\n %u", tmp, timeout);
+		/* unmask interrupts */
+		if (job_ring->jr_mode != SEC_NOTIFICATION_TYPE_POLL) {
+			jr_enable_irqs(job_ring);
+		}
+		return -1;
+	}
+	/* Initiate reset */
+	timeout = SEC_TIMEOUT;
+	sec_out32(&regs->jrcr, JR_REG_JRCR_VAL_RESET);
+
+	do {
+		tmp = sec_in32(&regs->jrcr);
+	} while (((tmp & JR_REG_JRCR_VAL_RESET) != 0U) &&
+		 ((--timeout) != 0U));
+
+	if (timeout == 0U) {
+		ERROR("Failed to reset hw job ring\n");
+		/* unmask interrupts */
+		if (job_ring->jr_mode != SEC_NOTIFICATION_TYPE_POLL) {
+			jr_enable_irqs(job_ring);
+		}
+		return -1;
+	}
+	/* unmask interrupts */
+	if (job_ring->jr_mode != SEC_NOTIFICATION_TYPE_POLL) {
+		jr_enable_irqs(job_ring);
+	}
+	return 0;
+
+}
+
+void hw_handle_job_ring_error(sec_job_ring_t *job_ring, uint32_t error_code)
+{
+	union hw_error_code hw_err_code;
+
+	hw_err_code.error = error_code;
+
+	switch (hw_err_code.error_desc.value.ssrc) {
+	case SEC_HW_ERR_SSRC_NO_SRC:
+		INFO("No Status Source ");
+		break;
+	case SEC_HW_ERR_SSRC_CCB_ERR:
+		INFO("CCB Status Source");
+		hw_handle_ccb_err(hw_err_code);
+		break;
+	case SEC_HW_ERR_SSRC_JMP_HALT_U:
+		INFO("Jump Halt User Status Source");
+		hw_handle_jmp_halt_user_err(hw_err_code);
+		break;
+	case SEC_HW_ERR_SSRC_DECO:
+		INFO("DECO Status Source");
+		hw_handle_deco_err(hw_err_code);
+		break;
+	case SEC_HW_ERR_SSRC_JR:
+		INFO("Job Ring Status Source");
+		hw_handle_jr_err(hw_err_code);
+		break;
+	case SEC_HW_ERR_SSRC_JMP_HALT_COND:
+		INFO("Jump Halt Condition Codes");
+		hw_handle_jmp_halt_cond_err(hw_err_code);
+		break;
+	default:
+		INFO("Unknown SSRC");
+		break;
+	}
+}
+
+int hw_job_ring_error(sec_job_ring_t *job_ring)
+{
+	uint32_t jrint_error_code;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	if (JR_REG_JRINT_JRE_EXTRACT(sec_in32(&regs->jrint)) == 0) {
+		return 0;
+	}
+
+	jrint_error_code =
+	    JR_REG_JRINT_ERR_TYPE_EXTRACT(sec_in32(&regs->jrint));
+	switch (jrint_error_code) {
+	case JRINT_ERR_WRITE_STATUS:
+		ERROR("Error writing status to Output Ring ");
+		break;
+	case JRINT_ERR_BAD_INPUT_BASE:
+		ERROR("Bad Input Ring Base (not on a 4-byte boundary)\n");
+		break;
+	case JRINT_ERR_BAD_OUTPUT_BASE:
+		ERROR("Bad Output Ring Base (not on a 4-byte boundary)\n");
+		break;
+	case JRINT_ERR_WRITE_2_IRBA:
+		ERROR("Invalid write to Input Ring Base Address Register\n");
+		break;
+	case JRINT_ERR_WRITE_2_ORBA:
+		ERROR("Invalid write to Output Ring Base Address Register\n");
+		break;
+	case JRINT_ERR_RES_B4_HALT:
+		ERROR("Job Ring released before Job Ring is halted\n");
+		break;
+	case JRINT_ERR_REM_TOO_MANY:
+		ERROR("Removed too many jobs from job ring\n");
+		break;
+	case JRINT_ERR_ADD_TOO_MANY:
+		ERROR("Added too many jobs on job ring\n");
+		break;
+	default:
+		ERROR("Unknown SEC JR Error :%d\n", jrint_error_code);
+		break;
+	}
+	return jrint_error_code;
+}
+
+int hw_job_ring_set_coalescing_param(sec_job_ring_t *job_ring,
+				     uint16_t irq_coalescing_timer,
+				     uint8_t irq_coalescing_count)
+{
+	uint32_t reg_val = 0U;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* Set descriptor count coalescing */
+	reg_val |= (irq_coalescing_count << JR_REG_JRCFG_LO_ICDCT_SHIFT);
+
+	/* Set coalescing timer value */
+	reg_val |= (irq_coalescing_timer << JR_REG_JRCFG_LO_ICTT_SHIFT);
+
+	/* Update parameters in HW */
+	sec_out32(&regs->jrcfg1, reg_val);
+
+	VERBOSE("Set coalescing params on jr\n");
+
+	return 0;
+}
+
+int hw_job_ring_enable_coalescing(sec_job_ring_t *job_ring)
+{
+	uint32_t reg_val = 0U;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* Get the current value of the register */
+	reg_val = sec_in32(&regs->jrcfg1);
+
+	/* Enable coalescing */
+	reg_val |= JR_REG_JRCFG_LO_ICEN_EN;
+
+	/* Write in hw */
+	sec_out32(&regs->jrcfg1, reg_val);
+
+	VERBOSE("Enabled coalescing on jr\n");
+
+	return 0;
+}
+
+int hw_job_ring_disable_coalescing(sec_job_ring_t *job_ring)
+{
+	uint32_t reg_val = 0U;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* Get the current value of the register */
+	reg_val = sec_in32(&regs->jrcfg1);
+
+	/* Disable coalescing */
+	reg_val &= ~JR_REG_JRCFG_LO_ICEN_EN;
+
+	/* Write in hw */
+	sec_out32(&regs->jrcfg1, reg_val);
+
+	VERBOSE("Disabled coalescing on jr");
+
+	return 0;
+
+}
+
+void hw_flush_job_ring(struct sec_job_ring_t *job_ring,
+		       uint32_t do_notify,
+		       uint32_t error_code, uint32_t *notified_descs)
+{
+	int32_t jobs_no_to_discard = 0;
+	int32_t discarded_descs_no = 0;
+	int32_t number_of_jobs_available = 0;
+
+	VERBOSE("JR pi[%d]i ci[%d]\n", job_ring->pidx, job_ring->cidx);
+	VERBOSE("error code %x\n", error_code);
+	VERBOSE("Notify_desc = %d\n", do_notify);
+
+	number_of_jobs_available = hw_get_no_finished_jobs(job_ring);
+
+	/* Discard all jobs */
+	jobs_no_to_discard = number_of_jobs_available;
+
+	VERBOSE("JR pi[%d]i ci[%d]\n", job_ring->pidx, job_ring->cidx);
+	VERBOSE("Discarding desc = %d\n", jobs_no_to_discard);
+
+	while (jobs_no_to_discard > discarded_descs_no) {
+		discarded_descs_no++;
+		/* Now increment the consumer index for the current job ring,
+		 * AFTER saving job in temporary location!
+		 * Increment the consumer index for the current job ring
+		 */
+
+		job_ring->cidx = SEC_CIRCULAR_COUNTER(job_ring->cidx,
+						      SEC_JOB_RING_SIZE);
+
+		hw_remove_entries(job_ring, 1);
+	}
+
+	if (do_notify == true) {
+		if (notified_descs == NULL) {
+			return;
+		}
+		*notified_descs = discarded_descs_no;
+	}
+}
+
+/* return >0 in case of success
+ *  -1 in case of error from SEC block
+ *  0 in case job not yet processed by SEC
+ *   or  Descriptor returned is NULL after dequeue
+ */
+int hw_poll_job_ring(struct sec_job_ring_t *job_ring, int32_t limit)
+{
+	int32_t jobs_no_to_notify = 0;
+	int32_t number_of_jobs_available = 0;
+	int32_t notified_descs_no = 0;
+	uint32_t error_descs_no = 0U;
+	uint32_t sec_error_code = 0U;
+	uint32_t do_driver_shutdown = false;
+	phys_addr_t *fnptr, *arg_addr;
+	user_callback usercall = NULL;
+	uint8_t *current_desc;
+	void *arg;
+	uintptr_t current_desc_addr;
+	phys_addr_t current_desc_loc;
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	inv_dcache_range((uintptr_t)job_ring->register_base_addr, sizeof(struct jobring_regs));
+	dmbsy();
+#endif
+
+	/* check here if any JR error that cannot be written
+	 * in the output status word has occurred
+	 */
+	sec_error_code = hw_job_ring_error(job_ring);
+	if (unlikely(sec_error_code) != 0) {
+		ERROR("Error here itself %x\n", sec_error_code);
+		return -1;
+	}
+	/* Compute the number of notifications that need to be raised to UA
+	 * If limit < 0 -> notify all done jobs
+	 * If limit > total number of done jobs -> notify all done jobs
+	 * If limit = 0 -> error
+	 * If limit > 0 && limit < total number of done jobs -> notify a number
+	 * of done jobs equal with limit
+	 */
+
+	/*compute the number of jobs available in the job ring based on the
+	 * producer and consumer index values.
+	 */
+
+	number_of_jobs_available = hw_get_no_finished_jobs(job_ring);
+	jobs_no_to_notify = (limit < 0 || limit > number_of_jobs_available) ?
+	    number_of_jobs_available : limit;
+	VERBOSE("JR - pi %d, ci %d, ", job_ring->pidx, job_ring->cidx);
+	VERBOSE("Jobs submitted %d", number_of_jobs_available);
+	VERBOSE("Jobs to notify %d\n", jobs_no_to_notify);
+
+	while (jobs_no_to_notify > notified_descs_no) {
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+		inv_dcache_range(
+			(uintptr_t)(&job_ring->output_ring[job_ring->cidx]),
+			sizeof(struct sec_outring_entry));
+		dmbsy();
+#endif
+
+		/* Get job status here */
+		sec_error_code =
+		    sec_in32(&(job_ring->output_ring[job_ring->cidx].status));
+
+		/* Get completed descriptor
+		 */
+		current_desc_loc = (uintptr_t)
+		    &job_ring->output_ring[job_ring->cidx].desc;
+		current_desc_addr = sec_read_addr(current_desc_loc);
+
+		current_desc = ptov((phys_addr_t *) current_desc_addr);
+		if (current_desc == 0) {
+			ERROR("No descriptor returned from SEC");
+			assert(current_desc);
+			return 0;
+		}
+		/* now increment the consumer index for the current job ring,
+		 * AFTER saving job in temporary location!
+		 */
+		job_ring->cidx = SEC_CIRCULAR_COUNTER(job_ring->cidx,
+						      SEC_JOB_RING_SIZE);
+
+		if (sec_error_code != 0) {
+			ERROR("desc at cidx %d\n ", job_ring->cidx);
+			ERROR("generated error %x\n", sec_error_code);
+
+			sec_handle_desc_error(job_ring,
+					      sec_error_code,
+					      &error_descs_no,
+					      &do_driver_shutdown);
+			hw_remove_entries(job_ring, 1);
+
+			return -1;
+		}
+		/* Signal that the job has been processed & the slot is free */
+		hw_remove_entries(job_ring, 1);
+		notified_descs_no++;
+
+		arg_addr = (phys_addr_t *) (current_desc +
+				(MAX_DESC_SIZE_WORDS * sizeof(uint32_t)));
+
+		fnptr = (phys_addr_t *) (current_desc +
+					(MAX_DESC_SIZE_WORDS * sizeof(uint32_t)
+					+  sizeof(void *)));
+
+		arg = (void *)*(arg_addr);
+		if (*fnptr != 0) {
+			VERBOSE("Callback Function called\n");
+			usercall = (user_callback) *(fnptr);
+			(*usercall) ((uint32_t *) current_desc,
+				     sec_error_code, arg, job_ring);
+		}
+	}
+
+	return notified_descs_no;
+}
+
+void sec_handle_desc_error(sec_job_ring_t *job_ring,
+			   uint32_t sec_error_code,
+			   uint32_t *notified_descs,
+			   uint32_t *do_driver_shutdown)
+{
+	/* Analyze the SEC error on this job ring */
+	hw_handle_job_ring_error(job_ring, sec_error_code);
+}
+
+void flush_job_rings(void)
+{
+	struct sec_job_ring_t *job_ring = NULL;
+	int i = 0;
+
+	for (i = 0; i < g_job_rings_no; i++) {
+		job_ring = &g_job_rings[i];
+		/* Producer index is frozen. If consumer index is not equal
+		 * with producer index, then we have descs to flush.
+		 */
+		while (job_ring->pidx != job_ring->cidx) {
+			hw_flush_job_ring(job_ring, false, 0,	/* no error */
+					  NULL);
+		}
+	}
+}
+
+int shutdown_job_ring(struct sec_job_ring_t *job_ring)
+{
+	int ret = 0;
+
+	ret = hw_shutdown_job_ring(job_ring);
+	if (ret != 0) {
+		ERROR("Failed to shutdown hardware job ring\n");
+		return ret;
+	}
+
+	if (job_ring->coalescing_en != 0) {
+		hw_job_ring_disable_coalescing(job_ring);
+	}
+
+	if (job_ring->jr_mode != SEC_NOTIFICATION_TYPE_POLL) {
+		ret = jr_disable_irqs(job_ring);
+		if (ret != 0) {
+			ERROR("Failed to disable irqs for job ring");
+			return ret;
+		}
+	}
+
+	return 0;
+}
+
+int jr_enable_irqs(struct sec_job_ring_t *job_ring)
+{
+	uint32_t reg_val = 0U;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* Get the current value of the register */
+	reg_val = sec_in32(&regs->jrcfg1);
+
+	/* Enable interrupts by disabling interrupt masking*/
+	reg_val &= ~JR_REG_JRCFG_LO_IMSK_EN;
+
+	/* Update parameters in HW */
+	sec_out32(&regs->jrcfg1, reg_val);
+
+	VERBOSE("Enable interrupts on JR\n");
+
+	return 0;
+}
+
+int jr_disable_irqs(struct sec_job_ring_t *job_ring)
+{
+	uint32_t reg_val = 0U;
+	struct jobring_regs *regs =
+	    (struct jobring_regs *)job_ring->register_base_addr;
+
+	/* Get the current value of the register */
+	reg_val = sec_in32(&regs->jrcfg1);
+
+	/* Disable interrupts by enabling interrupt masking*/
+	reg_val |= JR_REG_JRCFG_LO_IMSK_EN;
+
+	/* Update parameters in HW */
+	sec_out32(&regs->jrcfg1, reg_val);
+
+	VERBOSE("Disable interrupts on JR\n");
+
+	return 0;
+}
diff --git a/drivers/nxp/crypto/caam/src/sec_jr_driver.c b/drivers/nxp/crypto/caam/src/sec_jr_driver.c
new file mode 100644
index 0000000..1fe7007
--- /dev/null
+++ b/drivers/nxp/crypto/caam/src/sec_jr_driver.c
@@ -0,0 +1,241 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include "caam.h"
+#include <common/debug.h>
+#include "jobdesc.h"
+#include "nxp_timer.h"
+#include "sec_hw_specific.h"
+#include "sec_jr_driver.h"
+
+
+/* Job rings used for communication with SEC HW  */
+struct sec_job_ring_t g_job_rings[MAX_SEC_JOB_RINGS];
+
+/* The current state of SEC user space driver */
+volatile sec_driver_state_t g_driver_state = SEC_DRIVER_STATE_IDLE;
+
+int g_job_rings_no;
+
+uint8_t ip_ring[SEC_DMA_MEM_INPUT_RING_SIZE] __aligned(CACHE_WRITEBACK_GRANULE);
+uint8_t op_ring[SEC_DMA_MEM_OUTPUT_RING_SIZE] __aligned(CACHE_WRITEBACK_GRANULE);
+
+void *init_job_ring(uint8_t jr_mode,
+		    uint16_t irq_coalescing_timer,
+		    uint8_t irq_coalescing_count,
+		    void *reg_base_addr, uint32_t irq_id)
+{
+	struct sec_job_ring_t *job_ring = &g_job_rings[g_job_rings_no++];
+	int ret = 0;
+
+	job_ring->register_base_addr = reg_base_addr;
+	job_ring->jr_mode = jr_mode;
+	job_ring->irq_fd = irq_id;
+
+	job_ring->input_ring = vtop(ip_ring);
+	memset(job_ring->input_ring, 0, SEC_DMA_MEM_INPUT_RING_SIZE);
+
+	job_ring->output_ring = (struct sec_outring_entry *)vtop(op_ring);
+	memset(job_ring->output_ring, 0, SEC_DMA_MEM_OUTPUT_RING_SIZE);
+
+	dsb();
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)(job_ring->input_ring),
+				       SEC_DMA_MEM_INPUT_RING_SIZE),
+	flush_dcache_range((uintptr_t)(job_ring->output_ring),
+				       SEC_DMA_MEM_OUTPUT_RING_SIZE),
+
+	dmbsy();
+#endif
+	/* Reset job ring in SEC hw and configure job ring registers */
+	ret = hw_reset_job_ring(job_ring);
+	if (ret != 0) {
+		ERROR("Failed to reset hardware job ring\n");
+		return NULL;
+	}
+
+	if (jr_mode == SEC_NOTIFICATION_TYPE_IRQ) {
+		/* Enable IRQ if driver work sin interrupt mode */
+		ERROR("Enabling DONE IRQ generation on job ring\n");
+		ret = jr_enable_irqs(job_ring);
+		if (ret != 0) {
+			ERROR("Failed to enable irqs for job ring\n");
+			return NULL;
+		}
+	}
+	if ((irq_coalescing_timer != 0) || (irq_coalescing_count != 0)) {
+		hw_job_ring_set_coalescing_param(job_ring,
+						 irq_coalescing_timer,
+						 irq_coalescing_count);
+
+		hw_job_ring_enable_coalescing(job_ring);
+		job_ring->coalescing_en = 1;
+	}
+
+	job_ring->jr_state = SEC_JOB_RING_STATE_STARTED;
+
+	return job_ring;
+}
+
+int sec_release(void)
+{
+	int i;
+
+	/* Validate driver state */
+	if (g_driver_state == SEC_DRIVER_STATE_RELEASE) {
+		ERROR("Driver release is already in progress");
+		return SEC_DRIVER_RELEASE_IN_PROGRESS;
+	}
+	/* Update driver state */
+	g_driver_state = SEC_DRIVER_STATE_RELEASE;
+
+	/* If any descriptors in flight , poll and wait
+	 * until all descriptors are received and silently discarded.
+	 */
+
+	flush_job_rings();
+
+	for (i = 0; i < g_job_rings_no; i++) {
+		shutdown_job_ring(&g_job_rings[i]);
+	}
+	g_job_rings_no = 0;
+	g_driver_state = SEC_DRIVER_STATE_IDLE;
+
+	return SEC_SUCCESS;
+}
+
+int sec_jr_lib_init(void)
+{
+	/* Validate driver state */
+	if (g_driver_state != SEC_DRIVER_STATE_IDLE) {
+		ERROR("Driver already initialized\n");
+		return 0;
+	}
+
+	memset(g_job_rings, 0, sizeof(g_job_rings));
+	g_job_rings_no = 0;
+
+	/* Update driver state */
+	g_driver_state = SEC_DRIVER_STATE_STARTED;
+	return 0;
+}
+
+int dequeue_jr(void *job_ring_handle, int32_t limit)
+{
+	int ret = 0;
+	int notified_descs_no = 0;
+	struct sec_job_ring_t *job_ring = (sec_job_ring_t *) job_ring_handle;
+	uint64_t start_time;
+
+	/* Validate driver state */
+	if (g_driver_state != SEC_DRIVER_STATE_STARTED) {
+		ERROR("Driver release in progress or driver not initialized\n");
+		return -1;
+	}
+
+	/* Validate input arguments */
+	if (job_ring == NULL) {
+		ERROR("job_ring_handle is NULL\n");
+		return -1;
+	}
+	if (((limit == 0) || (limit > SEC_JOB_RING_SIZE))) {
+		ERROR("Invalid limit parameter configuration\n");
+		return -1;
+	}
+
+	VERBOSE("JR Polling limit[%d]\n", limit);
+
+	/* Poll job ring
+	 * If limit < 0 -> poll JR until no more notifications are available.
+	 * If limit > 0 -> poll JR until limit is reached.
+	 */
+
+	start_time = get_timer_val(0);
+
+	while (notified_descs_no == 0) {
+		/* Run hw poll job ring */
+		notified_descs_no = hw_poll_job_ring(job_ring, limit);
+		if (notified_descs_no < 0) {
+			ERROR("Error polling SEC engine job ring ");
+			return notified_descs_no;
+		}
+		VERBOSE("Jobs notified[%d]. ", notified_descs_no);
+
+		if (get_timer_val(start_time) >= CAAM_TIMEOUT) {
+			break;
+		}
+	}
+
+	if (job_ring->jr_mode == SEC_NOTIFICATION_TYPE_IRQ) {
+
+		/* Always enable IRQ generation when in pure IRQ mode */
+		ret = jr_enable_irqs(job_ring);
+		if (ret != 0) {
+			ERROR("Failed to enable irqs for job ring");
+			return ret;
+		}
+	}
+	return notified_descs_no;
+}
+
+int enq_jr_desc(void *job_ring_handle, struct job_descriptor *jobdescr)
+{
+	struct sec_job_ring_t *job_ring;
+
+	job_ring = (struct sec_job_ring_t *)job_ring_handle;
+
+	/* Validate driver state */
+	if (g_driver_state != SEC_DRIVER_STATE_STARTED) {
+		ERROR("Driver release in progress or driver not initialized\n");
+		return -1;
+	}
+
+	/* Check job ring state */
+	if (job_ring->jr_state != SEC_JOB_RING_STATE_STARTED) {
+		ERROR("Job ring is currently resetting\n");
+		return -1;
+	}
+
+	if (SEC_JOB_RING_IS_FULL(job_ring->pidx, job_ring->cidx,
+				 SEC_JOB_RING_SIZE, SEC_JOB_RING_SIZE)) {
+		ERROR("Job ring is full\n");
+		return -1;
+	}
+
+	/* Set ptr in input ring to current descriptor  */
+	sec_write_addr(&job_ring->input_ring[job_ring->pidx],
+		       (phys_addr_t) vtop(jobdescr->desc));
+
+	dsb();
+
+#if defined(SEC_MEM_NON_COHERENT) && defined(IMAGE_BL2)
+	flush_dcache_range((uintptr_t)(&job_ring->input_ring[job_ring->pidx]),
+			   sizeof(phys_addr_t));
+
+	inv_dcache_range((uintptr_t)(&job_ring->output_ring[job_ring->cidx]),
+			   sizeof(struct sec_outring_entry));
+	dmbsy();
+#endif
+	/* Notify HW that a new job is enqueued  */
+	hw_enqueue_desc_on_job_ring(
+			(struct jobring_regs *)job_ring->register_base_addr, 1);
+
+	/* increment the producer index for the current job ring */
+	job_ring->pidx = SEC_CIRCULAR_COUNTER(job_ring->pidx,
+					      SEC_JOB_RING_SIZE);
+
+	return 0;
+}
diff --git a/drivers/nxp/csu/csu.c b/drivers/nxp/csu/csu.c
new file mode 100644
index 0000000..9f90fe0
--- /dev/null
+++ b/drivers/nxp/csu/csu.c
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <endian.h>
+
+#include <common/debug.h>
+#include <csu.h>
+#include <lib/mmio.h>
+
+void enable_layerscape_ns_access(struct csu_ns_dev_st *csu_ns_dev,
+				 uint32_t num, uintptr_t nxp_csu_addr)
+{
+	uint32_t *base = (uint32_t *)nxp_csu_addr;
+	uint32_t *reg;
+	uint32_t val;
+	int i;
+
+	for (i = 0; i < num; i++) {
+		reg = base + csu_ns_dev[i].ind / 2U;
+		val = be32toh(mmio_read_32((uintptr_t)reg));
+		if (csu_ns_dev[i].ind % 2U == 0U) {
+			val &= 0x0000ffffU;
+			val |= csu_ns_dev[i].val << 16U;
+		} else {
+			val &= 0xffff0000U;
+			val |= csu_ns_dev[i].val;
+		}
+		mmio_write_32((uintptr_t)reg, htobe32(val));
+	}
+}
diff --git a/drivers/nxp/csu/csu.mk b/drivers/nxp/csu/csu.mk
new file mode 100644
index 0000000..bc16035
--- /dev/null
+++ b/drivers/nxp/csu/csu.mk
@@ -0,0 +1,26 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+ifeq (${CSU_ADDED},)
+
+CSU_ADDED		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/csu
+
+CSU_SOURCES		+= $(PLAT_DRIVERS_PATH)/csu/csu.c
+
+ifeq (${BL_COMM_CSU_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${CSU_SOURCES}
+else
+ifeq (${BL2_CSU_NEEDED},yes)
+BL2_SOURCES		+= ${CSU_SOURCES}
+endif
+ifeq (${BL31_CSU_NEEDED},yes)
+BL31_SOURCES		+= ${CSU_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/nxp/dcfg/dcfg.c b/drivers/nxp/dcfg/dcfg.c
new file mode 100644
index 0000000..a988c5d
--- /dev/null
+++ b/drivers/nxp/dcfg/dcfg.c
@@ -0,0 +1,159 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/debug.h>
+#include "dcfg.h"
+#include <lib/mmio.h>
+#ifdef NXP_SFP_ENABLED
+#include <sfp.h>
+#endif
+
+static soc_info_t soc_info = {0};
+static devdisr5_info_t devdisr5_info = {0};
+static dcfg_init_info_t *dcfg_init_info;
+
+/* Read the PORSR1 register */
+uint32_t read_reg_porsr1(void)
+{
+	unsigned int *porsr1_addr = NULL;
+
+	if (dcfg_init_info->porsr1 != 0U) {
+		return dcfg_init_info->porsr1;
+	}
+
+	porsr1_addr = (void *)
+			(dcfg_init_info->g_nxp_dcfg_addr + DCFG_PORSR1_OFFSET);
+	dcfg_init_info->porsr1 = gur_in32(porsr1_addr);
+
+	return dcfg_init_info->porsr1;
+}
+
+
+const soc_info_t *get_soc_info(void)
+{
+	uint32_t reg;
+
+	if (soc_info.is_populated == true) {
+		return (const soc_info_t *) &soc_info;
+	}
+
+	reg = gur_in32(dcfg_init_info->g_nxp_dcfg_addr + DCFG_SVR_OFFSET);
+
+	soc_info.svr_reg.val = reg;
+
+	/* zero means SEC enabled. */
+	soc_info.sec_enabled =
+		(((reg & SVR_SEC_MASK) >> SVR_SEC_SHIFT) == 0) ? true : false;
+
+	soc_info.is_populated = true;
+	return (const soc_info_t *) &soc_info;
+}
+
+void dcfg_init(dcfg_init_info_t *dcfg_init_data)
+{
+	dcfg_init_info = dcfg_init_data;
+	read_reg_porsr1();
+	get_soc_info();
+}
+
+bool is_sec_enabled(void)
+{
+	return soc_info.sec_enabled;
+}
+
+const devdisr5_info_t *get_devdisr5_info(void)
+{
+	uint32_t reg;
+
+	if (devdisr5_info.is_populated == true)
+		return (const devdisr5_info_t *) &devdisr5_info;
+
+	reg = gur_in32(dcfg_init_info->g_nxp_dcfg_addr + DCFG_DEVDISR5_OFFSET);
+
+#if defined(CONFIG_CHASSIS_3_2)
+	devdisr5_info.ddrc1_present = (reg & DISR5_DDRC1_MASK) ? 0 : 1;
+	devdisr5_info.ddrc2_present = (reg & DISR5_DDRC2_MASK) ? 0 : 1;
+	devdisr5_info.ocram_present = (reg & DISR5_OCRAM_MASK) ? 0 : 1;
+#elif defined(CONFIG_CHASSIS_2)
+	devdisr5_info.ddrc1_present = (reg & DISR5_DDRC1_MASK) ? 0 : 1;
+	devdisr5_info.ocram_present = (reg & DISR5_OCRAM_MASK) ? 0 : 1;
+#endif
+	devdisr5_info.is_populated = true;
+
+	return (const devdisr5_info_t *) &devdisr5_info;
+}
+
+int get_clocks(struct sysinfo *sys)
+{
+	unsigned int *rcwsr0 = NULL;
+	const unsigned long sysclk = dcfg_init_info->nxp_sysclk_freq;
+	const unsigned long ddrclk = dcfg_init_info->nxp_ddrclk_freq;
+
+	rcwsr0 = (void *)(dcfg_init_info->g_nxp_dcfg_addr + RCWSR0_OFFSET);
+	sys->freq_platform = sysclk;
+	sys->freq_ddr_pll0 = ddrclk;
+	sys->freq_ddr_pll1 = ddrclk;
+
+	sys->freq_platform *= (gur_in32(rcwsr0) >>
+				RCWSR0_SYS_PLL_RAT_SHIFT) &
+				RCWSR0_SYS_PLL_RAT_MASK;
+
+	sys->freq_platform /= dcfg_init_info->nxp_plat_clk_divider;
+
+	sys->freq_ddr_pll0 *= (gur_in32(rcwsr0) >>
+				RCWSR0_MEM_PLL_RAT_SHIFT) &
+				RCWSR0_MEM_PLL_RAT_MASK;
+	sys->freq_ddr_pll1 *= (gur_in32(rcwsr0) >>
+				RCWSR0_MEM2_PLL_RAT_SHIFT) &
+				RCWSR0_MEM2_PLL_RAT_MASK;
+	if (sys->freq_platform == 0) {
+		return 1;
+	} else {
+		return 0;
+	}
+}
+
+#ifdef NXP_SFP_ENABLED
+/*******************************************************************************
+ * Returns true if secur eboot is enabled on board
+ * mode = 0  (development mode - sb_en = 1)
+ * mode = 1 (production mode - ITS = 1)
+ ******************************************************************************/
+bool check_boot_mode_secure(uint32_t *mode)
+{
+	uint32_t val = 0U;
+	uint32_t *rcwsr = NULL;
+	*mode = 0U;
+
+	if (sfp_check_its() == 1) {
+		/* ITS =1 , Production mode */
+		*mode = 1U;
+		return true;
+	}
+
+	rcwsr = (void *)(dcfg_init_info->g_nxp_dcfg_addr + RCWSR_SB_EN_OFFSET);
+
+	val = (gur_in32(rcwsr) >> RCWSR_SBEN_SHIFT) &
+				RCWSR_SBEN_MASK;
+
+	if (val == RCWSR_SBEN_MASK) {
+		*mode = 0U;
+		return true;
+	}
+
+	return false;
+}
+#endif
+
+void error_handler(int error_code)
+{
+	 /* Dump error code in SCRATCH4 register */
+	INFO("Error in Fuse Provisioning: %x\n", error_code);
+	gur_out32((void *)
+		  (dcfg_init_info->g_nxp_dcfg_addr + DCFG_SCRATCH4_OFFSET),
+		  error_code);
+}
diff --git a/drivers/nxp/dcfg/dcfg.mk b/drivers/nxp/dcfg/dcfg.mk
new file mode 100644
index 0000000..206595f
--- /dev/null
+++ b/drivers/nxp/dcfg/dcfg.mk
@@ -0,0 +1,26 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_DCFG},)
+
+ADD_DCFG		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/dcfg
+
+DCFG_SOURCES		+= $(PLAT_DRIVERS_PATH)/dcfg/dcfg.c
+
+ifeq (${BL_COMM_DCFG_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${DCFG_SOURCES}
+else
+ifeq (${BL2_DCFG_NEEDED},yes)
+BL2_SOURCES		+= ${DCFG_SOURCES}
+endif
+ifeq (${BL31_DCFG_NEEDED},yes)
+BL31_SOURCES		+= ${DCFG_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/nxp/ddr/fsl-mmdc/ddr.mk b/drivers/nxp/ddr/fsl-mmdc/ddr.mk
new file mode 100644
index 0000000..afccb62
--- /dev/null
+++ b/drivers/nxp/ddr/fsl-mmdc/ddr.mk
@@ -0,0 +1,19 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+
+# MMDC ddr cntlr driver files
+
+DDR_DRIVERS_PATH	:=	drivers/nxp/ddr
+
+DDR_CNTLR_SOURCES	:=	${PLAT_DRIVERS_PATH}/ddr/fsl-mmdc/fsl_mmdc.c \
+				${PLAT_DRIVERS_PATH}/ddr/nxp-ddr/utility.c	\
+				${PLAT_DRIVERS_PATH}/ddr/nxp-ddr/ddr.c	\
+				${PLAT_DRIVERS_PATH}/ddr/nxp-ddr/ddrc.c
+
+PLAT_INCLUDES		+=	-I$(PLAT_DRIVERS_INCLUDE_PATH)/ddr	\
+				-I$(PLAT_DRIVERS_INCLUDE_PATH)/ddr/fsl-mmdc
+#------------------------------------------------
diff --git a/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.c b/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.c
new file mode 100644
index 0000000..7e6504e
--- /dev/null
+++ b/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.c
@@ -0,0 +1,176 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+/*
+ * Generic driver for Freescale MMDC(Multi Mode DDR Controller).
+ */
+
+#include <errno.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include "ddr_io.h"
+#include <drivers/delay_timer.h>
+#include <fsl_mmdc.h>
+
+static void set_wait_for_bits_clear(void *ptr, unsigned int value,
+				    unsigned int bits)
+{
+	int timeout = 1000;
+
+	ddr_out32(ptr, value);
+
+	while ((ddr_in32(ptr) & bits) != 0) {
+		udelay(100);
+		timeout--;
+	}
+	if (timeout <= 0) {
+		INFO("Error: %llx", (unsigned long long)ptr);
+		INFO(" wait for clear timeout.\n");
+	}
+}
+
+void mmdc_init(const struct fsl_mmdc_info *priv, uintptr_t nxp_ddr_addr)
+{
+	struct mmdc_regs *mmdc = (struct mmdc_regs *)nxp_ddr_addr;
+	unsigned int tmp;
+
+	/* 1. set configuration request */
+	ddr_out32(&mmdc->mdscr, MDSCR_ENABLE_CON_REQ);
+
+	/* 2. configure the desired timing parameters */
+	ddr_out32(&mmdc->mdotc, priv->mdotc);
+	ddr_out32(&mmdc->mdcfg0, priv->mdcfg0);
+	ddr_out32(&mmdc->mdcfg1, priv->mdcfg1);
+	ddr_out32(&mmdc->mdcfg2, priv->mdcfg2);
+
+	/* 3. configure DDR type and other miscellaneous parameters */
+	ddr_out32(&mmdc->mdmisc, priv->mdmisc);
+	ddr_out32(&mmdc->mpmur0, MMDC_MPMUR0_FRC_MSR);
+	ddr_out32(&mmdc->mdrwd, priv->mdrwd);
+	ddr_out32(&mmdc->mpodtctrl, priv->mpodtctrl);
+
+	/* 4. configure the required delay while leaving reset */
+	ddr_out32(&mmdc->mdor, priv->mdor);
+
+	/* 5. configure DDR physical parameters */
+	/* set row/column address width, burst length, data bus width */
+	tmp = priv->mdctl & ~(MDCTL_SDE0 | MDCTL_SDE1);
+	ddr_out32(&mmdc->mdctl, tmp);
+	/* configure address space partition */
+	ddr_out32(&mmdc->mdasp, priv->mdasp);
+
+	/* 6. perform a ZQ calibration - not needed here, doing in #8b */
+
+	/* 7. enable MMDC with the desired chip select */
+#if (DDRC_NUM_CS == 1)
+	ddr_out32(&mmdc->mdctl, tmp | MDCTL_SDE0);
+#elif (DDRC_NUM_CS == 2)
+	ddr_out32(&mmdc->mdctl, tmp | MDCTL_SDE0 | MDCTL_SDE1);
+#else
+#error "Unsupported DDRC_NUM_CS"
+#endif
+
+	/* 8a. dram init sequence: update MRs for ZQ, ODT, PRE, etc */
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(8) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG |
+				CMD_BANK_ADDR_2);
+
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(0) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG |
+				CMD_BANK_ADDR_3);
+
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(4) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG |
+				CMD_BANK_ADDR_1);
+
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_MSB_MR_OP(0x19) |
+				CMD_ADDR_LSB_MR_ADDR(0x30) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG | CMD_BANK_ADDR_0);
+
+	/* 8b. ZQ calibration */
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_MSB_MR_OP(0x4) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_ZQ_CALIBRATION | CMD_BANK_ADDR_0);
+
+	set_wait_for_bits_clear(&mmdc->mpzqhwctrl, priv->mpzqhwctrl,
+				MPZQHWCTRL_ZQ_HW_FORCE);
+
+	/* 9a. calibrations now, wr lvl */
+	ddr_out32(&mmdc->mdscr,  CMD_ADDR_LSB_MR_ADDR(0x84) | MDSCR_WL_EN |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG | CMD_BANK_ADDR_1);
+
+	set_wait_for_bits_clear(&mmdc->mpwlgcr, MPWLGCR_HW_WL_EN,
+				MPWLGCR_HW_WL_EN);
+
+	mdelay(1);
+
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(4) |
+				MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG | CMD_BANK_ADDR_1);
+
+	ddr_out32(&mmdc->mdscr, MDSCR_ENABLE_CON_REQ);
+
+	mdelay(1);
+
+	/* 9b. read DQS gating calibration */
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_MSB_MR_OP(4) | MDSCR_ENABLE_CON_REQ |
+				CMD_PRECHARGE_BANK_OPEN | CMD_BANK_ADDR_0);
+
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(4) | MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG | CMD_BANK_ADDR_3);
+
+	ddr_out32(&mmdc->mppdcmpr2, MPPDCMPR2_MPR_COMPARE_EN);
+
+	/* set absolute read delay offset */
+	if (priv->mprddlctl != 0) {
+		ddr_out32(&mmdc->mprddlctl, priv->mprddlctl);
+	} else {
+		ddr_out32(&mmdc->mprddlctl, MMDC_MPRDDLCTL_DEFAULT_DELAY);
+	}
+
+	set_wait_for_bits_clear(&mmdc->mpdgctrl0,
+				AUTO_RD_DQS_GATING_CALIBRATION_EN,
+				AUTO_RD_DQS_GATING_CALIBRATION_EN);
+
+	ddr_out32(&mmdc->mdscr,  MDSCR_ENABLE_CON_REQ | CMD_LOAD_MODE_REG |
+				CMD_BANK_ADDR_3);
+
+	/* 9c. read calibration */
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_MSB_MR_OP(4) | MDSCR_ENABLE_CON_REQ |
+				CMD_PRECHARGE_BANK_OPEN | CMD_BANK_ADDR_0);
+	ddr_out32(&mmdc->mdscr, CMD_ADDR_LSB_MR_ADDR(4) | MDSCR_ENABLE_CON_REQ |
+				CMD_LOAD_MODE_REG | CMD_BANK_ADDR_3);
+	ddr_out32(&mmdc->mppdcmpr2,  MPPDCMPR2_MPR_COMPARE_EN);
+	set_wait_for_bits_clear(&mmdc->mprddlhwctl,
+				MPRDDLHWCTL_AUTO_RD_CALIBRATION_EN,
+				MPRDDLHWCTL_AUTO_RD_CALIBRATION_EN);
+
+	ddr_out32(&mmdc->mdscr, MDSCR_ENABLE_CON_REQ | CMD_LOAD_MODE_REG |
+				CMD_BANK_ADDR_3);
+
+	/* 10. configure power-down, self-refresh entry, exit parameters */
+	ddr_out32(&mmdc->mdpdc, priv->mdpdc);
+	ddr_out32(&mmdc->mapsr, MMDC_MAPSR_PWR_SAV_CTRL_STAT);
+
+	/* 11. ZQ config again? do nothing here */
+
+	/* 12. refresh scheme */
+	set_wait_for_bits_clear(&mmdc->mdref, priv->mdref,
+				MDREF_START_REFRESH);
+
+	/* 13. disable CON_REQ */
+	ddr_out32(&mmdc->mdscr, MDSCR_DISABLE_CFG_REQ);
+}
diff --git a/drivers/nxp/ddr/nxp-ddr/README.odt b/drivers/nxp/ddr/nxp-ddr/README.odt
new file mode 100644
index 0000000..8796302
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/README.odt
@@ -0,0 +1,31 @@
+Table for dynamic ODT for DDR4 with PHY generation 2
+====================================================
+Two-slot system
+Only symmetric configurations are supported for interleaving. Non-symmetric
+configurations are possible but not covered here. First slot empty is possbile
+but prohibited for simplicity.
++-----------------------+-------------+---------------+-----------------------------+-----------------------------+
+|     Configuration     |             |DRAM controller|           Slot 1            |           Slot 2            |
++-----------+-----------+-------------+-------+-------+--------------+--------------+--------------+--------------+
+|           |           |             |       |       |    Rank 1    |   Rank 2     |   Rank 1     |    Rank 2    |
+|  Slot 1   |  Slot 2   | Write/Read  | Write | Read  |-------+------+-------+------+-------+------+-------+------+
+|           |           |             |       |       | Write | Read | Write | Read | Write | Read | Write | Read |
++-----------+-----------+------+------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |      |Rank 1|  off  |  60   |  240  | off  |   60  | 240  |   60  |  60  |   60  |  60  |
+|           |           |Slot 1|------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |      |Rank 2|  off  |  60   |   60  | 240  |  240  | off  |   60  |  60  |   60  |  60  |
+| Dual Rank | Dual Rank |------+------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |      |Rank 1|  off  |  60   |   60  |  60  |   60  |  60  |  240  | off  |   60  | 240  |
+|           |           |Slot 2|------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |      |Rank 2|  off  |  60   |   60  |  60  |   60  |  60  |   60  | 240  |  240  | off  |
++-----------+-----------+------+------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |  Slot 1     |  off  |  60   |   80  |  off |       |      |       |      |       |      |
+|Single Rank|Single Rank|-------------+-------+-------+-------+------+-------+------+-------+------+-------+------+
+|           |           |  Slot 2     |  off  |  60   |       |      |       |      |   80  | off  |
++-----------+-----------+------+------+-------+-------+-------+------+-------+------+-------+------+
+|           |           |      |Rank 1|  off  |  80   |   80  | off  |  off  | off  |
+| Dual Rank |           |Slot 1|------+-------+-------+-------+------+-------+------+
+|           |           |      |Rank 2|  off  |  80   |   80  | off  |  off  | off  |
++-----------+-----------+-------------+-------+-------+-------+------+-------+------+
+|Single Rank|           |  Slot 1     |  off  |  80   |   80  | off  |
++-----------+-----------+-------------+-------+-------+-------+------+
diff --git a/drivers/nxp/ddr/nxp-ddr/ddr.c b/drivers/nxp/ddr/nxp-ddr/ddr.c
new file mode 100644
index 0000000..c051b3b
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/ddr.c
@@ -0,0 +1,931 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#ifndef CONFIG_DDR_NODIMM
+#include <i2c.h>
+#endif
+#include <nxp_timer.h>
+
+struct dynamic_odt {
+	unsigned int odt_rd_cfg;
+	unsigned int odt_wr_cfg;
+	unsigned int odt_rtt_norm;
+	unsigned int odt_rtt_wr;
+};
+
+#ifndef CONFIG_STATIC_DDR
+#if defined(PHY_GEN2_FW_IMAGE_BUFFER) && !defined(NXP_DDR_PHY_GEN2)
+#error Missing NXP_DDR_PHY_GEN2
+#endif
+#ifdef NXP_DDR_PHY_GEN2
+static const struct dynamic_odt single_D[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs1 */
+		DDR_ODT_NEVER,
+		DDR_ODT_NEVER,
+		DDR4_RTT_OFF,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{}
+};
+
+static const struct dynamic_odt single_S[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{},
+	{},
+};
+
+static const struct dynamic_odt dual_DD[4] = {
+	{	/* cs0 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_60_OHM,
+		DDR4_RTT_WR_240_OHM
+	},
+	{	/* cs1 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_60_OHM,
+		DDR4_RTT_WR_240_OHM
+	},
+	{	/* cs2 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_60_OHM,
+		DDR4_RTT_WR_240_OHM
+	},
+	{	/* cs3 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_60_OHM,
+		DDR4_RTT_WR_240_OHM
+	}
+};
+
+static const struct dynamic_odt dual_SS[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{	/* cs2 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{}
+};
+
+static const struct dynamic_odt dual_D0[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_SAME_DIMM,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs1 */
+		DDR_ODT_NEVER,
+		DDR_ODT_NEVER,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{}
+};
+
+static const struct dynamic_odt dual_S0[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_CS,
+		DDR4_RTT_80_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{},
+	{}
+};
+#else
+static const struct dynamic_odt single_D[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_40_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs1 */
+		DDR_ODT_NEVER,
+		DDR_ODT_NEVER,
+		DDR4_RTT_OFF,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{}
+};
+
+static const struct dynamic_odt single_S[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_ALL,
+		DDR4_RTT_40_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{},
+	{},
+};
+
+static const struct dynamic_odt dual_DD[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_SAME_DIMM,
+		DDR4_RTT_120_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs1 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_OTHER_DIMM,
+		DDR4_RTT_34_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs2 */
+		DDR_ODT_NEVER,
+		DDR_ODT_SAME_DIMM,
+		DDR4_RTT_120_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs3 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_OTHER_DIMM,
+		DDR4_RTT_34_OHM,
+		DDR4_RTT_WR_OFF
+	}
+};
+
+static const struct dynamic_odt dual_SS[4] = {
+	{	/* cs0 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_34_OHM,
+		DDR4_RTT_WR_120_OHM
+	},
+	{},
+	{	/* cs2 */
+		DDR_ODT_OTHER_DIMM,
+		DDR_ODT_ALL,
+		DDR4_RTT_34_OHM,
+		DDR4_RTT_WR_120_OHM
+	},
+	{}
+};
+
+static const struct dynamic_odt dual_D0[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_SAME_DIMM,
+		DDR4_RTT_40_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{	/* cs1 */
+		DDR_ODT_NEVER,
+		DDR_ODT_NEVER,
+		DDR4_RTT_OFF,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{}
+};
+
+static const struct dynamic_odt dual_S0[4] = {
+	{	/* cs0 */
+		DDR_ODT_NEVER,
+		DDR_ODT_CS,
+		DDR4_RTT_40_OHM,
+		DDR4_RTT_WR_OFF
+	},
+	{},
+	{},
+	{}
+};
+#endif /* NXP_DDR_PHY_GEN2 */
+
+/*
+ * Automatically select bank interleaving mode based on DIMMs
+ * in this order: cs0_cs1_cs2_cs3, cs0_cs1, null.
+ * This function only deal with one or two slots per controller.
+ */
+static inline unsigned int auto_bank_intlv(const int cs_in_use,
+					   const struct dimm_params *pdimm)
+{
+	switch (cs_in_use) {
+	case 0xf:
+		return DDR_BA_INTLV_CS0123;
+	case 0x3:
+		return DDR_BA_INTLV_CS01;
+	case 0x1:
+		return DDR_BA_NONE;
+	case 0x5:
+		return DDR_BA_NONE;
+	default:
+		break;
+	}
+
+	return 0U;
+}
+
+static int cal_odt(const unsigned int clk,
+		   struct memctl_opt *popts,
+		   struct ddr_conf *conf,
+		   struct dimm_params *pdimm,
+		   const int dimm_slot_per_ctrl)
+
+{
+	unsigned int i;
+	const struct dynamic_odt *pdodt = NULL;
+
+	const static struct dynamic_odt *table[2][5] = {
+		{single_S, single_D, NULL, NULL},
+		{dual_SS, dual_DD, NULL, NULL},
+	};
+
+	if (dimm_slot_per_ctrl != 1 && dimm_slot_per_ctrl != 2) {
+		ERROR("Unsupported number of DIMMs\n");
+		return -EINVAL;
+	}
+
+	pdodt = table[dimm_slot_per_ctrl - 1][pdimm->n_ranks - 1];
+	if (pdodt == dual_SS) {
+		pdodt = (conf->cs_in_use == 0x5) ? dual_SS :
+			((conf->cs_in_use == 0x1) ? dual_S0 : NULL);
+	} else if (pdodt == dual_DD) {
+		pdodt = (conf->cs_in_use == 0xf) ? dual_DD :
+			((conf->cs_in_use == 0x3) ? dual_D0 : NULL);
+	}
+	if (pdodt == dual_DD && pdimm->package_3ds) {
+		ERROR("Too many 3DS DIMMs.\n");
+		return -EINVAL;
+	}
+
+	if (pdodt == NULL) {
+		ERROR("Error determing ODT.\n");
+		return -EINVAL;
+	}
+
+	/* Pick chip-select local options. */
+	for (i = 0U; i < DDRC_NUM_CS; i++) {
+		debug("cs %d\n", i);
+		popts->cs_odt[i].odt_rd_cfg = pdodt[i].odt_rd_cfg;
+		debug("     odt_rd_cfg 0x%x\n",
+			  popts->cs_odt[i].odt_rd_cfg);
+		popts->cs_odt[i].odt_wr_cfg = pdodt[i].odt_wr_cfg;
+		debug("     odt_wr_cfg 0x%x\n",
+			  popts->cs_odt[i].odt_wr_cfg);
+		popts->cs_odt[i].odt_rtt_norm = pdodt[i].odt_rtt_norm;
+		debug("     odt_rtt_norm 0x%x\n",
+			  popts->cs_odt[i].odt_rtt_norm);
+		popts->cs_odt[i].odt_rtt_wr = pdodt[i].odt_rtt_wr;
+		debug("     odt_rtt_wr 0x%x\n",
+			  popts->cs_odt[i].odt_rtt_wr);
+		popts->cs_odt[i].auto_precharge = 0;
+		debug("     auto_precharge %d\n",
+			  popts->cs_odt[i].auto_precharge);
+	}
+
+	return 0;
+}
+
+static int cal_opts(const unsigned int clk,
+		    struct memctl_opt *popts,
+		    struct ddr_conf *conf,
+		    struct dimm_params *pdimm,
+		    const int dimm_slot_per_ctrl,
+		    const unsigned int ip_rev)
+{
+	popts->rdimm = pdimm->rdimm;
+	popts->mirrored_dimm = pdimm->mirrored_dimm;
+#ifdef CONFIG_DDR_ECC_EN
+	popts->ecc_mode = pdimm->edc_config == 0x02 ? 1 : 0;
+#endif
+	popts->ctlr_init_ecc = popts->ecc_mode;
+	debug("ctlr_init_ecc %d\n", popts->ctlr_init_ecc);
+	popts->self_refresh_in_sleep = 1;
+	popts->dynamic_power = 0;
+
+	/*
+	 * check sdram width, allow platform override
+	 * 0 = 64-bit, 1 = 32-bit, 2 = 16-bit
+	 */
+	if (pdimm->primary_sdram_width == 64) {
+		popts->data_bus_dimm = DDR_DBUS_64;
+		popts->otf_burst_chop_en = 1;
+	} else if (pdimm->primary_sdram_width == 32) {
+		popts->data_bus_dimm = DDR_DBUS_32;
+		popts->otf_burst_chop_en = 0;
+	} else if (pdimm->primary_sdram_width == 16) {
+		popts->data_bus_dimm = DDR_DBUS_16;
+		popts->otf_burst_chop_en = 0;
+	} else {
+		ERROR("primary sdram width invalid!\n");
+		return -EINVAL;
+	}
+	popts->data_bus_used = popts->data_bus_dimm;
+	popts->x4_en = (pdimm->device_width == 4) ? 1 : 0;
+	debug("x4_en %d\n", popts->x4_en);
+
+	/* for RDIMM and DDR4 UDIMM/discrete memory, address parity enable */
+	if (popts->rdimm != 0) {
+		popts->ap_en = 1; /* 0 = disable,  1 = enable */
+	} else {
+		popts->ap_en = 0; /* disabled for DDR4 UDIMM/discrete default */
+	}
+
+	if (ip_rev == 0x50500) {
+		popts->ap_en = 0;
+	}
+
+	debug("ap_en %d\n", popts->ap_en);
+
+	/* BSTTOPRE precharge interval uses 1/4 of refint value. */
+	popts->bstopre = picos_to_mclk(clk, pdimm->refresh_rate_ps) >> 2;
+	popts->tfaw_ps = pdimm->tfaw_ps;
+
+	return 0;
+}
+
+static void cal_intlv(const int num_ctlrs,
+		      struct memctl_opt *popts,
+		      struct ddr_conf *conf,
+		      struct dimm_params *pdimm)
+{
+#ifdef NXP_DDR_INTLV_256B
+	if (num_ctlrs == 2) {
+		popts->ctlr_intlv = 1;
+		popts->ctlr_intlv_mode = DDR_256B_INTLV;
+	}
+#endif
+	debug("ctlr_intlv %d\n", popts->ctlr_intlv);
+	debug("ctlr_intlv_mode %d\n", popts->ctlr_intlv_mode);
+
+	popts->ba_intlv = auto_bank_intlv(conf->cs_in_use, pdimm);
+	debug("ba_intlv 0x%x\n", popts->ba_intlv);
+}
+
+static int update_burst_length(struct memctl_opt *popts)
+{
+	/* Choose burst length. */
+	if ((popts->data_bus_used == DDR_DBUS_32) ||
+	    (popts->data_bus_used == DDR_DBUS_16)) {
+		/* 32-bit or 16-bit bus */
+		popts->otf_burst_chop_en = 0;
+		popts->burst_length = DDR_BL8;
+	} else if (popts->otf_burst_chop_en != 0) { /* on-the-fly burst chop */
+		popts->burst_length = DDR_OTF;	/* on-the-fly BC4 and BL8 */
+	} else {
+		popts->burst_length = DDR_BL8;
+	}
+	debug("data_bus_used %d\n", popts->data_bus_used);
+	debug("otf_burst_chop_en %d\n", popts->otf_burst_chop_en);
+	debug("burst_length 0x%x\n", popts->burst_length);
+	/*
+	 * If a reduced data width is requested, but the SPD
+	 * specifies a physically wider device, adjust the
+	 * computed dimm capacities accordingly before
+	 * assigning addresses.
+	 * 0 = 64-bit, 1 = 32-bit, 2 = 16-bit
+	 */
+	if (popts->data_bus_dimm > popts->data_bus_used) {
+		ERROR("Data bus configuration error\n");
+		return -EINVAL;
+	}
+	popts->dbw_cap_shift = popts->data_bus_used - popts->data_bus_dimm;
+	debug("dbw_cap_shift %d\n", popts->dbw_cap_shift);
+
+	return 0;
+}
+
+int cal_board_params(struct ddr_info *priv,
+		     const struct board_timing *dimm,
+		     int len)
+{
+	const unsigned long speed = priv->clk / 1000000;
+	const struct dimm_params *pdimm = &priv->dimm;
+	struct memctl_opt *popts = &priv->opt;
+	struct rc_timing const *prt = NULL;
+	struct rc_timing const *chosen = NULL;
+	int i;
+
+	for (i = 0; i < len; i++) {
+		if (pdimm->rc == dimm[i].rc) {
+			prt = dimm[i].p;
+			break;
+		}
+	}
+	if (prt == NULL) {
+		ERROR("Board parameters no match.\n");
+		return -EINVAL;
+	}
+	while (prt->speed_bin != 0) {
+		if (speed <= prt->speed_bin) {
+			chosen = prt;
+			break;
+		}
+		prt++;
+	}
+	if (chosen == NULL) {
+		ERROR("timing no match for speed %lu\n", speed);
+		return -EINVAL;
+	}
+	popts->clk_adj = prt->clk_adj;
+	popts->wrlvl_start = prt->wrlvl;
+	popts->wrlvl_ctl_2 = (prt->wrlvl * 0x01010101 + dimm[i].add1) &
+			     0xFFFFFFFF;
+	popts->wrlvl_ctl_3 = (prt->wrlvl * 0x01010101 + dimm[i].add2) &
+			     0xFFFFFFFF;
+
+	return 0;
+}
+
+static int synthesize_ctlr(struct ddr_info *priv)
+{
+	int ret;
+
+	ret = cal_odt(priv->clk,
+		      &priv->opt,
+		      &priv->conf,
+		      &priv->dimm,
+		      priv->dimm_on_ctlr);
+	if (ret != 0) {
+		return ret;
+	}
+
+	ret = cal_opts(priv->clk,
+		       &priv->opt,
+		       &priv->conf,
+		       &priv->dimm,
+		       priv->dimm_on_ctlr,
+		       priv->ip_rev);
+
+	if (ret != 0) {
+		return ret;
+	}
+
+	cal_intlv(priv->num_ctlrs, &priv->opt, &priv->conf, &priv->dimm);
+	ret = ddr_board_options(priv);
+	if (ret != 0) {
+		ERROR("Failed matching board timing.\n");
+	}
+
+	ret = update_burst_length(&priv->opt);
+
+	return ret;
+}
+
+/* Return the bit mask of valid DIMMs found */
+static int parse_spd(struct ddr_info *priv)
+{
+	struct ddr_conf *conf = &priv->conf;
+	struct dimm_params *dimm = &priv->dimm;
+	int j, valid_mask = 0;
+
+#ifdef CONFIG_DDR_NODIMM
+	valid_mask = ddr_get_ddr_params(dimm, conf);
+	if (valid_mask < 0) {
+		ERROR("DDR params error\n");
+		return valid_mask;
+	}
+#else
+	const int *spd_addr = priv->spd_addr;
+	const int num_ctlrs = priv->num_ctlrs;
+	const int num_dimm = priv->dimm_on_ctlr;
+	struct ddr4_spd spd[2];
+	unsigned int spd_checksum[2];
+	int addr_idx = 0;
+	int spd_idx = 0;
+	int ret, addr, i;
+
+	/* Scan all DIMMs */
+	for (i = 0; i < num_ctlrs; i++) {
+		debug("Controller %d\n", i);
+		for (j = 0; j < num_dimm; j++, addr_idx++) {
+			debug("DIMM %d\n", j);
+			addr = spd_addr[addr_idx];
+			if (addr == 0) {
+				if (j == 0) {
+					ERROR("First SPD addr wrong.\n");
+					return -EINVAL;
+				}
+				continue;
+			}
+			debug("addr 0x%x\n", addr);
+			ret = read_spd(addr, &spd[spd_idx],
+				       sizeof(struct ddr4_spd));
+			if (ret != 0) {	/* invalid */
+				debug("Invalid SPD at address 0x%x\n", addr);
+				continue;
+			}
+
+			spd_checksum[spd_idx] =
+				(spd[spd_idx].crc[1] << 24) |
+				(spd[spd_idx].crc[0] << 16) |
+				(spd[spd_idx].mod_section.uc[127] << 8) |
+				(spd[spd_idx].mod_section.uc[126] << 0);
+			debug("checksum 0x%x\n", spd_checksum[spd_idx]);
+			if (spd_checksum[spd_idx] == 0) {
+				debug("Bad checksum, ignored.\n");
+				continue;
+			}
+			if (spd_idx == 0) {
+				/* first valid SPD */
+				ret = cal_dimm_params(&spd[0], dimm);
+				if (ret != 0) {
+					ERROR("SPD calculation error\n");
+					return -EINVAL;
+				}
+			}
+
+			if (spd_idx != 0 && spd_checksum[0] !=
+			    spd_checksum[spd_idx]) {
+				ERROR("Not identical DIMMs.\n");
+				return -EINVAL;
+			}
+			conf->dimm_in_use[j] = 1;
+			valid_mask |= 1 << addr_idx;
+			spd_idx = 1;
+		}
+		debug("done with controller %d\n", i);
+	}
+	switch (num_ctlrs) {
+	case 1:
+		if ((valid_mask & 0x1) == 0) {
+			ERROR("First slot cannot be empty.\n");
+			return -EINVAL;
+		}
+		break;
+	case 2:
+		switch (num_dimm) {
+		case 1:
+			if (valid_mask == 0) {
+				ERROR("Both slot empty\n");
+				return -EINVAL;
+			}
+			break;
+		case 2:
+			if (valid_mask != 0x5 &&
+			    valid_mask != 0xf &&
+			    (valid_mask & 0x7) != 0x4 &&
+			    (valid_mask & 0xd) != 0x1) {
+				ERROR("Invalid DIMM combination.\n");
+				return -EINVAL;
+			}
+			break;
+		default:
+			ERROR("Invalid number of DIMMs.\n");
+			return -EINVAL;
+		}
+		break;
+	default:
+		ERROR("Invalid number of controllers.\n");
+		return -EINVAL;
+	}
+	/* now we have valid and identical DIMMs on controllers */
+#endif	/* CONFIG_DDR_NODIMM */
+
+	debug("cal cs\n");
+	conf->cs_in_use = 0;
+	for (j = 0; j < DDRC_NUM_DIMM; j++) {
+		if (conf->dimm_in_use[j] == 0) {
+			continue;
+		}
+		switch (dimm->n_ranks) {
+		case 4:
+			ERROR("Quad-rank DIMM not supported\n");
+			return -EINVAL;
+		case 2:
+			conf->cs_on_dimm[j] = 0x3 << (j * CONFIG_CS_PER_SLOT);
+			conf->cs_in_use |= conf->cs_on_dimm[j];
+			break;
+		case 1:
+			conf->cs_on_dimm[j] = 0x1 << (j * CONFIG_CS_PER_SLOT);
+			conf->cs_in_use |= conf->cs_on_dimm[j];
+			break;
+		default:
+			ERROR("SPD error with n_ranks\n");
+			return -EINVAL;
+		}
+		debug("cs_in_use = %x\n", conf->cs_in_use);
+		debug("cs_on_dimm[%d] = %x\n", j, conf->cs_on_dimm[j]);
+	}
+#ifndef CONFIG_DDR_NODIMM
+	if (priv->dimm.rdimm != 0) {
+		NOTICE("RDIMM %s\n", priv->dimm.mpart);
+	} else {
+		NOTICE("UDIMM %s\n", priv->dimm.mpart);
+	}
+#else
+	NOTICE("%s\n", priv->dimm.mpart);
+#endif
+
+	return valid_mask;
+}
+
+static unsigned long long assign_intlv_addr(
+	const struct dimm_params *pdimm,
+	const struct memctl_opt *opt,
+	struct ddr_conf *conf,
+	const unsigned long long current_mem_base)
+{
+	int i;
+	int ctlr_density_mul = 0;
+	const unsigned long long rank_density = pdimm->rank_density >>
+						opt->dbw_cap_shift;
+	unsigned long long total_ctlr_mem;
+
+	debug("rank density 0x%llx\n", rank_density);
+	switch (opt->ba_intlv & DDR_BA_INTLV_CS0123) {
+	case DDR_BA_INTLV_CS0123:
+		ctlr_density_mul = 4;
+		break;
+	case DDR_BA_INTLV_CS01:
+		ctlr_density_mul = 2;
+		break;
+	default:
+		ctlr_density_mul = 1;
+		break;
+	}
+	debug("ctlr density mul %d\n", ctlr_density_mul);
+	switch (opt->ctlr_intlv_mode) {
+	case DDR_256B_INTLV:
+		total_ctlr_mem = 2 * ctlr_density_mul * rank_density;
+		break;
+	default:
+		ERROR("Unknown interleaving mode");
+		return 0;
+	}
+	conf->base_addr = current_mem_base;
+	conf->total_mem = total_ctlr_mem;
+
+	/* overwrite cs_in_use bitmask with controller interleaving */
+	conf->cs_in_use = (1 << ctlr_density_mul) - 1;
+	debug("Overwrite cs_in_use as %x\n", conf->cs_in_use);
+
+	/* Fill addr with each cs in use */
+	for (i = 0; i < ctlr_density_mul; i++) {
+		conf->cs_base_addr[i] = current_mem_base;
+		conf->cs_size[i] = total_ctlr_mem;
+		debug("CS %d\n", i);
+		debug("    base_addr 0x%llx\n", conf->cs_base_addr[i]);
+		debug("    size 0x%llx\n", conf->cs_size[i]);
+	}
+
+	return total_ctlr_mem;
+}
+
+static unsigned long long assign_non_intlv_addr(
+	const struct dimm_params *pdimm,
+	const struct memctl_opt *opt,
+	struct ddr_conf *conf,
+	unsigned long long current_mem_base)
+{
+	int i;
+	const unsigned long long rank_density = pdimm->rank_density >>
+						opt->dbw_cap_shift;
+	unsigned long long total_ctlr_mem = 0ULL;
+
+	debug("rank density 0x%llx\n", rank_density);
+	conf->base_addr = current_mem_base;
+
+	/* assign each cs */
+	switch (opt->ba_intlv & DDR_BA_INTLV_CS0123) {
+	case DDR_BA_INTLV_CS0123:
+		for (i = 0; i < DDRC_NUM_CS; i++) {
+			conf->cs_base_addr[i] = current_mem_base;
+			conf->cs_size[i] = rank_density << 2;
+			total_ctlr_mem += rank_density;
+		}
+		break;
+	case DDR_BA_INTLV_CS01:
+		for (i = 0; ((conf->cs_in_use & (1 << i)) != 0) && i < 2; i++) {
+			conf->cs_base_addr[i] = current_mem_base;
+			conf->cs_size[i] = rank_density << 1;
+			total_ctlr_mem += rank_density;
+		}
+		current_mem_base += total_ctlr_mem;
+		for (; ((conf->cs_in_use & (1 << i)) != 0) && i < DDRC_NUM_CS;
+		     i++) {
+			conf->cs_base_addr[i] = current_mem_base;
+			conf->cs_size[i] = rank_density;
+			total_ctlr_mem += rank_density;
+			current_mem_base += rank_density;
+		}
+		break;
+	case DDR_BA_NONE:
+		for (i = 0; ((conf->cs_in_use & (1 << i)) != 0) &&
+			     (i < DDRC_NUM_CS); i++) {
+			conf->cs_base_addr[i] = current_mem_base;
+			conf->cs_size[i] = rank_density;
+			current_mem_base += rank_density;
+			total_ctlr_mem += rank_density;
+		}
+		break;
+	default:
+		ERROR("Unsupported bank interleaving\n");
+		return 0;
+	}
+	for (i = 0; ((conf->cs_in_use & (1 << i)) != 0) &&
+		     (i < DDRC_NUM_CS); i++) {
+		debug("CS %d\n", i);
+		debug("    base_addr 0x%llx\n", conf->cs_base_addr[i]);
+		debug("    size 0x%llx\n", conf->cs_size[i]);
+	}
+
+	return total_ctlr_mem;
+}
+
+unsigned long long assign_addresses(struct ddr_info *priv)
+		   __attribute__ ((weak));
+
+unsigned long long assign_addresses(struct ddr_info *priv)
+{
+	struct memctl_opt *opt = &priv->opt;
+	const struct dimm_params *dimm = &priv->dimm;
+	struct ddr_conf *conf = &priv->conf;
+	unsigned long long current_mem_base = priv->mem_base;
+	unsigned long long total_mem;
+
+	total_mem = 0ULL;
+	debug("ctlr_intlv %d\n", opt->ctlr_intlv);
+	if (opt->ctlr_intlv != 0) {
+		total_mem = assign_intlv_addr(dimm, opt, conf,
+					      current_mem_base);
+	} else {
+		/*
+		 * Simple linear assignment if memory controllers are not
+		 * interleaved. This is only valid for SoCs with single DDRC.
+		 */
+		total_mem = assign_non_intlv_addr(dimm, opt, conf,
+						  current_mem_base);
+	}
+	conf->total_mem = total_mem;
+	debug("base 0x%llx\n", current_mem_base);
+	debug("Total mem by assignment is 0x%llx\n", total_mem);
+
+	return total_mem;
+}
+
+static int cal_ddrc_regs(struct ddr_info *priv)
+{
+	int ret;
+
+	ret = compute_ddrc(priv->clk,
+			   &priv->opt,
+			   &priv->conf,
+			   &priv->ddr_reg,
+			   &priv->dimm,
+			   priv->ip_rev);
+	if (ret != 0) {
+		ERROR("Calculating DDR registers failed\n");
+	}
+
+	return ret;
+}
+
+#endif /* CONFIG_STATIC_DDR */
+
+static int write_ddrc_regs(struct ddr_info *priv)
+{
+	int i;
+	int ret;
+
+	for (i = 0; i < priv->num_ctlrs; i++) {
+		ret = ddrc_set_regs(priv->clk, &priv->ddr_reg, priv->ddr[i], 0);
+		if (ret != 0) {
+			ERROR("Writing DDR register(s) failed\n");
+			return ret;
+		}
+	}
+
+	return 0;
+}
+
+long long dram_init(struct ddr_info *priv
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+		    , uintptr_t nxp_ccn_hn_f0_addr
+#endif
+		)
+{
+	uint64_t time __unused;
+	long long dram_size;
+	int ret;
+	const uint64_t time_base = get_timer_val(0);
+	unsigned int ip_rev = get_ddrc_version(priv->ddr[0]);
+
+	int valid_spd_mask __unused;
+	int scratch = 0x0;
+
+	priv->ip_rev = ip_rev;
+
+#ifndef CONFIG_STATIC_DDR
+	INFO("time base %" PRIu64 " ms\n", time_base);
+	debug("Parse DIMM SPD(s)\n");
+	valid_spd_mask = parse_spd(priv);
+
+	if (valid_spd_mask < 0) {
+		ERROR("Parsing DIMM Error\n");
+		return valid_spd_mask;
+	}
+
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+	if (priv->num_ctlrs == 2 || priv->num_ctlrs == 1) {
+		ret = disable_unused_ddrc(priv, valid_spd_mask,
+					  nxp_ccn_hn_f0_addr);
+		if (ret != 0) {
+			return ret;
+		}
+	}
+#endif
+
+	time = get_timer_val(time_base);
+	INFO("Time after parsing SPD %" PRIu64 " ms\n", time);
+	debug("Synthesize configurations\n");
+	ret = synthesize_ctlr(priv);
+	if (ret != 0) {
+		ERROR("Synthesize config error\n");
+		return ret;
+	}
+
+	debug("Assign binding addresses\n");
+	dram_size = assign_addresses(priv);
+	if (dram_size == 0) {
+		ERROR("Assigning address error\n");
+		return -EINVAL;
+	}
+
+	debug("Calculate controller registers\n");
+	ret = cal_ddrc_regs(priv);
+	if (ret != 0) {
+		ERROR("Calculate register error\n");
+		return ret;
+	}
+
+	ret = compute_ddr_phy(priv);
+	if (ret != 0)
+		ERROR("Calculating DDR PHY registers failed.\n");
+
+#else
+	dram_size = board_static_ddr(priv);
+	if (dram_size == 0) {
+		ERROR("Error getting static DDR settings.\n");
+		return -EINVAL;
+	}
+#endif
+
+	if (priv->warm_boot_flag == DDR_WARM_BOOT) {
+		scratch = (priv->ddr_reg).sdram_cfg[1];
+		scratch = scratch & ~(SDRAM_CFG2_D_INIT);
+		priv->ddr_reg.sdram_cfg[1] = scratch;
+	}
+
+	time = get_timer_val(time_base);
+	INFO("Time before programming controller %" PRIu64 " ms\n", time);
+	debug("Program controller registers\n");
+	ret = write_ddrc_regs(priv);
+	if (ret != 0) {
+		ERROR("Programing DDRC error\n");
+		return ret;
+	}
+
+	puts("");
+	NOTICE("%lld GB ", dram_size >> 30);
+	print_ddr_info(priv->ddr[0]);
+
+	time = get_timer_val(time_base);
+	INFO("Time used by DDR driver %" PRIu64 " ms\n", time);
+
+	return dram_size;
+}
diff --git a/drivers/nxp/ddr/nxp-ddr/ddr.mk b/drivers/nxp/ddr/nxp-ddr/ddr.mk
new file mode 100644
index 0000000..6bdd947
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/ddr.mk
@@ -0,0 +1,76 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq ($(PLAT_DDR_PHY), PHY_GEN2)
+$(eval $(call add_define, PHY_GEN2))
+PLAT_DDR_PHY_DIR		:= phy-gen2
+ifeq (${APPLY_MAX_CDD},yes)
+$(eval $(call add_define,NXP_APPLY_MAX_CDD))
+endif
+
+ifeq (${ERRATA_DDR_A011396}, 1)
+$(eval $(call add_define,ERRATA_DDR_A011396))
+endif
+
+ifeq (${ERRATA_DDR_A050450}, 1)
+$(eval $(call add_define,ERRATA_DDR_A050450))
+endif
+
+endif
+
+ifeq ($(PLAT_DDR_PHY), PHY_GEN1)
+PLAT_DDR_PHY_DIR		:= phy-gen1
+
+ifeq (${ERRATA_DDR_A008511},1)
+$(eval $(call add_define,ERRATA_DDR_A008511))
+endif
+
+ifeq (${ERRATA_DDR_A009803},1)
+$(eval $(call add_define,ERRATA_DDR_A009803))
+endif
+
+ifeq (${ERRATA_DDR_A009942},1)
+$(eval $(call add_define,ERRATA_DDR_A009942))
+endif
+
+ifeq (${ERRATA_DDR_A010165},1)
+$(eval $(call add_define,ERRATA_DDR_A010165))
+endif
+
+endif
+
+ifeq ($(DDR_BIST), yes)
+$(eval $(call add_define, BIST_EN))
+endif
+
+ifeq ($(DDR_DEBUG), yes)
+$(eval $(call add_define, DDR_DEBUG))
+endif
+
+ifeq ($(DDR_PHY_DEBUG), yes)
+$(eval $(call add_define, DDR_PHY_DEBUG))
+endif
+
+ifeq ($(DEBUG_PHY_IO), yes)
+$(eval $(call add_define, DEBUG_PHY_IO))
+endif
+
+ifeq ($(DEBUG_WARM_RESET), yes)
+$(eval $(call add_define, DEBUG_WARM_RESET))
+endif
+
+ifeq ($(DEBUG_DDR_INPUT_CONFIG), yes)
+$(eval $(call add_define, DEBUG_DDR_INPUT_CONFIG))
+endif
+
+DDR_CNTLR_SOURCES	:= $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/ddr.c \
+			   $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/ddrc.c \
+			   $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/dimm.c \
+			   $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/regs.c \
+			   $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/utility.c \
+			   $(PLAT_DRIVERS_PATH)/ddr/$(PLAT_DDR_PHY_DIR)/phy.c
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/ddr
diff --git a/drivers/nxp/ddr/nxp-ddr/ddrc.c b/drivers/nxp/ddr/nxp-ddr/ddrc.c
new file mode 100644
index 0000000..17a2b6a
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/ddrc.c
@@ -0,0 +1,594 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <drivers/delay_timer.h>
+#include <immap.h>
+
+#define BIST_CR		0x80060000
+#define BIST_CR_EN	0x80000000
+#define BIST_CR_STAT	0x00000001
+#define CTLR_INTLV_MASK	0x20000000
+
+#pragma weak run_bist
+
+bool run_bist(void)
+{
+#ifdef BIST_EN
+	return true;
+#else
+	return false;
+#endif
+}
+
+/*
+ * Perform build-in test on memory
+ * timeout value in 10ms
+ */
+int bist(const struct ccsr_ddr *ddr, int timeout)
+{
+	const unsigned int test_pattern[10] = {
+		0xffffffff,
+		0x00000000,
+		0xaaaaaaaa,
+		0x55555555,
+		0xcccccccc,
+		0x33333333,
+		0x12345678,
+		0xabcdef01,
+		0xaa55aa55,
+		0x55aa55aa
+	};
+	unsigned int mtcr, err_detect, err_sbe;
+	unsigned int cs0_config;
+	unsigned int csn_bnds[4];
+	int ret = 0;
+	uint32_t i;
+#ifdef CONFIG_DDR_ADDR_DEC
+	uint32_t dec_9 = ddr_in32(&ddr->dec[9]);
+	uint32_t pos = 0U;
+	uint32_t map_save = 0U;
+	uint32_t temp32 = 0U;
+	uint32_t map, shift, highest;
+#endif
+
+	cs0_config = ddr_in32(&ddr->csn_cfg[0]);
+	if ((cs0_config & CTLR_INTLV_MASK) != 0U) {
+		/* set bnds to non-interleaving */
+		for (i = 0U; i < 4U; i++) {
+			csn_bnds[i] = ddr_in32(&ddr->bnds[i].a);
+			ddr_out32(&ddr->bnds[i].a,
+				  (csn_bnds[i] & U(0xfffefffe)) >> 1U);
+		}
+		ddr_out32(&ddr->csn_cfg[0], cs0_config & ~CTLR_INTLV_MASK);
+#ifdef CONFIG_DDR_ADDR_DEC
+		if ((dec_9 & 0x1U) != 0U) {
+			highest = (dec_9 >> 26U) == U(0x3F) ? 0U : dec_9 >> 26U;
+			pos = 37U;
+			for (i = 0U; i < 36U; i++) {      /* Go through all 37 */
+				if ((i % 4U) == 0U) {
+					temp32 = ddr_in32(&ddr->dec[i >> 2U]);
+				}
+				shift = (3U - i % 4U) * 8U + 2U;
+				map = (temp32 >> shift) & U(0x3F);
+				if (map > highest && map != U(0x3F)) {
+					highest = map;
+					pos = i;
+				}
+			}
+			debug("\nFound highest position %d, mapping to %d, ",
+			      pos, highest);
+			map_save = ddr_in32(&ddr->dec[pos >> 2]);
+			shift = (3U - pos % 4U) * 8U + 2U;
+			debug("in dec[%d], bit %d (0x%x)\n",
+			      pos >> 2U, shift, map_save);
+			temp32 = map_save & ~(U(0x3F) << shift);
+			temp32 |= 8U << shift;
+			ddr_out32(&ddr->dec[pos >> 2U], temp32);
+			timeout <<= 2U;
+			debug("Increase wait time to %d ms\n", timeout * 10);
+		}
+#endif
+	}
+	for (i = 0U; i < 10U; i++) {
+		ddr_out32(&ddr->mtp[i], test_pattern[i]);
+	}
+	mtcr = BIST_CR;
+	ddr_out32(&ddr->mtcr, mtcr);
+	do {
+		mdelay(10);
+		mtcr = ddr_in32(&ddr->mtcr);
+	} while (timeout-- > 0 && ((mtcr & BIST_CR_EN) != 0));
+	if (timeout <= 0) {
+		ERROR("Timeout\n");
+	} else {
+		debug("Timer remains %d\n", timeout);
+	}
+
+	err_detect = ddr_in32(&ddr->err_detect);
+	err_sbe = ddr_in32(&ddr->err_sbe);
+	if (err_detect != 0U || ((err_sbe & U(0xffff)) != 0U)) {
+		ERROR("ECC error detected\n");
+		ret = -EIO;
+	}
+
+	if ((cs0_config & CTLR_INTLV_MASK) != 0) {
+		for (i = 0U; i < 4U; i++) {
+			ddr_out32(&ddr->bnds[i].a, csn_bnds[i]);
+		}
+		ddr_out32(&ddr->csn_cfg[0], cs0_config);
+#ifdef CONFIG_DDR_ADDR_DEC
+		if ((dec_9 & U(0x1)) != 0U) {
+			ddr_out32(&ddr->dec[pos >> 2], map_save);
+		}
+#endif
+	}
+	if ((mtcr & BIST_CR_STAT) != 0) {
+		ERROR("Built-in self test failed\n");
+		ret = -EIO;
+	} else {
+		NOTICE("Build-in self test passed\n");
+	}
+
+	return ret;
+}
+
+void dump_ddrc(unsigned int *ddr)
+{
+#ifdef DDR_DEBUG
+	uint32_t i;
+	unsigned long val;
+
+	for (i = 0U; i < U(0x400); i++, ddr++) {
+		val = ddr_in32(ddr);
+		if (val != 0U) {	/* skip zeros */
+			debug("*0x%lx = 0x%lx\n", (unsigned long)ddr, val);
+		}
+	}
+#endif
+}
+
+#ifdef ERRATA_DDR_A009803
+static void set_wait_for_bits_clear(const void *ptr,
+				    unsigned int value,
+				    unsigned int bits)
+{
+	int timeout = 1000;
+
+	ddr_out32(ptr, value);
+	do {
+		udelay(100);
+	} while (timeout-- > 0 && ((ddr_in32(ptr) & bits) != 0));
+
+	if (timeout <= 0) {
+		ERROR("wait for clear timeout.\n");
+	}
+}
+#endif
+
+#if (DDRC_NUM_CS > 4)
+#error Invalid setting for DDRC_NUM_CS
+#endif
+
+/*
+ * If supported by the platform, writing to DDR controller takes two
+ * passes to deassert DDR reset to comply with JEDEC specs for RDIMMs.
+ */
+int ddrc_set_regs(const unsigned long clk,
+		  const struct ddr_cfg_regs *regs,
+		  const struct ccsr_ddr *ddr,
+		  int twopass)
+{
+	unsigned int i, bus_width;
+	unsigned int temp_sdram_cfg;
+	unsigned int total_mem_per_ctrl, total_mem_per_ctrl_adj;
+	const int mod_bnds = regs->cs[0].config & CTLR_INTLV_MASK;
+	int timeout;
+	int ret = 0;
+#if defined(ERRATA_DDR_A009942) || defined(ERRATA_DDR_A010165)
+	unsigned long ddr_freq;
+	unsigned int tmp;
+#ifdef ERRATA_DDR_A009942
+	unsigned int check;
+	unsigned int cpo_min = U(0xff);
+	unsigned int cpo_max = 0U;
+#endif
+#endif
+
+	if (twopass == 2U) {
+		goto after_reset;
+	}
+
+	/* Set cdr1 first in case 0.9v VDD is enabled for some SoCs*/
+	ddr_out32(&ddr->ddr_cdr1, regs->cdr[0]);
+
+	ddr_out32(&ddr->sdram_clk_cntl, regs->clk_cntl);
+
+	for (i = 0U; i < DDRC_NUM_CS; i++) {
+		if (mod_bnds != 0U) {
+			ddr_out32(&ddr->bnds[i].a,
+				  (regs->cs[i].bnds & U(0xfffefffe)) >> 1U);
+		} else {
+			ddr_out32(&ddr->bnds[i].a, regs->cs[i].bnds);
+		}
+		ddr_out32(&ddr->csn_cfg_2[i], regs->cs[i].config_2);
+	}
+
+	ddr_out32(&ddr->timing_cfg_0, regs->timing_cfg[0]);
+	ddr_out32(&ddr->timing_cfg_1, regs->timing_cfg[1]);
+	ddr_out32(&ddr->timing_cfg_2, regs->timing_cfg[2]);
+	ddr_out32(&ddr->timing_cfg_3, regs->timing_cfg[3]);
+	ddr_out32(&ddr->timing_cfg_4, regs->timing_cfg[4]);
+	ddr_out32(&ddr->timing_cfg_5, regs->timing_cfg[5]);
+	ddr_out32(&ddr->timing_cfg_6, regs->timing_cfg[6]);
+	ddr_out32(&ddr->timing_cfg_7, regs->timing_cfg[7]);
+	ddr_out32(&ddr->timing_cfg_8, regs->timing_cfg[8]);
+	ddr_out32(&ddr->timing_cfg_9, regs->timing_cfg[9]);
+	ddr_out32(&ddr->zq_cntl, regs->zq_cntl);
+	for (i = 0U; i < 4U; i++) {
+		ddr_out32(&ddr->dq_map[i], regs->dq_map[i]);
+	}
+	ddr_out32(&ddr->sdram_cfg_3, regs->sdram_cfg[2]);
+	ddr_out32(&ddr->sdram_mode, regs->sdram_mode[0]);
+	ddr_out32(&ddr->sdram_mode_2, regs->sdram_mode[1]);
+	ddr_out32(&ddr->sdram_mode_3, regs->sdram_mode[2]);
+	ddr_out32(&ddr->sdram_mode_4, regs->sdram_mode[3]);
+	ddr_out32(&ddr->sdram_mode_5, regs->sdram_mode[4]);
+	ddr_out32(&ddr->sdram_mode_6, regs->sdram_mode[5]);
+	ddr_out32(&ddr->sdram_mode_7, regs->sdram_mode[6]);
+	ddr_out32(&ddr->sdram_mode_8, regs->sdram_mode[7]);
+	ddr_out32(&ddr->sdram_mode_9, regs->sdram_mode[8]);
+	ddr_out32(&ddr->sdram_mode_10, regs->sdram_mode[9]);
+	ddr_out32(&ddr->sdram_mode_11, regs->sdram_mode[10]);
+	ddr_out32(&ddr->sdram_mode_12, regs->sdram_mode[11]);
+	ddr_out32(&ddr->sdram_mode_13, regs->sdram_mode[12]);
+	ddr_out32(&ddr->sdram_mode_14, regs->sdram_mode[13]);
+	ddr_out32(&ddr->sdram_mode_15, regs->sdram_mode[14]);
+	ddr_out32(&ddr->sdram_mode_16, regs->sdram_mode[15]);
+	ddr_out32(&ddr->sdram_md_cntl, regs->md_cntl);
+#ifdef ERRATA_DDR_A009663
+	ddr_out32(&ddr->sdram_interval,
+		  regs->interval & ~SDRAM_INTERVAL_BSTOPRE);
+#else
+	ddr_out32(&ddr->sdram_interval, regs->interval);
+#endif
+	ddr_out32(&ddr->sdram_data_init, regs->data_init);
+	if (regs->eor != 0) {
+		ddr_out32(&ddr->eor, regs->eor);
+	}
+
+	ddr_out32(&ddr->wrlvl_cntl, regs->wrlvl_cntl[0]);
+#ifndef NXP_DDR_EMU
+	/*
+	 * Skip these two registers if running on emulator
+	 * because emulator doesn't have skew between bytes.
+	 */
+
+	if (regs->wrlvl_cntl[1] != 0) {
+		ddr_out32(&ddr->ddr_wrlvl_cntl_2, regs->wrlvl_cntl[1]);
+	}
+	if (regs->wrlvl_cntl[2] != 0) {
+		ddr_out32(&ddr->ddr_wrlvl_cntl_3, regs->wrlvl_cntl[2]);
+	}
+#endif
+
+	ddr_out32(&ddr->ddr_sr_cntr, regs->ddr_sr_cntr);
+	ddr_out32(&ddr->ddr_sdram_rcw_1, regs->sdram_rcw[0]);
+	ddr_out32(&ddr->ddr_sdram_rcw_2, regs->sdram_rcw[1]);
+	ddr_out32(&ddr->ddr_sdram_rcw_3, regs->sdram_rcw[2]);
+	ddr_out32(&ddr->ddr_sdram_rcw_4, regs->sdram_rcw[3]);
+	ddr_out32(&ddr->ddr_sdram_rcw_5, regs->sdram_rcw[4]);
+	ddr_out32(&ddr->ddr_sdram_rcw_6, regs->sdram_rcw[5]);
+	ddr_out32(&ddr->ddr_cdr2, regs->cdr[1]);
+	ddr_out32(&ddr->sdram_cfg_2, regs->sdram_cfg[1]);
+	ddr_out32(&ddr->init_addr, regs->init_addr);
+	ddr_out32(&ddr->init_ext_addr, regs->init_ext_addr);
+
+#ifdef ERRATA_DDR_A009803
+	/* part 1 of 2 */
+	if ((regs->sdram_cfg[1] & SDRAM_CFG2_AP_EN) != 0) {
+		if ((regs->sdram_cfg[0] & SDRAM_CFG_RD_EN) != 0) {
+			ddr_out32(&ddr->ddr_sdram_rcw_2,
+				  regs->sdram_rcw[1] & ~0xf0);
+		}
+
+		ddr_out32(&ddr->err_disable,
+				regs->err_disable | DDR_ERR_DISABLE_APED);
+	}
+#else
+	ddr_out32(&ddr->err_disable, regs->err_disable);
+#endif
+	ddr_out32(&ddr->err_int_en, regs->err_int_en);
+
+	/* For DDRC 5.05 only */
+	if (get_ddrc_version(ddr) == 0x50500) {
+		ddr_out32(&ddr->tx_cfg[1], 0x1f1f1f1f);
+		ddr_out32(&ddr->debug[3], 0x124a02c0);
+	}
+
+	for (i = 0U; i < 4U; i++) {
+		if (regs->tx_cfg[i] != 0) {
+			ddr_out32(&ddr->tx_cfg[i], regs->tx_cfg[i]);
+		}
+	}
+	for (i = 0U; i < 64U; i++) {
+		if (regs->debug[i] != 0) {
+#ifdef ERRATA_DDR_A009942
+			if (i == 28U) {
+				continue;
+			}
+#endif
+			ddr_out32(&ddr->debug[i], regs->debug[i]);
+		}
+	}
+#ifdef CONFIG_DDR_ADDR_DEC
+	if ((regs->dec[9] & 1) != 0U) {
+		for (i = 0U; i < 10U; i++) {
+			ddr_out32(&ddr->dec[i], regs->dec[i]);
+		}
+		if (mod_bnds != 0) {
+			debug("Disable address decoding\n");
+			ddr_out32(&ddr->dec[9], 0);
+		}
+	}
+#endif
+
+#ifdef ERRATA_DDR_A008511
+	/* Part 1 of 2 */
+	/* This erraum only applies to verion 5.2.1 */
+	if (get_ddrc_version(ddr) == 0x50200) {
+		ERROR("Unsupported SoC.\n");
+	} else if (get_ddrc_version(ddr) == 0x50201) {
+		ddr_out32(&ddr->debug[37], (U(1) << 31));
+		ddr_out32(&ddr->ddr_cdr2,
+			  regs->cdr[1] | DDR_CDR2_VREF_TRAIN_EN);
+	} else {
+		debug("Erratum A008511 doesn't apply.\n");
+	}
+#endif
+
+#ifdef ERRATA_DDR_A009942
+	ddr_freq = clk / 1000000U;
+	tmp = ddr_in32(&ddr->debug[28]);
+	tmp &= U(0xff0fff00);
+	tmp |= ddr_freq <= 1333U ? U(0x0080006a) :
+		(ddr_freq <= 1600U ? U(0x0070006f) :
+		 (ddr_freq <= 1867U ? U(0x00700076) : U(0x0060007b)));
+	if (regs->debug[28] != 0) {
+		tmp &= ~0xff;
+		tmp |= regs->debug[28] & 0xff;
+	} else {
+		WARN("Warning: Optimal CPO value not set.\n");
+	}
+	ddr_out32(&ddr->debug[28], tmp);
+#endif
+
+#ifdef ERRATA_DDR_A010165
+	ddr_freq = clk / 1000000U;
+	if ((ddr_freq > 1900) && (ddr_freq < 2300)) {
+		tmp = ddr_in32(&ddr->debug[28]);
+		ddr_out32(&ddr->debug[28], tmp | 0x000a0000);
+	}
+#endif
+	/*
+	 * For RDIMMs, JEDEC spec requires clocks to be stable before reset is
+	 * deasserted. Clocks start when any chip select is enabled and clock
+	 * control register is set. Because all DDR components are connected to
+	 * one reset signal, this needs to be done in two steps. Step 1 is to
+	 * get the clocks started. Step 2 resumes after reset signal is
+	 * deasserted.
+	 */
+	if (twopass == 1) {
+		udelay(200);
+		return 0;
+	}
+
+	/* As per new sequence flow shall be write CSn_CONFIG registers needs to
+	 * be set after all the other DDR controller registers are set, then poll
+	 * for PHY_INIT_CMPLT = 1 , then wait at least 100us (micro seconds),
+	 * then set the MEM_EN = 1
+	 */
+	for (i = 0U; i < DDRC_NUM_CS; i++) {
+		if (mod_bnds != 0U && i == 0U) {
+			ddr_out32(&ddr->csn_cfg[i],
+					(regs->cs[i].config & ~CTLR_INTLV_MASK));
+		} else {
+			ddr_out32(&ddr->csn_cfg[i], regs->cs[i].config);
+		}
+	}
+
+after_reset:
+	/* Set, but do not enable the memory */
+	temp_sdram_cfg = regs->sdram_cfg[0];
+	temp_sdram_cfg &= ~(SDRAM_CFG_MEM_EN);
+	ddr_out32(&ddr->sdram_cfg, temp_sdram_cfg);
+
+	if (get_ddrc_version(ddr) < U(0x50500)) {
+		/*
+		 * 500 painful micro-seconds must elapse between
+		 * the DDR clock setup and the DDR config enable.
+		 * DDR2 need 200 us, and DDR3 need 500 us from spec,
+		 * we choose the max, that is 500 us for all of case.
+		 */
+		udelay(500);
+		/* applied memory barrier */
+		mb();
+		isb();
+	} else {
+		/* wait for PHY complete */
+		timeout = 40;
+		while (((ddr_in32(&ddr->ddr_dsr2) & 0x4) != 0) &&
+		       (timeout > 0)) {
+			udelay(500);
+			timeout--;
+		}
+		if (timeout <= 0) {
+			printf("PHY handshake timeout, ddr_dsr2 = %x\n",
+			       ddr_in32(&ddr->ddr_dsr2));
+		} else {
+			debug("PHY handshake completed, timer remains %d\n",
+			      timeout);
+		}
+	}
+
+	temp_sdram_cfg = ddr_in32(&ddr->sdram_cfg);
+	/* Let the controller go */
+	udelay(100);
+	ddr_out32(&ddr->sdram_cfg, temp_sdram_cfg | SDRAM_CFG_MEM_EN);
+
+	/* applied memory barrier */
+	mb();
+	isb();
+
+	total_mem_per_ctrl = 0;
+	for (i = 0; i < DDRC_NUM_CS; i++) {
+		if ((regs->cs[i].config & 0x80000000) == 0) {
+			continue;
+		}
+		total_mem_per_ctrl += 1 << (
+			((regs->cs[i].config >> 14) & 0x3) + 2 +
+			((regs->cs[i].config >> 8) & 0x7) + 12 +
+			((regs->cs[i].config >> 4) & 0x3) + 0 +
+			((regs->cs[i].config >> 0) & 0x7) + 8 +
+			((regs->sdram_cfg[2] >> 4) & 0x3) +
+			3 - ((regs->sdram_cfg[0] >> 19) & 0x3) -
+			26);		/* minus 26 (count of 64M) */
+	}
+	total_mem_per_ctrl_adj = total_mem_per_ctrl;
+	/*
+	 * total memory / bus width = transactions needed
+	 * transactions needed / data rate = seconds
+	 * to add plenty of buffer, double the time
+	 * For example, 2GB on 666MT/s 64-bit bus takes about 402ms
+	 * Let's wait for 800ms
+	 */
+	bus_width = 3 - ((ddr_in32(&ddr->sdram_cfg) & SDRAM_CFG_DBW_MASK)
+			>> SDRAM_CFG_DBW_SHIFT);
+	timeout = ((total_mem_per_ctrl_adj << (6 - bus_width)) * 100 /
+		   (clk >> 20)) << 2;
+	total_mem_per_ctrl_adj >>= 4;	/* shift down to gb size */
+	if ((ddr_in32(&ddr->sdram_cfg_2) & SDRAM_CFG2_D_INIT) != 0) {
+		debug("total size %d GB\n", total_mem_per_ctrl_adj);
+		debug("Need to wait up to %d ms\n", timeout * 10);
+
+		do {
+			mdelay(10);
+		} while (timeout-- > 0 &&
+			 ((ddr_in32(&ddr->sdram_cfg_2) & SDRAM_CFG2_D_INIT)) != 0);
+
+		if (timeout <= 0) {
+			if (ddr_in32(&ddr->debug[1]) & 0x3d00) {
+				ERROR("Found training error(s): 0x%x\n",
+				      ddr_in32(&ddr->debug[1]));
+			}
+			ERROR("Error: Waiting for D_INIT timeout.\n");
+			return -EIO;
+		}
+	}
+
+	if (mod_bnds != 0U) {
+		debug("Restore original bnds\n");
+		for (i = 0U; i < DDRC_NUM_CS; i++) {
+			ddr_out32(&ddr->bnds[i].a, regs->cs[i].bnds);
+		}
+		ddr_out32(&ddr->csn_cfg[0], regs->cs[0].config);
+#ifdef CONFIG_DDR_ADDR_DEC
+		if ((regs->dec[9] & U(0x1)) != 0U) {
+			debug("Restore address decoding\n");
+			ddr_out32(&ddr->dec[9], regs->dec[9]);
+		}
+#endif
+	}
+
+#ifdef ERRATA_DDR_A009803
+	/* Part 2 of 2 */
+	if ((regs->sdram_cfg[1] & SDRAM_CFG2_AP_EN) != 0) {
+		timeout = 400;
+		do {
+			mdelay(1);
+		} while (timeout-- > 0 && ((ddr_in32(&ddr->debug[1]) & 0x2) == 0));
+
+		if ((regs->sdram_cfg[0] & SDRAM_CFG_RD_EN) != 0) {
+			for (i = 0U; i < DDRC_NUM_CS; i++) {
+				if ((regs->cs[i].config & SDRAM_CS_CONFIG_EN) == 0) {
+					continue;
+				}
+				set_wait_for_bits_clear(&ddr->sdram_md_cntl,
+						MD_CNTL_MD_EN |
+						MD_CNTL_CS_SEL(i) |
+						0x070000ed,
+						MD_CNTL_MD_EN);
+				udelay(1);
+			}
+		}
+
+		ddr_out32(&ddr->err_disable,
+			  regs->err_disable & ~DDR_ERR_DISABLE_APED);
+	}
+#endif
+
+#ifdef ERRATA_DDR_A009663
+	ddr_out32(&ddr->sdram_interval, regs->interval);
+#endif
+
+#ifdef ERRATA_DDR_A009942
+	timeout = 400;
+	do {
+		mdelay(1);
+	} while (timeout-- > 0 && ((ddr_in32(&ddr->debug[1]) & 0x2) == 0));
+	tmp = (regs->sdram_cfg[0] >> 19) & 0x3;
+	check = (tmp == DDR_DBUS_64) ? 4 : ((tmp == DDR_DBUS_32) ? 2 : 1);
+	for (i = 0; i < check; i++) {
+		tmp = ddr_in32(&ddr->debug[9 + i]);
+		debug("Reading debug[%d] as 0x%x\n", i + 9, tmp);
+		cpo_min = min(cpo_min,
+			      min((tmp >> 24) & 0xff, (tmp >> 8) & 0xff));
+		cpo_max = max(cpo_max,
+			      max((tmp >> 24) & 0xff, (tmp >> 8) & 0xff));
+	}
+	if ((regs->sdram_cfg[0] & SDRAM_CFG_ECC_EN) != 0) {
+		tmp = ddr_in32(&ddr->debug[13]);
+		cpo_min = min(cpo_min, (tmp >> 24) & 0xff);
+		cpo_max = max(cpo_max, (tmp >> 24) & 0xff);
+	}
+	debug("cpo_min 0x%x\n", cpo_min);
+	debug("cpo_max 0x%x\n", cpo_max);
+	tmp = ddr_in32(&ddr->debug[28]);
+	debug("debug[28] 0x%x\n", tmp);
+	if ((cpo_min + 0x3B) < (tmp & 0xff)) {
+		WARN("Warning: A009942 requires setting cpo_sample to 0x%x\n",
+		     (cpo_min + cpo_max) / 2 + 0x27);
+	} else {
+		debug("Optimal cpo_sample 0x%x\n",
+			(cpo_min + cpo_max) / 2 + 0x27);
+	}
+#endif
+	if (run_bist() != 0) {
+		if ((ddr_in32(&ddr->debug[1]) &
+		    ((get_ddrc_version(ddr) == 0x50500) ? 0x3c00 : 0x3d00)) != 0) {
+			ERROR("Found training error(s): 0x%x\n",
+			     ddr_in32(&ddr->debug[1]));
+			return -EIO;
+		}
+		INFO("Running built-in self test ...\n");
+		/* give it 10x time to cover whole memory */
+		timeout = ((total_mem_per_ctrl << (6 - bus_width)) *
+			   100 / (clk >> 20)) * 10;
+		INFO("\tWait up to %d ms\n", timeout * 10);
+		ret = bist(ddr, timeout);
+	}
+	dump_ddrc((void *)ddr);
+
+	return ret;
+}
diff --git a/drivers/nxp/ddr/nxp-ddr/dimm.c b/drivers/nxp/ddr/nxp-ddr/dimm.c
new file mode 100644
index 0000000..16efcba
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/dimm.c
@@ -0,0 +1,399 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <dimm.h>
+#include <i2c.h>
+#include <lib/utils.h>
+
+int read_spd(unsigned char chip, void *buf, int len)
+{
+	unsigned char dummy = 0U;
+	int ret;
+
+	if (len < 256) {
+		ERROR("Invalid SPD length\n");
+		return -EINVAL;
+	}
+
+	i2c_write(SPD_SPA0_ADDRESS, 0, 1, &dummy, 1);
+	ret = i2c_read(chip, 0, 1, buf, 256);
+	if (ret == 0) {
+		i2c_write(SPD_SPA1_ADDRESS, 0, 1, &dummy, 1);
+		ret = i2c_read(chip, 0, 1, buf + 256, min(256, len - 256));
+	}
+	if (ret != 0) {
+		zeromem(buf, len);
+	}
+
+	return ret;
+}
+
+int crc16(unsigned char *ptr, int count)
+{
+	int i;
+	int crc = 0;
+
+	while (--count >= 0) {
+		crc = crc ^ (int)*ptr++ << 8;
+		for (i = 0; i < 8; ++i) {
+			if ((crc & 0x8000) != 0) {
+				crc = crc << 1 ^ 0x1021;
+			} else {
+				crc = crc << 1;
+			}
+		}
+	}
+	return crc & 0xffff;
+}
+
+static int ddr4_spd_check(const struct ddr4_spd *spd)
+{
+	void *p = (void *)spd;
+	int csum16;
+	int len;
+	char crc_lsb;	/* byte 126 */
+	char crc_msb;	/* byte 127 */
+
+	len = 126;
+	csum16 = crc16(p, len);
+
+	crc_lsb = (char) (csum16 & 0xff);
+	crc_msb = (char) (csum16 >> 8);
+
+	if (spd->crc[0] != crc_lsb || spd->crc[1] != crc_msb) {
+		ERROR("SPD CRC = 0x%x%x, computed CRC = 0x%x%x\n",
+		      spd->crc[1], spd->crc[0], crc_msb, crc_lsb);
+		return -EINVAL;
+	}
+
+	p = (void *)spd + 128;
+	len = 126;
+	csum16 = crc16(p, len);
+
+	crc_lsb = (char) (csum16 & 0xff);
+	crc_msb = (char) (csum16 >> 8);
+
+	if (spd->mod_section.uc[126] != crc_lsb ||
+	    spd->mod_section.uc[127] != crc_msb) {
+		ERROR("SPD CRC = 0x%x%x, computed CRC = 0x%x%x\n",
+		      spd->mod_section.uc[127], spd->mod_section.uc[126],
+		      crc_msb, crc_lsb);
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+static unsigned long long
+compute_ranksize(const struct ddr4_spd *spd)
+{
+	unsigned long long bsize;
+
+	int nbit_sdram_cap_bsize = 0;
+	int nbit_primary_bus_width = 0;
+	int nbit_sdram_width = 0;
+	int die_count = 0;
+	bool package_3ds;
+
+	if ((spd->density_banks & 0xf) <= 7) {
+		nbit_sdram_cap_bsize = (spd->density_banks & 0xf) + 28;
+	}
+	if ((spd->bus_width & 0x7) < 4) {
+		nbit_primary_bus_width = (spd->bus_width & 0x7) + 3;
+	}
+	if ((spd->organization & 0x7) < 4) {
+		nbit_sdram_width = (spd->organization & 0x7) + 2;
+	}
+	package_3ds = (spd->package_type & 0x3) == 0x2;
+	if (package_3ds) {
+		die_count = (spd->package_type >> 4) & 0x7;
+	}
+
+	bsize = 1ULL << (nbit_sdram_cap_bsize - 3 +
+			 nbit_primary_bus_width - nbit_sdram_width +
+			 die_count);
+
+	return bsize;
+}
+
+int cal_dimm_params(const struct ddr4_spd *spd, struct dimm_params *pdimm)
+{
+	int ret;
+	int i;
+	static const unsigned char udimm_rc_e_dq[18] = {
+		0x0c, 0x2c, 0x15, 0x35, 0x15, 0x35, 0x0b, 0x2c, 0x15,
+		0x35, 0x0b, 0x35, 0x0b, 0x2c, 0x0b, 0x35, 0x15, 0x36
+	};
+	int spd_error = 0;
+	unsigned char *ptr;
+	unsigned char val;
+
+	if (spd->mem_type != SPD_MEMTYPE_DDR4) {
+		ERROR("Not a DDR4 DIMM.\n");
+		return -EINVAL;
+	}
+
+	ret = ddr4_spd_check(spd);
+	if (ret != 0) {
+		ERROR("DIMM SPD checksum mismatch\n");
+		return -EINVAL;
+	}
+
+	/*
+	 * The part name in ASCII in the SPD EEPROM is not null terminated.
+	 * Guarantee null termination here by presetting all bytes to 0
+	 * and copying the part name in ASCII from the SPD onto it
+	 */
+	if ((spd->info_size_crc & 0xF) > 2) {
+		memcpy(pdimm->mpart, spd->mpart, sizeof(pdimm->mpart) - 1);
+	}
+
+	/* DIMM organization parameters */
+	pdimm->n_ranks = ((spd->organization >> 3) & 0x7) + 1;
+	debug("n_ranks %d\n", pdimm->n_ranks);
+	pdimm->rank_density = compute_ranksize(spd);
+	if (pdimm->rank_density == 0) {
+		return -EINVAL;
+	}
+
+	debug("rank_density 0x%llx\n", pdimm->rank_density);
+	pdimm->capacity = pdimm->n_ranks * pdimm->rank_density;
+	debug("capacity 0x%llx\n", pdimm->capacity);
+	pdimm->die_density = spd->density_banks & 0xf;
+	debug("die density 0x%x\n", pdimm->die_density);
+	pdimm->primary_sdram_width = 1 << (3 + (spd->bus_width & 0x7));
+	debug("primary_sdram_width %d\n", pdimm->primary_sdram_width);
+	if (((spd->bus_width >> 3) & 0x3) != 0) {
+		pdimm->ec_sdram_width = 8;
+	} else {
+		pdimm->ec_sdram_width = 0;
+	}
+	debug("ec_sdram_width %d\n", pdimm->ec_sdram_width);
+	pdimm->device_width = 1 << ((spd->organization & 0x7) + 2);
+	debug("device_width %d\n", pdimm->device_width);
+	pdimm->package_3ds = (spd->package_type & 0x3) == 0x2 ?
+			     (spd->package_type >> 4) & 0x7 : 0;
+	debug("package_3ds %d\n", pdimm->package_3ds);
+
+	switch (spd->module_type & DDR4_SPD_MODULETYPE_MASK) {
+	case DDR4_SPD_RDIMM:
+	case DDR4_SPD_MINI_RDIMM:
+	case DDR4_SPD_72B_SO_RDIMM:
+		pdimm->rdimm = 1;
+		pdimm->rc = spd->mod_section.registered.ref_raw_card & 0x8f;
+		if ((spd->mod_section.registered.reg_map & 0x1) != 0) {
+			pdimm->mirrored_dimm = 1;
+		}
+		val = spd->mod_section.registered.ca_stren;
+		pdimm->rcw[3] = val >> 4;
+		pdimm->rcw[4] = ((val & 0x3) << 2) | ((val & 0xc) >> 2);
+		val = spd->mod_section.registered.clk_stren;
+		pdimm->rcw[5] = ((val & 0x3) << 2) | ((val & 0xc) >> 2);
+		pdimm->rcw[6] = 0xf;
+		/* A17 used for 16Gb+, C[2:0] used for 3DS */
+		pdimm->rcw[8] = pdimm->die_density >= 0x6 ? 0x0 : 0x8 |
+				(pdimm->package_3ds > 0x3 ? 0x0 :
+				 (pdimm->package_3ds > 0x1 ? 0x1 :
+				  (pdimm->package_3ds > 0 ? 0x2 : 0x3)));
+		if (pdimm->package_3ds != 0 || pdimm->n_ranks != 4) {
+			pdimm->rcw[13] = 0x4;
+		} else {
+			pdimm->rcw[13] = 0x5;
+		}
+		pdimm->rcw[13] |= pdimm->mirrored_dimm ? 0x8 : 0;
+		break;
+
+	case DDR4_SPD_UDIMM:
+	case DDR4_SPD_SO_DIMM:
+	case DDR4_SPD_MINI_UDIMM:
+	case DDR4_SPD_72B_SO_UDIMM:
+	case DDR4_SPD_16B_SO_DIMM:
+	case DDR4_SPD_32B_SO_DIMM:
+		pdimm->rc = spd->mod_section.unbuffered.ref_raw_card & 0x8f;
+		if ((spd->mod_section.unbuffered.addr_mapping & 0x1) != 0) {
+			pdimm->mirrored_dimm = 1;
+		}
+		if ((spd->mod_section.unbuffered.mod_height & 0xe0) == 0 &&
+		    (spd->mod_section.unbuffered.ref_raw_card == 0x04)) {
+			/* Fix SPD error found on DIMMs with raw card E0 */
+			for (i = 0; i < 18; i++) {
+				if (spd->mapping[i] == udimm_rc_e_dq[i]) {
+					continue;
+				}
+				spd_error = 1;
+				ptr = (unsigned char *)&spd->mapping[i];
+				*ptr = udimm_rc_e_dq[i];
+			}
+			if (spd_error != 0) {
+				INFO("SPD DQ mapping error fixed\n");
+			}
+		}
+		break;
+
+	default:
+		ERROR("Unknown module_type 0x%x\n", spd->module_type);
+		return -EINVAL;
+	}
+	debug("rdimm %d\n", pdimm->rdimm);
+	debug("mirrored_dimm %d\n", pdimm->mirrored_dimm);
+	debug("rc 0x%x\n", pdimm->rc);
+
+	/* SDRAM device parameters */
+	pdimm->n_row_addr = ((spd->addressing >> 3) & 0x7) + 12;
+	debug("n_row_addr %d\n", pdimm->n_row_addr);
+	pdimm->n_col_addr = (spd->addressing & 0x7) + 9;
+	debug("n_col_addr %d\n", pdimm->n_col_addr);
+	pdimm->bank_addr_bits = (spd->density_banks >> 4) & 0x3;
+	debug("bank_addr_bits %d\n", pdimm->bank_addr_bits);
+	pdimm->bank_group_bits = (spd->density_banks >> 6) & 0x3;
+	debug("bank_group_bits %d\n", pdimm->bank_group_bits);
+
+	if (pdimm->ec_sdram_width != 0) {
+		pdimm->edc_config = 0x02;
+	} else {
+		pdimm->edc_config = 0x00;
+	}
+	debug("edc_config %d\n", pdimm->edc_config);
+
+	/* DDR4 spec has BL8 -bit3, BC4 -bit2 */
+	pdimm->burst_lengths_bitmask = 0x0c;
+	debug("burst_lengths_bitmask 0x%x\n", pdimm->burst_lengths_bitmask);
+
+	/* MTB - medium timebase
+	 * The MTB in the SPD spec is 125ps,
+	 *
+	 * FTB - fine timebase
+	 * use 1/10th of ps as our unit to avoid floating point
+	 * eg, 10 for 1ps, 25 for 2.5ps, 50 for 5ps
+	 */
+	if ((spd->timebases & 0xf) == 0x0) {
+		pdimm->mtb_ps = 125;
+		pdimm->ftb_10th_ps = 10;
+
+	} else {
+		ERROR("Unknown Timebases\n");
+		return -EINVAL;
+	}
+
+	/* sdram minimum cycle time */
+	pdimm->tckmin_x_ps = spd_to_ps(spd->tck_min, spd->fine_tck_min);
+	debug("tckmin_x_ps %d\n", pdimm->tckmin_x_ps);
+
+	/* sdram max cycle time */
+	pdimm->tckmax_ps = spd_to_ps(spd->tck_max, spd->fine_tck_max);
+	debug("tckmax_ps %d\n", pdimm->tckmax_ps);
+
+	/*
+	 * CAS latency supported
+	 * bit0 - CL7
+	 * bit4 - CL11
+	 * bit8 - CL15
+	 * bit12- CL19
+	 * bit16- CL23
+	 */
+	pdimm->caslat_x  = (spd->caslat_b1 << 7)	|
+			   (spd->caslat_b2 << 15)	|
+			   (spd->caslat_b3 << 23);
+	debug("caslat_x 0x%x\n", pdimm->caslat_x);
+
+	if (spd->caslat_b4 != 0) {
+		WARN("Unhandled caslat_b4 value\n");
+	}
+
+	/*
+	 * min CAS latency time
+	 */
+	pdimm->taa_ps = spd_to_ps(spd->taa_min, spd->fine_taa_min);
+	debug("taa_ps %d\n", pdimm->taa_ps);
+
+	/*
+	 * min RAS to CAS delay time
+	 */
+	pdimm->trcd_ps = spd_to_ps(spd->trcd_min, spd->fine_trcd_min);
+	debug("trcd_ps %d\n", pdimm->trcd_ps);
+
+	/*
+	 * Min Row Precharge Delay Time
+	 */
+	pdimm->trp_ps = spd_to_ps(spd->trp_min, spd->fine_trp_min);
+	debug("trp_ps %d\n", pdimm->trp_ps);
+
+	/* min active to precharge delay time */
+	pdimm->tras_ps = (((spd->tras_trc_ext & 0xf) << 8) +
+			  spd->tras_min_lsb) * pdimm->mtb_ps;
+	debug("tras_ps %d\n", pdimm->tras_ps);
+
+	/* min active to actice/refresh delay time */
+	pdimm->trc_ps = spd_to_ps((((spd->tras_trc_ext & 0xf0) << 4) +
+				   spd->trc_min_lsb), spd->fine_trc_min);
+	debug("trc_ps %d\n", pdimm->trc_ps);
+	/* Min Refresh Recovery Delay Time */
+	pdimm->trfc1_ps = ((spd->trfc1_min_msb << 8) | (spd->trfc1_min_lsb)) *
+		       pdimm->mtb_ps;
+	debug("trfc1_ps %d\n", pdimm->trfc1_ps);
+	pdimm->trfc2_ps = ((spd->trfc2_min_msb << 8) | (spd->trfc2_min_lsb)) *
+		       pdimm->mtb_ps;
+	debug("trfc2_ps %d\n", pdimm->trfc2_ps);
+	pdimm->trfc4_ps = ((spd->trfc4_min_msb << 8) | (spd->trfc4_min_lsb)) *
+			pdimm->mtb_ps;
+	debug("trfc4_ps %d\n", pdimm->trfc4_ps);
+	/* min four active window delay time */
+	pdimm->tfaw_ps = (((spd->tfaw_msb & 0xf) << 8) | spd->tfaw_min) *
+			pdimm->mtb_ps;
+	debug("tfaw_ps %d\n", pdimm->tfaw_ps);
+
+	/* min row active to row active delay time, different bank group */
+	pdimm->trrds_ps = spd_to_ps(spd->trrds_min, spd->fine_trrds_min);
+	debug("trrds_ps %d\n", pdimm->trrds_ps);
+	/* min row active to row active delay time, same bank group */
+	pdimm->trrdl_ps = spd_to_ps(spd->trrdl_min, spd->fine_trrdl_min);
+	debug("trrdl_ps %d\n", pdimm->trrdl_ps);
+	/* min CAS to CAS Delay Time (tCCD_Lmin), same bank group */
+	pdimm->tccdl_ps = spd_to_ps(spd->tccdl_min, spd->fine_tccdl_min);
+	debug("tccdl_ps %d\n", pdimm->tccdl_ps);
+	if (pdimm->package_3ds != 0) {
+		if (pdimm->die_density > 5) {
+			debug("Unsupported logical rank density 0x%x\n",
+				  pdimm->die_density);
+			return -EINVAL;
+		}
+		pdimm->trfc_slr_ps = (pdimm->die_density <= 4) ?
+				     260000 : 350000;
+	}
+	debug("trfc_slr_ps %d\n", pdimm->trfc_slr_ps);
+
+	/* 15ns for all speed bins */
+	pdimm->twr_ps = 15000;
+	debug("twr_ps %d\n", pdimm->twr_ps);
+
+	/*
+	 * Average periodic refresh interval
+	 * tREFI = 7.8 us at normal temperature range
+	 */
+	pdimm->refresh_rate_ps = 7800000;
+	debug("refresh_rate_ps %d\n", pdimm->refresh_rate_ps);
+
+	for (i = 0; i < 18; i++) {
+		pdimm->dq_mapping[i] = spd->mapping[i];
+		debug("dq_mapping 0x%x\n", pdimm->dq_mapping[i]);
+	}
+
+	pdimm->dq_mapping_ors = ((spd->mapping[0] >> 6) & 0x3) == 0 ? 1 : 0;
+	debug("dq_mapping_ors %d\n", pdimm->dq_mapping_ors);
+
+	return 0;
+}
diff --git a/drivers/nxp/ddr/nxp-ddr/regs.c b/drivers/nxp/ddr/nxp-ddr/regs.c
new file mode 100644
index 0000000..cedd7ca
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/regs.c
@@ -0,0 +1,1394 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <lib/utils.h>
+
+static inline unsigned int cal_cwl(const unsigned long clk)
+{
+	const unsigned int mclk_ps = get_memory_clk_ps(clk);
+
+	return mclk_ps >= 1250U ? 9U :
+		(mclk_ps >= 1070U ? 10U :
+		 (mclk_ps >= 935U ? 11U :
+		  (mclk_ps >= 833U ? 12U :
+		   (mclk_ps >= 750U ? 14U :
+		    (mclk_ps >= 625U ? 16U : 18U)))));
+}
+
+static void cal_csn_config(int i,
+			   struct ddr_cfg_regs *regs,
+			   const struct memctl_opt *popts,
+			   const struct dimm_params *pdimm)
+{
+	unsigned int intlv_en = 0U;
+	unsigned int intlv_ctl = 0U;
+	const unsigned int cs_n_en = 1U;
+	const unsigned int ap_n_en = popts->cs_odt[i].auto_precharge;
+	const unsigned int odt_rd_cfg = popts->cs_odt[i].odt_rd_cfg;
+	const unsigned int odt_wr_cfg = popts->cs_odt[i].odt_wr_cfg;
+	const unsigned int ba_bits_cs_n = pdimm->bank_addr_bits;
+	const unsigned int row_bits_cs_n = pdimm->n_row_addr - 12U;
+	const unsigned int col_bits_cs_n = pdimm->n_col_addr - 8U;
+	const unsigned int bg_bits_cs_n = pdimm->bank_group_bits;
+
+	if (i == 0) {
+		/* These fields only available in CS0_CONFIG */
+		if (popts->ctlr_intlv != 0) {
+			switch (popts->ctlr_intlv_mode) {
+			case DDR_256B_INTLV:
+				intlv_en = popts->ctlr_intlv;
+				intlv_ctl = popts->ctlr_intlv_mode;
+				break;
+			default:
+				break;
+			}
+		}
+	}
+	regs->cs[i].config = ((cs_n_en & 0x1) << 31)		|
+			    ((intlv_en & 0x3) << 29)		|
+			    ((intlv_ctl & 0xf) << 24)		|
+			    ((ap_n_en & 0x1) << 23)		|
+			    ((odt_rd_cfg & 0x7) << 20)		|
+			    ((odt_wr_cfg & 0x7) << 16)		|
+			    ((ba_bits_cs_n & 0x3) << 14)	|
+			    ((row_bits_cs_n & 0x7) << 8)	|
+			    ((bg_bits_cs_n & 0x3) << 4)		|
+			    ((col_bits_cs_n & 0x7) << 0);
+	debug("cs%d\n", i);
+	debug("   _config = 0x%x\n", regs->cs[i].config);
+}
+
+static inline int avoid_odt_overlap(const struct ddr_conf *conf,
+				    const struct dimm_params *pdimm)
+{
+	if ((conf->cs_in_use == 0xf) != 0) {
+		return 2;
+	}
+
+#if DDRC_NUM_DIMM >= 2
+	if (conf->dimm_in_use[0] != 0 && conf->dimm_in_use[1] != 0) {
+		return 1;
+	}
+#endif
+	return 0;
+}
+
+/* Requires rcw2 set first */
+static void cal_timing_cfg(const unsigned long clk,
+			   struct ddr_cfg_regs *regs,
+			   const struct memctl_opt *popts,
+			   const struct dimm_params *pdimm,
+			   const struct ddr_conf *conf,
+			   unsigned int cas_latency,
+			   unsigned int additive_latency)
+{
+	const unsigned int mclk_ps = get_memory_clk_ps(clk);
+	/* tXP=max(4nCK, 6ns) */
+	const int txp = max((int)mclk_ps * 4, 6000);
+	/* DDR4 supports 10, 12, 14, 16, 18, 20, 24 */
+	static const int wrrec_table[] = {
+		10, 10, 10, 10, 10,
+		10, 10, 10, 10, 10,
+		12, 12, 14, 14, 16,
+		16, 18, 18, 20, 20,
+		24, 24, 24, 24,
+	};
+	int trwt_mclk = (clk / 1000000 > 1900) ? 3 : 2;
+	int twrt_mclk;
+	int trrt_mclk;
+	int twwt_mclk;
+	const int act_pd_exit_mclk = picos_to_mclk(clk, txp);
+	const int pre_pd_exit_mclk = act_pd_exit_mclk;
+	const int taxpd_mclk = 0;
+	/*
+	 * MRS_CYC = max(tMRD, tMOD)
+	 * tMRD = 8nCK, tMOD = max(24nCK, 15ns)
+	 */
+	const int tmrd_mclk = max(24U, picos_to_mclk(clk, 15000));
+	const int pretoact_mclk = picos_to_mclk(clk, pdimm->trp_ps);
+	const int acttopre_mclk = picos_to_mclk(clk, pdimm->tras_ps);
+	const int acttorw_mclk = picos_to_mclk(clk, pdimm->trcd_ps);
+	const int caslat_ctrl = (cas_latency - 1) << 1;
+	const int trfc1_min = pdimm->die_density >= 0x3 ? 16000 :
+			      (pdimm->die_density == 0x4 ? 26000 :
+			       (pdimm->die_density == 0x5 ? 35000 :
+				55000));
+	const int refrec_ctrl = picos_to_mclk(clk,
+							pdimm->trfc1_ps) - 8;
+	int wrrec_mclk = picos_to_mclk(clk, pdimm->twr_ps);
+	const int acttoact_mclk = max(picos_to_mclk(clk,
+							      pdimm->trrds_ps),
+						4U);
+	int wrtord_mclk = max(2U, picos_to_mclk(clk, 2500));
+	const unsigned int cpo = 0U;
+	const int wr_lat = cal_cwl(clk);
+	int rd_to_pre = picos_to_mclk(clk, 7500);
+	const int wr_data_delay = popts->wr_data_delay;
+	const int cke_pls = max(3U, picos_to_mclk(clk, 5000));
+#ifdef ERRATA_DDR_A050450
+	const unsigned short four_act = ((popts->twot_en == 0) &&
+					 (popts->threet_en == 0) &&
+					 (popts->tfaw_ps % 2 == 0)) ?
+						(picos_to_mclk(clk, popts->tfaw_ps) + 1) :
+						picos_to_mclk(clk, popts->tfaw_ps);
+#else
+	const unsigned short four_act = picos_to_mclk(clk,
+					 popts->tfaw_ps);
+#endif
+	const unsigned int cntl_adj = 0U;
+	const unsigned int ext_pretoact = picos_to_mclk(clk,
+							pdimm->trp_ps) >> 4U;
+	const unsigned int ext_acttopre = picos_to_mclk(clk,
+							pdimm->tras_ps) >> 4U;
+	const unsigned int ext_acttorw = picos_to_mclk(clk,
+						       pdimm->trcd_ps) >> 4U;
+	const unsigned int ext_caslat = (2U * cas_latency - 1U) >> 4U;
+	const unsigned int ext_add_lat = additive_latency >> 4U;
+	const unsigned int ext_refrec = (picos_to_mclk(clk,
+					       pdimm->trfc1_ps) - 8U) >> 4U;
+	const unsigned int ext_wrrec = (picos_to_mclk(clk, pdimm->twr_ps) +
+				  (popts->otf_burst_chop_en ? 2U : 0U)) >> 4U;
+	const unsigned int rwt_same_cs = 0U;
+	const unsigned int wrt_same_cs = 0U;
+	const unsigned int rrt_same_cs = popts->burst_length == DDR_BL8 ? 0U : 2U;
+	const unsigned int wwt_same_cs = popts->burst_length == DDR_BL8 ? 0U : 2U;
+	const unsigned int dll_lock = 2U;
+	unsigned int rodt_on = 0U;
+	const unsigned int rodt_off = 4U;
+	const unsigned int wodt_on = 1U;
+	const unsigned int wodt_off = 4U;
+	const unsigned int hs_caslat = 0U;
+	const unsigned int hs_wrlat = 0U;
+	const unsigned int hs_wrrec = 0U;
+	const unsigned int hs_clkadj = 0U;
+	const unsigned int hs_wrlvl_start = 0U;
+	const unsigned int txpr = max(5U,
+				      picos_to_mclk(clk,
+						    pdimm->trfc1_ps + 10000U));
+	const unsigned int tcksre = max(5U, picos_to_mclk(clk, 10000U));
+	const unsigned int tcksrx = max(5U, picos_to_mclk(clk, 10000U));
+	const unsigned int cs_to_cmd = 0U;
+	const unsigned int cke_rst = txpr <= 200U ? 0U :
+				     (txpr <= 256U ? 1U :
+				      (txpr <= 512U ? 2U : 3U));
+	const unsigned int cksre = tcksre <= 19U ? tcksre - 5U : 15U;
+	const unsigned int cksrx = tcksrx <= 19U ? tcksrx - 5U : 15U;
+	unsigned int par_lat = 0U;
+	const int tccdl = max(5U, picos_to_mclk(clk, pdimm->tccdl_ps));
+	int rwt_bg = cas_latency + 2 + 4 - wr_lat;
+	int wrt_bg = wr_lat + 4 + 1 - cas_latency;
+	const int rrt_bg = popts->burst_length == DDR_BL8 ?
+				tccdl - 4 : tccdl - 2;
+	const int wwt_bg = popts->burst_length == DDR_BL8 ?
+					tccdl - 4 : tccdl - 2;
+	const unsigned int acttoact_bg = picos_to_mclk(clk, pdimm->trrdl_ps);
+	const unsigned int wrtord_bg = max(4U, picos_to_mclk(clk, 7500)) +
+				       (popts->otf_burst_chop_en ? 2 : 0);
+	const unsigned int pre_all_rec = 0;
+	const unsigned int refrec_cid_mclk = pdimm->package_3ds ?
+				picos_to_mclk(clk, pdimm->trfc_slr_ps) : 0;
+	const unsigned int acttoact_cid_mclk = pdimm->package_3ds ? 4U : 0;
+
+
+	/* for two dual-rank DIMMs to avoid ODT overlap */
+	if (avoid_odt_overlap(conf, pdimm) == 2) {
+		twrt_mclk = 2;
+		twwt_mclk = 2;
+		trrt_mclk = 2;
+	} else {
+		twrt_mclk = 1;
+		twwt_mclk = 1;
+		trrt_mclk = 0;
+	}
+
+	if (popts->trwt_override != 0) {
+		trwt_mclk = popts->trwt;
+		if (popts->twrt != 0) {
+			twrt_mclk = popts->twrt;
+		}
+		if (popts->trrt != 0) {
+			trrt_mclk = popts->trrt;
+		}
+		if (popts->twwt != 0) {
+			twwt_mclk = popts->twwt;
+		}
+	}
+	regs->timing_cfg[0] = (((trwt_mclk & 0x3) << 30)		|
+			     ((twrt_mclk & 0x3) << 28)			|
+			     ((trrt_mclk & 0x3) << 26)			|
+			     ((twwt_mclk & 0x3) << 24)			|
+			     ((act_pd_exit_mclk & 0xf) << 20)		|
+			     ((pre_pd_exit_mclk & 0xF) << 16)		|
+			     ((taxpd_mclk & 0xf) << 8)			|
+			     ((tmrd_mclk & 0x1f) << 0));
+	debug("timing_cfg[0] = 0x%x\n", regs->timing_cfg[0]);
+
+	if ((wrrec_mclk < 1) || (wrrec_mclk > 24)) {
+		ERROR("WRREC doesn't support clock %d\n", wrrec_mclk);
+	} else {
+		wrrec_mclk = wrrec_table[wrrec_mclk - 1];
+	}
+
+	if (popts->otf_burst_chop_en != 0) {
+		wrrec_mclk += 2;
+		wrtord_mclk += 2;
+	}
+
+	if (pdimm->trfc1_ps < trfc1_min) {
+		ERROR("trfc1_ps (%d) < %d\n", pdimm->trfc1_ps, trfc1_min);
+	}
+
+	regs->timing_cfg[1] = (((pretoact_mclk & 0x0F) << 28)		|
+			     ((acttopre_mclk & 0x0F) << 24)		|
+			     ((acttorw_mclk & 0xF) << 20)		|
+			     ((caslat_ctrl & 0xF) << 16)		|
+			     ((refrec_ctrl & 0xF) << 12)		|
+			     ((wrrec_mclk & 0x0F) << 8)			|
+			     ((acttoact_mclk & 0x0F) << 4)		|
+			     ((wrtord_mclk & 0x0F) << 0));
+	debug("timing_cfg[1] = 0x%x\n", regs->timing_cfg[1]);
+
+	if (rd_to_pre < 4) {
+		rd_to_pre = 4;
+	}
+	if (popts->otf_burst_chop_en) {
+		rd_to_pre += 2;
+	}
+
+	regs->timing_cfg[2] = (((additive_latency & 0xf) << 28)		|
+			     ((cpo & 0x1f) << 23)			|
+			     ((wr_lat & 0xf) << 19)			|
+			     (((wr_lat & 0x10) >> 4) << 18)		|
+			     ((rd_to_pre & 0xf) << 13)			|
+			     ((wr_data_delay & 0xf) << 9)		|
+			     ((cke_pls & 0x7) << 6)			|
+			     ((four_act & 0x3f) << 0));
+	debug("timing_cfg[2] = 0x%x\n", regs->timing_cfg[2]);
+
+	regs->timing_cfg[3] = (((ext_pretoact & 0x1) << 28)		|
+			     ((ext_acttopre & 0x3) << 24)		|
+			     ((ext_acttorw & 0x1) << 22)		|
+			     ((ext_refrec & 0x3F) << 16)		|
+			     ((ext_caslat & 0x3) << 12)			|
+			     ((ext_add_lat & 0x1) << 10)		|
+			     ((ext_wrrec & 0x1) << 8)			|
+			     ((cntl_adj & 0x7) << 0));
+	debug("timing_cfg[3] = 0x%x\n", regs->timing_cfg[3]);
+
+	regs->timing_cfg[4] = (((rwt_same_cs & 0xf) << 28)		|
+			     ((wrt_same_cs & 0xf) << 24)		|
+			     ((rrt_same_cs & 0xf) << 20)		|
+			     ((wwt_same_cs & 0xf) << 16)		|
+			     ((trwt_mclk & 0xc) << 12)			|
+			     ((twrt_mclk & 0x4) << 10)			|
+			     ((trrt_mclk & 0x4) << 8)			|
+			     ((twwt_mclk & 0x4) << 6)			|
+			     (dll_lock & 0x3));
+	debug("timing_cfg[4] = 0x%x\n", regs->timing_cfg[4]);
+
+	/* rodt_on = timing_cfg_1[caslat] - timing_cfg_2[wrlat] + 1 */
+	if (cas_latency >= wr_lat) {
+		rodt_on = cas_latency - wr_lat + 1;
+	}
+
+	regs->timing_cfg[5] = (((rodt_on & 0x1f) << 24)			|
+			     ((rodt_off & 0x7) << 20)			|
+			     ((wodt_on & 0x1f) << 12)			|
+			     (wodt_off & 0x7) << 8);
+	debug("timing_cfg[5] = 0x%x\n", regs->timing_cfg[5]);
+
+	regs->timing_cfg[6] = (((hs_caslat & 0x1f) << 24)		|
+			     ((hs_wrlat & 0x1f) << 19)			|
+			     ((hs_wrrec & 0x1f) << 12)			|
+			     ((hs_clkadj & 0x1f) << 6)			|
+			     ((hs_wrlvl_start & 0x1f) << 0));
+	debug("timing_cfg[6] = 0x%x\n", regs->timing_cfg[6]);
+
+	if (popts->ap_en != 0) {
+		par_lat = (regs->sdram_rcw[1] & 0xf) + 1;
+		debug("PAR_LAT = 0x%x\n", par_lat);
+	}
+
+	regs->timing_cfg[7] = (((cke_rst & 0x3) << 28)			|
+			     ((cksre & 0xf) << 24)			|
+			     ((cksrx & 0xf) << 20)			|
+			     ((par_lat & 0xf) << 16)			|
+			     ((cs_to_cmd & 0xf) << 4));
+	debug("timing_cfg[7] = 0x%x\n", regs->timing_cfg[7]);
+
+	if (rwt_bg < tccdl) {
+		rwt_bg = tccdl - rwt_bg;
+	} else {
+		rwt_bg = 0;
+	}
+	if (wrt_bg < tccdl) {
+		wrt_bg = tccdl - wrt_bg;
+	} else {
+		wrt_bg = 0;
+	}
+	regs->timing_cfg[8] = (((rwt_bg & 0xf) << 28)			|
+			     ((wrt_bg & 0xf) << 24)			|
+			     ((rrt_bg & 0xf) << 20)			|
+			     ((wwt_bg & 0xf) << 16)			|
+			     ((acttoact_bg & 0xf) << 12)		|
+			     ((wrtord_bg & 0xf) << 8)			|
+			     ((pre_all_rec & 0x1f) << 0));
+	debug("timing_cfg[8] = 0x%x\n", regs->timing_cfg[8]);
+
+	regs->timing_cfg[9] = (refrec_cid_mclk & 0x3ff) << 16		|
+			      (acttoact_cid_mclk & 0xf) << 8;
+	debug("timing_cfg[9] = 0x%x\n", regs->timing_cfg[9]);
+}
+
+static void cal_ddr_sdram_rcw(const unsigned long clk,
+			      struct ddr_cfg_regs *regs,
+			      const struct memctl_opt *popts,
+			      const struct dimm_params *pdimm)
+{
+	const unsigned int freq = clk / 1000000U;
+	unsigned int rc0a, rc0f;
+
+	if (pdimm->rdimm == 0) {
+		return;
+	}
+
+	rc0a = freq > 3200U ? 7U :
+	       (freq > 2933U ? 6U :
+		(freq > 2666U ? 5U :
+		 (freq > 2400U ? 4U :
+		  (freq > 2133U ? 3U :
+		   (freq > 1866U ? 2U :
+		    (freq > 1600U ? 1U : 0U))))));
+	rc0f = freq > 3200U ? 3U :
+		(freq > 2400U ? 2U :
+		 (freq > 2133U ? 1U : 0U));
+	rc0f = (regs->sdram_cfg[1] & SDRAM_CFG2_AP_EN) ? rc0f : 4;
+	regs->sdram_rcw[0] =
+		pdimm->rcw[0] << 28	|
+		pdimm->rcw[1] << 24	|
+		pdimm->rcw[2] << 20	|
+		pdimm->rcw[3] << 16	|
+		pdimm->rcw[4] << 12	|
+		pdimm->rcw[5] << 8	|
+		pdimm->rcw[6] << 4	|
+		pdimm->rcw[7];
+	regs->sdram_rcw[1] =
+		pdimm->rcw[8] << 28	|
+		pdimm->rcw[9] << 24	|
+		rc0a << 20		|
+		pdimm->rcw[11] << 16	|
+		pdimm->rcw[12] << 12	|
+		pdimm->rcw[13] << 8	|
+		pdimm->rcw[14] << 4	|
+		rc0f;
+	regs->sdram_rcw[2] =
+		((freq - 1260 + 19) / 20) << 8;
+
+	debug("sdram_rcw[0] = 0x%x\n", regs->sdram_rcw[0]);
+	debug("sdram_rcw[1] = 0x%x\n", regs->sdram_rcw[1]);
+	debug("sdram_rcw[2] = 0x%x\n", regs->sdram_rcw[2]);
+}
+
+static void cal_ddr_sdram_cfg(const unsigned long clk,
+			      struct ddr_cfg_regs *regs,
+			      const struct memctl_opt *popts,
+			      const struct dimm_params *pdimm,
+			      const unsigned int ip_rev)
+{
+	const unsigned int mem_en = 1U;
+	const unsigned int sren = popts->self_refresh_in_sleep;
+	const unsigned int ecc_en = popts->ecc_mode;
+	const unsigned int rd_en = (pdimm->rdimm != 0U) ? 1U : 0U;
+	const unsigned int dyn_pwr = popts->dynamic_power;
+	const unsigned int dbw = popts->data_bus_used;
+	const unsigned int eight_be = (dbw == 1U ||
+				       popts->burst_length == DDR_BL8) ? 1U : 0U;
+	const unsigned int ncap = 0U;
+	const unsigned int threet_en = popts->threet_en;
+	const unsigned int twot_en = pdimm->rdimm ?
+					0U : popts->twot_en;
+	const unsigned int ba_intlv = popts->ba_intlv;
+	const unsigned int x32_en = 0U;
+	const unsigned int pchb8 = 0U;
+	const unsigned int hse = popts->half_strength_drive_en;
+	const unsigned int acc_ecc_en = (dbw != 0U && ecc_en == 1U) ? 1U : 0U;
+	const unsigned int mem_halt = 0U;
+#ifdef PHY_GEN2
+	const unsigned int bi = 1U;
+#else
+	const unsigned int bi = 0U;
+#endif
+	const unsigned int sdram_type = SDRAM_TYPE_DDR4;
+	unsigned int odt_cfg = 0U;
+	const unsigned int frc_sr = 0U;
+	const unsigned int sr_ie = popts->self_refresh_irq_en;
+	const unsigned int num_pr = pdimm->package_3ds + 1U;
+	const unsigned int slow = (clk < 1249000000U) ? 1U : 0U;
+	const unsigned int x4_en = popts->x4_en;
+	const unsigned int obc_cfg = popts->otf_burst_chop_en;
+	const unsigned int ap_en = ip_rev == 0x50500U ? 0U : popts->ap_en;
+	const unsigned int d_init = popts->ctlr_init_ecc;
+	const unsigned int rcw_en = popts->rdimm;
+	const unsigned int md_en = popts->mirrored_dimm;
+	const unsigned int qd_en = popts->quad_rank_present;
+	const unsigned int unq_mrs_en = ip_rev < 0x50500U ? 1U : 0U;
+	const unsigned int rd_pre = popts->quad_rank_present;
+	int i;
+
+	regs->sdram_cfg[0] = ((mem_en & 0x1) << 31)		|
+				((sren & 0x1) << 30)		|
+				((ecc_en & 0x1) << 29)		|
+				((rd_en & 0x1) << 28)		|
+				((sdram_type & 0x7) << 24)	|
+				((dyn_pwr & 0x1) << 21)		|
+				((dbw & 0x3) << 19)		|
+				((eight_be & 0x1) << 18)	|
+				((ncap & 0x1) << 17)		|
+				((threet_en & 0x1) << 16)	|
+				((twot_en & 0x1) << 15)		|
+				((ba_intlv & 0x7F) << 8)	|
+				((x32_en & 0x1) << 5)		|
+				((pchb8 & 0x1) << 4)		|
+				((hse & 0x1) << 3)		|
+				((acc_ecc_en & 0x1) << 2)	|
+				((mem_halt & 0x1) << 1)		|
+				((bi & 0x1) << 0);
+	debug("sdram_cfg[0] = 0x%x\n", regs->sdram_cfg[0]);
+
+	for (i = 0; i < DDRC_NUM_CS; i++) {
+		if (popts->cs_odt[i].odt_rd_cfg != 0 ||
+		    popts->cs_odt[i].odt_wr_cfg != 0) {
+			odt_cfg = SDRAM_CFG2_ODT_ONLY_READ;
+			break;
+		}
+	}
+
+	regs->sdram_cfg[1] = (0
+		| ((frc_sr & 0x1) << 31)
+		| ((sr_ie & 0x1) << 30)
+		| ((odt_cfg & 0x3) << 21)
+		| ((num_pr & 0xf) << 12)
+		| ((slow & 1) << 11)
+		| (x4_en << 10)
+		| (qd_en << 9)
+		| (unq_mrs_en << 8)
+		| ((obc_cfg & 0x1) << 6)
+		| ((ap_en & 0x1) << 5)
+		| ((d_init & 0x1) << 4)
+		| ((rcw_en & 0x1) << 2)
+		| ((md_en & 0x1) << 0)
+		);
+	debug("sdram_cfg[1] = 0x%x\n", regs->sdram_cfg[1]);
+
+	regs->sdram_cfg[2] = (rd_pre & 0x1) << 16	|
+				 (popts->rdimm ? 1 : 0);
+	if (pdimm->package_3ds != 0) {
+		if (((pdimm->package_3ds + 1) & 0x1) != 0) {
+			WARN("Unsupported 3DS DIMM\n");
+		} else {
+			regs->sdram_cfg[2] |= ((pdimm->package_3ds + 1) >> 1)
+						  << 4;
+		}
+	}
+	debug("sdram_cfg[2] = 0x%x\n", regs->sdram_cfg[2]);
+}
+
+
+static void cal_ddr_sdram_interval(const unsigned long clk,
+				   struct ddr_cfg_regs *regs,
+				   const struct memctl_opt *popts,
+				   const struct dimm_params *pdimm)
+{
+	const unsigned int refint = picos_to_mclk(clk, pdimm->refresh_rate_ps);
+	const unsigned int bstopre = popts->bstopre;
+
+	regs->interval = ((refint & 0xFFFF) << 16)	|
+				  ((bstopre & 0x3FFF) << 0);
+	debug("interval = 0x%x\n", regs->interval);
+}
+
+/* Require cs and cfg first */
+static void cal_ddr_sdram_mode(const unsigned long clk,
+			       struct ddr_cfg_regs *regs,
+			       const struct memctl_opt *popts,
+			       const struct ddr_conf *conf,
+			       const struct dimm_params *pdimm,
+			       unsigned int cas_latency,
+			       unsigned int additive_latency,
+			       const unsigned int ip_rev)
+{
+	int i;
+	unsigned short esdmode;		/* Extended SDRAM mode */
+	unsigned short sdmode;		/* SDRAM mode */
+
+	/* Mode Register - MR1 */
+	const unsigned int qoff = 0;
+	const unsigned int tdqs_en = 0;
+	unsigned int rtt;
+	const unsigned int wrlvl_en = 0;
+	unsigned int al = 0;
+	unsigned int dic = 0;
+	const unsigned int dll_en = 1;
+
+	/* Mode Register - MR0 */
+	unsigned int wr = 0;
+	const unsigned int dll_rst = 0;
+	const unsigned int mode = 0;
+	unsigned int caslat = 4;/* CAS# latency, default set as 6 cycles */
+	/* BT: Burst Type (0=Nibble Sequential, 1=Interleaved) */
+	const unsigned int bt = 0;
+	const unsigned int bl = popts->burst_length == DDR_BL8 ? 0 :
+				 (popts->burst_length == DDR_BC4 ? 2 : 1);
+
+	const unsigned int wr_mclk = picos_to_mclk(clk, pdimm->twr_ps);
+	/* DDR4 support WR 10, 12, 14, 16, 18, 20, 24 */
+	static const int wr_table[] = {
+		0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 6, 6
+	};
+	/* DDR4 support CAS 9, 10, 11, 12, 13, 14, 15, 16, 18, 20, 22, 24 */
+	static const int cas_latency_table[] = {
+		0, 1, 2, 3, 4, 5, 6, 7, 13, 8,
+		14, 9, 15, 10, 12, 11, 16, 17,
+		18, 19, 20, 21, 22, 23
+	};
+	const unsigned int unq_mrs_en = ip_rev < U(0x50500) ? 1U : 0U;
+	unsigned short esdmode2 = 0U;
+	unsigned short esdmode3 = 0U;
+	const unsigned int wr_crc = 0U;
+	unsigned int rtt_wr = 0U;
+	const unsigned int srt = 0U;
+	unsigned int cwl = cal_cwl(clk);
+	const unsigned int mpr = 0U;
+	const unsigned int mclk_ps = get_memory_clk_ps(clk);
+	const unsigned int wc_lat = 0U;
+	unsigned short esdmode4 = 0U;
+	unsigned short esdmode5;
+	int rtt_park_all = 0;
+	unsigned int rtt_park;
+	const bool four_cs = conf->cs_in_use == 0xf ? true : false;
+	unsigned short esdmode6 = 0U;	/* Extended SDRAM mode 6 */
+	unsigned short esdmode7 = 0U;	/* Extended SDRAM mode 7 */
+	const unsigned int tccdl_min = max(5U,
+					   picos_to_mclk(clk, pdimm->tccdl_ps));
+
+	if (popts->rtt_override != 0U) {
+		rtt = popts->rtt_override_value;
+	} else {
+		rtt = popts->cs_odt[0].odt_rtt_norm;
+	}
+
+	if (additive_latency == (cas_latency - 1)) {
+		al = 1;
+	}
+	if (additive_latency == (cas_latency - 2)) {
+		al = 2;
+	}
+
+	if (popts->quad_rank_present != 0 || popts->output_driver_impedance != 0) {
+		dic = 1;	/* output driver impedance 240/7 ohm */
+	}
+
+	esdmode = (((qoff & 0x1) << 12)				|
+		   ((tdqs_en & 0x1) << 11)			|
+		   ((rtt & 0x7) << 8)				|
+		   ((wrlvl_en & 0x1) << 7)			|
+		   ((al & 0x3) << 3)				|
+		   ((dic & 0x3) << 1)				|
+		   ((dll_en & 0x1) << 0));
+
+	if (wr_mclk >= 10 && wr_mclk <= 24) {
+		wr = wr_table[wr_mclk - 10];
+	} else {
+		ERROR("unsupported wc_mclk = %d for mode register\n", wr_mclk);
+	}
+
+	/* look up table to get the cas latency bits */
+	if (cas_latency >= 9 && cas_latency <= 32) {
+		caslat = cas_latency_table[cas_latency - 9];
+	} else {
+		WARN("Error: unsupported cas latency for mode register\n");
+	}
+
+	sdmode = (((caslat & 0x10) << 8)			|
+		  ((wr & 0x7) << 9)				|
+		  ((dll_rst & 0x1) << 8)			|
+		  ((mode & 0x1) << 7)				|
+		  (((caslat >> 1) & 0x7) << 4)			|
+		  ((bt & 0x1) << 3)				|
+		  ((caslat & 1) << 2)				|
+		  ((bl & 0x3) << 0));
+
+	regs->sdram_mode[0] = (((esdmode & 0xFFFF) << 16)	|
+				 ((sdmode & 0xFFFF) << 0));
+	debug("sdram_mode[0] = 0x%x\n", regs->sdram_mode[0]);
+
+	switch (cwl) {
+	case 9:
+	case 10:
+	case 11:
+	case 12:
+		cwl -= 9;
+		break;
+	case 14:
+		cwl -= 10;
+		break;
+	case 16:
+		cwl -= 11;
+		break;
+	case 18:
+		cwl -= 12;
+		break;
+	case 20:
+		cwl -= 13;
+		break;
+	default:
+		printf("Error CWL\n");
+		break;
+	}
+
+	if (popts->rtt_override != 0) {
+		rtt_wr = popts->rtt_wr_override_value;
+	} else {
+		rtt_wr = popts->cs_odt[0].odt_rtt_wr;
+	}
+
+	esdmode2 = ((wr_crc & 0x1) << 12)			|
+		   ((rtt_wr & 0x7) << 9)			|
+		   ((srt & 0x3) << 6)				|
+		   ((cwl & 0x7) << 3);
+	esdmode3 = ((mpr & 0x3) << 11) | ((wc_lat & 0x3) << 9);
+
+	regs->sdram_mode[1] = ((esdmode2 & 0xFFFF) << 16)	|
+				((esdmode3 & 0xFFFF) << 0);
+	debug("sdram_mode[1] = 0x%x\n", regs->sdram_mode[1]);
+
+	esdmode6 = ((tccdl_min - 4) & 0x7) << 10;
+	if (popts->vref_dimm != 0) {
+		esdmode6 |= popts->vref_dimm & 0x7f;
+	} else if ((popts->ddr_cdr2 & DDR_CDR2_VREF_RANGE_2) != 0) {
+		esdmode6 |= 1 << 6;	/* Range 2 */
+	}
+
+	regs->sdram_mode[9] = ((esdmode6 & 0xffff) << 16)	|
+				 ((esdmode7 & 0xffff) << 0);
+	debug("sdram_mode[9] = 0x%x\n", regs->sdram_mode[9]);
+
+	rtt_park = (popts->rtt_park != 0) ? popts->rtt_park : 240;
+	switch (rtt_park) {
+	case 240:
+		rtt_park = 0x4;
+		break;
+	case 120:
+		rtt_park = 0x2;
+		break;
+	case 80:
+		rtt_park = 0x6;
+		break;
+	case 60:
+		rtt_park = 0x1;
+		break;
+	case 48:
+		rtt_park = 0x5;
+		break;
+	case 40:
+		rtt_park = 0x3;
+		break;
+	case 34:
+		rtt_park = 0x7;
+		break;
+	default:
+		rtt_park = 0;
+		break;
+	}
+
+	for (i = 0; i < DDRC_NUM_CS; i++) {
+		if (i != 0 && unq_mrs_en == 0) {
+			break;
+		}
+
+		if (popts->rtt_override != 0) {
+			rtt = popts->rtt_override_value;
+			rtt_wr = popts->rtt_wr_override_value;
+		} else {
+			rtt = popts->cs_odt[i].odt_rtt_norm;
+			rtt_wr = popts->cs_odt[i].odt_rtt_wr;
+		}
+
+		esdmode &= 0xF8FF;	/* clear bit 10,9,8 for rtt */
+		esdmode |= (rtt & 0x7) << 8;
+		esdmode2 &= 0xF9FF;	/* clear bit 10, 9 */
+		esdmode2 |= (rtt_wr & 0x3) << 9;
+		esdmode5 = (popts->x4_en) ? 0 : 0x400; /* data mask */
+
+		if (rtt_park_all == 0 &&
+		    ((regs->cs[i].config & SDRAM_CS_CONFIG_EN) != 0)) {
+			esdmode5 |= rtt_park << 6;
+			rtt_park_all = four_cs ? 0 : 1;
+		}
+
+		if (((regs->sdram_cfg[1] & SDRAM_CFG2_AP_EN) != 0) &&
+		    (popts->rdimm == 0)) {
+			if (mclk_ps >= 935) {
+				esdmode5 |= DDR_MR5_CA_PARITY_LAT_4_CLK;
+			} else if (mclk_ps >= 833) {
+				esdmode5 |= DDR_MR5_CA_PARITY_LAT_5_CLK;
+			} else {
+				esdmode5 |= DDR_MR5_CA_PARITY_LAT_5_CLK;
+				WARN("mclk_ps not supported %d", mclk_ps);
+
+			}
+		}
+
+		switch (i) {
+		case 0:
+			regs->sdram_mode[8] = ((esdmode4 & 0xffff) << 16) |
+						((esdmode5 & 0xffff) << 0);
+			debug("sdram_mode[8] = 0x%x\n", regs->sdram_mode[8]);
+			break;
+		case 1:
+			regs->sdram_mode[2] = (((esdmode & 0xFFFF) << 16) |
+					      ((sdmode & 0xFFFF) << 0));
+			regs->sdram_mode[3] = ((esdmode2 & 0xFFFF) << 16) |
+					      ((esdmode3 & 0xFFFF) << 0);
+			regs->sdram_mode[10] = ((esdmode4 & 0xFFFF) << 16) |
+					       ((esdmode5 & 0xFFFF) << 0);
+			regs->sdram_mode[11] = ((esdmode6 & 0xFFFF) << 16) |
+					       ((esdmode7 & 0xFFFF) << 0);
+			debug("sdram_mode[2] = 0x%x\n", regs->sdram_mode[2]);
+			debug("sdram_mode[3] = 0x%x\n", regs->sdram_mode[3]);
+			debug("sdram_mode[10] = 0x%x\n", regs->sdram_mode[10]);
+			debug("sdram_mode[11] = 0x%x\n", regs->sdram_mode[11]);
+			break;
+		case 2:
+			regs->sdram_mode[4] = (((esdmode & 0xFFFF) << 16) |
+					      ((sdmode & 0xFFFF) << 0));
+			regs->sdram_mode[5] = ((esdmode2 & 0xFFFF) << 16) |
+					      ((esdmode3 & 0xFFFF) << 0);
+			regs->sdram_mode[12] = ((esdmode4 & 0xFFFF) << 16) |
+					       ((esdmode5 & 0xFFFF) << 0);
+			regs->sdram_mode[13] = ((esdmode6 & 0xFFFF) << 16) |
+					       ((esdmode7 & 0xFFFF) << 0);
+			debug("sdram_mode[4] = 0x%x\n", regs->sdram_mode[4]);
+			debug("sdram_mode[5] = 0x%x\n", regs->sdram_mode[5]);
+			debug("sdram_mode[12] = 0x%x\n", regs->sdram_mode[12]);
+			debug("sdram_mode[13] = 0x%x\n", regs->sdram_mode[13]);
+			break;
+		case 3:
+			regs->sdram_mode[6] = (((esdmode & 0xFFFF) << 16) |
+					      ((sdmode & 0xFFFF) << 0));
+			regs->sdram_mode[7] = ((esdmode2 & 0xFFFF) << 16) |
+					      ((esdmode3 & 0xFFFF) << 0);
+			regs->sdram_mode[14] = ((esdmode4 & 0xFFFF) << 16) |
+					       ((esdmode5 & 0xFFFF) << 0);
+			regs->sdram_mode[15] = ((esdmode6 & 0xFFFF) << 16) |
+					       ((esdmode7 & 0xFFFF) << 0);
+			debug("sdram_mode[6] = 0x%x\n", regs->sdram_mode[6]);
+			debug("sdram_mode[7] = 0x%x\n", regs->sdram_mode[7]);
+			debug("sdram_mode[14] = 0x%x\n", regs->sdram_mode[14]);
+			debug("sdram_mode[15] = 0x%x\n", regs->sdram_mode[15]);
+			break;
+		default:
+			break;
+		}
+	}
+}
+
+#ifndef CONFIG_MEM_INIT_VALUE
+#define CONFIG_MEM_INIT_VALUE 0xDEADBEEF
+#endif
+static void cal_ddr_data_init(struct ddr_cfg_regs *regs)
+{
+	regs->data_init = CONFIG_MEM_INIT_VALUE;
+}
+
+static void cal_ddr_dq_mapping(struct ddr_cfg_regs *regs,
+			       const struct dimm_params *pdimm)
+{
+	const unsigned int acc_ecc_en = (regs->sdram_cfg[0] >> 2) & 0x1;
+/* FIXME: revert the dq mapping from DIMM */
+	regs->dq_map[0] = ((pdimm->dq_mapping[0] & 0x3F) << 26)	|
+			 ((pdimm->dq_mapping[1] & 0x3F) << 20)	|
+			 ((pdimm->dq_mapping[2] & 0x3F) << 14)	|
+			 ((pdimm->dq_mapping[3] & 0x3F) << 8)	|
+			 ((pdimm->dq_mapping[4] & 0x3F) << 2);
+
+	regs->dq_map[1] = ((pdimm->dq_mapping[5] & 0x3F) << 26)	|
+			 ((pdimm->dq_mapping[6] & 0x3F) << 20)	|
+			 ((pdimm->dq_mapping[7] & 0x3F) << 14)	|
+			 ((pdimm->dq_mapping[10] & 0x3F) << 8)	|
+			 ((pdimm->dq_mapping[11] & 0x3F) << 2);
+
+	regs->dq_map[2] = ((pdimm->dq_mapping[12] & 0x3F) << 26)	|
+			 ((pdimm->dq_mapping[13] & 0x3F) << 20)		|
+			 ((pdimm->dq_mapping[14] & 0x3F) << 14)		|
+			 ((pdimm->dq_mapping[15] & 0x3F) << 8)		|
+			 ((pdimm->dq_mapping[16] & 0x3F) << 2);
+
+	/* dq_map for ECC[4:7] is set to 0 if accumulated ECC is enabled */
+	regs->dq_map[3] = ((pdimm->dq_mapping[17] & 0x3F) << 26)	|
+			 ((pdimm->dq_mapping[8] & 0x3F) << 20)		|
+			 ((acc_ecc_en != 0) ? 0 :
+			  (pdimm->dq_mapping[9] & 0x3F) << 14)		|
+			 pdimm->dq_mapping_ors;
+	debug("dq_map[0] = 0x%x\n", regs->dq_map[0]);
+	debug("dq_map[1] = 0x%x\n", regs->dq_map[1]);
+	debug("dq_map[2] = 0x%x\n", regs->dq_map[2]);
+	debug("dq_map[3] = 0x%x\n", regs->dq_map[3]);
+}
+static void cal_ddr_zq_cntl(struct ddr_cfg_regs *regs)
+{
+	const unsigned int zqinit = 10U;	/* 1024 clocks */
+	const unsigned int zqoper = 9U;		/* 512 clocks */
+	const unsigned int zqcs = 7U;		/* 128 clocks */
+	const unsigned int zqcs_init = 5U;	/* 1024 refresh seqences */
+	const unsigned int zq_en = 1U;		/* enabled */
+
+	regs->zq_cntl = ((zq_en & 0x1) << 31)			|
+			   ((zqinit & 0xF) << 24)		|
+			   ((zqoper & 0xF) << 16)		|
+			   ((zqcs & 0xF) << 8)			|
+			   ((zqcs_init & 0xF) << 0);
+	debug("zq_cntl = 0x%x\n", regs->zq_cntl);
+}
+
+static void cal_ddr_sr_cntr(struct ddr_cfg_regs *regs,
+			    const struct memctl_opt *popts)
+{
+	const unsigned int sr_it = (popts->auto_self_refresh_en) ?
+					popts->sr_it : 0;
+
+	regs->ddr_sr_cntr = (sr_it & 0xF) << 16;
+	debug("ddr_sr_cntr = 0x%x\n", regs->ddr_sr_cntr);
+}
+
+static void cal_ddr_eor(struct ddr_cfg_regs *regs,
+			const struct memctl_opt *popts)
+{
+	if (popts->addr_hash != 0) {
+		regs->eor = 0x40000000;	/* address hash enable */
+		debug("eor = 0x%x\n", regs->eor);
+	}
+}
+
+static void cal_ddr_csn_bnds(struct ddr_cfg_regs *regs,
+			     const struct memctl_opt *popts,
+			     const struct ddr_conf *conf,
+			     const struct dimm_params *pdimm)
+{
+	int i;
+	unsigned long long ea, sa;
+
+	/* Chip Select Memory Bounds (CSn_BNDS) */
+	for (i = 0;
+		i < DDRC_NUM_CS && conf->cs_size[i];
+		i++) {
+		debug("cs_in_use = 0x%x\n", conf->cs_in_use);
+		if (conf->cs_in_use != 0) {
+			sa = conf->cs_base_addr[i];
+			ea = sa + conf->cs_size[i] - 1;
+			sa >>= 24;
+			ea >>= 24;
+			regs->cs[i].bnds = ((sa & 0xffff) << 16) |
+					   ((ea & 0xffff) << 0);
+			cal_csn_config(i, regs, popts, pdimm);
+		} else {
+			/* setting bnds to 0xffffffff for inactive CS */
+			regs->cs[i].bnds = 0xffffffff;
+		}
+
+		debug("cs[%d].bnds = 0x%x\n", i, regs->cs[i].bnds);
+	}
+}
+
+static void cal_ddr_addr_dec(struct ddr_cfg_regs *regs)
+{
+#ifdef CONFIG_DDR_ADDR_DEC
+	unsigned int ba_bits __unused;
+	char p __unused;
+	const unsigned int cs0_config = regs->cs[0].config;
+	const int cacheline = PLATFORM_CACHE_LINE_SHIFT;
+	unsigned int bg_bits;
+	unsigned int row_bits;
+	unsigned int col_bits;
+	unsigned int cs;
+	unsigned int map_row[18];
+	unsigned int map_col[11];
+	unsigned int map_ba[2];
+	unsigned int map_cid[2] = {0x3F, 0x3F};
+	unsigned int map_bg[2] = {0x3F, 0x3F};
+	unsigned int map_cs[2] = {0x3F, 0x3F};
+	unsigned int dbw;
+	unsigned int ba_intlv;
+	int placement;
+	int intlv;
+	int abort = 0;
+	int i;
+	int j;
+
+	col_bits = (cs0_config >> 0) & 0x7;
+	if (col_bits < 4) {
+		col_bits += 8;
+	} else if (col_bits < 7 || col_bits > 10) {
+		ERROR("Error %s col_bits = %d\n", __func__, col_bits);
+	}
+	row_bits = ((cs0_config >> 8) & 0x7) + 12;
+	ba_bits = ((cs0_config >> 14) & 0x3) + 2;
+	bg_bits = ((cs0_config >> 4) & 0x3) + 0;
+	intlv = (cs0_config >> 24) & 0xf;
+	ba_intlv = (regs->sdram_cfg[0] >> 8) & 0x7f;
+	switch (ba_intlv) {
+	case DDR_BA_INTLV_CS01:
+		cs = 1;
+		break;
+	case DDR_BA_INTLV_CS0123:
+		cs = 2;
+		break;
+	case DDR_BA_NONE:
+		cs = 0;
+		break;
+	default:
+		ERROR("%s ba_intlv 0x%x\n", __func__, ba_intlv);
+		return;
+	}
+	debug("col %d, row %d, ba %d, bg %d, intlv %d\n",
+			col_bits, row_bits, ba_bits, bg_bits, intlv);
+	/*
+	 * Example mapping of 15x2x2x10
+	 * ---- --rr rrrr rrrr rrrr rCBB Gccc cccI cGcc cbbb
+	 */
+	dbw = (regs->sdram_cfg[0] >> 19) & 0x3;
+	switch (dbw) {
+	case 0:	/* 64-bit */
+		placement = 3;
+		break;
+	case 1:	/* 32-bit */
+		placement = 2;
+		break;
+	default:
+		ERROR("%s dbw = %d\n", __func__, dbw);
+		return;
+	}
+	debug("cacheline size %d\n", cacheline);
+	for (i = 0; placement < cacheline; i++) {
+		map_col[i] = placement++;
+	}
+	map_bg[0] = placement++;
+	for ( ; i < col_bits; i++) {
+		map_col[i] = placement++;
+		if (placement == intlv) {
+			placement++;
+		}
+	}
+	for ( ; i < 11; i++) {
+		map_col[i] = 0x3F;	/* unused col bits */
+	}
+
+	if (bg_bits >= 2) {
+		map_bg[1] = placement++;
+	}
+	map_ba[0] = placement++;
+	map_ba[1] = placement++;
+	if (cs != 0U) {
+		map_cs[0] = placement++;
+		if (cs == 2U) {
+			map_cs[1] = placement++;
+		}
+	} else {
+		map_cs[0] = U(0x3F);
+	}
+
+	for (i = 0; i < row_bits; i++) {
+		map_row[i] = placement++;
+	}
+
+	for ( ; i < 18; i++) {
+		map_row[i] = 0x3F;	/* unused row bits */
+	}
+
+	for (i = 39; i >= 0 ; i--) {
+		if (i == intlv) {
+			placement = 8;
+			p = 'I';
+		} else if (i < 3) {
+			p = 'b';
+			placement = 0;
+		} else {
+			placement = 0;
+			p = '-';
+		}
+		for (j = 0; j < 18; j++) {
+			if (map_row[j] != i) {
+				continue;
+			}
+			if (placement != 0) {
+				abort = 1;
+				ERROR("%s wrong address bit %d\n", __func__, i);
+			}
+			placement = i;
+			p = 'r';
+		}
+		for (j = 0; j < 11; j++) {
+			if (map_col[j] != i) {
+				continue;
+			}
+			if (placement != 0) {
+				abort = 1;
+				ERROR("%s wrong address bit %d\n", __func__, i);
+			}
+			placement = i;
+			p = 'c';
+		}
+		for (j = 0; j < 2; j++) {
+			if (map_ba[j] != i) {
+				continue;
+			}
+			if (placement != 0) {
+				abort = 1;
+				ERROR("%s wrong address bit %d\n", __func__, i);
+			}
+			placement = i;
+			p = 'B';
+		}
+		for (j = 0; j < 2; j++) {
+			if (map_bg[j] != i) {
+				continue;
+			}
+			if (placement != 0) {
+				abort = 1;
+				ERROR("%s wrong address bit %d\n", __func__, i);
+			}
+			placement = i;
+			p = 'G';
+		}
+		for (j = 0; j < 2; j++) {
+			if (map_cs[j] != i) {
+				continue;
+			}
+			if (placement != 0) {
+				abort = 1;
+				ERROR("%s wrong address bit %d\n", __func__, i);
+			}
+			placement = i;
+			p = 'C';
+		}
+#ifdef DDR_DEBUG
+		printf("%c", p);
+		if ((i % 4) == 0) {
+			printf(" ");
+		}
+#endif
+	}
+#ifdef DDR_DEBUG
+	puts("\n");
+#endif
+
+	if (abort != 0) {
+		return;
+	}
+
+	regs->dec[0] = map_row[17] << 26		|
+		      map_row[16] << 18			|
+		      map_row[15] << 10			|
+		      map_row[14] << 2;
+	regs->dec[1] = map_row[13] << 26		|
+		      map_row[12] << 18			|
+		      map_row[11] << 10			|
+		      map_row[10] << 2;
+	regs->dec[2] = map_row[9] << 26			|
+		      map_row[8] << 18			|
+		      map_row[7] << 10			|
+		      map_row[6] << 2;
+	regs->dec[3] = map_row[5] << 26			|
+		      map_row[4] << 18			|
+		      map_row[3] << 10			|
+		      map_row[2] << 2;
+	regs->dec[4] = map_row[1] << 26			|
+		      map_row[0] << 18			|
+		      map_col[10] << 10			|
+		      map_col[9] << 2;
+	regs->dec[5] = map_col[8] << 26			|
+		      map_col[7] << 18			|
+		      map_col[6] << 10			|
+		      map_col[5] << 2;
+	regs->dec[6] = map_col[4] << 26			|
+		      map_col[3] << 18			|
+		      map_col[2] << 10			|
+		      map_col[1] << 2;
+	regs->dec[7] = map_col[0] << 26			|
+		      map_ba[1] << 18			|
+		      map_ba[0] << 10			|
+		      map_cid[1] << 2;
+	regs->dec[8] = map_cid[1] << 26			|
+		      map_cs[1] << 18			|
+		      map_cs[0] << 10			|
+		      map_bg[1] << 2;
+	regs->dec[9] = map_bg[0] << 26			|
+		      1;
+	for (i = 0; i < 10; i++) {
+		debug("dec[%d] = 0x%x\n", i, regs->dec[i]);
+	}
+#endif
+}
+static unsigned int skip_caslat(unsigned int tckmin_ps,
+				unsigned int taamin_ps,
+				unsigned int mclk_ps,
+				unsigned int package_3ds)
+{
+	int i, j, k;
+	struct cas {
+		const unsigned int tckmin_ps;
+		const unsigned int caslat[4];
+	};
+	struct speed {
+		const struct cas *cl;
+		const unsigned int taamin_ps[4];
+	};
+	const struct cas cl_3200[] = {
+		{625,	{0xa00000, 0xb00000, 0xf000000,} },
+		{750,	{ 0x20000,  0x60000,  0xe00000,} },
+		{833,	{  0x8000,  0x18000,   0x38000,} },
+		{937,	{  0x4000,   0x4000,    0xc000,} },
+		{1071,	{  0x1000,   0x1000,    0x3000,} },
+		{1250,	{   0x400,    0x400,     0xc00,} },
+		{1500,	{       0,    0x600,     0x200,} },
+	};
+	const struct cas cl_2933[] = {
+		{682,	{       0,  0x80000, 0x180000, 0x380000} },
+		{750,	{ 0x20000,  0x60000,  0x60000,  0xe0000} },
+		{833,	{  0x8000,  0x18000,  0x18000,  0x38000} },
+		{937,	{  0x4000,   0x4000,   0x4000,   0xc000} },
+		{1071,	{  0x1000,   0x1000,   0x1000,   0x3000} },
+		{1250,	{   0x400,    0x400,    0x400,    0xc00} },
+		{1500,	{       0,    0x200,    0x200,    0x200} },
+	};
+	const struct cas cl_2666[] = {
+		{750,	{       0,  0x20000,  0x60000,  0xe0000} },
+		{833,	{  0x8000,  0x18000,  0x18000,  0x38000} },
+		{937,	{  0x4000,   0x4000,   0x4000,   0xc000} },
+		{1071,	{  0x1000,   0x1000,   0x1000,   0x3000} },
+		{1250,	{   0x400,    0x400,    0x400,    0xc00} },
+		{1500,	{       0,        0,    0x200,    0x200} },
+	};
+	const struct cas cl_2400[] = {
+		{833,	{       0,   0x8000,  0x18000,  0x38000} },
+		{937,	{  0xc000,   0x4000,   0x4000,   0xc000} },
+		{1071,	{  0x3000,   0x1000,   0x1000,   0x3000} },
+		{1250,	{   0xc00,    0x400,    0x400,    0xc00} },
+		{1500,	{       0,    0x400,    0x200,    0x200} },
+	};
+	const struct cas cl_2133[] = {
+		{937,	{       0,   0x4000,   0xc000,} },
+		{1071,	{  0x2000,        0,   0x2000,} },
+		{1250,	{   0x800,        0,    0x800,} },
+		{1500,	{       0,    0x400,    0x200,} },
+	};
+	const struct cas cl_1866[] = {
+		{1071,	{       0,   0x1000,   0x3000,} },
+		{1250,	{   0xc00,    0x400,    0xc00,} },
+		{1500,	{       0,    0x400,    0x200,} },
+	};
+	const struct cas cl_1600[] = {
+		{1250,	{       0,    0x400,    0xc00,} },
+		{1500,	{       0,    0x400,    0x200,} },
+	};
+	const struct speed bin_0[] = {
+		{cl_3200, {12500, 13750, 15000,} },
+		{cl_2933, {12960, 13640, 13750, 15000,} },
+		{cl_2666, {12750, 13500, 13750, 15000,} },
+		{cl_2400, {12500, 13320, 13750, 15000,} },
+		{cl_2133, {13130, 13500, 15000,} },
+		{cl_1866, {12850, 13500, 15000,} },
+		{cl_1600, {12500, 13500, 15000,} }
+	};
+	const struct cas cl_3200_3ds[] = {
+		{625,	{ 0xa000000, 0xb000000, 0xf000000,} },
+		{750,	{ 0xaa00000, 0xab00000, 0xef00000,} },
+		{833,	{ 0xaac0000, 0xaac0000, 0xebc0000,} },
+		{937,	{ 0xaab0000, 0xaab0000, 0xeaf0000,} },
+		{1071,	{ 0xaaa4000, 0xaaac000, 0xeaec000,} },
+		{1250,	{ 0xaaa0000, 0xaaa2000, 0xeaeb000,} },
+	};
+	const struct cas cl_2666_3ds[] = {
+		{750,	{ 0xa00000, 0xb00000, 0xf00000,} },
+		{833,	{ 0xac0000, 0xac0000, 0xbc0000,} },
+		{937,	{ 0xab0000, 0xab0000, 0xaf0000,} },
+		{1071,	{ 0xaa4000, 0xaac000, 0xaac000,} },
+		{1250,	{ 0xaa0000, 0xaaa000, 0xaaa000,} },
+	};
+	const struct cas cl_2400_3ds[] = {
+		{833,	{ 0xe00000, 0xe40000, 0xec0000, 0xb00000} },
+		{937,	{ 0xe00000, 0xe00000, 0xea0000, 0xae0000} },
+		{1071,	{ 0xe00000, 0xe04000, 0xeac000, 0xaec000} },
+		{1250,	{ 0xe00000, 0xe00000, 0xeaa000, 0xae2000} },
+	};
+	const struct cas cl_2133_3ds[] = {
+		{937,	{  0x90000,  0xb0000,  0xf0000,} },
+		{1071,	{  0x84000,  0xac000,  0xec000,} },
+		{1250,	{  0x80000,  0xa2000,  0xe2000,} },
+	};
+	const struct cas cl_1866_3ds[] = {
+		{1071,	{        0,   0x4000,   0xc000,} },
+		{1250,	{        0,   0x1000,   0x3000,} },
+	};
+	const struct cas cl_1600_3ds[] = {
+		{1250,	{        0,   0x1000,   0x3000,} },
+	};
+	const struct speed bin_3ds[] = {
+		{cl_3200_3ds, {15000, 16250, 17140,} },
+		{cl_2666_3ds, {15000, 16500, 17140,} },
+		{cl_2400_3ds, {15000, 15830, 16670, 17140} },
+		{cl_2133_3ds, {15950, 16880, 17140,} },
+		{cl_1866_3ds, {15000, 16070, 17140,} },
+		{cl_1600_3ds, {15000, 16250, 17500,} },
+	};
+	const struct speed *bin;
+	int size;
+	unsigned int taamin_max, tck_max;
+
+	if (taamin_ps > ((package_3ds != 0) ? 21500 : 18000)) {
+		ERROR("taamin_ps %u invalid\n", taamin_ps);
+		return 0;
+	}
+	if (package_3ds != 0) {
+		bin = bin_3ds;
+		size = ARRAY_SIZE(bin_3ds);
+		taamin_max = 1250;
+		tck_max = 1500;
+	} else {
+		bin = bin_0;
+		size = ARRAY_SIZE(bin_0);
+		taamin_max = 1500;
+		tck_max = 1600;
+	}
+	if (mclk_ps < 625 || mclk_ps > tck_max) {
+		ERROR("mclk %u invalid\n", mclk_ps);
+		return 0;
+	}
+
+	for (i = 0; i < size; i++) {
+		if (bin[i].cl[0].tckmin_ps >= tckmin_ps) {
+			break;
+		}
+	}
+	if (i >= size) {
+		ERROR("speed bin not found\n");
+		return 0;
+	}
+	if (bin[i].cl[0].tckmin_ps > tckmin_ps && i > 0) {
+		i--;
+	}
+
+	for (j = 0; j < 4; j++) {
+		if ((bin[i].taamin_ps[j] == 0) ||
+		    bin[i].taamin_ps[j] >= taamin_ps) {
+			break;
+		}
+	}
+
+	if (j >= 4) {
+		ERROR("taamin_ps out of range.\n");
+		return 0;
+	}
+
+	if ((bin[i].taamin_ps[j] == 0) ||
+	    (bin[i].taamin_ps[j] > taamin_ps && j > 0)) {
+		j--;
+	}
+
+	for (k = 0; bin[i].cl[k].tckmin_ps < mclk_ps &&
+		    bin[i].cl[k].tckmin_ps < taamin_max; k++)
+		;
+	if (bin[i].cl[k].tckmin_ps > mclk_ps && k > 0) {
+		k--;
+	}
+
+	debug("Skip CL mask for this speed 0x%x\n", bin[i].cl[k].caslat[j]);
+
+	return bin[i].cl[k].caslat[j];
+}
+
+int compute_ddrc(const unsigned long clk,
+		 const struct memctl_opt *popts,
+		 const struct ddr_conf *conf,
+		 struct ddr_cfg_regs *regs,
+		 const struct dimm_params *pdimm,
+		 unsigned int ip_rev)
+{
+	unsigned int cas_latency;
+	unsigned int caslat_skip;
+	unsigned int additive_latency;
+	const unsigned int mclk_ps = get_memory_clk_ps(clk);
+	int i;
+
+	zeromem(regs, sizeof(struct ddr_cfg_regs));
+
+	if (mclk_ps < pdimm->tckmin_x_ps) {
+		ERROR("DDR Clk: MCLK cycle is %u ps.\n", mclk_ps);
+		ERROR("DDR Clk is faster than DIMM can support.\n");
+	}
+
+	/* calculate cas latency, override first */
+	cas_latency = (popts->caslat_override != 0) ?
+			popts->caslat_override_value :
+			(pdimm->taa_ps + mclk_ps - 1) / mclk_ps;
+
+	/* skip unsupported caslat based on speed bin */
+	caslat_skip = skip_caslat(pdimm->tckmin_x_ps,
+				  pdimm->taa_ps,
+				  mclk_ps,
+				  pdimm->package_3ds);
+	debug("Skip caslat 0x%x\n", caslat_skip);
+
+	/* Check if DIMM supports the cas latency */
+	i = 24;
+	while (((pdimm->caslat_x & ~caslat_skip & (1 << cas_latency)) == 0) &&
+	       (i-- > 0)) {
+		cas_latency++;
+	}
+
+	if (i <= 0) {
+		ERROR("Failed to find a proper cas latency\n");
+		return -EINVAL;
+	}
+	/* Verify cas latency does not exceed 18ns for DDR4 */
+	if (cas_latency * mclk_ps > 18000) {
+		ERROR("cas latency is too large %d\n", cas_latency);
+		return -EINVAL;
+	}
+
+	additive_latency = (popts->addt_lat_override != 0) ?
+				popts->addt_lat_override_value : 0;
+
+	cal_ddr_csn_bnds(regs, popts, conf, pdimm);
+	cal_ddr_sdram_cfg(clk, regs, popts, pdimm, ip_rev);
+	cal_ddr_sdram_rcw(clk, regs, popts, pdimm);
+	cal_timing_cfg(clk, regs, popts, pdimm, conf, cas_latency,
+		       additive_latency);
+	cal_ddr_dq_mapping(regs, pdimm);
+
+	if (ip_rev >= 0x50500) {
+		cal_ddr_addr_dec(regs);
+	}
+
+	cal_ddr_sdram_mode(clk, regs, popts, conf, pdimm, cas_latency,
+			   additive_latency, ip_rev);
+	cal_ddr_eor(regs, popts);
+	cal_ddr_data_init(regs);
+	cal_ddr_sdram_interval(clk, regs, popts, pdimm);
+	cal_ddr_zq_cntl(regs);
+	cal_ddr_sr_cntr(regs, popts);
+
+	return 0;
+}
diff --git a/drivers/nxp/ddr/nxp-ddr/utility.c b/drivers/nxp/ddr/nxp-ddr/utility.c
new file mode 100644
index 0000000..d33ad77
--- /dev/null
+++ b/drivers/nxp/ddr/nxp-ddr/utility.c
@@ -0,0 +1,275 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <immap.h>
+#include <lib/mmio.h>
+
+#define UL_5POW12	244140625UL
+#define ULL_2E12	2000000000000ULL
+#define UL_2POW13	(1UL << 13)
+#define ULL_8FS		0xFFFFFFFFULL
+
+#define do_div(n, base) ({				\
+	unsigned int __base = (base);			\
+	unsigned int __rem;				\
+	__rem = ((unsigned long long)(n)) % __base;	\
+	(n) = ((unsigned long long)(n)) / __base;	\
+	__rem;						\
+})
+
+#define CCN_HN_F_SAM_NODEID_MASK	0x7f
+#ifdef NXP_HAS_CCN504
+#define CCN_HN_F_SAM_NODEID_DDR0	0x4
+#define CCN_HN_F_SAM_NODEID_DDR1	0xe
+#elif defined(NXP_HAS_CCN508)
+#define CCN_HN_F_SAM_NODEID_DDR0	0x8
+#define CCN_HN_F_SAM_NODEID_DDR1	0x18
+#endif
+
+unsigned long get_ddr_freq(struct sysinfo *sys, int ctrl_num)
+{
+	if (sys->freq_ddr_pll0 == 0) {
+		get_clocks(sys);
+	}
+
+	switch (ctrl_num) {
+	case 0:
+		return sys->freq_ddr_pll0;
+	case 1:
+		return sys->freq_ddr_pll0;
+	case 2:
+		return sys->freq_ddr_pll1;
+	}
+
+	return 0;
+}
+
+unsigned int get_memory_clk_ps(const unsigned long data_rate)
+{
+	unsigned int result;
+	/* Round to nearest 10ps, being careful about 64-bit multiply/divide */
+	unsigned long long rem, mclk_ps = ULL_2E12;
+
+	/* Now perform the big divide, the result fits in 32-bits */
+	rem = do_div(mclk_ps, data_rate);
+	result = (rem >= (data_rate >> 1)) ? mclk_ps + 1 : mclk_ps;
+
+	return result;
+}
+
+unsigned int picos_to_mclk(unsigned long data_rate, unsigned int picos)
+{
+	unsigned long long clks, clks_rem;
+
+	/* Short circuit for zero picos */
+	if ((picos == 0U) || (data_rate == 0UL)) {
+		return 0U;
+	}
+
+	/* First multiply the time by the data rate (32x32 => 64) */
+	clks = picos * (unsigned long long)data_rate;
+	/*
+	 * Now divide by 5^12 and track the 32-bit remainder, then divide
+	 * by 2*(2^12) using shifts (and updating the remainder).
+	 */
+	clks_rem = do_div(clks, UL_5POW12);
+	clks_rem += (clks & (UL_2POW13-1)) * UL_5POW12;
+	clks >>= 13U;
+
+	/* If we had a remainder greater than the 1ps error, then round up */
+	if (clks_rem > data_rate) {
+		clks++;
+	}
+
+	/* Clamp to the maximum representable value */
+	if (clks > ULL_8FS) {
+		clks = ULL_8FS;
+	}
+	return (unsigned int) clks;
+}
+
+/* valid_spd_mask has been checked by parse_spd */
+int disable_unused_ddrc(struct ddr_info *priv,
+			int valid_spd_mask, uintptr_t nxp_ccn_hn_f0_addr)
+{
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+	void *hnf_sam_ctrl = (void *)(nxp_ccn_hn_f0_addr + CCN_HN_F_SAM_CTL);
+	uint32_t val, nodeid;
+#ifdef NXP_HAS_CCN504
+	uint32_t num_hnf_nodes = 4U;
+#else
+	uint32_t num_hnf_nodes = 8U;
+#endif
+	int disable_ddrc = 0;
+	int i;
+
+	if (priv->num_ctlrs < 2) {
+		debug("%s: nothing to do.\n", __func__);
+	}
+
+	switch (priv->dimm_on_ctlr) {
+	case 1:
+		disable_ddrc = ((valid_spd_mask &0x2) == 0) ? 2 : 0;
+		disable_ddrc = ((valid_spd_mask &0x1) == 0) ? 1 : disable_ddrc;
+		break;
+	case 2:
+		disable_ddrc = ((valid_spd_mask &0x4) == 0) ? 2 : 0;
+		disable_ddrc = ((valid_spd_mask &0x1) == 0) ? 1 : disable_ddrc;
+		break;
+	default:
+		ERROR("Invalid number of DIMMs %d\n", priv->dimm_on_ctlr);
+		return -EINVAL;
+	}
+
+	if (disable_ddrc != 0) {
+		debug("valid_spd_mask = 0x%x\n", valid_spd_mask);
+	}
+
+	switch (disable_ddrc) {
+	case 1:
+		priv->num_ctlrs = 1;
+		priv->spd_addr = &priv->spd_addr[priv->dimm_on_ctlr];
+		priv->ddr[0] = priv->ddr[1];
+		priv->ddr[1] = NULL;
+		priv->phy[0] = priv->phy[0];
+		priv->phy[1] = NULL;
+		debug("Disable first DDR controller\n");
+		break;
+	case 2:
+		priv->num_ctlrs = 1;
+		priv->ddr[1] = NULL;
+		priv->phy[1] = NULL;
+		debug("Disable second DDR controller\n");
+		/* fallthrough */
+	case 0:
+		break;
+	default:
+		ERROR("Program error.\n");
+		return -EINVAL;
+	}
+
+	if (disable_ddrc == 0) {
+		debug("Both controllers in use.\n");
+		return 0;
+	}
+
+	for (i = 0; i < num_hnf_nodes; i++) {
+		val = mmio_read_64((uintptr_t)hnf_sam_ctrl);
+		nodeid = disable_ddrc == 1 ? CCN_HN_F_SAM_NODEID_DDR1 :
+			 (disable_ddrc == 2 ? CCN_HN_F_SAM_NODEID_DDR0 :
+			  (i < 4 ? CCN_HN_F_SAM_NODEID_DDR0
+				 : CCN_HN_F_SAM_NODEID_DDR1));
+		if (nodeid != (val & CCN_HN_F_SAM_NODEID_MASK)) {
+			debug("Setting HN-F node %d\n", i);
+			debug("nodeid = 0x%x\n", nodeid);
+			val &= ~CCN_HN_F_SAM_NODEID_MASK;
+			val |= nodeid;
+			mmio_write_64((uintptr_t)hnf_sam_ctrl, val);
+		}
+		hnf_sam_ctrl += CCN_HN_F_REGION_SIZE;
+	}
+#endif
+	return 0;
+}
+
+unsigned int get_ddrc_version(const struct ccsr_ddr *ddr)
+{
+	unsigned int ver;
+
+	ver = (ddr_in32(&ddr->ip_rev1) & 0xFFFF) << 8U;
+	ver |= (ddr_in32(&ddr->ip_rev2) & 0xFF00) >> 8U;
+
+	return ver;
+}
+
+void print_ddr_info(struct ccsr_ddr *ddr)
+{
+	unsigned int cs0_config = ddr_in32(&ddr->csn_cfg[0]);
+	unsigned int sdram_cfg = ddr_in32(&ddr->sdram_cfg);
+	int cas_lat;
+
+	if ((sdram_cfg & SDRAM_CFG_MEM_EN) == 0U) {
+		printf(" (DDR not enabled)\n");
+		return;
+	}
+
+	printf("DDR");
+	switch ((sdram_cfg & SDRAM_CFG_SDRAM_TYPE_MASK) >>
+		SDRAM_CFG_SDRAM_TYPE_SHIFT) {
+	case SDRAM_TYPE_DDR4:
+		printf("4");
+		break;
+	default:
+		printf("?");
+		break;
+	}
+
+	switch (sdram_cfg & SDRAM_CFG_DBW_MASK) {
+	case SDRAM_CFG_32_BW:
+		printf(", 32-bit");
+		break;
+	case SDRAM_CFG_16_BW:
+		printf(", 16-bit");
+		break;
+	case SDRAM_CFG_8_BW:
+		printf(", 8-bit");
+		break;
+	default:
+		printf(", 64-bit");
+		break;
+	}
+
+	/* Calculate CAS latency based on timing cfg values */
+	cas_lat = ((ddr_in32(&ddr->timing_cfg_1) >> 16) & 0xf);
+	cas_lat += 2;	/* for DDRC newer than 4.4 */
+	cas_lat += ((ddr_in32(&ddr->timing_cfg_3) >> 12) & 3) << 4;
+	printf(", CL=%d", cas_lat >> 1);
+	if ((cas_lat & 0x1) != 0) {
+		printf(".5");
+	}
+
+	if ((sdram_cfg & SDRAM_CFG_ECC_EN) != 0) {
+		printf(", ECC on");
+	} else {
+		printf(", ECC off");
+	}
+
+	if ((cs0_config & 0x20000000) != 0) {
+		printf(", ");
+		switch ((cs0_config >> 24) & 0xf) {
+		case DDR_256B_INTLV:
+			printf("256B");
+			break;
+		default:
+			printf("invalid");
+			break;
+		}
+	}
+
+	if (((sdram_cfg >> 8) & 0x7f) != 0) {
+		printf(", ");
+		switch (sdram_cfg >> 8 & 0x7f) {
+		case DDR_BA_INTLV_CS0123:
+			printf("CS0+CS1+CS2+CS3");
+			break;
+		case DDR_BA_INTLV_CS01:
+			printf("CS0+CS1");
+			break;
+		default:
+			printf("invalid");
+			break;
+		}
+	}
+	printf("\n");
+}
diff --git a/drivers/nxp/ddr/phy-gen1/phy.c b/drivers/nxp/ddr/phy-gen1/phy.c
new file mode 100644
index 0000000..4b66d38
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen1/phy.c
@@ -0,0 +1,97 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+
+static void cal_ddr_sdram_clk_cntl(struct ddr_cfg_regs *regs,
+					 const struct memctl_opt *popts)
+{
+	const unsigned int clk_adj = popts->clk_adj;
+	const unsigned int ss_en = 0U;
+
+	regs->clk_cntl = ((ss_en & U(0x1)) << 31U)		|
+				  ((clk_adj & U(0x1F)) << 22U);
+	debug("clk_cntl = 0x%x\n", regs->clk_cntl);
+}
+
+static void cal_ddr_cdr(struct ddr_cfg_regs *regs,
+			const struct memctl_opt *popts)
+{
+	regs->cdr[0] = popts->ddr_cdr1;
+	regs->cdr[1] = popts->ddr_cdr2;
+	debug("cdr[0] = 0x%x\n", regs->cdr[0]);
+	debug("cdr[1] = 0x%x\n", regs->cdr[1]);
+}
+
+static void cal_ddr_wrlvl_cntl(struct ddr_cfg_regs *regs,
+				const struct memctl_opt *popts)
+{
+	const unsigned int wrlvl_en = 1U;	/* enabled */
+	const unsigned int wrlvl_mrd = U(0x6);	/* > 40nCK */
+	const unsigned int wrlvl_odten = U(0x7);	/* 128 */
+	const unsigned int wrlvl_dqsen = U(0x5);	/* > 25nCK */
+	const unsigned int wrlvl_wlr = U(0x6);	/* > tWLO + 6 */
+	const unsigned int wrlvl_smpl = popts->wrlvl_override ?
+					popts->wrlvl_sample : U(0xf);
+	const unsigned int wrlvl_start = popts->wrlvl_start;
+
+	regs->wrlvl_cntl[0] = ((wrlvl_en & U(0x1)) << 31U)	|
+				  ((wrlvl_mrd & U(0x7)) << 24U)	|
+				  ((wrlvl_odten & U(0x7)) << 20U)	|
+				  ((wrlvl_dqsen & U(0x7)) << 16U)	|
+				  ((wrlvl_smpl & U(0xf)) << 12U)	|
+				  ((wrlvl_wlr & U(0x7)) << 8U)	|
+				  ((wrlvl_start & U(0x1F)) << 0U);
+	regs->wrlvl_cntl[1] = popts->wrlvl_ctl_2;
+	regs->wrlvl_cntl[2] = popts->wrlvl_ctl_3;
+	debug("wrlvl_cntl[0] = 0x%x\n", regs->wrlvl_cntl[0]);
+	debug("wrlvl_cntl[1] = 0x%x\n", regs->wrlvl_cntl[1]);
+	debug("wrlvl_cntl[2] = 0x%x\n", regs->wrlvl_cntl[2]);
+
+}
+
+static void cal_ddr_dbg(struct ddr_cfg_regs *regs,
+			const struct memctl_opt *popts)
+{
+	if (popts->cswl_override != 0) {
+		regs->debug[18] = popts->cswl_override;
+	}
+
+#ifdef CONFIG_SYS_FSL_DDR_EMU
+	/* disable DDR training for emulator */
+	regs->debug[2] = U(0x00000400);
+	regs->debug[4] = U(0xff800800);
+	regs->debug[5] = U(0x08000800);
+	regs->debug[6] = U(0x08000800);
+	regs->debug[7] = U(0x08000800);
+	regs->debug[8] = U(0x08000800);
+#endif
+	if (popts->cpo_sample != 0U) {
+		regs->debug[28] = popts->cpo_sample;
+		debug("debug[28] = 0x%x\n", regs->debug[28]);
+	}
+}
+
+int compute_ddr_phy(struct ddr_info *priv)
+{
+	const struct memctl_opt *popts = &priv->opt;
+	struct ddr_cfg_regs *regs = &priv->ddr_reg;
+
+	cal_ddr_sdram_clk_cntl(regs, popts);
+	cal_ddr_cdr(regs, popts);
+	cal_ddr_wrlvl_cntl(regs, popts);
+	cal_ddr_dbg(regs, popts);
+
+	return 0;
+}
diff --git a/drivers/nxp/ddr/phy-gen2/csr.h b/drivers/nxp/ddr/phy-gen2/csr.h
new file mode 100644
index 0000000..ee7b4d8
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/csr.h
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef CSR_H
+#define CSR_H
+
+#define t_anib					0
+#define t_dbyte					0x10000
+#define t_master				0x20000
+#define t_acsm					0x40000
+#define t_initeng				0x90000
+#define t_drtub					0xc0000
+#define t_apbonly				0xd0000
+#define csr_dbyte_misc_mode_addr		0x00
+#define csr_micro_cont_mux_sel_addr		0x00
+#define csr_uct_shadow_regs			0x04
+#define csr_cal_uclk_info_addr			0x08
+#define csr_seq0bdly0_addr			0x0b
+#define csr_seq0bdly1_addr			0x0c
+#define csr_seq0bdly2_addr			0x0d
+#define csr_seq0bdly3_addr			0x0e
+#define csr_seq0bdisable_flag0_addr		0x0c
+#define csr_seq0bdisable_flag1_addr		0x0d
+#define csr_seq0bdisable_flag2_addr		0x0e
+#define csr_seq0bdisable_flag3_addr		0x0f
+#define csr_seq0bdisable_flag4_addr		0x10
+#define csr_seq0bdisable_flag5_addr		0x11
+#define csr_seq0bdisable_flag6_addr		0x12
+#define csr_seq0bdisable_flag7_addr		0x13
+#define csr_dfi_mode_addr			0x18
+#define csr_tristate_mode_ca_addr		0x19
+#define csr_dfiphyupd_addr			0x21
+#define csr_dqs_preamble_control_addr		0x24
+#define csr_master_x4config_addr		0x25
+#define csr_enable_cs_multicast_addr		0x27
+#define csr_acx4_anib_dis_addr			0x2c
+#define csr_dmipin_present_addr			0x2d
+#define csr_ard_ptr_init_val_addr		0x2e
+#define csr_dct_write_prot			0x31
+#define csr_uct_write_only_shadow		0x32
+#define csr_uct_write_prot			0x33
+#define csr_uct_dat_write_only_shadow		0x34
+#define	csr_dbyte_dll_mode_cntrl_addr		0x3a
+#define csr_atx_impedance_addr			0x43
+#define csr_dq_dqs_rcv_cntrl_addr		0x43
+#define csr_cal_offsets_addr			0x45
+#define csr_tx_impedance_ctrl1_addr		0x49
+#define csr_dq_dqs_rcv_cntrl1_addr		0x4a
+#define csr_tx_odt_drv_stren_addr		0x4d
+#define csr_cal_drv_str0_addr			0x50
+#define csr_atx_slew_rate_addr			0x55
+#define csr_proc_odt_time_ctl_addr		0x56
+#define csr_mem_alert_control_addr		0x5b
+#define csr_mem_alert_control2_addr		0x5c
+#define csr_tx_slew_rate_addr			0x5f
+#define csr_mem_reset_l_addr			0x60
+#define csr_dfi_camode_addr			0x75
+#define csr_dll_gain_ctl_addr			0x7c
+#define csr_dll_lockparam_addr			0x7d
+#define csr_ucclk_hclk_enables_addr		0x80
+#define csr_acsm_playback0x0_addr		0x80
+#define csr_acsm_playback1x0_addr		0x81
+#define csr_cal_rate_addr			0x88
+#define csr_cal_zap_addr			0x89
+#define csr_cal_misc2_addr			0x98
+#define csr_micro_reset_addr			0x99
+#define csr_dfi_rd_data_cs_dest_map_addr	0xb0
+#define csr_vref_in_global_addr			0xb2
+#define csr_dfi_wr_data_cs_dest_map_addr	0xb4
+#define csr_pll_pwr_dn_addr			0xc3
+#define csr_pll_ctrl2_addr			0xc5
+#define csr_pll_ctrl1_addr			0xc7
+#define csr_pll_test_mode_addr			0xca
+#define csr_pll_ctrl4_addr			0xcc
+#define csr_dfi_freq_xlat0_addr			0xf0
+#define csr_acsm_ctrl0_addr			0xf0
+#define csr_dfi_freq_ratio_addr			0xfa
+#define csr_acsm_ctrl13_addr			0xfd
+#define csr_tx_pre_drv_mode_lsb			8
+#define csr_tx_pre_n_lsb			4
+#define csr_tx_pre_p_lsb			0
+#define csr_atx_pre_drv_mode_lsb		8
+#define csr_atx_pre_n_lsb			4
+#define csr_atx_pre_p_lsb			0
+#define csr_wdqsextension_lsb			8
+#define csr_lp4sttc_pre_bridge_rx_en_lsb	7
+#define csr_lp4postamble_ext_lsb		6
+#define csr_lp4tgl_two_tck_tx_dqs_pre_lsb	5
+#define csr_position_dfe_init_lsb		2
+#define csr_two_tck_tx_dqs_pre_lsb		1
+#define csr_two_tck_rx_dqs_pre_lsb		0
+#define csr_dll_rx_preamble_mode_lsb		1
+#define csr_odtstren_n_lsb			6
+#define csr_drv_stren_fsdq_n_lsb		6
+#define	csr_drv_stren_fsdq_p_lsb		0
+#define csr_adrv_stren_n_lsb			5
+#define csr_adrv_stren_p_lsb			0
+#define csr_cal_drv_str_pu50_lsb		4
+#define csr_cal_once_lsb			5
+#define csr_cal_interval_lsb			0
+#define csr_cal_run_lsb				4
+#define csr_global_vref_in_dac_lsb		3
+#define csr_gain_curr_adj_lsb			7
+#define csr_major_mode_dbyte_lsb		4
+#define csr_dfe_ctrl_lsb			2
+#define csr_ext_vref_range_lsb			1
+#define csr_sel_analog_vref_lsb			0
+#define csr_malertsync_bypass_lsb		0
+#define csr_ck_dis_val_lsb			2
+#define csr_ddr2tmode_lsb			1
+#define csr_dis_dyn_adr_tri_lsb			0
+#define	csr_dbyte_disable_lsb			2
+#define csr_power_down_rcvr_lsb			0
+#define csr_power_down_rcvr_dqs_lsb		9
+#define csr_rx_pad_standby_en_lsb		10
+#define csr_rx_pad_standby_en_mask		0x400
+#define csr_x4tg_lsb				0
+#define csr_reset_to_micro_mask			0x8
+#define csr_protect_mem_reset_mask		0x2
+#define csr_stall_to_micro_mask			0x1
+#define uct_write_prot_shadow_mask		0x1
+#define csr_acsm_par_mode_mask			0x4000
+#define csr_acsm_cke_enb_lsb			0
+#define csr_dfiphyupd_threshold_lsb		8
+#define csr_dfiphyupd_threshold_msb		11
+#define csr_dfiphyupd_threshold_mask		0xf00
+#define csr_dfi_rd_destm0_lsb			0
+#define csr_dfi_rd_destm1_lsb			2
+#define csr_dfi_rd_destm2_lsb			4
+#define csr_dfi_rd_destm3_lsb			6
+#define csr_dfi_wr_destm0_lsb			0
+#define csr_dfi_wr_destm1_lsb			2
+#define csr_dfi_wr_destm2_lsb			4
+#define csr_dfi_wr_destm3_lsb			6
+#define csr_acsm_2t_mode_mask			0x40
+#define csr_cal_misc2_err_dis			13
+#define csr_cal_offset_pdc_lsb			6
+#define csr_cal_offset_pdc_msb			9
+#define csr_cal_offset_pdc_mask			0xe0
+#define csr_cal_drv_pdth_mask			0x3c0
+
+
+struct impedance_mapping {
+	int ohm;
+	int code;
+};
+
+#endif
diff --git a/drivers/nxp/ddr/phy-gen2/ddr4fw.h b/drivers/nxp/ddr/phy-gen2/ddr4fw.h
new file mode 100644
index 0000000..f17f2e7
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/ddr4fw.h
@@ -0,0 +1,2897 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR4FW
+#define DDR4FW
+
+#define PHY_GEN2_MAX_IMAGE_SIZE		32768
+#define PHY_GEN2_IMEM_ADDR		0x50000
+#define PHY_GEN2_DMEM_ADDR		0x54000
+
+struct ddr4u1d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  reserved19[0x1B - 0x19];
+	uint8_t  share2dvref_result;
+	uint8_t  reserved1c[0x22 - 0x1c];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	int8_t   cdd_rr_3_2;
+	int8_t   cdd_rr_3_1;
+	int8_t   cdd_rr_3_0;
+	int8_t   cdd_rr_2_3;
+	int8_t   cdd_rr_2_1;
+	int8_t   cdd_rr_2_0;
+	int8_t   cdd_rr_1_3;
+	int8_t   cdd_rr_1_2;
+	int8_t   cdd_rr_1_0;
+	int8_t   cdd_rr_0_3;
+	int8_t   cdd_rr_0_2;
+	int8_t   cdd_rr_0_1;
+	int8_t   cdd_ww_3_2;
+	int8_t   cdd_ww_3_1;
+	int8_t   cdd_ww_3_0;
+	int8_t   cdd_ww_2_3;
+	int8_t   cdd_ww_2_1;
+	int8_t   cdd_ww_2_0;
+	int8_t   cdd_ww_1_3;
+	int8_t   cdd_ww_1_2;
+	int8_t   cdd_ww_1_0;
+	int8_t   cdd_ww_0_3;
+	int8_t   cdd_ww_0_2;
+	int8_t   cdd_ww_0_1;
+	int8_t   cdd_rw_3_3;
+	int8_t   cdd_rw_3_2;
+	int8_t   cdd_rw_3_1;
+	int8_t   cdd_rw_3_0;
+	int8_t   cdd_rw_2_3;
+	int8_t   cdd_rw_2_2;
+	int8_t   cdd_rw_2_1;
+	int8_t   cdd_rw_2_0;
+	int8_t   cdd_rw_1_3;
+	int8_t   cdd_rw_1_2;
+	int8_t   cdd_rw_1_1;
+	int8_t   cdd_rw_1_0;
+	int8_t   cdd_rw_0_3;
+	int8_t   cdd_rw_0_2;
+	int8_t   cdd_rw_0_1;
+	int8_t   cdd_rw_0_0;
+	int8_t   cdd_wr_3_3;
+	int8_t   cdd_wr_3_2;
+	int8_t   cdd_wr_3_1;
+	int8_t   cdd_wr_3_0;
+	int8_t   cdd_wr_2_3;
+	int8_t   cdd_wr_2_2;
+	int8_t   cdd_wr_2_1;
+	int8_t   cdd_wr_2_0;
+	int8_t   cdd_wr_1_3;
+	int8_t   cdd_wr_1_2;
+	int8_t   cdd_wr_1_1;
+	int8_t   cdd_wr_1_0;
+	int8_t   cdd_wr_0_3;
+	int8_t   cdd_wr_0_2;
+	int8_t   cdd_wr_0_1;
+	int8_t   cdd_wr_0_0;
+	uint8_t  reserved5d;
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  reserved_d6[0x3f6 - 0xd6];
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+
+struct ddr4u2d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  rx2d_train_opt;
+	uint8_t  tx2d_train_opt;
+	uint8_t  share2dvref_result;
+	uint8_t  delay_weight2d;
+	uint8_t  voltage_weight2d;
+	uint8_t  reserved1e[0x22 - 0x1e];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	uint8_t  r0_rx_clk_dly_margin;
+	uint8_t  r0_vref_dac_margin;
+	uint8_t  r0_tx_dq_dly_margin;
+	uint8_t  r0_device_vref_margin;
+	uint8_t  reserved29[0x33 - 0x29];
+	uint8_t  r1_rx_clk_dly_margin;
+	uint8_t  r1_vref_dac_margin;
+	uint8_t  r1_tx_dq_dly_margin;
+	uint8_t  r1_device_vref_margin;
+	uint8_t  reserved37[0x41 - 0x37];
+	uint8_t  r2_rx_clk_dly_margin;
+	uint8_t  r2_vref_dac_margin;
+	uint8_t  r2_tx_dq_dly_margin;
+	uint8_t  r2_device_vref_margin;
+	uint8_t  reserved45[0x4f - 0x45];
+	uint8_t  r3_rx_clk_dly_margin;
+	uint8_t  r3_vref_dac_margin;
+	uint8_t  r3_tx_dq_dly_margin;
+	uint8_t  r3_device_vref_margin;
+	uint8_t  reserved53[0x5e - 0x53];
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  reserved_d6[0x3f6 - 0xd6];
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+
+struct ddr4r1d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  reserved19[0x22 - 0x19];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	int8_t   cdd_rr_3_2;
+	int8_t   cdd_rr_3_1;
+	int8_t   cdd_rr_3_0;
+	int8_t   cdd_rr_2_3;
+	int8_t   cdd_rr_2_1;
+	int8_t   cdd_rr_2_0;
+	int8_t   cdd_rr_1_3;
+	int8_t   cdd_rr_1_2;
+	int8_t   cdd_rr_1_0;
+	int8_t   cdd_rr_0_3;
+	int8_t   cdd_rr_0_2;
+	int8_t   cdd_rr_0_1;
+	int8_t   cdd_ww_3_2;
+	int8_t   cdd_ww_3_1;
+	int8_t   cdd_ww_3_0;
+	int8_t   cdd_ww_2_3;
+	int8_t   cdd_ww_2_1;
+	int8_t   cdd_ww_2_0;
+	int8_t   cdd_ww_1_3;
+	int8_t   cdd_ww_1_2;
+	int8_t   cdd_ww_1_0;
+	int8_t   cdd_ww_0_3;
+	int8_t   cdd_ww_0_2;
+	int8_t   cdd_ww_0_1;
+	int8_t   cdd_rw_3_3;
+	int8_t   cdd_rw_3_2;
+	int8_t   cdd_rw_3_1;
+	int8_t   cdd_rw_3_0;
+	int8_t   cdd_rw_2_3;
+	int8_t   cdd_rw_2_2;
+	int8_t   cdd_rw_2_1;
+	int8_t   cdd_rw_2_0;
+	int8_t   cdd_rw_1_3;
+	int8_t   cdd_rw_1_2;
+	int8_t   cdd_rw_1_1;
+	int8_t   cdd_rw_1_0;
+	int8_t   cdd_rw_0_3;
+	int8_t   cdd_rw_0_2;
+	int8_t   cdd_rw_0_1;
+	int8_t   cdd_rw_0_0;
+	int8_t   cdd_wr_3_3;
+	int8_t   cdd_wr_3_2;
+	int8_t   cdd_wr_3_1;
+	int8_t   cdd_wr_3_0;
+	int8_t   cdd_wr_2_3;
+	int8_t   cdd_wr_2_2;
+	int8_t   cdd_wr_2_1;
+	int8_t   cdd_wr_2_0;
+	int8_t   cdd_wr_1_3;
+	int8_t   cdd_wr_1_2;
+	int8_t   cdd_wr_1_1;
+	int8_t   cdd_wr_1_0;
+	int8_t   cdd_wr_0_3;
+	int8_t   cdd_wr_0_2;
+	int8_t   cdd_wr_0_1;
+	int8_t   cdd_wr_0_0;
+	uint8_t  reserved5d;
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  f0rc00_d0;
+	uint8_t  f0rc01_d0;
+	uint8_t  f0rc02_d0;
+	uint8_t  f0rc03_d0;
+	uint8_t  f0rc04_d0;
+	uint8_t  f0rc05_d0;
+	uint8_t  f0rc06_d0;
+	uint8_t  f0rc07_d0;
+	uint8_t  f0rc08_d0;
+	uint8_t  f0rc09_d0;
+	uint8_t  f0rc0a_d0;
+	uint8_t  f0rc0b_d0;
+	uint8_t  f0rc0c_d0;
+	uint8_t  f0rc0d_d0;
+	uint8_t  f0rc0e_d0;
+	uint8_t  f0rc0f_d0;
+	uint8_t  f0rc1x_d0;
+	uint8_t  f0rc2x_d0;
+	uint8_t  f0rc3x_d0;
+	uint8_t  f0rc4x_d0;
+	uint8_t  f0rc5x_d0;
+	uint8_t  f0rc6x_d0;
+	uint8_t  f0rc7x_d0;
+	uint8_t  f0rc8x_d0;
+	uint8_t  f0rc9x_d0;
+	uint8_t  f0rcax_d0;
+	uint8_t  f0rcbx_d0;
+	uint8_t  f1rc00_d0;
+	uint8_t  f1rc01_d0;
+	uint8_t  f1rc02_d0;
+	uint8_t  f1rc03_d0;
+	uint8_t  f1rc04_d0;
+	uint8_t  f1rc05_d0;
+	uint8_t  f1rc06_d0;
+	uint8_t  f1rc07_d0;
+	uint8_t  f1rc08_d0;
+	uint8_t  f1rc09_d0;
+	uint8_t  f1rc0a_d0;
+	uint8_t  f1rc0b_d0;
+	uint8_t  f1rc0c_d0;
+	uint8_t  f1rc0d_d0;
+	uint8_t  f1rc0e_d0;
+	uint8_t  f1rc0f_d0;
+	uint8_t  f1rc1x_d0;
+	uint8_t  f1rc2x_d0;
+	uint8_t  f1rc3x_d0;
+	uint8_t  f1rc4x_d0;
+	uint8_t  f1rc5x_d0;
+	uint8_t  f1rc6x_d0;
+	uint8_t  f1rc7x_d0;
+	uint8_t  f1rc8x_d0;
+	uint8_t  f1rc9x_d0;
+	uint8_t  f1rcax_d0;
+	uint8_t  f1rcbx_d0;
+	uint8_t  f0rc00_d1;
+	uint8_t  f0rc01_d1;
+	uint8_t  f0rc02_d1;
+	uint8_t  f0rc03_d1;
+	uint8_t  f0rc04_d1;
+	uint8_t  f0rc05_d1;
+	uint8_t  f0rc06_d1;
+	uint8_t  f0rc07_d1;
+	uint8_t  f0rc08_d1;
+	uint8_t  f0rc09_d1;
+	uint8_t  f0rc0a_d1;
+	uint8_t  f0rc0b_d1;
+	uint8_t  f0rc0c_d1;
+	uint8_t  f0rc0d_d1;
+	uint8_t  f0rc0e_d1;
+	uint8_t  f0rc0f_d1;
+	uint8_t  f0rc1x_d1;
+	uint8_t  f0rc2x_d1;
+	uint8_t  f0rc3x_d1;
+	uint8_t  f0rc4x_d1;
+	uint8_t  f0rc5x_d1;
+	uint8_t  f0rc6x_d1;
+	uint8_t  f0rc7x_d1;
+	uint8_t  f0rc8x_d1;
+	uint8_t  f0rc9x_d1;
+	uint8_t  f0rcax_d1;
+	uint8_t  f0rcbx_d1;
+	uint8_t  f1rc00_d1;
+	uint8_t  f1rc01_d1;
+	uint8_t  f1rc02_d1;
+	uint8_t  f1rc03_d1;
+	uint8_t  f1rc04_d1;
+	uint8_t  f1rc05_d1;
+	uint8_t  f1rc06_d1;
+	uint8_t  f1rc07_d1;
+	uint8_t  f1rc08_d1;
+	uint8_t  f1rc09_d1;
+	uint8_t  f1rc0a_d1;
+	uint8_t  f1rc0b_d1;
+	uint8_t  f1rc0c_d1;
+	uint8_t  f1rc0d_d1;
+	uint8_t  f1rc0e_d1;
+	uint8_t  f1rc0f_d1;
+	uint8_t  f1rc1x_d1;
+	uint8_t  f1rc2x_d1;
+	uint8_t  f1rc3x_d1;
+	uint8_t  f1rc4x_d1;
+	uint8_t  f1rc5x_d1;
+	uint8_t  f1rc6x_d1;
+	uint8_t  f1rc7x_d1;
+	uint8_t  f1rc8x_d1;
+	uint8_t  f1rc9x_d1;
+	uint8_t  f1rcax_d1;
+	uint8_t  f1rcbx_d1;
+	uint8_t  reserved142[0x3f6 - 0x142];
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+
+struct ddr4r2d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  rx2d_train_opt;
+	uint8_t  tx2d_train_opt;
+	uint8_t  share2dvref_result;
+	uint8_t  delay_weight2d;
+	uint8_t  voltage_weight2d;
+	uint8_t  reserved1e[0x22-0x1e];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	uint8_t  r0_rx_clk_dly_margin;
+	uint8_t  r0_vref_dac_margin;
+	uint8_t  r0_tx_dq_dly_margin;
+	uint8_t  r0_device_vref_margin;
+	uint8_t  reserved29[0x33-0x29];
+	uint8_t  r1_rx_clk_dly_margin;
+	uint8_t  r1_vref_dac_margin;
+	uint8_t  r1_tx_dq_dly_margin;
+	uint8_t  r1_device_vref_margin;
+	uint8_t  reserved37[0x41-0x37];
+	uint8_t  r2_rx_clk_dly_margin;
+	uint8_t  r2_vref_dac_margin;
+	uint8_t  r2_tx_dq_dly_margin;
+	uint8_t  r2_device_vref_margin;
+	uint8_t  reserved45[0x4f - 0x45];
+	uint8_t  r3_rx_clk_dly_margin;
+	uint8_t  r3_vref_dac_margin;
+	uint8_t  r3_tx_dq_dly_margin;
+	uint8_t  r3_device_vref_margin;
+	uint8_t  reserved53[0x5e - 0x53];
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  f0rc00_d0;
+	uint8_t  f0rc01_d0;
+	uint8_t  f0rc02_d0;
+	uint8_t  f0rc03_d0;
+	uint8_t  f0rc04_d0;
+	uint8_t  f0rc05_d0;
+	uint8_t  f0rc06_d0;
+	uint8_t  f0rc07_d0;
+	uint8_t  f0rc08_d0;
+	uint8_t  f0rc09_d0;
+	uint8_t  f0rc0a_d0;
+	uint8_t  f0rc0b_d0;
+	uint8_t  f0rc0c_d0;
+	uint8_t  f0rc0d_d0;
+	uint8_t  f0rc0e_d0;
+	uint8_t  f0rc0f_d0;
+	uint8_t  f0rc1x_d0;
+	uint8_t  f0rc2x_d0;
+	uint8_t  f0rc3x_d0;
+	uint8_t  f0rc4x_d0;
+	uint8_t  f0rc5x_d0;
+	uint8_t  f0rc6x_d0;
+	uint8_t  f0rc7x_d0;
+	uint8_t  f0rc8x_d0;
+	uint8_t  f0rc9x_d0;
+	uint8_t  f0rcax_d0;
+	uint8_t  f0rcbx_d0;
+	uint8_t  f1rc00_d0;
+	uint8_t  f1rc01_d0;
+	uint8_t  f1rc02_d0;
+	uint8_t  f1rc03_d0;
+	uint8_t  f1rc04_d0;
+	uint8_t  f1rc05_d0;
+	uint8_t  f1rc06_d0;
+	uint8_t  f1rc07_d0;
+	uint8_t  f1rc08_d0;
+	uint8_t  f1rc09_d0;
+	uint8_t  f1rc0a_d0;
+	uint8_t  f1rc0b_d0;
+	uint8_t  f1rc0c_d0;
+	uint8_t  f1rc0d_d0;
+	uint8_t  f1rc0e_d0;
+	uint8_t  f1rc0f_d0;
+	uint8_t  f1rc1x_d0;
+	uint8_t  f1rc2x_d0;
+	uint8_t  f1rc3x_d0;
+	uint8_t  f1rc4x_d0;
+	uint8_t  f1rc5x_d0;
+	uint8_t  f1rc6x_d0;
+	uint8_t  f1rc7x_d0;
+	uint8_t  f1rc8x_d0;
+	uint8_t  f1rc9x_d0;
+	uint8_t  f1rcax_d0;
+	uint8_t  f1rcbx_d0;
+	uint8_t  f0rc00_d1;
+	uint8_t  f0rc01_d1;
+	uint8_t  f0rc02_d1;
+	uint8_t  f0rc03_d1;
+	uint8_t  f0rc04_d1;
+	uint8_t  f0rc05_d1;
+	uint8_t  f0rc06_d1;
+	uint8_t  f0rc07_d1;
+	uint8_t  f0rc08_d1;
+	uint8_t  f0rc09_d1;
+	uint8_t  f0rc0a_d1;
+	uint8_t  f0rc0b_d1;
+	uint8_t  f0rc0c_d1;
+	uint8_t  f0rc0d_d1;
+	uint8_t  f0rc0e_d1;
+	uint8_t  f0rc0f_d1;
+	uint8_t  f0rc1x_d1;
+	uint8_t  f0rc2x_d1;
+	uint8_t  f0rc3x_d1;
+	uint8_t  f0rc4x_d1;
+	uint8_t  f0rc5x_d1;
+	uint8_t  f0rc6x_d1;
+	uint8_t  f0rc7x_d1;
+	uint8_t  f0rc8x_d1;
+	uint8_t  f0rc9x_d1;
+	uint8_t  f0rcax_d1;
+	uint8_t  f0rcbx_d1;
+	uint8_t  f1rc00_d1;
+	uint8_t  f1rc01_d1;
+	uint8_t  f1rc02_d1;
+	uint8_t  f1rc03_d1;
+	uint8_t  f1rc04_d1;
+	uint8_t  f1rc05_d1;
+	uint8_t  f1rc06_d1;
+	uint8_t  f1rc07_d1;
+	uint8_t  f1rc08_d1;
+	uint8_t  f1rc09_d1;
+	uint8_t  f1rc0a_d1;
+	uint8_t  f1rc0b_d1;
+	uint8_t  f1rc0c_d1;
+	uint8_t  f1rc0d_d1;
+	uint8_t  f1rc0e_d1;
+	uint8_t  f1rc0f_d1;
+	uint8_t  f1rc1x_d1;
+	uint8_t  f1rc2x_d1;
+	uint8_t  f1rc3x_d1;
+	uint8_t  f1rc4x_d1;
+	uint8_t  f1rc5x_d1;
+	uint8_t  f1rc6x_d1;
+	uint8_t  f1rc7x_d1;
+	uint8_t  f1rc8x_d1;
+	uint8_t  f1rc9x_d1;
+	uint8_t  f1rcax_d1;
+	uint8_t  f1rcbx_d1;
+	uint8_t  reserved142[0x3f6 - 0x142];
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+
+struct ddr4lr1d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  reserved19[0x22 - 0x19];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	int8_t   cdd_rr_3_2;
+	int8_t   cdd_rr_3_1;
+	int8_t   cdd_rr_3_0;
+	int8_t   cdd_rr_2_3;
+	int8_t   cdd_rr_2_1;
+	int8_t   cdd_rr_2_0;
+	int8_t   cdd_rr_1_3;
+	int8_t   cdd_rr_1_2;
+	int8_t   cdd_rr_1_0;
+	int8_t   cdd_rr_0_3;
+	int8_t   cdd_rr_0_2;
+	int8_t   cdd_rr_0_1;
+	int8_t   cdd_ww_3_2;
+	int8_t   cdd_ww_3_1;
+	int8_t   cdd_ww_3_0;
+	int8_t   cdd_ww_2_3;
+	int8_t   cdd_ww_2_1;
+	int8_t   cdd_ww_2_0;
+	int8_t   cdd_ww_1_3;
+	int8_t   cdd_ww_1_2;
+	int8_t   cdd_ww_1_0;
+	int8_t   cdd_ww_0_3;
+	int8_t   cdd_ww_0_2;
+	int8_t   cdd_ww_0_1;
+	int8_t   cdd_rw_3_3;
+	int8_t   cdd_rw_3_2;
+	int8_t   cdd_rw_3_1;
+	int8_t   cdd_rw_3_0;
+	int8_t   cdd_rw_2_3;
+	int8_t   cdd_rw_2_2;
+	int8_t   cdd_rw_2_1;
+	int8_t   cdd_rw_2_0;
+	int8_t   cdd_rw_1_3;
+	int8_t   cdd_rw_1_2;
+	int8_t   cdd_rw_1_1;
+	int8_t   cdd_rw_1_0;
+	int8_t   cdd_rw_0_3;
+	int8_t   cdd_rw_0_2;
+	int8_t   cdd_rw_0_1;
+	int8_t   cdd_rw_0_0;
+	int8_t   cdd_wr_3_3;
+	int8_t   cdd_wr_3_2;
+	int8_t   cdd_wr_3_1;
+	int8_t   cdd_wr_3_0;
+	int8_t   cdd_wr_2_3;
+	int8_t   cdd_wr_2_2;
+	int8_t   cdd_wr_2_1;
+	int8_t   cdd_wr_2_0;
+	int8_t   cdd_wr_1_3;
+	int8_t   cdd_wr_1_2;
+	int8_t   cdd_wr_1_1;
+	int8_t   cdd_wr_1_0;
+	int8_t   cdd_wr_0_3;
+	int8_t   cdd_wr_0_2;
+	int8_t   cdd_wr_0_1;
+	int8_t   cdd_wr_0_0;
+	uint8_t  reserved5d;
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  f0rc00_d0;
+	uint8_t  f0rc01_d0;
+	uint8_t  f0rc02_d0;
+	uint8_t  f0rc03_d0;
+	uint8_t  f0rc04_d0;
+	uint8_t  f0rc05_d0;
+	uint8_t  f0rc06_d0;
+	uint8_t  f0rc07_d0;
+	uint8_t  f0rc08_d0;
+	uint8_t  f0rc09_d0;
+	uint8_t  f0rc0a_d0;
+	uint8_t  f0rc0b_d0;
+	uint8_t  f0rc0c_d0;
+	uint8_t  f0rc0d_d0;
+	uint8_t  f0rc0e_d0;
+	uint8_t  f0rc0f_d0;
+	uint8_t  f0rc1x_d0;
+	uint8_t  f0rc2x_d0;
+	uint8_t  f0rc3x_d0;
+	uint8_t  f0rc4x_d0;
+	uint8_t  f0rc5x_d0;
+	uint8_t  f0rc6x_d0;
+	uint8_t  f0rc7x_d0;
+	uint8_t  f0rc8x_d0;
+	uint8_t  f0rc9x_d0;
+	uint8_t  f0rcax_d0;
+	uint8_t  f0rcbx_d0;
+	uint8_t  f1rc00_d0;
+	uint8_t  f1rc01_d0;
+	uint8_t  f1rc02_d0;
+	uint8_t  f1rc03_d0;
+	uint8_t  f1rc04_d0;
+	uint8_t  f1rc05_d0;
+	uint8_t  f1rc06_d0;
+	uint8_t  f1rc07_d0;
+	uint8_t  f1rc08_d0;
+	uint8_t  f1rc09_d0;
+	uint8_t  f1rc0a_d0;
+	uint8_t  f1rc0b_d0;
+	uint8_t  f1rc0c_d0;
+	uint8_t  f1rc0d_d0;
+	uint8_t  f1rc0e_d0;
+	uint8_t  f1rc0f_d0;
+	uint8_t  f1rc1x_d0;
+	uint8_t  f1rc2x_d0;
+	uint8_t  f1rc3x_d0;
+	uint8_t  f1rc4x_d0;
+	uint8_t  f1rc5x_d0;
+	uint8_t  f1rc6x_d0;
+	uint8_t  f1rc7x_d0;
+	uint8_t  f1rc8x_d0;
+	uint8_t  f1rc9x_d0;
+	uint8_t  f1rcax_d0;
+	uint8_t  f1rcbx_d0;
+	uint8_t  f0rc00_d1;
+	uint8_t  f0rc01_d1;
+	uint8_t  f0rc02_d1;
+	uint8_t  f0rc03_d1;
+	uint8_t  f0rc04_d1;
+	uint8_t  f0rc05_d1;
+	uint8_t  f0rc06_d1;
+	uint8_t  f0rc07_d1;
+	uint8_t  f0rc08_d1;
+	uint8_t  f0rc09_d1;
+	uint8_t  f0rc0a_d1;
+	uint8_t  f0rc0b_d1;
+	uint8_t  f0rc0c_d1;
+	uint8_t  f0rc0d_d1;
+	uint8_t  f0rc0e_d1;
+	uint8_t  f0rc0f_d1;
+	uint8_t  f0rc1x_d1;
+	uint8_t  f0rc2x_d1;
+	uint8_t  f0rc3x_d1;
+	uint8_t  f0rc4x_d1;
+	uint8_t  f0rc5x_d1;
+	uint8_t  f0rc6x_d1;
+	uint8_t  f0rc7x_d1;
+	uint8_t  f0rc8x_d1;
+	uint8_t  f0rc9x_d1;
+	uint8_t  f0rcax_d1;
+	uint8_t  f0rcbx_d1;
+	uint8_t  f1rc00_d1;
+	uint8_t  f1rc01_d1;
+	uint8_t  f1rc02_d1;
+	uint8_t  f1rc03_d1;
+	uint8_t  f1rc04_d1;
+	uint8_t  f1rc05_d1;
+	uint8_t  f1rc06_d1;
+	uint8_t  f1rc07_d1;
+	uint8_t  f1rc08_d1;
+	uint8_t  f1rc09_d1;
+	uint8_t  f1rc0a_d1;
+	uint8_t  f1rc0b_d1;
+	uint8_t  f1rc0c_d1;
+	uint8_t  f1rc0d_d1;
+	uint8_t  f1rc0e_d1;
+	uint8_t  f1rc0f_d1;
+	uint8_t  f1rc1x_d1;
+	uint8_t  f1rc2x_d1;
+	uint8_t  f1rc3x_d1;
+	uint8_t  f1rc4x_d1;
+	uint8_t  f1rc5x_d1;
+	uint8_t  f1rc6x_d1;
+	uint8_t  f1rc7x_d1;
+	uint8_t  f1rc8x_d1;
+	uint8_t  f1rc9x_d1;
+	uint8_t  f1rcax_d1;
+	uint8_t  f1rcbx_d1;
+	uint8_t  bc00_d0;
+	uint8_t  bc01_d0;
+	uint8_t  bc02_d0;
+	uint8_t  bc03_d0;
+	uint8_t  bc04_d0;
+	uint8_t  bc05_d0;
+	uint8_t  bc06_d0;
+	uint8_t  bc07_d0;
+	uint8_t  bc08_d0;
+	uint8_t  bc09_d0;
+	uint8_t  bc0a_d0;
+	uint8_t  bc0b_d0;
+	uint8_t  bc0c_d0;
+	uint8_t  bc0d_d0;
+	uint8_t  bc0e_d0;
+	uint8_t  f0bc6x_d0;
+	uint8_t  f0bccx_d0;
+	uint8_t  f0bcdx_d0;
+	uint8_t  f0bcex_d0;
+	uint8_t  f0bcfx_d0;
+	uint8_t  f1bccx_d0;
+	uint8_t  f1bcdx_d0;
+	uint8_t  f1bcex_d0;
+	uint8_t  f1bcfx_d0;
+	uint8_t  f0bc2x_b0_d0;
+	uint8_t  f0bc3x_b0_d0;
+	uint8_t  f0bc4x_b0_d0;
+	uint8_t  f0bc5x_b0_d0;
+	uint8_t  f0bc8x_b0_d0;
+	uint8_t  f0bc9x_b0_d0;
+	uint8_t  f0bcax_b0_d0;
+	uint8_t  f0bcbx_b0_d0;
+	uint8_t  f1bc2x_b0_d0;
+	uint8_t  f1bc3x_b0_d0;
+	uint8_t  f1bc4x_b0_d0;
+	uint8_t  f1bc5x_b0_d0;
+	uint8_t  f1bc8x_b0_d0;
+	uint8_t  f1bc9x_b0_d0;
+	uint8_t  f1bcax_b0_d0;
+	uint8_t  f1bcbx_b0_d0;
+	uint8_t  f2bc2x_b0_d0;
+	uint8_t  f2bc3x_b0_d0;
+	uint8_t  f2bc4x_b0_d0;
+	uint8_t  f2bc5x_b0_d0;
+	uint8_t  f2bc8x_b0_d0;
+	uint8_t  f2bc9x_b0_d0;
+	uint8_t  f2bcax_b0_d0;
+	uint8_t  f2bcbx_b0_d0;
+	uint8_t  f3bc2x_b0_d0;
+	uint8_t  f3bc3x_b0_d0;
+	uint8_t  f3bc4x_b0_d0;
+	uint8_t  f3bc5x_b0_d0;
+	uint8_t  f3bc8x_b0_d0;
+	uint8_t  f3bc9x_b0_d0;
+	uint8_t  f3bcax_b0_d0;
+	uint8_t  f3bcbx_b0_d0;
+	uint8_t  f0bc2x_b1_d0;
+	uint8_t  f0bc3x_b1_d0;
+	uint8_t  f0bc4x_b1_d0;
+	uint8_t  f0bc5x_b1_d0;
+	uint8_t  f0bc8x_b1_d0;
+	uint8_t  f0bc9x_b1_d0;
+	uint8_t  f0bcax_b1_d0;
+	uint8_t  f0bcbx_b1_d0;
+	uint8_t  f1bc2x_b1_d0;
+	uint8_t  f1bc3x_b1_d0;
+	uint8_t  f1bc4x_b1_d0;
+	uint8_t  f1bc5x_b1_d0;
+	uint8_t  f1bc8x_b1_d0;
+	uint8_t  f1bc9x_b1_d0;
+	uint8_t  f1bcax_b1_d0;
+	uint8_t  f1bcbx_b1_d0;
+	uint8_t  f2bc2x_b1_d0;
+	uint8_t  f2bc3x_b1_d0;
+	uint8_t  f2bc4x_b1_d0;
+	uint8_t  f2bc5x_b1_d0;
+	uint8_t  f2bc8x_b1_d0;
+	uint8_t  f2bc9x_b1_d0;
+	uint8_t  f2bcax_b1_d0;
+	uint8_t  f2bcbx_b1_d0;
+	uint8_t  f3bc2x_b1_d0;
+	uint8_t  f3bc3x_b1_d0;
+	uint8_t  f3bc4x_b1_d0;
+	uint8_t  f3bc5x_b1_d0;
+	uint8_t  f3bc8x_b1_d0;
+	uint8_t  f3bc9x_b1_d0;
+	uint8_t  f3bcax_b1_d0;
+	uint8_t  f3bcbx_b1_d0;
+	uint8_t  f0bc2x_b2_d0;
+	uint8_t  f0bc3x_b2_d0;
+	uint8_t  f0bc4x_b2_d0;
+	uint8_t  f0bc5x_b2_d0;
+	uint8_t  f0bc8x_b2_d0;
+	uint8_t  f0bc9x_b2_d0;
+	uint8_t  f0bcax_b2_d0;
+	uint8_t  f0bcbx_b2_d0;
+	uint8_t  f1bc2x_b2_d0;
+	uint8_t  f1bc3x_b2_d0;
+	uint8_t  f1bc4x_b2_d0;
+	uint8_t  f1bc5x_b2_d0;
+	uint8_t  f1bc8x_b2_d0;
+	uint8_t  f1bc9x_b2_d0;
+	uint8_t  f1bcax_b2_d0;
+	uint8_t  f1bcbx_b2_d0;
+	uint8_t  f2bc2x_b2_d0;
+	uint8_t  f2bc3x_b2_d0;
+	uint8_t  f2bc4x_b2_d0;
+	uint8_t  f2bc5x_b2_d0;
+	uint8_t  f2bc8x_b2_d0;
+	uint8_t  f2bc9x_b2_d0;
+	uint8_t  f2bcax_b2_d0;
+	uint8_t  f2bcbx_b2_d0;
+	uint8_t  f3bc2x_b2_d0;
+	uint8_t  f3bc3x_b2_d0;
+	uint8_t  f3bc4x_b2_d0;
+	uint8_t  f3bc5x_b2_d0;
+	uint8_t  f3bc8x_b2_d0;
+	uint8_t  f3bc9x_b2_d0;
+	uint8_t  f3bcax_b2_d0;
+	uint8_t  f3bcbx_b2_d0;
+	uint8_t  f0bc2x_b3_d0;
+	uint8_t  f0bc3x_b3_d0;
+	uint8_t  f0bc4x_b3_d0;
+	uint8_t  f0bc5x_b3_d0;
+	uint8_t  f0bc8x_b3_d0;
+	uint8_t  f0bc9x_b3_d0;
+	uint8_t  f0bcax_b3_d0;
+	uint8_t  f0bcbx_b3_d0;
+	uint8_t  f1bc2x_b3_d0;
+	uint8_t  f1bc3x_b3_d0;
+	uint8_t  f1bc4x_b3_d0;
+	uint8_t  f1bc5x_b3_d0;
+	uint8_t  f1bc8x_b3_d0;
+	uint8_t  f1bc9x_b3_d0;
+	uint8_t  f1bcax_b3_d0;
+	uint8_t  f1bcbx_b3_d0;
+	uint8_t  f2bc2x_b3_d0;
+	uint8_t  f2bc3x_b3_d0;
+	uint8_t  f2bc4x_b3_d0;
+	uint8_t  f2bc5x_b3_d0;
+	uint8_t  f2bc8x_b3_d0;
+	uint8_t  f2bc9x_b3_d0;
+	uint8_t  f2bcax_b3_d0;
+	uint8_t  f2bcbx_b3_d0;
+	uint8_t  f3bc2x_b3_d0;
+	uint8_t  f3bc3x_b3_d0;
+	uint8_t  f3bc4x_b3_d0;
+	uint8_t  f3bc5x_b3_d0;
+	uint8_t  f3bc8x_b3_d0;
+	uint8_t  f3bc9x_b3_d0;
+	uint8_t  f3bcax_b3_d0;
+	uint8_t  f3bcbx_b3_d0;
+	uint8_t  f0bc2x_b4_d0;
+	uint8_t  f0bc3x_b4_d0;
+	uint8_t  f0bc4x_b4_d0;
+	uint8_t  f0bc5x_b4_d0;
+	uint8_t  f0bc8x_b4_d0;
+	uint8_t  f0bc9x_b4_d0;
+	uint8_t  f0bcax_b4_d0;
+	uint8_t  f0bcbx_b4_d0;
+	uint8_t  f1bc2x_b4_d0;
+	uint8_t  f1bc3x_b4_d0;
+	uint8_t  f1bc4x_b4_d0;
+	uint8_t  f1bc5x_b4_d0;
+	uint8_t  f1bc8x_b4_d0;
+	uint8_t  f1bc9x_b4_d0;
+	uint8_t  f1bcax_b4_d0;
+	uint8_t  f1bcbx_b4_d0;
+	uint8_t  f2bc2x_b4_d0;
+	uint8_t  f2bc3x_b4_d0;
+	uint8_t  f2bc4x_b4_d0;
+	uint8_t  f2bc5x_b4_d0;
+	uint8_t  f2bc8x_b4_d0;
+	uint8_t  f2bc9x_b4_d0;
+	uint8_t  f2bcax_b4_d0;
+	uint8_t  f2bcbx_b4_d0;
+	uint8_t  f3bc2x_b4_d0;
+	uint8_t  f3bc3x_b4_d0;
+	uint8_t  f3bc4x_b4_d0;
+	uint8_t  f3bc5x_b4_d0;
+	uint8_t  f3bc8x_b4_d0;
+	uint8_t  f3bc9x_b4_d0;
+	uint8_t  f3bcax_b4_d0;
+	uint8_t  f3bcbx_b4_d0;
+	uint8_t  f0bc2x_b5_d0;
+	uint8_t  f0bc3x_b5_d0;
+	uint8_t  f0bc4x_b5_d0;
+	uint8_t  f0bc5x_b5_d0;
+	uint8_t  f0bc8x_b5_d0;
+	uint8_t  f0bc9x_b5_d0;
+	uint8_t  f0bcax_b5_d0;
+	uint8_t  f0bcbx_b5_d0;
+	uint8_t  f1bc2x_b5_d0;
+	uint8_t  f1bc3x_b5_d0;
+	uint8_t  f1bc4x_b5_d0;
+	uint8_t  f1bc5x_b5_d0;
+	uint8_t  f1bc8x_b5_d0;
+	uint8_t  f1bc9x_b5_d0;
+	uint8_t  f1bcax_b5_d0;
+	uint8_t  f1bcbx_b5_d0;
+	uint8_t  f2bc2x_b5_d0;
+	uint8_t  f2bc3x_b5_d0;
+	uint8_t  f2bc4x_b5_d0;
+	uint8_t  f2bc5x_b5_d0;
+	uint8_t  f2bc8x_b5_d0;
+	uint8_t  f2bc9x_b5_d0;
+	uint8_t  f2bcax_b5_d0;
+	uint8_t  f2bcbx_b5_d0;
+	uint8_t  f3bc2x_b5_d0;
+	uint8_t  f3bc3x_b5_d0;
+	uint8_t  f3bc4x_b5_d0;
+	uint8_t  f3bc5x_b5_d0;
+	uint8_t  f3bc8x_b5_d0;
+	uint8_t  f3bc9x_b5_d0;
+	uint8_t  f3bcax_b5_d0;
+	uint8_t  f3bcbx_b5_d0;
+	uint8_t  f0bc2x_b6_d0;
+	uint8_t  f0bc3x_b6_d0;
+	uint8_t  f0bc4x_b6_d0;
+	uint8_t  f0bc5x_b6_d0;
+	uint8_t  f0bc8x_b6_d0;
+	uint8_t  f0bc9x_b6_d0;
+	uint8_t  f0bcax_b6_d0;
+	uint8_t  f0bcbx_b6_d0;
+	uint8_t  f1bc2x_b6_d0;
+	uint8_t  f1bc3x_b6_d0;
+	uint8_t  f1bc4x_b6_d0;
+	uint8_t  f1bc5x_b6_d0;
+	uint8_t  f1bc8x_b6_d0;
+	uint8_t  f1bc9x_b6_d0;
+	uint8_t  f1bcax_b6_d0;
+	uint8_t  f1bcbx_b6_d0;
+	uint8_t  f2bc2x_b6_d0;
+	uint8_t  f2bc3x_b6_d0;
+	uint8_t  f2bc4x_b6_d0;
+	uint8_t  f2bc5x_b6_d0;
+	uint8_t  f2bc8x_b6_d0;
+	uint8_t  f2bc9x_b6_d0;
+	uint8_t  f2bcax_b6_d0;
+	uint8_t  f2bcbx_b6_d0;
+	uint8_t  f3bc2x_b6_d0;
+	uint8_t  f3bc3x_b6_d0;
+	uint8_t  f3bc4x_b6_d0;
+	uint8_t  f3bc5x_b6_d0;
+	uint8_t  f3bc8x_b6_d0;
+	uint8_t  f3bc9x_b6_d0;
+	uint8_t  f3bcax_b6_d0;
+	uint8_t  f3bcbx_b6_d0;
+	uint8_t  f0bc2x_b7_d0;
+	uint8_t  f0bc3x_b7_d0;
+	uint8_t  f0bc4x_b7_d0;
+	uint8_t  f0bc5x_b7_d0;
+	uint8_t  f0bc8x_b7_d0;
+	uint8_t  f0bc9x_b7_d0;
+	uint8_t  f0bcax_b7_d0;
+	uint8_t  f0bcbx_b7_d0;
+	uint8_t  f1bc2x_b7_d0;
+	uint8_t  f1bc3x_b7_d0;
+	uint8_t  f1bc4x_b7_d0;
+	uint8_t  f1bc5x_b7_d0;
+	uint8_t  f1bc8x_b7_d0;
+	uint8_t  f1bc9x_b7_d0;
+	uint8_t  f1bcax_b7_d0;
+	uint8_t  f1bcbx_b7_d0;
+	uint8_t  f2bc2x_b7_d0;
+	uint8_t  f2bc3x_b7_d0;
+	uint8_t  f2bc4x_b7_d0;
+	uint8_t  f2bc5x_b7_d0;
+	uint8_t  f2bc8x_b7_d0;
+	uint8_t  f2bc9x_b7_d0;
+	uint8_t  f2bcax_b7_d0;
+	uint8_t  f2bcbx_b7_d0;
+	uint8_t  f3bc2x_b7_d0;
+	uint8_t  f3bc3x_b7_d0;
+	uint8_t  f3bc4x_b7_d0;
+	uint8_t  f3bc5x_b7_d0;
+	uint8_t  f3bc8x_b7_d0;
+	uint8_t  f3bc9x_b7_d0;
+	uint8_t  f3bcax_b7_d0;
+	uint8_t  f3bcbx_b7_d0;
+	uint8_t  f0bc2x_b8_d0;
+	uint8_t  f0bc3x_b8_d0;
+	uint8_t  f0bc4x_b8_d0;
+	uint8_t  f0bc5x_b8_d0;
+	uint8_t  f0bc8x_b8_d0;
+	uint8_t  f0bc9x_b8_d0;
+	uint8_t  f0bcax_b8_d0;
+	uint8_t  f0bcbx_b8_d0;
+	uint8_t  f1bc2x_b8_d0;
+	uint8_t  f1bc3x_b8_d0;
+	uint8_t  f1bc4x_b8_d0;
+	uint8_t  f1bc5x_b8_d0;
+	uint8_t  f1bc8x_b8_d0;
+	uint8_t  f1bc9x_b8_d0;
+	uint8_t  f1bcax_b8_d0;
+	uint8_t  f1bcbx_b8_d0;
+	uint8_t  f2bc2x_b8_d0;
+	uint8_t  f2bc3x_b8_d0;
+	uint8_t  f2bc4x_b8_d0;
+	uint8_t  f2bc5x_b8_d0;
+	uint8_t  f2bc8x_b8_d0;
+	uint8_t  f2bc9x_b8_d0;
+	uint8_t  f2bcax_b8_d0;
+	uint8_t  f2bcbx_b8_d0;
+	uint8_t  f3bc2x_b8_d0;
+	uint8_t  f3bc3x_b8_d0;
+	uint8_t  f3bc4x_b8_d0;
+	uint8_t  f3bc5x_b8_d0;
+	uint8_t  f3bc8x_b8_d0;
+	uint8_t  f3bc9x_b8_d0;
+	uint8_t  f3bcax_b8_d0;
+	uint8_t  f3bcbx_b8_d0;
+	uint8_t  f5bc5x_d0;
+	uint8_t  f5bc6x_d0;
+	uint8_t  f4bc8x_d0;
+	uint8_t  f4bc9x_d0;
+	uint8_t  f4bcax_d0;
+	uint8_t  f4bcbx_d0;
+	uint8_t  f4bccx_d0;
+	uint8_t  f4bcdx_d0;
+	uint8_t  f4bcex_d0;
+	uint8_t  f4bcfx_d0;
+	uint8_t  f5bc8x_d0;
+	uint8_t  f5bc9x_d0;
+	uint8_t  f5bcax_d0;
+	uint8_t  f5bcbx_d0;
+	uint8_t  f5bccx_d0;
+	uint8_t  f5bcdx_d0;
+	uint8_t  f5bcex_d0;
+	uint8_t  f5bcfx_d0;
+	uint8_t  f6bc8x_d0;
+	uint8_t  f6bc9x_d0;
+	uint8_t  f6bcax_d0;
+	uint8_t  f6bcbx_d0;
+	uint8_t  f6bccx_d0;
+	uint8_t  f6bcdx_d0;
+	uint8_t  f6bcex_d0;
+	uint8_t  f6bcfx_d0;
+	uint8_t  f7bc8x_d0;
+	uint8_t  f7bc9x_d0;
+	uint8_t  f7bcax_d0;
+	uint8_t  f7bcbx_d0;
+	uint8_t  f7bccx_d0;
+	uint8_t  f7bcdx_d0;
+	uint8_t  f7bcex_d0;
+	uint8_t  f7bcfx_d0;
+	uint8_t  bc00_d1;
+	uint8_t  bc01_d1;
+	uint8_t  bc02_d1;
+	uint8_t  bc03_d1;
+	uint8_t  bc04_d1;
+	uint8_t  bc05_d1;
+	uint8_t  bc06_d1;
+	uint8_t  bc07_d1;
+	uint8_t  bc08_d1;
+	uint8_t  bc09_d1;
+	uint8_t  bc0a_d1;
+	uint8_t  bc0b_d1;
+	uint8_t  bc0c_d1;
+	uint8_t  bc0d_d1;
+	uint8_t  bc0e_d1;
+	uint8_t  f0bc6x_d1;
+	uint8_t  f0bccx_d1;
+	uint8_t  f0bcdx_d1;
+	uint8_t  f0bcex_d1;
+	uint8_t  f0bcfx_d1;
+	uint8_t  f1bccx_d1;
+	uint8_t  f1bcdx_d1;
+	uint8_t  f1bcex_d1;
+	uint8_t  f1bcfx_d1;
+	uint8_t  f0bc2x_b0_d1;
+	uint8_t  f0bc3x_b0_d1;
+	uint8_t  f0bc4x_b0_d1;
+	uint8_t  f0bc5x_b0_d1;
+	uint8_t  f0bc8x_b0_d1;
+	uint8_t  f0bc9x_b0_d1;
+	uint8_t  f0bcax_b0_d1;
+	uint8_t  f0bcbx_b0_d1;
+	uint8_t  f1bc2x_b0_d1;
+	uint8_t  f1bc3x_b0_d1;
+	uint8_t  f1bc4x_b0_d1;
+	uint8_t  f1bc5x_b0_d1;
+	uint8_t  f1bc8x_b0_d1;
+	uint8_t  f1bc9x_b0_d1;
+	uint8_t  f1bcax_b0_d1;
+	uint8_t  f1bcbx_b0_d1;
+	uint8_t  f2bc2x_b0_d1;
+	uint8_t  f2bc3x_b0_d1;
+	uint8_t  f2bc4x_b0_d1;
+	uint8_t  f2bc5x_b0_d1;
+	uint8_t  f2bc8x_b0_d1;
+	uint8_t  f2bc9x_b0_d1;
+	uint8_t  f2bcax_b0_d1;
+	uint8_t  f2bcbx_b0_d1;
+	uint8_t  f3bc2x_b0_d1;
+	uint8_t  f3bc3x_b0_d1;
+	uint8_t  f3bc4x_b0_d1;
+	uint8_t  f3bc5x_b0_d1;
+	uint8_t  f3bc8x_b0_d1;
+	uint8_t  f3bc9x_b0_d1;
+	uint8_t  f3bcax_b0_d1;
+	uint8_t  f3bcbx_b0_d1;
+	uint8_t  f0bc2x_b1_d1;
+	uint8_t  f0bc3x_b1_d1;
+	uint8_t  f0bc4x_b1_d1;
+	uint8_t  f0bc5x_b1_d1;
+	uint8_t  f0bc8x_b1_d1;
+	uint8_t  f0bc9x_b1_d1;
+	uint8_t  f0bcax_b1_d1;
+	uint8_t  f0bcbx_b1_d1;
+	uint8_t  f1bc2x_b1_d1;
+	uint8_t  f1bc3x_b1_d1;
+	uint8_t  f1bc4x_b1_d1;
+	uint8_t  f1bc5x_b1_d1;
+	uint8_t  f1bc8x_b1_d1;
+	uint8_t  f1bc9x_b1_d1;
+	uint8_t  f1bcax_b1_d1;
+	uint8_t  f1bcbx_b1_d1;
+	uint8_t  f2bc2x_b1_d1;
+	uint8_t  f2bc3x_b1_d1;
+	uint8_t  f2bc4x_b1_d1;
+	uint8_t  f2bc5x_b1_d1;
+	uint8_t  f2bc8x_b1_d1;
+	uint8_t  f2bc9x_b1_d1;
+	uint8_t  f2bcax_b1_d1;
+	uint8_t  f2bcbx_b1_d1;
+	uint8_t  f3bc2x_b1_d1;
+	uint8_t  f3bc3x_b1_d1;
+	uint8_t  f3bc4x_b1_d1;
+	uint8_t  f3bc5x_b1_d1;
+	uint8_t  f3bc8x_b1_d1;
+	uint8_t  f3bc9x_b1_d1;
+	uint8_t  f3bcax_b1_d1;
+	uint8_t  f3bcbx_b1_d1;
+	uint8_t  f0bc2x_b2_d1;
+	uint8_t  f0bc3x_b2_d1;
+	uint8_t  f0bc4x_b2_d1;
+	uint8_t  f0bc5x_b2_d1;
+	uint8_t  f0bc8x_b2_d1;
+	uint8_t  f0bc9x_b2_d1;
+	uint8_t  f0bcax_b2_d1;
+	uint8_t  f0bcbx_b2_d1;
+	uint8_t  f1bc2x_b2_d1;
+	uint8_t  f1bc3x_b2_d1;
+	uint8_t  f1bc4x_b2_d1;
+	uint8_t  f1bc5x_b2_d1;
+	uint8_t  f1bc8x_b2_d1;
+	uint8_t  f1bc9x_b2_d1;
+	uint8_t  f1bcax_b2_d1;
+	uint8_t  f1bcbx_b2_d1;
+	uint8_t  f2bc2x_b2_d1;
+	uint8_t  f2bc3x_b2_d1;
+	uint8_t  f2bc4x_b2_d1;
+	uint8_t  f2bc5x_b2_d1;
+	uint8_t  f2bc8x_b2_d1;
+	uint8_t  f2bc9x_b2_d1;
+	uint8_t  f2bcax_b2_d1;
+	uint8_t  f2bcbx_b2_d1;
+	uint8_t  f3bc2x_b2_d1;
+	uint8_t  f3bc3x_b2_d1;
+	uint8_t  f3bc4x_b2_d1;
+	uint8_t  f3bc5x_b2_d1;
+	uint8_t  f3bc8x_b2_d1;
+	uint8_t  f3bc9x_b2_d1;
+	uint8_t  f3bcax_b2_d1;
+	uint8_t  f3bcbx_b2_d1;
+	uint8_t  f0bc2x_b3_d1;
+	uint8_t  f0bc3x_b3_d1;
+	uint8_t  f0bc4x_b3_d1;
+	uint8_t  f0bc5x_b3_d1;
+	uint8_t  f0bc8x_b3_d1;
+	uint8_t  f0bc9x_b3_d1;
+	uint8_t  f0bcax_b3_d1;
+	uint8_t  f0bcbx_b3_d1;
+	uint8_t  f1bc2x_b3_d1;
+	uint8_t  f1bc3x_b3_d1;
+	uint8_t  f1bc4x_b3_d1;
+	uint8_t  f1bc5x_b3_d1;
+	uint8_t  f1bc8x_b3_d1;
+	uint8_t  f1bc9x_b3_d1;
+	uint8_t  f1bcax_b3_d1;
+	uint8_t  f1bcbx_b3_d1;
+	uint8_t  f2bc2x_b3_d1;
+	uint8_t  f2bc3x_b3_d1;
+	uint8_t  f2bc4x_b3_d1;
+	uint8_t  f2bc5x_b3_d1;
+	uint8_t  f2bc8x_b3_d1;
+	uint8_t  f2bc9x_b3_d1;
+	uint8_t  f2bcax_b3_d1;
+	uint8_t  f2bcbx_b3_d1;
+	uint8_t  f3bc2x_b3_d1;
+	uint8_t  f3bc3x_b3_d1;
+	uint8_t  f3bc4x_b3_d1;
+	uint8_t  f3bc5x_b3_d1;
+	uint8_t  f3bc8x_b3_d1;
+	uint8_t  f3bc9x_b3_d1;
+	uint8_t  f3bcax_b3_d1;
+	uint8_t  f3bcbx_b3_d1;
+	uint8_t  f0bc2x_b4_d1;
+	uint8_t  f0bc3x_b4_d1;
+	uint8_t  f0bc4x_b4_d1;
+	uint8_t  f0bc5x_b4_d1;
+	uint8_t  f0bc8x_b4_d1;
+	uint8_t  f0bc9x_b4_d1;
+	uint8_t  f0bcax_b4_d1;
+	uint8_t  f0bcbx_b4_d1;
+	uint8_t  f1bc2x_b4_d1;
+	uint8_t  f1bc3x_b4_d1;
+	uint8_t  f1bc4x_b4_d1;
+	uint8_t  f1bc5x_b4_d1;
+	uint8_t  f1bc8x_b4_d1;
+	uint8_t  f1bc9x_b4_d1;
+	uint8_t  f1bcax_b4_d1;
+	uint8_t  f1bcbx_b4_d1;
+	uint8_t  f2bc2x_b4_d1;
+	uint8_t  f2bc3x_b4_d1;
+	uint8_t  f2bc4x_b4_d1;
+	uint8_t  f2bc5x_b4_d1;
+	uint8_t  f2bc8x_b4_d1;
+	uint8_t  f2bc9x_b4_d1;
+	uint8_t  f2bcax_b4_d1;
+	uint8_t  f2bcbx_b4_d1;
+	uint8_t  f3bc2x_b4_d1;
+	uint8_t  f3bc3x_b4_d1;
+	uint8_t  f3bc4x_b4_d1;
+	uint8_t  f3bc5x_b4_d1;
+	uint8_t  f3bc8x_b4_d1;
+	uint8_t  f3bc9x_b4_d1;
+	uint8_t  f3bcax_b4_d1;
+	uint8_t  f3bcbx_b4_d1;
+	uint8_t  f0bc2x_b5_d1;
+	uint8_t  f0bc3x_b5_d1;
+	uint8_t  f0bc4x_b5_d1;
+	uint8_t  f0bc5x_b5_d1;
+	uint8_t  f0bc8x_b5_d1;
+	uint8_t  f0bc9x_b5_d1;
+	uint8_t  f0bcax_b5_d1;
+	uint8_t  f0bcbx_b5_d1;
+	uint8_t  f1bc2x_b5_d1;
+	uint8_t  f1bc3x_b5_d1;
+	uint8_t  f1bc4x_b5_d1;
+	uint8_t  f1bc5x_b5_d1;
+	uint8_t  f1bc8x_b5_d1;
+	uint8_t  f1bc9x_b5_d1;
+	uint8_t  f1bcax_b5_d1;
+	uint8_t  f1bcbx_b5_d1;
+	uint8_t  f2bc2x_b5_d1;
+	uint8_t  f2bc3x_b5_d1;
+	uint8_t  f2bc4x_b5_d1;
+	uint8_t  f2bc5x_b5_d1;
+	uint8_t  f2bc8x_b5_d1;
+	uint8_t  f2bc9x_b5_d1;
+	uint8_t  f2bcax_b5_d1;
+	uint8_t  f2bcbx_b5_d1;
+	uint8_t  f3bc2x_b5_d1;
+	uint8_t  f3bc3x_b5_d1;
+	uint8_t  f3bc4x_b5_d1;
+	uint8_t  f3bc5x_b5_d1;
+	uint8_t  f3bc8x_b5_d1;
+	uint8_t  f3bc9x_b5_d1;
+	uint8_t  f3bcax_b5_d1;
+	uint8_t  f3bcbx_b5_d1;
+	uint8_t  f0bc2x_b6_d1;
+	uint8_t  f0bc3x_b6_d1;
+	uint8_t  f0bc4x_b6_d1;
+	uint8_t  f0bc5x_b6_d1;
+	uint8_t  f0bc8x_b6_d1;
+	uint8_t  f0bc9x_b6_d1;
+	uint8_t  f0bcax_b6_d1;
+	uint8_t  f0bcbx_b6_d1;
+	uint8_t  f1bc2x_b6_d1;
+	uint8_t  f1bc3x_b6_d1;
+	uint8_t  f1bc4x_b6_d1;
+	uint8_t  f1bc5x_b6_d1;
+	uint8_t  f1bc8x_b6_d1;
+	uint8_t  f1bc9x_b6_d1;
+	uint8_t  f1bcax_b6_d1;
+	uint8_t  f1bcbx_b6_d1;
+	uint8_t  f2bc2x_b6_d1;
+	uint8_t  f2bc3x_b6_d1;
+	uint8_t  f2bc4x_b6_d1;
+	uint8_t  f2bc5x_b6_d1;
+	uint8_t  f2bc8x_b6_d1;
+	uint8_t  f2bc9x_b6_d1;
+	uint8_t  f2bcax_b6_d1;
+	uint8_t  f2bcbx_b6_d1;
+	uint8_t  f3bc2x_b6_d1;
+	uint8_t  f3bc3x_b6_d1;
+	uint8_t  f3bc4x_b6_d1;
+	uint8_t  f3bc5x_b6_d1;
+	uint8_t  f3bc8x_b6_d1;
+	uint8_t  f3bc9x_b6_d1;
+	uint8_t  f3bcax_b6_d1;
+	uint8_t  f3bcbx_b6_d1;
+	uint8_t  f0bc2x_b7_d1;
+	uint8_t  f0bc3x_b7_d1;
+	uint8_t  f0bc4x_b7_d1;
+	uint8_t  f0bc5x_b7_d1;
+	uint8_t  f0bc8x_b7_d1;
+	uint8_t  f0bc9x_b7_d1;
+	uint8_t  f0bcax_b7_d1;
+	uint8_t  f0bcbx_b7_d1;
+	uint8_t  f1bc2x_b7_d1;
+	uint8_t  f1bc3x_b7_d1;
+	uint8_t  f1bc4x_b7_d1;
+	uint8_t  f1bc5x_b7_d1;
+	uint8_t  f1bc8x_b7_d1;
+	uint8_t  f1bc9x_b7_d1;
+	uint8_t  f1bcax_b7_d1;
+	uint8_t  f1bcbx_b7_d1;
+	uint8_t  f2bc2x_b7_d1;
+	uint8_t  f2bc3x_b7_d1;
+	uint8_t  f2bc4x_b7_d1;
+	uint8_t  f2bc5x_b7_d1;
+	uint8_t  f2bc8x_b7_d1;
+	uint8_t  f2bc9x_b7_d1;
+	uint8_t  f2bcax_b7_d1;
+	uint8_t  f2bcbx_b7_d1;
+	uint8_t  f3bc2x_b7_d1;
+	uint8_t  f3bc3x_b7_d1;
+	uint8_t  f3bc4x_b7_d1;
+	uint8_t  f3bc5x_b7_d1;
+	uint8_t  f3bc8x_b7_d1;
+	uint8_t  f3bc9x_b7_d1;
+	uint8_t  f3bcax_b7_d1;
+	uint8_t  f3bcbx_b7_d1;
+	uint8_t  f0bc2x_b8_d1;
+	uint8_t  f0bc3x_b8_d1;
+	uint8_t  f0bc4x_b8_d1;
+	uint8_t  f0bc5x_b8_d1;
+	uint8_t  f0bc8x_b8_d1;
+	uint8_t  f0bc9x_b8_d1;
+	uint8_t  f0bcax_b8_d1;
+	uint8_t  f0bcbx_b8_d1;
+	uint8_t  f1bc2x_b8_d1;
+	uint8_t  f1bc3x_b8_d1;
+	uint8_t  f1bc4x_b8_d1;
+	uint8_t  f1bc5x_b8_d1;
+	uint8_t  f1bc8x_b8_d1;
+	uint8_t  f1bc9x_b8_d1;
+	uint8_t  f1bcax_b8_d1;
+	uint8_t  f1bcbx_b8_d1;
+	uint8_t  f2bc2x_b8_d1;
+	uint8_t  f2bc3x_b8_d1;
+	uint8_t  f2bc4x_b8_d1;
+	uint8_t  f2bc5x_b8_d1;
+	uint8_t  f2bc8x_b8_d1;
+	uint8_t  f2bc9x_b8_d1;
+	uint8_t  f2bcax_b8_d1;
+	uint8_t  f2bcbx_b8_d1;
+	uint8_t  f3bc2x_b8_d1;
+	uint8_t  f3bc3x_b8_d1;
+	uint8_t  f3bc4x_b8_d1;
+	uint8_t  f3bc5x_b8_d1;
+	uint8_t  f3bc8x_b8_d1;
+	uint8_t  f3bc9x_b8_d1;
+	uint8_t  f3bcax_b8_d1;
+	uint8_t  f3bcbx_b8_d1;
+	uint8_t  f5bc5x_d1;
+	uint8_t  f5bc6x_d1;
+	uint8_t  f4bc8x_d1;
+	uint8_t  f4bc9x_d1;
+	uint8_t  f4bcax_d1;
+	uint8_t  f4bcbx_d1;
+	uint8_t  f4bccx_d1;
+	uint8_t  f4bcdx_d1;
+	uint8_t  f4bcex_d1;
+	uint8_t  f4bcfx_d1;
+	uint8_t  f5bc8x_d1;
+	uint8_t  f5bc9x_d1;
+	uint8_t  f5bcax_d1;
+	uint8_t  f5bcbx_d1;
+	uint8_t  f5bccx_d1;
+	uint8_t  f5bcdx_d1;
+	uint8_t  f5bcex_d1;
+	uint8_t  f5bcfx_d1;
+	uint8_t  f6bc8x_d1;
+	uint8_t  f6bc9x_d1;
+	uint8_t  f6bcax_d1;
+	uint8_t  f6bcbx_d1;
+	uint8_t  f6bccx_d1;
+	uint8_t  f6bcdx_d1;
+	uint8_t  f6bcex_d1;
+	uint8_t  f6bcfx_d1;
+	uint8_t  f7bc8x_d1;
+	uint8_t  f7bc9x_d1;
+	uint8_t  f7bcax_d1;
+	uint8_t  f7bcbx_d1;
+	uint8_t  f7bccx_d1;
+	uint8_t  f7bcdx_d1;
+	uint8_t  f7bcex_d1;
+	uint8_t  f7bcfx_d1;
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+
+struct ddr4lr2d {
+	uint8_t  reserved00;
+	uint8_t  msg_misc;
+	uint16_t pmu_revision;
+	uint8_t  pstate;
+	uint8_t  pll_bypass_en;
+	uint16_t dramfreq;
+	uint8_t  dfi_freq_ratio;
+	uint8_t  bpznres_val;
+	uint8_t  phy_odt_impedance;
+	uint8_t  phy_drv_impedance;
+	uint8_t  phy_vref;
+	uint8_t  dram_type;
+	uint8_t  disabled_dbyte;
+	uint8_t  enabled_dqs;
+	uint8_t  cs_present;
+	uint8_t  cs_present_d0;
+	uint8_t  cs_present_d1;
+	uint8_t  addr_mirror;
+	uint8_t  cs_test_fail;
+	uint8_t  phy_cfg;
+	uint16_t sequence_ctrl;
+	uint8_t  hdt_ctrl;
+	uint8_t  rx2d_train_opt;
+	uint8_t  tx2d_train_opt;
+	uint8_t  share2dvref_result;
+	uint8_t  delay_weight2d;
+	uint8_t  voltage_weight2d;
+	uint8_t  reserved1e[0x22 - 0x1e];
+	uint16_t phy_config_override;
+	uint8_t  dfimrlmargin;
+	uint8_t  r0_rx_clk_dly_margin;
+	uint8_t  r0_vref_dac_margin;
+	uint8_t  r0_tx_dq_dly_margin;
+	uint8_t  r0_device_vref_margin;
+	uint8_t  reserved29[0x33 - 0x29];
+	uint8_t  r1_rx_clk_dly_margin;
+	uint8_t  r1_vref_dac_margin;
+	uint8_t  r1_tx_dq_dly_margin;
+	uint8_t  r1_device_vref_margin;
+	uint8_t  reserved37[0x41 - 0x37];
+	uint8_t  r2_rx_clk_dly_margin;
+	uint8_t  r2_vref_dac_margin;
+	uint8_t  r2_tx_dq_dly_margin;
+	uint8_t  r2_device_vref_margin;
+	uint8_t  reserved45[0x4f - 0x45];
+	uint8_t  r3_rx_clk_dly_margin;
+	uint8_t  r3_vref_dac_margin;
+	uint8_t  r3_tx_dq_dly_margin;
+	uint8_t  r3_device_vref_margin;
+	uint8_t  reserved53[0x5e - 0x53];
+	uint16_t mr0;
+	uint16_t mr1;
+	uint16_t mr2;
+	uint16_t mr3;
+	uint16_t mr4;
+	uint16_t mr5;
+	uint16_t mr6;
+	uint8_t  x16present;
+	uint8_t  cs_setup_gddec;
+	uint16_t rtt_nom_wr_park0;
+	uint16_t rtt_nom_wr_park1;
+	uint16_t rtt_nom_wr_park2;
+	uint16_t rtt_nom_wr_park3;
+	uint16_t rtt_nom_wr_park4;
+	uint16_t rtt_nom_wr_park5;
+	uint16_t rtt_nom_wr_park6;
+	uint16_t rtt_nom_wr_park7;
+	uint8_t  acsm_odt_ctrl0;
+	uint8_t  acsm_odt_ctrl1;
+	uint8_t  acsm_odt_ctrl2;
+	uint8_t  acsm_odt_ctrl3;
+	uint8_t  acsm_odt_ctrl4;
+	uint8_t  acsm_odt_ctrl5;
+	uint8_t  acsm_odt_ctrl6;
+	uint8_t  acsm_odt_ctrl7;
+	uint8_t  vref_dq_r0nib0;
+	uint8_t  vref_dq_r0nib1;
+	uint8_t  vref_dq_r0nib2;
+	uint8_t  vref_dq_r0nib3;
+	uint8_t  vref_dq_r0nib4;
+	uint8_t  vref_dq_r0nib5;
+	uint8_t  vref_dq_r0nib6;
+	uint8_t  vref_dq_r0nib7;
+	uint8_t  vref_dq_r0nib8;
+	uint8_t  vref_dq_r0nib9;
+	uint8_t  vref_dq_r0nib10;
+	uint8_t  vref_dq_r0nib11;
+	uint8_t  vref_dq_r0nib12;
+	uint8_t  vref_dq_r0nib13;
+	uint8_t  vref_dq_r0nib14;
+	uint8_t  vref_dq_r0nib15;
+	uint8_t  vref_dq_r0nib16;
+	uint8_t  vref_dq_r0nib17;
+	uint8_t  vref_dq_r0nib18;
+	uint8_t  vref_dq_r0nib19;
+	uint8_t  vref_dq_r1nib0;
+	uint8_t  vref_dq_r1nib1;
+	uint8_t  vref_dq_r1nib2;
+	uint8_t  vref_dq_r1nib3;
+	uint8_t  vref_dq_r1nib4;
+	uint8_t  vref_dq_r1nib5;
+	uint8_t  vref_dq_r1nib6;
+	uint8_t  vref_dq_r1nib7;
+	uint8_t  vref_dq_r1nib8;
+	uint8_t  vref_dq_r1nib9;
+	uint8_t  vref_dq_r1nib10;
+	uint8_t  vref_dq_r1nib11;
+	uint8_t  vref_dq_r1nib12;
+	uint8_t  vref_dq_r1nib13;
+	uint8_t  vref_dq_r1nib14;
+	uint8_t  vref_dq_r1nib15;
+	uint8_t  vref_dq_r1nib16;
+	uint8_t  vref_dq_r1nib17;
+	uint8_t  vref_dq_r1nib18;
+	uint8_t  vref_dq_r1nib19;
+	uint8_t  vref_dq_r2nib0;
+	uint8_t  vref_dq_r2nib1;
+	uint8_t  vref_dq_r2nib2;
+	uint8_t  vref_dq_r2nib3;
+	uint8_t  vref_dq_r2nib4;
+	uint8_t  vref_dq_r2nib5;
+	uint8_t  vref_dq_r2nib6;
+	uint8_t  vref_dq_r2nib7;
+	uint8_t  vref_dq_r2nib8;
+	uint8_t  vref_dq_r2nib9;
+	uint8_t  vref_dq_r2nib10;
+	uint8_t  vref_dq_r2nib11;
+	uint8_t  vref_dq_r2nib12;
+	uint8_t  vref_dq_r2nib13;
+	uint8_t  vref_dq_r2nib14;
+	uint8_t  vref_dq_r2nib15;
+	uint8_t  vref_dq_r2nib16;
+	uint8_t  vref_dq_r2nib17;
+	uint8_t  vref_dq_r2nib18;
+	uint8_t  vref_dq_r2nib19;
+	uint8_t  vref_dq_r3nib0;
+	uint8_t  vref_dq_r3nib1;
+	uint8_t  vref_dq_r3nib2;
+	uint8_t  vref_dq_r3nib3;
+	uint8_t  vref_dq_r3nib4;
+	uint8_t  vref_dq_r3nib5;
+	uint8_t  vref_dq_r3nib6;
+	uint8_t  vref_dq_r3nib7;
+	uint8_t  vref_dq_r3nib8;
+	uint8_t  vref_dq_r3nib9;
+	uint8_t  vref_dq_r3nib10;
+	uint8_t  vref_dq_r3nib11;
+	uint8_t  vref_dq_r3nib12;
+	uint8_t  vref_dq_r3nib13;
+	uint8_t  vref_dq_r3nib14;
+	uint8_t  vref_dq_r3nib15;
+	uint8_t  vref_dq_r3nib16;
+	uint8_t  vref_dq_r3nib17;
+	uint8_t  vref_dq_r3nib18;
+	uint8_t  vref_dq_r3nib19;
+	uint8_t  f0rc00_d0;
+	uint8_t  f0rc01_d0;
+	uint8_t  f0rc02_d0;
+	uint8_t  f0rc03_d0;
+	uint8_t  f0rc04_d0;
+	uint8_t  f0rc05_d0;
+	uint8_t  f0rc06_d0;
+	uint8_t  f0rc07_d0;
+	uint8_t  f0rc08_d0;
+	uint8_t  f0rc09_d0;
+	uint8_t  f0rc0a_d0;
+	uint8_t  f0rc0b_d0;
+	uint8_t  f0rc0c_d0;
+	uint8_t  f0rc0d_d0;
+	uint8_t  f0rc0e_d0;
+	uint8_t  f0rc0f_d0;
+	uint8_t  f0rc1x_d0;
+	uint8_t  f0rc2x_d0;
+	uint8_t  f0rc3x_d0;
+	uint8_t  f0rc4x_d0;
+	uint8_t  f0rc5x_d0;
+	uint8_t  f0rc6x_d0;
+	uint8_t  f0rc7x_d0;
+	uint8_t  f0rc8x_d0;
+	uint8_t  f0rc9x_d0;
+	uint8_t  f0rcax_d0;
+	uint8_t  f0rcbx_d0;
+	uint8_t  f1rc00_d0;
+	uint8_t  f1rc01_d0;
+	uint8_t  f1rc02_d0;
+	uint8_t  f1rc03_d0;
+	uint8_t  f1rc04_d0;
+	uint8_t  f1rc05_d0;
+	uint8_t  f1rc06_d0;
+	uint8_t  f1rc07_d0;
+	uint8_t  f1rc08_d0;
+	uint8_t  f1rc09_d0;
+	uint8_t  f1rc0a_d0;
+	uint8_t  f1rc0b_d0;
+	uint8_t  f1rc0c_d0;
+	uint8_t  f1rc0d_d0;
+	uint8_t  f1rc0e_d0;
+	uint8_t  f1rc0f_d0;
+	uint8_t  f1rc1x_d0;
+	uint8_t  f1rc2x_d0;
+	uint8_t  f1rc3x_d0;
+	uint8_t  f1rc4x_d0;
+	uint8_t  f1rc5x_d0;
+	uint8_t  f1rc6x_d0;
+	uint8_t  f1rc7x_d0;
+	uint8_t  f1rc8x_d0;
+	uint8_t  f1rc9x_d0;
+	uint8_t  f1rcax_d0;
+	uint8_t  f1rcbx_d0;
+	uint8_t  f0rc00_d1;
+	uint8_t  f0rc01_d1;
+	uint8_t  f0rc02_d1;
+	uint8_t  f0rc03_d1;
+	uint8_t  f0rc04_d1;
+	uint8_t  f0rc05_d1;
+	uint8_t  f0rc06_d1;
+	uint8_t  f0rc07_d1;
+	uint8_t  f0rc08_d1;
+	uint8_t  f0rc09_d1;
+	uint8_t  f0rc0a_d1;
+	uint8_t  f0rc0b_d1;
+	uint8_t  f0rc0c_d1;
+	uint8_t  f0rc0d_d1;
+	uint8_t  f0rc0e_d1;
+	uint8_t  f0rc0f_d1;
+	uint8_t  f0rc1x_d1;
+	uint8_t  f0rc2x_d1;
+	uint8_t  f0rc3x_d1;
+	uint8_t  f0rc4x_d1;
+	uint8_t  f0rc5x_d1;
+	uint8_t  f0rc6x_d1;
+	uint8_t  f0rc7x_d1;
+	uint8_t  f0rc8x_d1;
+	uint8_t  f0rc9x_d1;
+	uint8_t  f0rcax_d1;
+	uint8_t  f0rcbx_d1;
+	uint8_t  f1rc00_d1;
+	uint8_t  f1rc01_d1;
+	uint8_t  f1rc02_d1;
+	uint8_t  f1rc03_d1;
+	uint8_t  f1rc04_d1;
+	uint8_t  f1rc05_d1;
+	uint8_t  f1rc06_d1;
+	uint8_t  f1rc07_d1;
+	uint8_t  f1rc08_d1;
+	uint8_t  f1rc09_d1;
+	uint8_t  f1rc0a_d1;
+	uint8_t  f1rc0b_d1;
+	uint8_t  f1rc0c_d1;
+	uint8_t  f1rc0d_d1;
+	uint8_t  f1rc0e_d1;
+	uint8_t  f1rc0f_d1;
+	uint8_t  f1rc1x_d1;
+	uint8_t  f1rc2x_d1;
+	uint8_t  f1rc3x_d1;
+	uint8_t  f1rc4x_d1;
+	uint8_t  f1rc5x_d1;
+	uint8_t  f1rc6x_d1;
+	uint8_t  f1rc7x_d1;
+	uint8_t  f1rc8x_d1;
+	uint8_t  f1rc9x_d1;
+	uint8_t  f1rcax_d1;
+	uint8_t  f1rcbx_d1;
+	uint8_t  bc00_d0;
+	uint8_t  bc01_d0;
+	uint8_t  bc02_d0;
+	uint8_t  bc03_d0;
+	uint8_t  bc04_d0;
+	uint8_t  bc05_d0;
+	uint8_t  bc06_d0;
+	uint8_t  bc07_d0;
+	uint8_t  bc08_d0;
+	uint8_t  bc09_d0;
+	uint8_t  bc0a_d0;
+	uint8_t  bc0b_d0;
+	uint8_t  bc0c_d0;
+	uint8_t  bc0d_d0;
+	uint8_t  bc0e_d0;
+	uint8_t  f0bc6x_d0;
+	uint8_t  f0bccx_d0;
+	uint8_t  f0bcdx_d0;
+	uint8_t  f0bcex_d0;
+	uint8_t  f0bcfx_d0;
+	uint8_t  f1bccx_d0;
+	uint8_t  f1bcdx_d0;
+	uint8_t  f1bcex_d0;
+	uint8_t  f1bcfx_d0;
+	uint8_t  f0bc2x_b0_d0;
+	uint8_t  f0bc3x_b0_d0;
+	uint8_t  f0bc4x_b0_d0;
+	uint8_t  f0bc5x_b0_d0;
+	uint8_t  f0bc8x_b0_d0;
+	uint8_t  f0bc9x_b0_d0;
+	uint8_t  f0bcax_b0_d0;
+	uint8_t  f0bcbx_b0_d0;
+	uint8_t  f1bc2x_b0_d0;
+	uint8_t  f1bc3x_b0_d0;
+	uint8_t  f1bc4x_b0_d0;
+	uint8_t  f1bc5x_b0_d0;
+	uint8_t  f1bc8x_b0_d0;
+	uint8_t  f1bc9x_b0_d0;
+	uint8_t  f1bcax_b0_d0;
+	uint8_t  f1bcbx_b0_d0;
+	uint8_t  f2bc2x_b0_d0;
+	uint8_t  f2bc3x_b0_d0;
+	uint8_t  f2bc4x_b0_d0;
+	uint8_t  f2bc5x_b0_d0;
+	uint8_t  f2bc8x_b0_d0;
+	uint8_t  f2bc9x_b0_d0;
+	uint8_t  f2bcax_b0_d0;
+	uint8_t  f2bcbx_b0_d0;
+	uint8_t  f3bc2x_b0_d0;
+	uint8_t  f3bc3x_b0_d0;
+	uint8_t  f3bc4x_b0_d0;
+	uint8_t  f3bc5x_b0_d0;
+	uint8_t  f3bc8x_b0_d0;
+	uint8_t  f3bc9x_b0_d0;
+	uint8_t  f3bcax_b0_d0;
+	uint8_t  f3bcbx_b0_d0;
+	uint8_t  f0bc2x_b1_d0;
+	uint8_t  f0bc3x_b1_d0;
+	uint8_t  f0bc4x_b1_d0;
+	uint8_t  f0bc5x_b1_d0;
+	uint8_t  f0bc8x_b1_d0;
+	uint8_t  f0bc9x_b1_d0;
+	uint8_t  f0bcax_b1_d0;
+	uint8_t  f0bcbx_b1_d0;
+	uint8_t  f1bc2x_b1_d0;
+	uint8_t  f1bc3x_b1_d0;
+	uint8_t  f1bc4x_b1_d0;
+	uint8_t  f1bc5x_b1_d0;
+	uint8_t  f1bc8x_b1_d0;
+	uint8_t  f1bc9x_b1_d0;
+	uint8_t  f1bcax_b1_d0;
+	uint8_t  f1bcbx_b1_d0;
+	uint8_t  f2bc2x_b1_d0;
+	uint8_t  f2bc3x_b1_d0;
+	uint8_t  f2bc4x_b1_d0;
+	uint8_t  f2bc5x_b1_d0;
+	uint8_t  f2bc8x_b1_d0;
+	uint8_t  f2bc9x_b1_d0;
+	uint8_t  f2bcax_b1_d0;
+	uint8_t  f2bcbx_b1_d0;
+	uint8_t  f3bc2x_b1_d0;
+	uint8_t  f3bc3x_b1_d0;
+	uint8_t  f3bc4x_b1_d0;
+	uint8_t  f3bc5x_b1_d0;
+	uint8_t  f3bc8x_b1_d0;
+	uint8_t  f3bc9x_b1_d0;
+	uint8_t  f3bcax_b1_d0;
+	uint8_t  f3bcbx_b1_d0;
+	uint8_t  f0bc2x_b2_d0;
+	uint8_t  f0bc3x_b2_d0;
+	uint8_t  f0bc4x_b2_d0;
+	uint8_t  f0bc5x_b2_d0;
+	uint8_t  f0bc8x_b2_d0;
+	uint8_t  f0bc9x_b2_d0;
+	uint8_t  f0bcax_b2_d0;
+	uint8_t  f0bcbx_b2_d0;
+	uint8_t  f1bc2x_b2_d0;
+	uint8_t  f1bc3x_b2_d0;
+	uint8_t  f1bc4x_b2_d0;
+	uint8_t  f1bc5x_b2_d0;
+	uint8_t  f1bc8x_b2_d0;
+	uint8_t  f1bc9x_b2_d0;
+	uint8_t  f1bcax_b2_d0;
+	uint8_t  f1bcbx_b2_d0;
+	uint8_t  f2bc2x_b2_d0;
+	uint8_t  f2bc3x_b2_d0;
+	uint8_t  f2bc4x_b2_d0;
+	uint8_t  f2bc5x_b2_d0;
+	uint8_t  f2bc8x_b2_d0;
+	uint8_t  f2bc9x_b2_d0;
+	uint8_t  f2bcax_b2_d0;
+	uint8_t  f2bcbx_b2_d0;
+	uint8_t  f3bc2x_b2_d0;
+	uint8_t  f3bc3x_b2_d0;
+	uint8_t  f3bc4x_b2_d0;
+	uint8_t  f3bc5x_b2_d0;
+	uint8_t  f3bc8x_b2_d0;
+	uint8_t  f3bc9x_b2_d0;
+	uint8_t  f3bcax_b2_d0;
+	uint8_t  f3bcbx_b2_d0;
+	uint8_t  f0bc2x_b3_d0;
+	uint8_t  f0bc3x_b3_d0;
+	uint8_t  f0bc4x_b3_d0;
+	uint8_t  f0bc5x_b3_d0;
+	uint8_t  f0bc8x_b3_d0;
+	uint8_t  f0bc9x_b3_d0;
+	uint8_t  f0bcax_b3_d0;
+	uint8_t  f0bcbx_b3_d0;
+	uint8_t  f1bc2x_b3_d0;
+	uint8_t  f1bc3x_b3_d0;
+	uint8_t  f1bc4x_b3_d0;
+	uint8_t  f1bc5x_b3_d0;
+	uint8_t  f1bc8x_b3_d0;
+	uint8_t  f1bc9x_b3_d0;
+	uint8_t  f1bcax_b3_d0;
+	uint8_t  f1bcbx_b3_d0;
+	uint8_t  f2bc2x_b3_d0;
+	uint8_t  f2bc3x_b3_d0;
+	uint8_t  f2bc4x_b3_d0;
+	uint8_t  f2bc5x_b3_d0;
+	uint8_t  f2bc8x_b3_d0;
+	uint8_t  f2bc9x_b3_d0;
+	uint8_t  f2bcax_b3_d0;
+	uint8_t  f2bcbx_b3_d0;
+	uint8_t  f3bc2x_b3_d0;
+	uint8_t  f3bc3x_b3_d0;
+	uint8_t  f3bc4x_b3_d0;
+	uint8_t  f3bc5x_b3_d0;
+	uint8_t  f3bc8x_b3_d0;
+	uint8_t  f3bc9x_b3_d0;
+	uint8_t  f3bcax_b3_d0;
+	uint8_t  f3bcbx_b3_d0;
+	uint8_t  f0bc2x_b4_d0;
+	uint8_t  f0bc3x_b4_d0;
+	uint8_t  f0bc4x_b4_d0;
+	uint8_t  f0bc5x_b4_d0;
+	uint8_t  f0bc8x_b4_d0;
+	uint8_t  f0bc9x_b4_d0;
+	uint8_t  f0bcax_b4_d0;
+	uint8_t  f0bcbx_b4_d0;
+	uint8_t  f1bc2x_b4_d0;
+	uint8_t  f1bc3x_b4_d0;
+	uint8_t  f1bc4x_b4_d0;
+	uint8_t  f1bc5x_b4_d0;
+	uint8_t  f1bc8x_b4_d0;
+	uint8_t  f1bc9x_b4_d0;
+	uint8_t  f1bcax_b4_d0;
+	uint8_t  f1bcbx_b4_d0;
+	uint8_t  f2bc2x_b4_d0;
+	uint8_t  f2bc3x_b4_d0;
+	uint8_t  f2bc4x_b4_d0;
+	uint8_t  f2bc5x_b4_d0;
+	uint8_t  f2bc8x_b4_d0;
+	uint8_t  f2bc9x_b4_d0;
+	uint8_t  f2bcax_b4_d0;
+	uint8_t  f2bcbx_b4_d0;
+	uint8_t  f3bc2x_b4_d0;
+	uint8_t  f3bc3x_b4_d0;
+	uint8_t  f3bc4x_b4_d0;
+	uint8_t  f3bc5x_b4_d0;
+	uint8_t  f3bc8x_b4_d0;
+	uint8_t  f3bc9x_b4_d0;
+	uint8_t  f3bcax_b4_d0;
+	uint8_t  f3bcbx_b4_d0;
+	uint8_t  f0bc2x_b5_d0;
+	uint8_t  f0bc3x_b5_d0;
+	uint8_t  f0bc4x_b5_d0;
+	uint8_t  f0bc5x_b5_d0;
+	uint8_t  f0bc8x_b5_d0;
+	uint8_t  f0bc9x_b5_d0;
+	uint8_t  f0bcax_b5_d0;
+	uint8_t  f0bcbx_b5_d0;
+	uint8_t  f1bc2x_b5_d0;
+	uint8_t  f1bc3x_b5_d0;
+	uint8_t  f1bc4x_b5_d0;
+	uint8_t  f1bc5x_b5_d0;
+	uint8_t  f1bc8x_b5_d0;
+	uint8_t  f1bc9x_b5_d0;
+	uint8_t  f1bcax_b5_d0;
+	uint8_t  f1bcbx_b5_d0;
+	uint8_t  f2bc2x_b5_d0;
+	uint8_t  f2bc3x_b5_d0;
+	uint8_t  f2bc4x_b5_d0;
+	uint8_t  f2bc5x_b5_d0;
+	uint8_t  f2bc8x_b5_d0;
+	uint8_t  f2bc9x_b5_d0;
+	uint8_t  f2bcax_b5_d0;
+	uint8_t  f2bcbx_b5_d0;
+	uint8_t  f3bc2x_b5_d0;
+	uint8_t  f3bc3x_b5_d0;
+	uint8_t  f3bc4x_b5_d0;
+	uint8_t  f3bc5x_b5_d0;
+	uint8_t  f3bc8x_b5_d0;
+	uint8_t  f3bc9x_b5_d0;
+	uint8_t  f3bcax_b5_d0;
+	uint8_t  f3bcbx_b5_d0;
+	uint8_t  f0bc2x_b6_d0;
+	uint8_t  f0bc3x_b6_d0;
+	uint8_t  f0bc4x_b6_d0;
+	uint8_t  f0bc5x_b6_d0;
+	uint8_t  f0bc8x_b6_d0;
+	uint8_t  f0bc9x_b6_d0;
+	uint8_t  f0bcax_b6_d0;
+	uint8_t  f0bcbx_b6_d0;
+	uint8_t  f1bc2x_b6_d0;
+	uint8_t  f1bc3x_b6_d0;
+	uint8_t  f1bc4x_b6_d0;
+	uint8_t  f1bc5x_b6_d0;
+	uint8_t  f1bc8x_b6_d0;
+	uint8_t  f1bc9x_b6_d0;
+	uint8_t  f1bcax_b6_d0;
+	uint8_t  f1bcbx_b6_d0;
+	uint8_t  f2bc2x_b6_d0;
+	uint8_t  f2bc3x_b6_d0;
+	uint8_t  f2bc4x_b6_d0;
+	uint8_t  f2bc5x_b6_d0;
+	uint8_t  f2bc8x_b6_d0;
+	uint8_t  f2bc9x_b6_d0;
+	uint8_t  f2bcax_b6_d0;
+	uint8_t  f2bcbx_b6_d0;
+	uint8_t  f3bc2x_b6_d0;
+	uint8_t  f3bc3x_b6_d0;
+	uint8_t  f3bc4x_b6_d0;
+	uint8_t  f3bc5x_b6_d0;
+	uint8_t  f3bc8x_b6_d0;
+	uint8_t  f3bc9x_b6_d0;
+	uint8_t  f3bcax_b6_d0;
+	uint8_t  f3bcbx_b6_d0;
+	uint8_t  f0bc2x_b7_d0;
+	uint8_t  f0bc3x_b7_d0;
+	uint8_t  f0bc4x_b7_d0;
+	uint8_t  f0bc5x_b7_d0;
+	uint8_t  f0bc8x_b7_d0;
+	uint8_t  f0bc9x_b7_d0;
+	uint8_t  f0bcax_b7_d0;
+	uint8_t  f0bcbx_b7_d0;
+	uint8_t  f1bc2x_b7_d0;
+	uint8_t  f1bc3x_b7_d0;
+	uint8_t  f1bc4x_b7_d0;
+	uint8_t  f1bc5x_b7_d0;
+	uint8_t  f1bc8x_b7_d0;
+	uint8_t  f1bc9x_b7_d0;
+	uint8_t  f1bcax_b7_d0;
+	uint8_t  f1bcbx_b7_d0;
+	uint8_t  f2bc2x_b7_d0;
+	uint8_t  f2bc3x_b7_d0;
+	uint8_t  f2bc4x_b7_d0;
+	uint8_t  f2bc5x_b7_d0;
+	uint8_t  f2bc8x_b7_d0;
+	uint8_t  f2bc9x_b7_d0;
+	uint8_t  f2bcax_b7_d0;
+	uint8_t  f2bcbx_b7_d0;
+	uint8_t  f3bc2x_b7_d0;
+	uint8_t  f3bc3x_b7_d0;
+	uint8_t  f3bc4x_b7_d0;
+	uint8_t  f3bc5x_b7_d0;
+	uint8_t  f3bc8x_b7_d0;
+	uint8_t  f3bc9x_b7_d0;
+	uint8_t  f3bcax_b7_d0;
+	uint8_t  f3bcbx_b7_d0;
+	uint8_t  f0bc2x_b8_d0;
+	uint8_t  f0bc3x_b8_d0;
+	uint8_t  f0bc4x_b8_d0;
+	uint8_t  f0bc5x_b8_d0;
+	uint8_t  f0bc8x_b8_d0;
+	uint8_t  f0bc9x_b8_d0;
+	uint8_t  f0bcax_b8_d0;
+	uint8_t  f0bcbx_b8_d0;
+	uint8_t  f1bc2x_b8_d0;
+	uint8_t  f1bc3x_b8_d0;
+	uint8_t  f1bc4x_b8_d0;
+	uint8_t  f1bc5x_b8_d0;
+	uint8_t  f1bc8x_b8_d0;
+	uint8_t  f1bc9x_b8_d0;
+	uint8_t  f1bcax_b8_d0;
+	uint8_t  f1bcbx_b8_d0;
+	uint8_t  f2bc2x_b8_d0;
+	uint8_t  f2bc3x_b8_d0;
+	uint8_t  f2bc4x_b8_d0;
+	uint8_t  f2bc5x_b8_d0;
+	uint8_t  f2bc8x_b8_d0;
+	uint8_t  f2bc9x_b8_d0;
+	uint8_t  f2bcax_b8_d0;
+	uint8_t  f2bcbx_b8_d0;
+	uint8_t  f3bc2x_b8_d0;
+	uint8_t  f3bc3x_b8_d0;
+	uint8_t  f3bc4x_b8_d0;
+	uint8_t  f3bc5x_b8_d0;
+	uint8_t  f3bc8x_b8_d0;
+	uint8_t  f3bc9x_b8_d0;
+	uint8_t  f3bcax_b8_d0;
+	uint8_t  f3bcbx_b8_d0;
+	uint8_t  f5bc5x_d0;
+	uint8_t  f5bc6x_d0;
+	uint8_t  f4bc8x_d0;
+	uint8_t  f4bc9x_d0;
+	uint8_t  f4bcax_d0;
+	uint8_t  f4bcbx_d0;
+	uint8_t  f4bccx_d0;
+	uint8_t  f4bcdx_d0;
+	uint8_t  f4bcex_d0;
+	uint8_t  f4bcfx_d0;
+	uint8_t  f5bc8x_d0;
+	uint8_t  f5bc9x_d0;
+	uint8_t  f5bcax_d0;
+	uint8_t  f5bcbx_d0;
+	uint8_t  f5bccx_d0;
+	uint8_t  f5bcdx_d0;
+	uint8_t  f5bcex_d0;
+	uint8_t  f5bcfx_d0;
+	uint8_t  f6bc8x_d0;
+	uint8_t  f6bc9x_d0;
+	uint8_t  f6bcax_d0;
+	uint8_t  f6bcbx_d0;
+	uint8_t  f6bccx_d0;
+	uint8_t  f6bcdx_d0;
+	uint8_t  f6bcex_d0;
+	uint8_t  f6bcfx_d0;
+	uint8_t  f7bc8x_d0;
+	uint8_t  f7bc9x_d0;
+	uint8_t  f7bcax_d0;
+	uint8_t  f7bcbx_d0;
+	uint8_t  f7bccx_d0;
+	uint8_t  f7bcdx_d0;
+	uint8_t  f7bcex_d0;
+	uint8_t  f7bcfx_d0;
+	uint8_t  bc00_d1;
+	uint8_t  bc01_d1;
+	uint8_t  bc02_d1;
+	uint8_t  bc03_d1;
+	uint8_t  bc04_d1;
+	uint8_t  bc05_d1;
+	uint8_t  bc06_d1;
+	uint8_t  bc07_d1;
+	uint8_t  bc08_d1;
+	uint8_t  bc09_d1;
+	uint8_t  bc0a_d1;
+	uint8_t  bc0b_d1;
+	uint8_t  bc0c_d1;
+	uint8_t  bc0d_d1;
+	uint8_t  bc0e_d1;
+	uint8_t  f0bc6x_d1;
+	uint8_t  f0bccx_d1;
+	uint8_t  f0bcdx_d1;
+	uint8_t  f0bcex_d1;
+	uint8_t  f0bcfx_d1;
+	uint8_t  f1bccx_d1;
+	uint8_t  f1bcdx_d1;
+	uint8_t  f1bcex_d1;
+	uint8_t  f1bcfx_d1;
+	uint8_t  f0bc2x_b0_d1;
+	uint8_t  f0bc3x_b0_d1;
+	uint8_t  f0bc4x_b0_d1;
+	uint8_t  f0bc5x_b0_d1;
+	uint8_t  f0bc8x_b0_d1;
+	uint8_t  f0bc9x_b0_d1;
+	uint8_t  f0bcax_b0_d1;
+	uint8_t  f0bcbx_b0_d1;
+	uint8_t  f1bc2x_b0_d1;
+	uint8_t  f1bc3x_b0_d1;
+	uint8_t  f1bc4x_b0_d1;
+	uint8_t  f1bc5x_b0_d1;
+	uint8_t  f1bc8x_b0_d1;
+	uint8_t  f1bc9x_b0_d1;
+	uint8_t  f1bcax_b0_d1;
+	uint8_t  f1bcbx_b0_d1;
+	uint8_t  f2bc2x_b0_d1;
+	uint8_t  f2bc3x_b0_d1;
+	uint8_t  f2bc4x_b0_d1;
+	uint8_t  f2bc5x_b0_d1;
+	uint8_t  f2bc8x_b0_d1;
+	uint8_t  f2bc9x_b0_d1;
+	uint8_t  f2bcax_b0_d1;
+	uint8_t  f2bcbx_b0_d1;
+	uint8_t  f3bc2x_b0_d1;
+	uint8_t  f3bc3x_b0_d1;
+	uint8_t  f3bc4x_b0_d1;
+	uint8_t  f3bc5x_b0_d1;
+	uint8_t  f3bc8x_b0_d1;
+	uint8_t  f3bc9x_b0_d1;
+	uint8_t  f3bcax_b0_d1;
+	uint8_t  f3bcbx_b0_d1;
+	uint8_t  f0bc2x_b1_d1;
+	uint8_t  f0bc3x_b1_d1;
+	uint8_t  f0bc4x_b1_d1;
+	uint8_t  f0bc5x_b1_d1;
+	uint8_t  f0bc8x_b1_d1;
+	uint8_t  f0bc9x_b1_d1;
+	uint8_t  f0bcax_b1_d1;
+	uint8_t  f0bcbx_b1_d1;
+	uint8_t  f1bc2x_b1_d1;
+	uint8_t  f1bc3x_b1_d1;
+	uint8_t  f1bc4x_b1_d1;
+	uint8_t  f1bc5x_b1_d1;
+	uint8_t  f1bc8x_b1_d1;
+	uint8_t  f1bc9x_b1_d1;
+	uint8_t  f1bcax_b1_d1;
+	uint8_t  f1bcbx_b1_d1;
+	uint8_t  f2bc2x_b1_d1;
+	uint8_t  f2bc3x_b1_d1;
+	uint8_t  f2bc4x_b1_d1;
+	uint8_t  f2bc5x_b1_d1;
+	uint8_t  f2bc8x_b1_d1;
+	uint8_t  f2bc9x_b1_d1;
+	uint8_t  f2bcax_b1_d1;
+	uint8_t  f2bcbx_b1_d1;
+	uint8_t  f3bc2x_b1_d1;
+	uint8_t  f3bc3x_b1_d1;
+	uint8_t  f3bc4x_b1_d1;
+	uint8_t  f3bc5x_b1_d1;
+	uint8_t  f3bc8x_b1_d1;
+	uint8_t  f3bc9x_b1_d1;
+	uint8_t  f3bcax_b1_d1;
+	uint8_t  f3bcbx_b1_d1;
+	uint8_t  f0bc2x_b2_d1;
+	uint8_t  f0bc3x_b2_d1;
+	uint8_t  f0bc4x_b2_d1;
+	uint8_t  f0bc5x_b2_d1;
+	uint8_t  f0bc8x_b2_d1;
+	uint8_t  f0bc9x_b2_d1;
+	uint8_t  f0bcax_b2_d1;
+	uint8_t  f0bcbx_b2_d1;
+	uint8_t  f1bc2x_b2_d1;
+	uint8_t  f1bc3x_b2_d1;
+	uint8_t  f1bc4x_b2_d1;
+	uint8_t  f1bc5x_b2_d1;
+	uint8_t  f1bc8x_b2_d1;
+	uint8_t  f1bc9x_b2_d1;
+	uint8_t  f1bcax_b2_d1;
+	uint8_t  f1bcbx_b2_d1;
+	uint8_t  f2bc2x_b2_d1;
+	uint8_t  f2bc3x_b2_d1;
+	uint8_t  f2bc4x_b2_d1;
+	uint8_t  f2bc5x_b2_d1;
+	uint8_t  f2bc8x_b2_d1;
+	uint8_t  f2bc9x_b2_d1;
+	uint8_t  f2bcax_b2_d1;
+	uint8_t  f2bcbx_b2_d1;
+	uint8_t  f3bc2x_b2_d1;
+	uint8_t  f3bc3x_b2_d1;
+	uint8_t  f3bc4x_b2_d1;
+	uint8_t  f3bc5x_b2_d1;
+	uint8_t  f3bc8x_b2_d1;
+	uint8_t  f3bc9x_b2_d1;
+	uint8_t  f3bcax_b2_d1;
+	uint8_t  f3bcbx_b2_d1;
+	uint8_t  f0bc2x_b3_d1;
+	uint8_t  f0bc3x_b3_d1;
+	uint8_t  f0bc4x_b3_d1;
+	uint8_t  f0bc5x_b3_d1;
+	uint8_t  f0bc8x_b3_d1;
+	uint8_t  f0bc9x_b3_d1;
+	uint8_t  f0bcax_b3_d1;
+	uint8_t  f0bcbx_b3_d1;
+	uint8_t  f1bc2x_b3_d1;
+	uint8_t  f1bc3x_b3_d1;
+	uint8_t  f1bc4x_b3_d1;
+	uint8_t  f1bc5x_b3_d1;
+	uint8_t  f1bc8x_b3_d1;
+	uint8_t  f1bc9x_b3_d1;
+	uint8_t  f1bcax_b3_d1;
+	uint8_t  f1bcbx_b3_d1;
+	uint8_t  f2bc2x_b3_d1;
+	uint8_t  f2bc3x_b3_d1;
+	uint8_t  f2bc4x_b3_d1;
+	uint8_t  f2bc5x_b3_d1;
+	uint8_t  f2bc8x_b3_d1;
+	uint8_t  f2bc9x_b3_d1;
+	uint8_t  f2bcax_b3_d1;
+	uint8_t  f2bcbx_b3_d1;
+	uint8_t  f3bc2x_b3_d1;
+	uint8_t  f3bc3x_b3_d1;
+	uint8_t  f3bc4x_b3_d1;
+	uint8_t  f3bc5x_b3_d1;
+	uint8_t  f3bc8x_b3_d1;
+	uint8_t  f3bc9x_b3_d1;
+	uint8_t  f3bcax_b3_d1;
+	uint8_t  f3bcbx_b3_d1;
+	uint8_t  f0bc2x_b4_d1;
+	uint8_t  f0bc3x_b4_d1;
+	uint8_t  f0bc4x_b4_d1;
+	uint8_t  f0bc5x_b4_d1;
+	uint8_t  f0bc8x_b4_d1;
+	uint8_t  f0bc9x_b4_d1;
+	uint8_t  f0bcax_b4_d1;
+	uint8_t  f0bcbx_b4_d1;
+	uint8_t  f1bc2x_b4_d1;
+	uint8_t  f1bc3x_b4_d1;
+	uint8_t  f1bc4x_b4_d1;
+	uint8_t  f1bc5x_b4_d1;
+	uint8_t  f1bc8x_b4_d1;
+	uint8_t  f1bc9x_b4_d1;
+	uint8_t  f1bcax_b4_d1;
+	uint8_t  f1bcbx_b4_d1;
+	uint8_t  f2bc2x_b4_d1;
+	uint8_t  f2bc3x_b4_d1;
+	uint8_t  f2bc4x_b4_d1;
+	uint8_t  f2bc5x_b4_d1;
+	uint8_t  f2bc8x_b4_d1;
+	uint8_t  f2bc9x_b4_d1;
+	uint8_t  f2bcax_b4_d1;
+	uint8_t  f2bcbx_b4_d1;
+	uint8_t  f3bc2x_b4_d1;
+	uint8_t  f3bc3x_b4_d1;
+	uint8_t  f3bc4x_b4_d1;
+	uint8_t  f3bc5x_b4_d1;
+	uint8_t  f3bc8x_b4_d1;
+	uint8_t  f3bc9x_b4_d1;
+	uint8_t  f3bcax_b4_d1;
+	uint8_t  f3bcbx_b4_d1;
+	uint8_t  f0bc2x_b5_d1;
+	uint8_t  f0bc3x_b5_d1;
+	uint8_t  f0bc4x_b5_d1;
+	uint8_t  f0bc5x_b5_d1;
+	uint8_t  f0bc8x_b5_d1;
+	uint8_t  f0bc9x_b5_d1;
+	uint8_t  f0bcax_b5_d1;
+	uint8_t  f0bcbx_b5_d1;
+	uint8_t  f1bc2x_b5_d1;
+	uint8_t  f1bc3x_b5_d1;
+	uint8_t  f1bc4x_b5_d1;
+	uint8_t  f1bc5x_b5_d1;
+	uint8_t  f1bc8x_b5_d1;
+	uint8_t  f1bc9x_b5_d1;
+	uint8_t  f1bcax_b5_d1;
+	uint8_t  f1bcbx_b5_d1;
+	uint8_t  f2bc2x_b5_d1;
+	uint8_t  f2bc3x_b5_d1;
+	uint8_t  f2bc4x_b5_d1;
+	uint8_t  f2bc5x_b5_d1;
+	uint8_t  f2bc8x_b5_d1;
+	uint8_t  f2bc9x_b5_d1;
+	uint8_t  f2bcax_b5_d1;
+	uint8_t  f2bcbx_b5_d1;
+	uint8_t  f3bc2x_b5_d1;
+	uint8_t  f3bc3x_b5_d1;
+	uint8_t  f3bc4x_b5_d1;
+	uint8_t  f3bc5x_b5_d1;
+	uint8_t  f3bc8x_b5_d1;
+	uint8_t  f3bc9x_b5_d1;
+	uint8_t  f3bcax_b5_d1;
+	uint8_t  f3bcbx_b5_d1;
+	uint8_t  f0bc2x_b6_d1;
+	uint8_t  f0bc3x_b6_d1;
+	uint8_t  f0bc4x_b6_d1;
+	uint8_t  f0bc5x_b6_d1;
+	uint8_t  f0bc8x_b6_d1;
+	uint8_t  f0bc9x_b6_d1;
+	uint8_t  f0bcax_b6_d1;
+	uint8_t  f0bcbx_b6_d1;
+	uint8_t  f1bc2x_b6_d1;
+	uint8_t  f1bc3x_b6_d1;
+	uint8_t  f1bc4x_b6_d1;
+	uint8_t  f1bc5x_b6_d1;
+	uint8_t  f1bc8x_b6_d1;
+	uint8_t  f1bc9x_b6_d1;
+	uint8_t  f1bcax_b6_d1;
+	uint8_t  f1bcbx_b6_d1;
+	uint8_t  f2bc2x_b6_d1;
+	uint8_t  f2bc3x_b6_d1;
+	uint8_t  f2bc4x_b6_d1;
+	uint8_t  f2bc5x_b6_d1;
+	uint8_t  f2bc8x_b6_d1;
+	uint8_t  f2bc9x_b6_d1;
+	uint8_t  f2bcax_b6_d1;
+	uint8_t  f2bcbx_b6_d1;
+	uint8_t  f3bc2x_b6_d1;
+	uint8_t  f3bc3x_b6_d1;
+	uint8_t  f3bc4x_b6_d1;
+	uint8_t  f3bc5x_b6_d1;
+	uint8_t  f3bc8x_b6_d1;
+	uint8_t  f3bc9x_b6_d1;
+	uint8_t  f3bcax_b6_d1;
+	uint8_t  f3bcbx_b6_d1;
+	uint8_t  f0bc2x_b7_d1;
+	uint8_t  f0bc3x_b7_d1;
+	uint8_t  f0bc4x_b7_d1;
+	uint8_t  f0bc5x_b7_d1;
+	uint8_t  f0bc8x_b7_d1;
+	uint8_t  f0bc9x_b7_d1;
+	uint8_t  f0bcax_b7_d1;
+	uint8_t  f0bcbx_b7_d1;
+	uint8_t  f1bc2x_b7_d1;
+	uint8_t  f1bc3x_b7_d1;
+	uint8_t  f1bc4x_b7_d1;
+	uint8_t  f1bc5x_b7_d1;
+	uint8_t  f1bc8x_b7_d1;
+	uint8_t  f1bc9x_b7_d1;
+	uint8_t  f1bcax_b7_d1;
+	uint8_t  f1bcbx_b7_d1;
+	uint8_t  f2bc2x_b7_d1;
+	uint8_t  f2bc3x_b7_d1;
+	uint8_t  f2bc4x_b7_d1;
+	uint8_t  f2bc5x_b7_d1;
+	uint8_t  f2bc8x_b7_d1;
+	uint8_t  f2bc9x_b7_d1;
+	uint8_t  f2bcax_b7_d1;
+	uint8_t  f2bcbx_b7_d1;
+	uint8_t  f3bc2x_b7_d1;
+	uint8_t  f3bc3x_b7_d1;
+	uint8_t  f3bc4x_b7_d1;
+	uint8_t  f3bc5x_b7_d1;
+	uint8_t  f3bc8x_b7_d1;
+	uint8_t  f3bc9x_b7_d1;
+	uint8_t  f3bcax_b7_d1;
+	uint8_t  f3bcbx_b7_d1;
+	uint8_t  f0bc2x_b8_d1;
+	uint8_t  f0bc3x_b8_d1;
+	uint8_t  f0bc4x_b8_d1;
+	uint8_t  f0bc5x_b8_d1;
+	uint8_t  f0bc8x_b8_d1;
+	uint8_t  f0bc9x_b8_d1;
+	uint8_t  f0bcax_b8_d1;
+	uint8_t  f0bcbx_b8_d1;
+	uint8_t  f1bc2x_b8_d1;
+	uint8_t  f1bc3x_b8_d1;
+	uint8_t  f1bc4x_b8_d1;
+	uint8_t  f1bc5x_b8_d1;
+	uint8_t  f1bc8x_b8_d1;
+	uint8_t  f1bc9x_b8_d1;
+	uint8_t  f1bcax_b8_d1;
+	uint8_t  f1bcbx_b8_d1;
+	uint8_t  f2bc2x_b8_d1;
+	uint8_t  f2bc3x_b8_d1;
+	uint8_t  f2bc4x_b8_d1;
+	uint8_t  f2bc5x_b8_d1;
+	uint8_t  f2bc8x_b8_d1;
+	uint8_t  f2bc9x_b8_d1;
+	uint8_t  f2bcax_b8_d1;
+	uint8_t  f2bcbx_b8_d1;
+	uint8_t  f3bc2x_b8_d1;
+	uint8_t  f3bc3x_b8_d1;
+	uint8_t  f3bc4x_b8_d1;
+	uint8_t  f3bc5x_b8_d1;
+	uint8_t  f3bc8x_b8_d1;
+	uint8_t  f3bc9x_b8_d1;
+	uint8_t  f3bcax_b8_d1;
+	uint8_t  f3bcbx_b8_d1;
+	uint8_t  f5bc5x_d1;
+	uint8_t  f5bc6x_d1;
+	uint8_t  f4bc8x_d1;
+	uint8_t  f4bc9x_d1;
+	uint8_t  f4bcax_d1;
+	uint8_t  f4bcbx_d1;
+	uint8_t  f4bccx_d1;
+	uint8_t  f4bcdx_d1;
+	uint8_t  f4bcex_d1;
+	uint8_t  f4bcfx_d1;
+	uint8_t  f5bc8x_d1;
+	uint8_t  f5bc9x_d1;
+	uint8_t  f5bcax_d1;
+	uint8_t  f5bcbx_d1;
+	uint8_t  f5bccx_d1;
+	uint8_t  f5bcdx_d1;
+	uint8_t  f5bcex_d1;
+	uint8_t  f5bcfx_d1;
+	uint8_t  f6bc8x_d1;
+	uint8_t  f6bc9x_d1;
+	uint8_t  f6bcax_d1;
+	uint8_t  f6bcbx_d1;
+	uint8_t  f6bccx_d1;
+	uint8_t  f6bcdx_d1;
+	uint8_t  f6bcex_d1;
+	uint8_t  f6bcfx_d1;
+	uint8_t  f7bc8x_d1;
+	uint8_t  f7bc9x_d1;
+	uint8_t  f7bcax_d1;
+	uint8_t  f7bcbx_d1;
+	uint8_t  f7bccx_d1;
+	uint8_t  f7bcdx_d1;
+	uint8_t  f7bcex_d1;
+	uint8_t  f7bcfx_d1;
+	uint16_t alt_cas_l;
+	uint8_t  alt_wcas_l;
+	uint8_t  d4misc;
+} __packed;
+#endif
diff --git a/drivers/nxp/ddr/phy-gen2/ddrphy.mk b/drivers/nxp/ddr/phy-gen2/ddrphy.mk
new file mode 100644
index 0000000..ba5c774
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/ddrphy.mk
@@ -0,0 +1,20 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#-----------------------------------------------------------------------------
+
+# SNPS ddr phy driver files
+
+DDR_PHY_C  =
+DDR_PHY_H  =
+
+$(DDR_PHY_C): $(DDR_PHY_H) $(COMMON_HDRS) src
+	@cp -r "$(DDR_PHY_PATH)/$@" "$(SRC_DIR)/$@"
+
+$(DDR_PHY_H): src
+	@cp -r "$(DDR_PHY_PATH)/$@" "$(SRC_DIR)/$@"
+
+#------------------------------------------------
diff --git a/drivers/nxp/ddr/phy-gen2/input.h b/drivers/nxp/ddr/phy-gen2/input.h
new file mode 100644
index 0000000..dbcd1ae
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/input.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _INPUT_H_
+#define _INPUT_H_
+
+enum dram_types {
+	DDR4,
+	DDR3,
+	LPDDR4,
+	LPDDR3,
+	LPDDR2,
+	DDR5,
+};
+
+enum dimm_types {
+	UDIMM,
+	SODIMM,
+	RDIMM,
+	LRDIMM,
+	NODIMM,
+};
+
+struct input_basic {
+	enum dram_types dram_type;
+	enum dimm_types dimm_type;
+	int lp4x_mode;		/* 0x1 = lpddr4x mode, when dram_type is lpddr4
+				 */
+				/* not used for protocols other than lpddr4 */
+	int num_dbyte;		/* number of dbytes physically instantiated */
+	int num_active_dbyte_dfi0;	/* number of active dbytes to be
+					 * controlled by dfi0
+					 */
+	int num_active_dbyte_dfi1;	/* number of active dbytes to be
+					 * controlled by  dfi1. Not used for
+					 * protocols other than lpddr3 and
+					 * lpddr4
+					 */
+	int num_anib;		/* number of anibs physically instantiated */
+	int num_rank_dfi0;	/* number of ranks in dfi0 channel */
+	int num_rank_dfi1;	/* number of ranks in dfi1 channel */
+	int dram_data_width;	/* 4,8,16 or 32 depending on protocol and dram
+				 * type
+				 */
+	int num_pstates;
+	int frequency;		/* memclk frequency in mhz -- round up */
+	int pll_bypass;		/* pll bypass enable */
+	int dfi_freq_ratio;	/* selected dfi frequency ratio */
+	int dfi1exists;		/* whether they phy config has dfi1 channel */
+	int train2d;
+	int hard_macro_ver;
+	int read_dbienable;
+	int dfi_mode;		/* no longer used */
+};
+
+struct input_advanced {
+	int d4rx_preamble_length;
+	int d4tx_preamble_length;
+	int ext_cal_res_val;	/* external pull-down resistor */
+	int is2ttiming;
+	int odtimpedance;
+	int tx_impedance;
+	int atx_impedance;
+	int mem_alert_en;
+	int mem_alert_puimp;
+	int mem_alert_vref_level;
+	int mem_alert_sync_bypass;
+	int dis_dyn_adr_tri;
+	int phy_mstr_train_interval;
+	int phy_mstr_max_req_to_ack;
+	int wdqsext;
+	int cal_interval;
+	int cal_once;
+	int dram_byte_swap;
+	int rx_en_back_off;
+	int train_sequence_ctrl;
+	int phy_gen2_umctl_opt;
+	int phy_gen2_umctl_f0rc5x;
+	int tx_slew_rise_dq;
+	int tx_slew_fall_dq;
+	int tx_slew_rise_ac;
+	int tx_slew_fall_ac;
+	int enable_high_clk_skew_fix;
+	int disable_unused_addr_lns;
+	int phy_init_sequence_num;
+	int cs_mode;		/* rdimm */
+	int cast_cs_to_cid;	/* rdimm */
+};
+
+struct input {
+	struct input_basic basic;
+	struct input_advanced adv;
+	unsigned int mr[7];
+	unsigned int cs_d0;
+	unsigned int cs_d1;
+	unsigned int mirror;
+	unsigned int odt[4];
+	unsigned int rcw[16];
+	unsigned int rcw3x;
+	unsigned int vref;
+};
+
+#endif
diff --git a/drivers/nxp/ddr/phy-gen2/messages.h b/drivers/nxp/ddr/phy-gen2/messages.h
new file mode 100644
index 0000000..7dec7df
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/messages.h
@@ -0,0 +1,2909 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef MESSAGE_H
+#define MESSAGE_H
+
+#ifdef DEBUG
+struct phy_msg {
+	uint32_t index;
+	const char *msg;
+};
+
+const static struct phy_msg messages_1d[] = {
+	{0x00000001,
+	 "PMU1:prbsGenCtl:%x\n"
+	},
+	{0x00010000,
+	 "PMU1: loading 2D acsm sequence\n"
+	},
+	{0x00020000,
+	 "PMU1: loading 1D acsm sequence\n"
+	},
+	{0x00030002,
+	 "PMU3: %d memclocks @ %d to get half of 300ns\n"
+	},
+	{0x00040000,
+	 "PMU: Error: User requested MPR read pattern for read DQS training in DDR3 Mode\n"
+	},
+	{0x00050000,
+	 "PMU3: Running 1D search for left eye edge\n"
+	},
+	{0x00060001,
+	 "PMU1: In Phase Left Edge Search cs %d\n"
+	},
+	{0x00070001,
+	 "PMU1: Out of Phase Left Edge Search cs %d\n"
+	},
+	{0x00080000,
+	 "PMU3: Running 1D search for right eye edge\n"
+	},
+	{0x00090001,
+	 "PMU1: In Phase Right Edge Search cs %d\n"
+	},
+	{0x000a0001,
+	 "PMU1: Out of Phase Right Edge Search cs %d\n"
+	},
+	{0x000b0001,
+	 "PMU1: mxRdLat training pstate %d\n"
+	},
+	{0x000c0001,
+	 "PMU1: mxRdLat search for cs %d\n"
+	},
+	{0x000d0001,
+	 "PMU0: MaxRdLat non consistent DtsmLoThldXingInd 0x%03x\n"
+	},
+	{0x000e0003,
+	 "PMU4: CS %d Dbyte %d worked with DFIMRL = %d DFICLKs\n"
+	},
+	{0x000f0004,
+	 "PMU3: MaxRdLat Read Lane err mask for csn %d, DFIMRL %2d DFIClks, dbyte %d = 0x%03x\n"
+	},
+	{0x00100003,
+	 "PMU3: MaxRdLat Read Lane err mask for csn %d DFIMRL %2d, All dbytes = 0x%03x\n"
+	},
+	{0x00110001,
+	 "PMU: Error: CS%d failed to find a DFIMRL setting that worked for all bytes during MaxRdLat training\n"
+	},
+	{0x00120002,
+	 "PMU3: Smallest passing DFIMRL for all dbytes in CS%d = %d DFIClks\n"
+	},
+	{0x00130000,
+	 "PMU: Error: No passing DFIMRL value found for any chip select during MaxRdLat training\n"
+	},
+	{0x00140003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly passing region is too small (width = %d)\n"
+	},
+	{0x00150006,
+	 "PMU10: Adjusting rxclkdly db %d nib %d from %d+%d=%d->%d\n"
+	},
+	{0x00160000,
+	 "PMU4: TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x00170005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00180002,
+	 "PMU2: TXDQ delayLeft[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00190004,
+	 "PMU2: TXDQ delayLeft[%2d] = %3d oopScaled = %3d selectOop %d\n"
+	},
+	{0x001a0002,
+	 "PMU2: TXDQ delayRight[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x001b0004,
+	 "PMU2: TXDQ delayRight[%2d] = %3d oopScaled = %3d selectOop %d\n"
+	},
+	{0x001c0003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly passing region is too small (width = %d)\n"
+	},
+	{0x001d0000,
+	 "PMU4: TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x001e0002,
+	 "PMU4: DB %d Lane %d: (DISCONNECTED)\n"
+	},
+	{0x001f0005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00200002,
+	 "PMU3: Running 1D search csn %d for DM Right/NotLeft(%d) eye edge\n"
+	},
+	{0x00210002,
+	 "PMU3: WrDq DM byte%2d with Errcnt %d\n"
+	},
+	{0x00220002,
+	 "PMU3: WrDq DM byte%2d avgDly 0x%04x\n"
+	},
+	{0x00230002,
+	 "PMU1: WrDq DM byte%2d with Errcnt %d\n"
+	},
+	{0x00240001,
+	 "PMU: Error: Dbyte %d txDqDly DM training did not start inside the eye\n"
+	},
+	{0x00250000,
+	 "PMU4: DM TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x00260002,
+	 "PMU4: DB %d Lane %d: (DISCONNECTED)\n"
+	},
+	{0x00270005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00280003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly DM passing region is too small (width = %d)\n"
+	},
+	{0x00290004,
+	 "PMU3: Errcnt for MRD/MWD search nib %2d delay = (%d, 0x%02x) = %d\n"
+	},
+	{0x002a0000,
+	 "PMU3: Precharge all open banks\n"
+	},
+	{0x002b0002,
+	 "PMU: Error: Dbyte %d nibble %d found mutliple working coarse delay setting for MRD/MWD\n"
+	},
+	{0x002c0000,
+	 "PMU4: MRD Passing Regions (coarseVal, fineLeft fineRight -> fineCenter)\n"
+	},
+	{0x002d0000,
+	 "PMU4: MWD Passing Regions (coarseVal, fineLeft fineRight -> fineCenter)\n"
+	},
+	{0x002e0004,
+	 "PMU10: Warning: DB %d nibble %d has multiple working coarse delays, %d and %d, choosing the smaller delay\n"
+	},
+	{0x002f0003,
+	 "PMU: Error: Dbyte %d nibble %d MRD/MWD passing region is too small (width = %d)\n"
+	},
+	{0x00300006,
+	 "PMU4: DB %d nibble %d: %3d, %3d %3d -> %3d\n"
+	},
+	{0x00310002,
+	 "PMU1: Start MRD/nMWD %d for csn %d\n"
+	},
+	{0x00320002,
+	 "PMU2: RXDQS delayLeft[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00330006,
+	 "PMU2: RXDQS delayLeft[%2d] = %3d delayOop[%2d] = %3d OopScaled %4d, selectOop %d\n"
+	},
+	{0x00340002,
+	 "PMU2: RXDQS delayRight[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00350006,
+	 "PMU2: RXDQS delayRight[%2d] = %3d delayOop[%2d] = %4d OopScaled %4d, selectOop %d\n"
+	},
+	{0x00360000,
+	 "PMU4: RxClkDly Passing Regions (EyeLeft EyeRight -> EyeCenter)\n"
+	},
+	{0x00370002,
+	 "PMU4: DB %d nibble %d: (DISCONNECTED)\n"
+	},
+	{0x00380005,
+	 "PMU4: DB %d nibble %d: %3d %3d -> %3d\n"
+	},
+	{0x00390003,
+	 "PMU: Error: Dbyte %d nibble %d rxClkDly passing region is too small (width = %d)\n"
+	},
+	{0x003a0002,
+	 "PMU0: goodbar = %d for RDWR_BLEN %d\n"
+	},
+	{0x003b0001,
+	 "PMU3: RxClkDly = %d\n"
+	},
+	{0x003c0005,
+	 "PMU0: db %d l %d absLane %d -> bottom %d top %d\n"
+	},
+	{0x003d0009,
+	 "PMU3: BYTE %d - %3d %3d %3d %3d %3d %3d %3d %3d\n"
+	},
+	{0x003e0002,
+	 "PMU: Error: dbyte %d lane %d's per-lane vrefDAC's had no passing region\n"
+	},
+	{0x003f0004,
+	 "PMU0: db%d l%d - %d %d\n"
+	},
+	{0x00400002,
+	 "PMU0: goodbar = %d for RDWR_BLEN %d\n"
+	},
+	{0x00410004,
+	 "PMU3: db%d l%d saw %d issues at rxClkDly %d\n"
+	},
+	{0x00420003,
+	 "PMU3: db%d l%d first saw a pass->fail edge at rxClkDly %d\n"
+	},
+	{0x00430002,
+	 "PMU3: lane %d PBD = %d\n"
+	},
+	{0x00440003,
+	 "PMU3: db%d l%d first saw a DBI pass->fail edge at rxClkDly %d\n"
+	},
+	{0x00450003,
+	 "PMU2: db%d l%d already passed rxPBD = %d\n"
+	},
+	{0x00460003,
+	 "PMU0: db%d l%d, PBD = %d\n"
+	},
+	{0x00470002,
+	 "PMU: Error: dbyte %d lane %d failed read deskew\n"
+	},
+	{0x00480003,
+	 "PMU0: db%d l%d, inc PBD = %d\n"
+	},
+	{0x00490003,
+	 "PMU1: Running lane deskew on pstate %d csn %d rdDBIEn %d\n"
+	},
+	{0x004a0000,
+	 "PMU: Error: Read deskew training has been requested, but csrMajorModeDbyte[2] is set\n"
+	},
+	{0x004b0002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x004c0002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x004d0001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D3U Type\n"
+	},
+	{0x004e0001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D3R Type\n"
+	},
+	{0x004f0001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4U Type\n"
+	},
+	{0x00500001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4R Type\n"
+	},
+	{0x00510001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4LR Type\n"
+	},
+	{0x00520000,
+	 "PMU: Error: Both 2t timing mode and ddr4 geardown mode specified in the messageblock's PhyCfg and MR3 fields. Only one can be enabled\n"
+	},
+	{0x00530003,
+	 "PMU10: PHY TOTALS - NUM_DBYTES %d NUM_NIBBLES %d NUM_ANIBS %d\n"
+	},
+	{0x00540006,
+	 "PMU10: CSA=0x%02x, CSB=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, MMISC=%d DRAMFreq=%dMT DramType=LPDDR3\n"
+	},
+	{0x00550006,
+	 "PMU10: CSA=0x%02x, CSB=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, MMISC=%d DRAMFreq=%dMT DramType=LPDDR4\n"
+	},
+	{0x00560008,
+	 "PMU10: CS=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, 2T=%d, MMISC=%d AddrMirror=%d DRAMFreq=%dMT DramType=%d\n"
+	},
+	{0x00570004,
+	 "PMU10: Pstate%d MR0=0x%04x MR1=0x%04x MR2=0x%04x\n"
+	},
+	{0x00580008,
+	 "PMU10: Pstate%d MRS MR0=0x%04x MR1=0x%04x MR2=0x%04x MR3=0x%04x MR4=0x%04x MR5=0x%04x MR6=0x%04x\n"
+	},
+	{0x00590005,
+	 "PMU10: Pstate%d MRS MR1_A0=0x%04x MR2_A0=0x%04x MR3_A0=0x%04x MR11_A0=0x%04x\n"
+	},
+	{0x005a0000,
+	 "PMU10: UseBroadcastMR set. All ranks and channels use MRXX_A0 for MR settings.\n"
+	},
+	{0x005b0005,
+	 "PMU10: Pstate%d MRS MR01_A0=0x%02x MR02_A0=0x%02x MR03_A0=0x%02x MR11_A0=0x%02x\n"
+	},
+	{0x005c0005,
+	 "PMU10: Pstate%d MRS MR12_A0=0x%02x MR13_A0=0x%02x MR14_A0=0x%02x MR22_A0=0x%02x\n"
+	},
+	{0x005d0005,
+	 "PMU10: Pstate%d MRS MR01_A1=0x%02x MR02_A1=0x%02x MR03_A1=0x%02x MR11_A1=0x%02x\n"
+	},
+	{0x005e0005,
+	 "PMU10: Pstate%d MRS MR12_A1=0x%02x MR13_A1=0x%02x MR14_A1=0x%02x MR22_A1=0x%02x\n"
+	},
+	{0x005f0005,
+	 "PMU10: Pstate%d MRS MR01_B0=0x%02x MR02_B0=0x%02x MR03_B0=0x%02x MR11_B0=0x%02x\n"
+	},
+	{0x00600005,
+	 "PMU10: Pstate%d MRS MR12_B0=0x%02x MR13_B0=0x%02x MR14_B0=0x%02x MR22_B0=0x%02x\n"
+	},
+	{0x00610005,
+	 "PMU10: Pstate%d MRS MR01_B1=0x%02x MR02_B1=0x%02x MR03_B1=0x%02x MR11_B1=0x%02x\n"
+	},
+	{0x00620005,
+	 "PMU10: Pstate%d MRS MR12_B1=0x%02x MR13_B1=0x%02x MR14_B1=0x%02x MR22_B1=0x%02x\n"
+	},
+	{0x00630002,
+	 "PMU1: AcsmOdtCtrl%02d 0x%02x\n"
+	},
+	{0x00640002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00650002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00660000,
+	 "PMU1: HwtCAMode set\n"
+	},
+	{0x00670001,
+	 "PMU3: DDR4 infinite preamble enter/exit mode %d\n"
+	},
+	{0x00680002,
+	 "PMU1: In rxenb_train() csn=%d pstate=%d\n"
+	},
+	{0x00690000,
+	 "PMU3: Finding DQS falling edge\n"
+	},
+	{0x006a0000,
+	 "PMU3: Searching for DDR3/LPDDR3/LPDDR4 read preamble\n"
+	},
+	{0x006b0009,
+	 "PMU3: dtsm fails Even Nibbles : %2x %2x %2x %2x %2x %2x %2x %2x %2x\n"
+	},
+	{0x006c0009,
+	 "PMU3: dtsm fails Odd  Nibbles : %2x %2x %2x %2x %2x %2x %2x %2x %2x\n"
+	},
+	{0x006d0002,
+	 "PMU3: Preamble search pass=%d anyfail=%d\n"
+	},
+	{0x006e0000,
+	 "PMU: Error: RxEn training preamble not found\n"
+	},
+	{0x006f0000,
+	 "PMU3: Found DQS pre-amble\n"
+	},
+	{0x00700001,
+	 "PMU: Error: Dbyte %d couldn't find the rising edge of DQS during RxEn Training\n"
+	},
+	{0x00710000,
+	 "PMU3: RxEn aligning to first rising edge of burst\n"
+	},
+	{0x00720001,
+	 "PMU3: Decreasing RxEn delay by %d fine step to allow full capture of reads\n"
+	},
+	{0x00730001,
+	 "PMU3: MREP Delay = %d\n"
+	},
+	{0x00740003,
+	 "PMU3: Errcnt for MREP nib %2d delay = %2d is %d\n"
+	},
+	{0x00750002,
+	 "PMU3: MREP nibble %d sampled a 1 at data buffer delay %d\n"
+	},
+	{0x00760002,
+	 "PMU3: MREP nibble %d saw a 0 to 1 transition at data buffer delay %d\n"
+	},
+	{0x00770000,
+	 "PMU2:  MREP did not find a 0 to 1 transition for all nibbles. Failing nibbles assumed to have rising edge close to fine delay 63\n"
+	},
+	{0x00780002,
+	 "PMU2:  Rising edge found in alias window, setting rxDly for nibble %d = %d\n"
+	},
+	{0x00790002,
+	 "PMU: Error: Failed MREP for nib %d with %d one\n"
+	},
+	{0x007a0003,
+	 "PMU2:  Rising edge not found in alias window with %d one, leaving rxDly for nibble %d = %d\n"
+	},
+	{0x007b0002,
+	 "PMU3: Training DIMM %d CSn %d\n"
+	},
+	{0x007c0001,
+	 "PMU3: exitCAtrain_lp3 cs 0x%x\n"
+	},
+	{0x007d0001,
+	 "PMU3: enterCAtrain_lp3 cs 0x%x\n"
+	},
+	{0x007e0001,
+	 "PMU3: CAtrain_switchmsb_lp3 cs 0x%x\n"
+	},
+	{0x007f0001,
+	 "PMU3: CATrain_rdwr_lp3 looking for pattern %x\n"
+	},
+	{0x00800000,
+	 "PMU3: exitCAtrain_lp4\n"
+	},
+	{0x00810001,
+	 "PMU3: DEBUG enterCAtrain_lp4 1: cs 0x%x\n"
+	},
+	{0x00820001,
+	 "PMU3: DEBUG enterCAtrain_lp4 3: Put dbyte %d in async mode\n"
+	},
+	{0x00830000,
+	 "PMU3: DEBUG enterCAtrain_lp4 5: Send MR13 to turn on CA training\n"
+	},
+	{0x00840003,
+	 "PMU3: DEBUG enterCAtrain_lp4 7: idx = %d vref = %x mr12 = %x\n"
+	},
+	{0x00850001,
+	 "PMU3: CATrain_rdwr_lp4 looking for pattern %x\n"
+	},
+	{0x00860004,
+	 "PMU3: Phase %d CAreadbackA db:%d %x xo:%x\n"
+	},
+	{0x00870005,
+	 "PMU3: DEBUG lp4SetCatrVref 1: cs=%d chan=%d mr12=%x vref=%d.%d%%\n"
+	},
+	{0x00880003,
+	 "PMU3: DEBUG lp4SetCatrVref 3: mr12 = %x send vref= %x to db=%d\n"
+	},
+	{0x00890000,
+	 "PMU10:Optimizing vref\n"
+	},
+	{0x008a0004,
+	 "PMU4:mr12:%2x cs:%d chan %d r:%4x\n"
+	},
+	{0x008b0005,
+	 "PMU3: i:%2d bstr:%2d bsto:%2d st:%d r:%d\n"
+	},
+	{0x008c0002,
+	 "Failed to find sufficient CA Vref Passing Region for CS %d ch. %d\n"
+	},
+	{0x008d0005,
+	 "PMU3:Found %d.%d%% MR12:%x for cs:%d chan %d\n"
+	},
+	{0x008e0002,
+	 "PMU3:Calculated %d for AtxImpedence from acx %d.\n"
+	},
+	{0x008f0000,
+	 "PMU3:CA Odt impedence ==0.  Use default vref.\n"
+	},
+	{0x00900003,
+	 "PMU3:Calculated %d.%d%% for Vref MR12=0x%x.\n"
+	},
+	{0x00910000,
+	 "PMU3: CAtrain_lp\n"
+	},
+	{0x00920000,
+	 "PMU3: CAtrain Begins.\n"
+	},
+	{0x00930001,
+	 "PMU3: CAtrain_lp testing dly %d\n"
+	},
+	{0x00940001,
+	 "PMU5: CA bitmap dump for cs %x\n"
+	},
+	{0x00950001,
+	 "PMU5: CAA%d "
+	},
+	{0x00960001, "%02x"
+	},
+	{0x00970000, "\n"
+	},
+	{0x00980001,
+	 "PMU5: CAB%d "
+	},
+	{0x00990001, "%02x"
+	},
+	{0x009a0000, "\n"
+	},
+	{0x009b0003,
+	 "PMU3: anibi=%d, anibichan[anibi]=%d ,chan=%d\n"
+	},
+	{0x009c0001, "%02x"
+	},
+	{0x009d0001, "\nPMU3:Raw CA setting :%x"
+	},
+	{0x009e0002, "\nPMU3:ATxDly setting:%x margin:%d\n"
+	},
+	{0x009f0002, "\nPMU3:InvClk ATxDly setting:%x margin:%d\n"
+	},
+	{0x00a00000, "\nPMU3:No Range found!\n"
+	},
+	{0x00a10003,
+	 "PMU3: 2 anibi=%d, anibichan[anibi]=%d ,chan=%d"
+	},
+	{0x00a20002, "\nPMU3: no neg clock => CA setting anib=%d, :%d\n"
+	},
+	{0x00a30001,
+	 "PMU3:Normal margin:%d\n"
+	},
+	{0x00a40001,
+	 "PMU3:Inverted margin:%d\n"
+	},
+	{0x00a50000,
+	 "PMU3:Using Inverted clock\n"
+	},
+	{0x00a60000,
+	 "PMU3:Using normal clk\n"
+	},
+	{0x00a70003,
+	 "PMU3: 3 anibi=%d, anibichan[anibi]=%d ,chan=%d\n"
+	},
+	{0x00a80002,
+	 "PMU3: Setting ATxDly for anib %x to %x\n"
+	},
+	{0x00a90000,
+	 "PMU: Error: CA Training Failed.\n"
+	},
+	{0x00aa0000,
+	 "PMU1: Writing MRs\n"
+	},
+	{0x00ab0000,
+	 "PMU4:Using MR12 values from 1D CA VREF training.\n"
+	},
+	{0x00ac0000,
+	 "PMU3:Writing all MRs to fsp 1\n"
+	},
+	{0x00ad0000,
+	 "PMU10:Lp4Quickboot mode.\n"
+	},
+	{0x00ae0000,
+	 "PMU3: Writing MRs\n"
+	},
+	{0x00af0001,
+	 "PMU10: Setting boot clock divider to %d\n"
+	},
+	{0x00b00000,
+	 "PMU3: Resetting DRAM\n"
+	},
+	{0x00b10000,
+	 "PMU3: setup for RCD initalization\n"
+	},
+	{0x00b20000,
+	 "PMU3: pmu_exit_SR from dev_init()\n"
+	},
+	{0x00b30000,
+	 "PMU3: initializing RCD\n"
+	},
+	{0x00b40000,
+	 "PMU10: **** Executing 2D Image ****\n"
+	},
+	{0x00b50001,
+	 "PMU10: **** Start DDR4 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x00b60001,
+	 "PMU10: **** Start DDR3 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x00b70001,
+	 "PMU10: **** Start LPDDR3 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x00b80001,
+	 "PMU10: **** Start LPDDR4 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x00b90000,
+	 "PMU: Error: Mismatched internal revision between DCCM and ICCM images\n"
+	},
+	{0x00ba0001,
+	 "PMU10: **** Testchip %d Specific Firmware ****\n"
+	},
+	{0x00bb0000,
+	 "PMU1: LRDIMM with EncodedCS mode, one DIMM\n"
+	},
+	{0x00bc0000,
+	 "PMU1: LRDIMM with EncodedCS mode, two DIMMs\n"
+	},
+	{0x00bd0000,
+	 "PMU1: RDIMM with EncodedCS mode, one DIMM\n"
+	},
+	{0x00be0000,
+	 "PMU2: Starting LRDIMM MREP training for all ranks\n"
+	},
+	{0x00bf0000,
+	 "PMU199: LRDIMM MREP training for all ranks completed\n"
+	},
+	{0x00c00000,
+	 "PMU2: Starting LRDIMM DWL training for all ranks\n"
+	},
+	{0x00c10000,
+	 "PMU199: LRDIMM DWL training for all ranks completed\n"
+	},
+	{0x00c20000,
+	 "PMU2: Starting LRDIMM MRD training for all ranks\n"
+	},
+	{0x00c30000,
+	 "PMU199: LRDIMM MRD training for all ranks completed\n"
+	},
+	{0x00c40000,
+	 "PMU2: Starting RXEN training for all ranks\n"
+	},
+	{0x00c50000,
+	 "PMU2: Starting write leveling fine delay training for all ranks\n"
+	},
+	{0x00c60000,
+	 "PMU2: Starting LRDIMM MWD training for all ranks\n"
+	},
+	{0x00c70000,
+	 "PMU199: LRDIMM MWD training for all ranks completed\n"
+	},
+	{0x00c80000,
+	 "PMU2: Starting write leveling fine delay training for all ranks\n"
+	},
+	{0x00c90000,
+	 "PMU2: Starting read deskew training\n"
+	},
+	{0x00ca0000,
+	 "PMU2: Starting SI friendly 1d RdDqs training for all ranks\n"
+	},
+	{0x00cb0000,
+	 "PMU2: Starting write leveling coarse delay training for all ranks\n"
+	},
+	{0x00cc0000,
+	 "PMU2: Starting 1d WrDq training for all ranks\n"
+	},
+	{0x00cd0000,
+	 "PMU2: Running DQS2DQ Oscillator for all ranks\n"
+	},
+	{0x00ce0000,
+	 "PMU2: Starting again read deskew training but with PRBS\n"
+	},
+	{0x00cf0000,
+	 "PMU2: Starting 1d RdDqs training for all ranks\n"
+	},
+	{0x00d00000,
+	 "PMU2: Starting again 1d WrDq training for all ranks\n"
+	},
+	{0x00d10000,
+	 "PMU2: Starting MaxRdLat training\n"
+	},
+	{0x00d20000,
+	 "PMU2: Starting 2d WrDq training for all ranks\n"
+	},
+	{0x00d30000,
+	 "PMU2: Starting 2d RdDqs training for all ranks\n"
+	},
+	{0x00d40002,
+	 "PMU3:read_fifo %x %x\n"
+	},
+	{0x00d50001,
+	 "PMU: Error: Invalid PhyDrvImpedance of 0x%x specified in message block.\n"
+	},
+	{0x00d60001,
+	 "PMU: Error: Invalid PhyOdtImpedance of 0x%x specified in message block.\n"
+	},
+	{0x00d70001,
+	 "PMU: Error: Invalid BPZNResVal of 0x%x specified in message block.\n"
+	},
+	{0x00d80005,
+	 "PMU3: fixRxEnBackOff csn:%d db:%d dn:%d bo:%d dly:%x\n"
+	},
+	{0x00d90001,
+	 "PMU3: fixRxEnBackOff dly:%x\n"
+	},
+	{0x00da0000,
+	 "PMU3: Entering setupPpt\n"
+	},
+	{0x00db0000,
+	 "PMU3: Start lp4PopulateHighLowBytes\n"
+	},
+	{0x00dc0002,
+	 "PMU3:Dbyte Detect: db%d received %x\n"
+	},
+	{0x00dd0002,
+	 "PMU3:getDqs2Dq read %x from dbyte %d\n"
+	},
+	{0x00de0002,
+	 "PMU3:getDqs2Dq(2) read %x from dbyte %d\n"
+	},
+	{0x00df0001,
+	 "PMU: Error: Dbyte %d read 0 from the DQS oscillator it is connected to\n"
+	},
+	{0x00e00002,
+	 "PMU4: Dbyte %d dqs2dq = %d/32 UI\n"
+	},
+	{0x00e10003,
+	 "PMU3:getDqs2Dq set dqs2dq:%d/32 ui (%d ps) from dbyte %d\n"
+	},
+	{0x00e20003,
+	 "PMU3: Setting coarse delay in AtxDly chiplet %d from 0x%02x to 0x%02x\n"
+	},
+	{0x00e30003,
+	 "PMU3: Clearing coarse delay in AtxDly chiplet %d from 0x%02x to 0x%02x\n"
+	},
+	{0x00e40000,
+	 "PMU3: Performing DDR4 geardown sync sequence\n"
+	},
+	{0x00e50000,
+	 "PMU1: Enter self refresh\n"
+	},
+	{0x00e60000,
+	 "PMU1: Exit self refresh\n"
+	},
+	{0x00e70000,
+	 "PMU: Error: No dbiEnable with lp4\n"
+	},
+	{0x00e80000,
+	 "PMU: Error: No dbiDisable with lp4\n"
+	},
+	{0x00e90001,
+	 "PMU1: DDR4 update Rx DBI Setting disable %d\n"
+	},
+	{0x00ea0001,
+	 "PMU1: DDR4 update 2nCk WPre Setting disable %d\n"
+	},
+	{0x00eb0005,
+	 "PMU1: read_delay: db%d lane%d delays[%2d] = 0x%02x (max 0x%02x)\n"
+	},
+	{0x00ec0004,
+	 "PMU1: write_delay: db%d lane%d delays[%2d] = 0x%04x\n"
+	},
+	{0x00ed0001,
+	 "PMU5: ID=%d -- db0  db1  db2  db3  db4  db5  db6  db7  db8  db9 --\n"
+	},
+	{0x00ee000b,
+	 "PMU5: [%d]:0x %04x %04x %04x %04x %04x %04x %04x %04x %04x %04x\n"
+	},
+	{0x00ef0003,
+	 "PMU2: dump delays - pstate=%d dimm=%d csn=%d\n"
+	},
+	{0x00f00000,
+	 "PMU3: Printing Mid-Training Delay Information\n"
+	},
+	{0x00f10001,
+	 "PMU5: CS%d <<KEY>> 0 TrainingCntr <<KEY>> coarse(15:10) fine(9:0)\n"
+	},
+	{0x00f20001,
+	 "PMU5: CS%d <<KEY>> 0 RxEnDly, 1 RxClkDly <<KEY>> coarse(10:6) fine(5:0)\n"
+	},
+	{0x00f30001,
+	 "PMU5: CS%d <<KEY>> 0 TxDqsDly, 1 TxDqDly <<KEY>> coarse(9:6) fine(5:0)\n"
+	},
+	{0x00f40001,
+	 "PMU5: CS%d <<KEY>> 0 RxPBDly <<KEY>> 1 Delay Unit ~= 7ps\n"
+	},
+	{0x00f50000,
+	 "PMU5: all CS <<KEY>> 0 DFIMRL <<KEY>> Units = DFI clocks\n"
+	},
+	{0x00f60000,
+	 "PMU5: all CS <<KEY>> VrefDACs <<KEY>> DAC(6:0)\n"
+	},
+	{0x00f70000,
+	 "PMU1: Set DMD in MR13 and wrDBI in MR3 for training\n"
+	},
+	{0x00f80000,
+	 "PMU: Error: getMaxRxen() failed to find largest rxen nibble delay\n"
+	},
+	{0x00f90003,
+	 "PMU2: getMaxRxen(): maxDly %d maxTg %d maxNib %d\n"
+	},
+	{0x00fa0003,
+	 "PMU2: getRankMaxRxen(): maxDly %d Tg %d maxNib %d\n"
+	},
+	{0x00fb0000,
+	 "PMU1: skipping CDD calculation in 2D image\n"
+	},
+	{0x00fc0001,
+	 "PMU3: Calculating CDDs for pstate %d\n"
+	},
+	{0x00fd0003,
+	 "PMU3: rxFromDly[%d][%d] = %d\n"
+	},
+	{0x00fe0003,
+	 "PMU3: rxToDly  [%d][%d] = %d\n"
+	},
+	{0x00ff0003,
+	 "PMU3: rxDly    [%d][%d] = %d\n"
+	},
+	{0x01000003,
+	 "PMU3: txDly    [%d][%d] = %d\n"
+	},
+	{0x01010003,
+	 "PMU3: allFine CDD_RR_%d_%d = %d\n"
+	},
+	{0x01020003,
+	 "PMU3: allFine CDD_WW_%d_%d = %d\n"
+	},
+	{0x01030003,
+	 "PMU3: CDD_RR_%d_%d = %d\n"
+	},
+	{0x01040003,
+	 "PMU3: CDD_WW_%d_%d = %d\n"
+	},
+	{0x01050003,
+	 "PMU3: allFine CDD_RW_%d_%d = %d\n"
+	},
+	{0x01060003,
+	 "PMU3: allFine CDD_WR_%d_%d = %d\n"
+	},
+	{0x01070003,
+	 "PMU3: CDD_RW_%d_%d = %d\n"
+	},
+	{0x01080003,
+	 "PMU3: CDD_WR_%d_%d = %d\n"
+	},
+	{0x01090004,
+	 "PMU3: F%dBC2x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010a0004,
+	 "PMU3: F%dBC3x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010b0004,
+	 "PMU3: F%dBC4x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010c0004,
+	 "PMU3: F%dBC5x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010d0004,
+	 "PMU3: F%dBC8x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010e0004,
+	 "PMU3: F%dBC9x_B%d_D%d = 0x%02x\n"
+	},
+	{0x010f0004,
+	 "PMU3: F%dBCAx_B%d_D%d = 0x%02x\n"
+	},
+	{0x01100004,
+	 "PMU3: F%dBCBx_B%d_D%d = 0x%02x\n"
+	},
+	{0x01110000,
+	 "PMU10: Entering context_switch_postamble\n"
+	},
+	{0x01120003,
+	 "PMU10: context_switch_postamble is enabled for DIMM %d, RC0A=0x%x, RC3x=0x%x\n"
+	},
+	{0x01130000,
+	 "PMU10: Setting bcw fspace 0\n"
+	},
+	{0x01140001,
+	 "PMU10: Sending BC0A = 0x%x\n"
+	},
+	{0x01150001,
+	 "PMU10: Sending BC6x = 0x%x\n"
+	},
+	{0x01160001,
+	 "PMU10: Sending RC0A = 0x%x\n"
+	},
+	{0x01170001,
+	 "PMU10: Sending RC3x = 0x%x\n"
+	},
+	{0x01180001,
+	 "PMU10: Sending RC0A = 0x%x\n"
+	},
+	{0x01190001,
+	 "PMU1: enter_lp3: DEBUG: pstate = %d\n"
+	},
+	{0x011a0001,
+	 "PMU1: enter_lp3: DEBUG: dfifreqxlat_pstate = %d\n"
+	},
+	{0x011b0001,
+	 "PMU1: enter_lp3: DEBUG: pllbypass = %d\n"
+	},
+	{0x011c0001,
+	 "PMU1: enter_lp3: DEBUG: forcecal = %d\n"
+	},
+	{0x011d0001,
+	 "PMU1: enter_lp3: DEBUG: pllmaxrange = 0x%x\n"
+	},
+	{0x011e0001,
+	 "PMU1: enter_lp3: DEBUG: dacval_out = 0x%x\n"
+	},
+	{0x011f0001,
+	 "PMU1: enter_lp3: DEBUG: pllctrl3 = 0x%x\n"
+	},
+	{0x01200000,
+	 "PMU3: Loading DRAM with BIOS supplied MR values and entering self refresh prior to exiting PMU code.\n"
+	},
+	{0x01210002,
+	 "PMU3: Setting DataBuffer function space of dimmcs 0x%02x to %d\n"
+	},
+	{0x01220002,
+	 "PMU4: Setting RCW FxRC%Xx = 0x%02x\n"
+	},
+	{0x01230002,
+	 "PMU4: Setting RCW FxRC%02x = 0x%02x\n"
+	},
+	{0x01240001,
+	 "PMU1: DDR4 update Rd Pre Setting disable %d\n"
+	},
+	{0x01250002,
+	 "PMU2: Setting BCW FxBC%Xx = 0x%02x\n"
+	},
+	{0x01260002,
+	 "PMU2: Setting BCW BC%02x = 0x%02x\n"
+	},
+	{0x01270002,
+	 "PMU2: Setting BCW PBA mode FxBC%Xx = 0x%02x\n"
+	},
+	{0x01280002,
+	 "PMU2: Setting BCW PBA mode BC%02x = 0x%02x\n"
+	},
+	{0x01290003,
+	 "PMU4: BCW value for dimm %d, fspace %d, addr 0x%04x\n"
+	},
+	{0x012a0002,
+	 "PMU4: DB %d, value 0x%02x\n"
+	},
+	{0x012b0000,
+	 "PMU6: WARNING MREP underflow, set to min value -2 coarse, 0 fine\n"
+	},
+	{0x012c0004,
+	 "PMU6: LRDIMM Writing final data buffer fine delay value nib %2d, trainDly %3d, fineDly code %2d, new MREP fine %2d\n"
+	},
+	{0x012d0003,
+	 "PMU6: LRDIMM Writing final data buffer fine delay value nib %2d, trainDly %3d, fineDly code %2d\n"
+	},
+	{0x012e0003,
+	 "PMU6: LRDIMM Writing data buffer fine delay type %d nib %2d, code %2d\n"
+	},
+	{0x012f0002,
+	 "PMU6: Writing final data buffer coarse delay value dbyte %2d, coarse = 0x%02x\n"
+	},
+	{0x01300003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x saved at CSR addr 0x%08x\n"
+	},
+	{0x01310003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x restored from CSR addr 0x%08x\n"
+	},
+	{0x01320003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x saved at CSR addr 0x%08x\n"
+	},
+	{0x01330003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x restored from CSR addr 0x%08x\n"
+	},
+	{0x01340001,
+	 "PMU3: Update BC00, BC01, BC02 for rank-dimm 0x%02x\n"
+	},
+	{0x01350000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F0RC00 -> F0RC0F\n"
+	},
+	{0x01360000,
+	 "PMU3: Disable parity in F0RC0E\n"
+	},
+	{0x01370000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F1RC00 -> F1RC05\n"
+	},
+	{0x01380000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F1RC1x -> F1RC9x\n"
+	},
+	{0x01390000,
+	 "PMU3: Writing D4 Data buffer Control words BC00 -> BC0E\n"
+	},
+	{0x013a0002,
+	 "PMU1: setAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x013b0002,
+	 "PMU1: restoreFromAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x013c0002,
+	 "PMU1: restoreAcsmFromAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x013d0002,
+	 "PMU2: Setting D3R RC%d = 0x%01x\n"
+	},
+	{0x013e0000,
+	 "PMU3: Writing D3 RDIMM RCD Control words RC0 -> RC11\n"
+	},
+	{0x013f0002,
+	 "PMU0: VrefDAC0/1 vddqStart %d dacToVddq %d\n"
+	},
+	{0x01400001,
+	 "PMU: Error: Messageblock phyVref=0x%x is above the limit for TSMC28's attenuated LPDDR4 receivers. Please see the pub databook\n"
+	},
+	{0x01410001,
+	 "PMU: Error: Messageblock phyVref=0x%x is above the limit for TSMC28's attenuated DDR4 receivers. Please see the pub databook\n"
+	},
+	{0x01420001,
+	 "PMU0: PHY VREF @ (%d/1000) VDDQ\n"
+	},
+	{0x01430002,
+	 "PMU0: initalizing phy vrefDacs to %d ExtVrefRange %x\n"
+	},
+	{0x01440002,
+	 "PMU0: initalizing global vref to %d range %d\n"
+	},
+	{0x01450002,
+	 "PMU4: Setting initial device vrefDQ for CS%d to MR6 = 0x%04x\n"
+	},
+	{0x01460003,
+	 "PMU1: In write_level_fine() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01470000,
+	 "PMU3: Fine write leveling hardware search increasing TxDqsDly until full bursts are seen\n"
+	},
+	{0x01480000,
+	 "PMU4: WL normalized pos   : ........................|........................\n"
+	},
+	{0x01490007,
+	 "PMU4: WL margin for nib %2d: %08x%08x%08x%08x%08x%08x\n"
+	},
+	{0x014a0000,
+	 "PMU4: WL normalized pos   : ........................|........................\n"
+	},
+	{0x014b0000,
+	 "PMU3: Exiting write leveling mode\n"
+	},
+	{0x014c0001,
+	 "PMU3: got %d for cl in load_wrlvl_acsm\n"
+	},
+	{0x014d0003,
+	 "PMU1: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x014e0003,
+	 "PMU3: left eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x014f0003,
+	 "PMU3: right eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01500004,
+	 "PMU3: eye center db:%d ln:%d dly:0x%x (maxdq:%x)\n"
+	},
+	{0x01510003,
+	 "PMU3: Wrote to TxDqDly db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01520003,
+	 "PMU3: Wrote to TxDqDly db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01530002,
+	 "PMU3: Coarse write leveling dbyte%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x01540002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x01550000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x01560001,
+	 "PMU3: got %d for cl in load_wrlvl_acsm\n"
+	},
+	{0x01570003,
+	 "PMU3: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01580003,
+	 "PMU3: left eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01590003,
+	 "PMU3: right eye edge search db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x015a0004,
+	 "PMU3: eye center db: %d ln: %d dly: 0x%x (maxdq: 0x%x)\n"
+	},
+	{0x015b0003,
+	 "PMU3: Wrote to TxDqDly db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x015c0003,
+	 "PMU3: Wrote to TxDqDly db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x015d0002,
+	 "PMU3: Coarse write leveling nibble%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x015e0002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x015f0000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x01600000,
+	 "PMU4: WL normalized pos   : ................................|................................\n"
+	},
+	{0x01610009,
+	 "PMU4: WL margin for nib %2d: %08x%08x%08x%08x%08x%08x%08x%08x\n"
+	},
+	{0x01620000,
+	 "PMU4: WL normalized pos   : ................................|................................\n"
+	},
+	{0x01630001,
+	 "PMU8: Adjust margin after WL coarse to be larger than %d\n"
+	},
+	{0x01640001,
+	 "PMU: Error: All margin after write leveling coarse are smaller than minMargin %d\n"
+	},
+	{0x01650002,
+	 "PMU8: Decrement nib %d TxDqsDly by %d fine step\n"
+	},
+	{0x01660003,
+	 "PMU3: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01670005,
+	 "PMU2: Write level: dbyte %d nib%d dq/dmbi %2d dqsfine 0x%04x dqDly 0x%04x\n"
+	},
+	{0x01680002,
+	 "PMU3: Coarse write leveling nibble%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x01690002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x016a0000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x016b0001,
+	 "PMU3: DWL delay = %d\n"
+	},
+	{0x016c0003,
+	 "PMU3: Errcnt for DWL nib %2d delay = %2d is %d\n"
+	},
+	{0x016d0002,
+	 "PMU3: DWL nibble %d sampled a 1 at delay %d\n"
+	},
+	{0x016e0003,
+	 "PMU3: DWL nibble %d passed at delay %d. Rising edge was at %d\n"
+	},
+	{0x016f0000,
+	 "PMU2: DWL did nto find a rising edge of memclk for all nibbles. Failing nibbles assumed to have rising edge close to fine delay 63\n"
+	},
+	{0x01700002,
+	 "PMU2:  Rising edge found in alias window, setting wrlvlDly for nibble %d = %d\n"
+	},
+	{0x01710002,
+	 "PMU: Error: Failed DWL for nib %d with %d one\n"
+	},
+	{0x01720003,
+	 "PMU2:  Rising edge not found in alias window with %d one, leaving wrlvlDly for nibble %d = %d\n"
+	},
+	{0x04000000,
+	 "PMU: Error:Mailbox Buffer Overflowed.\n"
+	},
+	{0x04010000,
+	 "PMU: Error:Mailbox Buffer Overflowed.\n"
+	},
+	{0x04020000,
+	 "PMU: ***** Assertion Error - terminating *****\n"
+	},
+	{0x04030002,
+	 "PMU1: swapByte db %d by %d\n"
+	},
+	{0x04040003,
+	 "PMU3: get_cmd_dly max(%d ps, %d memclk) = %d\n"
+	},
+	{0x04050002,
+	 "PMU0: Write CSR 0x%06x 0x%04x\n"
+	},
+	{0x04060002,
+	 "PMU0: hwt_init_ppgc_prbs(): Polynomial: %x, Deg: %d\n"
+	},
+	{0x04070001,
+	 "PMU: Error: acsm_set_cmd to non existent instruction address %d\n"
+	},
+	{0x04080001,
+	 "PMU: Error: acsm_set_cmd with unknown ddr cmd 0x%x\n"
+	},
+	{0x0409000c,
+	 "PMU1: acsm_addr %02x, acsm_flgs %04x, ddr_cmd %02x, cmd_dly %02x, ddr_addr %04x, ddr_bnk %02x, ddr_cs %02x, cmd_rcnt %02x, AcsmSeq0/1/2/3 %04x %04x %04x %04x\n"
+	},
+	{0x040a0000,
+	 "PMU: Error: Polling on ACSM done failed to complete in acsm_poll_done()...\n"
+	},
+	{0x040b0000,
+	 "PMU1: acsm RUN\n"
+	},
+	{0x040c0000,
+	 "PMU1: acsm STOPPED\n"
+	},
+	{0x040d0002,
+	 "PMU1: acsm_init: acsm_mode %04x mxrdlat %04x\n"
+	},
+	{0x040e0002,
+	 "PMU: Error: setAcsmCLCWL: cl and cwl must be each >= 2 and 5, resp. CL=%d CWL=%d\n"
+	},
+	{0x040f0002,
+	 "PMU: Error: setAcsmCLCWL: cl and cwl must be each >= 5. CL=%d CWL=%d\n"
+	},
+	{0x04100002,
+	 "PMU1: setAcsmCLCWL: CASL %04d WCASL %04d\n"
+	},
+	{0x04110001,
+	 "PMU: Error: Reserved value of register F0RC0F found in message block: 0x%04x\n"
+	},
+	{0x04120001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x04130001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x04140000,
+	 "PMU3: Entering Boot Freq Mode.\n"
+	},
+	{0x04150001,
+	 "PMU: Error: Boot clock divider setting of %d is too small\n"
+	},
+	{0x04160000,
+	 "PMU3: Exiting Boot Freq Mode.\n"
+	},
+	{0x04170002,
+	 "PMU3: Writing MR%d OP=%x\n"
+	},
+	{0x04180000,
+	 "PMU: Error: Delay too large in slomo\n"
+	},
+	{0x04190001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x041a0000,
+	 "PMU3: Enable Channel A\n"
+	},
+	{0x041b0000,
+	 "PMU3: Enable Channel B\n"
+	},
+	{0x041c0000,
+	 "PMU3: Enable All Channels\n"
+	},
+	{0x041d0002,
+	 "PMU2: Use PDA mode to set MR%d with value 0x%02x\n"
+	},
+	{0x041e0001,
+	 "PMU3: Written Vref with PDA to CS=0x%02x\n"
+	},
+	{0x041f0000,
+	 "PMU1: start_cal: DEBUG: setting CalRun to 1\n"
+	},
+	{0x04200000,
+	 "PMU1: start_cal: DEBUG: setting CalRun to 0\n"
+	},
+	{0x04210001,
+	 "PMU1: lock_pll_dll: DEBUG: pstate = %d\n"
+	},
+	{0x04220001,
+	 "PMU1: lock_pll_dll: DEBUG: dfifreqxlat_pstate = %d\n"
+	},
+	{0x04230001,
+	 "PMU1: lock_pll_dll: DEBUG: pllbypass = %d\n"
+	},
+	{0x04240001,
+	 "PMU3: SaveLcdlSeed: Saving seed %d\n"
+	},
+	{0x04250000,
+	 "PMU1: in phy_defaults()\n"
+	},
+	{0x04260003,
+	 "PMU3: ACXConf:%d MaxNumDbytes:%d NumDfi:%d\n"
+	},
+	{0x04270005,
+	 "PMU1: setAltAcsmCLCWL setting cl=%d cwl=%d\n"
+	},
+};
+
+const static struct phy_msg messages_2d[] = {
+	{0x00000001,
+	 "PMU0: Converting %d into an MR\n"
+	},
+	{0x00010003,
+	 "PMU DEBUG: vref_idx %d -= %d, range_idx = %d\n"
+	},
+	{0x00020002,
+	 "PMU0: vrefIdx. Passing range %d, remaining vrefidx = %d\n"
+	},
+	{0x00030002,
+	 "PMU0: VrefIdx %d -> MR[6:0] 0x%02x\n"
+	},
+	{0x00040001,
+	 "PMU0: Converting MR 0x%04x to vrefIdx\n"
+	},
+	{0x00050002,
+	 "PMU0: DAC %d Range %d\n"
+	},
+	{0x00060003,
+	 "PMU0: Range %d, Range_idx %d, vref_idx offset %d\n"
+	},
+	{0x00070002,
+	 "PMU0: MR 0x%04x -> VrefIdx %d\n"
+	},
+	{0x00080001,
+	 "PMU: Error: Illegal timing group number ,%d, in getPtrVrefDq\n"
+	},
+	{0x00090003,
+	 "PMU1: VrefDqR%dNib%d = %d\n"
+	},
+	{0x000a0003,
+	 "PMU0: VrefDqR%dNib%d = %d\n"
+	},
+	{0x000b0000,
+	 "PMU0: ----------------MARGINS-------\n"
+	},
+	{0x000c0002,
+	 "PMU0: R%d_RxClkDly_Margin = %d\n"
+	},
+	{0x000d0002,
+	 "PMU0: R%d_VrefDac_Margin = %d\n"
+	},
+	{0x000e0002,
+	 "PMU0: R%d_TxDqDly_Margin = %d\n"
+	},
+	{0x000f0002,
+	 "PMU0: R%d_DeviceVref_Margin = %d\n"
+	},
+	{0x00100000,
+	 "PMU0: -----------------------\n"
+	},
+	{0x00110003,
+	 "PMU0: eye %d's for all TG's is [%d ... %d]\n"
+	},
+	{0x00120000,
+	 "PMU0: ------- settingWeight -----\n"
+	},
+	{0x00130002,
+	 "PMU0: Weight %d @ Setting %d\n"
+	},
+	{0x0014001f,
+	 "PMU4: %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d >%3d< %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d %3d\n"
+	},
+	{0x00150002,
+	 "PMU3: Voltage Range = [%d, %d]\n"
+	},
+	{0x00160004,
+	 "PMU4: -- DB%d L%d -- centers: delay = %d, voltage = %d\n"
+	},
+	{0x00170001,
+	 "PMU5: <<KEY>> 0 TxDqDlyTg%d <<KEY>> coarse(6:6) fine(5:0)\n"
+	},
+	{0x00180001,
+	 "PMU5: <<KEY>> 0 messageBlock VrefDqR%d <<KEY>> MR6(6:0)\n"
+	},
+	{0x00190001,
+	 "PMU5: <<KEY>> 0 RxClkDlyTg%d <<KEY>> fine(5:0)\n"
+	},
+	{0x001a0003,
+	 "PMU0: tgToCsn: tg %d + 0x%04x -> csn %d\n"
+	},
+	{0x001b0002,
+	 "PMU: Error: LP4 rank %d cannot be mapped on tg %d\n"
+	},
+	{0x001c0002,
+	 "PMU3: Sending vref %d,  Mr = 0X%05x, to all devices\n"
+	},
+	{0x001d0004,
+	 "PMU4: -------- %dD Write Scanning TG %d (CS 0x%x) Lanes 0x%03x --------\n"
+	},
+	{0x001e0002,
+	 "PMU0: training lanes 0x%03x using lanes 0x%03x\n"
+	},
+	{0x001f0003,
+	 "PMU4: ------- 2D-DFE Read Scanning TG %d (CS 0x%x) Lanes 0x%03x -------\n"
+	},
+	{0x00200004,
+	 "PMU4: ------- %dD Read Scanning TG %d (CS 0x%x) Lanes 0x%03x -------\n"
+	},
+	{0x00210003,
+	 "PMU4: TG%d MR1[13,6,5]=0x%x MR6[13,9,8]=0x%x\n"
+	},
+	{0x00220002,
+	 "PMU0: training lanes 0x%03x using lanes 0x%03x\n"
+	},
+	{0x00230003,
+	 "PMU4: ------- 2D-DFE Read Scanning TG %d (CS 0x%x) Lanes 0x%03x -------\n"
+	},
+	{0x00240004,
+	 "PMU4: ------- %dD Read Scanning TG %d (CS 0x%x) Lanes 0x%03x -------\n"
+	},
+	{0x00250002,
+	 "PMU0: training lanes 0x%03x using lanes 0x%03x\n"
+	},
+	{0x00260002,
+	 "PMU3: Sending vref %d,  Mr = 0X%05x, to all devices\n"
+	},
+	{0x00270004,
+	 "PMU4: -------- %dD Write Scanning TG %d (CS 0x%x) Lanes 0x%03x --------\n"
+	},
+	{0x00280001,
+	 "PMU0: input %d\n"
+	},
+	{0x00290002,
+	 "PMU4: Programmed Voltage Search Range [%d, %d]\n"
+	},
+	{0x002a0002,
+	 "PMU3: Delay Stepsize = %d Fine, Voltage Stepsize = %d DAC\n"
+	},
+	{0x002b0002,
+	 "PMU4: Delay Weight = %d, Voltage Weight = %d\n"
+	},
+	{0x002c0003,
+	 "PMU0: raw 0x%x allFine %d incDec %d"
+	},
+	{0x002d0008,
+	 "PMU0: db%d l%d, voltage 0x%x (u_r %d) delay 0x%x (u_r %d) - lcdl %d mask 0x%x\n"
+	},
+	{0x002e0005,
+	 "PMU0: DB%d L%d, Eye %d, Seed = (0x%x, 0x%x)\n"
+	},
+	{0x002f0002,
+	 "PMU3: 2D Enables       : %d,                    1,                %d\n"
+	},
+	{0x00300006,
+	 "PMU3: 2D Delay   Ranges: OOPL[0x%04x,0x%04x], IP[0x%04x,0x%04x], OOPR[0x%04x,0x%04x]\n"
+	},
+	{0x00310002,
+	 "PMU3: 2D Voltage Search Range : [%d, %d]\n"
+	},
+	{0x00320002,
+	 "PMU4: Found Voltage Search Range [%d, %d]\n"
+	},
+	{0x00330002,
+	 "PMU0: User Weight = %d, Voltage Weight = %d\n"
+	},
+	{0x00340005,
+	 "PMU0: D(%d,%d) V(%d,%d | %d)\n"
+	},
+	{0x00350002,
+	 "PMU0: Norm Weight = %d, Voltage Weight = %d\n"
+	},
+	{0x00360002,
+	 "PMU0: seed 0 = (%d,%d) (center)\n"
+	},
+	{0x00370003,
+	 "PMU0: seed 1 = (%d,%d).min edge at idx %d\n"
+	},
+	{0x00380003,
+	 "PMU0: seed 2 = (%d,%d) max edge at idx %d\n"
+	},
+	{0x00390003,
+	 "PMU0: Search point %d = (%d,%d)\n"
+	},
+	{0x003a0005,
+	 "PMU0: YMARGIN: ^ %d, - %d, v %d. rate %d = %d\n"
+	},
+	{0x003b0003,
+	 "PMU0: XMARGIN: center %d, edge %d. = %d\n"
+	},
+	{0x003c0002,
+	 "PMU0: ----------- weighting (%d,%d) ----------------\n"
+	},
+	{0x003d0003,
+	 "PMU0: X margin - L %d R %d - Min %d\n"
+	},
+	{0x003e0003,
+	 "PMU0: Y margin - L %d R %d - Min %d\n"
+	},
+	{0x003f0003,
+	 "PMU0: center (%d,%d) weight = %d\n"
+	},
+	{0x00400003,
+	 "PMU4: Eye argest blob area %d from %d to %d\n"
+	},
+	{0x00410002,
+	 "PMU0: Compute centroid min_x %d max_x %d\n"
+	},
+	{0x00420003,
+	 "PMU0: Compute centroid sumLnDlyWidth %d sumLnVrefWidth %d sumLnWidht %d\n"
+	},
+	{0x00430000,
+	 "PMU: Error: No passing region found for 1 or more lanes. Set hdtCtrl=4 to see passing regions\n"
+	},
+	{0x00440003,
+	 "PMU0: Centroid ( %d, %d ) found with sumLnWidht %d\n"
+	},
+	{0x00450003,
+	 "PMU0: Optimal allFine Center ( %d + %d ,%d )\n"
+	},
+	{0x00460003,
+	 "PMU3: point %d starting at (%d,%d)\n"
+	},
+	{0x00470002,
+	 "PMU0: picking left (%d > %d)\n"
+	},
+	{0x00480002,
+	 "PMU0: picking right (%d > %d)\n"
+	},
+	{0x00490002,
+	 "PMU0: picking down (%d > %d)\n"
+	},
+	{0x004a0002,
+	 "PMU0: picking up (%d > %d)\n"
+	},
+	{0x004b0009,
+	 "PMU3: new center @ (%3d, %3d). Moved (%2i, %2i) -- L %d, R %d, C %d, U %d, D %d\n"
+	},
+	{0x004c0003,
+	 "PMU3: cordNum %d imporved %d to %d\n"
+	},
+	{0x004d0000,
+	 "PMU: Error: No passing region found for 1 or more lanes. Set hdtCtrl=4 to see passing regions\n"
+	},
+	{0x004e0004,
+	 "PMU0: Optimal allFine Center ( %d + %d ,%d ), found with weight %d.\n"
+	},
+	{0x004f0003,
+	 "PMU0: merging lanes=%d..%d, centerMerge_t %d\n"
+	},
+	{0x00500001,
+	 "PMU0: laneVal %d is disable\n"
+	},
+	{0x00510002,
+	 "PMU0: checking common center %d against current center %d\n"
+	},
+	{0x00520001,
+	 "PMU: Error: getCompoundEye Called on lane%d eye with non-compatible centers\n"
+	},
+	{0x00530001,
+	 "PMU0: laneItr %d is disable\n"
+	},
+	{0x00540005,
+	 "PMU0: lane %d, data_idx %d, offset_idx %d, = [%d..%d]\n"
+	},
+	{0x00550003,
+	 "PMU0: lane %d, data_idx %d, offset_idx %d, offset_idx out of range!\n"
+	},
+	{0x00560003,
+	 "PMU0: mergeData[%d] = max_v_low %d, min_v_high %d\n"
+	},
+	{0x00570005,
+	 "PMU1: writing merged center (%d,%d) back to dataBlock[%d]. doDelay %d, doVoltage %d\n"
+	},
+	{0x00580005,
+	 "PMU0: applying relative (%i,%i) back to dataBlock[%d]. doDelay %d, doVoltage %d\n"
+	},
+	{0x00590002,
+	 "PMU0: drvstren %x is idx %d in the table\n"
+	},
+	{0x005a0000,
+	 "PMU4: truncating FFE drive strength search range. Out of drive strengths to check.\n"
+	},
+	{0x005b0002,
+	 "PMU5: Weak 1 changed to pull-up %5d ohms, pull-down %5d ohms\n"
+	},
+	{0x005c0002,
+	 "PMU5: Weak 0 changed to pull-up %5d ohms, pull-down %5d ohms\n"
+	},
+	{0x005d0003,
+	 "PMU0: dlyMargin L %02d R %02d, min %02d\n"
+	},
+	{0x005e0003,
+	 "PMU0: vrefMargin T %02d B %02d, min %02d\n"
+	},
+	{0x005f0002,
+	 "PMU3: new minimum VrefMargin (%d < %d) recorded\n"
+	},
+	{0x00600002,
+	 "PMU3: new minimum DlyMargin (%d < %d) recorded\n"
+	},
+	{0x00610000,
+	 "PMU0: RX finding the per-nibble, per-tg rxClkDly values\n"
+	},
+	{0x00620003,
+	 "PMU0: Merging collected eyes [%d..%d) and analyzing for nibble %d's optimal rxClkDly\n"
+	},
+	{0x00630002,
+	 "PMU0: -- centers: delay = %d, voltage = %d\n"
+	},
+	{0x00640003,
+	 "PMU0: dumping optimized eye -- centers: delay = %d (%d), voltage = %d\n"
+	},
+	{0x00650000,
+	 "PMU0: TX optimizing txDqDelays\n"
+	},
+	{0x00660001,
+	 "PMU3: Analyzing collected eye %d for a lane's optimal TxDqDly\n"
+	},
+	{0x00670001,
+	 "PMU0: eye-lane %d is disable\n"
+	},
+	{0x00680000,
+	 "PMU0: TX optimizing device voltages\n"
+	},
+	{0x00690002,
+	 "PMU0: Merging collected eyes [%d..%d) and analyzing for optimal device txVref\n"
+	},
+	{0x006a0002,
+	 "PMU0: -- centers: delay = %d, voltage = %d\n"
+	},
+	{0x006b0003,
+	 "PMU0: dumping optimized eye -- centers: delay = %d (%d), voltage = %d\n"
+	},
+	{0x006c0000,
+	 "PMU4: VrefDac (compound all TG) Bottom Top -> Center\n"
+	},
+	{0x006d0005,
+	 "PMU4: DB%d L%d   %3d   %3d  ->  %3d (DISCONNECTED)\n"
+	},
+	{0x006e0005,
+	 "PMU4: DB%d L%d   %3d   %3d  ->  %3d\n"
+	},
+	{0x006f0005,
+	 "PMU0: writing rxClkDelay for tg%d db%1d nib%1d to 0x%02x from eye[%02d] (DISCONNECTED)\n"
+	},
+	{0x00700003,
+	 "PMU: Error: Dbyte %d nibble %d's optimal rxClkDly of 0x%x is out of bounds\n"
+	},
+	{0x00710005,
+	 "PMU0: writing rxClkDelay for tg%d db%1d nib%1d to 0x%02x from eye[%02d]\n"
+	},
+	{0x00720005,
+	 "PMU0: tx voltage for tg%2d nib%2d to %3d (%d) from eye[%02d]\n"
+	},
+	{0x00730001,
+	 "PMU0: vref Sum = %d\n"
+	},
+	{0x00740004,
+	 "PMU0: tx voltage total is %d/%d -> %d -> %d\n"
+	},
+	{0x00750007,
+	 "PMU0: writing txDqDelay for tg%1d db%1d ln%1d to  0x%02x (%d coarse, %d fine) from eye[%02d] (DISCONNECTED)\n"
+	},
+	{0x00760003,
+	 "PMU: Error: Dbyte %d lane %d's optimal txDqDly of 0x%x is out of bounds\n"
+	},
+	{0x00770007,
+	 "PMU0: writing txDqDelay for tg%1d db%1d l%1d to  0x%02x (%d coarse, %d fine) from eye[%02d]\n"
+	},
+	{0x00780002,
+	 "PMU0: %d (0=tx, 1=rx) TgMask for this simulation: %x\n"
+	},
+	{0x00790001,
+	 "PMU0: eye-byte %d is disable\n"
+	},
+	{0x007a0001,
+	 "PMU0: eye-lane %d is disable\n"
+	},
+	{0x007b0003,
+	 "PMU10: Start d4_2d_lrdimm_rx_dfe dimm %d nbTap %d biasStepMode %d\n"
+	},
+	{0x007c0001,
+	 "PMU10: DB DFE feature not fully supported, F2BCEx value is 0x%02x\n"
+	},
+	{0x007d0001,
+	 "PMU10: DB DFE feature fully supported, F2BCEx value is 0x%02x\n"
+	},
+	{0x007e0002,
+	 "PMU8: Start d4_2d_lrdimm_rx_dfe for tap %d biasStepInc %d\n"
+	},
+	{0x007f0001,
+	 "PMU7: Start d4_2d_lrdimm_rx_dfe tapCoff 0x%0x\n"
+	},
+	{0x00800003,
+	 "PMU6: d4_2d_lrdimm_rx_dfe db %d lane %d area %d\n"
+	},
+	{0x00810004,
+	 "PMU7: d4_2d_lrdimm_rx_dfe db %d lane %d max area %d best bias 0x%0x\n"
+	},
+	{0x00820001,
+	 "PMU0: eye-lane %d is disable\n"
+	},
+	{0x00830003,
+	 "PMU5: Setting 0x%x improved rank weight (%4d < %4d)\n"
+	},
+	{0x00840001,
+	 "PMU4: Setting 0x%x still optimal\n"
+	},
+	{0x00850002,
+	 "PMU5: ---- Training CS%d MR%d DRAM Equalization ----\n"
+	},
+	{0x00860001,
+	 "PMU0: eye-lane %d is disable\n"
+	},
+	{0x00870003,
+	 "PMU0: eye %d weight %d allTgWeight %d\n"
+	},
+	{0x00880002,
+	 "PMU5: FFE figure of merit improved from %d to %d\n"
+	},
+	{0x00890002,
+	 "PMU: Error: LP4 rank %d cannot be mapped on tg %d\n"
+	},
+	{0x008a0000,
+	 "PMU4: Adjusting vrefDac0 for just 1->x transitions\n"
+	},
+	{0x008b0000,
+	 "PMU4: Adjusting vrefDac1 for just 0->x transitions\n"
+	},
+	{0x008c0001,
+	 "PMU5: Strong 1, pull-up %d ohms\n"
+	},
+	{0x008d0001,
+	 "PMU5: Strong 0, pull-down %d ohms\n"
+	},
+	{0x008e0000,
+	 "PMU4: Enabling weak drive strengths (FFE)\n"
+	},
+	{0x008f0000,
+	 "PMU5: Changing all weak driver strengths\n"
+	},
+	{0x00900000,
+	 "PMU5: Finalizing weak drive strengths\n"
+	},
+	{0x00910000,
+	 "PMU4: retraining with optimal drive strength settings\n"
+	},
+	{0x00920002,
+	 "PMU0: targeting CsX = %d and CsY = %d\n"
+	},
+	{0x00930001,
+	 "PMU1:prbsGenCtl:%x\n"
+	},
+	{0x00940000,
+	 "PMU1: loading 2D acsm sequence\n"
+	},
+	{0x00950000,
+	 "PMU1: loading 1D acsm sequence\n"
+	},
+	{0x00960002,
+	 "PMU3: %d memclocks @ %d to get half of 300ns\n"
+	},
+	{0x00970000,
+	 "PMU: Error: User requested MPR read pattern for read DQS training in DDR3 Mode\n"
+	},
+	{0x00980000,
+	 "PMU3: Running 1D search for left eye edge\n"
+	},
+	{0x00990001,
+	 "PMU1: In Phase Left Edge Search cs %d\n"
+	},
+	{0x009a0001,
+	 "PMU1: Out of Phase Left Edge Search cs %d\n"
+	},
+	{0x009b0000,
+	 "PMU3: Running 1D search for right eye edge\n"
+	},
+	{0x009c0001,
+	 "PMU1: In Phase Right Edge Search cs %d\n"
+	},
+	{0x009d0001,
+	 "PMU1: Out of Phase Right Edge Search cs %d\n"
+	},
+	{0x009e0001,
+	 "PMU1: mxRdLat training pstate %d\n"
+	},
+	{0x009f0001,
+	 "PMU1: mxRdLat search for cs %d\n"
+	},
+	{0x00a00001,
+	 "PMU0: MaxRdLat non consistent DtsmLoThldXingInd 0x%03x\n"
+	},
+	{0x00a10003,
+	 "PMU4: CS %d Dbyte %d worked with DFIMRL = %d DFICLKs\n"
+	},
+	{0x00a20004,
+	 "PMU3: MaxRdLat Read Lane err mask for csn %d, DFIMRL %2d DFIClks, dbyte %d = 0x%03x\n"
+	},
+	{0x00a30003,
+	 "PMU3: MaxRdLat Read Lane err mask for csn %d DFIMRL %2d, All dbytes = 0x%03x\n"
+	},
+	{0x00a40001,
+	 "PMU: Error: CS%d failed to find a DFIMRL setting that worked for all bytes during MaxRdLat training\n"
+	},
+	{0x00a50002,
+	 "PMU3: Smallest passing DFIMRL for all dbytes in CS%d = %d DFIClks\n"
+	},
+	{0x00a60000,
+	 "PMU: Error: No passing DFIMRL value found for any chip select during MaxRdLat training\n"
+	},
+	{0x00a70003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly passing region is too small (width = %d)\n"
+	},
+	{0x00a80006,
+	 "PMU10: Adjusting rxclkdly db %d nib %d from %d+%d=%d->%d\n"
+	},
+	{0x00a90000,
+	 "PMU4: TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x00aa0005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00ab0002,
+	 "PMU2: TXDQ delayLeft[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00ac0004,
+	 "PMU2: TXDQ delayLeft[%2d] = %3d oopScaled = %3d selectOop %d\n"
+	},
+	{0x00ad0002,
+	 "PMU2: TXDQ delayRight[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00ae0004,
+	 "PMU2: TXDQ delayRight[%2d] = %3d oopScaled = %3d selectOop %d\n"
+	},
+	{0x00af0003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly passing region is too small (width = %d)\n"
+	},
+	{0x00b00000,
+	 "PMU4: TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x00b10002,
+	 "PMU4: DB %d Lane %d: (DISCONNECTED)\n"
+	},
+	{0x00b20005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00b30002,
+	 "PMU3: Running 1D search csn %d for DM Right/NotLeft(%d) eye edge\n"
+	},
+	{0x00b40002,
+	 "PMU3: WrDq DM byte%2d with Errcnt %d\n"
+	},
+	{0x00b50002,
+	 "PMU3: WrDq DM byte%2d avgDly 0x%04x\n"
+	},
+	{0x00b60002,
+	 "PMU1: WrDq DM byte%2d with Errcnt %d\n"
+	},
+	{0x00b70001,
+	 "PMU: Error: Dbyte %d txDqDly DM training did not start inside the eye\n"
+	},
+	{0x00b80000,
+	 "PMU4: DM TxDqDly Passing Regions (EyeLeft EyeRight -> EyeCenter) Units=1/32 UI\n"
+	},
+	{0x00b90002,
+	 "PMU4: DB %d Lane %d: (DISCONNECTED)\n"
+	},
+	{0x00ba0005,
+	 "PMU4: DB %d Lane %d: %3d %3d -> %3d\n"
+	},
+	{0x00bb0003,
+	 "PMU: Error: Dbyte %d lane %d txDqDly DM passing region is too small (width = %d)\n"
+	},
+	{0x00bc0004,
+	 "PMU3: Errcnt for MRD/MWD search nib %2d delay = (%d, 0x%02x) = %d\n"
+	},
+	{0x00bd0000,
+	 "PMU3: Precharge all open banks\n"
+	},
+	{0x00be0002,
+	 "PMU: Error: Dbyte %d nibble %d found mutliple working coarse delay setting for MRD/MWD\n"
+	},
+	{0x00bf0000,
+	 "PMU4: MRD Passing Regions (coarseVal, fineLeft fineRight -> fineCenter)\n"
+	},
+	{0x00c00000,
+	 "PMU4: MWD Passing Regions (coarseVal, fineLeft fineRight -> fineCenter)\n"
+	},
+	{0x00c10004,
+	 "PMU10: Warning: DB %d nibble %d has multiple working coarse delays, %d and %d, choosing the smaller delay\n"
+	},
+	{0x00c20003,
+	 "PMU: Error: Dbyte %d nibble %d MRD/MWD passing region is too small (width = %d)\n"
+	},
+	{0x00c30006,
+	 "PMU4: DB %d nibble %d: %3d, %3d %3d -> %3d\n"
+	},
+	{0x00c40002,
+	 "PMU1: Start MRD/nMWD %d for csn %d\n"
+	},
+	{0x00c50002,
+	 "PMU2: RXDQS delayLeft[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00c60006,
+	 "PMU2: RXDQS delayLeft[%2d] = %3d delayOop[%2d] = %3d OopScaled %4d, selectOop %d\n"
+	},
+	{0x00c70002,
+	 "PMU2: RXDQS delayRight[%2d] = %3d (DISCONNECTED)\n"
+	},
+	{0x00c80006,
+	 "PMU2: RXDQS delayRight[%2d] = %3d delayOop[%2d] = %4d OopScaled %4d, selectOop %d\n"
+	},
+	{0x00c90000,
+	 "PMU4: RxClkDly Passing Regions (EyeLeft EyeRight -> EyeCenter)\n"
+	},
+	{0x00ca0002,
+	 "PMU4: DB %d nibble %d: (DISCONNECTED)\n"
+	},
+	{0x00cb0005,
+	 "PMU4: DB %d nibble %d: %3d %3d -> %3d\n"
+	},
+	{0x00cc0003,
+	 "PMU: Error: Dbyte %d nibble %d rxClkDly passing region is too small (width = %d)\n"
+	},
+	{0x00cd0002,
+	 "PMU0: goodbar = %d for RDWR_BLEN %d\n"
+	},
+	{0x00ce0001,
+	 "PMU3: RxClkDly = %d\n"
+	},
+	{0x00cf0005,
+	 "PMU0: db %d l %d absLane %d -> bottom %d top %d\n"
+	},
+	{0x00d00009,
+	 "PMU3: BYTE %d - %3d %3d %3d %3d %3d %3d %3d %3d\n"
+	},
+	{0x00d10002,
+	 "PMU: Error: dbyte %d lane %d's per-lane vrefDAC's had no passing region\n"
+	},
+	{0x00d20004,
+	 "PMU0: db%d l%d - %d %d\n"
+	},
+	{0x00d30002,
+	 "PMU0: goodbar = %d for RDWR_BLEN %d\n"
+	},
+	{0x00d40004,
+	 "PMU3: db%d l%d saw %d issues at rxClkDly %d\n"
+	},
+	{0x00d50003,
+	 "PMU3: db%d l%d first saw a pass->fail edge at rxClkDly %d\n"
+	},
+	{0x00d60002,
+	 "PMU3: lane %d PBD = %d\n"
+	},
+	{0x00d70003,
+	 "PMU3: db%d l%d first saw a DBI pass->fail edge at rxClkDly %d\n"
+	},
+	{0x00d80003,
+	 "PMU2: db%d l%d already passed rxPBD = %d\n"
+	},
+	{0x00d90003,
+	 "PMU0: db%d l%d, PBD = %d\n"
+	},
+	{0x00da0002,
+	 "PMU: Error: dbyte %d lane %d failed read deskew\n"
+	},
+	{0x00db0003,
+	 "PMU0: db%d l%d, inc PBD = %d\n"
+	},
+	{0x00dc0003,
+	 "PMU1: Running lane deskew on pstate %d csn %d rdDBIEn %d\n"
+	},
+	{0x00dd0000,
+	 "PMU: Error: Read deskew training has been requested, but csrMajorModeDbyte[2] is set\n"
+	},
+	{0x00de0002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00df0002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00e00001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D3U Type\n"
+	},
+	{0x00e10001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D3R Type\n"
+	},
+	{0x00e20001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4U Type\n"
+	},
+	{0x00e30001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4R Type\n"
+	},
+	{0x00e40001,
+	 "PMU: Error: Wrong PMU image loaded. message Block DramType = 0x%02x, but image built for D4LR Type\n"
+	},
+	{0x00e50000,
+	 "PMU: Error: Both 2t timing mode and ddr4 geardown mode specified in the messageblock's PhyCfg and MR3 fields. Only one can be enabled\n"
+	},
+	{0x00e60003,
+	 "PMU10: PHY TOTALS - NUM_DBYTES %d NUM_NIBBLES %d NUM_ANIBS %d\n"
+	},
+	{0x00e70006,
+	 "PMU10: CSA=0x%02x, CSB=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, MMISC=%d DRAMFreq=%dMT DramType=LPDDR3\n"
+	},
+	{0x00e80006,
+	 "PMU10: CSA=0x%02x, CSB=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, MMISC=%d DRAMFreq=%dMT DramType=LPDDR4\n"
+	},
+	{0x00e90008,
+	 "PMU10: CS=0x%02x, TSTAGES=0x%04x, HDTOUT=%d, 2T=%d, MMISC=%d AddrMirror=%d DRAMFreq=%dMT DramType=%d\n"
+	},
+	{0x00ea0004,
+	 "PMU10: Pstate%d MR0=0x%04x MR1=0x%04x MR2=0x%04x\n"
+	},
+	{0x00eb0008,
+	 "PMU10: Pstate%d MRS MR0=0x%04x MR1=0x%04x MR2=0x%04x MR3=0x%04x MR4=0x%04x MR5=0x%04x MR6=0x%04x\n"
+	},
+	{0x00ec0005,
+	 "PMU10: Pstate%d MRS MR1_A0=0x%04x MR2_A0=0x%04x MR3_A0=0x%04x MR11_A0=0x%04x\n"
+	},
+	{0x00ed0000,
+	 "PMU10: UseBroadcastMR set. All ranks and channels use MRXX_A0 for MR settings.\n"
+	},
+	{0x00ee0005,
+	 "PMU10: Pstate%d MRS MR01_A0=0x%02x MR02_A0=0x%02x MR03_A0=0x%02x MR11_A0=0x%02x\n"
+	},
+	{0x00ef0005,
+	 "PMU10: Pstate%d MRS MR12_A0=0x%02x MR13_A0=0x%02x MR14_A0=0x%02x MR22_A0=0x%02x\n"
+	},
+	{0x00f00005,
+	 "PMU10: Pstate%d MRS MR01_A1=0x%02x MR02_A1=0x%02x MR03_A1=0x%02x MR11_A1=0x%02x\n"
+	},
+	{0x00f10005,
+	 "PMU10: Pstate%d MRS MR12_A1=0x%02x MR13_A1=0x%02x MR14_A1=0x%02x MR22_A1=0x%02x\n"
+	},
+	{0x00f20005,
+	 "PMU10: Pstate%d MRS MR01_B0=0x%02x MR02_B0=0x%02x MR03_B0=0x%02x MR11_B0=0x%02x\n"
+	},
+	{0x00f30005,
+	 "PMU10: Pstate%d MRS MR12_B0=0x%02x MR13_B0=0x%02x MR14_B0=0x%02x MR22_B0=0x%02x\n"
+	},
+	{0x00f40005,
+	 "PMU10: Pstate%d MRS MR01_B1=0x%02x MR02_B1=0x%02x MR03_B1=0x%02x MR11_B1=0x%02x\n"
+	},
+	{0x00f50005,
+	 "PMU10: Pstate%d MRS MR12_B1=0x%02x MR13_B1=0x%02x MR14_B1=0x%02x MR22_B1=0x%02x\n"
+	},
+	{0x00f60002,
+	 "PMU1: AcsmOdtCtrl%02d 0x%02x\n"
+	},
+	{0x00f70002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00f80002,
+	 "PMU1: AcsmCsMapCtrl%02d 0x%04x\n"
+	},
+	{0x00f90000,
+	 "PMU1: HwtCAMode set\n"
+	},
+	{0x00fa0001,
+	 "PMU3: DDR4 infinite preamble enter/exit mode %d\n"
+	},
+	{0x00fb0002,
+	 "PMU1: In rxenb_train() csn=%d pstate=%d\n"
+	},
+	{0x00fc0000,
+	 "PMU3: Finding DQS falling edge\n"
+	},
+	{0x00fd0000,
+	 "PMU3: Searching for DDR3/LPDDR3/LPDDR4 read preamble\n"
+	},
+	{0x00fe0009,
+	 "PMU3: dtsm fails Even Nibbles : %2x %2x %2x %2x %2x %2x %2x %2x %2x\n"
+	},
+	{0x00ff0009,
+	 "PMU3: dtsm fails Odd  Nibbles : %2x %2x %2x %2x %2x %2x %2x %2x %2x\n"
+	},
+	{0x01000002,
+	 "PMU3: Preamble search pass=%d anyfail=%d\n"
+	},
+	{0x01010000,
+	 "PMU: Error: RxEn training preamble not found\n"
+	},
+	{0x01020000,
+	 "PMU3: Found DQS pre-amble\n"
+	},
+	{0x01030001,
+	 "PMU: Error: Dbyte %d couldn't find the rising edge of DQS during RxEn Training\n"
+	},
+	{0x01040000,
+	 "PMU3: RxEn aligning to first rising edge of burst\n"
+	},
+	{0x01050001,
+	 "PMU3: Decreasing RxEn delay by %d fine step to allow full capture of reads\n"
+	},
+	{0x01060001,
+	 "PMU3: MREP Delay = %d\n"
+	},
+	{0x01070003,
+	 "PMU3: Errcnt for MREP nib %2d delay = %2d is %d\n"
+	},
+	{0x01080002,
+	 "PMU3: MREP nibble %d sampled a 1 at data buffer delay %d\n"
+	},
+	{0x01090002,
+	 "PMU3: MREP nibble %d saw a 0 to 1 transition at data buffer delay %d\n"
+	},
+	{0x010a0000,
+	 "PMU2:  MREP did not find a 0 to 1 transition for all nibbles. Failing nibbles assumed to have rising edge close to fine delay 63\n"
+	},
+	{0x010b0002,
+	 "PMU2:  Rising edge found in alias window, setting rxDly for nibble %d = %d\n"
+	},
+	{0x010c0002,
+	 "PMU: Error: Failed MREP for nib %d with %d one\n"
+	},
+	{0x010d0003,
+	 "PMU2:  Rising edge not found in alias window with %d one, leaving rxDly for nibble %d = %d\n"
+	},
+	{0x010e0002,
+	 "PMU3: Training DIMM %d CSn %d\n"
+	},
+	{0x010f0001,
+	 "PMU3: exitCAtrain_lp3 cs 0x%x\n"
+	},
+	{0x01100001,
+	 "PMU3: enterCAtrain_lp3 cs 0x%x\n"
+	},
+	{0x01110001,
+	 "PMU3: CAtrain_switchmsb_lp3 cs 0x%x\n"
+	},
+	{0x01120001,
+	 "PMU3: CATrain_rdwr_lp3 looking for pattern %x\n"
+	},
+	{0x01130000,
+	 "PMU3: exitCAtrain_lp4\n"
+	},
+	{0x01140001,
+	 "PMU3: DEBUG enterCAtrain_lp4 1: cs 0x%x\n"
+	},
+	{0x01150001,
+	 "PMU3: DEBUG enterCAtrain_lp4 3: Put dbyte %d in async mode\n"
+	},
+	{0x01160000,
+	 "PMU3: DEBUG enterCAtrain_lp4 5: Send MR13 to turn on CA training\n"
+	},
+	{0x01170003,
+	 "PMU3: DEBUG enterCAtrain_lp4 7: idx = %d vref = %x mr12 = %x\n"
+	},
+	{0x01180001,
+	 "PMU3: CATrain_rdwr_lp4 looking for pattern %x\n"
+	},
+	{0x01190004,
+	 "PMU3: Phase %d CAreadbackA db:%d %x xo:%x\n"
+	},
+	{0x011a0005,
+	 "PMU3: DEBUG lp4SetCatrVref 1: cs=%d chan=%d mr12=%x vref=%d.%d%%\n"
+	},
+	{0x011b0003,
+	 "PMU3: DEBUG lp4SetCatrVref 3: mr12 = %x send vref= %x to db=%d\n"
+	},
+	{0x011c0000,
+	 "PMU10:Optimizing vref\n"
+	},
+	{0x011d0004,
+	 "PMU4:mr12:%2x cs:%d chan %d r:%4x\n"
+	},
+	{0x011e0005,
+	 "PMU3: i:%2d bstr:%2d bsto:%2d st:%d r:%d\n"
+	},
+	{0x011f0002,
+	 "Failed to find sufficient CA Vref Passing Region for CS %d ch. %d\n"
+	},
+	{0x01200005,
+	 "PMU3:Found %d.%d%% MR12:%x for cs:%d chan %d\n"
+	},
+	{0x01210002,
+	 "PMU3:Calculated %d for AtxImpedence from acx %d.\n"
+	},
+	{0x01220000,
+	 "PMU3:CA Odt impedence ==0.  Use default vref.\n"
+	},
+	{0x01230003,
+	 "PMU3:Calculated %d.%d%% for Vref MR12=0x%x.\n"
+	},
+	{0x01240000,
+	 "PMU3: CAtrain_lp\n"
+	},
+	{0x01250000,
+	 "PMU3: CAtrain Begins.\n"
+	},
+	{0x01260001,
+	 "PMU3: CAtrain_lp testing dly %d\n"
+	},
+	{0x01270001,
+	 "PMU5: CA bitmap dump for cs %x\n"
+	},
+	{0x01280001,
+	 "PMU5: CAA%d "
+	},
+	{0x01290001, "%02x"
+	},
+	{0x012a0000, "\n"
+	},
+	{0x012b0001,
+	 "PMU5: CAB%d "
+	},
+	{0x012c0001, "%02x"
+	},
+	{0x012d0000, "\n"
+	},
+	{0x012e0003,
+	 "PMU3: anibi=%d, anibichan[anibi]=%d ,chan=%d\n"
+	},
+	{0x012f0001, "%02x"
+	},
+	{0x01300001, "\nPMU3:Raw CA setting :%x"
+	},
+	{0x01310002, "\nPMU3:ATxDly setting:%x margin:%d\n"
+	},
+	{0x01320002, "\nPMU3:InvClk ATxDly setting:%x margin:%d\n"
+	},
+	{0x01330000, "\nPMU3:No Range found!\n"
+	},
+	{0x01340003,
+	 "PMU3: 2 anibi=%d, anibichan[anibi]=%d ,chan=%d"
+	},
+	{0x01350002, "\nPMU3: no neg clock => CA setting anib=%d, :%d\n"
+	},
+	{0x01360001,
+	 "PMU3:Normal margin:%d\n"
+	},
+	{0x01370001,
+	 "PMU3:Inverted margin:%d\n"
+	},
+	{0x01380000,
+	 "PMU3:Using Inverted clock\n"
+	},
+	{0x01390000,
+	 "PMU3:Using normal clk\n"
+	},
+	{0x013a0003,
+	 "PMU3: 3 anibi=%d, anibichan[anibi]=%d ,chan=%d\n"
+	},
+	{0x013b0002,
+	 "PMU3: Setting ATxDly for anib %x to %x\n"
+	},
+	{0x013c0000,
+	 "PMU: Error: CA Training Failed.\n"
+	},
+	{0x013d0000,
+	 "PMU1: Writing MRs\n"
+	},
+	{0x013e0000,
+	 "PMU4:Using MR12 values from 1D CA VREF training.\n"
+	},
+	{0x013f0000,
+	 "PMU3:Writing all MRs to fsp 1\n"
+	},
+	{0x01400000,
+	 "PMU10:Lp4Quickboot mode.\n"
+	},
+	{0x01410000,
+	 "PMU3: Writing MRs\n"
+	},
+	{0x01420001,
+	 "PMU10: Setting boot clock divider to %d\n"
+	},
+	{0x01430000,
+	 "PMU3: Resetting DRAM\n"
+	},
+	{0x01440000,
+	 "PMU3: setup for RCD initalization\n"
+	},
+	{0x01450000,
+	 "PMU3: pmu_exit_SR from dev_init()\n"
+	},
+	{0x01460000,
+	 "PMU3: initializing RCD\n"
+	},
+	{0x01470000,
+	 "PMU10: **** Executing 2D Image ****\n"
+	},
+	{0x01480001,
+	 "PMU10: **** Start DDR4 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x01490001,
+	 "PMU10: **** Start DDR3 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x014a0001,
+	 "PMU10: **** Start LPDDR3 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x014b0001,
+	 "PMU10: **** Start LPDDR4 Training. PMU Firmware Revision 0x%04x ****\n"
+	},
+	{0x014c0000,
+	 "PMU: Error: Mismatched internal revision between DCCM and ICCM images\n"
+	},
+	{0x014d0001,
+	 "PMU10: **** Testchip %d Specific Firmware ****\n"
+	},
+	{0x014e0000,
+	 "PMU1: LRDIMM with EncodedCS mode, one DIMM\n"
+	},
+	{0x014f0000,
+	 "PMU1: LRDIMM with EncodedCS mode, two DIMMs\n"
+	},
+	{0x01500000,
+	 "PMU1: RDIMM with EncodedCS mode, one DIMM\n"
+	},
+	{0x01510000,
+	 "PMU2: Starting LRDIMM MREP training for all ranks\n"
+	},
+	{0x01520000,
+	 "PMU199: LRDIMM MREP training for all ranks completed\n"
+	},
+	{0x01530000,
+	 "PMU2: Starting LRDIMM DWL training for all ranks\n"
+	},
+	{0x01540000,
+	 "PMU199: LRDIMM DWL training for all ranks completed\n"
+	},
+	{0x01550000,
+	 "PMU2: Starting LRDIMM MRD training for all ranks\n"
+	},
+	{0x01560000,
+	 "PMU199: LRDIMM MRD training for all ranks completed\n"
+	},
+	{0x01570000,
+	 "PMU2: Starting RXEN training for all ranks\n"
+	},
+	{0x01580000,
+	 "PMU2: Starting write leveling fine delay training for all ranks\n"
+	},
+	{0x01590000,
+	 "PMU2: Starting LRDIMM MWD training for all ranks\n"
+	},
+	{0x015a0000,
+	 "PMU199: LRDIMM MWD training for all ranks completed\n"
+	},
+	{0x015b0000,
+	 "PMU2: Starting write leveling fine delay training for all ranks\n"
+	},
+	{0x015c0000,
+	 "PMU2: Starting read deskew training\n"
+	},
+	{0x015d0000,
+	 "PMU2: Starting SI friendly 1d RdDqs training for all ranks\n"
+	},
+	{0x015e0000,
+	 "PMU2: Starting write leveling coarse delay training for all ranks\n"
+	},
+	{0x015f0000,
+	 "PMU2: Starting 1d WrDq training for all ranks\n"
+	},
+	{0x01600000,
+	 "PMU2: Running DQS2DQ Oscillator for all ranks\n"
+	},
+	{0x01610000,
+	 "PMU2: Starting again read deskew training but with PRBS\n"
+	},
+	{0x01620000,
+	 "PMU2: Starting 1d RdDqs training for all ranks\n"
+	},
+	{0x01630000,
+	 "PMU2: Starting again 1d WrDq training for all ranks\n"
+	},
+	{0x01640000,
+	 "PMU2: Starting MaxRdLat training\n"
+	},
+	{0x01650000,
+	 "PMU2: Starting 2d WrDq training for all ranks\n"
+	},
+	{0x01660000,
+	 "PMU2: Starting 2d RdDqs training for all ranks\n"
+	},
+	{0x01670002,
+	 "PMU3:read_fifo %x %x\n"
+	},
+	{0x01680001,
+	 "PMU: Error: Invalid PhyDrvImpedance of 0x%x specified in message block.\n"
+	},
+	{0x01690001,
+	 "PMU: Error: Invalid PhyOdtImpedance of 0x%x specified in message block.\n"
+	},
+	{0x016a0001,
+	 "PMU: Error: Invalid BPZNResVal of 0x%x specified in message block.\n"
+	},
+	{0x016b0005,
+	 "PMU3: fixRxEnBackOff csn:%d db:%d dn:%d bo:%d dly:%x\n"
+	},
+	{0x016c0001,
+	 "PMU3: fixRxEnBackOff dly:%x\n"
+	},
+	{0x016d0000,
+	 "PMU3: Entering setupPpt\n"
+	},
+	{0x016e0000,
+	 "PMU3: Start lp4PopulateHighLowBytes\n"
+	},
+	{0x016f0002,
+	 "PMU3:Dbyte Detect: db%d received %x\n"
+	},
+	{0x01700002,
+	 "PMU3:getDqs2Dq read %x from dbyte %d\n"
+	},
+	{0x01710002,
+	 "PMU3:getDqs2Dq(2) read %x from dbyte %d\n"
+	},
+	{0x01720001,
+	 "PMU: Error: Dbyte %d read 0 from the DQS oscillator it is connected to\n"
+	},
+	{0x01730002,
+	 "PMU4: Dbyte %d dqs2dq = %d/32 UI\n"
+	},
+	{0x01740003,
+	 "PMU3:getDqs2Dq set dqs2dq:%d/32 ui (%d ps) from dbyte %d\n"
+	},
+	{0x01750003,
+	 "PMU3: Setting coarse delay in AtxDly chiplet %d from 0x%02x to 0x%02x\n"
+	},
+	{0x01760003,
+	 "PMU3: Clearing coarse delay in AtxDly chiplet %d from 0x%02x to 0x%02x\n"
+	},
+	{0x01770000,
+	 "PMU3: Performing DDR4 geardown sync sequence\n"
+	},
+	{0x01780000,
+	 "PMU1: Enter self refresh\n"
+	},
+	{0x01790000,
+	 "PMU1: Exit self refresh\n"
+	},
+	{0x017a0000,
+	 "PMU: Error: No dbiEnable with lp4\n"
+	},
+	{0x017b0000,
+	 "PMU: Error: No dbiDisable with lp4\n"
+	},
+	{0x017c0001,
+	 "PMU1: DDR4 update Rx DBI Setting disable %d\n"
+	},
+	{0x017d0001,
+	 "PMU1: DDR4 update 2nCk WPre Setting disable %d\n"
+	},
+	{0x017e0005,
+	 "PMU1: read_delay: db%d lane%d delays[%2d] = 0x%02x (max 0x%02x)\n"
+	},
+	{0x017f0004,
+	 "PMU1: write_delay: db%d lane%d delays[%2d] = 0x%04x\n"
+	},
+	{0x01800001,
+	 "PMU5: ID=%d -- db0  db1  db2  db3  db4  db5  db6  db7  db8  db9 --\n"
+	},
+	{0x0181000b,
+	 "PMU5: [%d]:0x %04x %04x %04x %04x %04x %04x %04x %04x %04x %04x\n"
+	},
+	{0x01820003,
+	 "PMU2: dump delays - pstate=%d dimm=%d csn=%d\n"
+	},
+	{0x01830000,
+	 "PMU3: Printing Mid-Training Delay Information\n"
+	},
+	{0x01840001,
+	 "PMU5: CS%d <<KEY>> 0 TrainingCntr <<KEY>> coarse(15:10) fine(9:0)\n"
+	},
+	{0x01850001,
+	 "PMU5: CS%d <<KEY>> 0 RxEnDly, 1 RxClkDly <<KEY>> coarse(10:6) fine(5:0)\n"
+	},
+	{0x01860001,
+	 "PMU5: CS%d <<KEY>> 0 TxDqsDly, 1 TxDqDly <<KEY>> coarse(9:6) fine(5:0)\n"
+	},
+	{0x01870001,
+	 "PMU5: CS%d <<KEY>> 0 RxPBDly <<KEY>> 1 Delay Unit ~= 7ps\n"
+	},
+	{0x01880000,
+	 "PMU5: all CS <<KEY>> 0 DFIMRL <<KEY>> Units = DFI clocks\n"
+	},
+	{0x01890000,
+	 "PMU5: all CS <<KEY>> VrefDACs <<KEY>> DAC(6:0)\n"
+	},
+	{0x018a0000,
+	 "PMU1: Set DMD in MR13 and wrDBI in MR3 for training\n"
+	},
+	{0x018b0000,
+	 "PMU: Error: getMaxRxen() failed to find largest rxen nibble delay\n"
+	},
+	{0x018c0003,
+	 "PMU2: getMaxRxen(): maxDly %d maxTg %d maxNib %d\n"
+	},
+	{0x018d0003,
+	 "PMU2: getRankMaxRxen(): maxDly %d Tg %d maxNib %d\n"
+	},
+	{0x018e0000,
+	 "PMU1: skipping CDD calculation in 2D image\n"
+	},
+	{0x018f0001,
+	 "PMU3: Calculating CDDs for pstate %d\n"
+	},
+	{0x01900003,
+	 "PMU3: rxFromDly[%d][%d] = %d\n"
+	},
+	{0x01910003,
+	 "PMU3: rxToDly  [%d][%d] = %d\n"
+	},
+	{0x01920003,
+	 "PMU3: rxDly    [%d][%d] = %d\n"
+	},
+	{0x01930003,
+	 "PMU3: txDly    [%d][%d] = %d\n"
+	},
+	{0x01940003,
+	 "PMU3: allFine CDD_RR_%d_%d = %d\n"
+	},
+	{0x01950003,
+	 "PMU3: allFine CDD_WW_%d_%d = %d\n"
+	},
+	{0x01960003,
+	 "PMU3: CDD_RR_%d_%d = %d\n"
+	},
+	{0x01970003,
+	 "PMU3: CDD_WW_%d_%d = %d\n"
+	},
+	{0x01980003,
+	 "PMU3: allFine CDD_RW_%d_%d = %d\n"
+	},
+	{0x01990003,
+	 "PMU3: allFine CDD_WR_%d_%d = %d\n"
+	},
+	{0x019a0003,
+	 "PMU3: CDD_RW_%d_%d = %d\n"
+	},
+	{0x019b0003,
+	 "PMU3: CDD_WR_%d_%d = %d\n"
+	},
+	{0x019c0004,
+	 "PMU3: F%dBC2x_B%d_D%d = 0x%02x\n"
+	},
+	{0x019d0004,
+	 "PMU3: F%dBC3x_B%d_D%d = 0x%02x\n"
+	},
+	{0x019e0004,
+	 "PMU3: F%dBC4x_B%d_D%d = 0x%02x\n"
+	},
+	{0x019f0004,
+	 "PMU3: F%dBC5x_B%d_D%d = 0x%02x\n"
+	},
+	{0x01a00004,
+	 "PMU3: F%dBC8x_B%d_D%d = 0x%02x\n"
+	},
+	{0x01a10004,
+	 "PMU3: F%dBC9x_B%d_D%d = 0x%02x\n"
+	},
+	{0x01a20004,
+	 "PMU3: F%dBCAx_B%d_D%d = 0x%02x\n"
+	},
+	{0x01a30004,
+	 "PMU3: F%dBCBx_B%d_D%d = 0x%02x\n"
+	},
+	{0x01a40000,
+	 "PMU10: Entering context_switch_postamble\n"
+	},
+	{0x01a50003,
+	 "PMU10: context_switch_postamble is enabled for DIMM %d, RC0A=0x%x, RC3x=0x%x\n"
+	},
+	{0x01a60000,
+	 "PMU10: Setting bcw fspace 0\n"
+	},
+	{0x01a70001,
+	 "PMU10: Sending BC0A = 0x%x\n"
+	},
+	{0x01a80001,
+	 "PMU10: Sending BC6x = 0x%x\n"
+	},
+	{0x01a90001,
+	 "PMU10: Sending RC0A = 0x%x\n"
+	},
+	{0x01aa0001,
+	 "PMU10: Sending RC3x = 0x%x\n"
+	},
+	{0x01ab0001,
+	 "PMU10: Sending RC0A = 0x%x\n"
+	},
+	{0x01ac0001,
+	 "PMU1: enter_lp3: DEBUG: pstate = %d\n"
+	},
+	{0x01ad0001,
+	 "PMU1: enter_lp3: DEBUG: dfifreqxlat_pstate = %d\n"
+	},
+	{0x01ae0001,
+	 "PMU1: enter_lp3: DEBUG: pllbypass = %d\n"
+	},
+	{0x01af0001,
+	 "PMU1: enter_lp3: DEBUG: forcecal = %d\n"
+	},
+	{0x01b00001,
+	 "PMU1: enter_lp3: DEBUG: pllmaxrange = 0x%x\n"
+	},
+	{0x01b10001,
+	 "PMU1: enter_lp3: DEBUG: dacval_out = 0x%x\n"
+	},
+	{0x01b20001,
+	 "PMU1: enter_lp3: DEBUG: pllctrl3 = 0x%x\n"
+	},
+	{0x01b30000,
+	 "PMU3: Loading DRAM with BIOS supplied MR values and entering self refresh prior to exiting PMU code.\n"
+	},
+	{0x01b40002,
+	 "PMU3: Setting DataBuffer function space of dimmcs 0x%02x to %d\n"
+	},
+	{0x01b50002,
+	 "PMU4: Setting RCW FxRC%Xx = 0x%02x\n"
+	},
+	{0x01b60002,
+	 "PMU4: Setting RCW FxRC%02x = 0x%02x\n"
+	},
+	{0x01b70001,
+	 "PMU1: DDR4 update Rd Pre Setting disable %d\n"
+	},
+	{0x01b80002,
+	 "PMU2: Setting BCW FxBC%Xx = 0x%02x\n"
+	},
+	{0x01b90002,
+	 "PMU2: Setting BCW BC%02x = 0x%02x\n"
+	},
+	{0x01ba0002,
+	 "PMU2: Setting BCW PBA mode FxBC%Xx = 0x%02x\n"
+	},
+	{0x01bb0002,
+	 "PMU2: Setting BCW PBA mode BC%02x = 0x%02x\n"
+	},
+	{0x01bc0003,
+	 "PMU4: BCW value for dimm %d, fspace %d, addr 0x%04x\n"
+	},
+	{0x01bd0002,
+	 "PMU4: DB %d, value 0x%02x\n"
+	},
+	{0x01be0000,
+	 "PMU6: WARNING MREP underflow, set to min value -2 coarse, 0 fine\n"
+	},
+	{0x01bf0004,
+	 "PMU6: LRDIMM Writing final data buffer fine delay value nib %2d, trainDly %3d, fineDly code %2d, new MREP fine %2d\n"
+	},
+	{0x01c00003,
+	 "PMU6: LRDIMM Writing final data buffer fine delay value nib %2d, trainDly %3d, fineDly code %2d\n"
+	},
+	{0x01c10003,
+	 "PMU6: LRDIMM Writing data buffer fine delay type %d nib %2d, code %2d\n"
+	},
+	{0x01c20002,
+	 "PMU6: Writing final data buffer coarse delay value dbyte %2d, coarse = 0x%02x\n"
+	},
+	{0x01c30003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x saved at CSR addr 0x%08x\n"
+	},
+	{0x01c40003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x restored from CSR addr 0x%08x\n"
+	},
+	{0x01c50003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x saved at CSR addr 0x%08x\n"
+	},
+	{0x01c60003,
+	 "PMU4: data 0x%04x at MB addr 0x%08x restored from CSR addr 0x%08x\n"
+	},
+	{0x01c70001,
+	 "PMU3: Update BC00, BC01, BC02 for rank-dimm 0x%02x\n"
+	},
+	{0x01c80000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F0RC00 -> F0RC0F\n"
+	},
+	{0x01c90000,
+	 "PMU3: Disable parity in F0RC0E\n"
+	},
+	{0x01ca0000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F1RC00 -> F1RC05\n"
+	},
+	{0x01cb0000,
+	 "PMU3: Writing D4 RDIMM RCD Control words F1RC1x -> F1RC9x\n"
+	},
+	{0x01cc0000,
+	 "PMU3: Writing D4 Data buffer Control words BC00 -> BC0E\n"
+	},
+	{0x01cd0002,
+	 "PMU1: setAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x01ce0002,
+	 "PMU1: restoreFromAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x01cf0002,
+	 "PMU1: restoreAcsmFromAltCL Sending MR0 0x%x cl=%d\n"
+	},
+	{0x01d00002,
+	 "PMU2: Setting D3R RC%d = 0x%01x\n"
+	},
+	{0x01d10000,
+	 "PMU3: Writing D3 RDIMM RCD Control words RC0 -> RC11\n"
+	},
+	{0x01d20002,
+	 "PMU0: VrefDAC0/1 vddqStart %d dacToVddq %d\n"
+	},
+	{0x01d30001,
+	 "PMU: Error: Messageblock phyVref=0x%x is above the limit for TSMC28's attenuated LPDDR4 receivers. Please see the pub databook\n"
+	},
+	{0x01d40001,
+	 "PMU: Error: Messageblock phyVref=0x%x is above the limit for TSMC28's attenuated DDR4 receivers. Please see the pub databook\n"
+	},
+	{0x01d50001,
+	 "PMU0: PHY VREF @ (%d/1000) VDDQ\n"
+	},
+	{0x01d60002,
+	 "PMU0: initalizing phy vrefDacs to %d ExtVrefRange %x\n"
+	},
+	{0x01d70002,
+	 "PMU0: initalizing global vref to %d range %d\n"
+	},
+	{0x01d80002,
+	 "PMU4: Setting initial device vrefDQ for CS%d to MR6 = 0x%04x\n"
+	},
+	{0x01d90003,
+	 "PMU1: In write_level_fine() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01da0000,
+	 "PMU3: Fine write leveling hardware search increasing TxDqsDly until full bursts are seen\n"
+	},
+	{0x01db0000,
+	 "PMU4: WL normalized pos   : ........................|........................\n"
+	},
+	{0x01dc0007,
+	 "PMU4: WL margin for nib %2d: %08x%08x%08x%08x%08x%08x\n"
+	},
+	{0x01dd0000,
+	 "PMU4: WL normalized pos   : ........................|........................\n"
+	},
+	{0x01de0000,
+	 "PMU3: Exiting write leveling mode\n"
+	},
+	{0x01df0001,
+	 "PMU3: got %d for cl in load_wrlvl_acsm\n"
+	},
+	{0x01e00003,
+	 "PMU1: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01e10003,
+	 "PMU3: left eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01e20003,
+	 "PMU3: right eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01e30004,
+	 "PMU3: eye center db:%d ln:%d dly:0x%x (maxdq:%x)\n"
+	},
+	{0x01e40003,
+	 "PMU3: Wrote to TxDqDly db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01e50003,
+	 "PMU3: Wrote to TxDqDly db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01e60002,
+	 "PMU3: Coarse write leveling dbyte%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x01e70002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x01e80000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x01e90001,
+	 "PMU3: got %d for cl in load_wrlvl_acsm\n"
+	},
+	{0x01ea0003,
+	 "PMU3: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01eb0003,
+	 "PMU3: left eye edge search db:%d ln:%d dly:0x%x\n"
+	},
+	{0x01ec0003,
+	 "PMU3: right eye edge search db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x01ed0004,
+	 "PMU3: eye center db: %d ln: %d dly: 0x%x (maxdq: 0x%x)\n"
+	},
+	{0x01ee0003,
+	 "PMU3: Wrote to TxDqDly db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x01ef0003,
+	 "PMU3: Wrote to TxDqDly db: %d ln: %d dly: 0x%x\n"
+	},
+	{0x01f00002,
+	 "PMU3: Coarse write leveling nibble%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x01f10002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x01f20000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x01f30000,
+	 "PMU4: WL normalized pos   : ................................|................................\n"
+	},
+	{0x01f40009,
+	 "PMU4: WL margin for nib %2d: %08x%08x%08x%08x%08x%08x%08x%08x\n"
+	},
+	{0x01f50000,
+	 "PMU4: WL normalized pos   : ................................|................................\n"
+	},
+	{0x01f60001,
+	 "PMU8: Adjust margin after WL coarse to be larger than %d\n"
+	},
+	{0x01f70001,
+	 "PMU: Error: All margin after write leveling coarse are smaller than minMargin %d\n"
+	},
+	{0x01f80002,
+	 "PMU8: Decrement nib %d TxDqsDly by %d fine step\n"
+	},
+	{0x01f90003,
+	 "PMU3: In write_level_coarse() csn=%d dimm=%d pstate=%d\n"
+	},
+	{0x01fa0005,
+	 "PMU2: Write level: dbyte %d nib%d dq/dmbi %2d dqsfine 0x%04x dqDly 0x%04x\n"
+	},
+	{0x01fb0002,
+	 "PMU3: Coarse write leveling nibble%2d is still failing for TxDqsDly=0x%04x\n"
+	},
+	{0x01fc0002,
+	 "PMU4: Coarse write leveling iteration %d saw %d data miscompares across the entire phy\n"
+	},
+	{0x01fd0000,
+	 "PMU: Error: Failed write leveling coarse\n"
+	},
+	{0x01fe0001,
+	 "PMU3: DWL delay = %d\n"
+	},
+	{0x01ff0003,
+	 "PMU3: Errcnt for DWL nib %2d delay = %2d is %d\n"
+	},
+	{0x02000002,
+	 "PMU3: DWL nibble %d sampled a 1 at delay %d\n"
+	},
+	{0x02010003,
+	 "PMU3: DWL nibble %d passed at delay %d. Rising edge was at %d\n"
+	},
+	{0x02020000,
+	 "PMU2: DWL did nto find a rising edge of memclk for all nibbles. Failing nibbles assumed to have rising edge close to fine delay 63\n"
+	},
+	{0x02030002,
+	 "PMU2:  Rising edge found in alias window, setting wrlvlDly for nibble %d = %d\n"
+	},
+	{0x02040002,
+	 "PMU: Error: Failed DWL for nib %d with %d one\n"
+	},
+	{0x02050003,
+	 "PMU2:  Rising edge not found in alias window with %d one, leaving wrlvlDly for nibble %d = %d\n"
+	},
+	{0x04000000,
+	 "PMU: Error:Mailbox Buffer Overflowed.\n"
+	},
+	{0x04010000,
+	 "PMU: Error:Mailbox Buffer Overflowed.\n"
+	},
+	{0x04020000,
+	 "PMU: ***** Assertion Error - terminating *****\n"
+	},
+	{0x04030002,
+	 "PMU1: swapByte db %d by %d\n"
+	},
+	{0x04040003,
+	 "PMU3: get_cmd_dly max(%d ps, %d memclk) = %d\n"
+	},
+	{0x04050002,
+	 "PMU0: Write CSR 0x%06x 0x%04x\n"
+	},
+	{0x04060002,
+	 "PMU0: hwt_init_ppgc_prbs(): Polynomial: %x, Deg: %d\n"
+	},
+	{0x04070001,
+	 "PMU: Error: acsm_set_cmd to non existent instruction address %d\n"
+	},
+	{0x04080001,
+	 "PMU: Error: acsm_set_cmd with unknown ddr cmd 0x%x\n"
+	},
+	{0x0409000c,
+	 "PMU1: acsm_addr %02x, acsm_flgs %04x, ddr_cmd %02x, cmd_dly %02x, ddr_addr %04x, ddr_bnk %02x, ddr_cs %02x, cmd_rcnt %02x, AcsmSeq0/1/2/3 %04x %04x %04x %04x\n"
+	},
+	{0x040a0000,
+	 "PMU: Error: Polling on ACSM done failed to complete in acsm_poll_done()...\n"
+	},
+	{0x040b0000,
+	 "PMU1: acsm RUN\n"
+	},
+	{0x040c0000,
+	 "PMU1: acsm STOPPED\n"
+	},
+	{0x040d0002,
+	 "PMU1: acsm_init: acsm_mode %04x mxrdlat %04x\n"
+	},
+	{0x040e0002,
+	 "PMU: Error: setAcsmCLCWL: cl and cwl must be each >= 2 and 5, resp. CL=%d CWL=%d\n"
+	},
+	{0x040f0002,
+	 "PMU: Error: setAcsmCLCWL: cl and cwl must be each >= 5. CL=%d CWL=%d\n"
+	},
+	{0x04100002,
+	 "PMU1: setAcsmCLCWL: CASL %04d WCASL %04d\n"
+	},
+	{0x04110001,
+	 "PMU: Error: Reserved value of register F0RC0F found in message block: 0x%04x\n"
+	},
+	{0x04120001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x04130001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x04140000,
+	 "PMU3: Entering Boot Freq Mode.\n"
+	},
+	{0x04150001,
+	 "PMU: Error: Boot clock divider setting of %d is too small\n"
+	},
+	{0x04160000,
+	 "PMU3: Exiting Boot Freq Mode.\n"
+	},
+	{0x04170002,
+	 "PMU3: Writing MR%d OP=%x\n"
+	},
+	{0x04180000,
+	 "PMU: Error: Delay too large in slomo\n"
+	},
+	{0x04190001,
+	 "PMU3: Written MRS to CS=0x%02x\n"
+	},
+	{0x041a0000,
+	 "PMU3: Enable Channel A\n"
+	},
+	{0x041b0000,
+	 "PMU3: Enable Channel B\n"
+	},
+	{0x041c0000,
+	 "PMU3: Enable All Channels\n"
+	},
+	{0x041d0002,
+	 "PMU2: Use PDA mode to set MR%d with value 0x%02x\n"
+	},
+	{0x041e0001,
+	 "PMU3: Written Vref with PDA to CS=0x%02x\n"
+	},
+	{0x041f0000,
+	 "PMU1: start_cal: DEBUG: setting CalRun to 1\n"
+	},
+	{0x04200000,
+	 "PMU1: start_cal: DEBUG: setting CalRun to 0\n"
+	},
+	{0x04210001,
+	 "PMU1: lock_pll_dll: DEBUG: pstate = %d\n"
+	},
+	{0x04220001,
+	 "PMU1: lock_pll_dll: DEBUG: dfifreqxlat_pstate = %d\n"
+	},
+	{0x04230001,
+	 "PMU1: lock_pll_dll: DEBUG: pllbypass = %d\n"
+	},
+	{0x04240001,
+	 "PMU3: SaveLcdlSeed: Saving seed %d\n"
+	},
+	{0x04250000,
+	 "PMU1: in phy_defaults()\n"
+	},
+	{0x04260003,
+	 "PMU3: ACXConf:%d MaxNumDbytes:%d NumDfi:%d\n"
+	},
+	{0x04270005,
+	 "PMU1: setAltAcsmCLCWL setting cl=%d cwl=%d\n"
+	},
+};
+#endif /* DEBUG */
+#endif
diff --git a/drivers/nxp/ddr/phy-gen2/phy.c b/drivers/nxp/ddr/phy-gen2/phy.c
new file mode 100644
index 0000000..9c84b00
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/phy.c
@@ -0,0 +1,2669 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include "csr.h"
+#include <ddr.h>
+#include "ddr4fw.h"
+#include <drivers/delay_timer.h>
+#ifdef NXP_WARM_BOOT
+#include <fspi_api.h>
+#endif
+#include "input.h"
+#include <lib/mmio.h>
+#include <lib/utils.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#ifdef DDR_PHY_DEBUG
+#include "messages.h"
+#endif
+#ifdef NXP_WARM_BOOT
+#include "phy.h"
+#endif
+#include "pie.h"
+
+#define TIMEOUTDEFAULT 500
+#define MAP_PHY_ADDR(pstate, n, instance, offset, c) \
+		((((pstate * n) + instance + c) << 12) + offset)
+
+static uint32_t map_phy_addr_space(uint32_t addr)
+{
+	/* 23 bit addressing */
+	uint32_t pstate =     (addr & U(0x700000)) >> 20U; /* bit 22:20 */
+	uint32_t block_type = (addr & U(0x0f0000)) >> 16U; /* bit 19:16 */
+	uint32_t instance =   (addr & U(0x00f000)) >> 12U; /* bit 15:12 */
+	uint32_t offset =     (addr & U(0x000fff));        /* bit 11:0 */
+
+	switch (block_type) {
+	case 0x0: /* 0x0 : ANIB */
+		return MAP_PHY_ADDR(pstate, 12, instance, offset, 0);
+	case 0x1: /* 0x1 : DBYTE */
+		return MAP_PHY_ADDR(pstate, 10, instance, offset, 0x30);
+	case 0x2: /* 0x2 : MASTER */
+		return MAP_PHY_ADDR(pstate, 1, 0, offset, 0x58);
+	case 0x4: /* 0x4 : ACSM */
+		return MAP_PHY_ADDR(pstate, 1, 0, offset, 0x5c);
+	case 0x5: /* 0x5 : μCTL Memory */
+		return MAP_PHY_ADDR(pstate, 0, instance, offset, 0x60);
+	case 0x7: /* 0x7 : PPGC */
+		return MAP_PHY_ADDR(pstate, 0, 0, offset, 0x68);
+	case 0x9: /* 0x9 : INITENG */
+		return MAP_PHY_ADDR(pstate, 1, 0, offset, 0x69);
+	case 0xc: /* 0xC : DRTUB */
+		return MAP_PHY_ADDR(pstate, 0, 0, offset, 0x6d);
+	case 0xd: /* 0xD : APB Only */
+		return MAP_PHY_ADDR(pstate, 0, 0, offset, 0x6e);
+	default:
+		printf("ERR: Invalid block_type = 0x%x\n", block_type);
+		return 0;
+	}
+}
+
+static inline uint16_t *phy_io_addr(void *phy, uint32_t addr)
+{
+	return phy + (map_phy_addr_space(addr) << 2);
+}
+
+static inline void phy_io_write16(uint16_t *phy, uint32_t addr, uint16_t data)
+{
+	mmio_write_16((uintptr_t)phy_io_addr(phy, addr), data);
+#ifdef DEBUG_PHY_IO
+	printf("0x%06x,0x%x\n", addr, data);
+#endif
+}
+
+static inline uint16_t phy_io_read16(uint16_t *phy, uint32_t addr)
+{
+	uint16_t reg = mmio_read_16((uintptr_t) phy_io_addr(phy, addr));
+
+#ifdef DEBUG_PHY_IO
+	printf("R: 0x%06x,0x%x\n", addr, reg);
+#endif
+
+	return reg;
+}
+
+#ifdef NXP_APPLY_MAX_CDD
+
+#define CDD_VAL_READ_ADDR (0x054012)
+#define CDD_DATA_LEN    (60)
+
+static void read_phy_reg(uint16_t *phy, uint32_t addr,
+		uint16_t *buf, uint32_t len)
+{
+	uint32_t i = 0U;
+
+	for (i = 0U; i < len/2; i++) {
+		buf[i] = phy_io_read16(phy, (addr + i));
+	}
+}
+
+static uint32_t findrank(uint32_t cs_in_use)
+{
+	uint32_t val = 0U;
+
+	switch (cs_in_use) {
+	case U(0xf):
+		val = 4U;
+		break;
+	case U(0x3):
+		val = 2U;
+		break;
+	case U(0x1):
+		val = 1U;
+		break;
+	default:
+		printf("Error - Invalid cs_in_use value\n");
+	}
+	return val;
+}
+
+static uint8_t findmax(uint8_t *buf, uint32_t len)
+{
+	uint8_t max = 0U;
+	uint32_t i = 0U;
+
+	for (i = 0U; i < len; i++) {
+		if (buf[i] > max) {
+			max = buf[i];
+		}
+	}
+
+	return max;
+}
+
+static void get_cdd_val(uint16_t **phy_ptr, uint32_t rank, uint32_t freq,
+		uint32_t *tcfg0, uint32_t *tcfg4)
+{
+	uint8_t cdd[CDD_DATA_LEN+4] = {0U};
+	uint32_t i, val = 0U;
+	uint16_t *phy;
+	uint8_t buf[16] = {U(0x0)};
+	uint8_t trr = 0U, tww = 0U, trw = 0U, twr = 0U;
+	uint8_t rrmax = 0U, wwmax = 0U, rwmax = 0U, wrmax = 0U;
+	uint8_t tmp = U(0x0);
+	uint8_t *c =  NULL;
+
+	for (i = 0U; i < NUM_OF_DDRC; i++) {
+
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, U(0x0));
+
+		read_phy_reg(phy, CDD_VAL_READ_ADDR,
+				(uint16_t *)&cdd, CDD_DATA_LEN);
+
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, U(0x1));
+
+	/* CDD values and address
+	 *
+	 *   0x054012    0x24    cdd[0]  CDD[X][X]
+	 *   0x054012    0x25    cdd[1]  RR[3][2]
+	 *   0x054013    0x26    cdd[2]  RR[3][1]
+	 *   0x054013    0x27    cdd[3]  RR[3][0]
+	 *   0x054014    0x28    cdd[4]  RR[2][3]
+	 *   0x054014    0x29    cdd[5]  RR[2][1]
+	 *   0x054015    0x2a    cdd[6]  RR[2][0]
+	 *   0x054015    0x2b    cdd[7]  RR[1][3]
+	 *   0x054016    0x2c    cdd[8]  RR[1][2]
+	 *   0x054016    0x2d    cdd[9]  RR[1][0]
+	 *   0x054017    0x2e    cdd[10] RR[0][3]
+	 *   0x054017    0x2f    cdd[11] RR[0][2]
+	 *   0x054018    0x30    cdd[12] RR[0][1]
+
+	 *   0x054018    0x31    cdd[13] WW[3][2]
+	 *   0x054019    0x32    cdd[14] WW[3][1]
+	 *   0x054019    0x33    cdd[15] WW[3][0]
+	 *   0x05401a    0x34    cdd[16] WW[2][3]
+	 *   0x05401a    0x35    cdd[17] WW[2][1]
+	 *   0x05401b    0x36    cdd[18] WW[2][0]
+	 *   0x05401b    0x37    cdd[19] WW[1][3]
+	 *   0x05401c    0x38    cdd[20] WW[1][2]
+	 *   0x05401c    0x39    cdd[21] WW[1][0]
+	 *   0x05401d    0x3a    cdd[22] WW[0][3]
+	 *   0x05401d    0x3b    cdd[23] WW[0][2]
+	 *   0x05401e    0x3c    cdd[24] WW[0][1]
+
+	 *   0x05401e    0x3d    cdd[25] RW[3][3]
+	 *   0x05401f    0x3e    cdd[26] RW[3][2]
+	 *   0x05401f    0x3f    cdd[27] RW[3][1]
+	 *   0x054020    0x40    cdd[28] RW[3][0]
+	 *   0x054020    0x41    cdd[29] RW[2][3]
+	 *   0x054021    0x42    cdd[30] RW[2][2]
+	 *   0x054021    0x43    cdd[31] RW[2][1]
+	 *   0x054022    0x44    cdd[32] RW[2][0]
+	 *   0x054022    0x45    cdd[33] RW[1][3]
+	 *   0x054023    0x46    cdd[34] RW[1][2]
+	 *   0x054023    0x47    cdd[35] RW[1][1]
+	 *   0x054024    0x48    cdd[36] RW[1][0]
+	 *   0x054024    0x49    cdd[37] RW[0][3]
+	 *   0x054025    0x4a    cdd[38] RW[0][2]
+	 *   0x054025    0x4b    cdd[39] RW[0][1]
+	 *   0x054026    0x4c    cdd[40] RW[0][0]
+
+	 *   0x054026    0x4d    cdd[41] WR[3][3]
+	 *   0x054027    0x4e    cdd[42] WR[3][2]
+	 *   0x054027    0x4f    cdd[43] WR[3][1]
+	 *   0x054028    0x50    cdd[44] WR[3][0]
+	 *   0x054028    0x51    cdd[45] WR[2][3]
+	 *   0x054029    0x52    cdd[46] WR[2][2]
+	 *   0x054029    0x53    cdd[47] WR[2][1]
+	 *   0x05402a    0x54    cdd[48] WR[2][0]
+	 *   0x05402a    0x55    cdd[49] WR[1][3]
+	 *   0x05402b    0x56    cdd[50] WR[1][2]
+	 *   0x05402b    0x57    cdd[51] WR[1][1]
+	 *   0x05402c    0x58    cdd[52] WR[1][0]
+	 *   0x05402c    0x59    cdd[53] WR[0][3]
+	 *   0x05402d    0x5a    cdd[54] WR[0][2]
+	 *   0x05402d    0x5b    cdd[55] WR[0][1]
+	 *   0x05402e    0x5c    cdd[56] WR[0][0]
+	 *   0x05402e    0x5d    cdd[57] CDD[Y][Y]
+	 */
+
+		switch (rank) {
+		case 1U:
+			tmp = rwmax;
+			rwmax = cdd[40];
+			if (tmp > rwmax) {
+				rwmax = tmp;
+			}
+
+			tmp = wrmax;
+			wrmax = cdd[56];
+			if (tmp > wrmax) {
+				wrmax = tmp;
+			}
+
+			break;
+
+		case 2U:
+			buf[0] = cdd[12];
+			buf[1] = cdd[9];
+			tmp = rrmax;
+			rrmax = findmax(buf, 2U);
+			if (tmp > rrmax) {
+				rrmax = tmp;
+			}
+
+			buf[0] = cdd[24];
+			buf[1] = cdd[21];
+			tmp = wwmax;
+			wwmax = findmax(buf, 2U);
+			if (tmp > wwmax) {
+				wwmax = tmp;
+			}
+
+			buf[0] = cdd[40];
+			buf[1] = cdd[39];
+			buf[2] = cdd[36];
+			buf[3] = cdd[35];
+			tmp = rwmax;
+			rwmax = findmax(buf, 4U);
+			if (tmp > rwmax) {
+				rwmax = tmp;
+			}
+
+			buf[0] = cdd[56];
+			buf[1] = cdd[55];
+			buf[2] = cdd[52];
+			buf[3] = cdd[51];
+			tmp = wrmax;
+			wrmax = findmax(buf, 4U);
+			if (tmp > wrmax) {
+				wrmax = tmp;
+			}
+
+			break;
+
+		case 4U:
+			tmp = rrmax;
+			c = &cdd[1];
+			rrmax = findmax(c, 12U);
+			if (tmp > rrmax) {
+				rrmax = tmp;
+			}
+
+			tmp = wwmax;
+			c = &cdd[13];
+			wwmax = findmax(c, 12U);
+			if (tmp > wwmax) {
+				wwmax = tmp;
+			}
+
+			tmp = rwmax;
+			c = &cdd[25];
+			rwmax = findmax(c, 16U);
+			if (tmp > rwmax) {
+				rwmax = tmp;
+			}
+
+			tmp = wrmax;
+			c = &cdd[41];
+			wrmax = findmax(c, 16U);
+			if (tmp > wrmax) {
+				wrmax = tmp;
+			}
+
+			break;
+
+		}
+	}
+
+	rrmax += 3U;
+	wwmax += 4U;
+
+	if (wwmax > 7U) {
+		wwmax = 7U;
+	}
+
+	if (rrmax > 7U) {
+		rrmax = 7U;
+	}
+
+	if (wrmax > U(0xf)) {
+		wrmax = 0U;
+	}
+
+	if (rwmax > U(0x7)) {
+		rwmax = U(0x7);
+	}
+
+	val = *tcfg0;
+	tww = (val >> 24U) & U(0x3);
+	trr = (val >> 26U) & U(0x3);
+	twr = (val >> 28U) & U(0x3);
+	trw = (val >> 30U) & U(0x3);
+
+	val = *tcfg4;
+	tww = tww | (((val >> 8U) & U(0x1)) << 2U);
+	trr = trr | (((val >> 10U) & U(0x1)) << 2U);
+	twr = twr | (((val >> 12U) & U(0x1)) << 2U);
+	trw = trw | (((val >> 14U) & U(0x3)) << 2U);
+
+	if (trr > rrmax) {
+		rrmax = trr;
+	}
+
+	if (tww > wwmax) {
+		wwmax = tww;
+	}
+
+	if (trw > rwmax) {
+		rwmax = trw;
+	}
+
+	if (twr > wrmax) {
+		wrmax = twr;
+	}
+
+	debug("CDD rrmax %x wwmax %x rwmax %x wrmax %x\n",
+			rrmax, wwmax, rwmax, wrmax);
+
+	val = ((wwmax & U(0x3)) << 24U)
+		| ((rrmax & U(0x3)) << 26U)
+		| ((wrmax & U(0x3)) << 28U)
+		| ((rwmax & U(0x3)) << 30U);
+
+	*tcfg0 = (*tcfg0 & U(0x00FFFFFF)) | (val);
+
+	val = (((wwmax >> 2U) & U(0x1)) << 8U)
+		| (((rrmax >> 2U) & U(0x1)) << 10U)
+		| (((wrmax >> 2U) & U(0x1)) << 12U)
+		| (((rwmax >> 2U) & U(0x3)) << 14U);
+
+	*tcfg4 = (*tcfg4 & U(0xffff00ff)) | val;
+}
+#endif
+
+#ifdef NXP_WARM_BOOT
+int save_phy_training_values(uint16_t **phy_ptr, uint32_t address_to_store,
+		uint32_t num_of_phy, int train2d)
+{
+	uint16_t *phy = NULL, value = 0x0;
+	uint32_t size = 1U, num_of_regs = 1U, phy_store = 0U;
+	int i = 0, j = 0, ret = -EINVAL;
+
+	ret = xspi_sector_erase(address_to_store, PHY_ERASE_SIZE);
+	if (ret != 0) {
+		return -EINVAL;
+	}
+
+	for (j = 0; j < num_of_phy; j++) {
+		/* Save training values of all PHYs */
+		phy = phy_ptr[j];
+		size = sizeof(training_1D_values);
+		num_of_regs = ARRAY_SIZE(training_1D_values);
+
+		/* Enable access to the internal CSRs */
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, 0x0);
+		/* Enable clocks in case they were disabled. */
+		phy_io_write16(phy, t_drtub |
+				csr_ucclk_hclk_enables_addr, 0x3);
+		if (train2d != 0) {
+		/* Address to store training values is
+		 * to be appended for next PHY
+		 */
+			phy_store = address_to_store + (j *
+					(sizeof(training_1D_values) +
+					 sizeof(training_2D_values)));
+		} else {
+			phy_store = address_to_store + (j *
+					(sizeof(training_1D_values)));
+		}
+		debug("Saving 1D Training reg val at: %d\n", phy_store);
+		for (i = 0; i < num_of_regs; i++) {
+			value = phy_io_read16(phy, training_1D_values[i].addr);
+#ifdef DEBUG_WARM_RESET
+			debug("%d. Reg: %x, value: %x PHY: %p\n", i,
+					training_1D_values[i].addr, value,
+					phy_io_addr(phy,
+						training_1D_values[i].addr));
+#endif
+			training_1D_values[i].data = value;
+		}
+		/* Storing 1D training values on flash */
+		ret = xspi_write(phy_store, (void *)training_1D_values, size);
+		if (train2d != 0) {
+			phy_store = phy_store+size;
+			size = sizeof(training_2D_values);
+			num_of_regs = ARRAY_SIZE(training_2D_values);
+			debug("Saving 2D Training reg val at:%d\n", phy_store);
+			for (i = 0; i < num_of_regs; i++) {
+				value = phy_io_read16(phy,
+						training_2D_values[i].addr);
+				training_2D_values[i].data = value;
+#ifdef DEBUG_WARM_RESET
+				debug("%d.2D addr:0x%x,val:0x%x,PHY:0x%p\n",
+						i, training_2D_values[i].addr,
+						value, phy_io_addr(phy,
+						training_2D_values[i].addr));
+#endif
+			}
+			/* Storing 2D training values on flash */
+			ret = xspi_write(phy_store, training_2D_values,
+					size);
+		}
+		/* Disable clocks in case they were disabled. */
+		phy_io_write16(phy, t_drtub |
+				csr_ucclk_hclk_enables_addr, 0x0);
+		/* Disable access to the internal CSRs */
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, 0x1);
+	}
+	if (ret != 0) {
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+int restore_phy_training_values(uint16_t **phy_ptr, uint32_t address_to_restore,
+		uint32_t num_of_phy, int train2d)
+{
+	uint16_t *phy = NULL;
+	uint32_t size = 1U, num_of_regs = 1U, phy_store = 0U;
+	int i = 0, j = 0, ret = -EINVAL;
+
+	debug("Restoring Training register values\n");
+	for (j = 0; j < num_of_phy; j++) {
+		phy = phy_ptr[j];
+		size = sizeof(training_1D_values);
+		num_of_regs = ARRAY_SIZE(training_1D_values);
+		if (train2d != 0) {
+		/* The address to restore training values is
+		 * to be appended for next PHY
+		 */
+			phy_store = address_to_restore + (j *
+					(sizeof(training_1D_values) +
+					 sizeof(training_2D_values)));
+		} else {
+			phy_store = address_to_restore + (j *
+					(sizeof(training_1D_values)));
+		}
+		/* Enable access to the internal CSRs */
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, 0x0);
+		/* Enable clocks in case they were disabled. */
+		phy_io_write16(phy, t_drtub |
+				csr_ucclk_hclk_enables_addr, 0x3);
+
+		/* Reading 1D training values from flash*/
+		ret = xspi_read(phy_store, (uint32_t *)training_1D_values,
+				size);
+		debug("Restoring 1D Training reg val at:%08x\n", phy_store);
+		for (i = 0; i < num_of_regs; i++) {
+			phy_io_write16(phy, training_1D_values[i].addr,
+					training_1D_values[i].data);
+#ifdef DEBUG_WARM_RESET
+			debug("%d. Reg: %x, value: %x PHY: %p\n", i,
+					training_1D_values[i].addr,
+					training_1D_values[i].data,
+					phy_io_addr(phy,
+						training_1D_values[i].addr));
+#endif
+		}
+		if (train2d != 0) {
+			phy_store = phy_store + size;
+			size = sizeof(training_2D_values);
+			num_of_regs = ARRAY_SIZE(training_2D_values);
+			/* Reading 2D training values from flash */
+			ret = xspi_read(phy_store,
+					(uint32_t *)training_2D_values,	size);
+			debug("Restoring 2D Training reg val at:%08x\n",
+					phy_store);
+			for (i = 0; i < num_of_regs; i++) {
+				phy_io_write16(phy, training_2D_values[i].addr,
+						training_2D_values[i].data);
+#ifdef DEBUG_WARM_RESET
+				debug("%d. Reg: %x, value: %x PHY: %p\n", i,
+						training_2D_values[i].addr,
+						training_2D_values[i].data,
+						phy_io_addr(phy,
+						training_1D_values[i].addr));
+#endif
+			}
+		}
+		/* Disable clocks in case they were disabled. */
+		phy_io_write16(phy, t_drtub |
+				csr_ucclk_hclk_enables_addr, 0x0);
+		/* Disable access to the internal CSRs */
+		phy_io_write16(phy, t_apbonly |
+				csr_micro_cont_mux_sel_addr, 0x1);
+	}
+	if (ret != 0) {
+		return -EINVAL;
+	}
+	return 0;
+}
+#endif
+
+static void load_pieimage(uint16_t *phy,
+			  enum dimm_types dimm_type)
+{
+	int i;
+	int size;
+	const struct pie *image = NULL;
+
+	switch (dimm_type) {
+	case UDIMM:
+	case SODIMM:
+	case NODIMM:
+		image = pie_udimm;
+		size = ARRAY_SIZE(pie_udimm);
+		break;
+	case RDIMM:
+		image = pie_rdimm;
+		size = ARRAY_SIZE(pie_rdimm);
+		break;
+	case LRDIMM:
+		image = pie_lrdimm;
+		size = ARRAY_SIZE(pie_lrdimm);
+		break;
+	default:
+		printf("Unsupported DIMM type\n");
+		break;
+	}
+
+	if (image != NULL) {
+		for (i = 0; i < size; i++)
+			phy_io_write16(phy, image[i].addr, image[i].data);
+	}
+}
+
+static void prog_acsm_playback(uint16_t *phy,
+			       const struct input *input, const void *msg)
+{
+	int vec;
+	const struct ddr4r1d *msg_blk;
+	uint16_t acsmplayback[2][3];
+	uint32_t f0rc0a;
+	uint32_t f0rc3x;
+	uint32_t f0rc5x;
+
+	if (input->basic.dimm_type != RDIMM) {
+		return;
+	}
+
+	msg_blk = msg;
+	f0rc0a = (msg_blk->f0rc0a_d0 & U(0xf)) | U(0xa0);
+	f0rc3x = (msg_blk->f0rc3x_d0 & U(0xff)) | U(0x300);
+	f0rc5x = (input->adv.phy_gen2_umctl_f0rc5x & U(0xff)) | U(0x500);
+
+	acsmplayback[0][0] = U(0x3ff) & f0rc0a;
+	acsmplayback[1][0] = (U(0x1c00) & f0rc0a) >> 10U;
+	acsmplayback[0][1] = U(0x3ff) & f0rc3x;
+	acsmplayback[1][1] = (U(0x1c00) & f0rc3x) >> 10U;
+	acsmplayback[0][2] = U(0x3ff) & f0rc5x;
+	acsmplayback[1][2] = (U(0x1c00) & f0rc5x) >> 10U;
+	for (vec = 0; vec < 3; vec++) {
+		phy_io_write16(phy, t_acsm | (csr_acsm_playback0x0_addr +
+			       (vec << 1)), acsmplayback[0][vec]);
+		phy_io_write16(phy, t_acsm | (csr_acsm_playback1x0_addr +
+			       (vec << 1)), acsmplayback[1][vec]);
+	}
+}
+
+static void prog_acsm_ctr(uint16_t *phy,
+			  const struct input *input)
+{
+	if (input->basic.dimm_type != RDIMM) {
+		return;
+	}
+
+	phy_io_write16(phy, t_acsm | csr_acsm_ctrl13_addr,
+		       0xf << csr_acsm_cke_enb_lsb);
+
+	phy_io_write16(phy, t_acsm | csr_acsm_ctrl0_addr,
+		       csr_acsm_par_mode_mask | csr_acsm_2t_mode_mask);
+}
+
+static void prog_cal_rate_run(uint16_t *phy,
+			  const struct input *input)
+{
+	int cal_rate;
+	int cal_interval;
+	int cal_once;
+	uint32_t addr;
+
+	cal_interval = input->adv.cal_interval;
+	cal_once = input->adv.cal_once;
+	cal_rate = 0x1 << csr_cal_run_lsb		|
+			cal_once << csr_cal_once_lsb	|
+			cal_interval << csr_cal_interval_lsb;
+	addr = t_master | csr_cal_rate_addr;
+	phy_io_write16(phy, addr, cal_rate);
+}
+
+static void prog_seq0bdly0(uint16_t *phy,
+		    const struct input *input)
+{
+	int ps_count[4];
+	int frq;
+	uint32_t addr;
+	int lower_freq_opt = 0;
+
+	__unused const soc_info_t *soc_info;
+
+	frq = input->basic.frequency >> 1;
+	ps_count[0] = frq >> 3; /* 0.5 * frq / 4*/
+	if (input->basic.frequency < 400) {
+		lower_freq_opt = (input->basic.dimm_type == RDIMM) ? 7 : 3;
+	} else if (input->basic.frequency < 533) {
+		lower_freq_opt = (input->basic.dimm_type == RDIMM) ? 14 : 11;
+	}
+
+	/* 1.0 * frq / 4 - lower_freq */
+	ps_count[1] = (frq >> 2) - lower_freq_opt;
+	ps_count[2] = (frq << 1) +  (frq >> 1); /* 10.0 * frq / 4 */
+
+#ifdef DDR_PLL_FIX
+	soc_info = get_soc_info();
+	if (soc_info->svr_reg.bf.maj_ver == 1) {
+		ps_count[0] = 0x520; /* seq0bdly0 */
+		ps_count[1] = 0xa41; /* seq0bdly1 */
+		ps_count[2] = 0x668a; /* seq0bdly2 */
+	}
+#endif
+	if (frq > 266) {
+		ps_count[3] = 44;
+	} else if (frq > 200) {
+		ps_count[3] = 33;
+	} else {
+		ps_count[3] = 16;
+	}
+
+	addr = t_master | csr_seq0bdly0_addr;
+	phy_io_write16(phy, addr, ps_count[0]);
+
+	debug("seq0bdly0 = 0x%x\n", phy_io_read16(phy, addr));
+
+	addr = t_master | csr_seq0bdly1_addr;
+	phy_io_write16(phy, addr, ps_count[1]);
+
+	debug("seq0bdly1 = 0x%x\n", phy_io_read16(phy, addr));
+
+	addr = t_master | csr_seq0bdly2_addr;
+	phy_io_write16(phy, addr, ps_count[2]);
+
+	debug("seq0bdly2 = 0x%x\n", phy_io_read16(phy, addr));
+
+	addr = t_master | csr_seq0bdly3_addr;
+	phy_io_write16(phy, addr, ps_count[3]);
+
+	debug("seq0bdly3 = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+/* Only RDIMM requires msg_blk */
+static void i_load_pie(uint16_t **phy_ptr,
+		       const struct input *input,
+		       const void *msg)
+{
+	int i;
+	uint16_t *phy;
+
+	for (i = 0; i < NUM_OF_DDRC; i++) {
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+
+		phy_io_write16(phy,
+			       t_apbonly | csr_micro_cont_mux_sel_addr,
+			       0U);
+
+		load_pieimage(phy, input->basic.dimm_type);
+
+		prog_seq0bdly0(phy, input);
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag0_addr,
+			       U(0x0000));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag1_addr,
+			       U(0x0173));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag2_addr,
+			       U(0x0060));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag3_addr,
+			       U(0x6110));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag4_addr,
+			       U(0x2152));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag5_addr,
+			       U(0xdfbd));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag6_addr,
+			       input->basic.dimm_type == RDIMM &&
+			       input->adv.phy_gen2_umctl_opt == 1U ?
+			       U(0x6000) : U(0xffff));
+		phy_io_write16(phy, t_initeng | csr_seq0bdisable_flag7_addr,
+			       U(0x6152));
+		prog_acsm_playback(phy, input, msg);		/* rdimm */
+		prog_acsm_ctr(phy, input);			/* rdimm */
+
+		phy_io_write16(phy, t_master | csr_cal_zap_addr, U(0x1));
+		prog_cal_rate_run(phy, input);
+
+		phy_io_write16(phy, t_drtub | csr_ucclk_hclk_enables_addr,
+			       input->basic.dimm_type == RDIMM ? U(0x2) : 0U);
+
+		phy_io_write16(phy, t_apbonly | csr_micro_cont_mux_sel_addr, 1U);
+	}
+}
+
+static void phy_gen2_init_input(struct input *input)
+{
+	int i;
+
+	input->adv.dram_byte_swap		= 0;
+	input->adv.ext_cal_res_val		= 0;
+	input->adv.tx_slew_rise_dq		= 0xf;
+	input->adv.tx_slew_fall_dq		= 0xf;
+	input->adv.tx_slew_rise_ac		= 0xf;
+	input->adv.tx_slew_fall_ac		= 0xf;
+	input->adv.mem_alert_en			= 0;
+	input->adv.mem_alert_puimp		= 5;
+	input->adv.mem_alert_vref_level		= 0x29;
+	input->adv.mem_alert_sync_bypass	= 0;
+	input->adv.cal_interval			= 0x9;
+	input->adv.cal_once			= 0;
+	input->adv.dis_dyn_adr_tri		= 0;
+	input->adv.is2ttiming			= 0;
+	input->adv.d4rx_preamble_length		= 0;
+	input->adv.d4tx_preamble_length		= 0;
+
+	for (i = 0; i < 7; i++) {
+		debug("mr[%d] = 0x%x\n", i, input->mr[i]);
+	}
+
+	debug("input->cs_d0 = 0x%x\n", input->cs_d0);
+	debug("input->cs_d1 = 0x%x\n", input->cs_d1);
+	debug("input->mirror = 0x%x\n", input->mirror);
+	debug("PHY ODT impedance = %d ohm\n", input->adv.odtimpedance);
+	debug("PHY DQ driver impedance = %d ohm\n", input->adv.tx_impedance);
+	debug("PHY Addr driver impedance = %d ohm\n", input->adv.atx_impedance);
+
+	for (i = 0; i < 4; i++) {
+		debug("odt[%d] = 0x%x\n", i, input->odt[i]);
+	}
+
+	if (input->basic.dimm_type == RDIMM) {
+		for (i = 0; i < 16; i++) {
+			debug("input->rcw[%d] = 0x%x\n", i, input->rcw[i]);
+		}
+		debug("input->rcw3x = 0x%x\n", input->rcw3x);
+	}
+}
+
+/*
+ * All protocols share the same base structure of message block.
+ * RDIMM and LRDIMM have more entries defined than UDIMM.
+ * Create message blocks for 1D and 2D training.
+ * Update len with message block size.
+ */
+static int phy_gen2_msg_init(void *msg_1d,
+			     void *msg_2d,
+			     const struct input *input)
+{
+	struct ddr4u1d *msg_blk = msg_1d;
+	struct ddr4u2d *msg_blk_2d = msg_2d;
+	struct ddr4r1d *msg_blk_r;
+	struct ddr4lr1d *msg_blk_lr;
+
+	switch (input->basic.dimm_type) {
+	case UDIMM:
+	case SODIMM:
+	case NODIMM:
+		msg_blk->dram_type	= U(0x2);
+		break;
+	case RDIMM:
+		msg_blk->dram_type	= U(0x4);
+		break;
+	case LRDIMM:
+		msg_blk->dram_type	= U(0x5);
+		break;
+	default:
+		ERROR("Unsupported DIMM type\n");
+		return -EINVAL;
+	}
+	msg_blk->pstate			= 0U;
+
+	/*Enable quickRd2D, a substage of read deskew, to 1D training.*/
+	msg_blk->reserved00             = U(0x20);
+
+	/*Enable High-Effort WrDQ1D.*/
+	msg_blk->reserved00             |= U(0x40);
+
+	/* Enable 1D extra effort training.*/
+	msg_blk->reserved1c[3]		= U(0x3);
+
+	if (input->basic.dimm_type == LRDIMM) {
+		msg_blk->sequence_ctrl	= U(0x3f1f);
+	} else {
+		msg_blk->sequence_ctrl	= U(0x031f);
+	}
+	msg_blk->phy_config_override	= 0U;
+#ifdef DDR_PHY_DEBUG
+	msg_blk->hdt_ctrl		= U(0x5);
+#else
+	msg_blk->hdt_ctrl		= U(0xc9);
+#endif
+	msg_blk->msg_misc		= U(0x0);
+	msg_blk->dfimrlmargin		= U(0x1);
+	msg_blk->phy_vref		= input->vref ? input->vref : U(0x61);
+	msg_blk->cs_present		= input->cs_d0 | input->cs_d1;
+	msg_blk->cs_present_d0		= input->cs_d0;
+	msg_blk->cs_present_d1		= input->cs_d1;
+	if (input->mirror != 0) {
+		msg_blk->addr_mirror	= U(0x0a);	/* odd CS are mirrored */
+	}
+	msg_blk->share2dvref_result	= 1U;
+
+	msg_blk->acsm_odt_ctrl0		= input->odt[0];
+	msg_blk->acsm_odt_ctrl1		= input->odt[1];
+	msg_blk->acsm_odt_ctrl2		= input->odt[2];
+	msg_blk->acsm_odt_ctrl3		= input->odt[3];
+	msg_blk->enabled_dqs = (input->basic.num_active_dbyte_dfi0 +
+				input->basic.num_active_dbyte_dfi1) * 8;
+	msg_blk->x16present		= input->basic.dram_data_width == 0x10 ?
+					  msg_blk->cs_present : 0;
+	msg_blk->d4misc			= U(0x1);
+	msg_blk->cs_setup_gddec		= U(0x1);
+	msg_blk->rtt_nom_wr_park0	= 0U;
+	msg_blk->rtt_nom_wr_park1	= 0U;
+	msg_blk->rtt_nom_wr_park2	= 0U;
+	msg_blk->rtt_nom_wr_park3	= 0U;
+	msg_blk->rtt_nom_wr_park4	= 0U;
+	msg_blk->rtt_nom_wr_park5	= 0U;
+	msg_blk->rtt_nom_wr_park6	= 0U;
+	msg_blk->rtt_nom_wr_park7	= 0U;
+	msg_blk->mr0			= input->mr[0];
+	msg_blk->mr1			= input->mr[1];
+	msg_blk->mr2			= input->mr[2];
+	msg_blk->mr3			= input->mr[3];
+	msg_blk->mr4			= input->mr[4];
+	msg_blk->mr5			= input->mr[5];
+	msg_blk->mr6			= input->mr[6];
+	if ((msg_blk->mr4 & U(0x1c0)) != 0U) {
+		ERROR("Setting DRAM CAL mode is not supported\n");
+	}
+
+	msg_blk->alt_cas_l		= 0U;
+	msg_blk->alt_wcas_l		= 0U;
+
+	msg_blk->dramfreq		= input->basic.frequency * 2U;
+	msg_blk->pll_bypass_en		= input->basic.pll_bypass;
+	msg_blk->dfi_freq_ratio		= input->basic.dfi_freq_ratio == 0U ? 1U :
+					  input->basic.dfi_freq_ratio == 1U ? 2U :
+					  4U;
+	msg_blk->bpznres_val		= input->adv.ext_cal_res_val;
+	msg_blk->disabled_dbyte		= 0U;
+
+	debug("msg_blk->dram_type = 0x%x\n", msg_blk->dram_type);
+	debug("msg_blk->sequence_ctrl = 0x%x\n", msg_blk->sequence_ctrl);
+	debug("msg_blk->phy_cfg = 0x%x\n", msg_blk->phy_cfg);
+	debug("msg_blk->x16present = 0x%x\n", msg_blk->x16present);
+	debug("msg_blk->dramfreq = 0x%x\n", msg_blk->dramfreq);
+	debug("msg_blk->pll_bypass_en = 0x%x\n", msg_blk->pll_bypass_en);
+	debug("msg_blk->dfi_freq_ratio = 0x%x\n", msg_blk->dfi_freq_ratio);
+	debug("msg_blk->phy_odt_impedance = 0x%x\n",
+						msg_blk->phy_odt_impedance);
+	debug("msg_blk->phy_drv_impedance = 0x%x\n",
+						msg_blk->phy_drv_impedance);
+	debug("msg_blk->bpznres_val = 0x%x\n", msg_blk->bpznres_val);
+	debug("msg_blk->enabled_dqs = 0x%x\n", msg_blk->enabled_dqs);
+	debug("msg_blk->acsm_odt_ctrl0 = 0x%x\n", msg_blk->acsm_odt_ctrl0);
+	debug("msg_blk->acsm_odt_ctrl1 = 0x%x\n", msg_blk->acsm_odt_ctrl1);
+	debug("msg_blk->acsm_odt_ctrl2 = 0x%x\n", msg_blk->acsm_odt_ctrl2);
+	debug("msg_blk->acsm_odt_ctrl3 = 0x%x\n", msg_blk->acsm_odt_ctrl3);
+
+	/* RDIMM only */
+	if (input->basic.dimm_type == RDIMM ||
+	    input->basic.dimm_type == LRDIMM) {
+		msg_blk_r = (struct ddr4r1d *)msg_blk;
+		if (msg_blk_r->cs_present_d0 != 0U) {
+			msg_blk_r->f0rc00_d0 = input->rcw[0];
+			msg_blk_r->f0rc01_d0 = input->rcw[1];
+			msg_blk_r->f0rc02_d0 = input->rcw[2];
+			msg_blk_r->f0rc03_d0 = input->rcw[3];
+			msg_blk_r->f0rc04_d0 = input->rcw[4];
+			msg_blk_r->f0rc05_d0 = input->rcw[5];
+			msg_blk_r->f0rc06_d0 = input->rcw[6];
+			msg_blk_r->f0rc07_d0 = input->rcw[7];
+			msg_blk_r->f0rc08_d0 = input->rcw[8];
+			msg_blk_r->f0rc09_d0 = input->rcw[9];
+			msg_blk_r->f0rc0a_d0 = input->rcw[10];
+			msg_blk_r->f0rc0b_d0 = input->rcw[11];
+			msg_blk_r->f0rc0c_d0 = input->rcw[12];
+			msg_blk_r->f0rc0d_d0 = input->rcw[13];
+			msg_blk_r->f0rc0e_d0 = input->rcw[14];
+			msg_blk_r->f0rc0f_d0 = input->rcw[15];
+			msg_blk_r->f0rc3x_d0 = input->rcw3x;
+		}
+		if (msg_blk_r->cs_present_d1 != 0) {
+			msg_blk_r->f0rc00_d1 = input->rcw[0];
+			msg_blk_r->f0rc01_d1 = input->rcw[1];
+			msg_blk_r->f0rc02_d1 = input->rcw[2];
+			msg_blk_r->f0rc03_d1 = input->rcw[3];
+			msg_blk_r->f0rc04_d1 = input->rcw[4];
+			msg_blk_r->f0rc05_d1 = input->rcw[5];
+			msg_blk_r->f0rc06_d1 = input->rcw[6];
+			msg_blk_r->f0rc07_d1 = input->rcw[7];
+			msg_blk_r->f0rc08_d1 = input->rcw[8];
+			msg_blk_r->f0rc09_d1 = input->rcw[9];
+			msg_blk_r->f0rc0a_d1 = input->rcw[10];
+			msg_blk_r->f0rc0b_d1 = input->rcw[11];
+			msg_blk_r->f0rc0c_d1 = input->rcw[12];
+			msg_blk_r->f0rc0d_d1 = input->rcw[13];
+			msg_blk_r->f0rc0e_d1 = input->rcw[14];
+			msg_blk_r->f0rc0f_d1 = input->rcw[15];
+			msg_blk_r->f0rc3x_d1 = input->rcw3x;
+		}
+		if (input->basic.dimm_type == LRDIMM) {
+			msg_blk_lr = (struct ddr4lr1d *)msg_blk;
+			msg_blk_lr->bc0a_d0 = msg_blk_lr->f0rc0a_d0;
+			msg_blk_lr->bc0a_d1 = msg_blk_lr->f0rc0a_d1;
+			msg_blk_lr->f0bc6x_d0 = msg_blk_lr->f0rc3x_d0;
+			msg_blk_lr->f0bc6x_d1 = msg_blk_lr->f0rc3x_d1;
+		}
+	}
+
+	/* below is different for 1D and 2D message block */
+	if (input->basic.train2d != 0) {
+		memcpy(msg_blk_2d, msg_blk, sizeof(struct ddr4u1d));
+		/*High-Effort WrDQ1D is applicable to 2D traning also*/
+		msg_blk_2d->reserved00          |= U(0x40);
+		msg_blk_2d->sequence_ctrl	= U(0x0061);
+		msg_blk_2d->rx2d_train_opt	= 0U;
+		msg_blk_2d->tx2d_train_opt	= 0U;
+		msg_blk_2d->share2dvref_result	= 1U;
+		msg_blk_2d->delay_weight2d	= U(0x20);
+		msg_blk_2d->voltage_weight2d	= U(0x80);
+		debug("rx2d_train_opt %d, tx2d_train_opt %d\n",
+				msg_blk_2d->rx2d_train_opt,
+				msg_blk_2d->tx2d_train_opt);
+	}
+
+	msg_blk->phy_cfg = (((msg_blk->mr3 & U(0x8)) != 0U) ||
+				((msg_blk_2d->mr3 & 0x8) != 0U)) ? 0U
+				: input->adv.is2ttiming;
+
+	return 0;
+}
+
+static void prog_tx_pre_drv_mode(uint16_t *phy,
+				 const struct input *input)
+{
+	int lane, byte, b_addr, c_addr, p_addr;
+	int tx_slew_rate, tx_pre_p, tx_pre_n;
+	int tx_pre_drv_mode = 0x2;
+	uint32_t addr;
+
+	/* Program TxPreDrvMode with 0x2 */
+	/* FIXME: TxPreDrvMode depends on DramType? */
+	tx_pre_p = input->adv.tx_slew_rise_dq;
+	tx_pre_n = input->adv.tx_slew_fall_dq;
+	tx_slew_rate = tx_pre_drv_mode << csr_tx_pre_drv_mode_lsb	|
+		     tx_pre_p << csr_tx_pre_p_lsb			|
+		     tx_pre_n << csr_tx_pre_n_lsb;
+	p_addr = 0;
+	for (byte = 0; byte < input->basic.num_dbyte; byte++) {
+		c_addr = byte << 12;
+		for (lane = 0; lane <= 1; lane++) {
+			b_addr = lane << 8;
+			addr = p_addr | t_dbyte | c_addr | b_addr |
+					csr_tx_slew_rate_addr;
+			phy_io_write16(phy, addr, tx_slew_rate);
+		}
+	}
+}
+
+static void prog_atx_pre_drv_mode(uint16_t *phy,
+				  const struct input *input)
+{
+	int anib, c_addr;
+	int atx_slew_rate, atx_pre_p, atx_pre_n, atx_pre_drv_mode,
+		ck_anib_inst[2];
+	uint32_t addr;
+
+	atx_pre_n = input->adv.tx_slew_fall_ac;
+	atx_pre_p = input->adv.tx_slew_rise_ac;
+
+	if (input->basic.num_anib == 8) {
+		ck_anib_inst[0] = 1;
+		ck_anib_inst[1] = 1;
+	} else if (input->basic.num_anib == 10 || input->basic.num_anib == 12 ||
+	    input->basic.num_anib == 13) {
+		ck_anib_inst[0] = 4;
+		ck_anib_inst[1] = 5;
+	} else {
+		ERROR("Invalid number of aNIBs: %d\n", input->basic.num_anib);
+		return;
+	}
+
+	for (anib = 0; anib < input->basic.num_anib; anib++) {
+		c_addr = anib << 12;
+		if (anib == ck_anib_inst[0] || anib == ck_anib_inst[1]) {
+			atx_pre_drv_mode = 0;
+		} else {
+			atx_pre_drv_mode = 3;
+		}
+		atx_slew_rate = atx_pre_drv_mode << csr_atx_pre_drv_mode_lsb |
+				atx_pre_n << csr_atx_pre_n_lsb		     |
+				atx_pre_p << csr_atx_pre_p_lsb;
+		addr = t_anib | c_addr | csr_atx_slew_rate_addr;
+		phy_io_write16(phy, addr, atx_slew_rate);
+	}
+}
+
+static void prog_enable_cs_multicast(uint16_t *phy,
+				     const struct input *input)
+{
+	uint32_t addr = t_master | csr_enable_cs_multicast_addr;
+
+	if (input->basic.dimm_type != RDIMM &&
+	    input->basic.dimm_type != LRDIMM) {
+		return;
+	}
+
+	phy_io_write16(phy, addr, input->adv.cast_cs_to_cid);
+}
+
+static void prog_dfi_rd_data_cs_dest_map(uint16_t *phy,
+					 unsigned int ip_rev,
+					 const struct input *input,
+					 const struct ddr4lr1d *msg)
+{
+	const struct ddr4lr1d *msg_blk;
+	uint16_t dfi_xxdestm0 = 0U;
+	uint16_t dfi_xxdestm1 = 0U;
+	uint16_t dfi_xxdestm2 = 0U;
+	uint16_t dfi_xxdestm3 = 0U;
+	uint16_t dfi_rd_data_cs_dest_map;
+	uint16_t dfi_wr_data_cs_dest_map;
+	__unused const soc_info_t *soc_info;
+
+#ifdef ERRATA_DDR_A011396
+	/* Only apply to DDRC 5.05.00 */
+	soc_info = get_soc_info();
+	if ((soc_info->svr_reg.bf.maj_ver == 1U) && (ip_rev == U(0x50500))) {
+		phy_io_write16(phy,
+				t_master | csr_dfi_rd_data_cs_dest_map_addr,
+				0U);
+		return;
+	}
+#endif
+
+	msg_blk = msg;
+
+	switch (input->basic.dimm_type) {
+	case UDIMM:
+	case SODIMM:
+	case NODIMM:
+		if ((msg_blk->msg_misc & U(0x40)) != 0U) {
+			dfi_rd_data_cs_dest_map = U(0xa0);
+			dfi_wr_data_cs_dest_map = U(0xa0);
+
+			phy_io_write16(phy,
+				t_master | csr_dfi_rd_data_cs_dest_map_addr,
+				dfi_rd_data_cs_dest_map);
+			phy_io_write16(phy,
+				t_master | csr_dfi_wr_data_cs_dest_map_addr,
+				dfi_wr_data_cs_dest_map);
+		}
+		break;
+	case LRDIMM:
+		if (msg->cs_present_d1 != 0U) {
+			dfi_xxdestm2 = 1U;
+			dfi_xxdestm3 = 1U;
+		}
+
+		dfi_rd_data_cs_dest_map =
+			dfi_xxdestm0 << csr_dfi_rd_destm0_lsb	|
+			dfi_xxdestm1 << csr_dfi_rd_destm1_lsb	|
+			dfi_xxdestm2 << csr_dfi_rd_destm2_lsb	|
+			dfi_xxdestm3 << csr_dfi_rd_destm3_lsb;
+		dfi_wr_data_cs_dest_map =
+			dfi_xxdestm0 << csr_dfi_wr_destm0_lsb	|
+			dfi_xxdestm1 << csr_dfi_wr_destm1_lsb	|
+			dfi_xxdestm2 << csr_dfi_wr_destm2_lsb	|
+			dfi_xxdestm3 << csr_dfi_wr_destm3_lsb;
+		phy_io_write16(phy, t_master | csr_dfi_rd_data_cs_dest_map_addr,
+				dfi_rd_data_cs_dest_map);
+		phy_io_write16(phy, t_master | csr_dfi_wr_data_cs_dest_map_addr,
+				dfi_wr_data_cs_dest_map);
+
+		break;
+	default:
+		break;
+	}
+}
+
+static void prog_pll_ctrl(uint16_t *phy,
+			   const struct input *input)
+{
+	uint32_t addr;
+	int pll_ctrl1 = 0x21; /* 000100001b */
+	int pll_ctrl4 = 0x17f; /* 101111111b */
+	int pll_test_mode = 0x24; /* 00100100b */
+
+	addr = t_master | csr_pll_ctrl1_addr;
+	phy_io_write16(phy, addr, pll_ctrl1);
+
+	debug("pll_ctrl1 = 0x%x\n", phy_io_read16(phy, addr));
+
+	addr = t_master | csr_pll_test_mode_addr;
+	phy_io_write16(phy, addr, pll_test_mode);
+
+	debug("pll_test_mode = 0x%x\n", phy_io_read16(phy, addr));
+
+	addr = t_master | csr_pll_ctrl4_addr;
+	phy_io_write16(phy, addr, pll_ctrl4);
+
+	debug("pll_ctrl4 = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+static void prog_pll_ctrl2(uint16_t *phy,
+			   const struct input *input)
+{
+	int pll_ctrl2;
+	uint32_t addr = t_master | csr_pll_ctrl2_addr;
+
+	if (input->basic.frequency / 2 < 235) {
+		pll_ctrl2 = 0x7;
+	} else if (input->basic.frequency / 2 < 313) {
+		pll_ctrl2 = 0x6;
+	} else if (input->basic.frequency / 2 < 469) {
+		pll_ctrl2 = 0xb;
+	} else if (input->basic.frequency / 2 < 625) {
+		pll_ctrl2 = 0xa;
+	} else if (input->basic.frequency / 2 < 938) {
+		pll_ctrl2 = 0x19;
+	} else if (input->basic.frequency / 2 < 1067) {
+		pll_ctrl2 = 0x18;
+	} else {
+		pll_ctrl2 = 0x19;
+	}
+
+	phy_io_write16(phy, addr, pll_ctrl2);
+
+	debug("pll_ctrl2 = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+static void prog_dll_lck_param(uint16_t *phy, const struct input *input)
+{
+	uint32_t addr = t_master | csr_dll_lockparam_addr;
+
+	phy_io_write16(phy, addr, U(0x212));
+	debug("dll_lck_param = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+static void prog_dll_gain_ctl(uint16_t *phy, const struct input *input)
+{
+	uint32_t addr = t_master | csr_dll_gain_ctl_addr;
+
+	phy_io_write16(phy, addr, U(0x61));
+	debug("dll_gain_ctl = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+static void prog_pll_pwr_dn(uint16_t *phy,
+			   const struct input *input)
+{
+	uint32_t addr;
+
+	addr = t_master | csr_pll_pwr_dn_addr;
+	phy_io_write16(phy, addr, 0U);
+
+	debug("pll_pwrdn = 0x%x\n", phy_io_read16(phy, addr));
+}
+
+static void prog_ard_ptr_init_val(uint16_t *phy,
+				  const struct input *input)
+{
+	int ard_ptr_init_val;
+	uint32_t addr = t_master | csr_ard_ptr_init_val_addr;
+
+	if (input->basic.frequency >= 933) {
+		ard_ptr_init_val = 0x2;
+	} else {
+		ard_ptr_init_val = 0x1;
+	}
+
+	phy_io_write16(phy, addr, ard_ptr_init_val);
+}
+
+static void prog_dqs_preamble_control(uint16_t *phy,
+				      const struct input *input)
+{
+	int data;
+	uint32_t addr = t_master | csr_dqs_preamble_control_addr;
+	const int wdqsextension = 0;
+	const int lp4sttc_pre_bridge_rx_en = 0;
+	const int lp4postamble_ext = 0;
+	const int lp4tgl_two_tck_tx_dqs_pre = 0;
+	const int position_dfe_init = 2;
+	const int dll_rx_preamble_mode = 1;
+	int two_tck_tx_dqs_pre = input->adv.d4tx_preamble_length;
+	int two_tck_rx_dqs_pre = input->adv.d4rx_preamble_length;
+
+	data = wdqsextension << csr_wdqsextension_lsb			|
+	       lp4sttc_pre_bridge_rx_en << csr_lp4sttc_pre_bridge_rx_en_lsb |
+	       lp4postamble_ext << csr_lp4postamble_ext_lsb		|
+	       lp4tgl_two_tck_tx_dqs_pre << csr_lp4tgl_two_tck_tx_dqs_pre_lsb |
+	       position_dfe_init << csr_position_dfe_init_lsb		|
+	       two_tck_tx_dqs_pre << csr_two_tck_tx_dqs_pre_lsb		|
+	       two_tck_rx_dqs_pre << csr_two_tck_rx_dqs_pre_lsb;
+	phy_io_write16(phy, addr, data);
+
+	data = dll_rx_preamble_mode << csr_dll_rx_preamble_mode_lsb;
+	addr = t_master | csr_dbyte_dll_mode_cntrl_addr;
+	phy_io_write16(phy, addr, data);
+}
+
+static void prog_proc_odt_time_ctl(uint16_t *phy,
+				   const struct input *input)
+{
+	int proc_odt_time_ctl;
+	uint32_t addr = t_master | csr_proc_odt_time_ctl_addr;
+
+	if (input->adv.wdqsext != 0) {
+		proc_odt_time_ctl = 0x3;
+	} else if (input->basic.frequency <= 933) {
+		proc_odt_time_ctl = 0xa;
+	} else if (input->basic.frequency <= 1200) {
+		if (input->adv.d4rx_preamble_length == 1) {
+			proc_odt_time_ctl = 0x2;
+		} else {
+			proc_odt_time_ctl = 0x6;
+		}
+	} else {
+		if (input->adv.d4rx_preamble_length == 1) {
+			proc_odt_time_ctl = 0x3;
+		} else {
+			proc_odt_time_ctl = 0x7;
+		}
+	}
+	phy_io_write16(phy, addr, proc_odt_time_ctl);
+}
+
+static const struct impedance_mapping map[] = {
+	{	29,	0x3f	},
+	{	31,	0x3e	},
+	{	33,	0x3b	},
+	{	36,	0x3a	},
+	{	39,	0x39	},
+	{	42,	0x38	},
+	{	46,	0x1b	},
+	{	51,	0x1a	},
+	{	57,	0x19	},
+	{	64,	0x18	},
+	{	74,	0x0b	},
+	{	88,	0x0a	},
+	{	108,	0x09	},
+	{	140,	0x08	},
+	{	200,	0x03	},
+	{	360,	0x02	},
+	{	481,	0x01	},
+	{}
+};
+
+static int map_impedance(int strength)
+{
+	const struct impedance_mapping *tbl = map;
+	int val = 0;
+
+	if (strength == 0) {
+		return 0;
+	}
+
+	while (tbl->ohm != 0U) {
+		if (strength < tbl->ohm) {
+			val = tbl->code;
+			break;
+		}
+		tbl++;
+	}
+
+	return val;
+}
+
+static int map_odtstren_p(int strength, int hard_macro_ver)
+{
+	int val = -1;
+
+	if (hard_macro_ver == 4) {
+		if (strength == 0) {
+			val = 0;
+		} else if (strength == 120) {
+			val = 0x8;
+		} else if (strength == 60) {
+			val = 0x18;
+		} else if (strength == 40) {
+			val = 0x38;
+		} else {
+			printf("error: unsupported ODTStrenP %d\n", strength);
+		}
+	} else {
+		val = map_impedance(strength);
+	}
+
+	return val;
+}
+
+static void prog_tx_odt_drv_stren(uint16_t *phy,
+				  const struct input *input)
+{
+	int lane, byte, b_addr, c_addr;
+	int tx_odt_drv_stren;
+	int odtstren_p, odtstren_n;
+	uint32_t addr;
+
+	odtstren_p = map_odtstren_p(input->adv.odtimpedance,
+				input->basic.hard_macro_ver);
+	if (odtstren_p < 0) {
+		return;
+	}
+
+	odtstren_n = 0;	/* always high-z */
+	tx_odt_drv_stren = odtstren_n << csr_odtstren_n_lsb | odtstren_p;
+	for (byte = 0; byte < input->basic.num_dbyte; byte++) {
+		c_addr = byte << 12;
+		for (lane = 0; lane <= 1; lane++) {
+			b_addr = lane << 8;
+			addr = t_dbyte | c_addr | b_addr |
+				csr_tx_odt_drv_stren_addr;
+			phy_io_write16(phy, addr, tx_odt_drv_stren);
+		}
+	}
+}
+
+static int map_drvstren_fsdq_p(int strength, int hard_macro_ver)
+{
+	int val = -1;
+
+	if (hard_macro_ver == 4) {
+		if (strength == 0) {
+			val = 0x07;
+		} else if (strength == 120) {
+			val = 0x0F;
+		} else if (strength == 60) {
+			val = 0x1F;
+		} else if (strength == 40) {
+			val = 0x3F;
+		} else {
+			printf("error: unsupported drv_stren_fSDq_p %d\n",
+			       strength);
+		}
+	} else {
+		val = map_impedance(strength);
+	}
+
+	return val;
+}
+
+static int map_drvstren_fsdq_n(int strength, int hard_macro_ver)
+{
+	int val = -1;
+
+	if (hard_macro_ver == 4) {
+		if (strength == 0) {
+			val = 0x00;
+		} else if (strength == 120) {
+			val = 0x08;
+		} else if (strength == 60) {
+			val = 0x18;
+		} else if (strength == 40) {
+			val = 0x38;
+		} else {
+			printf("error: unsupported drvStrenFSDqN %d\n",
+			       strength);
+		}
+	} else {
+		val = map_impedance(strength);
+	}
+
+	return val;
+}
+
+static void prog_tx_impedance_ctrl1(uint16_t *phy,
+				    const struct input *input)
+{
+	int lane, byte, b_addr, c_addr;
+	int tx_impedance_ctrl1;
+	int drv_stren_fsdq_p, drv_stren_fsdq_n;
+	uint32_t addr;
+
+	drv_stren_fsdq_p = map_drvstren_fsdq_p(input->adv.tx_impedance,
+					input->basic.hard_macro_ver);
+	drv_stren_fsdq_n = map_drvstren_fsdq_n(input->adv.tx_impedance,
+					input->basic.hard_macro_ver);
+	tx_impedance_ctrl1 = drv_stren_fsdq_n << csr_drv_stren_fsdq_n_lsb |
+			   drv_stren_fsdq_p << csr_drv_stren_fsdq_p_lsb;
+
+	for (byte = 0; byte < input->basic.num_dbyte; byte++) {
+		c_addr = byte << 12;
+		for (lane = 0; lane <= 1; lane++) {
+			b_addr = lane << 8;
+			addr = t_dbyte | c_addr | b_addr |
+				csr_tx_impedance_ctrl1_addr;
+			phy_io_write16(phy, addr, tx_impedance_ctrl1);
+		}
+	}
+}
+
+static int map_adrv_stren_p(int strength, int hard_macro_ver)
+{
+	int val = -1;
+
+	if (hard_macro_ver == 4) {
+		if (strength == 120) {
+			val = 0x1c;
+		} else if (strength == 60) {
+			val = 0x1d;
+		} else if (strength == 40) {
+			val = 0x1f;
+		} else {
+			printf("error: unsupported aDrv_stren_p %d\n",
+			       strength);
+		}
+	} else {
+		if (strength == 120) {
+			val = 0x00;
+		} else if (strength == 60) {
+			val = 0x01;
+		} else if (strength == 40) {
+			val = 0x03;
+		} else if (strength == 30) {
+			val = 0x07;
+		} else if (strength == 24) {
+			val = 0x0f;
+		} else if (strength == 20) {
+			val = 0x1f;
+		} else {
+			printf("error: unsupported aDrv_stren_p %d\n",
+			       strength);
+		}
+	}
+
+	return val;
+}
+
+static int map_adrv_stren_n(int strength, int hard_macro_ver)
+{
+	int val = -1;
+
+	if (hard_macro_ver == 4) {
+		if (strength == 120) {
+			val = 0x00;
+		} else if (strength == 60) {
+			val = 0x01;
+		} else if (strength == 40) {
+			val = 0x03;
+		} else {
+			printf("Error: unsupported ADrvStrenP %d\n", strength);
+		}
+	} else {
+		if (strength == 120) {
+			val = 0x00;
+		} else if (strength == 60) {
+			val = 0x01;
+		} else if (strength == 40) {
+			val = 0x03;
+		} else if (strength == 30) {
+			val = 0x07;
+		} else if (strength == 24) {
+			val = 0x0f;
+		} else if (strength == 20) {
+			val = 0x1f;
+		} else {
+			printf("Error: unsupported ADrvStrenP %d\n", strength);
+		}
+	}
+
+	return val;
+}
+
+static void prog_atx_impedance(uint16_t *phy,
+			       const struct input *input)
+{
+	int anib, c_addr;
+	int atx_impedance;
+	int adrv_stren_p;
+	int adrv_stren_n;
+	uint32_t addr;
+
+	if (input->basic.hard_macro_ver == 4 &&
+	    input->adv.atx_impedance == 20) {
+		printf("Error:ATxImpedance has to be 40 for HardMacroVer 4\n");
+		return;
+	}
+
+	adrv_stren_p = map_adrv_stren_p(input->adv.atx_impedance,
+					input->basic.hard_macro_ver);
+	adrv_stren_n = map_adrv_stren_n(input->adv.atx_impedance,
+					input->basic.hard_macro_ver);
+	atx_impedance = adrv_stren_n << csr_adrv_stren_n_lsb		|
+		       adrv_stren_p << csr_adrv_stren_p_lsb;
+	for (anib = 0; anib < input->basic.num_anib; anib++) {
+		c_addr = anib << 12;
+		addr = t_anib | c_addr | csr_atx_impedance_addr;
+		phy_io_write16(phy, addr, atx_impedance);
+	}
+}
+
+static void prog_dfi_mode(uint16_t *phy,
+			  const struct input *input)
+{
+	int dfi_mode;
+	uint32_t addr;
+
+	if (input->basic.dfi1exists == 1) {
+		dfi_mode = 0x5;	/* DFI1 exists but disabled */
+	} else {
+		dfi_mode = 0x1;	/* DFI1 does not physically exists */
+	}
+	addr = t_master | csr_dfi_mode_addr;
+	phy_io_write16(phy, addr, dfi_mode);
+}
+
+static void prog_acx4_anib_dis(uint16_t *phy, const struct input *input)
+{
+	uint32_t addr;
+
+	addr = t_master | csr_acx4_anib_dis_addr;
+	phy_io_write16(phy, addr, 0x0);
+	debug("%s 0x%x\n", __func__, phy_io_read16(phy, addr));
+}
+
+static void prog_dfi_camode(uint16_t *phy,
+			    const struct input *input)
+{
+	int dfi_camode = 2;
+	uint32_t addr = t_master | csr_dfi_camode_addr;
+
+	phy_io_write16(phy, addr, dfi_camode);
+}
+
+static void prog_cal_drv_str0(uint16_t *phy,
+			      const struct input *input)
+{
+	int cal_drv_str0;
+	int cal_drv_str_pd50;
+	int cal_drv_str_pu50;
+	uint32_t addr;
+
+	cal_drv_str_pu50 = input->adv.ext_cal_res_val;
+	cal_drv_str_pd50 = cal_drv_str_pu50;
+	cal_drv_str0 = cal_drv_str_pu50 << csr_cal_drv_str_pu50_lsb |
+			cal_drv_str_pd50;
+	addr = t_master | csr_cal_drv_str0_addr;
+	phy_io_write16(phy, addr, cal_drv_str0);
+}
+
+static void prog_cal_uclk_info(uint16_t *phy,
+			       const struct input *input)
+{
+	int cal_uclk_ticks_per1u_s;
+	uint32_t addr;
+
+	cal_uclk_ticks_per1u_s = input->basic.frequency >> 1;
+	if (cal_uclk_ticks_per1u_s < 24) {
+		cal_uclk_ticks_per1u_s = 24;
+	}
+
+	addr = t_master | csr_cal_uclk_info_addr;
+	phy_io_write16(phy, addr, cal_uclk_ticks_per1u_s);
+}
+
+static void prog_cal_rate(uint16_t *phy,
+			  const struct input *input)
+{
+	int cal_rate;
+	int cal_interval;
+	int cal_once;
+	uint32_t addr;
+
+	cal_interval = input->adv.cal_interval;
+	cal_once = input->adv.cal_once;
+	cal_rate = cal_once << csr_cal_once_lsb		|
+		  cal_interval << csr_cal_interval_lsb;
+	addr = t_master | csr_cal_rate_addr;
+	phy_io_write16(phy, addr, cal_rate);
+}
+
+static void prog_vref_in_global(uint16_t *phy,
+				const struct input *input,
+				const struct ddr4u1d *msg)
+{
+	int vref_in_global;
+	int global_vref_in_dac = 0;
+	int global_vref_in_sel = 0;
+	uint32_t addr;
+
+	/*
+	 * phy_vref_prcnt = msg->phy_vref / 128.0
+	 *  global_vref_in_dac = (phy_vref_prcnt - 0.345) / 0.005;
+	 */
+	global_vref_in_dac = (msg->phy_vref * 1000 - 345 * 128 + 320) /
+			     (5 * 128);
+
+	vref_in_global = global_vref_in_dac << csr_global_vref_in_dac_lsb |
+		       global_vref_in_sel;
+	addr = t_master | csr_vref_in_global_addr;
+	phy_io_write16(phy, addr, vref_in_global);
+}
+
+static void prog_dq_dqs_rcv_cntrl(uint16_t *phy,
+				  const struct input *input)
+{
+	int lane, byte, b_addr, c_addr;
+	int dq_dqs_rcv_cntrl;
+	int gain_curr_adj_defval = 0xb;
+	int major_mode_dbyte = 3;
+	int dfe_ctrl_defval = 0;
+	int ext_vref_range_defval = 0;
+	int sel_analog_vref = 1;
+	uint32_t addr;
+
+	dq_dqs_rcv_cntrl = gain_curr_adj_defval << csr_gain_curr_adj_lsb |
+			major_mode_dbyte << csr_major_mode_dbyte_lsb	|
+			dfe_ctrl_defval << csr_dfe_ctrl_lsb		|
+			ext_vref_range_defval << csr_ext_vref_range_lsb	|
+			sel_analog_vref << csr_sel_analog_vref_lsb;
+	for (byte = 0; byte < input->basic.num_dbyte; byte++) {
+		c_addr = byte << 12;
+		for (lane = 0; lane <= 1; lane++) {
+			b_addr = lane << 8;
+			addr = t_dbyte | c_addr | b_addr |
+					csr_dq_dqs_rcv_cntrl_addr;
+			phy_io_write16(phy, addr, dq_dqs_rcv_cntrl);
+		}
+	}
+}
+
+static void prog_mem_alert_control(uint16_t *phy,
+				   const struct input *input)
+{
+	int mem_alert_control;
+	int mem_alert_control2;
+	int malertpu_en;
+	int malertrx_en;
+	int malertvref_level;
+	int malertpu_stren;
+	int malertsync_bypass;
+	int malertdisable_val_defval = 1;
+	uint32_t addr;
+
+	if (input->basic.dram_type == DDR4 && input->adv.mem_alert_en == 1) {
+		malertpu_en = 1;
+		malertrx_en = 1;
+		malertpu_stren = input->adv.mem_alert_puimp;
+		malertvref_level = input->adv.mem_alert_vref_level;
+		malertsync_bypass = input->adv.mem_alert_sync_bypass;
+		mem_alert_control = malertdisable_val_defval << 14	|
+				  malertrx_en << 13		|
+				  malertpu_en << 12		|
+				  malertpu_stren << 8		|
+				  malertvref_level;
+		mem_alert_control2 = malertsync_bypass <<
+					csr_malertsync_bypass_lsb;
+		addr = t_master | csr_mem_alert_control_addr;
+		phy_io_write16(phy, addr, mem_alert_control);
+		addr = t_master | csr_mem_alert_control2_addr;
+		phy_io_write16(phy, addr, mem_alert_control2);
+	}
+}
+
+static void prog_dfi_freq_ratio(uint16_t *phy,
+				const struct input *input)
+{
+	int dfi_freq_ratio;
+	uint32_t addr = t_master | csr_dfi_freq_ratio_addr;
+
+	dfi_freq_ratio = input->basic.dfi_freq_ratio;
+	phy_io_write16(phy, addr, dfi_freq_ratio);
+}
+
+static void prog_tristate_mode_ca(uint16_t *phy,
+				  const struct input *input)
+{
+	int tristate_mode_ca;
+	int dis_dyn_adr_tri;
+	int ddr2tmode;
+	int ck_dis_val_def = 1;
+	uint32_t addr = t_master | csr_tristate_mode_ca_addr;
+
+	dis_dyn_adr_tri = input->adv.dis_dyn_adr_tri;
+	ddr2tmode = input->adv.is2ttiming;
+	tristate_mode_ca = ck_dis_val_def << csr_ck_dis_val_lsb	|
+			 ddr2tmode << csr_ddr2tmode_lsb		|
+			 dis_dyn_adr_tri << csr_dis_dyn_adr_tri_lsb;
+	phy_io_write16(phy, addr, tristate_mode_ca);
+}
+
+static void prog_dfi_xlat(uint16_t *phy,
+			  const struct input *input)
+{
+	uint16_t loop_vector;
+	int dfifreqxlat_dat;
+	int pllbypass_dat;
+	uint32_t addr;
+
+	/* fIXME: Shall unused P1, P2, P3 be bypassed? */
+	pllbypass_dat = input->basic.pll_bypass; /* only [0] is used */
+	for (loop_vector = 0; loop_vector < 8; loop_vector++) {
+		if (loop_vector == 0) {
+			dfifreqxlat_dat = pllbypass_dat + 0x5555;
+		} else if (loop_vector == 7) {
+			dfifreqxlat_dat = 0xf000;
+		} else {
+			dfifreqxlat_dat = 0x5555;
+		}
+		addr = t_master | (csr_dfi_freq_xlat0_addr + loop_vector);
+		phy_io_write16(phy, addr, dfifreqxlat_dat);
+	}
+}
+
+static void prog_dbyte_misc_mode(uint16_t *phy,
+				 const struct input *input,
+				 const struct ddr4u1d *msg)
+{
+	int dbyte_misc_mode;
+	int dq_dqs_rcv_cntrl1;
+	int dq_dqs_rcv_cntrl1_1;
+	int byte, c_addr;
+	uint32_t addr;
+
+	dbyte_misc_mode = 0x1 << csr_dbyte_disable_lsb;
+	dq_dqs_rcv_cntrl1 = 0x1ff << csr_power_down_rcvr_lsb		|
+			 0x1 << csr_power_down_rcvr_dqs_lsb	|
+			 0x1 << csr_rx_pad_standby_en_lsb;
+	dq_dqs_rcv_cntrl1_1 = (0x100 << csr_power_down_rcvr_lsb |
+			csr_rx_pad_standby_en_mask);
+	for (byte = 0; byte < input->basic.num_dbyte; byte++) {
+		c_addr = byte << 12;
+		if (byte <= input->basic.num_active_dbyte_dfi0 - 1) {
+			/* disable RDBI lane if not used. */
+			if ((input->basic.dram_data_width != 4) &&
+				(((msg->mr5 >> 12) & 0x1) == 0)) {
+				addr = t_dbyte
+					| c_addr
+					| csr_dq_dqs_rcv_cntrl1_addr;
+				phy_io_write16(phy, addr, dq_dqs_rcv_cntrl1_1);
+			}
+		} else {
+			addr = t_dbyte | c_addr | csr_dbyte_misc_mode_addr;
+			phy_io_write16(phy, addr, dbyte_misc_mode);
+			addr = t_dbyte | c_addr | csr_dq_dqs_rcv_cntrl1_addr;
+			phy_io_write16(phy, addr, dq_dqs_rcv_cntrl1);
+		}
+	}
+}
+
+static void prog_master_x4config(uint16_t *phy,
+				 const struct input *input)
+{
+	int master_x4config;
+	int x4tg;
+	uint32_t addr = t_master | csr_master_x4config_addr;
+
+	x4tg = input->basic.dram_data_width == 4 ? 0xf : 0;
+	master_x4config = x4tg << csr_x4tg_lsb;
+	phy_io_write16(phy, addr, master_x4config);
+}
+
+static void prog_dmipin_present(uint16_t *phy,
+				const struct input *input,
+				const struct ddr4u1d *msg)
+{
+	int dmipin_present;
+	uint32_t addr = t_master | csr_dmipin_present_addr;
+
+	dmipin_present = (msg->mr5 >> 12) & 0x1;
+	phy_io_write16(phy, addr, dmipin_present);
+}
+
+static void prog_dfi_phyupd(uint16_t *phy,
+			  const struct input *input)
+{
+	int dfiphyupd_dat;
+	uint32_t addr;
+
+	addr = t_master | (csr_dfiphyupd_addr);
+	dfiphyupd_dat = phy_io_read16(phy, addr) &
+				~csr_dfiphyupd_threshold_mask;
+
+	phy_io_write16(phy, addr, dfiphyupd_dat);
+}
+
+static void prog_cal_misc2(uint16_t *phy,
+			  const struct input *input)
+{
+	int cal_misc2_dat, cal_drv_pdth_data, cal_offsets_dat;
+	uint32_t addr;
+
+	addr = t_master | (csr_cal_misc2_addr);
+	cal_misc2_dat = phy_io_read16(phy, addr) |
+			(1 << csr_cal_misc2_err_dis);
+
+	phy_io_write16(phy, addr, cal_misc2_dat);
+
+	addr = t_master | (csr_cal_offsets_addr);
+
+	cal_drv_pdth_data = 0x9 << 6;
+	cal_offsets_dat = (phy_io_read16(phy, addr) & ~csr_cal_drv_pdth_mask)
+			| cal_drv_pdth_data;
+
+	phy_io_write16(phy, addr, cal_offsets_dat);
+}
+
+static int c_init_phy_config(uint16_t **phy_ptr,
+			     unsigned int ip_rev,
+			     const struct input *input,
+			     const void *msg)
+{
+	int i;
+	uint16_t *phy;
+	__unused const soc_info_t *soc_info;
+
+	for (i = 0; i < NUM_OF_DDRC; i++) {
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+
+		debug("Initialize PHY %d config\n", i);
+		prog_dfi_phyupd(phy, input);
+		prog_cal_misc2(phy, input);
+		prog_tx_pre_drv_mode(phy, input);
+		prog_atx_pre_drv_mode(phy, input);
+		prog_enable_cs_multicast(phy, input);	/* rdimm and lrdimm */
+		prog_dfi_rd_data_cs_dest_map(phy, ip_rev, input, msg);
+		prog_pll_ctrl2(phy, input);
+#ifdef DDR_PLL_FIX
+		soc_info = get_soc_info();
+		debug("SOC_SI_REV = %x\n", soc_info->svr_reg.bf.maj_ver);
+		if (soc_info->svr_reg.bf.maj_ver == 1) {
+			prog_pll_pwr_dn(phy, input);
+
+			/*Enable FFE aka TxEqualizationMode for rev1 SI*/
+			phy_io_write16(phy, 0x010048, 0x1);
+		}
+#endif
+		prog_ard_ptr_init_val(phy, input);
+		prog_dqs_preamble_control(phy, input);
+		prog_dll_lck_param(phy, input);
+		prog_dll_gain_ctl(phy, input);
+		prog_proc_odt_time_ctl(phy, input);
+		prog_tx_odt_drv_stren(phy, input);
+		prog_tx_impedance_ctrl1(phy, input);
+		prog_atx_impedance(phy, input);
+		prog_dfi_mode(phy, input);
+		prog_dfi_camode(phy, input);
+		prog_cal_drv_str0(phy, input);
+		prog_cal_uclk_info(phy, input);
+		prog_cal_rate(phy, input);
+		prog_vref_in_global(phy, input, msg);
+		prog_dq_dqs_rcv_cntrl(phy, input);
+		prog_mem_alert_control(phy, input);
+		prog_dfi_freq_ratio(phy, input);
+		prog_tristate_mode_ca(phy, input);
+		prog_dfi_xlat(phy, input);
+		prog_dbyte_misc_mode(phy, input, msg);
+		prog_master_x4config(phy, input);
+		prog_dmipin_present(phy, input, msg);
+		prog_acx4_anib_dis(phy, input);
+	}
+
+	return 0;
+}
+
+static uint32_t get_mail(uint16_t *phy, int stream)
+{
+	int timeout;
+	uint32_t mail = 0U;
+
+	timeout = TIMEOUTDEFAULT;
+	while (((--timeout) != 0) &&
+	       ((phy_io_read16(phy, t_apbonly | csr_uct_shadow_regs)
+		& uct_write_prot_shadow_mask) != 0)) {
+		mdelay(10);
+	}
+	if (timeout == 0) {
+		ERROR("Timeout getting mail from PHY\n");
+		return 0xFFFF;
+	}
+
+	mail = phy_io_read16(phy, t_apbonly |
+			     csr_uct_write_only_shadow);
+	if (stream != 0) {
+		mail |= phy_io_read16(phy, t_apbonly |
+				      csr_uct_dat_write_only_shadow) << 16;
+	}
+
+	/* Ack */
+	phy_io_write16(phy, t_apbonly | csr_dct_write_prot, 0);
+
+	timeout = TIMEOUTDEFAULT;
+	while (((--timeout) != 0) &&
+	       ((phy_io_read16(phy, t_apbonly | csr_uct_shadow_regs)
+		 & uct_write_prot_shadow_mask) == 0)) {
+		mdelay(1);
+	}
+	if (timeout == 0) {
+		ERROR("Timeout ack PHY mail\n");
+	}
+
+	/* completed */
+	phy_io_write16(phy, t_apbonly | csr_dct_write_prot, 1U);
+
+	return mail;
+}
+
+#ifdef DDR_PHY_DEBUG
+static const char *lookup_msg(uint32_t index, int train2d)
+{
+	int i;
+	int size;
+	const struct phy_msg *messages;
+	const char *ptr = NULL;
+
+	if (train2d != 0) {
+		messages = messages_2d;
+		size = ARRAY_SIZE(messages_2d);
+	} else {
+		messages = messages_1d;
+		size = ARRAY_SIZE(messages_1d);
+	}
+	for (i = 0; i < size; i++) {
+		if (messages[i].index == index) {
+			ptr = messages[i].msg;
+			break;
+		}
+	}
+
+	return ptr;
+}
+#endif
+
+#define MAX_ARGS 32
+static void decode_stream_message(uint16_t *phy, int train2d)
+{
+	uint32_t index __unused;
+
+	__unused const char *format;
+	__unused uint32_t args[MAX_ARGS];
+	__unused int i;
+
+#ifdef DDR_PHY_DEBUG
+	index = get_mail(phy, 1);
+	if ((index & 0xffff) > MAX_ARGS) {	/* up to MAX_ARGS args so far */
+		printf("Program error in %s\n", __func__);
+	}
+	for (i = 0; i < (index & 0xffff) && i < MAX_ARGS; i++) {
+		args[i] = get_mail(phy, 1);
+	}
+
+	format = lookup_msg(index, train2d);
+	if (format != NULL) {
+		printf("0x%08x: ", index);
+		printf(format, args[0], args[1], args[2], args[3], args[4],
+		       args[5], args[6], args[7], args[8], args[9], args[10],
+		       args[11], args[12], args[13], args[14], args[15],
+		       args[16], args[17], args[18], args[19], args[20],
+		       args[21], args[22], args[23], args[24], args[25],
+		       args[26], args[27], args[28], args[29], args[30],
+		       args[31]);
+	}
+#endif
+}
+
+static int wait_fw_done(uint16_t *phy, int train2d)
+{
+	uint32_t mail = 0U;
+
+	while (mail == U(0x0)) {
+		mail = get_mail(phy, 0);
+		switch (mail) {
+		case U(0x7):
+			debug("%s Training completed\n", train2d ? "2D" : "1D");
+			break;
+		case U(0xff):
+			debug("%s Training failure\n", train2d ? "2D" : "1D");
+			break;
+		case U(0x0):
+			debug("End of initialization\n");
+			mail = 0U;
+			break;
+		case U(0x1):
+			debug("End of fine write leveling\n");
+			mail = 0U;
+			break;
+		case U(0x2):
+			debug("End of read enable training\n");
+			mail = 0U;
+			break;
+		case U(0x3):
+			debug("End of read delay center optimization\n");
+			mail = 0U;
+			break;
+		case U(0x4):
+			debug("End of write delay center optimization\n");
+			mail = 0U;
+			break;
+		case U(0x5):
+			debug("End of 2D read delay/voltage center optimztn\n");
+			mail = 0U;
+			break;
+		case U(0x6):
+			debug("End of 2D write delay/voltage center optmztn\n");
+			mail = 0U;
+			break;
+		case U(0x8):
+			decode_stream_message(phy, train2d);
+			mail = 0U;
+			break;
+		case U(0x9):
+			debug("End of max read latency training\n");
+			mail = 0U;
+			break;
+		case U(0xa):
+			debug("End of read dq deskew training\n");
+			mail = 0U;
+			break;
+		case U(0xc):
+			debug("End of LRDIMM Specific training, including:\n");
+			debug("/tDWL, MREP, MRD and MWD\n");
+			mail = 0U;
+			break;
+		case U(0xd):
+			debug("End of CA training\n");
+			mail = 0U;
+			break;
+		case U(0xfd):
+			debug("End of MPR read delay center optimization\n");
+			mail = 0U;
+			break;
+		case U(0xfe):
+			debug("End of Write leveling coarse delay\n");
+			mail = 0U;
+			break;
+		case U(0xffff):
+			debug("Timed out\n");
+			break;
+		default:
+			mail = 0U;
+			break;
+		}
+	}
+
+	if (mail == U(0x7)) {
+		return 0;
+	} else if (mail == U(0xff)) {
+		return -EIO;
+	} else if (mail == U(0xffff)) {
+		return -ETIMEDOUT;
+	}
+
+	debug("PHY_GEN2 FW: Unxpected mail = 0x%x\n", mail);
+
+	return -EINVAL;
+}
+
+static int g_exec_fw(uint16_t **phy_ptr, int train2d, struct input *input)
+{
+	int ret = -EINVAL;
+	int i;
+	uint16_t *phy;
+
+	for (i = 0; i < NUM_OF_DDRC; i++) {
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+		debug("Applying PLL optimal settings\n");
+		prog_pll_ctrl2(phy, input);
+		prog_pll_ctrl(phy, input);
+		phy_io_write16(phy,
+			       t_apbonly | csr_micro_cont_mux_sel_addr,
+			       0x1);
+		phy_io_write16(phy,
+			       t_apbonly | csr_micro_reset_addr,
+			       csr_reset_to_micro_mask |
+			       csr_stall_to_micro_mask);
+		phy_io_write16(phy,
+			       t_apbonly | csr_micro_reset_addr,
+			       csr_stall_to_micro_mask);
+		phy_io_write16(phy,
+			       t_apbonly | csr_micro_reset_addr,
+			       0);
+
+		ret = wait_fw_done(phy, train2d);
+		if (ret == -ETIMEDOUT) {
+			ERROR("Wait timed out: Firmware execution on PHY %d\n",
+			      i);
+		}
+	}
+	return ret;
+}
+
+static inline int send_fw(uint16_t *phy,
+			   uint32_t dst,
+			   uint16_t *img,
+			   uint32_t size)
+{
+	uint32_t i;
+
+	if ((size % 2U) != 0U) {
+		ERROR("Wrong image size 0x%x\n", size);
+		return -EINVAL;
+	}
+
+	for (i = 0U; i < size / 2; i++) {
+		phy_io_write16(phy, dst + i, *(img + i));
+	}
+
+	return 0;
+}
+
+static int load_fw(uint16_t **phy_ptr,
+		   struct input *input,
+		   int train2d,
+		   void *msg,
+		   size_t len,
+		   uintptr_t phy_gen2_fw_img_buf,
+		   int (*img_loadr)(unsigned int, uintptr_t *, uint32_t *),
+		   uint32_t warm_boot_flag)
+{
+	uint32_t imem_id, dmem_id;
+	uintptr_t image_buf;
+	uint32_t size;
+	int ret;
+	int i;
+	uint16_t *phy;
+
+	switch (input->basic.dimm_type) {
+	case UDIMM:
+	case SODIMM:
+	case NODIMM:
+		imem_id = train2d ? DDR_IMEM_UDIMM_2D_IMAGE_ID :
+			  DDR_IMEM_UDIMM_1D_IMAGE_ID;
+		dmem_id = train2d ? DDR_DMEM_UDIMM_2D_IMAGE_ID :
+			  DDR_DMEM_UDIMM_1D_IMAGE_ID;
+		break;
+	case RDIMM:
+		imem_id = train2d ? DDR_IMEM_RDIMM_2D_IMAGE_ID :
+			  DDR_IMEM_RDIMM_1D_IMAGE_ID;
+		dmem_id = train2d ? DDR_DMEM_RDIMM_2D_IMAGE_ID :
+			  DDR_DMEM_RDIMM_1D_IMAGE_ID;
+		break;
+	default:
+		ERROR("Unsupported DIMM type\n");
+		return -EINVAL;
+	}
+
+	size = PHY_GEN2_MAX_IMAGE_SIZE;
+	image_buf = (uintptr_t)phy_gen2_fw_img_buf;
+	mmap_add_dynamic_region(phy_gen2_fw_img_buf,
+			phy_gen2_fw_img_buf,
+			PHY_GEN2_MAX_IMAGE_SIZE,
+			MT_MEMORY | MT_RW | MT_SECURE);
+	ret = img_loadr(imem_id, &image_buf, &size);
+	if (ret != 0) {
+		ERROR("Failed to load %d firmware.\n", imem_id);
+		return ret;
+	}
+	debug("Loaded Imaged id %d of size %x at address %lx\n",
+						imem_id, size, image_buf);
+
+	for (i = 0; i < NUM_OF_DDRC; i++) {
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+
+		if (warm_boot_flag != DDR_WARM_BOOT) {
+			if (train2d == 0) {
+				phy_io_write16(phy, t_master |
+						csr_mem_reset_l_addr,
+						csr_protect_mem_reset_mask);
+			}
+		}
+		/* Enable access to the internal CSRs */
+		phy_io_write16(phy, t_apbonly | csr_micro_cont_mux_sel_addr, 0);
+
+		ret = send_fw(phy, PHY_GEN2_IMEM_ADDR,
+			      (uint16_t *)image_buf, size);
+		if (ret != 0) {
+			return ret;
+		}
+	}
+
+	size = PHY_GEN2_MAX_IMAGE_SIZE;
+	image_buf = (uintptr_t)phy_gen2_fw_img_buf;
+	ret = img_loadr(dmem_id, &image_buf, &size);
+	if (ret != 0) {
+		ERROR("Failed to load %d firmware.\n", dmem_id);
+		return ret;
+	}
+	debug("Loaded Imaged id %d of size %x at address %lx\n",
+						dmem_id, size, image_buf);
+	image_buf += len;
+	size -= len;
+
+	for (i = 0; i < NUM_OF_DDRC; i++) {
+		phy = phy_ptr[i];
+		if (phy == NULL) {
+			continue;
+		}
+
+		ret = send_fw(phy, PHY_GEN2_DMEM_ADDR, msg, len);
+		if (ret != 0) {
+			return ret;
+		}
+
+		ret = send_fw(phy, PHY_GEN2_DMEM_ADDR + len / 2,
+			      (uint16_t *)image_buf, size);
+		if (ret != 0) {
+			return ret;
+		}
+	}
+
+	return ret;
+}
+
+static void parse_odt(const unsigned int val,
+		       const int read,
+		       const int i,
+		       const unsigned int cs_d0,
+		       const unsigned int cs_d1,
+		       unsigned int *odt)
+{
+	int shift = read ? 4 : 0;
+	int j;
+
+	if (i < 0 || i > 3) {
+		printf("Error: invalid chip-select value\n");
+	}
+	switch (val) {
+	case DDR_ODT_CS:
+		odt[i] |= (1 << i) << shift;
+		break;
+	case DDR_ODT_ALL_OTHER_CS:
+		for (j = 0; j < DDRC_NUM_CS; j++) {
+			if (i == j) {
+				continue;
+			}
+			if (((cs_d0 | cs_d1) & (1 << j)) == 0) {
+				continue;
+			}
+			odt[j] |= (1 << i) << shift;
+		}
+		break;
+	case DDR_ODT_CS_AND_OTHER_DIMM:
+		odt[i] |= (1 << i) << 4;
+		/* fallthrough */
+	case DDR_ODT_OTHER_DIMM:
+		for (j = 0; j < DDRC_NUM_CS; j++) {
+			if ((((cs_d0 & (1 << i)) != 0) &&
+						((cs_d1 & (1 << j)) != 0)) ||
+			    (((cs_d1 & (1 << i)) != 0) &&
+						((cs_d0 & (1 << j)) != 0))) {
+				odt[j] |= (1 << i) << shift;
+			}
+		}
+		break;
+	case DDR_ODT_ALL:
+		for (j = 0; j < DDRC_NUM_CS; j++) {
+			if (((cs_d0 | cs_d1) & (1 << j)) == 0) {
+				continue;
+			}
+			odt[j] |= (1 << i) << shift;
+		}
+		break;
+	case DDR_ODT_SAME_DIMM:
+		for (j = 0; j < DDRC_NUM_CS; j++) {
+			if ((((cs_d0 & (1 << i)) != 0) &&
+						((cs_d0 & (1 << j)) != 0)) ||
+			    (((cs_d1 & (1 << i)) != 0) &&
+						((cs_d1 & (1 << j)) != 0))) {
+				odt[j] |= (1 << i) << shift;
+			}
+		}
+		break;
+	case DDR_ODT_OTHER_CS_ONSAMEDIMM:
+		for (j = 0; j < DDRC_NUM_CS; j++) {
+			if (i == j) {
+				continue;
+			}
+			if ((((cs_d0 & (1 << i)) != 0) &&
+						((cs_d0 & (1 << j)) != 0)) ||
+			    (((cs_d1 & (1 << i)) != 0) &&
+						((cs_d1 & (1 << j)) != 0))) {
+				odt[j] |= (1 << i) << shift;
+			}
+		}
+		break;
+	case DDR_ODT_NEVER:
+		break;
+	default:
+		break;
+	}
+}
+
+#ifdef DEBUG_DDR_INPUT_CONFIG
+char *dram_types_str[] = {
+		"DDR4",
+		"DDR3",
+		"LDDDR4",
+		"LPDDR3",
+		"LPDDR2",
+		"DDR5"
+};
+
+char *dimm_types_str[] = {
+		"UDIMM",
+		"SODIMM",
+		"RDIMM",
+		"LRDIMM",
+		"NODIMM",
+};
+
+
+static void print_jason_format(struct input *input,
+			       struct ddr4u1d *msg_1d,
+			       struct ddr4u2d *msg_2d)
+{
+
+	printf("\n{");
+	printf("\n    \"dram_type\": \"%s\",", dram_types_str[input->basic.dram_type]);
+	printf("\n    \"dimm_type\": \"%s\",", dimm_types_str[input->basic.dimm_type]);
+	printf("\n    \"hard_macro_ver\": \"%d\",", input->basic.hard_macro_ver);
+	printf("\n    \"num_dbyte\": \"0x%04x\",", (unsigned int)input->basic.num_dbyte);
+	printf("\n    \"num_active_dbyte_dfi0\": \"0x%04x\",", (unsigned int)input->basic.num_active_dbyte_dfi0);
+	printf("\n    \"num_anib\": \"0x%04x\",", (unsigned int)input->basic.num_anib);
+	printf("\n    \"num_rank_dfi0\": \"0x%04x\",", (unsigned int)input->basic.num_rank_dfi0);
+	printf("\n    \"num_pstates\": \"0x%04x\",", (unsigned int)input->basic.num_pstates);
+	printf("\n    \"frequency\": \"%d\",", input->basic.frequency);
+	printf("\n    \"pll_bypass\": \"0x%04x\",", (unsigned int)input->basic.dfi_freq_ratio);
+	printf("\n    \"dfi_freq_ratio\": \"0x%04x\",", (unsigned int)input->basic.dfi_freq_ratio);
+	printf("\n    \"dfi1_exists\":  \"0x%04x\",", (unsigned int)input->basic.dfi1exists);
+	printf("\n    \"dram_data_width\": \"0x%04x\",", (unsigned int)input->basic.dram_data_width);
+	printf("\n    \"dram_byte_swap\": \"0x%04x\",", (unsigned int)input->adv.dram_byte_swap);
+	printf("\n    \"ext_cal_res_val\": \"0x%04x\",", (unsigned int)input->adv.ext_cal_res_val);
+	printf("\n    \"tx_slew_rise_dq\": \"0x%04x\",", (unsigned int)input->adv.tx_slew_rise_dq);
+	printf("\n    \"tx_slew_fall_dq\": \"0x%04x\",", (unsigned int)input->adv.tx_slew_fall_dq);
+	printf("\n    \"tx_slew_rise_ac\": \"0x%04x\",", (unsigned int)input->adv.tx_slew_rise_ac);
+	printf("\n    \"tx_slew_fall_ac\": \"0x%04x\",", (unsigned int)input->adv.tx_slew_fall_ac);
+	printf("\n    \"odt_impedance\": \"%d\",", input->adv.odtimpedance);
+	printf("\n    \"tx_impedance\": \"%d\",", input->adv.tx_impedance);
+	printf("\n    \"atx_impedance\": \"%d\",", input->adv.atx_impedance);
+	printf("\n    \"mem_alert_en\": \"0x%04x\",", (unsigned int)input->adv.mem_alert_en);
+	printf("\n    \"mem_alert_pu_imp\": \"0x%04x\",", (unsigned int)input->adv.mem_alert_puimp);
+	printf("\n    \"mem_alert_vref_level\": \"0x%04x\",", (unsigned int)input->adv.mem_alert_vref_level);
+	printf("\n    \"mem_alert_sync_bypass\": \"0x%04x\",", (unsigned int)input->adv.mem_alert_sync_bypass);
+	printf("\n    \"cal_interval\": \"0x%04x\",", (unsigned int)input->adv.cal_interval);
+	printf("\n    \"cal_once\": \"0x%04x\",", (unsigned int)input->adv.cal_once);
+	printf("\n    \"dis_dyn_adr_tri\": \"0x%04x\",", (unsigned int)input->adv.dis_dyn_adr_tri);
+	printf("\n    \"is2t_timing\": \"0x%04x\",", (unsigned int)input->adv.is2ttiming);
+	printf("\n    \"d4rx_preabmle_length\": \"0x%04x\",", (unsigned int)input->adv.d4rx_preamble_length);
+	printf("\n    \"d4tx_preamble_length\": \"0x%04x\",", (unsigned int)input->adv.d4tx_preamble_length);
+	printf("\n    \"msg_misc\": \"0x%02x\",", (unsigned int)msg_1d->msg_misc);
+	printf("\n    \"reserved00\": \"0x%01x\",", (unsigned int)msg_1d->reserved00);
+	printf("\n    \"hdt_ctrl\": \"0x%02x\",", (unsigned int)msg_1d->hdt_ctrl);
+	printf("\n    \"cs_present\": \"0x%02x\",", (unsigned int)msg_1d->cs_present);
+	printf("\n    \"phy_vref\": \"0x%02x\",", (unsigned int)msg_1d->phy_vref);
+	printf("\n    \"dfi_mrl_margin\": \"0x%02x\",", (unsigned int)msg_1d->dfimrlmargin);
+	printf("\n    \"addr_mirror\": \"0x%02x\",", (unsigned int)msg_1d->addr_mirror);
+	printf("\n    \"wr_odt_pat_rank0\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl0 & 0x0f));
+	printf("\n    \"wr_odt_pat_rank1\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl1 & 0x0f));
+	printf("\n    \"wr_odt_pat_rank2\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl2 & 0x0f));
+	printf("\n    \"wr_odt_pat_rank3\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl3 & 0x0f));
+	printf("\n    \"rd_odt_pat_rank0\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl0 & 0xf0));
+	printf("\n    \"rd_odt_pat_rank1\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl1 & 0xf0));
+	printf("\n    \"rd_odt_pat_rank2\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl2 & 0xf0));
+	printf("\n    \"rd_odt_pat_rank3\": \"0x%02x\",", (unsigned int)(msg_1d->acsm_odt_ctrl3 & 0xf0));
+	printf("\n    \"d4_misc\": \"0x%01x\",", (unsigned int)msg_1d->d4misc);
+	printf("\n    \"share_2d_vref_results\": \"0x%01x\",", (unsigned int)msg_1d->share2dvref_result);
+	printf("\n    \"sequence_ctrl\": \"0x%04x\",", (unsigned int)msg_1d->sequence_ctrl);
+	printf("\n    \"mr0\": \"0x%04x\",", (unsigned int)msg_1d->mr0);
+	printf("\n    \"mr1\": \"0x%04x\",", (unsigned int)msg_1d->mr1);
+	printf("\n    \"mr2\": \"0x%04x\",", (unsigned int)msg_1d->mr2);
+	printf("\n    \"mr3\": \"0x%04x\",", (unsigned int)msg_1d->mr3);
+	printf("\n    \"mr4\": \"0x%04x\",", (unsigned int)msg_1d->mr4);
+	printf("\n    \"mr5\": \"0x%04x\",", (unsigned int)msg_1d->mr5);
+	printf("\n    \"mr6\": \"0x%04x\",", (unsigned int)msg_1d->mr6);
+	printf("\n    \"alt_cal_l\": \"0x%04x\",", (unsigned int)msg_1d->alt_cas_l);
+	printf("\n    \"alt_wcal_l\": \"0x%04x\",", (unsigned int)msg_1d->alt_wcas_l);
+	printf("\n    \"sequence_ctrl_2d\": \"0x%04x\",", (unsigned int)msg_2d->sequence_ctrl);
+	printf("\n    \"rtt_nom_wr_park0\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park0);
+	printf("\n    \"rtt_nom_wr_park1\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park1);
+	printf("\n    \"rtt_nom_wr_park2\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park2);
+	printf("\n    \"rtt_nom_wr_park3\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park3);
+	printf("\n    \"rtt_nom_wr_park4\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park4);
+	printf("\n    \"rtt_nom_wr_park5\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park5);
+	printf("\n    \"rtt_nom_wr_park6\": \"0x%01x\",", (unsigned int)msg_1d->rtt_nom_wr_park6);
+	printf("\n    \"rtt_nom_wr_park7\": \"0x%01x\"", (unsigned int)msg_1d->rtt_nom_wr_park7);
+	printf("\n}");
+	printf("\n");
+}
+#endif
+
+int compute_ddr_phy(struct ddr_info *priv)
+{
+	const unsigned long clk = priv->clk;
+	const struct memctl_opt *popts = &priv->opt;
+	const struct ddr_conf *conf = &priv->conf;
+	const struct dimm_params *dimm_param = &priv->dimm;
+	struct ddr_cfg_regs *regs = &priv->ddr_reg;
+	int ret;
+	static struct input input;
+	static struct ddr4u1d msg_1d;
+	static struct ddr4u2d msg_2d;
+	unsigned int i;
+	unsigned int odt_rd, odt_wr;
+	__unused const soc_info_t *soc_info;
+#ifdef NXP_APPLY_MAX_CDD
+	unsigned int tcfg0, tcfg4, rank;
+#endif
+
+	if (dimm_param == NULL) {
+		ERROR("Empty DIMM parameters.\n");
+		return -EINVAL;
+	}
+
+	zeromem(&input, sizeof(input));
+	zeromem(&msg_1d, sizeof(msg_1d));
+	zeromem(&msg_2d, sizeof(msg_2d));
+
+	input.basic.dram_type = DDR4;
+	/* FIXME: Add condition for LRDIMM */
+	input.basic.dimm_type = (dimm_param->rdimm != 0) ? RDIMM : UDIMM;
+	input.basic.num_dbyte = dimm_param->primary_sdram_width / 8 +
+				 dimm_param->ec_sdram_width / 8;
+	input.basic.num_active_dbyte_dfi0 = input.basic.num_dbyte;
+	input.basic.num_rank_dfi0 = dimm_param->n_ranks;
+	input.basic.dram_data_width = dimm_param->device_width;
+	input.basic.hard_macro_ver	= 0xa;
+	input.basic.num_pstates	= 1;
+	input.basic.dfi_freq_ratio	= 1;
+	input.basic.num_anib		= 0xc;
+	input.basic.train2d		= popts->skip2d ? 0 : 1;
+	input.basic.frequency = (int) (clk / 2000000ul);
+	debug("frequency = %dMHz\n", input.basic.frequency);
+	input.cs_d0 = conf->cs_on_dimm[0];
+#if DDRC_NUM_DIMM > 1
+	input.cs_d1 = conf->cs_on_dimm[1];
+#endif
+	input.mirror = dimm_param->mirrored_dimm;
+	input.mr[0] = regs->sdram_mode[0] & U(0xffff);
+	input.mr[1] = regs->sdram_mode[0] >> 16U;
+	input.mr[2] = regs->sdram_mode[1] >> 16U;
+	input.mr[3] = regs->sdram_mode[1] & U(0xffff);
+	input.mr[4] = regs->sdram_mode[8] >> 16U;
+	input.mr[5] = regs->sdram_mode[8] & U(0xffff);
+	input.mr[6] = regs->sdram_mode[9] >> 16U;
+	input.vref = popts->vref_phy;
+	debug("Vref_phy = %d percent\n", (input.vref * 100U) >> 7U);
+	for (i = 0U; i < DDRC_NUM_CS; i++) {
+		if ((regs->cs[i].config & SDRAM_CS_CONFIG_EN) == 0U) {
+			continue;
+		}
+		odt_rd = (regs->cs[i].config >> 20U) & U(0x7);
+		odt_wr = (regs->cs[i].config >> 16U) & U(0x7);
+		parse_odt(odt_rd, true, i, input.cs_d0, input.cs_d1,
+			   input.odt);
+		parse_odt(odt_wr, false, i, input.cs_d0, input.cs_d1,
+			   input.odt);
+	}
+
+	/* Do not set sdram_cfg[RD_EN] or sdram_cfg2[RCW_EN] for RDIMM */
+	if (dimm_param->rdimm != 0U) {
+		regs->sdram_cfg[0] &= ~(1 << 28U);
+		regs->sdram_cfg[1] &= ~(1 << 2U);
+		input.rcw[0] = (regs->sdram_rcw[0] >> 28U) & U(0xf);
+		input.rcw[1] = (regs->sdram_rcw[0] >> 24U) & U(0xf);
+		input.rcw[2] = (regs->sdram_rcw[0] >> 20U) & U(0xf);
+		input.rcw[3] = (regs->sdram_rcw[0] >> 16U) & U(0xf);
+		input.rcw[4] = (regs->sdram_rcw[0] >> 12U) & U(0xf);
+		input.rcw[5] = (regs->sdram_rcw[0] >> 8U) & U(0xf);
+		input.rcw[6] = (regs->sdram_rcw[0] >> 4U) & U(0xf);
+		input.rcw[7] = (regs->sdram_rcw[0] >> 0U) & U(0xf);
+		input.rcw[8] = (regs->sdram_rcw[1] >> 28U) & U(0xf);
+		input.rcw[9] = (regs->sdram_rcw[1] >> 24U) & U(0xf);
+		input.rcw[10] = (regs->sdram_rcw[1] >> 20U) & U(0xf);
+		input.rcw[11] = (regs->sdram_rcw[1] >> 16U) & U(0xf);
+		input.rcw[12] = (regs->sdram_rcw[1] >> 12U) & U(0xf);
+		input.rcw[13] = (regs->sdram_rcw[1] >> 8U) & U(0xf);
+		input.rcw[14] = (regs->sdram_rcw[1] >> 4U) & U(0xf);
+		input.rcw[15] = (regs->sdram_rcw[1] >> 0U) & U(0xf);
+		input.rcw3x = (regs->sdram_rcw[2] >> 8U) & U(0xff);
+	}
+
+	input.adv.odtimpedance = popts->odt ? popts->odt : 60;
+	input.adv.tx_impedance = popts->phy_tx_impedance ?
+					popts->phy_tx_impedance : 28;
+	input.adv.atx_impedance = popts->phy_atx_impedance ?
+					popts->phy_atx_impedance : 30;
+
+	debug("Initializing input adv data structure\n");
+	phy_gen2_init_input(&input);
+
+	debug("Initializing message block\n");
+	ret = phy_gen2_msg_init(&msg_1d, &msg_2d, &input);
+	if (ret != 0) {
+		ERROR("Init msg failed (error code %d)\n", ret);
+		return ret;
+	}
+
+	ret = c_init_phy_config(priv->phy, priv->ip_rev, &input, &msg_1d);
+	if (ret != 0) {
+		ERROR("Init PHY failed (error code %d)\n", ret);
+		return ret;
+	}
+#ifdef NXP_WARM_BOOT
+	debug("Warm boot flag value %0x\n", priv->warm_boot_flag);
+	if (priv->warm_boot_flag == DDR_WARM_BOOT) {
+		debug("Restoring the Phy training data\n");
+		// Restore the training data
+		ret = restore_phy_training_values(priv->phy,
+						  PHY_TRAINING_REGS_ON_FLASH,
+						  priv->num_ctlrs,
+						  input.basic.train2d);
+		if (ret != 0) {
+			ERROR("Restoring of training data failed %d\n", ret);
+			return ret;
+		}
+	} else {
+#endif
+
+		debug("Load 1D firmware\n");
+		ret = load_fw(priv->phy, &input, 0, &msg_1d,
+			      sizeof(struct ddr4u1d), priv->phy_gen2_fw_img_buf,
+					priv->img_loadr, priv->warm_boot_flag);
+		if (ret != 0) {
+			ERROR("Loading firmware failed (error code %d)\n", ret);
+			return ret;
+		}
+
+		debug("Execute firmware\n");
+		ret = g_exec_fw(priv->phy, 0, &input);
+		if (ret != 0) {
+			ERROR("Execution FW failed (error code %d)\n", ret);
+		}
+
+#ifdef NXP_APPLY_MAX_CDD
+		soc_info = get_soc_info();
+		if (soc_info->svr_reg.bf.maj_ver == 2) {
+			tcfg0 = regs->timing_cfg[0];
+			tcfg4 = regs->timing_cfg[4];
+			rank = findrank(conf->cs_in_use);
+			get_cdd_val(priv->phy, rank, input.basic.frequency,
+					&tcfg0, &tcfg4);
+			regs->timing_cfg[0] = tcfg0;
+			regs->timing_cfg[4] = tcfg4;
+		}
+#endif
+
+		if ((ret == 0) && (input.basic.train2d != 0)) {
+			/* 2D training starts here */
+			debug("Load 2D firmware\n");
+			ret = load_fw(priv->phy, &input, 1, &msg_2d,
+				      sizeof(struct ddr4u2d),
+				      priv->phy_gen2_fw_img_buf,
+				      priv->img_loadr,
+				      priv->warm_boot_flag);
+			if (ret != 0) {
+				ERROR("Loading fw failed (err code %d)\n", ret);
+			} else {
+				debug("Execute 2D firmware\n");
+				ret = g_exec_fw(priv->phy, 1, &input);
+				if (ret != 0) {
+					ERROR("Execution FW failed (err %d)\n",
+					       ret);
+				}
+			}
+		}
+#ifdef NXP_WARM_BOOT
+		if (priv->warm_boot_flag != DDR_WRM_BOOT_NT_SUPPORTED &&
+		    ret == 0) {
+			debug("save the phy training data\n");
+			//Save training data TBD
+			ret = save_phy_training_values(priv->phy,
+						PHY_TRAINING_REGS_ON_FLASH,
+						priv->num_ctlrs,
+						input.basic.train2d);
+			if (ret != 0) {
+				ERROR("Saving training data failed.");
+				ERROR("Warm boot will fail. Error=%d.\n", ret);
+			}
+		}
+	} /* else */
+#endif
+
+	if (ret == 0) {
+		debug("Load PIE\n");
+		i_load_pie(priv->phy, &input, &msg_1d);
+
+		NOTICE("DDR4 %s with %d-rank %d-bit bus (x%d)\n",
+		       input.basic.dimm_type == RDIMM ? "RDIMM" :
+		       input.basic.dimm_type == LRDIMM ? "LRDIMM" :
+		       "UDIMM",
+		       dimm_param->n_ranks,
+		       dimm_param->primary_sdram_width,
+		       dimm_param->device_width);
+	}
+#ifdef DEBUG_DDR_INPUT_CONFIG
+	print_jason_format(&input, &msg_1d, &msg_2d);
+#endif
+
+	return ret;
+}
diff --git a/drivers/nxp/ddr/phy-gen2/phy.h b/drivers/nxp/ddr/phy-gen2/phy.h
new file mode 100644
index 0000000..15e80d1
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/phy.h
@@ -0,0 +1,334 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#if !defined(PHY_H) && defined(NXP_WARM_BOOT)
+#define PHY_H
+
+#include <flash_info.h>
+
+/* To store sector size to be erase on flash*/
+#define PHY_ERASE_SIZE F_SECTOR_ERASE_SZ
+
+/*Structure to implement address-data map tuples to store PHY training values*/
+struct phy_training_values {
+	uint32_t addr;
+	uint16_t data;
+};
+/* Saves PHY Training Register values after cold reset
+ *@param[in] phy_ptr array to store addresses of PHYs
+ *@param[in] address_to_store address to save PHY training register values
+ *on flash
+ *@param[in] num_of_phy the number of PHY for which training values are
+ *to be saved
+ *@param[in] train2d flag to store whether 2D training registers are to
+ *be saved or not
+ *
+ *PHY training values will be stored on flash at contigous memory in the order:
+ *1D training registers, 2D training registers
+ *for each PHY
+ *
+ *if train2d is false saving 2D training registers will be skipped
+ */
+int save_phy_training_values(uint16_t **phy_ptr, uint32_t address_to_store,
+		uint32_t num_of_phy, int train2d);
+
+/*Restores PHY Training Register values after warm reset
+ *@param[in] phy_ptr array to store addresses of PHYs
+ *@param[in] address_to_store address to retrieve PHY training register
+ *values from flash
+ *@param[in] num_of_phy the number of PHY for which training values are
+ *to be restored
+ *@param[in] train2d flag to store whether 2D training registers are
+ *to be restored or not
+ *
+ *if train2d is false saving 2D training registers will be skipped
+ */
+
+int restore_phy_training_values(uint16_t **phy_ptr, uint32_t address_to_restore,
+		uint32_t num_of_phy, int train2d);
+
+/*
+ * Address data tuples to store the PHY 1D
+ */
+
+struct phy_training_values training_1D_values[] = {
+	{0x200B2, 0},	{0x200CB, 0},	{0x10043, 0},	{0x11043, 0},
+	{0x12043, 0},	{0x13043, 0},	{0x14043, 0},	{0x15043, 0},
+	{0x16043, 0},	{0x17043, 0},	{0x18043, 0},	{0x10143, 0},
+	{0x11143, 0},	{0x12143, 0},	{0x13143, 0},	{0x14143, 0},
+	{0x15143, 0},	{0x16143, 0},	{0x17143, 0},	{0x18143, 0},
+	{0x10080, 0},	{0x11080, 0},	{0x12080, 0},	{0x13080, 0},
+	{0x14080, 0},	{0x15080, 0},	{0x16080, 0},	{0x17080, 0},
+	{0x18080, 0},	{0x10180, 0},	{0x11180, 0},	{0x12180, 0},
+	{0x13180, 0},	{0x14180, 0},	{0x15180, 0},	{0x16180, 0},
+	{0x17180, 0},	{0x18180, 0},	{0x10081, 0},	{0x11081, 0},
+	{0x12081, 0},	{0x13081, 0},	{0x14081, 0},	{0x15081, 0},
+	{0x16081, 0},	{0x17081, 0},	{0x18081, 0},	{0x10181, 0},
+	{0x11181, 0},	{0x12181, 0},	{0x13181, 0},	{0x14181, 0},
+	{0x15181, 0},	{0x16181, 0},	{0x17181, 0},	{0x18181, 0},
+	{0x10082, 0},	{0x11082, 0},	{0x12082, 0},	{0x13082, 0},
+	{0x14082, 0},	{0x15082, 0},	{0x16082, 0},	{0x17082, 0},
+	{0x18082, 0},	{0x10182, 0},	{0x11182, 0},	{0x12182, 0},
+	{0x13182, 0},	{0x14182, 0},	{0x15182, 0},	{0x16182, 0},
+	{0x17182, 0},	{0x18182, 0},	{0x10083, 0},	{0x11083, 0},
+	{0x12083, 0},	{0x13083, 0},	{0x14083, 0},	{0x15083, 0},
+	{0x16083, 0},	{0x17083, 0},	{0x18083, 0},	{0x10183, 0},
+	{0x11183, 0},	{0x12183, 0},	{0x13183, 0},	{0x14183, 0},
+	{0x15183, 0},	{0x16183, 0},	{0x17183, 0},	{0x18183, 0},
+	{0x100D0, 0},	{0x110D0, 0},	{0x120D0, 0},	{0x130D0, 0},
+	{0x140D0, 0},	{0x150D0, 0},	{0x160D0, 0},	{0x170D0, 0},
+	{0x180D0, 0},	{0x101D0, 0},	{0x111D0, 0},	{0x121D0, 0},
+	{0x131D0, 0},	{0x141D0, 0},	{0x151D0, 0},	{0x161D0, 0},
+	{0x171D0, 0},	{0x181D0, 0},	{0x100D1, 0},	{0x110D1, 0},
+	{0x120D1, 0},	{0x130D1, 0},	{0x140D1, 0},	{0x150D1, 0},
+	{0x160D1, 0},	{0x170D1, 0},	{0x180D1, 0},	{0x101D1, 0},
+	{0x111D1, 0},	{0x121D1, 0},	{0x131D1, 0},	{0x141D1, 0},
+	{0x151D1, 0},	{0x161D1, 0},	{0x171D1, 0},	{0x181D1, 0},
+	{0x100D2, 0},	{0x110D2, 0},	{0x120D2, 0},	{0x130D2, 0},
+	{0x140D2, 0},	{0x150D2, 0},	{0x160D2, 0},	{0x170D2, 0},
+	{0x180D2, 0},	{0x101D2, 0},	{0x111D2, 0},	{0x121D2, 0},
+	{0x131D2, 0},	{0x141D2, 0},	{0x151D2, 0},	{0x161D2, 0},
+	{0x171D2, 0},	{0x181D2, 0},	{0x100D3, 0},	{0x110D3, 0},
+	{0x120D3, 0},	{0x130D3, 0},	{0x140D3, 0},	{0x150D3, 0},
+	{0x160D3, 0},	{0x170D3, 0},	{0x180D3, 0},	{0x101D3, 0},
+	{0x111D3, 0},	{0x121D3, 0},	{0x131D3, 0},	{0x141D3, 0},
+	{0x151D3, 0},	{0x161D3, 0},	{0x171D3, 0},	{0x181D3, 0},
+	{0x10068, 0},	{0x11068, 0},	{0x12068, 0},	{0x13068, 0},
+	{0x14068, 0},	{0x15068, 0},	{0x16068, 0},	{0x17068, 0},
+	{0x18068, 0},	{0x10168, 0},	{0x11168, 0},	{0x12168, 0},
+	{0x13168, 0},	{0x14168, 0},	{0x15168, 0},	{0x16168, 0},
+	{0x17168, 0},	{0x18168, 0},	{0x10268, 0},	{0x11268, 0},
+	{0x12268, 0},	{0x13268, 0},	{0x14268, 0},	{0x15268, 0},
+	{0x16268, 0},	{0x17268, 0},	{0x18268, 0},	{0x10368, 0},
+	{0x11368, 0},	{0x12368, 0},	{0x13368, 0},	{0x14368, 0},
+	{0x15368, 0},	{0x16368, 0},	{0x17368, 0},	{0x18368, 0},
+	{0x10468, 0},	{0x11468, 0},	{0x12468, 0},	{0x13468, 0},
+	{0x14468, 0},	{0x15468, 0},	{0x16468, 0},	{0x17468, 0},
+	{0x18468, 0},	{0x10568, 0},	{0x11568, 0},	{0x12568, 0},
+	{0x13568, 0},	{0x14568, 0},	{0x15568, 0},	{0x16568, 0},
+	{0x17568, 0},	{0x18568, 0},	{0x10668, 0},	{0x11668, 0},
+	{0x12668, 0},	{0x13668, 0},	{0x14668, 0},	{0x15668, 0},
+	{0x16668, 0},	{0x17668, 0},	{0x18668, 0},	{0x10768, 0},
+	{0x11768, 0},	{0x12768, 0},	{0x13768, 0},	{0x14768, 0},
+	{0x15768, 0},	{0x16768, 0},	{0x17768, 0},	{0x18768, 0},
+	{0x10868, 0},	{0x11868, 0},	{0x12868, 0},	{0x13868, 0},
+	{0x14868, 0},	{0x15868, 0},	{0x16868, 0},	{0x17868, 0},
+	{0x18868, 0},	{0x10069, 0},	{0x11069, 0},	{0x12069, 0},
+	{0x13069, 0},	{0x14069, 0},	{0x15069, 0},	{0x16069, 0},
+	{0x17069, 0},	{0x18069, 0},	{0x10169, 0},	{0x11169, 0},
+	{0x12169, 0},	{0x13169, 0},	{0x14169, 0},	{0x15169, 0},
+	{0x16169, 0},	{0x17169, 0},	{0x18169, 0},	{0x10269, 0},
+	{0x11269, 0},	{0x12269, 0},	{0x13269, 0},	{0x14269, 0},
+	{0x15269, 0},	{0x16269, 0},	{0x17269, 0},	{0x18269, 0},
+	{0x10369, 0},	{0x11369, 0},	{0x12369, 0},	{0x13369, 0},
+	{0x14369, 0},	{0x15369, 0},	{0x16369, 0},	{0x17369, 0},
+	{0x18369, 0},	{0x10469, 0},	{0x11469, 0},	{0x12469, 0},
+	{0x13469, 0},	{0x14469, 0},	{0x15469, 0},	{0x16469, 0},
+	{0x17469, 0},	{0x18469, 0},	{0x10569, 0},	{0x11569, 0},
+	{0x12569, 0},	{0x13569, 0},	{0x14569, 0},	{0x15569, 0},
+	{0x16569, 0},	{0x17569, 0},	{0x18569, 0},	{0x10669, 0},
+	{0x11669, 0},	{0x12669, 0},	{0x13669, 0},	{0x14669, 0},
+	{0x15669, 0},	{0x16669, 0},	{0x17669, 0},	{0x18669, 0},
+	{0x10769, 0},	{0x11769, 0},	{0x12769, 0},	{0x13769, 0},
+	{0x14769, 0},	{0x15769, 0},	{0x16769, 0},	{0x17769, 0},
+	{0x18769, 0},	{0x10869, 0},	{0x11869, 0},	{0x12869, 0},
+	{0x13869, 0},	{0x14869, 0},	{0x15869, 0},	{0x16869, 0},
+	{0x17869, 0},	{0x18869, 0},	{0x1006A, 0},	{0x1106A, 0},
+	{0x1206A, 0},	{0x1306A, 0},	{0x1406A, 0},	{0x1506A, 0},
+	{0x1606A, 0},	{0x1706A, 0},	{0x1806A, 0},	{0x1016A, 0},
+	{0x1116A, 0},	{0x1216A, 0},	{0x1316A, 0},	{0x1416A, 0},
+	{0x1516A, 0},	{0x1616A, 0},	{0x1716A, 0},	{0x1816A, 0},
+	{0x1026A, 0},	{0x1126A, 0},	{0x1226A, 0},	{0x1326A, 0},
+	{0x1426A, 0},	{0x1526A, 0},	{0x1626A, 0},	{0x1726A, 0},
+	{0x1826A, 0},	{0x1036A, 0},	{0x1136A, 0},	{0x1236A, 0},
+	{0x1336A, 0},	{0x1436A, 0},	{0x1536A, 0},	{0x1636A, 0},
+	{0x1736A, 0},	{0x1836A, 0},	{0x1046A, 0},	{0x1146A, 0},
+	{0x1246A, 0},	{0x1346A, 0},	{0x1446A, 0},	{0x1546A, 0},
+	{0x1646A, 0},	{0x1746A, 0},	{0x1846A, 0},	{0x1056A, 0},
+	{0x1156A, 0},	{0x1256A, 0},	{0x1356A, 0},	{0x1456A, 0},
+	{0x1556A, 0},	{0x1656A, 0},	{0x1756A, 0},	{0x1856A, 0},
+	{0x1066A, 0},	{0x1166A, 0},	{0x1266A, 0},	{0x1366A, 0},
+	{0x1466A, 0},	{0x1566A, 0},	{0x1666A, 0},	{0x1766A, 0},
+	{0x1866A, 0},	{0x1076A, 0},	{0x1176A, 0},	{0x1276A, 0},
+	{0x1376A, 0},	{0x1476A, 0},	{0x1576A, 0},	{0x1676A, 0},
+	{0x1776A, 0},	{0x1876A, 0},	{0x1086A, 0},	{0x1186A, 0},
+	{0x1286A, 0},	{0x1386A, 0},	{0x1486A, 0},	{0x1586A, 0},
+	{0x1686A, 0},	{0x1786A, 0},	{0x1886A, 0},	{0x1006B, 0},
+	{0x1106B, 0},	{0x1206B, 0},	{0x1306B, 0},	{0x1406B, 0},
+	{0x1506B, 0},	{0x1606B, 0},	{0x1706B, 0},	{0x1806B, 0},
+	{0x1016B, 0},	{0x1116B, 0},	{0x1216B, 0},	{0x1316B, 0},
+	{0x1416B, 0},	{0x1516B, 0},	{0x1616B, 0},	{0x1716B, 0},
+	{0x1816B, 0},	{0x1026B, 0},	{0x1126B, 0},	{0x1226B, 0},
+	{0x1326B, 0},	{0x1426B, 0},	{0x1526B, 0},	{0x1626B, 0},
+	{0x1726B, 0},	{0x1826B, 0},	{0x1036B, 0},	{0x1136B, 0},
+	{0x1236B, 0},	{0x1336B, 0},	{0x1436B, 0},	{0x1536B, 0},
+	{0x1636B, 0},	{0x1736B, 0},	{0x1836B, 0},	{0x1046B, 0},
+	{0x1146B, 0},	{0x1246B, 0},	{0x1346B, 0},	{0x1446B, 0},
+	{0x1546B, 0},	{0x1646B, 0},	{0x1746B, 0},	{0x1846B, 0},
+	{0x1056B, 0},	{0x1156B, 0},	{0x1256B, 0},	{0x1356B, 0},
+	{0x1456B, 0},	{0x1556B, 0},	{0x1656B, 0},	{0x1756B, 0},
+	{0x1856B, 0},	{0x1066B, 0},	{0x1166B, 0},	{0x1266B, 0},
+	{0x1366B, 0},	{0x1466B, 0},	{0x1566B, 0},	{0x1666B, 0},
+	{0x1766B, 0},	{0x1866B, 0},	{0x1076B, 0},	{0x1176B, 0},
+	{0x1276B, 0},	{0x1376B, 0},	{0x1476B, 0},	{0x1576B, 0},
+	{0x1676B, 0},	{0x1776B, 0},	{0x1876B, 0},	{0x1086B, 0},
+	{0x1186B, 0},	{0x1286B, 0},	{0x1386B, 0},	{0x1486B, 0},
+	{0x1586B, 0},	{0x1686B, 0},	{0x1786B, 0},	{0x1886B, 0},
+	{0x1008C, 0},	{0x1108C, 0},	{0x1208C, 0},	{0x1308C, 0},
+	{0x1408C, 0},	{0x1508C, 0},	{0x1608C, 0},	{0x1708C, 0},
+	{0x1808C, 0},	{0x1018C, 0},	{0x1118C, 0},	{0x1218C, 0},
+	{0x1318C, 0},	{0x1418C, 0},	{0x1518C, 0},	{0x1618C, 0},
+	{0x1718C, 0},	{0x1818C, 0},	{0x1008D, 0},	{0x1108D, 0},
+	{0x1208D, 0},	{0x1308D, 0},	{0x1408D, 0},	{0x1508D, 0},
+	{0x1608D, 0},	{0x1708D, 0},	{0x1808D, 0},	{0x1018D, 0},
+	{0x1118D, 0},	{0x1218D, 0},	{0x1318D, 0},	{0x1418D, 0},
+	{0x1518D, 0},	{0x1618D, 0},	{0x1718D, 0},	{0x1818D, 0},
+	{0x1008E, 0},	{0x1108E, 0},	{0x1208E, 0},	{0x1308E, 0},
+	{0x1408E, 0},	{0x1508E, 0},	{0x1608E, 0},	{0x1708E, 0},
+	{0x1808E, 0},	{0x1018E, 0},	{0x1118E, 0},	{0x1218E, 0},
+	{0x1318E, 0},	{0x1418E, 0},	{0x1518E, 0},	{0x1618E, 0},
+	{0x1718E, 0},	{0x1818E, 0},	{0x1008F, 0},	{0x1108F, 0},
+	{0x1208F, 0},	{0x1308F, 0},	{0x1408F, 0},	{0x1508F, 0},
+	{0x1608F, 0},	{0x1708F, 0},	{0x1808F, 0},	{0x1018F, 0},
+	{0x1118F, 0},	{0x1218F, 0},	{0x1318F, 0},	{0x1418F, 0},
+	{0x1518F, 0},	{0x1618F, 0},	{0x1718F, 0},	{0x1818F, 0},
+	{0x100C0, 0},	{0x110C0, 0},	{0x120C0, 0},	{0x130C0, 0},
+	{0x140C0, 0},	{0x150C0, 0},	{0x160C0, 0},	{0x170C0, 0},
+	{0x180C0, 0},	{0x101C0, 0},	{0x111C0, 0},	{0x121C0, 0},
+	{0x131C0, 0},	{0x141C0, 0},	{0x151C0, 0},	{0x161C0, 0},
+	{0x171C0, 0},	{0x181C0, 0},	{0x102C0, 0},	{0x112C0, 0},
+	{0x122C0, 0},	{0x132C0, 0},	{0x142C0, 0},	{0x152C0, 0},
+	{0x162C0, 0},	{0x172C0, 0},	{0x182C0, 0},	{0x103C0, 0},
+	{0x113C0, 0},	{0x123C0, 0},	{0x133C0, 0},	{0x143C0, 0},
+	{0x153C0, 0},	{0x163C0, 0},	{0x173C0, 0},	{0x183C0, 0},
+	{0x104C0, 0},	{0x114C0, 0},	{0x124C0, 0},	{0x134C0, 0},
+	{0x144C0, 0},	{0x154C0, 0},	{0x164C0, 0},	{0x174C0, 0},
+	{0x184C0, 0},	{0x105C0, 0},	{0x115C0, 0},	{0x125C0, 0},
+	{0x135C0, 0},	{0x145C0, 0},	{0x155C0, 0},	{0x165C0, 0},
+	{0x175C0, 0},	{0x185C0, 0},	{0x106C0, 0},	{0x116C0, 0},
+	{0x126C0, 0},	{0x136C0, 0},	{0x146C0, 0},	{0x156C0, 0},
+	{0x166C0, 0},	{0x176C0, 0},	{0x186C0, 0},	{0x107C0, 0},
+	{0x117C0, 0},	{0x127C0, 0},	{0x137C0, 0},	{0x147C0, 0},
+	{0x157C0, 0},	{0x167C0, 0},	{0x177C0, 0},	{0x187C0, 0},
+	{0x108C0, 0},	{0x118C0, 0},	{0x128C0, 0},	{0x138C0, 0},
+	{0x148C0, 0},	{0x158C0, 0},	{0x168C0, 0},	{0x178C0, 0},
+	{0x188C0, 0},	{0x100C1, 0},	{0x110C1, 0},	{0x120C1, 0},
+	{0x130C1, 0},	{0x140C1, 0},	{0x150C1, 0},	{0x160C1, 0},
+	{0x170C1, 0},	{0x180C1, 0},	{0x101C1, 0},	{0x111C1, 0},
+	{0x121C1, 0},	{0x131C1, 0},	{0x141C1, 0},	{0x151C1, 0},
+	{0x161C1, 0},	{0x171C1, 0},	{0x181C1, 0},	{0x102C1, 0},
+	{0x112C1, 0},	{0x122C1, 0},	{0x132C1, 0},	{0x142C1, 0},
+	{0x152C1, 0},	{0x162C1, 0},	{0x172C1, 0},	{0x182C1, 0},
+	{0x103C1, 0},	{0x113C1, 0},	{0x123C1, 0},	{0x133C1, 0},
+	{0x143C1, 0},	{0x153C1, 0},	{0x163C1, 0},	{0x173C1, 0},
+	{0x183C1, 0},	{0x104C1, 0},	{0x114C1, 0},	{0x124C1, 0},
+	{0x134C1, 0},	{0x144C1, 0},	{0x154C1, 0},	{0x164C1, 0},
+	{0x174C1, 0},	{0x184C1, 0},	{0x105C1, 0},	{0x115C1, 0},
+	{0x125C1, 0},	{0x135C1, 0},	{0x145C1, 0},	{0x155C1, 0},
+	{0x165C1, 0},	{0x175C1, 0},	{0x185C1, 0},	{0x106C1, 0},
+	{0x116C1, 0},	{0x126C1, 0},	{0x136C1, 0},	{0x146C1, 0},
+	{0x156C1, 0},	{0x166C1, 0},	{0x176C1, 0},	{0x186C1, 0},
+	{0x107C1, 0},	{0x117C1, 0},	{0x127C1, 0},	{0x137C1, 0},
+	{0x147C1, 0},	{0x157C1, 0},	{0x167C1, 0},	{0x177C1, 0},
+	{0x187C1, 0},	{0x108C1, 0},	{0x118C1, 0},	{0x128C1, 0},
+	{0x138C1, 0},	{0x148C1, 0},	{0x158C1, 0},	{0x168C1, 0},
+	{0x178C1, 0},	{0x188C1, 0},	{0x100C2, 0},	{0x110C2, 0},
+	{0x120C2, 0},	{0x130C2, 0},	{0x140C2, 0},	{0x150C2, 0},
+	{0x160C2, 0},	{0x170C2, 0},	{0x180C2, 0},	{0x101C2, 0},
+	{0x111C2, 0},	{0x121C2, 0},	{0x131C2, 0},	{0x141C2, 0},
+	{0x151C2, 0},	{0x161C2, 0},	{0x171C2, 0},	{0x181C2, 0},
+	{0x102C2, 0},	{0x112C2, 0},	{0x122C2, 0},	{0x132C2, 0},
+	{0x142C2, 0},	{0x152C2, 0},	{0x162C2, 0},	{0x172C2, 0},
+	{0x182C2, 0},	{0x103C2, 0},	{0x113C2, 0},	{0x123C2, 0},
+	{0x133C2, 0},	{0x143C2, 0},	{0x153C2, 0},	{0x163C2, 0},
+	{0x173C2, 0},	{0x183C2, 0},	{0x104C2, 0},	{0x114C2, 0},
+	{0x124C2, 0},	{0x134C2, 0},	{0x144C2, 0},	{0x154C2, 0},
+	{0x164C2, 0},	{0x174C2, 0},	{0x184C2, 0},	{0x105C2, 0},
+	{0x115C2, 0},	{0x125C2, 0},	{0x135C2, 0},	{0x145C2, 0},
+	{0x155C2, 0},	{0x165C2, 0},	{0x175C2, 0},	{0x185C2, 0},
+	{0x106C2, 0},	{0x116C2, 0},	{0x126C2, 0},	{0x136C2, 0},
+	{0x146C2, 0},	{0x156C2, 0},	{0x166C2, 0},	{0x176C2, 0},
+	{0x186C2, 0},	{0x107C2, 0},	{0x117C2, 0},	{0x127C2, 0},
+	{0x137C2, 0},	{0x147C2, 0},	{0x157C2, 0},	{0x167C2, 0},
+	{0x177C2, 0},	{0x187C2, 0},	{0x108C2, 0},	{0x118C2, 0},
+	{0x128C2, 0},	{0x138C2, 0},	{0x148C2, 0},	{0x158C2, 0},
+	{0x168C2, 0},	{0x178C2, 0},	{0x188C2, 0},	{0x100C3, 0},
+	{0x110C3, 0},	{0x120C3, 0},	{0x130C3, 0},	{0x140C3, 0},
+	{0x150C3, 0},	{0x160C3, 0},	{0x170C3, 0},	{0x180C3, 0},
+	{0x101C3, 0},	{0x111C3, 0},	{0x121C3, 0},	{0x131C3, 0},
+	{0x141C3, 0},	{0x151C3, 0},	{0x161C3, 0},	{0x171C3, 0},
+	{0x181C3, 0},	{0x102C3, 0},	{0x112C3, 0},	{0x122C3, 0},
+	{0x132C3, 0},	{0x142C3, 0},	{0x152C3, 0},	{0x162C3, 0},
+	{0x172C3, 0},	{0x182C3, 0},	{0x103C3, 0},	{0x113C3, 0},
+	{0x123C3, 0},	{0x133C3, 0},	{0x143C3, 0},	{0x153C3, 0},
+	{0x163C3, 0},	{0x173C3, 0},	{0x183C3, 0},	{0x104C3, 0},
+	{0x114C3, 0},	{0x124C3, 0},	{0x134C3, 0},	{0x144C3, 0},
+	{0x154C3, 0},	{0x164C3, 0},	{0x174C3, 0},	{0x184C3, 0},
+	{0x105C3, 0},	{0x115C3, 0},	{0x125C3, 0},	{0x135C3, 0},
+	{0x145C3, 0},	{0x155C3, 0},	{0x165C3, 0},	{0x175C3, 0},
+	{0x185C3, 0},	{0x106C3, 0},	{0x116C3, 0},	{0x126C3, 0},
+	{0x136C3, 0},	{0x146C3, 0},	{0x156C3, 0},	{0x166C3, 0},
+	{0x176C3, 0},	{0x186C3, 0},	{0x107C3, 0},	{0x117C3, 0},
+	{0x127C3, 0},	{0x137C3, 0},	{0x147C3, 0},	{0x157C3, 0},
+	{0x167C3, 0},	{0x177C3, 0},	{0x187C3, 0},	{0x108C3, 0},
+	{0x118C3, 0},	{0x128C3, 0},	{0x138C3, 0},	{0x148C3, 0},
+	{0x158C3, 0},	{0x168C3, 0},	{0x178C3, 0},	{0x188C3, 0},
+	{0x10020, 0},	{0x11020, 0},	{0x12020, 0},	{0x13020, 0},
+	{0x14020, 0},	{0x15020, 0},	{0x16020, 0},	{0x17020, 0},
+	{0x18020, 0},	{0x2007D, 0},	{0x20077, 0}
+};
+
+/*
+ *Array to store the PHY 2D Training register addresses
+ */
+struct phy_training_values training_2D_values[] = {
+	{0x1008C, 0},   {0x1108C, 0},   {0x1208C, 0},   {0x1308C, 0},
+	{0x1408C, 0},   {0x1508C, 0},   {0x1608C, 0},   {0x1708C, 0},
+	{0x1808C, 0},   {0x1018C, 0},   {0x1118C, 0},   {0x1218C, 0},
+	{0x1318C, 0},   {0x1418C, 0},   {0x1518C, 0},   {0x1618C, 0},
+	{0x1718C, 0},   {0x1818C, 0},   {0x10040, 0},   {0x11040, 0},
+	{0x12040, 0},   {0x13040, 0},   {0x14040, 0},   {0x15040, 0},
+	{0x16040, 0},   {0x17040, 0},   {0x18040, 0},   {0x10140, 0},
+	{0x11140, 0},   {0x12140, 0},   {0x13140, 0},   {0x14140, 0},
+	{0x15140, 0},   {0x16140, 0},   {0x17140, 0},   {0x18140, 0},
+	{0x10240, 0},   {0x11240, 0},   {0x12240, 0},   {0x13240, 0},
+	{0x14240, 0},   {0x15240, 0},   {0x16240, 0},   {0x17240, 0},
+	{0x18240, 0},   {0x10340, 0},   {0x11340, 0},   {0x12340, 0},
+	{0x13340, 0},   {0x14340, 0},   {0x15340, 0},   {0x16340, 0},
+	{0x17340, 0},   {0x18340, 0},   {0x10440, 0},   {0x11440, 0},
+	{0x12440, 0},   {0x13440, 0},   {0x14440, 0},   {0x15440, 0},
+	{0x16440, 0},   {0x17440, 0},   {0x18440, 0},   {0x10540, 0},
+	{0x11540, 0},   {0x12540, 0},   {0x13540, 0},   {0x14540, 0},
+	{0x15540, 0},   {0x16540, 0},   {0x17540, 0},   {0x18540, 0},
+	{0x10640, 0},   {0x11640, 0},   {0x12640, 0},   {0x13640, 0},
+	{0x14640, 0},   {0x15640, 0},   {0x16640, 0},   {0x17640, 0},
+	{0x18640, 0},   {0x10740, 0},   {0x11740, 0},   {0x12740, 0},
+	{0x13740, 0},   {0x14740, 0},   {0x15740, 0},   {0x16740, 0},
+	{0x17740, 0},   {0x18740, 0},   {0x10840, 0},   {0x11840, 0},
+	{0x12840, 0},   {0x13840, 0},   {0x14840, 0},   {0x15840, 0},
+	{0x16840, 0},   {0x17840, 0},   {0x18840, 0},   {0x10030, 0},
+	{0x11030, 0},   {0x12030, 0},   {0x13030, 0},   {0x14030, 0},
+	{0x15030, 0},   {0x16030, 0},   {0x17030, 0},   {0x18030, 0},
+	{0x10130, 0},   {0x11130, 0},   {0x12130, 0},   {0x13130, 0},
+	{0x14130, 0},   {0x15130, 0},   {0x16130, 0},   {0x17130, 0},
+	{0x18130, 0},   {0x10230, 0},   {0x11230, 0},   {0x12230, 0},
+	{0x13230, 0},   {0x14230, 0},   {0x15230, 0},   {0x16230, 0},
+	{0x17230, 0},   {0x18230, 0},   {0x10330, 0},   {0x11330, 0},
+	{0x12330, 0},   {0x13330, 0},   {0x14330, 0},   {0x15330, 0},
+	{0x16330, 0},   {0x17330, 0},   {0x18330, 0},   {0x10430, 0},
+	{0x11430, 0},   {0x12430, 0},   {0x13430, 0},   {0x14430, 0},
+	{0x15430, 0},   {0x16430, 0},   {0x17430, 0},   {0x18430, 0},
+	{0x10530, 0},   {0x11530, 0},   {0x12530, 0},   {0x13530, 0},
+	{0x14530, 0},   {0x15530, 0},   {0x16530, 0},   {0x17530, 0},
+	{0x18530, 0},   {0x10630, 0},   {0x11630, 0},   {0x12630, 0},
+	{0x13630, 0},   {0x14630, 0},   {0x15630, 0},   {0x16630, 0},
+	{0x17630, 0},   {0x18630, 0},   {0x10730, 0},   {0x11730, 0},
+	{0x12730, 0},   {0x13730, 0},   {0x14730, 0},   {0x15730, 0},
+	{0x16730, 0},   {0x17730, 0},   {0x18730, 0},   {0x10830, 0},
+	{0x11830, 0},   {0x12830, 0},   {0x13830, 0},   {0x14830, 0},
+	{0x15830, 0},   {0x16830, 0},   {0x17830, 0},   {0x18830, 0}
+};
+
+#endif
diff --git a/drivers/nxp/ddr/phy-gen2/pie.h b/drivers/nxp/ddr/phy-gen2/pie.h
new file mode 100644
index 0000000..b89066a
--- /dev/null
+++ b/drivers/nxp/ddr/phy-gen2/pie.h
@@ -0,0 +1,632 @@
+/*
+ * Copyright 2021 NXP
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PIE_H
+#define PIE_H
+
+struct pie {
+	uint32_t addr;
+	uint16_t data;
+};
+
+static const struct pie pie_udimm[] = {
+	{0x90000, 0x10},
+	{0x90001, 0x400},
+	{0x90002, 0x10e},
+	{0x90003, 0x0},
+	{0x90004, 0x0},
+	{0x90005, 0x8},
+	{0x90029, 0xb},
+	{0x9002a, 0x480},
+	{0x9002b, 0x109},
+	{0x9002c, 0x8},
+	{0x9002d, 0x448},
+	{0x9002e, 0x139},
+	{0x9002f, 0x8},
+	{0x90030, 0x478},
+	{0x90031, 0x109},
+	{0x90032, 0x2},
+	{0x90033, 0x10},
+	{0x90034, 0x139},
+	{0x90035, 0xb},
+	{0x90036, 0x7c0},
+	{0x90037, 0x139},
+	{0x90038, 0x44},
+	{0x90039, 0x633},
+	{0x9003a, 0x159},
+	{0x9003b, 0x14f},
+	{0x9003c, 0x630},
+	{0x9003d, 0x159},
+	{0x9003e, 0x47},
+	{0x9003f, 0x633},
+	{0x90040, 0x149},
+	{0x90041, 0x4f},
+	{0x90042, 0x633},
+	{0x90043, 0x179},
+	{0x90044, 0x8},
+	{0x90045, 0xe0},
+	{0x90046, 0x109},
+	{0x90047, 0x0},
+	{0x90048, 0x7c8},
+	{0x90049, 0x109},
+	{0x9004a, 0x0},
+	{0x9004b, 0x1},
+	{0x9004c, 0x8},
+	{0x9004d, 0x0},
+	{0x9004e, 0x45a},
+	{0x9004f, 0x9},
+	{0x90050, 0x0},
+	{0x90051, 0x448},
+	{0x90052, 0x109},
+	{0x90053, 0x40},
+	{0x90054, 0x633},
+	{0x90055, 0x179},
+	{0x90056, 0x1},
+	{0x90057, 0x618},
+	{0x90058, 0x109},
+	{0x90059, 0x40c0},
+	{0x9005a, 0x633},
+	{0x9005b, 0x149},
+	{0x9005c, 0x8},
+	{0x9005d, 0x4},
+	{0x9005e, 0x48},
+	{0x9005f, 0x4040},
+	{0x90060, 0x633},
+	{0x90061, 0x149},
+	{0x90062, 0x0},
+	{0x90063, 0x4},
+	{0x90064, 0x48},
+	{0x90065, 0x40},
+	{0x90066, 0x633},
+	{0x90067, 0x149},
+	{0x90068, 0x10},
+	{0x90069, 0x4},
+	{0x9006a, 0x18},
+	{0x9006b, 0x0},
+	{0x9006c, 0x4},
+	{0x9006d, 0x78},
+	{0x9006e, 0x549},
+	{0x9006f, 0x633},
+	{0x90070, 0x159},
+	{0x90071, 0xd49},
+	{0x90072, 0x633},
+	{0x90073, 0x159},
+	{0x90074, 0x94a},
+	{0x90075, 0x633},
+	{0x90076, 0x159},
+	{0x90077, 0x441},
+	{0x90078, 0x633},
+	{0x90079, 0x149},
+	{0x9007a, 0x42},
+	{0x9007b, 0x633},
+	{0x9007c, 0x149},
+	{0x9007d, 0x1},
+	{0x9007e, 0x633},
+	{0x9007f, 0x149},
+	{0x90080, 0x0},
+	{0x90081, 0xe0},
+	{0x90082, 0x109},
+	{0x90083, 0xa},
+	{0x90084, 0x10},
+	{0x90085, 0x109},
+	{0x90086, 0x9},
+	{0x90087, 0x3c0},
+	{0x90088, 0x149},
+	{0x90089, 0x9},
+	{0x9008a, 0x3c0},
+	{0x9008b, 0x159},
+	{0x9008c, 0x18},
+	{0x9008d, 0x10},
+	{0x9008e, 0x109},
+	{0x9008f, 0x0},
+	{0x90090, 0x3c0},
+	{0x90091, 0x109},
+	{0x90092, 0x18},
+	{0x90093, 0x4},
+	{0x90094, 0x48},
+	{0x90095, 0x18},
+	{0x90096, 0x4},
+	{0x90097, 0x58},
+	{0x90098, 0xb},
+	{0x90099, 0x10},
+	{0x9009a, 0x109},
+	{0x9009b, 0x1},
+	{0x9009c, 0x10},
+	{0x9009d, 0x109},
+	{0x9009e, 0x5},
+	{0x9009f, 0x7c0},
+	{0x900a0, 0x109},
+	{0x900a1, 0x0},
+	{0x900a2, 0x8140},
+	{0x900a3, 0x10c},
+	{0x900a4, 0x10},
+	{0x900a5, 0x8138},
+	{0x900a6, 0x10c},
+	{0x900a7, 0x8},
+	{0x900a8, 0x7c8},
+	{0x900a9, 0x101},
+	{0x900aa, 0x8},
+	{0x900ab, 0x448},
+	{0x900ac, 0x109},
+	{0x900ad, 0xf},
+	{0x900ae, 0x7c0},
+	{0x900af, 0x109},
+	{0x900b0, 0x47},
+	{0x900b1, 0x630},
+	{0x900b2, 0x109},
+	{0x900b3, 0x8},
+	{0x900b4, 0x618},
+	{0x900b5, 0x109},
+	{0x900b6, 0x8},
+	{0x900b7, 0xe0},
+	{0x900b8, 0x109},
+	{0x900b9, 0x0},
+	{0x900ba, 0x7c8},
+	{0x900bb, 0x109},
+	{0x900bc, 0x8},
+	{0x900bd, 0x8140},
+	{0x900be, 0x10c},
+	{0x900bf, 0x0},
+	{0x900c0, 0x478},
+	{0x900c1, 0x109},
+	{0x900c2, 0x0},
+	{0x900c3, 0x1},
+	{0x900c4, 0x8},
+	{0x900c5, 0x8},
+	{0x900c6, 0x4},
+	{0x900c7, 0x8},
+	{0x900c8, 0x8},
+	{0x900c9, 0x7c8},
+	{0x900ca, 0x101},
+	{0x90006, 0x0},
+	{0x90007, 0x0},
+	{0x90008, 0x8},
+	{0x90009, 0x0},
+	{0x9000a, 0x0},
+	{0x9000b, 0x0},
+	{0xd00e7, 0x400},
+	{0x90017, 0x0},
+	{0x90026, 0x2b},
+};
+
+static const struct pie pie_rdimm[] = {
+	{0x90000, 0x10},
+	{0x90001, 0x400},
+	{0x90002, 0x10e},
+	{0x90003, 0x0},
+	{0x90004, 0x0},
+	{0x90005, 0x8},
+	{0x40000, 0x10},
+	{0x40020, 0x0},
+	{0x40040, 0x0},
+	{0x40060, 0x0},
+	{0x40001, 0x70a},
+	{0x40021, 0x7005},
+	{0x40041, 0x0},
+	{0x40061, 0x2001},
+	{0x40002, 0x4010},
+	{0x40022, 0x0},
+	{0x40042, 0x0},
+	{0x40062, 0x0},
+	{0x90029, 0x10},
+	{0x9002a, 0x400},
+	{0x9002b, 0x16e},
+	{0x9002c, 0x8},
+	{0x9002d, 0x370},
+	{0x9002e, 0x169},
+	{0x9002f, 0x8},
+	{0x90030, 0x7aa},
+	{0x90031, 0x6a},
+	{0x90032, 0x10},
+	{0x90033, 0x7b2},
+	{0x90034, 0x6a},
+	{0x90035, 0x0},
+	{0x90036, 0x48a},
+	{0x90037, 0x6a},
+	{0x90038, 0x9},
+	{0x90039, 0x480},
+	{0x9003a, 0x16a},
+	{0x9003b, 0x4},
+	{0x9003c, 0x790},
+	{0x9003d, 0x16a},
+	{0x9003e, 0xc},
+	{0x9003f, 0x408},
+	{0x90040, 0x169},
+	{0x90041, 0xa},
+	{0x90042, 0x0},
+	{0x90043, 0x68},
+	{0x90044, 0x0},
+	{0x90045, 0x408},
+	{0x90046, 0x169},
+	{0x90047, 0x1},
+	{0x90048, 0x480},
+	{0x90049, 0x16a},
+	{0x9004a, 0xb},
+	{0x9004b, 0x480},
+	{0x9004c, 0x109},
+	{0x9004d, 0x8},
+	{0x9004e, 0x448},
+	{0x9004f, 0x139},
+	{0x90050, 0x78},
+	{0x90051, 0x8},
+	{0x90052, 0x139},
+	{0x90053, 0x2},
+	{0x90054, 0x10},
+	{0x90055, 0x139},
+	{0x90056, 0xb},
+	{0x90057, 0x7c0},
+	{0x90058, 0x139},
+	{0x90059, 0x44},
+	{0x9005a, 0x633},
+	{0x9005b, 0x159},
+	{0x9005c, 0x14f},
+	{0x9005d, 0x630},
+	{0x9005e, 0x159},
+	{0x9005f, 0x47},
+	{0x90060, 0x633},
+	{0x90061, 0x149},
+	{0x90062, 0x4f},
+	{0x90063, 0x633},
+	{0x90064, 0x179},
+	{0x90065, 0x8},
+	{0x90066, 0xe0},
+	{0x90067, 0x109},
+	{0x90068, 0x0},
+	{0x90069, 0x7c8},
+	{0x9006a, 0x109},
+	{0x9006b, 0x0},
+	{0x9006c, 0x1},
+	{0x9006d, 0x8},
+	{0x9006e, 0x0},
+	{0x9006f, 0x45a},
+	{0x90070, 0x9},
+	{0x90071, 0x0},
+	{0x90072, 0x448},
+	{0x90073, 0x109},
+	{0x90074, 0x40},
+	{0x90075, 0x633},
+	{0x90076, 0x179},
+	{0x90077, 0x1},
+	{0x90078, 0x618},
+	{0x90079, 0x109},
+	{0x9007a, 0x40c0},
+	{0x9007b, 0x633},
+	{0x9007c, 0x149},
+	{0x9007d, 0x8},
+	{0x9007e, 0x4},
+	{0x9007f, 0x48},
+	{0x90080, 0x4040},
+	{0x90081, 0x633},
+	{0x90082, 0x149},
+	{0x90083, 0x0},
+	{0x90084, 0x4},
+	{0x90085, 0x48},
+	{0x90086, 0x40},
+	{0x90087, 0x633},
+	{0x90088, 0x149},
+	{0x90089, 0x10},
+	{0x9008a, 0x4},
+	{0x9008b, 0x18},
+	{0x9008c, 0x0},
+	{0x9008d, 0x4},
+	{0x9008e, 0x78},
+	{0x9008f, 0x549},
+	{0x90090, 0x633},
+	{0x90091, 0x159},
+	{0x90092, 0xd49},
+	{0x90093, 0x633},
+	{0x90094, 0x159},
+	{0x90095, 0x94a},
+	{0x90096, 0x633},
+	{0x90097, 0x159},
+	{0x90098, 0x441},
+	{0x90099, 0x633},
+	{0x9009a, 0x149},
+	{0x9009b, 0x42},
+	{0x9009c, 0x633},
+	{0x9009d, 0x149},
+	{0x9009e, 0x1},
+	{0x9009f, 0x633},
+	{0x900a0, 0x149},
+	{0x900a1, 0x0},
+	{0x900a2, 0xe0},
+	{0x900a3, 0x109},
+	{0x900a4, 0xa},
+	{0x900a5, 0x10},
+	{0x900a6, 0x109},
+	{0x900a7, 0x9},
+	{0x900a8, 0x3c0},
+	{0x900a9, 0x149},
+	{0x900aa, 0x9},
+	{0x900ab, 0x3c0},
+	{0x900ac, 0x159},
+	{0x900ad, 0x18},
+	{0x900ae, 0x10},
+	{0x900af, 0x109},
+	{0x900b0, 0x0},
+	{0x900b1, 0x3c0},
+	{0x900b2, 0x109},
+	{0x900b3, 0x18},
+	{0x900b4, 0x4},
+	{0x900b5, 0x48},
+	{0x900b6, 0x18},
+	{0x900b7, 0x4},
+	{0x900b8, 0x58},
+	{0x900b9, 0xb},
+	{0x900ba, 0x10},
+	{0x900bb, 0x109},
+	{0x900bc, 0x1},
+	{0x900bd, 0x10},
+	{0x900be, 0x109},
+	{0x900bf, 0x5},
+	{0x900c0, 0x7c0},
+	{0x900c1, 0x109},
+	{0x900c2, 0x3},
+	{0x900c3, 0x370},
+	{0x900c4, 0x169},
+	{0x900c5, 0x3},
+	{0x900c6, 0x8},
+	{0x900c7, 0x139},
+	{0x900c8, 0x0},
+	{0x900c9, 0x400},
+	{0x900ca, 0x16e},
+	{0x900cb, 0x8},
+	{0x900cc, 0x478},
+	{0x900cd, 0x109},
+	{0x900ce, 0x0},
+	{0x900cf, 0x8140},
+	{0x900d0, 0x10c},
+	{0x900d1, 0x10},
+	{0x900d2, 0x8138},
+	{0x900d3, 0x10c},
+	{0x900d4, 0x8},
+	{0x900d5, 0x7c8},
+	{0x900d6, 0x101},
+	{0x900d7, 0x7a},
+	{0x900d8, 0x8},
+	{0x900d9, 0x109},
+	{0x900da, 0x8},
+	{0x900db, 0x448},
+	{0x900dc, 0x109},
+	{0x900dd, 0xf},
+	{0x900de, 0x7c0},
+	{0x900df, 0x109},
+	{0x900e0, 0x47},
+	{0x900e1, 0x630},
+	{0x900e2, 0x109},
+	{0x900e3, 0x8},
+	{0x900e4, 0x618},
+	{0x900e5, 0x109},
+	{0x900e6, 0x8},
+	{0x900e7, 0xe0},
+	{0x900e8, 0x109},
+	{0x900e9, 0x0},
+	{0x900ea, 0x8},
+	{0x900eb, 0x109},
+	{0x900ec, 0x0},
+	{0x900ed, 0x7c8},
+	{0x900ee, 0x109},
+	{0x900ef, 0x8},
+	{0x900f0, 0x8140},
+	{0x900f1, 0x10c},
+	{0x900f2, 0x0},
+	{0x900f3, 0x478},
+	{0x900f4, 0x109},
+	{0x900f5, 0x0},
+	{0x900f6, 0x1},
+	{0x900f7, 0x8},
+	{0x900f8, 0x8},
+	{0x900f9, 0x4},
+	{0x900fa, 0x8},
+	{0x900fb, 0x8},
+	{0x900fc, 0x7c8},
+	{0x900fd, 0x101},
+	{0x90006, 0x0},
+	{0x90007, 0x0},
+	{0x90008, 0x8},
+	{0x90009, 0x0},
+	{0x9000a, 0x0},
+	{0x9000b, 0x0},
+	{0xd00e7, 0x400},
+	{0x90017, 0x0},
+	{0x90026, 0x3a},
+};
+
+static const struct pie pie_lrdimm[] = {
+	{0x90000, 0x10},
+	{0x90001, 0x400},
+	{0x90002, 0x10e},
+	{0x90003, 0x0},
+	{0x90004, 0x0},
+	{0x90005, 0x8},
+	{0x90029, 0xb},
+	{0x9002a, 0x480},
+	{0x9002b, 0x109},
+	{0x9002c, 0x8},
+	{0x9002d, 0x448},
+	{0x9002e, 0x139},
+	{0x9002f, 0x78},
+	{0x90030, 0x8},
+	{0x90031, 0x139},
+	{0x90032, 0x2},
+	{0x90033, 0x10},
+	{0x90034, 0x139},
+	{0x90035, 0xb},
+	{0x90036, 0x7c0},
+	{0x90037, 0x139},
+	{0x90038, 0x44},
+	{0x90039, 0x633},
+	{0x9003a, 0x159},
+	{0x9003b, 0x14f},
+	{0x9003c, 0x630},
+	{0x9003d, 0x159},
+	{0x9003e, 0x47},
+	{0x9003f, 0x633},
+	{0x90040, 0x149},
+	{0x90041, 0x4f},
+	{0x90042, 0x633},
+	{0x90043, 0x179},
+	{0x90044, 0x8},
+	{0x90045, 0xe0},
+	{0x90046, 0x109},
+	{0x90047, 0x0},
+	{0x90048, 0x7c8},
+	{0x90049, 0x109},
+	{0x9004a, 0x0},
+	{0x9004b, 0x1},
+	{0x9004c, 0x8},
+	{0x9004d, 0x0},
+	{0x9004e, 0x45a},
+	{0x9004f, 0x9},
+	{0x90050, 0x0},
+	{0x90051, 0x448},
+	{0x90052, 0x109},
+	{0x90053, 0x40},
+	{0x90054, 0x633},
+	{0x90055, 0x179},
+	{0x90056, 0x1},
+	{0x90057, 0x618},
+	{0x90058, 0x109},
+	{0x90059, 0x40c0},
+	{0x9005a, 0x633},
+	{0x9005b, 0x149},
+	{0x9005c, 0x8},
+	{0x9005d, 0x4},
+	{0x9005e, 0x48},
+	{0x9005f, 0x4040},
+	{0x90060, 0x633},
+	{0x90061, 0x149},
+	{0x90062, 0x0},
+	{0x90063, 0x4},
+	{0x90064, 0x48},
+	{0x90065, 0x40},
+	{0x90066, 0x633},
+	{0x90067, 0x149},
+	{0x90068, 0x10},
+	{0x90069, 0x4},
+	{0x9006a, 0x18},
+	{0x9006b, 0x0},
+	{0x9006c, 0x4},
+	{0x9006d, 0x78},
+	{0x9006e, 0x549},
+	{0x9006f, 0x633},
+	{0x90070, 0x159},
+	{0x90071, 0xd49},
+	{0x90072, 0x633},
+	{0x90073, 0x159},
+	{0x90074, 0x94a},
+	{0x90075, 0x633},
+	{0x90076, 0x159},
+	{0x90077, 0x441},
+	{0x90078, 0x633},
+	{0x90079, 0x149},
+	{0x9007a, 0x42},
+	{0x9007b, 0x633},
+	{0x9007c, 0x149},
+	{0x9007d, 0x1},
+	{0x9007e, 0x633},
+	{0x9007f, 0x149},
+	{0x90080, 0x0},
+	{0x90081, 0xe0},
+	{0x90082, 0x109},
+	{0x90083, 0xa},
+	{0x90084, 0x10},
+	{0x90085, 0x109},
+	{0x90086, 0x9},
+	{0x90087, 0x3c0},
+	{0x90088, 0x149},
+	{0x90089, 0x9},
+	{0x9008a, 0x3c0},
+	{0x9008b, 0x159},
+	{0x9008c, 0x18},
+	{0x9008d, 0x10},
+	{0x9008e, 0x109},
+	{0x9008f, 0x0},
+	{0x90090, 0x3c0},
+	{0x90091, 0x109},
+	{0x90092, 0x18},
+	{0x90093, 0x4},
+	{0x90094, 0x48},
+	{0x90095, 0x18},
+	{0x90096, 0x4},
+	{0x90097, 0x58},
+	{0x90098, 0xb},
+	{0x90099, 0x10},
+	{0x9009a, 0x109},
+	{0x9009b, 0x1},
+	{0x9009c, 0x10},
+	{0x9009d, 0x109},
+	{0x9009e, 0x5},
+	{0x9009f, 0x7c0},
+	{0x900a0, 0x109},
+	{0x900a1, 0x3},
+	{0x900a2, 0x8},
+	{0x900a3, 0x139},
+	{0x900a4, 0x0},
+	{0x900a5, 0x400},
+	{0x900a6, 0x16e},
+	{0x900a7, 0x8},
+	{0x900a8, 0x478},
+	{0x900a9, 0x109},
+	{0x900aa, 0x0},
+	{0x900ab, 0x8140},
+	{0x900ac, 0x10c},
+	{0x900ad, 0x10},
+	{0x900ae, 0x8138},
+	{0x900af, 0x10c},
+	{0x900b0, 0x8},
+	{0x900b1, 0x7c8},
+	{0x900b2, 0x101},
+	{0x900b3, 0x7a},
+	{0x900b4, 0x8},
+	{0x900b5, 0x109},
+	{0x900b6, 0x8},
+	{0x900b7, 0x448},
+	{0x900b8, 0x109},
+	{0x900b9, 0xf},
+	{0x900ba, 0x7c0},
+	{0x900bb, 0x109},
+	{0x900bc, 0x47},
+	{0x900bd, 0x630},
+	{0x900be, 0x109},
+	{0x900bf, 0x8},
+	{0x900c0, 0x618},
+	{0x900c1, 0x109},
+	{0x900c2, 0x8},
+	{0x900c3, 0xe0},
+	{0x900c4, 0x109},
+	{0x900c5, 0x0},
+	{0x900c6, 0x8},
+	{0x900c7, 0x109},
+	{0x900c8, 0x0},
+	{0x900c9, 0x7c8},
+	{0x900ca, 0x109},
+	{0x900cb, 0x8},
+	{0x900cc, 0x8140},
+	{0x900cd, 0x10c},
+	{0x900ce, 0x0},
+	{0x900cf, 0x478},
+	{0x900d0, 0x109},
+	{0x900d1, 0x0},
+	{0x900d2, 0x1},
+	{0x900d3, 0x8},
+	{0x900d4, 0x8},
+	{0x900d5, 0x4},
+	{0x900d6, 0x8},
+	{0x900d7, 0x8},
+	{0x900d8, 0x7c8},
+	{0x900d9, 0x101},
+	{0x90006, 0x0},
+	{0x90007, 0x0},
+	{0x90008, 0x8},
+	{0x90009, 0x0},
+	{0x9000a, 0x0},
+	{0x9000b, 0x0},
+	{0xd00e7, 0x400},
+	{0x90017, 0x0},
+	{0x90026, 0x2e},
+};
+#endif
diff --git a/drivers/nxp/drivers.mk b/drivers/nxp/drivers.mk
new file mode 100644
index 0000000..c2db363
--- /dev/null
+++ b/drivers/nxp/drivers.mk
@@ -0,0 +1,91 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+###############################################################################
+
+
+PLAT_DRIVERS_PATH		:=	drivers/nxp
+PLAT_DRIVERS_INCLUDE_PATH	:=	include/drivers/nxp
+
+ifeq (${SMMU_NEEDED},yes)
+PLAT_INCLUDES	+= -Iinclude/drivers/nxp/smmu/
+endif
+
+ifeq (${DCFG_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/dcfg/dcfg.mk
+endif
+
+ifeq (${CSU_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/csu/csu.mk
+endif
+
+ifeq (${TIMER_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/timer/timer.mk
+endif
+
+ifeq (${INTERCONNECT_NEEDED},yes)
+include ${PLAT_DRIVERS_PATH}/interconnect/interconnect.mk
+endif
+
+ifeq (${GIC_NEEDED},yes)
+include ${PLAT_DRIVERS_PATH}/gic/gic.mk
+endif
+
+ifeq (${SD_MMC_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/sd/sd_mmc.mk
+endif
+
+ifeq (${CONSOLE_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/console/console.mk
+endif
+
+ifeq (${SFP_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/sfp/sfp.mk
+endif
+
+ifeq (${XSPI_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/flexspi/nor/flexspi_nor.mk
+endif
+
+ifeq (${QSPI_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/qspi/qspi.mk
+endif
+
+ifeq (${SNVS_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/sec_mon/sec_mon.mk
+endif
+
+ifeq ($(I2C_NEEDED),yes)
+$(eval $(call add_define, I2C_INIT))
+include $(PLAT_DRIVERS_PATH)/i2c/i2c.mk
+endif
+
+ifeq ($(DDR_DRIVER_NEEDED),yes)
+$(eval $(call add_define, DDR_INIT))
+# define DDR_CNTRL_SOURCES
+ifeq ($(DDRCNTLR),MMDC)
+include $(PLAT_DRIVERS_PATH)/ddr/fsl-mmdc/ddr.mk
+else
+include $(PLAT_DRIVERS_PATH)/ddr/nxp-ddr/ddr.mk
+endif # DDR_CNTRL_SOURCES
+endif
+
+ifeq (${PMU_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/pmu/pmu.mk
+endif
+
+ifeq (${CRYPTO_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/crypto/caam/caam.mk
+endif
+
+ifeq (${TZASC_NEEDED},yes)
+include $(PLAT_DRIVERS_PATH)/tzc/tzc.mk
+endif
+
+ifeq (${GPIO_NEEDED},yes)
+include ${PLAT_DRIVERS_PATH}/gpio/gpio.mk
+endif
diff --git a/drivers/nxp/flexspi/nor/flexspi_nor.c b/drivers/nxp/flexspi/nor/flexspi_nor.c
new file mode 100644
index 0000000..748228d
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/flexspi_nor.c
@@ -0,0 +1,25 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <fspi_api.h>
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+int flexspi_nor_io_setup(uintptr_t nxp_flexspi_flash_addr,
+			 size_t nxp_flexspi_flash_size, uint32_t fspi_base_reg_addr)
+{
+	int ret = 0;
+
+	ret = fspi_init(fspi_base_reg_addr, nxp_flexspi_flash_addr);
+	/* Adding NOR Memory Map in XLAT Table */
+	mmap_add_region(nxp_flexspi_flash_addr, nxp_flexspi_flash_addr,
+			nxp_flexspi_flash_size, MT_MEMORY | MT_RW);
+
+	return ret;
+}
diff --git a/drivers/nxp/flexspi/nor/flexspi_nor.h b/drivers/nxp/flexspi/nor/flexspi_nor.h
new file mode 100644
index 0000000..61fc236
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/flexspi_nor.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef FLEXSPI_NOR_H
+#define FLEXSPI_NOR_H
+
+int flexspi_nor_io_setup(uintptr_t nxp_flexspi_flash_addr,
+			 size_t nxp_flexspi_flash_size,
+			 uint32_t fspi_base_reg_addr);
+
+#endif /*	FLEXSPI_NOR_H	*/
diff --git a/drivers/nxp/flexspi/nor/flexspi_nor.mk b/drivers/nxp/flexspi/nor/flexspi_nor.mk
new file mode 100644
index 0000000..6d9eebb
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/flexspi_nor.mk
@@ -0,0 +1,35 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${XSPI_NOR},)
+XSPI_NOR	:= 1
+
+FLEXSPI_DRIVERS_PATH	:=  ${PLAT_DRIVERS_PATH}/flexspi/nor
+
+PLAT_XSPI_INCLUDES	+= -I$(FLEXSPI_DRIVERS_PATH)
+
+XSPI_BOOT_SOURCES	+= $(FLEXSPI_DRIVERS_PATH)/flexspi_nor.c	\
+			   ${FLEXSPI_DRIVERS_PATH}/fspi.c
+ifeq ($(DEBUG),1)
+XSPI_BOOT_SOURCES	+= ${FLEXSPI_DRIVERS_PATH}/test_fspi.c
+endif
+
+PLAT_XSPI_INCLUDES	+= -Iinclude/drivers/nxp/flexspi
+
+PLAT_INCLUDES		+= ${PLAT_XSPI_INCLUDES}
+
+ifeq (${BL_COMM_XSPI_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${XSPI_BOOT_SOURCES}
+else
+ifeq (${BL2_XSPI_NEEDED},yes)
+BL2_SOURCES		+= ${XSPI_BOOT_SOURCES}
+endif
+ifeq (${BL31_XSPI_NEEDED},yes)
+BL31_SOURCES		+= ${XSPI_BOOT_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/nxp/flexspi/nor/fspi.c b/drivers/nxp/flexspi/nor/fspi.c
new file mode 100644
index 0000000..7c919b8
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/fspi.c
@@ -0,0 +1,853 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * NXP FlexSpi Controller Driver.
+ * Copyright 2021 NXP
+ *
+ */
+#include <endian.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <flash_info.h>
+#include "fspi.h"
+#include <fspi_api.h>
+#include <xspi_error_codes.h>
+
+#ifdef DEBUG_FLEXSPI
+#define PR printf("In [%s][%d]\n", __func__, __LINE__)
+#define PRA(a, b) printf("In [%s][%d] %s="a"\n", __func__, __LINE__, #b, b)
+#else
+#define PR
+#define PRA(a, b)
+#endif
+
+/*
+ * This errata is valid for all NXP SoC.
+ */
+#define ERRATA_FLASH_A050272 1
+
+static uintptr_t fspi_base_reg_addr;
+static uintptr_t fspi_flash_base_addr;
+
+static void fspi_RDSR(uint32_t *, const void *, uint32_t);
+
+static void fspi_writel(uint32_t x_addr, uint32_t x_val)
+{
+	fspi_out32((uint32_t *)(fspi_base_reg_addr + x_addr),
+		 (uint32_t) x_val);
+}
+
+static uint32_t fspi_readl(uint32_t x_addr)
+{
+	return fspi_in32((uint32_t *)(fspi_base_reg_addr + x_addr));
+}
+
+static void fspi_MDIS(uint8_t x_disable)
+{
+	uint32_t ui_reg;
+
+	ui_reg = fspi_readl(FSPI_MCR0);
+	if (x_disable != 0U) {
+		ui_reg |= FSPI_MCR0_MDIS;
+	} else {
+		ui_reg &= (uint32_t) (~FSPI_MCR0_MDIS);
+	}
+
+	fspi_writel(FSPI_MCR0, ui_reg);
+}
+
+static void fspi_lock_LUT(void)
+{
+	fspi_writel(FSPI_LUTKEY, FSPI_LUTKEY_VALUE);
+	VERBOSE("%s 0x%x\n", __func__, fspi_readl(FSPI_LCKCR));
+	fspi_writel(FSPI_LCKCR, FSPI_LCKER_LOCK);
+	VERBOSE("%s 0x%x\n", __func__, fspi_readl(FSPI_LCKCR));
+}
+
+static void fspi_unlock_LUT(void)
+{
+	fspi_writel(FSPI_LUTKEY,  FSPI_LUTKEY_VALUE);
+	VERBOSE("%s 0x%x\n", __func__, fspi_readl(FSPI_LCKCR));
+	fspi_writel(FSPI_LCKCR, FSPI_LCKER_UNLOCK);
+	VERBOSE("%s 0x%x\n", __func__, fspi_readl(FSPI_LCKCR));
+}
+
+static void fspi_op_setup(uint32_t fspi_op_seq_id, bool ignore_flash_sz)
+{
+	uint32_t x_addr, x_instr0 = 0, x_instr1 = 0, x_instr2 = 0;
+	uint32_t cmd_id1, cmd_id2;
+
+	VERBOSE("In func %s\n", __func__);
+
+	switch (fspi_op_seq_id) {
+	case FSPI_READ_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_READ;
+		cmd_id2 = FSPI_NOR_CMD_READ_4B;
+		x_instr2 = FSPI_INSTR_OPRND0(0) | FSPI_INSTR_PAD0(FSPI_LUT_PAD1)
+				| FSPI_INSTR_OPCODE0(FSPI_LUT_READ);
+		break;
+	case FSPI_FASTREAD_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_FASTREAD;
+		cmd_id2 = FSPI_NOR_CMD_FASTREAD_4B;
+		x_instr2 = FSPI_INSTR_OPRND0(8) | FSPI_INSTR_PAD0(FSPI_LUT_PAD1)
+				| FSPI_INSTR_OPCODE0(FSPI_DUMMY_SDR)
+				| FSPI_INSTR_OPRND1(0)
+				| FSPI_INSTR_PAD1(FSPI_LUT_PAD1)
+				| FSPI_INSTR_OPCODE1(FSPI_LUT_READ);
+		break;
+	case FSPI_WRITE_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_PP;
+		cmd_id2 = FSPI_NOR_CMD_PP_4B;
+		x_instr2 = FSPI_INSTR_OPRND0(0) | FSPI_INSTR_PAD0(FSPI_LUT_PAD1)
+				| FSPI_INSTR_OPCODE0(FSPI_LUT_WRITE);
+		break;
+	case FSPI_WREN_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_WREN;
+		cmd_id2 = FSPI_NOR_CMD_WREN;
+		break;
+	case FSPI_SE_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_SE_64K;
+		cmd_id2 = FSPI_NOR_CMD_SE_64K_4B;
+		break;
+	case FSPI_4K_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_SE_4K;
+		cmd_id2 = FSPI_NOR_CMD_SE_4K_4B;
+		break;
+	case FSPI_BE_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_BE;
+		cmd_id2 = FSPI_NOR_CMD_BE;
+		break;
+	case FSPI_RDSR_SEQ_ID:
+		cmd_id1 = FSPI_NOR_CMD_RDSR;
+		cmd_id2 = FSPI_NOR_CMD_RDSR;
+		break;
+	}
+
+	x_addr = FSPI_LUTREG_OFFSET + (uint32_t)(0x10 * fspi_op_seq_id);
+	if ((F_FLASH_SIZE_BYTES <= SZ_16M_BYTES) || (ignore_flash_sz)) {
+		x_instr0 = FSPI_INSTR_OPRND0(cmd_id1);
+		x_instr1 = FSPI_INSTR_OPRND1(FSPI_LUT_ADDR24BIT);
+		VERBOSE("CMD_ID = %x offset = 0x%x\n", cmd_id1, x_addr);
+	} else {
+		x_instr0 = FSPI_INSTR_OPRND0(cmd_id2);
+		x_instr1 = FSPI_INSTR_OPRND1(FSPI_LUT_ADDR32BIT);
+		VERBOSE("CMD_ID = %x offset = 0x%x\n", cmd_id2, x_addr);
+	}
+	x_instr0 |= FSPI_INSTR_PAD0(FSPI_LUT_PAD1)
+		| FSPI_INSTR_OPCODE0(FSPI_LUT_CMD);
+
+	x_instr1 |= FSPI_INSTR_PAD1(FSPI_LUT_PAD1)
+		| FSPI_INSTR_OPCODE1(FSPI_LUT_ADDR);
+
+	if (fspi_op_seq_id == FSPI_RDSR_SEQ_ID) {
+		x_instr0 |= FSPI_INSTR_OPRND1(1) | FSPI_INSTR_PAD1(FSPI_LUT_PAD1)
+					| FSPI_INSTR_OPCODE1(FSPI_LUT_READ);
+	} else if ((fspi_op_seq_id != FSPI_BE_SEQ_ID)
+			&& (fspi_op_seq_id != FSPI_WREN_SEQ_ID)) {
+		x_instr0 |= x_instr1;
+	}
+
+	fspi_writel((x_addr), x_instr0);
+	fspi_writel((x_addr + U(0x4)), x_instr2);
+	fspi_writel((x_addr + U(0x8)), (uint32_t) 0x0);	/* STOP command */
+	fspi_writel((x_addr + U(0xc)), (uint32_t) 0x0);	/* STOP command */
+}
+
+static void fspi_setup_LUT(void)
+{
+	VERBOSE("In func %s\n", __func__);
+	fspi_unlock_LUT();
+
+	/* LUT Setup for READ Command 3-Byte low Frequency */
+	fspi_op_setup(FSPI_READ_SEQ_ID, false);
+
+	/* LUT Setup for FAST READ Command 3-Byte/4-Byte high Frequency */
+	fspi_op_setup(FSPI_FASTREAD_SEQ_ID, false);
+
+	/* LUT Setup for Page Program */
+	fspi_op_setup(FSPI_WRITE_SEQ_ID, false);
+
+	/* LUT Setup for WREN */
+	fspi_op_setup(FSPI_WREN_SEQ_ID, true);
+
+	/* LUT Setup for Sector_Erase */
+	fspi_op_setup(FSPI_SE_SEQ_ID, false);
+
+	/* LUT Setup for Sub Sector 4K Erase */
+	fspi_op_setup(FSPI_4K_SEQ_ID, false);
+
+	/* LUT Setup for Bulk_Erase */
+	fspi_op_setup(FSPI_BE_SEQ_ID, true);
+
+	/* Read Status */
+	fspi_op_setup(FSPI_RDSR_SEQ_ID, true);
+
+	fspi_lock_LUT();
+}
+
+static inline void fspi_ahb_invalidate(void)
+{
+	uint32_t reg;
+
+	VERBOSE("In func %s %d\n", __func__, __LINE__);
+	reg = fspi_readl(FSPI_MCR0);
+	reg |= FSPI_MCR0_SWRST;
+	fspi_writel(FSPI_MCR0, reg);
+	while ((fspi_readl(FSPI_MCR0) & FSPI_MCR0_SWRST) != 0)
+		;  /* FSPI_MCR0_SWRESET_MASK */
+	VERBOSE("In func %s %d\n", __func__, __LINE__);
+}
+
+#if defined(CONFIG_FSPI_AHB)
+static void fspi_init_ahb(void)
+{
+	uint32_t i, x_flash_cr2, seq_id;
+
+	x_flash_cr2 = 0;
+	/* Reset AHB RX buffer CR configuration */
+	for (i = 0; i < 8; i++) {
+		fspi_writel((FSPI_AHBRX_BUF0CR0 + 4 * i), 0U);
+	}
+
+	/* Set ADATSZ with the maximum AHB buffer size */
+	fspi_writel(FSPI_AHBRX_BUF7CR0,
+			((uint32_t) ((FSPI_RX_MAX_AHBBUF_SIZE / 8U) |
+				    FSPI_AHBRXBUF0CR7_PREF)));
+
+	/* Known limitation handling: prefetch and
+	 * no start address alignment.*/
+	fspi_writel(FSPI_AHBCR, FSPI_AHBCR_PREF_EN);
+	INFO("xAhbcr=0x%x\n", fspi_readl(FSPI_AHBCR));
+
+	// Setup AHB READ sequenceID for all flashes.
+	x_flash_cr2 = fspi_readl(FSPI_FLSHA1CR2);
+	INFO("x_flash_cr2=0x%x\n", x_flash_cr2);
+
+	seq_id = CONFIG_FSPI_FASTREAD ?
+			FSPI_FASTREAD_SEQ_ID : FSPI_READ_SEQ_ID;
+	x_flash_cr2 |= ((seq_id << FSPI_FLSHXCR2_ARDSEQI_SHIFT) & 0x1f);
+
+	INFO("x_flash_cr2=0x%x\n", x_flash_cr2);
+
+	fspi_writel(FSPI_FLSHA1CR2,  x_flash_cr2);
+	x_flash_cr2 = fspi_readl(FSPI_FLSHA1CR2);
+	INFO("x_flash_cr2=0x%x\n", x_flash_cr2);
+}
+#endif
+
+int xspi_read(uint32_t pc_rx_addr, uint32_t *pc_rx_buf, uint32_t x_size_bytes)
+{
+	if (x_size_bytes == 0) {
+		ERROR("Zero length reads are not allowed\n");
+		return XSPI_READ_FAIL;
+	}
+
+#if defined(CONFIG_FSPI_AHB)
+	return xspi_ahb_read(pc_rx_addr, pc_rx_buf, x_size_bytes);
+#else
+	return xspi_ip_read(pc_rx_addr, pc_rx_buf, x_size_bytes);
+#endif
+}
+#if defined(CONFIG_FSPI_AHB)
+int xspi_ahb_read(uint32_t pc_rx_addr, uint32_t *pc_rx_buf, uint32_t x_size_bytes)
+{
+	VERBOSE("In func %s 0x%x\n", __func__, (pc_rx_addr));
+
+	if (F_FLASH_SIZE_BYTES <= SZ_16M_BYTES) {
+		pc_rx_addr = ((uint32_t)(pcRxAddr & MASK_24BIT_ADDRESS));
+	} else {
+		pc_rx_addr = ((uint32_t)(pcRxAddr & MASK_32BIT_ADDRESS));
+	}
+
+	pc_rx_addr = ((uint32_t)(pcRxAddr + fspi_flash_base_addr));
+
+	if (((pc_rx_addr % 4) != 0) || (((uintptr_t)pc_rx_buf % 4) != 0)) {
+		WARN("%s: unaligned Start Address src=%ld dst=0x%p\n",
+		     __func__, (pc_rx_addr - fspi_flash_base_addr), pc_rx_buf);
+	}
+
+	/* Directly copy from AHB Buffer */
+	memcpy(pc_rx_buf, (void *)(uintptr_t)pc_rx_addr, x_size_bytes);
+
+	fspi_ahb_invalidate();
+	return XSPI_SUCCESS;
+}
+#endif
+
+int xspi_ip_read(uint32_t pc_rx_addr, uint32_t *pv_rx_buf, uint32_t ui_len)
+{
+
+	uint32_t i = 0U, j = 0U, x_rem = 0U;
+	uint32_t x_iteration = 0U, x_size_rx = 0U, x_size_wm, temp_size;
+	uint32_t data = 0U;
+	uint32_t x_len_bytes;
+	uint32_t x_addr, sts0, intr, seq_id;
+
+	x_addr = (uint32_t) pc_rx_addr;
+	x_len_bytes = ui_len;
+
+	/* Watermark level : 8 bytes. (BY DEFAULT) */
+	x_size_wm = 8U;
+
+	/* Clear  RX Watermark interrupt in INT register, if any existing.  */
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPRXWA);
+	PRA("0x%x", fspi_readl(FSPI_INTR));
+	/* Invalid the RXFIFO, to run next IP Command */
+	/* Clears data entries in IP Rx FIFOs, Also reset R/W pointers */
+	fspi_writel(FSPI_IPRXFCR, FSPI_IPRXFCR_CLR);
+	fspi_writel(FSPI_INTR, FSPI_INTEN_IPCMDDONE);
+
+	while (x_len_bytes) {
+
+		/* FlexSPI can store no more than  FSPI_RX_IPBUF_SIZE */
+		x_size_rx = (x_len_bytes >  FSPI_RX_IPBUF_SIZE) ?
+			   FSPI_RX_IPBUF_SIZE : x_len_bytes;
+
+		/* IP Control Register0 - SF Address to be read */
+		fspi_writel(FSPI_IPCR0, x_addr);
+		PRA("0x%x", fspi_readl(FSPI_IPCR0));
+		/* IP Control Register1 - SEQID_READ operation, Size */
+
+		seq_id = CONFIG_FSPI_FASTREAD ?
+				FSPI_FASTREAD_SEQ_ID : FSPI_READ_SEQ_ID;
+
+		fspi_writel(FSPI_IPCR1,
+			    (uint32_t)(seq_id << FSPI_IPCR1_ISEQID_SHIFT) |
+			    (uint16_t) x_size_rx);
+
+		PRA("0x%x", fspi_readl(FSPI_IPCR1));
+
+		do {
+			sts0 = fspi_readl(FSPI_STS0);
+		} while (((sts0 & FSPI_STS0_ARB_IDLE) == 0) &&
+			 ((sts0 & FSPI_STS0_SEQ_IDLE) == 0));
+
+		/* Trigger IP Read Command */
+		fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+		PRA("0x%x", fspi_readl(FSPI_IPCMD));
+
+		intr = fspi_readl(FSPI_INTR);
+		if (((intr & FSPI_INTR_IPCMDGE) != 0) ||
+		    ((intr & FSPI_INTR_IPCMDERR) != 0)) {
+			ERROR("Error in IP READ INTR=0x%x\n", intr);
+			return -XSPI_IP_READ_FAIL;
+		}
+		/* Will read in n iterations of each 8 FIFO's(WM level) */
+		x_iteration = x_size_rx / x_size_wm;
+		for (i = 0U; i < x_iteration; i++) {
+			if ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPRXWA_MASK) == 0) {
+				PRA("0x%x", fspi_readl(FSPI_INTR));
+			}
+			/* Wait for IP Rx Watermark Fill event */
+			while (!(fspi_readl(FSPI_INTR) & FSPI_INTR_IPRXWA_MASK)) {
+				PRA("0x%x", fspi_readl(FSPI_INTR));
+			}
+
+			/* Read RX FIFO's(upto WM level) & copy to rxbuffer */
+			for (j = 0U; j < x_size_wm; j += 4U) {
+				/* Read FIFO Data Register */
+				data = fspi_readl(FSPI_RFDR + j);
+#if FSPI_IPDATA_SWAP /* Just In case you want swap */
+				data = bswap32(data);
+#endif
+				memcpy(pv_rx_buf++, &data, 4);
+			}
+
+			/* Clear IP_RX_WATERMARK Event in INTR register */
+			/* Reset FIFO Read pointer for next iteration.*/
+			fspi_writel(FSPI_INTR, FSPI_INTR_IPRXWA);
+		}
+
+		x_rem = x_size_rx % x_size_wm;
+
+		if (x_rem != 0U) {
+			/* Wait for data filled */
+			while (!(fspi_readl(FSPI_IPRXFSTS) & FSPI_IPRXFSTS_FILL_MASK)) {
+				PRA("0x%x", fspi_readl(FSPI_IPRXFSTS));
+			}
+
+			temp_size = 0;
+			j = 0U;
+			while (x_rem > 0U) {
+				data = 0U;
+				data =  fspi_readl(FSPI_RFDR + j);
+#if FSPI_IPDATA_SWAP /* Just In case you want swap */
+				data = bswap32(data);
+#endif
+				temp_size = (x_rem < 4) ? x_rem : 4;
+				memcpy(pv_rx_buf++, &data, temp_size);
+				x_rem -= temp_size;
+			}
+		}
+
+
+		while (!(fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK)) {
+			PRA("0x%x", fspi_readl(FSPI_INTR));
+		}
+
+		/* Invalid the RX FIFO, to run next IP Command */
+		fspi_writel(FSPI_IPRXFCR, FSPI_IPRXFCR_CLR);
+		/* Clear IP Command Done flag in interrupt register*/
+		fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+
+		/* Update remaining len, Increment x_addr read pointer. */
+		x_len_bytes -= x_size_rx;
+		x_addr += x_size_rx;
+	}
+	PR;
+	return XSPI_SUCCESS;
+}
+
+void xspi_ip_write(uint32_t pc_wr_addr, uint32_t *pv_wr_buf, uint32_t ui_len)
+{
+
+	uint32_t x_iteration = 0U, x_rem = 0U;
+	uint32_t x_size_tx = 0U, x_size_wm, temp_size;
+	uint32_t i = 0U, j = 0U;
+	uint32_t ui_data = 0U;
+	uint32_t x_addr, x_len_bytes;
+
+
+	x_size_wm = 8U;	/* Default TX WaterMark level: 8 Bytes. */
+	x_addr = (uint32_t)pc_wr_addr;
+	x_len_bytes = ui_len;
+	VERBOSE("In func %s[%d] x_addr =0x%x xLen_bytes=%d\n",
+			__func__, __LINE__, x_addr, x_len_bytes);
+
+	while (x_len_bytes != 0U) {
+
+		x_size_tx = (x_len_bytes >  FSPI_TX_IPBUF_SIZE) ?
+				FSPI_TX_IPBUF_SIZE : x_len_bytes;
+
+		/* IP Control Register0 - SF Address to be read */
+		fspi_writel(FSPI_IPCR0, x_addr);
+		INFO("In func %s[%d] x_addr =0x%x xLen_bytes=%d\n",
+				__func__, __LINE__, x_addr, x_len_bytes);
+
+		/*
+		 * Fill TX FIFO's..
+		 *
+		 */
+
+		x_iteration = x_size_tx / x_size_wm;
+		for (i = 0U; i < x_iteration; i++) {
+
+			/* Ensure TX FIFO Watermark Available */
+			while ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPTXWE_MASK) == 0)
+				;
+
+
+			/* Fill TxFIFO's ( upto watermark level) */
+			for (j = 0U; j < x_size_wm; j += 4U) {
+				memcpy(&ui_data, pv_wr_buf++,  4);
+				/* Write TX FIFO Data Register */
+				fspi_writel((FSPI_TFDR + j), ui_data);
+
+			}
+
+			/* Clear IP_TX_WATERMARK Event in INTR register */
+			/* Reset the FIFO Write pointer for next iteration */
+			fspi_writel(FSPI_INTR, FSPI_INTR_IPTXWE);
+		}
+
+		x_rem = x_size_tx % x_size_wm;
+
+		if (x_rem != 0U) {
+			/* Wait for TXFIFO empty */
+			while (!(fspi_readl(FSPI_INTR) & FSPI_INTR_IPTXWE))
+				;
+
+			temp_size = 0U;
+			j = 0U;
+			while (x_rem > 0U) {
+				ui_data = 0U;
+				temp_size = (x_rem < 4U) ? x_rem : 4U;
+				memcpy(&ui_data, pv_wr_buf++, temp_size);
+				INFO("%d ---> pv_wr_buf=0x%p\n", __LINE__, pv_wr_buf);
+				fspi_writel((FSPI_TFDR + j), ui_data);
+				x_rem -= temp_size;
+				j += 4U ; /* TODO: May not be needed*/
+			}
+			/* Clear IP_TX_WATERMARK Event in INTR register */
+			/* Reset FIFO's Write pointer for next iteration.*/
+			fspi_writel(FSPI_INTR, FSPI_INTR_IPTXWE);
+		}
+
+		/* IP Control Register1 - SEQID_WRITE operation, Size */
+		fspi_writel(FSPI_IPCR1, (uint32_t)(FSPI_WRITE_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) | (uint16_t) x_size_tx);
+		/* Trigger IP Write Command */
+		fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+
+		/* Wait for IP Write command done */
+		while (!(fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK))
+			;
+
+		/* Invalidate TX FIFOs & acknowledge IP_CMD_DONE event */
+		fspi_writel(FSPI_IPTXFCR, FSPI_IPTXFCR_CLR);
+		fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+
+		/* for next iteration */
+		x_len_bytes  -=  x_size_tx;
+		x_addr += x_size_tx;
+	}
+
+}
+
+int xspi_write(uint32_t pc_wr_addr, void *pv_wr_buf, uint32_t ui_len)
+{
+
+	uint32_t x_addr;
+	uint32_t x_page1_len = 0U, x_page_l_len = 0U;
+	uint32_t i, j = 0U;
+	void *buf = pv_wr_buf;
+
+	VERBOSE("\nIn func %s\n", __func__);
+
+	x_addr = (uint32_t)(pc_wr_addr);
+	if ((ui_len <= F_PAGE_256) && ((x_addr % F_PAGE_256) == 0)) {
+		x_page1_len = ui_len;
+		INFO("%d ---> x_page1_len=0x%x x_page_l_len =0x%x j=0x%x\n", __LINE__, x_page1_len, x_page_l_len, j);
+	} else if ((ui_len <= F_PAGE_256) && ((x_addr % F_PAGE_256) != 0)) {
+		x_page1_len = (F_PAGE_256 - (x_addr % F_PAGE_256));
+		if (ui_len > x_page1_len) {
+			x_page_l_len = (ui_len - x_page1_len) % F_PAGE_256;
+		} else {
+			x_page1_len = ui_len;
+			x_page_l_len = 0;
+		}
+		j = 0U;
+		INFO("%d 0x%x 0x%x\n", x_addr % F_PAGE_256, x_addr % F_PAGE_256, F_PAGE_256);
+		INFO("%d ---> x_page1_len=0x%x x_page_l_len =0x%x j=0x%x\n", __LINE__, x_page1_len, x_page_l_len, j);
+	} else if ((ui_len > F_PAGE_256) && ((x_addr % F_PAGE_256) == 0)) {
+		j = ui_len / F_PAGE_256;
+		x_page_l_len = ui_len % F_PAGE_256;
+		INFO("%d ---> x_page1_len=0x%x x_page_l_len =0x%x j=0x%x\n", __LINE__, x_page1_len, x_page_l_len, j);
+	} else if ((ui_len > F_PAGE_256) && ((x_addr % F_PAGE_256) != 0)) {
+		x_page1_len = (F_PAGE_256 - (x_addr % F_PAGE_256));
+		j = (ui_len - x_page1_len) / F_PAGE_256;
+		x_page_l_len = (ui_len - x_page1_len) % F_PAGE_256;
+		INFO("%d ---> x_page1_len=0x%x x_page_l_len =0x%x j=0x%x\n", __LINE__, x_page1_len, x_page_l_len, j);
+	}
+
+	if (x_page1_len != 0U) {
+		xspi_wren(x_addr);
+		xspi_ip_write(x_addr, (uint32_t *)buf, x_page1_len);
+		while (is_flash_busy())
+			;
+		INFO("%d Initial pc_wr_addr=0x%x, Final x_addr=0x%x, Initial ui_len=0x%x Final ui_len=0x%x\n",
+		     __LINE__, pc_wr_addr, x_addr, ui_len, (x_addr-pc_wr_addr));
+		INFO("Initial Buf pv_wr_buf=%p, final Buf=%p\n", pv_wr_buf, buf);
+		x_addr += x_page1_len;
+		/* TODO What is buf start is not 4 aligned */
+		buf = buf + x_page1_len;
+	}
+
+	for (i = 0U; i < j; i++) {
+		INFO("In for loop Buf pv_wr_buf=%p, final Buf=%p x_addr=0x%x offset_buf %d.\n",
+				pv_wr_buf, buf, x_addr, x_page1_len/4);
+		xspi_wren(x_addr);
+		xspi_ip_write(x_addr, (uint32_t *)buf, F_PAGE_256);
+		while (is_flash_busy())
+			;
+		INFO("%d Initial pc_wr_addr=0x%x, Final x_addr=0x%x, Initial ui_len=0x%x Final ui_len=0x%x\n",
+		     __LINE__, pc_wr_addr, x_addr, ui_len, (x_addr-pc_wr_addr));
+		x_addr += F_PAGE_256;
+		/* TODO What is buf start is not 4 aligned */
+		buf = buf + F_PAGE_256;
+		INFO("Initial Buf pv_wr_buf=%p, final Buf=%p\n", pv_wr_buf, buf);
+	}
+
+	if (x_page_l_len != 0U) {
+		INFO("%d Initial Buf pv_wr_buf=%p, final Buf=%p x_page_l_len=0x%x\n", __LINE__, pv_wr_buf, buf, x_page_l_len);
+		xspi_wren(x_addr);
+		xspi_ip_write(x_addr, (uint32_t *)buf, x_page_l_len);
+		while (is_flash_busy())
+			;
+		INFO("%d Initial pc_wr_addr=0x%x, Final x_addr=0x%x, Initial ui_len=0x%x Final ui_len=0x%x\n",
+				__LINE__, pc_wr_addr, x_addr, ui_len, (x_addr-pc_wr_addr));
+	}
+
+	VERBOSE("Now calling func call Invalidate%s\n", __func__);
+	fspi_ahb_invalidate();
+	return XSPI_SUCCESS;
+}
+
+int xspi_wren(uint32_t pc_wr_addr)
+{
+	VERBOSE("In func %s Addr=0x%x\n", __func__, pc_wr_addr);
+
+	fspi_writel(FSPI_IPTXFCR, FSPI_IPTXFCR_CLR);
+
+	fspi_writel(FSPI_IPCR0, (uint32_t)pc_wr_addr);
+	fspi_writel(FSPI_IPCR1, ((FSPI_WREN_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) |  0));
+	fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+
+	while ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK) == 0)
+		;
+
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+	return XSPI_SUCCESS;
+}
+
+static void fspi_bbluk_er(void)
+{
+	VERBOSE("In func %s\n", __func__);
+	fspi_writel(FSPI_IPCR0, 0x0);
+	fspi_writel(FSPI_IPCR1, ((FSPI_BE_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) | 20));
+	fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+
+	while ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK) == 0)
+		;
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+
+}
+
+static void fspi_RDSR(uint32_t *rxbuf, const void *p_addr, uint32_t size)
+{
+	uint32_t iprxfcr = 0U;
+	uint32_t data = 0U;
+
+	iprxfcr = fspi_readl(FSPI_IPRXFCR);
+	/* IP RX FIFO would be read by processor */
+	iprxfcr = iprxfcr & (uint32_t)~FSPI_IPRXFCR_CLR;
+	/* Invalid data entries in IP RX FIFO */
+	iprxfcr = iprxfcr | FSPI_IPRXFCR_CLR;
+	fspi_writel(FSPI_IPRXFCR, iprxfcr);
+
+	fspi_writel(FSPI_IPCR0, (uintptr_t) p_addr);
+	fspi_writel(FSPI_IPCR1,
+		    (uint32_t) ((FSPI_RDSR_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT)
+		    | (uint16_t) size));
+	/* Trigger the command */
+	fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+	/* Wait for command done */
+	while ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK) == 0)
+		;
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+
+	data = fspi_readl(FSPI_RFDR);
+	memcpy(rxbuf, &data, size);
+
+	/* Rx FIFO invalidation needs to be done prior w1c of INTR.IPRXWA bit */
+	fspi_writel(FSPI_IPRXFCR, FSPI_IPRXFCR_CLR);
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPRXWA_MASK);
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+
+}
+
+bool is_flash_busy(void)
+{
+#define FSPI_ONE_BYTE 1
+	uint8_t data[4];
+
+	VERBOSE("In func %s\n\n", __func__);
+	fspi_RDSR((uint32_t *) data, 0, FSPI_ONE_BYTE);
+
+	return !!((uint32_t) data[0] & FSPI_NOR_SR_WIP_MASK);
+}
+
+int xspi_bulk_erase(void)
+{
+	VERBOSE("In func %s\n", __func__);
+	xspi_wren((uint32_t) 0x0);
+	fspi_bbluk_er();
+	while (is_flash_busy())
+		;
+	fspi_ahb_invalidate();
+	return XSPI_SUCCESS;
+}
+
+static void fspi_sec_er(uint32_t pc_wr_addr)
+{
+	uint32_t x_addr;
+
+	VERBOSE("In func %s\n", __func__);
+	x_addr = (uint32_t)(pc_wr_addr);
+
+	fspi_writel(FSPI_IPCR0, x_addr);
+	INFO("In [%s][%d] Erase address 0x%x\n", __func__, __LINE__, (x_addr));
+#if CONFIG_FSPI_ERASE_4K
+	fspi_writel(FSPI_IPCR1, ((FSPI_4K_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) | 0));
+#else
+	fspi_writel(FSPI_IPCR1, ((FSPI_SE_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) | 0));
+#endif
+	fspi_writel(FSPI_IPCMD, FSPI_IPCMD_TRG_MASK);
+
+	while ((fspi_readl(FSPI_INTR) & FSPI_INTR_IPCMDDONE_MASK) == 0) {
+		PRA("0x%x", fspi_readl(FSPI_INTR));
+	}
+	fspi_writel(FSPI_INTR, FSPI_INTR_IPCMDDONE_MASK);
+}
+
+int xspi_sector_erase(uint32_t pc_wr_addr, uint32_t ui_len)
+{
+	uint32_t x_addr, x_len_bytes, i, num_sector = 0U;
+
+	VERBOSE("In func %s\n", __func__);
+	x_addr = (uint32_t)(pc_wr_addr);
+	if ((x_addr % F_SECTOR_ERASE_SZ) != 0) {
+		ERROR("!!! In func %s, unalinged start address can only be in multiples of 0x%x\n",
+		      __func__, F_SECTOR_ERASE_SZ);
+		return -XSPI_ERASE_FAIL;
+	}
+
+	x_len_bytes = ui_len * 1;
+	if (x_len_bytes < F_SECTOR_ERASE_SZ) {
+		ERROR("!!! In func %s, Less than 1 sector can only be in multiples of 0x%x\n",
+				__func__, F_SECTOR_ERASE_SZ);
+		return -XSPI_ERASE_FAIL;
+	}
+
+	num_sector = x_len_bytes/F_SECTOR_ERASE_SZ;
+	num_sector += x_len_bytes % F_SECTOR_ERASE_SZ ? 1U : 0U;
+	INFO("F_SECTOR_ERASE_SZ: 0x%08x, num_sector: %d\n", F_SECTOR_ERASE_SZ, num_sector);
+
+	for (i = 0U; i < num_sector ; i++) {
+		xspi_wren(x_addr + (F_SECTOR_ERASE_SZ * i));
+		fspi_sec_er(x_addr + (F_SECTOR_ERASE_SZ * i));
+		while (is_flash_busy())
+			;
+	}
+	fspi_ahb_invalidate();
+	return XSPI_SUCCESS;
+}
+
+
+__attribute__((unused)) static void  fspi_delay_ms(uint32_t x)
+{
+	volatile unsigned long  ul_count;
+
+	for (ul_count = 0U; ul_count < (30U * x); ul_count++)
+		;
+
+}
+
+
+#if defined(DEBUG_FLEXSPI)
+static void fspi_dump_regs(void)
+{
+	uint32_t i;
+
+	VERBOSE("\nRegisters Dump:\n");
+	VERBOSE("Flexspi: Register FSPI_MCR0(0x%x) = 0x%08x\n", FSPI_MCR0, fspi_readl(FSPI_MCR0));
+	VERBOSE("Flexspi: Register FSPI_MCR2(0x%x) = 0x%08x\n", FSPI_MCR2, fspi_readl(FSPI_MCR2));
+	VERBOSE("Flexspi: Register FSPI_DLL_A_CR(0x%x) = 0x%08x\n", FSPI_DLLACR, fspi_readl(FSPI_DLLACR));
+	VERBOSE("\n");
+
+	for (i = 0U; i < 8U; i++) {
+		VERBOSE("Flexspi: Register FSPI_AHBRX_BUF0CR0(0x%x) = 0x%08x\n", FSPI_AHBRX_BUF0CR0 + i * 4, fspi_readl((FSPI_AHBRX_BUF0CR0 + i * 4)));
+	}
+	VERBOSE("\n");
+
+	VERBOSE("Flexspi: Register FSPI_AHBRX_BUF7CR0(0x%x) = 0x%08x\n", FSPI_AHBRX_BUF7CR0, fspi_readl(FSPI_AHBRX_BUF7CR0));
+	VERBOSE("Flexspi: Register FSPI_AHB_CR(0x%x) \t  = 0x%08x\n", FSPI_AHBCR, fspi_readl(FSPI_AHBCR));
+	VERBOSE("\n");
+
+	for (i = 0U; i < 4U; i++) {
+		VERBOSE("Flexspi: Register FSPI_FLSH_A1_CR2,(0x%x) = 0x%08x\n", FSPI_FLSHA1CR2 + i * 4, fspi_readl(FSPI_FLSHA1CR2 + i * 4));
+	}
+}
+#endif
+
+int fspi_init(uint32_t base_reg_addr, uint32_t flash_start_addr)
+{
+	uint32_t	mcrx;
+	uint32_t	flash_size;
+
+	if (fspi_base_reg_addr != 0U) {
+		INFO("FSPI is already initialized.\n");
+		return XSPI_SUCCESS;
+	}
+
+	fspi_base_reg_addr = base_reg_addr;
+	fspi_flash_base_addr = flash_start_addr;
+
+	INFO("Flexspi driver: Version v1.0\n");
+	INFO("Flexspi: Default MCR0 = 0x%08x, before reset\n", fspi_readl(FSPI_MCR0));
+	VERBOSE("Flexspi: Resetting controller...\n");
+
+	/* Reset FlexSpi Controller */
+	fspi_writel(FSPI_MCR0, FSPI_MCR0_SWRST);
+	while ((fspi_readl(FSPI_MCR0) & FSPI_MCR0_SWRST))
+		;  /* FSPI_MCR0_SWRESET_MASK */
+
+
+	/* Disable Controller Module before programming its registersi, especially MCR0 (Master Control Register0) */
+	fspi_MDIS(1);
+	/*
+	 * Program MCR0 with default values, AHB Timeout(0xff), IP Timeout(0xff).  {FSPI_MCR0- 0xFFFF0000}
+	 */
+
+	/* Timeout wait cycle for AHB command grant */
+	mcrx = fspi_readl(FSPI_MCR0);
+	mcrx |= (uint32_t)((FSPI_MAX_TIMEOUT_AHBCMD << FSPI_MCR0_AHBGRANTWAIT_SHIFT) & (FSPI_MCR0_AHBGRANTWAIT_MASK));
+
+	/* Time out wait cycle for IP command grant*/
+	mcrx |= (uint32_t) (FSPI_MAX_TIMEOUT_IPCMD << FSPI_MCR0_IPGRANTWAIT_SHIFT) & (FSPI_MCR0_IPGRANTWAIT_MASK);
+
+	/* TODO why BE64 set BE32*/
+	mcrx |= (uint32_t) (FSPI_ENDCFG_LE64 << FSPI_MCR0_ENDCFG_SHIFT) & FSPI_MCR0_ENDCFG_MASK;
+
+	fspi_writel(FSPI_MCR0, mcrx);
+
+	/* Reset the DLL register to default value */
+	fspi_writel(FSPI_DLLACR, FSPI_DLLACR_OVRDEN);
+	fspi_writel(FSPI_DLLBCR, FSPI_DLLBCR_OVRDEN);
+
+#if ERRATA_FLASH_A050272	/* ERRATA DLL */
+	for (uint8_t delay = 100U; delay > 0U; delay--)	{
+		__asm__ volatile ("nop");
+	}
+#endif
+
+	/* Configure flash control registers for different chip select */
+	flash_size = (F_FLASH_SIZE_BYTES * FLASH_NUM) / FSPI_BYTES_PER_KBYTES;
+	fspi_writel(FSPI_FLSHA1CR0, flash_size);
+	fspi_writel(FSPI_FLSHA2CR0, 0U);
+	fspi_writel(FSPI_FLSHB1CR0, 0U);
+	fspi_writel(FSPI_FLSHB2CR0, 0U);
+
+#if defined(CONFIG_FSPI_AHB)
+	fspi_init_ahb();
+#endif
+	/* RE-Enable Controller Module */
+	fspi_MDIS(0);
+	INFO("Flexspi: After MCR0 = 0x%08x,\n", fspi_readl(FSPI_MCR0));
+	fspi_setup_LUT();
+
+	/* Dump of all registers, ensure controller not disabled anymore*/
+#if defined(DEBUG_FLEXSPI)
+	fspi_dump_regs();
+#endif
+
+	INFO("Flexspi: Init done!!\n");
+
+#if DEBUG_FLEXSPI
+
+	uint32_t xspi_addr = SZ_57M;
+
+	/*
+	 * Second argument of fspi_test is the size of buffer(s) passed
+	 * to the function.
+	 * SIZE_BUFFER defined in test_fspi.c is kept large enough to
+	 * accommodate variety of sizes for regressive tests.
+	 */
+	fspi_test(xspi_addr, 0x40, 0);
+	fspi_test(xspi_addr, 0x15, 2);
+	fspi_test(xspi_addr, 0x80, 0);
+	fspi_test(xspi_addr, 0x81, 0);
+	fspi_test(xspi_addr, 0x79, 3);
+
+	fspi_test(xspi_addr + 0x11, 0x15, 0);
+	fspi_test(xspi_addr + 0x11, 0x40, 0);
+	fspi_test(xspi_addr + 0xff, 0x40, 1);
+	fspi_test(xspi_addr + 0x25, 0x81, 2);
+	fspi_test(xspi_addr + 0xef, 0x6f, 3);
+
+	fspi_test((xspi_addr - F_SECTOR_ERASE_SZ), 0x229, 0);
+#endif
+
+	return XSPI_SUCCESS;
+}
diff --git a/drivers/nxp/flexspi/nor/fspi.h b/drivers/nxp/flexspi/nor/fspi.h
new file mode 100644
index 0000000..da2e269
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/fspi.h
@@ -0,0 +1,385 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * FlexSpi Registers & Bits definition.
+ *
+ */
+
+#ifndef FSPI_H
+#define FSPI_H
+
+#ifndef __ASSEMBLER__
+#include <lib/mmio.h>
+
+#ifdef NXP_FSPI_BE
+#define fspi_in32(a)		bswap32(mmio_read_32((uintptr_t)(a)))
+#define fspi_out32(a, v)	mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_FSPI_LE)
+#define fspi_in32(a)		mmio_read_32((uintptr_t)(a))
+#define fspi_out32(a, v)	mmio_write_32((uintptr_t)(a), v)
+#else
+#error Please define FSPI register endianness
+#endif
+
+#endif
+
+/* All LE so not swap needed */
+#define FSPI_IPDATA_SWAP		0U
+#define FSPI_AHBDATA_SWAP		0U
+
+#define CONFIG_FSPI_FASTREAD		1U
+
+#define FSPI_BYTES_PER_KBYTES		0x400U
+#define FLASH_NUM			1U
+
+#define FSPI_READ_SEQ_ID		0U
+#define FSPI_WREN_SEQ_ID		1U
+#define FSPI_WRITE_SEQ_ID		2U
+#define FSPI_SE_SEQ_ID			3U
+#define FSPI_RDSR_SEQ_ID		4U
+#define FSPI_BE_SEQ_ID			5U
+#define FSPI_FASTREAD_SEQ_ID		6U
+#define FSPI_4K_SEQ_ID			7U
+
+/*
+ * LUT register layout:
+ *
+ *  ---------------------------------------------------
+ *  | INSTR1 | PAD1 | OPRND1 | INSTR0 | PAD0 | OPRND0 |
+ *  ---------------------------------------------------
+ *
+ *    INSTR_SHIFT- 10, PAD_SHIFT - 8, OPRND_SHIFT -0
+ */
+#define FSPI_INSTR_OPRND0_SHIFT		0
+#define FSPI_INSTR_OPRND0(x)		(x << FSPI_INSTR_OPRND0_SHIFT)
+#define FSPI_INSTR_PAD0_SHIFT		8
+#define FSPI_INSTR_PAD0(x)		((x) << FSPI_INSTR_PAD0_SHIFT)
+#define FSPI_INSTR_OPCODE0_SHIFT	10
+#define FSPI_INSTR_OPCODE0(x)		((x) << FSPI_INSTR_OPCODE0_SHIFT)
+#define FSPI_INSTR_OPRND1_SHIFT		16
+#define FSPI_INSTR_OPRND1(x)		((x) << FSPI_INSTR_OPRND1_SHIFT)
+#define FSPI_INSTR_PAD1_SHIFT		24
+#define FSPI_INSTR_PAD1(x)		((x) << FSPI_INSTR_PAD1_SHIFT)
+#define FSPI_INSTR_OPCODE1_SHIFT	26
+#define FSPI_INSTR_OPCODE1(x)		((x) << FSPI_INSTR_OPCODE1_SHIFT)
+
+/* Instruction set for the LUT register. */
+#define LUT_STOP			0x00
+#define LUT_CMD				0x01
+#define LUT_ADDR			0x02
+#define LUT_CADDR_SDR			0x03
+#define LUT_MODE			0x04
+#define LUT_MODE2			0x05
+#define LUT_MODE4			0x06
+#define LUT_MODE8			0x07
+#define LUT_NXP_WRITE			0x08
+#define LUT_NXP_READ			0x09
+
+#define LUT_LEARN_SDR			0x0A
+#define LUT_DATSZ_SDR			0x0B
+#define LUT_DUMMY			0x0C
+#define LUT_DUMMY_RWDS_SDR		0x0D
+#define LUT_JMP_ON_CS			0x1F
+#define LUT_CMD_DDR			0x21
+#define LUT_ADDR_DDR			0x22
+#define LUT_CADDR_DDR			0x23
+#define LUT_MODE_DDR			0x24
+#define LUT_MODE2_DDR			0x25
+#define LUT_MODE4_DDR			0x26
+#define LUT_MODE8_DDR			0x27
+#define LUT_WRITE_DDR			0x28
+#define LUT_READ_DDR			0x29
+#define LUT_LEARN_DDR			0x2A
+#define LUT_DATSZ_DDR			0x2B
+#define LUT_DUMMY_DDR			0x2C
+#define LUT_DUMMY_RWDS_DDR		0x2D
+
+#define FSPI_NOR_CMD_READ		0x03
+#define FSPI_NOR_CMD_READ_4B		0x13
+#define FSPI_NOR_CMD_FASTREAD		0x0b
+#define FSPI_NOR_CMD_FASTREAD_4B	0x0c
+#define FSPI_NOR_CMD_PP			0x02
+#define FSPI_NOR_CMD_PP_4B		0x12
+#define FSPI_NOR_CMD_WREN		0x06
+#define FSPI_NOR_CMD_SE_64K		0xd8
+#define FSPI_NOR_CMD_SE_64K_4B		0xdc
+#define FSPI_NOR_CMD_SE_4K		0x20
+#define FSPI_NOR_CMD_SE_4K_4B		0x21
+#define FSPI_NOR_CMD_BE			0x60
+#define FSPI_NOR_CMD_RDSR		0x05
+#define FSPI_NOR_CMD_WREN_STOP		0x04
+
+#define FSPI_LUT_STOP			0x00
+#define FSPI_LUT_CMD			0x01
+#define FSPI_LUT_ADDR			0x02
+
+#define FSPI_LUT_PAD1			0
+#define FSPI_LUT_PAD2			1
+#define FSPI_LUT_PAD4			2
+#define FSPI_LUT_PAD8			3
+
+#define FSPI_LUT_ADDR24BIT		0x18
+#define FSPI_LUT_ADDR32BIT		0x20
+
+#define FSPI_LUT_WRITE			0x08
+#define FSPI_LUT_READ			0x09
+#define FSPI_DUMMY_SDR			0x0c
+
+/* TODO Check size if functional*/
+#define FSPI_RX_IPBUF_SIZE		0x200	/*  64*64 bits  */
+#define FSPI_TX_IPBUF_SIZE		0x400	/* 128*64 bits */
+
+#define FSPI_RX_MAX_AHBBUF_SIZE		0x800 /* 256 * 64bits */
+#define FSPI_TX_MAX_AHBBUF_SIZE		0x40  /* 8 * 64bits   */
+
+#define FSPI_LUTREG_OFFSET			0x200ul
+
+#define FSPI_MAX_TIMEOUT_AHBCMD		0xFFU
+#define FSPI_MAX_TIMEOUT_IPCMD		0xFF
+#define FSPI_SER_CLK_DIV		0x04
+#define FSPI_HSEN			0
+#define FSPI_ENDCFG_BE64		0x01
+#define FSPI_ENDCFG_BE32		0x03
+#define FSPI_ENDCFG_LE32		0x02
+#define FSPI_ENDCFG_LE64		0x0
+
+#define MASK_24BIT_ADDRESS		0x00ffffff
+#define MASK_32BIT_ADDRESS		0xffffffff
+
+/* Registers used by the driver */
+#define FSPI_MCR0			0x0ul
+#define FSPI_MCR0_AHB_TIMEOUT(x)	((x) << 24)
+#define FSPI_MCR0_IP_TIMEOUT(x)		((x) << 16)
+#define FSPI_MCR0_LEARN_EN		BIT(15)
+#define FSPI_MCR0_SCRFRUN_EN		BIT(14)
+#define FSPI_MCR0_OCTCOMB_EN		BIT(13)
+#define FSPI_MCR0_DOZE_EN		BIT(12)
+#define FSPI_MCR0_HSEN			BIT(11)
+#define FSPI_MCR0_SERCLKDIV		BIT(8)
+#define FSPI_MCR0_ATDF_EN		BIT(7)
+#define FSPI_MCR0_ARDF_EN		BIT(6)
+#define FSPI_MCR0_RXCLKSRC(x)		((x) << 4)
+#define FSPI_MCR0_END_CFG(x)		((x) << 2)
+#define FSPI_MCR0_MDIS			BIT(1)
+#define FSPI_MCR0_SWRST			BIT(0)
+
+#define FSPI_MCR0_AHBGRANTWAIT_SHIFT	24
+#define FSPI_MCR0_AHBGRANTWAIT_MASK	(0xFFU << FSPI_MCR0_AHBGRANTWAIT_SHIFT)
+#define FSPI_MCR0_IPGRANTWAIT_SHIFT	16
+#define FSPI_MCR0_IPGRANTWAIT_MASK	(0xFF << FSPI_MCR0_IPGRANTWAIT_SHIFT)
+#define FSPI_MCR0_HSEN_SHIFT		11
+#define FSPI_MCR0_HSEN_MASK		(1 << FSPI_MCR0_HSEN_SHIFT)
+#define FSPI_MCR0_SERCLKDIV_SHIFT	8
+#define FSPI_MCR0_SERCLKDIV_MASK	(7 << FSPI_MCR0_SERCLKDIV_SHIFT)
+#define FSPI_MCR0_ENDCFG_SHIFT		2
+#define FSPI_MCR0_ENDCFG_MASK		(3 << FSPI_MCR0_ENDCFG_SHIFT)
+#define FSPI_MCR0_RXCLKSRC_SHIFT	4
+#define FSPI_MCR0_RXCLKSRC_MASK		(3 << FSPI_MCR0_RXCLKSRC_SHIFT)
+
+#define FSPI_MCR1			0x04
+#define FSPI_MCR1_SEQ_TIMEOUT(x)	((x) << 16)
+#define FSPI_MCR1_AHB_TIMEOUT(x)	(x)
+
+#define FSPI_MCR2			0x08
+#define FSPI_MCR2_IDLE_WAIT(x)		((x) << 24)
+#define FSPI_MCR2_SAMEDEVICEEN		BIT(15)
+#define FSPI_MCR2_CLRLRPHS		BIT(14)
+#define FSPI_MCR2_ABRDATSZ		BIT(8)
+#define FSPI_MCR2_ABRLEARN		BIT(7)
+#define FSPI_MCR2_ABR_READ		BIT(6)
+#define FSPI_MCR2_ABRWRITE		BIT(5)
+#define FSPI_MCR2_ABRDUMMY		BIT(4)
+#define FSPI_MCR2_ABR_MODE		BIT(3)
+#define FSPI_MCR2_ABRCADDR		BIT(2)
+#define FSPI_MCR2_ABRRADDR		BIT(1)
+#define FSPI_MCR2_ABR_CMD		BIT(0)
+
+#define FSPI_AHBCR			0x0c
+#define FSPI_AHBCR_RDADDROPT		BIT(6)
+#define FSPI_AHBCR_PREF_EN		BIT(5)
+#define FSPI_AHBCR_BUFF_EN		BIT(4)
+#define FSPI_AHBCR_CACH_EN		BIT(3)
+#define FSPI_AHBCR_CLRTXBUF		BIT(2)
+#define FSPI_AHBCR_CLRRXBUF		BIT(1)
+#define FSPI_AHBCR_PAR_EN		BIT(0)
+
+#define FSPI_INTEN			0x10
+#define FSPI_INTEN_SCLKSBWR		BIT(9)
+#define FSPI_INTEN_SCLKSBRD		BIT(8)
+#define FSPI_INTEN_DATALRNFL		BIT(7)
+#define FSPI_INTEN_IPTXWE		BIT(6)
+#define FSPI_INTEN_IPRXWA		BIT(5)
+#define FSPI_INTEN_AHBCMDERR		BIT(4)
+#define FSPI_INTEN_IPCMDERR		BIT(3)
+#define FSPI_INTEN_AHBCMDGE		BIT(2)
+#define FSPI_INTEN_IPCMDGE		BIT(1)
+#define FSPI_INTEN_IPCMDDONE		BIT(0)
+
+#define FSPI_INTR			0x14
+#define FSPI_INTR_SCLKSBWR		BIT(9)
+#define FSPI_INTR_SCLKSBRD		BIT(8)
+#define FSPI_INTR_DATALRNFL		BIT(7)
+#define FSPI_INTR_IPTXWE		BIT(6)
+#define FSPI_INTR_IPRXWA		BIT(5)
+#define FSPI_INTR_AHBCMDERR		BIT(4)
+#define FSPI_INTR_IPCMDERR		BIT(3)
+#define FSPI_INTR_AHBCMDGE		BIT(2)
+#define FSPI_INTR_IPCMDGE		BIT(1)
+#define FSPI_INTR_IPCMDDONE		BIT(0)
+
+#define FSPI_LUTKEY			0x18
+#define FSPI_LUTKEY_VALUE		0x5AF05AF0
+
+#define FSPI_LCKCR			0x1C
+
+#define FSPI_LCKER_LOCK			0x1
+#define FSPI_LCKER_UNLOCK		0x2
+
+#define FSPI_BUFXCR_INVALID_MSTRID	0xE
+#define FSPI_AHBRX_BUF0CR0		0x20
+#define FSPI_AHBRX_BUF1CR0		0x24
+#define FSPI_AHBRX_BUF2CR0		0x28
+#define FSPI_AHBRX_BUF3CR0		0x2C
+#define FSPI_AHBRX_BUF4CR0		0x30
+#define FSPI_AHBRX_BUF5CR0		0x34
+#define FSPI_AHBRX_BUF6CR0		0x38
+#define FSPI_AHBRX_BUF7CR0		0x3C
+
+#define FSPI_AHBRXBUF0CR7_PREF		BIT(31)
+
+#define FSPI_AHBRX_BUF0CR1		0x40
+#define FSPI_AHBRX_BUF1CR1		0x44
+#define FSPI_AHBRX_BUF2CR1		0x48
+#define FSPI_AHBRX_BUF3CR1		0x4C
+#define FSPI_AHBRX_BUF4CR1		0x50
+#define FSPI_AHBRX_BUF5CR1		0x54
+#define FSPI_AHBRX_BUF6CR1		0x58
+#define FSPI_AHBRX_BUF7CR1		0x5C
+
+#define FSPI_FLSHA1CR0			0x60
+#define FSPI_FLSHA2CR0			0x64
+#define FSPI_FLSHB1CR0			0x68
+#define FSPI_FLSHB2CR0			0x6C
+#define FSPI_FLSHXCR0_SZ_KB		10
+#define FSPI_FLSHXCR0_SZ(x)		((x) >> FSPI_FLSHXCR0_SZ_KB)
+
+#define FSPI_FLSHA1CR1			0x70
+#define FSPI_FLSHA2CR1			0x74
+#define FSPI_FLSHB1CR1			0x78
+#define FSPI_FLSHB2CR1			0x7C
+#define FSPI_FLSHXCR1_CSINTR(x)		((x) << 16)
+#define FSPI_FLSHXCR1_CAS(x)		((x) << 11)
+#define FSPI_FLSHXCR1_WA		BIT(10)
+#define FSPI_FLSHXCR1_TCSH(x)		((x) << 5)
+#define FSPI_FLSHXCR1_TCSS(x)		(x)
+
+#define FSPI_FLSHXCR1_TCSH_SHIFT	5
+#define FSPI_FLSHXCR1_TCSH_MASK		(0x1F << FSPI_FLSHXCR1_TCSH_SHIFT)
+#define FSPI_FLSHXCR1_TCSS_SHIFT	0
+#define FSPI_FLSHXCR1_TCSS_MASK		(0x1F << FSPI_FLSHXCR1_TCSS_SHIFT)
+
+#define FSPI_FLSHA1CR2			0x80
+#define FSPI_FLSHA2CR2			0x84
+#define FSPI_FLSHB1CR2			0x88
+#define FSPI_FLSHB2CR2			0x8C
+#define FSPI_FLSHXCR2_CLRINSP		BIT(24)
+#define FSPI_FLSHXCR2_AWRWAIT		BIT(16)
+#define FSPI_FLSHXCR2_AWRSEQN_SHIFT	13
+#define FSPI_FLSHXCR2_AWRSEQI_SHIFT	8
+#define FSPI_FLSHXCR2_ARDSEQN_SHIFT	5
+#define FSPI_FLSHXCR2_ARDSEQI_SHIFT	0
+
+#define FSPI_IPCR0			0xA0
+
+#define FSPI_IPCR1			0xA4
+#define FSPI_IPCR1_IPAREN		BIT(31)
+#define FSPI_IPCR1_SEQNUM_SHIFT		24
+#define FSPI_IPCR1_SEQID_SHIFT		16
+#define FSPI_IPCR1_IDATSZ(x)		(x)
+
+#define FSPI_IPCMD			0xB0
+#define FSPI_IPCMD_TRG			BIT(0)
+
+
+/* IP Command Register */
+#define FSPI_IPCMD_TRG_SHIFT		0
+#define FSPI_IPCMD_TRG_MASK		(1 << FSPI_IPCMD_TRG_SHIFT)
+
+#define FSPI_INTR_IPRXWA_SHIFT		5
+#define FSPI_INTR_IPRXWA_MASK		(1 << FSPI_INTR_IPRXWA_SHIFT)
+
+#define FSPI_INTR_IPCMDDONE_SHIFT	0
+#define FSPI_INTR_IPCMDDONE_MASK	(1 << FSPI_INTR_IPCMDDONE_SHIFT)
+
+#define FSPI_INTR_IPTXWE_SHIFT		6
+#define FSPI_INTR_IPTXWE_MASK		(1 << FSPI_INTR_IPTXWE_SHIFT)
+
+#define FSPI_IPTXFSTS_FILL_SHIFT	0
+#define FSPI_IPTXFSTS_FILL_MASK		(0xFF << FSPI_IPTXFSTS_FILL_SHIFT)
+
+#define FSPI_IPCR1_ISEQID_SHIFT		16
+#define FSPI_IPCR1_ISEQID_MASK		(0x1F << FSPI_IPCR1_ISEQID_SHIFT)
+
+#define FSPI_IPRXFSTS_FILL_SHIFT	0
+#define FSPI_IPRXFSTS_FILL_MASK		(0xFF << FSPI_IPRXFSTS_FILL_SHIFT)
+
+#define FSPI_DLPR			0xB4
+
+#define FSPI_IPRXFCR			0xB8
+#define FSPI_IPRXFCR_CLR		BIT(0)
+#define FSPI_IPRXFCR_DMA_EN		BIT(1)
+#define FSPI_IPRXFCR_WMRK(x)		((x) << 2)
+
+#define FSPI_IPTXFCR			0xBC
+#define FSPI_IPTXFCR_CLR		BIT(0)
+#define FSPI_IPTXFCR_DMA_EN		BIT(1)
+#define FSPI_IPTXFCR_WMRK(x)		((x) << 2)
+
+#define FSPI_DLLACR			0xC0
+#define FSPI_DLLACR_OVRDEN		BIT(8)
+
+#define FSPI_DLLBCR			0xC4
+#define FSPI_DLLBCR_OVRDEN		BIT(8)
+
+#define FSPI_STS0			0xE0
+#define FSPI_STS0_DLPHB(x)		((x) << 8)
+#define FSPI_STS0_DLPHA(x)		((x) << 4)
+#define FSPI_STS0_CMD_SRC(x)		((x) << 2)
+#define FSPI_STS0_ARB_IDLE		BIT(1)
+#define FSPI_STS0_SEQ_IDLE		BIT(0)
+
+#define FSPI_STS1			0xE4
+#define FSPI_STS1_IP_ERRCD(x)		((x) << 24)
+#define FSPI_STS1_IP_ERRID(x)		((x) << 16)
+#define FSPI_STS1_AHB_ERRCD(x)		((x) << 8)
+#define FSPI_STS1_AHB_ERRID(x)		(x)
+
+#define FSPI_AHBSPNST			0xEC
+#define FSPI_AHBSPNST_DATLFT(x)		((x) << 16)
+#define FSPI_AHBSPNST_BUFID(x)		((x) << 1)
+#define FSPI_AHBSPNST_ACTIVE		BIT(0)
+
+#define FSPI_IPRXFSTS			0xF0
+#define FSPI_IPRXFSTS_RDCNTR(x)		((x) << 16)
+#define FSPI_IPRXFSTS_FILL(x)		(x)
+
+#define FSPI_IPTXFSTS			0xF4
+#define FSPI_IPTXFSTS_WRCNTR(x)		((x) << 16)
+#define FSPI_IPTXFSTS_FILL(x)		(x)
+
+#define FSPI_NOR_SR_WIP_SHIFT		(0)
+#define FSPI_NOR_SR_WIP_MASK		(1 << FSPI_NOR_SR_WIP_SHIFT)
+
+#define FSPI_RFDR			0x100
+#define FSPI_TFDR			0x180
+
+#define FSPI_LUT_BASE			0x200
+#define FSPI_LUT_OFFSET			(SEQID_LUT * 4 * 4)
+#define FSPI_LUT_REG(idx) \
+	(FSPI_LUT_BASE + FSPI_LUT_OFFSET + (idx) * 4)
+
+/* register map end */
+
+#endif
diff --git a/drivers/nxp/flexspi/nor/test_fspi.c b/drivers/nxp/flexspi/nor/test_fspi.c
new file mode 100644
index 0000000..c36c5b8
--- /dev/null
+++ b/drivers/nxp/flexspi/nor/test_fspi.c
@@ -0,0 +1,91 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdint.h>
+#include <stdio.h>
+
+#include <common/debug.h>
+#include <flash_info.h>
+#include "fspi.h"
+#include <fspi_api.h>
+
+/*
+ * The macros are defined to be used as test vector for testing fspi.
+ */
+#define	SIZE_BUFFER			0x250
+
+/*
+ * You may choose fspi_swap based on core endianness and flexspi IP/AHB
+ * buffer endianness set in MCR.
+ */
+#define fspi_swap32(A)			(A)
+
+void fspi_test(uint32_t fspi_test_addr, uint32_t size, int extra)
+{
+	uint32_t buffer[SIZE_BUFFER];
+	uint32_t count = 1;
+	uint32_t failed, i;
+
+	NOTICE("-------------------------- %d----------------------------------\n", count++);
+	INFO("Sector Erase size: 0x%08x, size: %d\n", F_SECTOR_ERASE_SZ, size);
+	/* Test Sector Erase */
+	xspi_sector_erase(fspi_test_addr - fspi_test_addr % F_SECTOR_ERASE_SZ,
+			  F_SECTOR_ERASE_SZ);
+
+	/* Test Erased data using IP read */
+	xspi_ip_read((fspi_test_addr), buffer, size * 4);
+
+	failed = 0;
+	for (i = 0; i < size; i++)
+		if (fspi_swap32(0xffffffff) != buffer[i]) {
+			failed = 1;
+			break;
+		}
+
+	if (failed == 0) {
+		NOTICE("[%d]: Success Erase: data in buffer[%d] 0x%08x\n", __LINE__, i-3, buffer[i-3]);
+	} else {
+		ERROR("Erase: Failed  -->xxx with buffer[%d]=0x%08x\n", i, buffer[i]);
+	}
+
+	for (i = 0; i < SIZE_BUFFER; i++)
+		buffer[i] = 0x12345678;
+
+	/* Write data from buffer to flash */
+	xspi_write(fspi_test_addr, (void *)buffer, (size * 4 + extra));
+	/* Check written data using IP read */
+	xspi_ip_read(fspi_test_addr, buffer, (size * 4 + extra));
+	failed = 0;
+	for (i = 0; i < size; i++)
+		if (fspi_swap32(0x12345678) != buffer[i]) {
+			failed = 1;
+			break;
+		}
+
+	if (failed == 0) {
+		NOTICE("[%d]: Success IpWrite with IP READ in buffer[%d] 0x%08x\n", __LINE__, i-3, buffer[i-3]);
+	} else {
+		ERROR("Write: Failed  -->xxxx with IP READ in buffer[%d]=0x%08x\n", i, buffer[i]);
+		return;
+	}
+
+	/* xspi_read may use AHB read */
+	xspi_read((fspi_test_addr), buffer, (size * 4 + extra));
+	failed = 0;
+	for (i = 0; i < size; i++)
+		if (fspi_swap32(0x12345678) != buffer[i]) {
+			failed = 1;
+			break;
+		}
+
+	if (failed == 0) {
+		NOTICE("[%d]: Success IpWrite with AHB OR IP READ on buffer[%d] 0x%08x\n", __LINE__, i-3, buffer[i-3]);
+	} else {
+		ERROR("Write: Failed  -->xxxx with AHB READ on buffer[%d]=0x%08x\n", i, buffer[i]);
+		return;
+	}
+}
diff --git a/drivers/nxp/gic/gic.mk b/drivers/nxp/gic/gic.mk
new file mode 100644
index 0000000..d75e071
--- /dev/null
+++ b/drivers/nxp/gic/gic.mk
@@ -0,0 +1,46 @@
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the GIC files
+#
+# -----------------------------------------------------------------------------
+
+ifeq (${ADD_GIC},)
+ADD_GIC			:= 1
+ifeq ($(GIC), GIC400)
+include drivers/arm/gic/v2/gicv2.mk
+GIC_SOURCES		+=	${GICV2_SOURCES}
+GIC_SOURCES		+=	${PLAT_DRIVERS_PATH}/gic/ls_gicv2.c	\
+				plat/common/plat_gicv2.c
+
+PLAT_INCLUDES		+=	-I${PLAT_DRIVERS_INCLUDE_PATH}/gic/gicv2
+else
+ifeq ($(GIC), GIC500)
+include drivers/arm/gic/v3/gicv3.mk
+GIC_SOURCES		+=	${GICV3_SOURCES}
+GIC_SOURCES		+=	${PLAT_DRIVERS_PATH}/gic/ls_gicv3.c	\
+				plat/common/plat_gicv3.c
+
+PLAT_INCLUDES		+=	-I${PLAT_DRIVERS_INCLUDE_PATH}/gic/gicv3
+else
+    $(error -> GIC type not set!)
+endif
+endif
+
+ifeq (${BL_COMM_GIC_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${GIC_SOURCES}
+else
+ifeq (${BL2_GIC_NEEDED},yes)
+BL2_SOURCES		+= ${GIC_SOURCES}
+endif
+ifeq (${BL31_GIC_NEEDED},yes)
+BL31_SOURCES		+= ${GIC_SOURCES}
+endif
+endif
+endif
+
+# -----------------------------------------------------------------------------
diff --git a/drivers/nxp/gic/ls_gicv2.c b/drivers/nxp/gic/ls_gicv2.c
new file mode 100644
index 0000000..62bc8db
--- /dev/null
+++ b/drivers/nxp/gic/ls_gicv2.c
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <gicv2.h>
+#include <plat_gic.h>
+
+
+/*
+ * NXP common helper to initialize the GICv3 only driver.
+ */
+void plat_ls_gic_driver_init(uintptr_t nxp_gicd_addr,
+			     uintptr_t nxp_gicc_addr,
+			     uint8_t plat_core_count,
+			     interrupt_prop_t *ls_interrupt_props,
+			     uint8_t ls_interrupt_prop_count,
+			     uint32_t *target_mask_array)
+{
+	static struct gicv2_driver_data ls_gic_data;
+
+	ls_gic_data.gicd_base = nxp_gicd_addr;
+	ls_gic_data.gicc_base = nxp_gicc_addr;
+	ls_gic_data.target_masks = target_mask_array;
+	ls_gic_data.target_masks_num = plat_core_count;
+	ls_gic_data.interrupt_props = ls_interrupt_props;
+	ls_gic_data.interrupt_props_num = ls_interrupt_prop_count;
+
+	gicv2_driver_init(&ls_gic_data);
+}
+
+void plat_ls_gic_init(void)
+{
+	gicv2_distif_init();
+	gicv2_pcpu_distif_init();
+	gicv2_cpuif_enable();
+}
+
+/******************************************************************************
+ * ARM common helper to enable the GICv2 CPU interface
+ *****************************************************************************/
+void plat_ls_gic_cpuif_enable(void)
+{
+	gicv2_cpuif_enable();
+}
+
+/******************************************************************************
+ * ARM common helper to disable the GICv2 CPU interface
+ *****************************************************************************/
+void plat_ls_gic_cpuif_disable(void)
+{
+	gicv2_cpuif_disable();
+}
+
+/******************************************************************************
+ * NXP common helper to initialize GICv2 per cpu
+ *****************************************************************************/
+void plat_gic_pcpu_init(void)
+{
+	gicv2_pcpu_distif_init();
+	gicv2_cpuif_enable();
+}
+
+/******************************************************************************
+ * Stubs for Redistributor power management. Although GICv2 doesn't have
+ * Redistributor interface, these are provided for the sake of uniform GIC API
+ *****************************************************************************/
+void plat_ls_gic_redistif_on(void)
+{
+}
+
+void plat_ls_gic_redistif_off(void)
+{
+}
diff --git a/drivers/nxp/gic/ls_gicv3.c b/drivers/nxp/gic/ls_gicv3.c
new file mode 100644
index 0000000..9c02bd6
--- /dev/null
+++ b/drivers/nxp/gic/ls_gicv3.c
@@ -0,0 +1,78 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <drivers/arm/gicv3.h>
+#include <plat_gic.h>
+#include <plat/common/platform.h>
+
+/*
+ * NXP common helper to initialize the GICv3 only driver.
+ */
+void plat_ls_gic_driver_init(uintptr_t nxp_gicd_addr,
+			     uintptr_t nxp_gicr_addr,
+			     uint8_t plat_core_count,
+			     interrupt_prop_t *ls_interrupt_props,
+			     uint8_t ls_interrupt_prop_count,
+			     uintptr_t *target_mask_array,
+			     mpidr_hash_fn mpidr_to_core_pos)
+{
+	static struct gicv3_driver_data ls_gic_data;
+
+	ls_gic_data.gicd_base = nxp_gicd_addr;
+	ls_gic_data.gicr_base = nxp_gicr_addr;
+	ls_gic_data.interrupt_props = ls_interrupt_props;
+	ls_gic_data.interrupt_props_num = ls_interrupt_prop_count;
+	ls_gic_data.rdistif_num = plat_core_count;
+	ls_gic_data.rdistif_base_addrs = target_mask_array;
+	ls_gic_data.mpidr_to_core_pos = mpidr_to_core_pos;
+
+	gicv3_driver_init(&ls_gic_data);
+}
+
+void plat_ls_gic_init(void)
+{
+	gicv3_distif_init();
+	gicv3_rdistif_init(plat_my_core_pos());
+	gicv3_cpuif_enable(plat_my_core_pos());
+}
+
+/*
+ * NXP common helper to enable the GICv3 CPU interface
+ */
+void plat_ls_gic_cpuif_enable(void)
+{
+	gicv3_cpuif_enable(plat_my_core_pos());
+}
+
+/*
+ * NXP common helper to disable the GICv3 CPU interface
+ */
+void plat_ls_gic_cpuif_disable(void)
+{
+	gicv3_cpuif_disable(plat_my_core_pos());
+}
+
+/*
+ * NXP common helper to initialize the per cpu distributor interface in GICv3
+ */
+void plat_gic_pcpu_init(void)
+{
+	gicv3_rdistif_init(plat_my_core_pos());
+	gicv3_cpuif_enable(plat_my_core_pos());
+}
+
+/*
+ * Stubs for Redistributor power management. Although GICv3 doesn't have
+ * Redistributor interface, these are provided for the sake of uniform GIC API
+ */
+void plat_ls_gic_redistif_on(void)
+{
+}
+
+void plat_ls_gic_redistif_off(void)
+{
+}
diff --git a/drivers/nxp/gpio/gpio.mk b/drivers/nxp/gpio/gpio.mk
new file mode 100644
index 0000000..74f0dc4
--- /dev/null
+++ b/drivers/nxp/gpio/gpio.mk
@@ -0,0 +1,28 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+
+ifeq (${GPIO_ADDED},)
+
+GPIO_ADDED		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/gpio
+
+GPIO_SOURCES		:= $(PLAT_DRIVERS_PATH)/gpio/nxp_gpio.c
+
+ifeq (${BL_COMM_GPIO_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${GPIO_SOURCES}
+else
+ifeq (${BL2_GPIO_NEEDED},yes)
+BL2_SOURCES		+= ${GPIO_SOURCES}
+endif
+ifeq (${BL31_GPIO_NEEDED},yes)
+BL31_SOURCES		+= ${GPIO_SOURCES}
+endif
+endif
+
+endif
+#------------------------------------------------
diff --git a/drivers/nxp/gpio/nxp_gpio.c b/drivers/nxp/gpio/nxp_gpio.c
new file mode 100644
index 0000000..28c9db9
--- /dev/null
+++ b/drivers/nxp/gpio/nxp_gpio.c
@@ -0,0 +1,144 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <nxp_gpio.h>
+
+static gpio_init_info_t *gpio_init_info;
+
+void gpio_init(gpio_init_info_t *gpio_init_data)
+{
+	gpio_init_info = gpio_init_data;
+}
+
+/* This function set GPIO pin for raising POVDD. */
+int set_gpio_bit(uint32_t *gpio_base_addr,
+		 uint32_t bit_num)
+{
+	uint32_t val = 0U;
+	uint32_t *gpdir = NULL;
+	uint32_t *gpdat = NULL;
+
+	if (gpio_init_info == NULL) {
+		ERROR("GPIO is not initialized.\n");
+		return GPIO_FAILURE;
+	}
+
+	gpdir = gpio_base_addr + GPDIR_REG_OFFSET;
+	gpdat = gpio_base_addr + (GPDAT_REG_OFFSET >> 2);
+
+	/*
+	 * Set the corresponding bit in direction register
+	 * to configure the GPIO as output.
+	 */
+	val = gpio_read32(gpdir);
+	val = val | bit_num;
+	gpio_write32(gpdir, val);
+
+	/* Set the corresponding bit in GPIO data register */
+	val = gpio_read32(gpdat);
+	val = val | bit_num;
+	gpio_write32(gpdat, val);
+
+	val = gpio_read32(gpdat);
+
+	if ((val & bit_num) == 0U) {
+		return GPIO_FAILURE;
+	}
+
+	return GPIO_SUCCESS;
+}
+
+/* This function reset GPIO pin set for raising POVDD. */
+int clr_gpio_bit(uint32_t *gpio_base_addr, uint32_t bit_num)
+{
+	uint32_t val = 0U;
+	uint32_t *gpdir = NULL;
+	uint32_t *gpdat = NULL;
+
+
+	if (gpio_init_info == NULL) {
+		ERROR("GPIO is not initialized.\n");
+		return GPIO_FAILURE;
+	}
+
+	gpdir = gpio_base_addr + GPDIR_REG_OFFSET;
+	gpdat = gpio_base_addr + GPDAT_REG_OFFSET;
+
+	/*
+	 * Reset the corresponding bit in direction and data register
+	 * to configure the GPIO as input.
+	 */
+	val = gpio_read32(gpdat);
+	val = val & ~(bit_num);
+	gpio_write32(gpdat, val);
+
+	val = gpio_read32(gpdat);
+
+	val = gpio_read32(gpdir);
+	val = val & ~(bit_num);
+	gpio_write32(gpdir, val);
+
+	val = gpio_read32(gpdat);
+
+	if ((val & bit_num) != 0U) {
+		return GPIO_FAILURE;
+	}
+
+	return GPIO_SUCCESS;
+}
+
+uint32_t *select_gpio_n_bitnum(uint32_t povdd_gpio, uint32_t *bit_num)
+{
+	uint32_t *ret_gpio;
+	uint32_t povdd_gpio_val = 0U;
+	uint32_t gpio_num = 0U;
+
+	if (gpio_init_info == NULL) {
+		ERROR("GPIO is not initialized.\n");
+	}
+	/*
+	 * Subtract 1 from fuse_hdr povdd_gpio value as
+	 * for 0x1 value, bit 0 is to be set
+	 * for 0x20 value i.e 32, bit 31 i.e. 0x1f is to be set.
+	 * 0x1f - 0x00 : GPIO_1
+	 * 0x3f - 0x20 : GPIO_2
+	 * 0x5f - 0x40 : GPIO_3
+	 * 0x7f - 0x60 : GPIO_4
+	 */
+	povdd_gpio_val = (povdd_gpio - 1U) & GPIO_SEL_MASK;
+
+	/* Right shift by 5 to divide by 32 */
+	gpio_num = povdd_gpio_val >> GPIO_ID_BASE_ADDR_SHIFT;
+	*bit_num = 1U << (GPIO_BITS_PER_BASE_REG
+			  - (povdd_gpio_val & GPIO_BIT_MASK)
+			  - 1U);
+
+	switch (gpio_num) {
+	case GPIO_0:
+		ret_gpio = (uint32_t *) gpio_init_info->gpio1_base_addr;
+		break;
+	case GPIO_1:
+		ret_gpio = (uint32_t *) gpio_init_info->gpio2_base_addr;
+		break;
+	case GPIO_2:
+		ret_gpio = (uint32_t *) gpio_init_info->gpio3_base_addr;
+		break;
+	case GPIO_3:
+		ret_gpio = (uint32_t *) gpio_init_info->gpio4_base_addr;
+		break;
+	default:
+		ret_gpio = NULL;
+	}
+
+	if (ret_gpio == NULL) {
+		INFO("GPIO_NUM = %d doesn't exist.\n", gpio_num);
+	}
+
+	return ret_gpio;
+}
diff --git a/drivers/nxp/i2c/i2c.c b/drivers/nxp/i2c/i2c.c
new file mode 100644
index 0000000..9281409
--- /dev/null
+++ b/drivers/nxp/i2c/i2c.c
@@ -0,0 +1,257 @@
+/*
+ * Copyright 2016-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include "i2c.h"
+#include <nxp_timer.h>
+
+static uintptr_t g_nxp_i2c_addr;
+
+void i2c_init(uintptr_t nxp_i2c_addr)
+{
+	struct ls_i2c *ccsr_i2c = (void *)nxp_i2c_addr;
+
+	g_nxp_i2c_addr = nxp_i2c_addr;
+	/* Presume workaround for erratum a009203 applied */
+	i2c_out(&ccsr_i2c->cr, I2C_CR_DIS);
+	i2c_out(&ccsr_i2c->fd, I2C_FD_CONSERV);
+	i2c_out(&ccsr_i2c->sr, I2C_SR_RST);
+	i2c_out(&ccsr_i2c->cr, I2C_CR_EN);
+}
+
+static int wait_for_state(struct ls_i2c *ccsr_i2c,
+			  unsigned char state, unsigned char mask)
+{
+	unsigned char sr;
+	uint64_t start_time = get_timer_val(0);
+	uint64_t timer;
+
+	do {
+		sr = i2c_in(&ccsr_i2c->sr);
+		if (sr & I2C_SR_AL) {
+			i2c_out(&ccsr_i2c->sr, sr);
+			WARN("I2C arbitration lost\n");
+			return -EIO;
+		}
+		if ((sr & mask) == state) {
+			return (int)sr;
+		}
+
+		timer = get_timer_val(start_time);
+		if (timer > I2C_TIMEOUT)
+			break;
+		mdelay(1);
+	} while (1);
+	WARN("I2C: Timeout waiting for state 0x%x, sr = 0x%x\n", state, sr);
+
+	return -ETIMEDOUT;
+}
+
+static int tx_byte(struct ls_i2c *ccsr_i2c, unsigned char c)
+{
+	int ret;
+
+	i2c_out(&ccsr_i2c->sr, I2C_SR_IF);
+	i2c_out(&ccsr_i2c->dr, c);
+	ret = wait_for_state(ccsr_i2c, I2C_SR_IF, I2C_SR_IF);
+	if (ret < 0) {
+		WARN("%s: state error\n", __func__);
+		return ret;
+	}
+	if (ret & I2C_SR_RX_NAK) {
+		WARN("%s: nodev\n", __func__);
+		return -ENODEV;
+	}
+
+	return 0;
+}
+
+static int gen_stop(struct ls_i2c *ccsr_i2c)
+{
+	unsigned char cr;
+	int ret;
+
+	cr = i2c_in(&ccsr_i2c->cr);
+	cr &= ~(I2C_CR_MA | I2C_CR_TX);
+	i2c_out(&ccsr_i2c->cr, cr);
+	ret = wait_for_state(ccsr_i2c, I2C_SR_IDLE, I2C_SR_BB);
+	if (ret < 0) {
+		WARN("I2C: Generating stop failed.\n");
+	}
+	return ret;
+}
+
+static int i2c_write_addr(struct ls_i2c *ccsr_i2c, unsigned char chip,
+			  int addr, int alen)
+{
+	int ret;
+	unsigned char cr;
+
+	if (alen != 1) {
+		WARN("I2C: Unsupported address len [%d]\n", alen);
+		return -EIO;
+	}
+
+	if (i2c_in(&ccsr_i2c->ad) == (chip << 1)) {
+		WARN("I2C: slave address same as self\n");
+		return -ENODEV;
+	}
+	i2c_out(&ccsr_i2c->sr, I2C_SR_IF);
+	ret = wait_for_state(ccsr_i2c, I2C_SR_IDLE, I2C_SR_BB);
+	if (ret < 0) {
+		return ret;
+	}
+
+	cr = i2c_in(&ccsr_i2c->cr);
+	cr |= I2C_CR_MA;
+	i2c_out(&ccsr_i2c->cr, cr);
+	ret = wait_for_state(ccsr_i2c, I2C_SR_BB, I2C_SR_BB);
+	if (ret < 0) {
+		return ret;
+	}
+
+	VERBOSE("Before writing chip %d\n", chip);
+	cr |= I2C_CR_TX | I2C_CR_TX_NAK;
+	i2c_out(&ccsr_i2c->cr, cr);
+	ret = tx_byte(ccsr_i2c, chip << 1);
+	if (ret < 0) {
+		gen_stop(ccsr_i2c);
+		return ret;
+	}
+
+	VERBOSE("Before writing addr\n");
+	while (alen--) {
+		ret = tx_byte(ccsr_i2c, (addr >> (alen << 3)) & 0xff);
+		if (ret < 0) {
+			gen_stop(ccsr_i2c);
+			return ret;
+		}
+	}
+
+	return 0;
+}
+
+static int read_data(struct ls_i2c *ccsr_i2c, unsigned char chip,
+		     unsigned char *buf, int len)
+{
+	int i;
+	int ret;
+	unsigned char cr;
+
+	cr = i2c_in(&ccsr_i2c->cr);
+	cr &= ~(I2C_CR_TX | I2C_CR_TX_NAK);
+	if (len == 1) {
+		cr |= I2C_CR_TX_NAK;
+	}
+	i2c_out(&ccsr_i2c->cr, cr);
+	i2c_out(&ccsr_i2c->sr, I2C_SR_IF);
+	i2c_in(&ccsr_i2c->dr);	/* dummy read */
+	for (i = 0; i < len; i++) {
+		ret = wait_for_state(ccsr_i2c, I2C_SR_IF, I2C_SR_IF);
+		if (ret < 0) {
+			gen_stop(ccsr_i2c);
+			return ret;
+		}
+		if (i == (len - 1)) {
+			gen_stop(ccsr_i2c);
+		} else if (i == (len - 2)) {
+			/* Updating the command to send
+			 * No ACK.
+			 */
+			cr = i2c_in(&ccsr_i2c->cr);
+			cr |= I2C_CR_TX_NAK;
+			i2c_out(&ccsr_i2c->cr, cr);
+		}
+		i2c_out(&ccsr_i2c->sr, I2C_SR_IF);
+		buf[i] = i2c_in(&ccsr_i2c->dr);
+	}
+
+	return 0;
+}
+
+static int write_data(struct ls_i2c *ccsr_i2c, unsigned char chip,
+		      const unsigned char *buf, int len)
+{
+	int i;
+	int ret;
+
+	for (i = 0; i < len; i++) {
+		ret = tx_byte(ccsr_i2c, buf[i]);
+		if (ret < 0) {
+			break;
+		}
+	}
+	ret = gen_stop(ccsr_i2c);
+
+	return ret;
+}
+
+
+int i2c_read(unsigned char chip, int addr, int alen,
+	     unsigned char *buf, int len)
+{
+	int ret;
+	unsigned char cr;
+	struct ls_i2c *ccsr_i2c = (void *)g_nxp_i2c_addr;
+
+	ret = i2c_write_addr(ccsr_i2c, chip, addr, alen);
+	if (ret < 0) {
+		gen_stop(ccsr_i2c);
+		return ret;
+	}
+
+	cr = i2c_in(&ccsr_i2c->cr);
+	cr |= I2C_CR_RSTA;
+	i2c_out(&ccsr_i2c->cr, cr);
+
+	ret = tx_byte(ccsr_i2c, (chip << 1) | 1);
+	if (ret < 0) {
+		gen_stop(ccsr_i2c);
+		return ret;
+	}
+
+	return read_data(ccsr_i2c, chip, buf, len);
+}
+
+int i2c_write(unsigned char chip, int addr, int alen,
+	      const unsigned char *buf, int len)
+{
+	int ret;
+	struct ls_i2c *ccsr_i2c = (void *)g_nxp_i2c_addr;
+
+	ret = i2c_write_addr(ccsr_i2c, chip, addr, alen);
+	if (ret < 0) {
+		return ret;
+	}
+
+	return write_data(ccsr_i2c, chip, buf, len);
+}
+
+int i2c_probe_chip(unsigned char chip)
+{
+	int ret;
+	struct ls_i2c *ccsr_i2c = (void *)g_nxp_i2c_addr;
+
+	ret = i2c_write_addr(ccsr_i2c, chip, 0, 0);
+	if (ret < 0) {
+		WARN("write addr failed\n");
+		return ret;
+	}
+
+	ret = gen_stop(ccsr_i2c);
+	if (ret < 0) {
+		WARN("I2C: Probe not complete.\n");
+	}
+
+	return ret;
+}
diff --git a/drivers/nxp/i2c/i2c.mk b/drivers/nxp/i2c/i2c.mk
new file mode 100644
index 0000000..716e14a
--- /dev/null
+++ b/drivers/nxp/i2c/i2c.mk
@@ -0,0 +1,25 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_I2C},)
+
+ADD_I2C			:= 1
+
+I2C_SOURCES		+= $(PLAT_DRIVERS_PATH)/i2c/i2c.c
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/i2c
+
+ifeq (${BL_COMM_I2C_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${I2C_SOURCES}
+else
+ifeq (${BL2_I2C_NEEDED},yes)
+BL2_SOURCES		+= ${I2C_SOURCES}
+endif
+ifeq (${BL31_I2C_NEEDED},yes)
+BL31_SOURCES		+= ${I2C_SOURCES}
+endif
+endif
+endif
diff --git a/drivers/nxp/interconnect/interconnect.mk b/drivers/nxp/interconnect/interconnect.mk
new file mode 100644
index 0000000..aa51be4
--- /dev/null
+++ b/drivers/nxp/interconnect/interconnect.mk
@@ -0,0 +1,44 @@
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the Interconnect files
+#
+# -----------------------------------------------------------------------------
+
+ifeq (${ADD_INTERCONNECT},)
+
+ADD_INTERCONNECT	:= 1
+PLAT_INCLUDES		+= -I${PLAT_DRIVERS_INCLUDE_PATH}/interconnect
+
+ifeq (, $(filter $(INTERCONNECT), CCI400 CCN502 CCN504 CCN508))
+    $(error -> Interconnect type not set!)
+else
+$(eval $(call add_define_val,INTERCONNECT,${INTERCONNECT}))
+ifeq ($(INTERCONNECT), $(filter $(INTERCONNECT), CCN502 CCN504 CCN508))
+INTERCONNECT_SOURCES	:= 	drivers/arm/ccn/ccn.c 		\
+				${PLAT_DRIVERS_PATH}/interconnect/ls_ccn.c
+else
+ifeq ($(INTERCONNECT), CCI400)
+INTERCONNECT_SOURCES	:= 	drivers/arm/cci/cci.c 		\
+				${PLAT_DRIVERS_PATH}/interconnect/ls_cci.c
+endif
+endif
+endif
+
+ifeq (${BL_COMM_INTERCONNECT_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${INTERCONNECT_SOURCES}
+else
+ifeq (${BL2_INTERCONNECT_NEEDED},yes)
+BL2_SOURCES		+= ${INTERCONNECT_SOURCES}
+endif
+ifeq (${BL31_INTERCONNECT_NEEDED},yes)
+BL31_SOURCES		+= ${INTERCONNECT_SOURCES}
+endif
+endif
+endif
+
+# -----------------------------------------------------------------------------
diff --git a/drivers/nxp/interconnect/ls_cci.c b/drivers/nxp/interconnect/ls_cci.c
new file mode 100644
index 0000000..72a898a
--- /dev/null
+++ b/drivers/nxp/interconnect/ls_cci.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <arch.h>
+#include <cci.h>
+
+#include <plat_arm.h>
+
+/******************************************************************************
+ * The following functions are defined as weak to allow a platform to override
+ * the way ARM CCI driver is initialised and used.
+ *****************************************************************************/
+#pragma weak plat_arm_interconnect_enter_coherency
+#pragma weak plat_arm_interconnect_exit_coherency
+
+/******************************************************************************
+ * Helper function to place current master into coherency
+ *****************************************************************************/
+void plat_ls_interconnect_enter_coherency(unsigned int num_clusters)
+{
+	cci_enable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr_el1()));
+
+	for (uint32_t index = 1U; index < num_clusters; index++) {
+		cci_enable_snoop_dvm_reqs(index);
+	}
+}
+
+/******************************************************************************
+ * Helper function to remove current master from coherency
+ *****************************************************************************/
+void plat_ls_interconnect_exit_coherency(void)
+{
+	cci_disable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr_el1()));
+}
diff --git a/drivers/nxp/interconnect/ls_ccn.c b/drivers/nxp/interconnect/ls_ccn.c
new file mode 100644
index 0000000..8f90325
--- /dev/null
+++ b/drivers/nxp/interconnect/ls_ccn.c
@@ -0,0 +1,31 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <arch.h>
+#include <ccn.h>
+
+#include <plat_arm.h>
+
+/******************************************************************************
+ * Helper function to place current master into coherency
+ *****************************************************************************/
+void plat_ls_interconnect_enter_coherency(unsigned int num_clusters)
+{
+	ccn_enter_snoop_dvm_domain(1ULL << MPIDR_AFFLVL1_VAL(read_mpidr_el1()));
+
+	for (uint32_t index = 1U; index < num_clusters; index++) {
+		ccn_enter_snoop_dvm_domain(1ULL << index);
+	}
+}
+
+/******************************************************************************
+ * Helper function to remove current master from coherency
+ *****************************************************************************/
+void plat_ls_interconnect_exit_coherency(void)
+{
+	ccn_exit_snoop_dvm_domain(1ULL << MPIDR_AFFLVL1_VAL(read_mpidr_el1()));
+}
diff --git a/drivers/nxp/pmu/pmu.c b/drivers/nxp/pmu/pmu.c
new file mode 100644
index 0000000..2a907c8
--- /dev/null
+++ b/drivers/nxp/pmu/pmu.c
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <dcfg.h>
+#include <lib/mmio.h>
+#include <pmu.h>
+
+void enable_timer_base_to_cluster(uintptr_t nxp_pmu_addr)
+{
+	uint32_t *cltbenr = NULL;
+	uint32_t cltbenr_val = 0U;
+
+	cltbenr = (uint32_t *)(nxp_pmu_addr
+				+ CLUST_TIMER_BASE_ENBL_OFFSET);
+
+	cltbenr_val = mmio_read_32((uintptr_t)cltbenr);
+
+	cltbenr_val = cltbenr_val
+			| (1 << MPIDR_AFFLVL1_VAL(read_mpidr_el1()));
+
+	mmio_write_32((uintptr_t)cltbenr, cltbenr_val);
+
+	VERBOSE("Enable cluster time base\n");
+}
+
+/*
+ * Enable core timebase.  In certain Layerscape SoCs, the clock for each core's
+ * has an enable bit in the PMU Physical Core Time Base Enable
+ * Register (PCTBENR), which allows the watchdog to operate.
+ */
+
+void enable_core_tb(uintptr_t nxp_pmu_addr)
+{
+	uint32_t *pctbenr = (uint32_t *) (nxp_pmu_addr +
+					  CORE_TIMEBASE_ENBL_OFFSET);
+
+	mmio_write_32((uintptr_t)pctbenr, 0xff);
+}
diff --git a/drivers/nxp/pmu/pmu.mk b/drivers/nxp/pmu/pmu.mk
new file mode 100644
index 0000000..8d2ef07
--- /dev/null
+++ b/drivers/nxp/pmu/pmu.mk
@@ -0,0 +1,26 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+ifeq (${PMU_ADDED},)
+
+PMU_ADDED		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/pmu
+
+PMU_SOURCES		+= $(PLAT_DRIVERS_PATH)/pmu/pmu.c
+
+ifeq (${BL_COMM_PMU_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${PMU_SOURCES}
+else
+ifeq (${BL2_PMU_NEEDED},yes)
+BL2_SOURCES		+= ${PMU_SOURCES}
+endif
+ifeq (${BL31_PMU_NEEDED},yes)
+BL31_SOURCES		+= ${PMU_SOURCES}
+endif
+endif
+endif
+#------------------------------------------------
diff --git a/drivers/nxp/qspi/qspi.c b/drivers/nxp/qspi/qspi.c
new file mode 100644
index 0000000..97b2a19
--- /dev/null
+++ b/drivers/nxp/qspi/qspi.c
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <qspi.h>
+
+int qspi_io_setup(uintptr_t nxp_qspi_flash_addr,
+		  size_t nxp_qspi_flash_size,
+		  uintptr_t fip_offset)
+{
+	uint32_t qspi_mcr_val = qspi_in32(CHS_QSPI_MCR);
+
+	/* Enable and change endianness of QSPI IP */
+	qspi_out32(CHS_QSPI_MCR, (qspi_mcr_val | CHS_QSPI_64LE));
+
+	/* Adding QSPI Memory Map in XLAT Table */
+	mmap_add_region(nxp_qspi_flash_addr, nxp_qspi_flash_addr,
+			nxp_qspi_flash_size, MT_MEMORY | MT_RW);
+
+	return 0;
+}
diff --git a/drivers/nxp/qspi/qspi.mk b/drivers/nxp/qspi/qspi.mk
new file mode 100644
index 0000000..b83dee2
--- /dev/null
+++ b/drivers/nxp/qspi/qspi.mk
@@ -0,0 +1,26 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${QSPI_ADDED},)
+
+QSPI_ADDED		:= 1
+
+QSPI_SOURCES		:= $(PLAT_DRIVERS_PATH)/qspi/qspi.c
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_PATH)/qspi
+
+ifeq (${BL_COMM_QSPI_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${QSPI_SOURCES}
+else
+ifeq (${BL2_QSPI_NEEDED},yes)
+BL2_SOURCES		+= ${QSPI_SOURCES}
+endif
+ifeq (${BL31_QSPI_NEEDED},yes)
+BL31_SOURCES		+= ${QSPI_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/nxp/sd/sd_mmc.c b/drivers/nxp/sd/sd_mmc.c
new file mode 100644
index 0000000..f7f48e7
--- /dev/null
+++ b/drivers/nxp/sd/sd_mmc.c
@@ -0,0 +1,1496 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ *
+ */
+
+#include <endian.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/io/io_block.h>
+#include "nxp_timer.h"
+#include "sd_mmc.h"
+#include <utils.h>
+#include <utils_def.h>
+
+
+/* Private structure for MMC driver data */
+static struct mmc mmc_drv_data;
+
+#ifndef NXP_POLICY_OTA
+/*
+ * For NXP_POLICY_OTA, SD needs to do R/W on OCRAM. OCRAM is secure memory at
+ * default. SD can only do non-secure DMA. Configuring SD to work in PIO mode
+ * instead of DMA mode will make SD R/W on OCRAM available.
+ */
+/* To debug without dma comment this MACRO */
+#define NXP_SD_DMA_CAPABILITY
+#endif
+#define SD_TIMEOUT        1000 /* ms */
+#define SD_TIMEOUT_HIGH   20000 /* ms */
+#define SD_BLOCK_TIMEOUT  8 /* ms */
+
+#define ERROR_ESDHC_CARD_DETECT_FAIL	-1
+#define ERROR_ESDHC_UNUSABLE_CARD	-2
+#define ERROR_ESDHC_COMMUNICATION_ERROR	-3
+#define ERROR_ESDHC_BLOCK_LENGTH	-4
+#define ERROR_ESDHC_DMA_ERROR		-5
+#define ERROR_ESDHC_BUSY		-6
+
+/***************************************************************
+ * Function    :    set_speed
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  clock - Clock Value to be set
+ * Return      :    void
+ * Description :    Calculates the value of SDCLKFS and DVS to be set
+ *                  for getting the required clock assuming the base_clk
+ *                  as a fixed value (MAX_PLATFORM_CLOCK)
+ *****************************************************************/
+static void set_speed(struct mmc *mmc, uint32_t clock)
+{
+	/* sdhc_clk = (base clock) / [(SDCLKFS × 2) × (DVS +1)] */
+
+	uint32_t dvs = 1U;
+	uint32_t sdclkfs = 2U;
+	/* TBD - Change this to actual platform clock by reading via RCW */
+	uint32_t base_clk = MAX_PLATFORM_CLOCK;
+
+	if (base_clk / 16 > clock) {
+		for (sdclkfs = 2U; sdclkfs < 256U; sdclkfs *= 2U) {
+			if ((base_clk / sdclkfs) <= (clock * 16)) {
+				break;
+			}
+		}
+	}
+
+	for (dvs = 1U; dvs <= 16U; dvs++) {
+		if ((base_clk / (dvs * sdclkfs)) <= clock) {
+			break;
+		}
+	}
+
+	sdclkfs >>= 1U;
+	dvs -= 1U;
+
+	esdhc_out32(&mmc->esdhc_regs->sysctl,
+			(ESDHC_SYSCTL_DTOCV(TIMEOUT_COUNTER_SDCLK_2_27) |
+			 ESDHC_SYSCTL_SDCLKFS(sdclkfs) | ESDHC_SYSCTL_DVS(dvs) |
+			 ESDHC_SYSCTL_SDCLKEN));
+}
+
+/***************************************************************************
+ * Function    :    esdhc_init
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  card_detect - flag to indicate if card insert needs
+ *                  to be detected or not. For SDHC2 controller, Card detect
+ *                  is not present, so this field will be false
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Set Initial Clock Speed
+ *                  2. Card Detect if not eMMC
+ *                  3. Enable Controller Clock
+ *                  4. Send 80 ticks for card to power up
+ *                  5. Set LE mode and Bus Width as 1 bit.
+ ***************************************************************************/
+static int esdhc_init(struct mmc *mmc, bool card_detect)
+{
+	uint32_t val;
+	uint64_t start_time;
+
+	/* Reset the entire host controller */
+	val = esdhc_in32(&mmc->esdhc_regs->sysctl) | ESDHC_SYSCTL_RSTA;
+	esdhc_out32(&mmc->esdhc_regs->sysctl, val);
+
+	/* Wait until the controller is available */
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->sysctl) & ESDHC_SYSCTL_RSTA;
+		if (val == 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->sysctl) &
+		(ESDHC_SYSCTL_RSTA);
+	if (val != 0U) {
+		ERROR("SD Reset failed\n");
+		return ERROR_ESDHC_BUSY;
+	}
+
+	/* Set initial clock speed */
+	set_speed(mmc, CARD_IDENTIFICATION_FREQ);
+
+	if (card_detect) {
+		/* Check CINS in prsstat register */
+		val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+			ESDHC_PRSSTAT_CINS;
+		if (val == 0) {
+			ERROR("CINS not set in prsstat\n");
+			return ERROR_ESDHC_CARD_DETECT_FAIL;
+		}
+	}
+
+	/* Enable controller clock */
+	val = esdhc_in32(&mmc->esdhc_regs->sysctl) | ESDHC_SYSCTL_SDCLKEN;
+	esdhc_out32(&mmc->esdhc_regs->sysctl, val);
+
+	/* Send 80 clock ticks for the card to power up */
+	val = esdhc_in32(&mmc->esdhc_regs->sysctl) | ESDHC_SYSCTL_INITA;
+	esdhc_out32(&mmc->esdhc_regs->sysctl, val);
+
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT) {
+		val = esdhc_in32(&mmc->esdhc_regs->sysctl) & ESDHC_SYSCTL_INITA;
+		if (val != 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->sysctl) & ESDHC_SYSCTL_INITA;
+	if (val == 0U) {
+		ERROR("Failed to power up the card\n");
+		return ERROR_ESDHC_CARD_DETECT_FAIL;
+	}
+
+	INFO("Card detected successfully\n");
+
+	val = esdhc_in32(&mmc->esdhc_regs->proctl);
+	val = val | (ESDHC_PROCTL_EMODE_LE | ESDHC_PROCTL_DTW_1BIT);
+
+	/* Set little endian mode, set bus width as 1-bit */
+	esdhc_out32(&mmc->esdhc_regs->proctl, val);
+
+	/* Enable cache snooping for DMA transactions */
+	val = esdhc_in32(&mmc->esdhc_regs->ctl) | ESDHC_DCR_SNOOP;
+	esdhc_out32(&mmc->esdhc_regs->ctl, val);
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_send_cmd
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  cmd - Command Number
+ *                  args - Command Args
+ * Return      :    SUCCESS is 0, or Error Code ( < 0)
+ * Description :    Updates the eSDHC registers cmdargs and xfertype
+ ***************************************************************************/
+static int esdhc_send_cmd(struct mmc *mmc, uint32_t cmd, uint32_t args)
+{
+	uint32_t val;
+	uint64_t start_time;
+	uint32_t xfertyp = 0;
+
+	esdhc_out32(&mmc->esdhc_regs->irqstat, ESDHC_IRQSTAT_CLEAR_ALL);
+
+	/* Wait for the command line & data line to be free */
+	/* (poll the CIHB,CDIHB bit of the present state register) */
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+			(ESDHC_PRSSTAT_CIHB | ESDHC_PRSSTAT_CDIHB);
+		if (val == 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+		(ESDHC_PRSSTAT_CIHB | ESDHC_PRSSTAT_CDIHB);
+	if (val != 0U) {
+		ERROR("SD send cmd: Command Line or Data Line Busy cmd = %x\n",
+				cmd);
+		return ERROR_ESDHC_BUSY;
+	}
+
+	if (cmd == CMD2 || cmd == CMD9) {
+		xfertyp |= ESDHC_XFERTYP_RSPTYP_136;
+	} else  if (cmd == CMD7 || (cmd == CMD6 && mmc->card.type == MMC_CARD)) {
+		xfertyp |= ESDHC_XFERTYP_RSPTYP_48_BUSY;
+	} else if (cmd != CMD0) {
+		xfertyp |= ESDHC_XFERTYP_RSPTYP_48;
+	}
+
+	if (cmd == CMD2 || cmd == CMD9) {
+		xfertyp |= ESDHC_XFERTYP_CCCEN; /* Command index check enable */
+	} else if ((cmd != CMD0) && (cmd != ACMD41) && (cmd != CMD1)) {
+		xfertyp = xfertyp | ESDHC_XFERTYP_CCCEN | ESDHC_XFERTYP_CICEN;
+	}
+
+	if ((cmd == CMD8 || cmd == CMD14 || cmd == CMD19) &&
+			mmc->card.type == MMC_CARD) {
+		xfertyp |=  ESDHC_XFERTYP_DPSEL;
+		if (cmd != CMD19) {
+			xfertyp |= ESDHC_XFERTYP_DTDSEL;
+		}
+	}
+
+	if (cmd == CMD6 || cmd == CMD17 || cmd == CMD18 || cmd == CMD24 ||
+	    cmd == ACMD51) {
+		if (!(mmc->card.type == MMC_CARD && cmd == CMD6)) {
+			if (cmd == CMD24) {
+				xfertyp |= ESDHC_XFERTYP_DPSEL;
+			} else {
+				xfertyp |= (ESDHC_XFERTYP_DPSEL |
+					    ESDHC_XFERTYP_DTDSEL);
+			}
+		}
+
+		if (cmd == CMD18) {
+			xfertyp |= ESDHC_XFERTYP_BCEN;
+			if (mmc->dma_support != 0) {
+				/* Set BCEN of XFERTYP */
+				xfertyp |= ESDHC_XFERTYP_DMAEN;
+			}
+		}
+
+		if ((cmd == CMD17 || cmd == CMD24) && (mmc->dma_support != 0)) {
+			xfertyp |= ESDHC_XFERTYP_DMAEN;
+		}
+	}
+
+	xfertyp |= ((cmd & 0x3F) << 24);
+	esdhc_out32(&mmc->esdhc_regs->cmdarg, args);
+	esdhc_out32(&mmc->esdhc_regs->xfertyp, xfertyp);
+
+#ifdef NXP_SD_DEBUG
+	INFO("cmd = %d\n", cmd);
+	INFO("args = %x\n", args);
+	INFO("xfertyp: = %x\n", xfertyp);
+#endif
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_wait_response
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  response - Value updated
+ * Return      :    SUCCESS - Response Received
+ *                  COMMUNICATION_ERROR - Command not Complete
+ *                  COMMAND_ERROR - CIE, CCE or CEBE  error
+ *                  RESP_TIMEOUT - CTOE error
+ * Description :    Checks for successful command completion.
+ *                  Clears the CC bit at the end.
+ ***************************************************************************/
+static int esdhc_wait_response(struct mmc *mmc, uint32_t *response)
+{
+	uint32_t val;
+	uint64_t start_time;
+	uint32_t status = 0U;
+
+	/* Wait for the command to complete */
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_CC;
+		if (val != 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_CC;
+	if (val == 0U) {
+		ERROR("%s:IRQSTAT Cmd not complete(CC not set)\n", __func__);
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+
+	/* Check whether the interrupt is a CRC, CTOE or CIE error */
+	if ((status & (ESDHC_IRQSTAT_CIE | ESDHC_IRQSTAT_CEBE |
+				ESDHC_IRQSTAT_CCE)) != 0) {
+		ERROR("%s: IRQSTAT CRC, CEBE or CIE error = %x\n",
+							__func__, status);
+		return COMMAND_ERROR;
+	}
+
+	if ((status & ESDHC_IRQSTAT_CTOE) != 0) {
+		INFO("%s: IRQSTAT CTOE set = %x\n", __func__, status);
+		return RESP_TIMEOUT;
+	}
+
+	if ((status & ESDHC_IRQSTAT_DMAE) != 0) {
+		ERROR("%s: IRQSTAT DMAE set = %x\n", __func__, status);
+		return ERROR_ESDHC_DMA_ERROR;
+	}
+
+	if (response != NULL) {
+		/* Get response values from eSDHC CMDRSPx registers. */
+		response[0] = esdhc_in32(&mmc->esdhc_regs->cmdrsp[0]);
+		response[1] = esdhc_in32(&mmc->esdhc_regs->cmdrsp[1]);
+		response[2] = esdhc_in32(&mmc->esdhc_regs->cmdrsp[2]);
+		response[3] = esdhc_in32(&mmc->esdhc_regs->cmdrsp[3]);
+#ifdef NXP_SD_DEBUG
+		INFO("Resp R1 R2 R3 R4\n");
+		INFO("Resp R1 = %x\n", response[0]);
+		INFO("R2 = %x\n", response[1]);
+		INFO("R3 = %x\n", response[2]);
+		INFO("R4 = %x\n", response[3]);
+		INFO("\n");
+#endif
+	}
+
+	/* Clear the CC bit - w1c */
+	val = esdhc_in32(&mmc->esdhc_regs->irqstat) | ESDHC_IRQSTAT_CC;
+	esdhc_out32(&mmc->esdhc_regs->irqstat, val);
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    mmc_switch_to_high_frquency
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    mmc card bellow ver 4.0 does not support high speed
+ *                  freq = 20 MHz
+ *                  Send CMD6 (CMD_SWITCH_FUNC) With args 0x03B90100
+ *                  Send CMD13 (CMD_SEND_STATUS)
+ *                  if SWITCH Error, freq = 26 MHz
+ *                  if no error, freq = 52 MHz
+ ***************************************************************************/
+static int mmc_switch_to_high_frquency(struct mmc *mmc)
+{
+	int error;
+	uint32_t response[4];
+	uint64_t start_time;
+
+	mmc->card.bus_freq = MMC_SS_20MHZ;
+	/* mmc card bellow ver 4.0 does not support high speed */
+	if (mmc->card.version < MMC_CARD_VERSION_4_X) {
+		return 0;
+	}
+
+	/* send switch cmd to change the card to High speed */
+	error = esdhc_send_cmd(mmc, CMD_SWITCH_FUNC, SET_EXT_CSD_HS_TIMING);
+	if (error != 0) {
+		return error;
+	}
+	error = esdhc_wait_response(mmc, response);
+	if (error != 0) {
+		return error;
+	}
+
+	start_time = get_timer_val(0);
+	do {
+		/* check the status for which error */
+		error = esdhc_send_cmd(mmc,
+				CMD_SEND_STATUS, mmc->card.rca << 16);
+		if (error != 0) {
+			return error;
+		}
+
+		error = esdhc_wait_response(mmc, response);
+		if (error != 0) {
+			return error;
+		}
+	} while (((response[0] & SWITCH_ERROR) != 0) &&
+			(get_timer_val(start_time) < SD_TIMEOUT));
+
+	/* Check for the present state of card */
+	if ((response[0] & SWITCH_ERROR) != 0) {
+		mmc->card.bus_freq = MMC_HS_26MHZ;
+	} else {
+		mmc->card.bus_freq = MMC_HS_52MHZ;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_set_data_attributes
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  blkcnt
+ *                  blklen
+ * Return      :    SUCCESS or Error Code
+ * Description :    Set block attributes and watermark level register
+ ***************************************************************************/
+static int esdhc_set_data_attributes(struct mmc *mmc, uint32_t *dest_ptr,
+		uint32_t blkcnt, uint32_t blklen)
+{
+	uint32_t val;
+	uint64_t start_time;
+	uint32_t wml;
+	uint32_t wl;
+	uint32_t dst = (uint32_t)((uint64_t)(dest_ptr));
+
+	/* set blkattr when no transactions are executing */
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->prsstat) & ESDHC_PRSSTAT_DLA;
+		if (val == 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->prsstat) & ESDHC_PRSSTAT_DLA;
+	if (val != 0U) {
+		ERROR("%s: Data line active.Can't set attribute\n", __func__);
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	wml = esdhc_in32(&mmc->esdhc_regs->wml);
+	wml &= ~(ESDHC_WML_WR_BRST_MASK | ESDHC_WML_RD_BRST_MASK |
+			ESDHC_WML_RD_WML_MASK | ESDHC_WML_WR_WML_MASK);
+
+	if ((mmc->dma_support != 0) && (dest_ptr != NULL)) {
+		/* Set burst length to 128 bytes */
+		esdhc_out32(&mmc->esdhc_regs->wml,
+				wml | ESDHC_WML_WR_BRST(BURST_128_BYTES));
+		esdhc_out32(&mmc->esdhc_regs->wml,
+				wml | ESDHC_WML_RD_BRST(BURST_128_BYTES));
+
+		/* Set DMA System Destination Address */
+		esdhc_out32(&mmc->esdhc_regs->dsaddr, dst);
+	} else {
+		wl = (blklen >= BLOCK_LEN_512) ?
+			WML_512_BYTES : ((blklen + 3) / 4);
+		/* Set 'Read Water Mark Level' register */
+		esdhc_out32(&mmc->esdhc_regs->wml, wml | ESDHC_WML_RD_WML(wl));
+	}
+
+	/* Configure block Attributes register */
+	esdhc_out32(&mmc->esdhc_regs->blkattr,
+		ESDHC_BLKATTR_BLKCNT(blkcnt) | ESDHC_BLKATTR_BLKSZE(blklen));
+
+	mmc->block_len = blklen;
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_read_data_nodma
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  dest_ptr - Bufffer where read data is to be copied
+ *                  len - Length of Data to be read
+ * Return      :    SUCCESS or Error Code
+ * Description :    Read data from the sdhc buffer without using DMA
+ *                  and using polling mode
+ ***************************************************************************/
+static int esdhc_read_data_nodma(struct mmc *mmc, void *dest_ptr, uint32_t len)
+{
+	uint32_t i = 0U;
+	uint32_t status;
+	uint32_t num_blocks;
+	uint32_t *dst = (uint32_t *)dest_ptr;
+	uint32_t val;
+	uint64_t start_time;
+
+	num_blocks = len / mmc->block_len;
+
+	while ((num_blocks--) != 0U) {
+
+		start_time = get_timer_val(0);
+		while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+			val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+				ESDHC_PRSSTAT_BREN;
+			if (val != 0U) {
+				break;
+			}
+		}
+
+		val = esdhc_in32(&mmc->esdhc_regs->prsstat)
+			& ESDHC_PRSSTAT_BREN;
+		if (val == 0U) {
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+
+		for (i = 0U, status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+				i < mmc->block_len / 4;    i++, dst++) {
+			/* get data from data port */
+			val = mmio_read_32(
+					(uintptr_t)&mmc->esdhc_regs->datport);
+			esdhc_out32(dst, val);
+			/* Increment destination pointer */
+			status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+		}
+		/* Check whether the interrupt is an DTOE/DCE/DEBE */
+		if ((status & (ESDHC_IRQSTAT_DTOE | ESDHC_IRQSTAT_DCE |
+					ESDHC_IRQSTAT_DEBE)) != 0) {
+			ERROR("SD read error - DTOE, DCE, DEBE bit set = %x\n",
+									status);
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+	}
+
+	/* Wait for TC */
+
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_TC;
+		if (val != 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_TC;
+	if (val == 0U) {
+		ERROR("SD read timeout: Transfer bit not set in IRQSTAT\n");
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_write_data_nodma
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  src_ptr - Buffer where data is copied from
+ *                  len - Length of Data to be written
+ * Return      :    SUCCESS or Error Code
+ * Description :    Write data to the sdhc buffer without using DMA
+ *                  and using polling mode
+ ***************************************************************************/
+static int esdhc_write_data_nodma(struct mmc *mmc, void *src_ptr, uint32_t len)
+{
+	uint32_t i = 0U;
+	uint32_t status;
+	uint32_t num_blocks;
+	uint32_t *src = (uint32_t *)src_ptr;
+	uint32_t val;
+	uint64_t start_time;
+
+	num_blocks = len / mmc->block_len;
+
+	while ((num_blocks--) != 0U) {
+		start_time = get_timer_val(0);
+		while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+			val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+					 ESDHC_PRSSTAT_BWEN;
+			if (val != 0U) {
+				break;
+			}
+		}
+
+		val = esdhc_in32(&mmc->esdhc_regs->prsstat) &
+				 ESDHC_PRSSTAT_BWEN;
+		if (val == 0U) {
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+
+		for (i = 0U, status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+		     i < mmc->block_len / 4; i++, src++) {
+			val = esdhc_in32(src);
+			/* put data to data port */
+			mmio_write_32((uintptr_t)&mmc->esdhc_regs->datport,
+				      val);
+			/* Increment source pointer */
+			status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+		}
+		/* Check whether the interrupt is an DTOE/DCE/DEBE */
+		if ((status & (ESDHC_IRQSTAT_DTOE | ESDHC_IRQSTAT_DCE |
+					ESDHC_IRQSTAT_DEBE)) != 0) {
+			ERROR("SD write error - DTOE, DCE, DEBE bit set = %x\n",
+			      status);
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+	}
+
+	/* Wait for TC */
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_TC;
+		if (val != 0U) {
+			break;
+		}
+	}
+
+	val = esdhc_in32(&mmc->esdhc_regs->irqstat) & ESDHC_IRQSTAT_TC;
+	if (val == 0U) {
+		ERROR("SD write timeout: Transfer bit not set in IRQSTAT\n");
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_read_data_dma
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  len - Length of Data to be read
+ * Return      :    SUCCESS or Error Code
+ * Description :    Read data from the sd card using DMA.
+ ***************************************************************************/
+static int esdhc_read_data_dma(struct mmc *mmc, uint32_t len)
+{
+	uint32_t status;
+	uint32_t tblk;
+	uint64_t start_time;
+
+	tblk = SD_BLOCK_TIMEOUT * (len / mmc->block_len);
+
+	start_time = get_timer_val(0);
+
+	/* poll till TC is set */
+	do {
+		status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+
+		if ((status & (ESDHC_IRQSTAT_DEBE | ESDHC_IRQSTAT_DCE
+					| ESDHC_IRQSTAT_DTOE)) != 0) {
+			ERROR("SD read error - DTOE, DCE, DEBE bit set = %x\n",
+								 status);
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+
+		if ((status & ESDHC_IRQSTAT_DMAE) != 0) {
+			ERROR("SD read error - DMA error = %x\n", status);
+			return ERROR_ESDHC_DMA_ERROR;
+		}
+
+	} while (((status & ESDHC_IRQSTAT_TC) == 0) &&
+		((esdhc_in32(&mmc->esdhc_regs->prsstat) & ESDHC_PRSSTAT_DLA) != 0) &&
+		(get_timer_val(start_time) < SD_TIMEOUT_HIGH + tblk));
+
+	if (get_timer_val(start_time) > SD_TIMEOUT_HIGH + tblk) {
+		ERROR("SD read DMA timeout\n");
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_write_data_dma
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  len - Length of Data to be written
+ * Return      :    SUCCESS or Error Code
+ * Description :    Write data to the sd card using DMA.
+ ***************************************************************************/
+static int esdhc_write_data_dma(struct mmc *mmc, uint32_t len)
+{
+	uint32_t status;
+	uint32_t tblk;
+	uint64_t start_time;
+
+	tblk = SD_BLOCK_TIMEOUT * (len / mmc->block_len);
+
+	start_time = get_timer_val(0);
+
+	/* poll till TC is set */
+	do {
+		status = esdhc_in32(&mmc->esdhc_regs->irqstat);
+
+		if ((status & (ESDHC_IRQSTAT_DEBE | ESDHC_IRQSTAT_DCE
+					| ESDHC_IRQSTAT_DTOE)) != 0) {
+			ERROR("SD write error - DTOE, DCE, DEBE bit set = %x\n",
+			      status);
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+
+		if ((status & ESDHC_IRQSTAT_DMAE) != 0) {
+			ERROR("SD write error - DMA error = %x\n", status);
+			return ERROR_ESDHC_DMA_ERROR;
+		}
+	} while (((status & ESDHC_IRQSTAT_TC) == 0) &&
+		((esdhc_in32(&mmc->esdhc_regs->prsstat) & ESDHC_PRSSTAT_DLA) != 0) &&
+		(get_timer_val(start_time) < SD_TIMEOUT_HIGH + tblk));
+
+	if (get_timer_val(start_time) > SD_TIMEOUT_HIGH + tblk) {
+		ERROR("SD write DMA timeout\n");
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_read_data
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  dest_ptr - Bufffer where read data is to be copied
+ *                  len - Length of Data to be read
+ * Return      :    SUCCESS or Error Code
+ * Description :    Calls esdhc_read_data_nodma and clear interrupt status
+ ***************************************************************************/
+int esdhc_read_data(struct mmc *mmc, void *dest_ptr, uint32_t len)
+{
+	int ret;
+
+	if (mmc->dma_support && len > 64) {
+		ret = esdhc_read_data_dma(mmc, len);
+	} else {
+		ret = esdhc_read_data_nodma(mmc, dest_ptr, len);
+	}
+
+	/* clear interrupt status */
+	esdhc_out32(&mmc->esdhc_regs->irqstat, ESDHC_IRQSTAT_CLEAR_ALL);
+
+	return ret;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_write_data
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  src_ptr - Buffer where data is copied from
+ *                  len - Length of Data to be written
+ * Return      :    SUCCESS or Error Code
+ * Description :    Calls esdhc_write_data_nodma and clear interrupt status
+ ***************************************************************************/
+int esdhc_write_data(struct mmc *mmc, void *src_ptr, uint32_t len)
+{
+	int ret;
+
+	if (mmc->dma_support && len > 64) {
+		ret = esdhc_write_data_dma(mmc, len);
+	} else {
+		ret = esdhc_write_data_nodma(mmc, src_ptr, len);
+	}
+
+	/* clear interrupt status */
+	esdhc_out32(&mmc->esdhc_regs->irqstat, ESDHC_IRQSTAT_CLEAR_ALL);
+
+	return ret;
+}
+
+/***************************************************************************
+ * Function    :    sd_switch_to_high_freq
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Send ACMD51 (CMD_SEND_SCR)
+ *                  2. Read the SCR to check if card supports higher freq
+ *                  3. check version from SCR
+ *                  4. If SD 1.0, return (no Switch) freq = 25 MHz.
+ *                  5. Send CMD6 (CMD_SWITCH_FUNC) with args 0x00FFFFF1 to
+ *                     check the status of switch func
+ *                  6. Send CMD6 (CMD_SWITCH_FUNC) With args 0x80FFFFF1 to
+ *                     switch to high frequency = 50 Mhz
+ ***************************************************************************/
+static int sd_switch_to_high_freq(struct mmc *mmc)
+{
+	int err;
+	uint8_t scr[8];
+	uint8_t status[64];
+	uint32_t response[4];
+	uint32_t version;
+	uint32_t count;
+	uint32_t sd_versions[] = {SD_CARD_VERSION_1_0, SD_CARD_VERSION_1_10,
+		SD_CARD_VERSION_2_0};
+
+	mmc->card.bus_freq = SD_SS_25MHZ;
+	/* Send Application command */
+	err = esdhc_send_cmd(mmc, CMD_APP_CMD, mmc->card.rca << 16);
+	if (err != 0) {
+		return err;
+	}
+
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	esdhc_set_data_attributes(mmc, NULL, 1, 8);
+	/* Read the SCR to find out if this card supports higher speeds */
+	err = esdhc_send_cmd(mmc, CMD_SEND_SCR,  mmc->card.rca << 16);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	/* read 8 bytes of scr data */
+	err = esdhc_read_data(mmc, scr, 8U);
+	if (err != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	/* check version from SCR */
+	version = scr[0] & U(0xF);
+	if (version <= 2U) {
+		mmc->card.version = sd_versions[version];
+	} else {
+		mmc->card.version = SD_CARD_VERSION_2_0;
+	}
+
+	/* does not support switch func */
+	if (mmc->card.version == SD_CARD_VERSION_1_0) {
+		return 0;
+	}
+
+	/* read 64 bytes of status */
+	esdhc_set_data_attributes(mmc, NULL, 1U, 64U);
+
+	/* check the status of switch func */
+	for (count = 0U; count < 4U; count++) {
+		err = esdhc_send_cmd(mmc, CMD_SWITCH_FUNC,
+				SD_SWITCH_FUNC_CHECK_MODE);
+		if (err != 0) {
+			return err;
+		}
+		err = esdhc_wait_response(mmc, response);
+		if (err != 0) {
+			return err;
+		}
+		/* read 64 bytes of scr data */
+		err = esdhc_read_data(mmc, status, 64U);
+		if (err != 0) {
+			return ERROR_ESDHC_COMMUNICATION_ERROR;
+		}
+
+		if ((status[29] & SD_SWITCH_FUNC_HIGH_SPEED) == 0) {
+			break;
+		}
+	}
+
+	if ((status[13] & SD_SWITCH_FUNC_HIGH_SPEED) == 0) {
+		return 0;
+	}
+
+	/* SWITCH */
+	esdhc_set_data_attributes(mmc, NULL, 1, 64);
+	err = esdhc_send_cmd(mmc, CMD_SWITCH_FUNC, SD_SWITCH_FUNC_SWITCH_MODE);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	err = esdhc_read_data(mmc, status, 64U);
+	if (err != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	if ((status[16]) == U(0x01)) {
+		mmc->card.bus_freq = SD_HS_50MHZ;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    change_state_to_transfer_state
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Send CMD7 (CMD_SELECT_CARD) to toggles the card
+ *                     between stand-by and transfer state
+ *                  2. Send CMD13 (CMD_SEND_STATUS) to check state as
+ *                     Transfer State
+ ***************************************************************************/
+static int change_state_to_transfer_state(struct mmc *mmc)
+{
+	int error = 0;
+	uint32_t response[4];
+	uint64_t start_time;
+
+	/* Command CMD_SELECT_CARD/CMD7 toggles the card between stand-by
+	 * and transfer states
+	 */
+	error = esdhc_send_cmd(mmc, CMD_SELECT_CARD, mmc->card.rca << 16);
+	if (error != 0) {
+		return error;
+	}
+	error = esdhc_wait_response(mmc, response);
+	if (error != 0) {
+		return error;
+	}
+
+	start_time = get_timer_val(0);
+	while (get_timer_val(start_time) < SD_TIMEOUT_HIGH) {
+		/* send CMD13 to check card status */
+		error = esdhc_send_cmd(mmc,
+					CMD_SEND_STATUS, mmc->card.rca << 16);
+		if (error != 0) {
+			return error;
+		}
+		error = esdhc_wait_response(mmc, response);
+		if ((error != 0) || ((response[0] & R1_ERROR) != 0)) {
+			return error;
+		}
+
+		/* Check for the present state of card */
+		if (((response[0] >> 9U) & U(0xF)) == STATE_TRAN) {
+			break;
+		}
+	}
+	if (((response[0] >> 9U) & U(0xF)) == STATE_TRAN) {
+		return 0;
+	} else {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+}
+
+/***************************************************************************
+ * Function    :    get_cid_rca_csd
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Send CMD2 (CMD_ALL_SEND_CID)
+ *                  2. get RCA for SD cards, set rca for mmc cards
+ *                     Send CMD3 (CMD_SEND_RELATIVE_ADDR)
+ *                  3. Send CMD9 (CMD_SEND_CSD)
+ *                  4. Get MMC Version from CSD
+ ***************************************************************************/
+static int get_cid_rca_csd(struct mmc *mmc)
+{
+	int err;
+	uint32_t version;
+	uint32_t response[4];
+	uint32_t mmc_version[] = {MMC_CARD_VERSION_1_2, MMC_CARD_VERSION_1_4,
+		MMC_CARD_VERSION_2_X, MMC_CARD_VERSION_3_X,
+		MMC_CARD_VERSION_4_X};
+
+	err = esdhc_send_cmd(mmc, CMD_ALL_SEND_CID, 0);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	/* get RCA for SD cards, set rca for mmc cards */
+	mmc->card.rca = SD_MMC_CARD_RCA;
+
+	/* send RCA cmd */
+	err = esdhc_send_cmd(mmc, CMD_SEND_RELATIVE_ADDR, mmc->card.rca << 16);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	/* for SD, get the the RCA */
+	if (mmc->card.type == SD_CARD) {
+		mmc->card.rca = (response[0] >> 16) & 0xFFFF;
+	}
+
+	/* Get the CSD (card specific data) from card. */
+	err = esdhc_send_cmd(mmc, CMD_SEND_CSD, mmc->card.rca << 16);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, response);
+	if (err != 0) {
+		return err;
+	}
+
+	version = (response[3] >> 18U) & U(0xF);
+	if (mmc->card.type == MMC_CARD) {
+		if (version <= MMC_CARD_VERSION_4_X) {
+			mmc->card.version = mmc_version[version];
+		} else {
+			mmc->card.version = MMC_CARD_VERSION_4_X;
+		}
+	}
+
+	mmc->card.block_len = 1 << ((response[2] >> 8) & 0xF);
+
+	if (mmc->card.block_len > BLOCK_LEN_512) {
+		mmc->card.block_len = BLOCK_LEN_512;
+	}
+
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    identify_mmc_card
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Send Reset Command
+ *                  2. Send CMD1 with args to set voltage range and Sector
+ *                     Mode. (Voltage Args = 0xFF8)
+ *                  3. Check the OCR Response
+ ***************************************************************************/
+static int identify_mmc_card(struct mmc *mmc)
+{
+	uint64_t start_time;
+	uint32_t resp[4];
+	int ret;
+	uint32_t args;
+
+	/* card reset */
+	ret = esdhc_send_cmd(mmc, CMD_GO_IDLE_STATE, 0U);
+	if (ret != 0) {
+		return ret;
+	}
+	ret = esdhc_wait_response(mmc, resp);
+	if (ret != 0) {
+		return ret;
+	}
+
+	/* Send CMD1 to get the ocr value repeatedly till the card */
+	/* busy is clear. timeout = 20sec */
+
+	start_time = get_timer_val(0);
+	do {
+		/* set the bits for the voltage ranges supported by host */
+		args = mmc->voltages_caps | MMC_OCR_SECTOR_MODE;
+		ret = esdhc_send_cmd(mmc, CMD_MMC_SEND_OP_COND, args);
+		if (ret != 0) {
+			return ret;
+		}
+		ret = esdhc_wait_response(mmc, resp);
+		if (ret != 0) {
+			return ERROR_ESDHC_UNUSABLE_CARD;
+		}
+	} while (((resp[0] & MMC_OCR_BUSY) == 0U) &&
+			(get_timer_val(start_time) < SD_TIMEOUT_HIGH));
+
+	if (get_timer_val(start_time) > SD_TIMEOUT_HIGH) {
+		return ERROR_ESDHC_UNUSABLE_CARD;
+	}
+
+	if ((resp[0] & MMC_OCR_CCS) == MMC_OCR_CCS) {
+		mmc->card.is_high_capacity = 1;
+	}
+
+	return MMC_CARD;
+}
+
+/***************************************************************************
+ * Function    :    check_for_sd_card
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    1. Send Reset Command
+ *                  2. Send CMD8 with pattern 0xAA (to check for SD 2.0)
+ *                  3. Send ACMD41 with args to set voltage range and HCS
+ *                     HCS is set only for SD Card > 2.0
+ *                     Voltage Caps = 0xFF8
+ *                  4. Check the OCR Response
+ ***************************************************************************/
+static int check_for_sd_card(struct mmc *mmc)
+{
+	uint64_t start_time;
+	uint32_t args;
+	int  ret;
+	uint32_t resp[4];
+
+	/* Send reset command */
+	ret = esdhc_send_cmd(mmc, CMD_GO_IDLE_STATE, 0U);
+	if (ret != 0) {
+		return ret;
+	}
+	ret = esdhc_wait_response(mmc, resp);
+	if (ret != 0) {
+		return ret;
+	}
+
+	/* send CMD8 with  pattern 0xAA */
+	args = MMC_VDD_HIGH_VOLTAGE | 0xAA;
+	ret = esdhc_send_cmd(mmc, CMD_SEND_IF_COND, args);
+	if (ret != 0) {
+		return ret;
+	}
+	ret = esdhc_wait_response(mmc, resp);
+	if (ret == RESP_TIMEOUT) { /* sd ver 1.x or not sd */
+		mmc->card.is_high_capacity = 0;
+	} else if ((resp[0] & U(0xFF)) == U(0xAA)) { /* ver 2.0 or later */
+		mmc->card.version = SD_CARD_VERSION_2_0;
+	} else {
+		return  NOT_SD_CARD;
+	}
+	/* Send Application command-55 to get the ocr value repeatedly till
+	 * the card busy is clear. timeout = 20sec
+	 */
+
+	start_time = get_timer_val(0);
+	do {
+		ret = esdhc_send_cmd(mmc, CMD_APP_CMD, 0U);
+		if (ret != 0) {
+			return ret;
+		}
+		ret = esdhc_wait_response(mmc, resp);
+		if (ret == COMMAND_ERROR) {
+			return ERROR_ESDHC_UNUSABLE_CARD;
+		}
+
+		/* set the bits for the voltage ranges supported by host */
+		args = mmc->voltages_caps;
+		if (mmc->card.version == SD_CARD_VERSION_2_0) {
+			args |= SD_OCR_HCS;
+		}
+
+		/* Send ACMD41 to set voltage range */
+		ret = esdhc_send_cmd(mmc, CMD_SD_SEND_OP_COND, args);
+		if (ret != 0) {
+			return ret;
+		}
+		ret = esdhc_wait_response(mmc, resp);
+		if (ret == COMMAND_ERROR) {
+			return ERROR_ESDHC_UNUSABLE_CARD;
+		} else if (ret == RESP_TIMEOUT) {
+			return NOT_SD_CARD;
+		}
+	} while (((resp[0] & MMC_OCR_BUSY) == 0U) &&
+			(get_timer_val(start_time) < SD_TIMEOUT_HIGH));
+
+	if (get_timer_val(start_time) > SD_TIMEOUT_HIGH) {
+		INFO("SD_TIMEOUT_HIGH\n");
+		return ERROR_ESDHC_UNUSABLE_CARD;
+	}
+
+	/* bit set in card capacity status */
+	if ((resp[0] & MMC_OCR_CCS) == MMC_OCR_CCS) {
+		mmc->card.is_high_capacity = 1;
+	}
+
+	return SD_CARD;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_emmc_init
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  src_emmc - Flag to Indicate SRC as emmc
+ * Return      :    SUCCESS or Error Code (< 0)
+ * Description :    Base Function called from sd_mmc_init or emmc_init
+ ***************************************************************************/
+int esdhc_emmc_init(struct mmc *mmc, bool card_detect)
+{
+	int error = 0;
+	int ret = 0;
+
+	error = esdhc_init(mmc, card_detect);
+	if (error != 0) {
+		return error;
+	}
+
+	mmc->card.bus_freq = CARD_IDENTIFICATION_FREQ;
+	mmc->card.rca = 0;
+	mmc->card.is_high_capacity = 0;
+	mmc->card.type = ERROR_ESDHC_UNUSABLE_CARD;
+
+	/* Set Voltage caps as FF8 i.e all supported */
+	/* high voltage bits 2.7 - 3.6 */
+	mmc->voltages_caps = MMC_OCR_VDD_FF8;
+
+#ifdef NXP_SD_DMA_CAPABILITY
+	/* Getting host DMA capabilities. */
+	mmc->dma_support = esdhc_in32(&mmc->esdhc_regs->hostcapblt) &
+					ESDHC_HOSTCAPBLT_DMAS;
+#else
+	mmc->dma_support = 0;
+#endif
+
+	ret = NOT_SD_CARD;
+	/* If SRC is not EMMC, check for SD or MMC */
+	ret = check_for_sd_card(mmc);
+	switch (ret) {
+	case SD_CARD:
+		mmc->card.type = SD_CARD;
+		break;
+
+	case NOT_SD_CARD:
+		/* try for MMC card */
+		if (identify_mmc_card(mmc) == MMC_CARD) {
+			mmc->card.type = MMC_CARD;
+		} else {
+			return ERROR_ESDHC_UNUSABLE_CARD;
+		}
+		break;
+
+	default:
+		return ERROR_ESDHC_UNUSABLE_CARD;
+	}
+
+	/* get CID, RCA and CSD. For MMC, set the rca */
+	error = get_cid_rca_csd(mmc);
+	if (error != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	/* change state to Transfer mode */
+	error = change_state_to_transfer_state(mmc);
+	if (error != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	/* change to high frequency if supported */
+	if (mmc->card.type == SD_CARD) {
+		error = sd_switch_to_high_freq(mmc);
+	} else {
+		error = mmc_switch_to_high_frquency(mmc);
+	}
+	if (error != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	/* mmc: 20000000, 26000000, 52000000 */
+	/* sd: 25000000, 50000000 */
+	set_speed(mmc, mmc->card.bus_freq);
+
+	INFO("init done:\n");
+	return 0;
+}
+
+/***************************************************************************
+ * Function    :    sd_mmc_init
+ * Arguments   :    mmc - Pointer to mmc struct
+ * Return      :    SUCCESS or Error Code
+ * Description :    Base Function called via hal_init for SD/MMC
+ *                  initialization
+ ***************************************************************************/
+int sd_mmc_init(uintptr_t nxp_esdhc_addr, bool card_detect)
+{
+	struct mmc *mmc = NULL;
+	int ret;
+
+	mmc = &mmc_drv_data;
+	memset(mmc, 0, sizeof(struct mmc));
+	mmc->esdhc_regs = (struct esdhc_regs *)nxp_esdhc_addr;
+
+	INFO("esdhc_emmc_init\n");
+	ret = esdhc_emmc_init(mmc, card_detect);
+	return ret;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_read_block
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  dst - Destination Pointer
+ *                  block - Block Number
+ * Return      :    SUCCESS or Error Code
+ * Description :    Read a Single block to Destination Pointer
+ *                  1. Send CMD16 (CMD_SET_BLOCKLEN) with args as blocklen
+ *                  2. Send CMD17 (CMD_READ_SINGLE_BLOCK) with args offset
+ ***************************************************************************/
+static int esdhc_read_block(struct mmc *mmc, void *dst, uint32_t block)
+{
+	uint32_t offset;
+	int err;
+
+	/* send cmd16 to set the block size. */
+	err = esdhc_send_cmd(mmc, CMD_SET_BLOCKLEN, mmc->card.block_len);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, NULL);
+	if (err != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	if (mmc->card.is_high_capacity != 0) {
+		offset = block;
+	} else {
+		offset = block * mmc->card.block_len;
+	}
+
+	esdhc_set_data_attributes(mmc, dst, 1, mmc->card.block_len);
+	err = esdhc_send_cmd(mmc, CMD_READ_SINGLE_BLOCK, offset);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, NULL);
+	if (err != 0) {
+		return err;
+	}
+
+	err = esdhc_read_data(mmc, dst, mmc->card.block_len);
+
+	return err;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_write_block
+ * Arguments   :    mmc - Pointer to mmc struct
+ *                  src - Source Pointer
+ *                  block - Block Number
+ * Return      :    SUCCESS or Error Code
+ * Description :    Write a Single block from Source Pointer
+ *                  1. Send CMD16 (CMD_SET_BLOCKLEN) with args as blocklen
+ *                  2. Send CMD24 (CMD_WRITE_SINGLE_BLOCK) with args offset
+ ***************************************************************************/
+static int esdhc_write_block(struct mmc *mmc, void *src, uint32_t block)
+{
+	uint32_t offset;
+	int err;
+
+	/* send cmd16 to set the block size. */
+	err = esdhc_send_cmd(mmc, CMD_SET_BLOCKLEN, mmc->card.block_len);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, NULL);
+	if (err != 0) {
+		return ERROR_ESDHC_COMMUNICATION_ERROR;
+	}
+
+	if (mmc->card.is_high_capacity != 0) {
+		offset = block;
+	} else {
+		offset = block * mmc->card.block_len;
+	}
+
+	esdhc_set_data_attributes(mmc, src, 1, mmc->card.block_len);
+	err = esdhc_send_cmd(mmc, CMD_WRITE_SINGLE_BLOCK, offset);
+	if (err != 0) {
+		return err;
+	}
+	err = esdhc_wait_response(mmc, NULL);
+	if (err != 0) {
+		return err;
+	}
+
+	err = esdhc_write_data(mmc, src, mmc->card.block_len);
+
+	return err;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_read
+ * Arguments   :    src_offset - offset on sd/mmc to read from. Should be block
+ *		    size aligned
+ *                  dst - Destination Pointer
+ *                  size - Length of Data ( Multiple of block size)
+ * Return      :    SUCCESS or Error Code
+ * Description :    Calls esdhc_read_block repeatedly for reading the
+ *                  data.
+ ***************************************************************************/
+int esdhc_read(struct mmc *mmc, uint32_t src_offset, uintptr_t dst, size_t size)
+{
+	int error = 0;
+	uint32_t blk, num_blocks;
+	uint8_t *buff = (uint8_t *)dst;
+
+#ifdef NXP_SD_DEBUG
+	INFO("sd mmc read\n");
+	INFO("src = %x, dst = %lxsize = %lu\n", src_offset, dst, size);
+#endif
+
+	/* check for size */
+	if (size == 0) {
+		return 0;
+	}
+
+	if ((size % mmc->card.block_len) != 0) {
+		ERROR("Size is not block aligned\n");
+		return -1;
+	}
+
+	if ((src_offset % mmc->card.block_len) != 0) {
+		ERROR("Size is not block aligned\n");
+		return -1;
+	}
+
+	/* start block */
+	blk = src_offset / mmc->card.block_len;
+#ifdef NXP_SD_DEBUG
+	INFO("blk = %x\n", blk);
+#endif
+
+	/* Number of blocks to be read */
+	num_blocks = size / mmc->card.block_len;
+
+	while (num_blocks) {
+		error = esdhc_read_block(mmc, buff, blk);
+		if (error != 0) {
+			ERROR("Read error = %x\n", error);
+			return error;
+		}
+
+		buff = buff + mmc->card.block_len;
+		blk++;
+		num_blocks--;
+	}
+
+	INFO("sd-mmc read done.\n");
+	return error;
+}
+
+/***************************************************************************
+ * Function    :    esdhc_write
+ * Arguments   :    src - Source Pointer
+ *                  dst_offset - offset on sd/mmc to write to. Should be block
+ *		    size aligned
+ *                  size - Length of Data (Multiple of block size)
+ * Return      :    SUCCESS or Error Code
+ * Description :    Calls esdhc_write_block repeatedly for writing the
+ *                  data.
+ ***************************************************************************/
+int esdhc_write(struct mmc *mmc, uintptr_t src, uint32_t dst_offset,
+		size_t size)
+{
+	int error = 0;
+	uint32_t blk, num_blocks;
+	uint8_t *buff = (uint8_t *)src;
+
+#ifdef NXP_SD_DEBUG
+	INFO("sd mmc write\n");
+	INFO("src = %x, dst = %lxsize = %lu\n", src, dst_offset, size);
+#endif
+
+	/* check for size */
+	if (size == 0) {
+		return 0;
+	}
+
+	if ((size % mmc->card.block_len) != 0) {
+		ERROR("Size is not block aligned\n");
+		return -1;
+	}
+
+	if ((dst_offset % mmc->card.block_len) != 0) {
+		ERROR("Size is not block aligned\n");
+		return -1;
+	}
+
+	/* start block */
+	blk = dst_offset / mmc->card.block_len;
+#ifdef NXP_SD_DEBUG
+	INFO("blk = %x\n", blk);
+#endif
+
+	/* Number of blocks to be written */
+	num_blocks = size / mmc->card.block_len;
+
+	while (num_blocks != 0U) {
+		error = esdhc_write_block(mmc, buff, blk);
+		if (error != 0U) {
+			ERROR("Write error = %x\n", error);
+			return error;
+		}
+
+		buff = buff + mmc->card.block_len;
+		blk++;
+		num_blocks--;
+	}
+
+	INFO("sd-mmc write done.\n");
+	return error;
+}
+
+static size_t ls_sd_emmc_read(int lba, uintptr_t buf, size_t size)
+{
+	struct mmc *mmc = NULL;
+	int ret;
+
+	mmc = &mmc_drv_data;
+	lba *= BLOCK_LEN_512;
+	ret = esdhc_read(mmc, lba, buf, size);
+	return ret ? 0 : size;
+}
+
+static struct io_block_dev_spec ls_emmc_dev_spec = {
+	.buffer = {
+		.offset = 0,
+		.length = 0,
+	},
+	.ops = {
+		.read = ls_sd_emmc_read,
+	},
+	.block_size = BLOCK_LEN_512,
+};
+
+int sd_emmc_init(uintptr_t *block_dev_spec,
+			uintptr_t nxp_esdhc_addr,
+			size_t nxp_sd_block_offset,
+			size_t nxp_sd_block_size,
+			bool card_detect)
+{
+	int ret;
+
+	ret = sd_mmc_init(nxp_esdhc_addr, card_detect);
+	if (ret != 0) {
+		return ret;
+	}
+
+	ls_emmc_dev_spec.buffer.offset = nxp_sd_block_offset;
+	ls_emmc_dev_spec.buffer.length = nxp_sd_block_size;
+	*block_dev_spec = (uintptr_t)&ls_emmc_dev_spec;
+
+	return 0;
+}
diff --git a/drivers/nxp/sd/sd_mmc.mk b/drivers/nxp/sd/sd_mmc.mk
new file mode 100644
index 0000000..c83b1bd
--- /dev/null
+++ b/drivers/nxp/sd/sd_mmc.mk
@@ -0,0 +1,26 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_SD_MMC},)
+
+ADD_SD_MMC	:= 1
+
+SD_MMC_BOOT_SOURCES	+= ${PLAT_DRIVERS_PATH}/sd/sd_mmc.c \
+			   drivers/io/io_block.c
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/sd
+
+ifeq (${BL_COMM_SD_MMC_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${SD_MMC_BOOT_SOURCES}
+else
+ifeq (${BL2_SD_MMC_NEEDED},yes)
+BL2_SOURCES		+= ${SD_MMC_BOOT_SOURCES}
+endif
+ifeq (${BL3_SD_MMC_NEEDED},yes)
+BL31_SOURCES		+= ${SD_MMC_BOOT_SOURCES}
+endif
+endif
+endif
diff --git a/drivers/nxp/sec_mon/sec_mon.mk b/drivers/nxp/sec_mon/sec_mon.mk
new file mode 100644
index 0000000..aaac53f
--- /dev/null
+++ b/drivers/nxp/sec_mon/sec_mon.mk
@@ -0,0 +1,25 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_SNVS},)
+
+ADD_SNVS		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/sec_mon
+
+SNVS_SOURCES		+= $(PLAT_DRIVERS_PATH)/sec_mon/snvs.c
+
+ifeq (${BL_COMM_SNVS_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${SNVS_SOURCES}
+else
+ifeq (${BL2_SNVS_NEEDED},yes)
+BL2_SOURCES		+= ${SNVS_SOURCES}
+endif
+ifeq (${BL31_SNVS_NEEDED},yes)
+BL31_SOURCES		+= ${SNVS_SOURCES}
+endif
+endif
+endif
diff --git a/drivers/nxp/sec_mon/snvs.c b/drivers/nxp/sec_mon/snvs.c
new file mode 100644
index 0000000..6208b67
--- /dev/null
+++ b/drivers/nxp/sec_mon/snvs.c
@@ -0,0 +1,186 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <snvs.h>
+
+static uintptr_t g_nxp_snvs_addr;
+
+void snvs_init(uintptr_t nxp_snvs_addr)
+{
+	g_nxp_snvs_addr = nxp_snvs_addr;
+}
+
+uint32_t get_snvs_state(void)
+{
+	struct snvs_regs *snvs = (struct snvs_regs *) (g_nxp_snvs_addr);
+
+	return (snvs_read32(&snvs->hp_stat) & HPSTS_MASK_SSM_ST);
+}
+
+static uint32_t do_snvs_state_transition(uint32_t state_transtion_bit,
+					 uint32_t target_state)
+{
+	struct snvs_regs *snvs = (struct snvs_regs *) (g_nxp_snvs_addr);
+	uint32_t sts = get_snvs_state();
+	uint32_t fetch_cnt = 16U;
+	uint32_t val = snvs_read32(&snvs->hp_com) | state_transtion_bit;
+
+	snvs_write32(&snvs->hp_com, val);
+
+	/* polling loop till SNVS is in target state */
+	do {
+		sts = get_snvs_state();
+	} while ((sts != target_state) && ((--fetch_cnt) != 0));
+
+	return sts;
+}
+void transition_snvs_non_secure(void)
+{
+	struct snvs_regs *snvs = (struct snvs_regs *) (g_nxp_snvs_addr);
+	uint32_t sts = get_snvs_state();
+
+	switch (sts) {
+		/* If initial state is check or Non-Secure, then
+		 * set the Software Security Violation Bit and
+		 * transition to Non-Secure State.
+		 */
+	case HPSTS_CHECK_SSM_ST:
+		sts = do_snvs_state_transition(HPCOM_SW_SV, HPSTS_NON_SECURE_SSM_ST);
+		break;
+
+		/* If initial state is Trusted, Secure or Soft-Fail, then
+		 * first set the Software Security Violation Bit and
+		 * transition to Soft-Fail State.
+		 */
+	case HPSTS_TRUST_SSM_ST:
+	case HPSTS_SECURE_SSM_ST:
+	case HPSTS_SOFT_FAIL_SSM_ST:
+		sts = do_snvs_state_transition(HPCOM_SW_SV, HPSTS_NON_SECURE_SSM_ST);
+
+		/* If SSM Soft Fail to Non-Secure State Transition
+		 * Disable is not set, then set SSM_ST bit and
+		 * transition to Non-Secure State.
+		 */
+		if ((snvs_read32(&snvs->hp_com) & HPCOM_SSM_SFNS_DIS) == 0) {
+			sts = do_snvs_state_transition(HPCOM_SSM_ST, HPSTS_NON_SECURE_SSM_ST);
+		}
+		break;
+	default:
+		break;
+	}
+}
+
+void transition_snvs_soft_fail(void)
+{
+	do_snvs_state_transition(HPCOM_SW_FSV, HPSTS_SOFT_FAIL_SSM_ST);
+}
+
+uint32_t transition_snvs_trusted(void)
+{
+	struct snvs_regs *snvs = (struct snvs_regs *) (g_nxp_snvs_addr);
+	uint32_t sts = get_snvs_state();
+
+	switch (sts) {
+		/* If initial state is check, set the SSM_ST bit to
+		 * change the state to trusted.
+		 */
+	case HPSTS_CHECK_SSM_ST:
+		sts = do_snvs_state_transition(HPCOM_SSM_ST, HPSTS_TRUST_SSM_ST);
+		break;
+		/* If SSM Secure to Trusted State Transition Disable
+		 * is not set, then set SSM_ST bit and
+		 * transition to Trusted State.
+		 */
+	case HPSTS_SECURE_SSM_ST:
+		if ((snvs_read32(&snvs->hp_com) & HPCOM_SSM_ST_DIS) == 0) {
+			sts = do_snvs_state_transition(HPCOM_SSM_ST, HPSTS_TRUST_SSM_ST);
+		}
+		break;
+		/* If initial state is Soft-Fail or Non-Secure, then
+		 * transition to Trusted is not Possible.
+		 */
+	default:
+		break;
+	}
+
+	return sts;
+}
+
+uint32_t transition_snvs_secure(void)
+{
+	uint32_t sts = get_snvs_state();
+
+	if (sts == HPSTS_SECURE_SSM_ST) {
+		return sts;
+	}
+
+	if (sts != HPSTS_TRUST_SSM_ST) {
+		sts = transition_snvs_trusted();
+		if (sts != HPSTS_TRUST_SSM_ST) {
+			return sts;
+		}
+	}
+
+	sts = do_snvs_state_transition(HPCOM_SSM_ST, HPSTS_TRUST_SSM_ST);
+
+	return sts;
+}
+
+void snvs_write_lp_gpr_bit(uint32_t offset, uint32_t bit_pos, bool flag_val)
+{
+	if (flag_val) {
+		snvs_write32(g_nxp_snvs_addr + offset,
+			     (snvs_read32(g_nxp_snvs_addr + offset))
+			     | (1 << bit_pos));
+	} else {
+		snvs_write32(g_nxp_snvs_addr + offset,
+			     (snvs_read32(g_nxp_snvs_addr + offset))
+			     & ~(1 << bit_pos));
+	}
+}
+
+uint32_t snvs_read_lp_gpr_bit(uint32_t offset, uint32_t bit_pos)
+{
+	return (snvs_read32(g_nxp_snvs_addr + offset) & (1 << bit_pos));
+}
+
+void snvs_disable_zeroize_lp_gpr(void)
+{
+	snvs_write_lp_gpr_bit(NXP_LPCR_OFFSET,
+			  NXP_GPR_Z_DIS_BIT,
+			  true);
+}
+
+#if defined(NXP_NV_SW_MAINT_LAST_EXEC_DATA) && defined(NXP_COINED_BB)
+void snvs_write_app_data_bit(uint32_t bit_pos)
+{
+	snvs_write_lp_gpr_bit(NXP_APP_DATA_LP_GPR_OFFSET,
+			      bit_pos,
+			      true);
+}
+
+uint32_t snvs_read_app_data(void)
+{
+	return snvs_read32(g_nxp_snvs_addr + NXP_APP_DATA_LP_GPR_OFFSET);
+}
+
+uint32_t snvs_read_app_data_bit(uint32_t bit_pos)
+{
+	uint8_t ret = snvs_read_lp_gpr_bit(NXP_APP_DATA_LP_GPR_OFFSET, bit_pos);
+
+	return ((ret != 0U) ? 1U : 0U);
+}
+
+void snvs_clear_app_data(void)
+{
+	snvs_write32(g_nxp_snvs_addr + NXP_APP_DATA_LP_GPR_OFFSET, 0x0);
+}
+#endif
diff --git a/drivers/nxp/sfp/fuse_prov.c b/drivers/nxp/sfp/fuse_prov.c
new file mode 100644
index 0000000..165474f
--- /dev/null
+++ b/drivers/nxp/sfp/fuse_prov.c
@@ -0,0 +1,462 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <caam.h>
+#include <common/debug.h>
+#include <dcfg.h>
+#include <drivers/delay_timer.h>
+#include <fuse_prov.h>
+#include <sfp.h>
+#include <sfp_error_codes.h>
+
+
+static int write_a_fuse(uint32_t *fuse_addr, uint32_t *fuse_hdr_val,
+			uint32_t mask)
+{
+	uint32_t last_stored_val = sfp_read32(fuse_addr);
+
+	 /* Check if fuse already blown or not */
+	if ((last_stored_val & mask) == mask) {
+		return ERROR_ALREADY_BLOWN;
+	}
+
+	 /* Write fuse in mirror registers */
+	sfp_write32(fuse_addr, last_stored_val | (*fuse_hdr_val & mask));
+
+	 /* Read back to check if write success */
+	if (sfp_read32(fuse_addr) != (last_stored_val | (*fuse_hdr_val & mask))) {
+		return ERROR_WRITE;
+	}
+
+	return 0;
+}
+
+static int write_fuses(uint32_t *fuse_addr, uint32_t *fuse_hdr_val, uint8_t len)
+{
+	int i;
+
+	 /* Check if fuse already blown or not */
+	for (i = 0; i < len; i++) {
+		if (sfp_read32(&fuse_addr[i]) != 0) {
+			return ERROR_ALREADY_BLOWN;
+		}
+	}
+
+	 /* Write fuse in mirror registers */
+	for (i = 0; i < len; i++) {
+		sfp_write32(&fuse_addr[i], fuse_hdr_val[i]);
+	}
+
+	 /* Read back to check if write success */
+	for (i = 0; i < len; i++) {
+		if (sfp_read32(&fuse_addr[i]) != fuse_hdr_val[i]) {
+			return ERROR_WRITE;
+		}
+	}
+
+	return 0;
+}
+
+/*
+ * This function program Super Root Key Hash (SRKH) in fuse
+ * registers.
+ */
+static int prog_srkh(struct fuse_hdr_t *fuse_hdr,
+		     struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int ret = 0;
+
+	ret = write_fuses(sfp_ccsr_regs->srk_hash, fuse_hdr->srkh, 8);
+
+	if (ret != 0) {
+		ret = (ret == ERROR_ALREADY_BLOWN) ?
+			ERROR_SRKH_ALREADY_BLOWN : ERROR_SRKH_WRITE;
+	}
+
+	return ret;
+}
+
+/* This function program OEMUID[0-4] in fuse registers. */
+static int prog_oemuid(struct fuse_hdr_t *fuse_hdr,
+		       struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int i, ret = 0;
+
+	for (i = 0; i < 5; i++) {
+		 /* Check OEMUIDx to be blown or not */
+		if (((fuse_hdr->flags >> (FLAG_OUID0_SHIFT + i)) & 0x1) != 0) {
+			 /* Check if OEMUID[i] already blown or not */
+			ret = write_fuses(&sfp_ccsr_regs->oem_uid[i],
+					 &fuse_hdr->oem_uid[i], 1);
+
+			if (ret != 0) {
+				ret = (ret == ERROR_ALREADY_BLOWN) ?
+					ERROR_OEMUID_ALREADY_BLOWN
+					: ERROR_OEMUID_WRITE;
+			}
+		}
+	}
+	return ret;
+}
+
+/* This function program DCV[0-1], DRV[0-1] in fuse registers. */
+static int prog_debug(struct fuse_hdr_t *fuse_hdr,
+		      struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int ret;
+
+	 /* Check DCV to be blown or not */
+	if (((fuse_hdr->flags >> (FLAG_DCV0_SHIFT)) & 0x3) != 0) {
+		 /* Check if DCV[i] already blown or not */
+		ret = write_fuses(sfp_ccsr_regs->dcv, fuse_hdr->dcv, 2);
+
+		if (ret != 0) {
+			ret = (ret == ERROR_ALREADY_BLOWN) ?
+				ERROR_DCV_ALREADY_BLOWN
+				: ERROR_DCV_WRITE;
+		}
+	}
+
+	 /* Check DRV to be blown or not */
+	if ((((fuse_hdr->flags >> (FLAG_DRV0_SHIFT)) & 0x3)) != 0) {
+		 /* Check if DRV[i] already blown or not */
+		ret = write_fuses(sfp_ccsr_regs->drv, fuse_hdr->drv, 2);
+
+		if (ret != 0) {
+			ret = (ret == ERROR_ALREADY_BLOWN) ?
+				ERROR_DRV_ALREADY_BLOWN
+				: ERROR_DRV_WRITE;
+		} else {
+			 /* Check for DRV hamming error */
+			if (sfp_read32((void *)(get_sfp_addr()
+							+ SFP_SVHESR_OFFSET))
+				& SFP_SVHESR_DRV_MASK) {
+				return ERROR_DRV_HAMMING_ERROR;
+			}
+		}
+	}
+
+	return 0;
+}
+
+ /*
+  * Turn a 256-bit random value (32 bytes) into an OTPMK code word
+  * modifying the input data array in place
+  */
+static void otpmk_make_code_word_256(uint8_t *otpmk, bool minimal_flag)
+{
+	int i;
+	uint8_t parity_bit;
+	uint8_t code_bit;
+
+	if (minimal_flag == true) {
+		 /*
+		  * Force bits 252, 253, 254 and 255 to 1
+		  * This is because these fuses may have already been blown
+		  * and the OTPMK cannot force them back to 0
+		  */
+		otpmk[252/8] |= (1 << (252%8));
+		otpmk[253/8] |= (1 << (253%8));
+		otpmk[254/8] |= (1 << (254%8));
+		otpmk[255/8] |= (1 << (255%8));
+	}
+
+	 /* Generate the hamming code for the code word */
+	parity_bit = 0;
+	code_bit = 0;
+	for (i = 0; i < 256; i += 1) {
+		if ((otpmk[i/8] & (1 << (i%8))) != 0) {
+			parity_bit ^= 1;
+			code_bit   ^= i;
+		}
+	}
+
+	 /* Inverting otpmk[code_bit] will cause the otpmk
+	  * to become a valid code word (except for overall parity)
+	  */
+	if (code_bit < 252) {
+		otpmk[code_bit/8] ^= (1 << (code_bit % 8));
+		parity_bit  ^= 1;  // account for flipping a bit changing parity
+	} else {
+		 /* Invert two bits:  (code_bit - 4) and 4
+		  * Because we invert two bits, no need to touch the parity bit
+		  */
+		otpmk[(code_bit - 4)/8] ^= (1 << ((code_bit - 4) % 8));
+		otpmk[4/8] ^= (1 << (4 % 8));
+	}
+
+	 /* Finally, adjust the overall parity of the otpmk
+	  * otpmk bit 0
+	  */
+	otpmk[0] ^= parity_bit;
+}
+
+/* This function program One Time Programmable Master Key (OTPMK)
+ *  in fuse registers.
+ */
+static int prog_otpmk(struct fuse_hdr_t *fuse_hdr,
+		      struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int ret = 0;
+	uint32_t otpmk_flags;
+	uint32_t otpmk_random[8] __aligned(CACHE_WRITEBACK_GRANULE);
+
+	otpmk_flags = (fuse_hdr->flags >> (FLAG_OTPMK_SHIFT)) & FLAG_OTPMK_MASK;
+
+	switch (otpmk_flags) {
+	case PROG_OTPMK_MIN:
+		memset(fuse_hdr->otpmk, 0, sizeof(fuse_hdr->otpmk));
+
+		 /* Minimal OTPMK value (252-255 bits set to 1) */
+		fuse_hdr->otpmk[0] |= OTPMK_MIM_BITS_MASK;
+		break;
+
+	case PROG_OTPMK_RANDOM:
+		if (is_sec_enabled() == false) {
+			ret = ERROR_OTPMK_SEC_DISABLED;
+			goto out;
+		}
+
+		 /* Generate Random number using CAAM for OTPMK */
+		memset(otpmk_random, 0, sizeof(otpmk_random));
+		if (get_rand_bytes_hw((uint8_t *)otpmk_random,
+				      sizeof(otpmk_random)) != 0) {
+			ret = ERROR_OTPMK_SEC_ERROR;
+			goto out;
+		}
+
+		 /* Run hamming over random no. to make OTPMK */
+		otpmk_make_code_word_256((uint8_t *)otpmk_random, false);
+
+		 /* Swap OTPMK */
+		fuse_hdr->otpmk[0] = otpmk_random[7];
+		fuse_hdr->otpmk[1] = otpmk_random[6];
+		fuse_hdr->otpmk[2] = otpmk_random[5];
+		fuse_hdr->otpmk[3] = otpmk_random[4];
+		fuse_hdr->otpmk[4] = otpmk_random[3];
+		fuse_hdr->otpmk[5] = otpmk_random[2];
+		fuse_hdr->otpmk[6] = otpmk_random[1];
+		fuse_hdr->otpmk[7] = otpmk_random[0];
+		break;
+
+	case PROG_OTPMK_USER:
+		break;
+
+	case PROG_OTPMK_RANDOM_MIN:
+		 /* Here assumption is that user is aware of minimal OTPMK
+		  * already blown.
+		  */
+
+		 /* Generate Random number using CAAM for OTPMK */
+		if (is_sec_enabled() == false) {
+			ret = ERROR_OTPMK_SEC_DISABLED;
+			goto out;
+		}
+
+		memset(otpmk_random, 0, sizeof(otpmk_random));
+		if (get_rand_bytes_hw((uint8_t *)otpmk_random,
+				      sizeof(otpmk_random)) != 0) {
+			ret = ERROR_OTPMK_SEC_ERROR;
+			goto out;
+		}
+
+		 /* Run hamming over random no. to make OTPMK */
+		otpmk_make_code_word_256((uint8_t *)otpmk_random, true);
+
+		 /* Swap OTPMK */
+		fuse_hdr->otpmk[0] = otpmk_random[7];
+		fuse_hdr->otpmk[1] = otpmk_random[6];
+		fuse_hdr->otpmk[2] = otpmk_random[5];
+		fuse_hdr->otpmk[3] = otpmk_random[4];
+		fuse_hdr->otpmk[4] = otpmk_random[3];
+		fuse_hdr->otpmk[5] = otpmk_random[2];
+		fuse_hdr->otpmk[6] = otpmk_random[1];
+		fuse_hdr->otpmk[7] = otpmk_random[0];
+		break;
+
+	case PROG_OTPMK_USER_MIN:
+		 /*
+		  * Here assumption is that user is aware of minimal OTPMK
+		  * already blown. Check if minimal bits are set in user
+		  * supplied OTPMK.
+		  */
+		if ((fuse_hdr->otpmk[0] & OTPMK_MIM_BITS_MASK) !=
+							OTPMK_MIM_BITS_MASK) {
+			ret = ERROR_OTPMK_USER_MIN;
+			goto out;
+		}
+		break;
+
+	default:
+		ret = 0;
+		goto out;
+	}
+
+	ret = write_fuses(sfp_ccsr_regs->otpmk, fuse_hdr->otpmk, 8);
+
+	if (ret != 0) {
+		ret = (ret == ERROR_ALREADY_BLOWN) ?
+			ERROR_OTPMK_ALREADY_BLOWN
+			: ERROR_OTPMK_WRITE;
+	} else {
+		 /* Check for DRV hamming error */
+		if ((sfp_read32((void *)(get_sfp_addr() + SFP_SVHESR_OFFSET))
+			& SFP_SVHESR_OTPMK_MASK) != 0) {
+			ret = ERROR_OTPMK_HAMMING_ERROR;
+		}
+	}
+
+out:
+	return ret;
+}
+
+/* This function program OSPR1 in fuse registers.
+ */
+static int prog_ospr1(struct fuse_hdr_t *fuse_hdr,
+		      struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int ret;
+	uint32_t mask = 0;
+
+#ifdef NXP_SFP_VER_3_4
+	if (((fuse_hdr->flags >> FLAG_MC_SHIFT) & 0x1) != 0) {
+		mask = OSPR1_MC_MASK;
+	}
+#endif
+	if (((fuse_hdr->flags >> FLAG_DBG_LVL_SHIFT) & 0x1) != 0) {
+		mask = mask | OSPR1_DBG_LVL_MASK;
+	}
+
+	ret = write_a_fuse(&sfp_ccsr_regs->ospr1, &fuse_hdr->ospr1, mask);
+
+	if (ret != 0) {
+		ret = (ret == ERROR_ALREADY_BLOWN) ?
+				ERROR_OSPR1_ALREADY_BLOWN
+				: ERROR_OSPR1_WRITE;
+	}
+
+	return ret;
+}
+
+/* This function program SYSCFG in fuse registers.
+ */
+static int prog_syscfg(struct fuse_hdr_t *fuse_hdr,
+		       struct sfp_ccsr_regs_t *sfp_ccsr_regs)
+{
+	int ret;
+
+	 /* Check if SYSCFG already blown or not */
+	ret = write_a_fuse(&sfp_ccsr_regs->ospr, &fuse_hdr->sc, OSPR0_SC_MASK);
+
+	if (ret != 0) {
+		ret = (ret == ERROR_ALREADY_BLOWN) ?
+				ERROR_SC_ALREADY_BLOWN
+				: ERROR_SC_WRITE;
+	}
+
+	return ret;
+}
+
+/* This function does fuse provisioning.
+ */
+int provision_fuses(unsigned long long fuse_scr_addr,
+		    bool en_povdd_status)
+{
+	struct fuse_hdr_t *fuse_hdr = NULL;
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(get_sfp_addr()
+							+ SFP_FUSE_REGS_OFFSET);
+	int ret = 0;
+
+	fuse_hdr = (struct fuse_hdr_t *)fuse_scr_addr;
+
+	/*
+	 * Check for Write Protect (WP) fuse. If blown then do
+	 *  no fuse provisioning.
+	 */
+	if ((sfp_read32(&sfp_ccsr_regs->ospr) & 0x1) != 0) {
+		goto out;
+	}
+
+	 /* Check if SRKH to be blown or not */
+	if (((fuse_hdr->flags >> FLAG_SRKH_SHIFT) & 0x1) != 0) {
+		INFO("Fuse: Program SRKH\n");
+		ret = prog_srkh(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+	 /* Check if OEMUID to be blown or not */
+	if (((fuse_hdr->flags >> FLAG_OUID0_SHIFT) & FLAG_OUID_MASK) != 0) {
+		INFO("Fuse: Program OEMUIDs\n");
+		ret = prog_oemuid(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+	 /* Check if Debug values to be blown or not */
+	if (((fuse_hdr->flags >> FLAG_DCV0_SHIFT) & FLAG_DEBUG_MASK) != 0) {
+		INFO("Fuse: Program Debug values\n");
+		ret = prog_debug(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+	 /* Check if OTPMK values to be blown or not */
+	if (((fuse_hdr->flags >> FLAG_OTPMK_SHIFT) & PROG_NO_OTPMK) !=
+		PROG_NO_OTPMK) {
+		INFO("Fuse: Program OTPMK\n");
+		ret = prog_otpmk(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+
+	 /* Check if MC or DBG LVL to be blown or not */
+	if ((((fuse_hdr->flags >> FLAG_MC_SHIFT) & 0x1) != 0) ||
+		(((fuse_hdr->flags >> FLAG_DBG_LVL_SHIFT) & 0x1) != 0)) {
+		INFO("Fuse: Program OSPR1\n");
+		ret = prog_ospr1(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+	 /* Check if SYSCFG to be blown or not */
+	if (((fuse_hdr->flags >> FLAG_SYSCFG_SHIFT) & 0x1) != 0) {
+		INFO("Fuse: Program SYSCFG\n");
+		ret = prog_syscfg(fuse_hdr, sfp_ccsr_regs);
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+
+	if (en_povdd_status) {
+		ret = sfp_program_fuses();
+		if (ret != 0) {
+			error_handler(ret);
+			goto out;
+		}
+	}
+out:
+	return ret;
+}
diff --git a/drivers/nxp/sfp/sfp.c b/drivers/nxp/sfp/sfp.c
new file mode 100644
index 0000000..e06c6b9
--- /dev/null
+++ b/drivers/nxp/sfp/sfp.c
@@ -0,0 +1,167 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <caam.h>
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <sfp.h>
+#include <sfp_error_codes.h>
+
+static uintptr_t g_nxp_sfp_addr;
+static uint32_t srk_hash[SRK_HASH_SIZE/sizeof(uint32_t)]
+					__aligned(CACHE_WRITEBACK_GRANULE);
+
+void sfp_init(uintptr_t nxp_sfp_addr)
+{
+	g_nxp_sfp_addr = nxp_sfp_addr;
+}
+
+uintptr_t get_sfp_addr(void)
+{
+	return g_nxp_sfp_addr;
+}
+
+uint32_t *get_sfp_srk_hash(void)
+{
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs =
+			(void *) (g_nxp_sfp_addr + SFP_FUSE_REGS_OFFSET);
+	int i = 0;
+
+	/* Add comparison of hash with SFP hash here */
+	for (i = 0; i < SRK_HASH_SIZE/sizeof(uint32_t); i++)
+		srk_hash[i] =
+			mmio_read_32((uintptr_t)&sfp_ccsr_regs->srk_hash[i]);
+
+	return srk_hash;
+}
+
+void set_sfp_wr_disable(void)
+{
+	/*
+	 * Mark SFP Write Disable and Write Disable Lock
+	 * Bit to prevent write to SFP fuses like
+	 * OUID's, Key Revocation fuse etc
+	 */
+	void *sfpcr = (void *)(g_nxp_sfp_addr + SFP_SFPCR_OFFSET);
+	uint32_t sfpcr_val;
+
+	sfpcr_val = sfp_read32(sfpcr);
+	sfpcr_val |= (SFP_SFPCR_WD | SFP_SFPCR_WDL);
+	sfp_write32(sfpcr, sfpcr_val);
+}
+
+int sfp_program_fuses(void)
+{
+	uint32_t ingr;
+	uint32_t sfp_cmd_status = 0U;
+	int ret = 0;
+
+	/* Program SFP fuses from mirror registers */
+	sfp_write32((void *)(g_nxp_sfp_addr + SFP_INGR_OFFSET),
+		    SFP_INGR_PROGFB_CMD);
+
+	/* Wait until fuse programming is successful */
+	do {
+		ingr = sfp_read32(g_nxp_sfp_addr + SFP_INGR_OFFSET);
+	} while (ingr & SFP_INGR_PROGFB_CMD);
+
+	/* Check for SFP fuse programming error */
+	sfp_cmd_status = sfp_read32(g_nxp_sfp_addr + SFP_INGR_OFFSET)
+			 & SFP_INGR_ERROR_MASK;
+
+	if (sfp_cmd_status != 0U) {
+		return ERROR_PROGFB_CMD;
+	}
+
+	return ret;
+}
+
+uint32_t sfp_read_oem_uid(uint8_t oem_uid)
+{
+	uint32_t val = 0U;
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(g_nxp_sfp_addr
+							+ SFP_FUSE_REGS_OFFSET);
+
+	if (oem_uid > MAX_OEM_UID) {
+		ERROR("Invalid OEM UID received.\n");
+		return ERROR_OEMUID_WRITE;
+	}
+
+	val = sfp_read32(&sfp_ccsr_regs->oem_uid[oem_uid]);
+
+	return val;
+}
+
+/*
+ * return val:  0 - No update required.
+ *              1 - successful update done.
+ *              ERROR_OEMUID_WRITE - Invalid OEM UID
+ */
+uint32_t sfp_write_oem_uid(uint8_t oem_uid, uint32_t sfp_val)
+{
+	uint32_t val = 0U;
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(g_nxp_sfp_addr
+							+ SFP_FUSE_REGS_OFFSET);
+
+	val = sfp_read_oem_uid(oem_uid);
+
+	if (val == ERROR_OEMUID_WRITE) {
+		return ERROR_OEMUID_WRITE;
+	}
+
+	/* Counter already set. No need to do anything */
+	if ((val & sfp_val) != 0U) {
+		return 0U;
+	}
+
+	val |= sfp_val;
+
+	INFO("SFP Value is %x for setting sfp_val = %d\n", val, sfp_val);
+
+	sfp_write32(&sfp_ccsr_regs->oem_uid[oem_uid], val);
+
+	return 1U;
+}
+
+int sfp_check_its(void)
+{
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(g_nxp_sfp_addr
+							+ SFP_FUSE_REGS_OFFSET);
+
+	if ((sfp_read32(&sfp_ccsr_regs->ospr) & OSPR_ITS_MASK) != 0) {
+		return 1;
+	} else {
+		return 0;
+	}
+}
+
+int sfp_check_oem_wp(void)
+{
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(g_nxp_sfp_addr
+							+ SFP_FUSE_REGS_OFFSET);
+
+	if ((sfp_read32(&sfp_ccsr_regs->ospr) & OSPR_WP_MASK) != 0) {
+		return 1;
+	} else {
+		return 0;
+	}
+}
+
+/* This function returns ospr's key_revoc values.*/
+uint32_t get_key_revoc(void)
+{
+	struct sfp_ccsr_regs_t *sfp_ccsr_regs = (void *)(g_nxp_sfp_addr
+							+ SFP_FUSE_REGS_OFFSET);
+
+	return (sfp_read32(&sfp_ccsr_regs->ospr) & OSPR_KEY_REVOC_MASK) >>
+						OSPR_KEY_REVOC_SHIFT;
+}
diff --git a/drivers/nxp/sfp/sfp.mk b/drivers/nxp/sfp/sfp.mk
new file mode 100644
index 0000000..de708c5
--- /dev/null
+++ b/drivers/nxp/sfp/sfp.mk
@@ -0,0 +1,33 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+ifeq (${SFP_ADDED},)
+
+SFP_ADDED		:= 1
+$(eval $(call add_define, NXP_SFP_ENABLED))
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/sfp
+
+SFP_SOURCES		+= $(PLAT_DRIVERS_PATH)/sfp/sfp.c
+
+ifeq (${FUSE_PROG}, 1)
+SFP_BL2_SOURCES		+= $(PLAT_DRIVERS_PATH)/sfp/fuse_prov.c
+endif
+
+ifeq (${BL_COMM_SFP_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${SFP_SOURCES}
+BL2_SOURCES		+= ${SFP_BL2_SOURCES}
+else
+ifeq (${BL2_SFP_NEEDED},yes)
+BL2_SOURCES		+= ${SFP_SOURCES}\
+			   ${SFP_BL2_SOURCES}
+endif
+ifeq (${BL31_SFP_NEEDED},yes)
+BL31_SOURCES		+= ${SFP_SOURCES}
+endif
+endif
+endif
+#------------------------------------------------
diff --git a/drivers/nxp/timer/nxp_timer.c b/drivers/nxp/timer/nxp_timer.c
new file mode 100644
index 0000000..8eecd2e
--- /dev/null
+++ b/drivers/nxp/timer/nxp_timer.c
@@ -0,0 +1,143 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <nxp_timer.h>
+#include <plat/common/platform.h>
+
+static uintptr_t g_nxp_timer_addr;
+static timer_ops_t ops;
+
+uint64_t get_timer_val(uint64_t start)
+{
+	uint64_t cntpct;
+
+	isb();
+	cntpct = read_cntpct_el0();
+	return (cntpct * 1000ULL / read_cntfrq_el0() - start);
+}
+
+static uint32_t timer_get_value(void)
+{
+	uint64_t cntpct;
+
+	isb();
+	cntpct = read_cntpct_el0();
+#ifdef ERRATA_SOC_A008585
+	uint8_t	max_fetch_count = 10U;
+	/* This erratum number needs to be confirmed to match ARM document */
+	uint64_t temp;
+
+	isb();
+	temp = read_cntpct_el0();
+
+	while (temp != cntpct && max_fetch_count) {
+		isb();
+		cntpct = read_cntpct_el0();
+		isb();
+		temp = read_cntpct_el0();
+		max_fetch_count--;
+	}
+#endif
+
+	/*
+	 * Generic delay timer implementation expects the timer to be a down
+	 * counter. We apply bitwise NOT operator to the tick values returned
+	 * by read_cntpct_el0() to simulate the down counter. The value is
+	 * clipped from 64 to 32 bits.
+	 */
+	return (uint32_t)(~cntpct);
+}
+
+static void delay_timer_init_args(uint32_t mult, uint32_t div)
+{
+	ops.get_timer_value	= timer_get_value,
+	ops.clk_mult		= mult;
+	ops.clk_div		= div;
+
+	timer_init(&ops);
+
+	VERBOSE("Generic delay timer configured with mult=%u and div=%u\n",
+		mult, div);
+}
+
+/*
+ * Initialise the nxp on-chip free rolling usec counter as the delay
+ * timer.
+ */
+void delay_timer_init(uintptr_t nxp_timer_addr)
+{
+	/* Value in ticks */
+	unsigned int mult = MHZ_TICKS_PER_SEC;
+
+	unsigned int div;
+
+	unsigned int counter_base_frequency = plat_get_syscnt_freq2();
+
+	g_nxp_timer_addr = nxp_timer_addr;
+	/* Rounding off the Counter Frequency to MHZ_TICKS_PER_SEC */
+	if (counter_base_frequency > MHZ_TICKS_PER_SEC) {
+		counter_base_frequency = (counter_base_frequency
+					/ MHZ_TICKS_PER_SEC)
+					* MHZ_TICKS_PER_SEC;
+	} else {
+		counter_base_frequency = (counter_base_frequency
+					/ KHZ_TICKS_PER_SEC)
+					* KHZ_TICKS_PER_SEC;
+	}
+
+	/* Value in ticks per second (Hz) */
+	div = counter_base_frequency;
+
+	/* Reduce multiplier and divider by dividing them repeatedly by 10 */
+	while ((mult % 10U == 0U) && (div % 10U == 0U)) {
+		mult /= 10U;
+		div /= 10U;
+	}
+
+	/* Enable and initialize the System level generic timer */
+	mmio_write_32(g_nxp_timer_addr + CNTCR_OFF,
+			CNTCR_FCREQ(0) | CNTCR_EN);
+
+	delay_timer_init_args(mult, div);
+}
+
+
+#ifdef IMAGE_BL31
+/*******************************************************************************
+ * TBD: Configures access to the system counter timer module.
+ ******************************************************************************/
+void ls_configure_sys_timer(uintptr_t ls_sys_timctl_base,
+			    uint8_t ls_config_cntacr,
+			    uint8_t plat_ls_ns_timer_frame_id)
+{
+	unsigned int reg_val;
+
+	if (ls_config_cntacr == 1U) {
+		reg_val = (1U << CNTACR_RPCT_SHIFT) | (1U << CNTACR_RVCT_SHIFT);
+		reg_val |= (1U << CNTACR_RFRQ_SHIFT) | (1U << CNTACR_RVOFF_SHIFT);
+		reg_val |= (1U << CNTACR_RWVT_SHIFT) | (1U << CNTACR_RWPT_SHIFT);
+		mmio_write_32(ls_sys_timctl_base +
+		      CNTACR_BASE(plat_ls_ns_timer_frame_id), reg_val);
+		mmio_write_32(ls_sys_timctl_base, plat_get_syscnt_freq2());
+	}
+
+	reg_val = (1U << CNTNSAR_NS_SHIFT(plat_ls_ns_timer_frame_id));
+	mmio_write_32(ls_sys_timctl_base + CNTNSAR, reg_val);
+}
+
+void enable_init_timer(void)
+{
+	/* Enable and initialize the System level generic timer */
+	mmio_write_32(g_nxp_timer_addr + CNTCR_OFF,
+			CNTCR_FCREQ(0) | CNTCR_EN);
+}
+#endif
diff --git a/drivers/nxp/timer/timer.mk b/drivers/nxp/timer/timer.mk
new file mode 100644
index 0000000..d658d19
--- /dev/null
+++ b/drivers/nxp/timer/timer.mk
@@ -0,0 +1,25 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_TIMER},)
+
+ADD_TIMER		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/timer
+TIMER_SOURCES		+= drivers/delay_timer/delay_timer.c	\
+			   $(PLAT_DRIVERS_PATH)/timer/nxp_timer.c
+
+ifeq (${BL_COMM_TIMER_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${TIMER_SOURCES}
+else
+ifeq (${BL2_TIMER_NEEDED},yes)
+BL2_SOURCES		+= ${TIMER_SOURCES}
+endif
+ifeq (${BL31_TIMER_NEEDED},yes)
+BL31_SOURCES		+= ${TIMER_SOURCES}
+endif
+endif
+endif
diff --git a/drivers/nxp/tzc/plat_tzc400.c b/drivers/nxp/tzc/plat_tzc400.c
new file mode 100644
index 0000000..4fe5221
--- /dev/null
+++ b/drivers/nxp/tzc/plat_tzc400.c
@@ -0,0 +1,187 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/debug.h>
+
+#include <plat_tzc400.h>
+
+#pragma weak populate_tzc400_reg_list
+
+#ifdef DEFAULT_TZASC_CONFIG
+/*
+ * Typical Memory map of DRAM0
+ *    |-----------NXP_NS_DRAM_ADDR ( = NXP_DRAM0_ADDR)----------|
+ *    |								|
+ *    |								|
+ *    |			Non-SECURE REGION			|
+ *    |								|
+ *    |								|
+ *    |								|
+ *    |------- (NXP_NS_DRAM_ADDR + NXP_NS_DRAM_SIZE - 1) -------|
+ *    |-----------------NXP_SECURE_DRAM_ADDR--------------------|
+ *    |								|
+ *    |								|
+ *    |								|
+ *    |			SECURE REGION (= 64MB)			|
+ *    |								|
+ *    |								|
+ *    |								|
+ *    |--- (NXP_SECURE_DRAM_ADDR + NXP_SECURE_DRAM_SIZE - 1)----|
+ *    |-----------------NXP_SP_SHRD_DRAM_ADDR-------------------|
+ *    |								|
+ *    |	       Secure EL1 Payload SHARED REGION (= 2MB)         |
+ *    |								|
+ *    |-----------(NXP_DRAM0_ADDR + NXP_DRAM0_SIZE - 1)---------|
+ *
+ *
+ *
+ * Typical Memory map of DRAM1
+ *    |---------------------NXP_DRAM1_ADDR----------------------|
+ *    |								|
+ *    |								|
+ *    |			Non-SECURE REGION			|
+ *    |								|
+ *    |								|
+ *    |---(NXP_DRAM1_ADDR + Dynamically calculated Size - 1) ---|
+ *
+ *
+ * Typical Memory map of DRAM2
+ *    |---------------------NXP_DRAM2_ADDR----------------------|
+ *    |								|
+ *    |								|
+ *    |			Non-SECURE REGION			|
+ *    |								|
+ *    |								|
+ *    |---(NXP_DRAM2_ADDR + Dynamically calculated Size - 1) ---|
+ */
+
+/*****************************************************************************
+ * This function sets up access permissions on memory regions
+ *
+ * Input:
+ *	tzc400_reg_list	: TZC400 Region List
+ *	dram_idx	: DRAM index
+ *	list_idx	: TZC400 Region List Index
+ *	dram_start_addr	: Start address of DRAM at dram_idx.
+ *	dram_size	: Size of DRAM at dram_idx.
+ *	secure_dram_sz	: Secure DRAM Size
+ *	shrd_dram_sz	: Shared DRAM Size
+ *
+ * Out:
+ *	list_idx	: last populated index + 1
+ *
+ ****************************************************************************/
+int populate_tzc400_reg_list(struct tzc400_reg *tzc400_reg_list,
+			     int dram_idx, int list_idx,
+			     uint64_t dram_start_addr,
+			     uint64_t dram_size,
+			     uint32_t secure_dram_sz,
+			     uint32_t shrd_dram_sz)
+{
+	if (list_idx == 0) {
+		/* No need to configure TZC Region 0 in this list.
+		 */
+		list_idx++;
+	}
+	/* Continue with list entries for index > 0 */
+	if (dram_idx == 0) {
+		/* TZC Region 1 on DRAM0 for Secure Memory*/
+		tzc400_reg_list[list_idx].reg_filter_en = 1;
+		tzc400_reg_list[list_idx].start_addr = dram_start_addr + dram_size;
+		tzc400_reg_list[list_idx].end_addr = dram_start_addr + dram_size
+						+ secure_dram_sz - 1;
+		tzc400_reg_list[list_idx].sec_attr = TZC_REGION_S_RDWR;
+		tzc400_reg_list[list_idx].nsaid_permissions = TZC_REGION_NS_NONE;
+		list_idx++;
+
+		/* TZC Region 2 on DRAM0 for Shared Memory*/
+		tzc400_reg_list[list_idx].reg_filter_en = 1;
+		tzc400_reg_list[list_idx].start_addr = dram_start_addr + dram_size
+							+ secure_dram_sz;
+		tzc400_reg_list[list_idx].end_addr = dram_start_addr + dram_size
+							+ secure_dram_sz
+							+ shrd_dram_sz
+							- 1;
+		tzc400_reg_list[list_idx].sec_attr = TZC_REGION_S_RDWR;
+		tzc400_reg_list[list_idx].nsaid_permissions = TZC_NS_ACCESS_ID;
+		list_idx++;
+
+		/* TZC Region 3 on DRAM0 for Non-Secure Memory*/
+		tzc400_reg_list[list_idx].reg_filter_en = 1;
+		tzc400_reg_list[list_idx].start_addr = dram_start_addr;
+		tzc400_reg_list[list_idx].end_addr = dram_start_addr + dram_size
+							- 1;
+		tzc400_reg_list[list_idx].sec_attr = TZC_REGION_S_RDWR;
+		tzc400_reg_list[list_idx].nsaid_permissions = TZC_NS_ACCESS_ID;
+		list_idx++;
+	} else {
+		/* TZC Region 3+i on DRAM(> 0) for Non-Secure Memory*/
+		tzc400_reg_list[list_idx].reg_filter_en = 1;
+		tzc400_reg_list[list_idx].start_addr = dram_start_addr;
+		tzc400_reg_list[list_idx].end_addr = dram_start_addr + dram_size
+							- 1;
+		tzc400_reg_list[list_idx].sec_attr = TZC_REGION_S_RDWR;
+		tzc400_reg_list[list_idx].nsaid_permissions = TZC_NS_ACCESS_ID;
+		list_idx++;
+	}
+
+	return list_idx;
+}
+#else
+int populate_tzc400_reg_list(struct tzc400_reg *tzc400_reg_list,
+			     int dram_idx, int list_idx,
+			     uint64_t dram_start_addr,
+			     uint64_t dram_size,
+			     uint32_t secure_dram_sz,
+			     uint32_t shrd_dram_sz)
+{
+	ERROR("tzc400_reg_list used is not a default list\n");
+	ERROR("%s needs to be over-written.\n", __func__);
+	return 0;
+}
+#endif	/* DEFAULT_TZASC_CONFIG */
+
+/*******************************************************************************
+ * Configure memory access permissions
+ *   - Region 0 with no access;
+ *   - Region 1 to 4 as per the tzc400_reg_list populated by
+ *     function populate_tzc400_reg_list() with default for all the SoC.
+ ******************************************************************************/
+void mem_access_setup(uintptr_t base, uint32_t total_regions,
+		      struct tzc400_reg *tzc400_reg_list)
+{
+	uint32_t list_indx = 0U;
+
+	INFO("Configuring TrustZone Controller\n");
+
+	tzc400_init(base);
+
+	/* Disable filters. */
+	tzc400_disable_filters();
+
+	/* Region 0 set to no access by default */
+	tzc400_configure_region0(TZC_REGION_S_NONE, 0U);
+
+	for (list_indx = 1U; list_indx < total_regions; list_indx++) {
+		tzc400_configure_region(
+			tzc400_reg_list[list_indx].reg_filter_en,
+			list_indx,
+			tzc400_reg_list[list_indx].start_addr,
+			tzc400_reg_list[list_indx].end_addr,
+			tzc400_reg_list[list_indx].sec_attr,
+			tzc400_reg_list[list_indx].nsaid_permissions);
+	}
+
+	/*
+	 * Raise an exception if a NS device tries to access secure memory
+	 * TODO: Add interrupt handling support.
+	 */
+	tzc400_set_action(TZC_ACTION_ERR);
+
+	/* Enable filters. */
+	tzc400_enable_filters();
+}
diff --git a/drivers/nxp/tzc/tzc.mk b/drivers/nxp/tzc/tzc.mk
new file mode 100644
index 0000000..3fba28f
--- /dev/null
+++ b/drivers/nxp/tzc/tzc.mk
@@ -0,0 +1,33 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${ADD_TZASC},)
+
+ADD_TZASC		:= 1
+
+PLAT_INCLUDES		+= -I$(PLAT_DRIVERS_INCLUDE_PATH)/tzc
+
+ifeq ($(TZC_ID), TZC400)
+TZASC_SOURCES		+= drivers/arm/tzc/tzc400.c\
+			   $(PLAT_DRIVERS_PATH)/tzc/plat_tzc400.c
+else ifeq ($(TZC_ID), NONE)
+    $(info -> No TZC present on platform)
+else
+    $(error -> TZC type not set!)
+endif
+
+ifeq (${BL_COMM_TZASC_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${TZASC_SOURCES}
+else
+ifeq (${BL2_TZASC_NEEDED},yes)
+BL2_SOURCES		+= ${TZASC_SOURCES}
+endif
+ifeq (${BL31_TZASC_NEEDED},yes)
+BL31_SOURCES		+= ${TZASC_SOURCES}
+endif
+endif
+
+endif
diff --git a/drivers/partition/partition.c b/drivers/partition/partition.c
index 68133ea..fdea10d 100644
--- a/drivers/partition/partition.c
+++ b/drivers/partition/partition.c
@@ -5,6 +5,7 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
 #include <stdio.h>
 #include <string.h>
 
@@ -31,7 +32,7 @@
 			name[len + j] = ' ';
 		}
 		name[EFI_NAMELEN - 1] = '\0';
-		VERBOSE("%d: %s %llx-%llx\n", i + 1, name, list.list[i].start,
+		VERBOSE("%d: %s %" PRIx64 "-%" PRIx64 "\n", i + 1, name, list.list[i].start,
 			list.list[i].start + list.list[i].length - 4);
 	}
 }
diff --git a/drivers/rambus/trng_ip_76.c b/drivers/rambus/trng_ip_76.c
new file mode 100644
index 0000000..8de12e9
--- /dev/null
+++ b/drivers/rambus/trng_ip_76.c
@@ -0,0 +1,249 @@
+/*
+ * Copyright (c) 2020, Marvell Technology Group Ltd. All rights reserved.
+ *
+ * Based on Linux kernel omap-rng.c - RNG driver for TI OMAP CPU family
+ *
+ * Author: Deepak Saxena <dsaxena@plexity.net>
+ *
+ * Copyright 2005 (c) MontaVista Software, Inc.
+ *
+ * Mostly based on original driver:
+ *
+ * Copyright (C) 2005 Nokia Corporation
+ * Author: Juha Yrjölä <juha.yrjola@nokia.com>
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <drivers/rambus/trng_ip_76.h>
+#include <lib/mmio.h>
+#include <lib/spinlock.h>
+#include <lib/utils.h>
+
+#define RNG_REG_STATUS_RDY			(1 << 0)
+
+#define RNG_REG_INTACK_RDY_MASK			(1 << 0)
+
+#define RNG_CONTROL_ENABLE_TRNG_MASK		(1 << 10)
+
+#define RNG_CONFIG_NOISE_BLOCKS(val)		((0xff & (val)) << 0)
+#define RNG_CONFIG_NOISE_BLK_VAL		0x5
+
+#define RNG_CONFIG_SAMPLE_CYCLES(val)		((0xff & (val)) << 16)
+#define RNG_CONFIG_SAMPLE_CYCLES_VAL		0x22
+
+#define RNG_REG_FRO_ENABLE_MASK			0xffffff
+#define RNG_REG_FRO_DETUNE_MASK			0x0
+
+#define EIP76_RNG_OUTPUT_SIZE			0x10
+#define EIP76_RNG_WAIT_ROUNDS			10
+
+#define RNG_HW_IS_EIP76(ver)			((ver) & (0xff == 0x4C))
+#define RNG_HW_VER_MAJOR(ver)			(((ver) & (0xf << 24)) >> 24)
+#define RNG_HW_VER_MINOR(ver)			(((ver) & (0xf << 20)) >> 20)
+#define RNG_HW_VER_PATCH(ver)			(((ver) & (0xf << 16)) >> 16)
+
+
+enum {
+	RNG_OUTPUT_0_REG = 0,
+	RNG_OUTPUT_1_REG,
+	RNG_OUTPUT_2_REG,
+	RNG_OUTPUT_3_REG,
+	RNG_STATUS_REG,
+	RNG_INTMASK_REG,
+	RNG_INTACK_REG,
+	RNG_CONTROL_REG,
+	RNG_CONFIG_REG,
+	RNG_ALARMCNT_REG,
+	RNG_FROENABLE_REG,
+	RNG_FRODETUNE_REG,
+	RNG_ALARMMASK_REG,
+	RNG_ALARMSTOP_REG,
+	RNG_REV_REG
+};
+
+static uint16_t reg_map_eip76[] = {
+	[RNG_OUTPUT_0_REG]	= 0x0,
+	[RNG_OUTPUT_1_REG]	= 0x4,
+	[RNG_OUTPUT_2_REG]	= 0x8,
+	[RNG_OUTPUT_3_REG]	= 0xc,
+	[RNG_STATUS_REG]	= 0x10,
+	[RNG_INTACK_REG]	= 0x10,
+	[RNG_CONTROL_REG]	= 0x14,
+	[RNG_CONFIG_REG]	= 0x18,
+	[RNG_ALARMCNT_REG]	= 0x1c,
+	[RNG_FROENABLE_REG]	= 0x20,
+	[RNG_FRODETUNE_REG]	= 0x24,
+	[RNG_ALARMMASK_REG]	= 0x28,
+	[RNG_ALARMSTOP_REG]	= 0x2c,
+	[RNG_REV_REG]		= 0x7c,
+};
+
+struct eip76_rng_dev {
+	uintptr_t	base;
+	uint16_t	*regs;
+};
+
+/* Locals */
+static struct eip76_rng_dev eip76_dev;
+static spinlock_t rng_lock;
+
+static inline uint32_t eip76_rng_read(struct eip76_rng_dev *dev, uint16_t reg)
+{
+	return mmio_read_32(dev->base + dev->regs[reg]);
+}
+
+static inline void eip76_rng_write(struct eip76_rng_dev *dev,
+				   uint16_t reg, uint32_t val)
+{
+	mmio_write_32(dev->base + dev->regs[reg], val);
+}
+
+static void eip76_rng_init(struct eip76_rng_dev *dev)
+{
+	uint32_t val;
+
+	/* Return if RNG is already running. */
+	if (eip76_rng_read(dev, RNG_CONTROL_REG) &
+			   RNG_CONTROL_ENABLE_TRNG_MASK) {
+		return;
+	}
+
+	/*  This field sets the number of 512-bit blocks of raw Noise Source
+	 * output data that must be processed by either the Conditioning
+	 * Function or the SP 800-90 DRBG ‘BC_DF’ functionality to yield
+	 * a ‘full entropy’ output value. As according to [SP 800-90B draft]
+	 * the amount of entropy input to this functionality must be twice
+	 * the amount that is output and the 8-bit samples output by the Noise
+	 * Source are supposed to have one bit of entropy each, the settings
+	 * for this field are as follows:
+	 * - SHA-1 Conditioning Function:
+	 *  generates 160 bits output, requiring 2560 sample bits,
+	 *  equivalent to 5 blocks of raw Noise Source input.
+	 * - SHA-256 Conditioning Function:
+	 *  generates 256 bits output, requiring 4096 sample bits, equivalent
+	 *  to 8 blocks of raw Noise Source input. Note that two blocks of 256
+	 *  bits are needed to start or re-seed the SP 800-90 DRBG
+	 *  (in the EIP-76d-*-SHA2 configurations)
+	 * - SP 800-90 DRBG ‘BC_DF’ functionality:
+	 *  generates 384 bits output, requiring 6144 sample bits, equivalent
+	 *  to 12 blocks of raw Noise Source input.
+	 *  This field can only be modified when ‘enable_trng’ in TRNG_CONTROL
+	 *  is ‘0’ or when either of the ‘test_known_noise’ or ‘test_cond_func’
+	 *  bits in TRNG_TEST is ‘1’. Value 0 in this field selects 256 blocks
+	 *  of 512 bits to be processed.
+	 */
+	val = RNG_CONFIG_NOISE_BLOCKS(RNG_CONFIG_NOISE_BLK_VAL);
+
+	/* This field sets the number of FRO samples that are XOR-ed together
+	 * into one bit to be shifted into the main shift register.
+	 * This value must be such that there is at least one bit of entropy
+	 * (in total) in each 8 bits that are shifted.
+	 * This field can only be modified when ‘enable_trng’ in TRNG_CONTROL
+	 * is ‘0’ or when either of the ‘test_known_noise’ or ‘test_cond_func’
+	 * bits in TRNG_TEST is ‘1’. Value 0 in this field selects 65536 FRO
+	 * samples to be XOR-ed together
+	 */
+	val |= RNG_CONFIG_SAMPLE_CYCLES(RNG_CONFIG_SAMPLE_CYCLES_VAL);
+	eip76_rng_write(dev, RNG_CONFIG_REG, val);
+
+	/* Enable all available FROs */
+	eip76_rng_write(dev, RNG_FRODETUNE_REG, RNG_REG_FRO_DETUNE_MASK);
+	eip76_rng_write(dev, RNG_FROENABLE_REG, RNG_REG_FRO_ENABLE_MASK);
+
+	/* Enable TRNG */
+	eip76_rng_write(dev, RNG_CONTROL_REG, RNG_CONTROL_ENABLE_TRNG_MASK);
+}
+
+int32_t eip76_rng_read_rand_buf(void *data, bool wait)
+{
+	uint32_t i, present;
+
+	if (!eip76_dev.base) /* not initialized */
+		return -1;
+
+	for (i = 0; i < EIP76_RNG_WAIT_ROUNDS; i++) {
+		present = eip76_rng_read(&eip76_dev, RNG_STATUS_REG) &
+					 RNG_REG_STATUS_RDY;
+		if (present || !wait) {
+			break;
+		}
+
+		udelay(10);
+	}
+
+	if (present != 0U) {
+		return 0;
+	}
+
+	memcpy(data,
+	       (void *)(eip76_dev.base + eip76_dev.regs[RNG_OUTPUT_0_REG]),
+	       EIP76_RNG_OUTPUT_SIZE);
+
+	eip76_rng_write(&eip76_dev, RNG_INTACK_REG, RNG_REG_INTACK_RDY_MASK);
+
+	return EIP76_RNG_OUTPUT_SIZE;
+}
+
+int32_t eip76_rng_probe(uintptr_t base_addr)
+{
+	uint32_t ver;
+
+	eip76_dev.base = base_addr;
+	eip76_dev.regs = reg_map_eip76;
+
+	eip76_rng_init(&eip76_dev);
+
+	ver = eip76_rng_read(&eip76_dev, RNG_REV_REG);
+
+	INFO("%s Random Number Generator HW ver. %01x.%01x.%01x\n",
+	     RNG_HW_IS_EIP76(ver) ? "TRNG-IP-76" : "Unknown",
+	     RNG_HW_VER_MAJOR(ver), RNG_HW_VER_MINOR(ver),
+	     RNG_HW_VER_PATCH(ver));
+
+	return 0;
+}
+
+int32_t eip76_rng_get_random(uint8_t *data, uint32_t len)
+{
+	static uint8_t rand[EIP76_RNG_OUTPUT_SIZE];
+	static uint8_t pos;
+	uint32_t i;
+	int32_t ret = 0;
+
+	if (!data)
+		return -1;
+
+	spin_lock(&rng_lock);
+
+	for (i = 0; i < len; i++) {
+		if (pos >= EIP76_RNG_OUTPUT_SIZE) {
+			pos = 0;
+		}
+
+		if (pos != 0U) {
+			ret = eip76_rng_read_rand_buf(rand, true);
+		}
+
+		/* Only advance FIFO index if it is non zero or
+		 * the update from TRNG HW was successful
+		 */
+		if (pos || ret > 0) {
+			data[i] = rand[pos++];
+			ret = 0;
+		} else {
+			ret = -1;
+			break;
+		}
+	}
+
+	spin_unlock(&rng_lock);
+
+	return ret;
+}
diff --git a/drivers/renesas/common/auth/auth_mod.c b/drivers/renesas/common/auth/auth_mod.c
new file mode 100644
index 0000000..4aa86e2
--- /dev/null
+++ b/drivers/renesas/common/auth/auth_mod.c
@@ -0,0 +1,172 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights
+ * reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <plat/common/platform.h>
+
+#include <platform_def.h>
+#include "rom_api.h"
+
+typedef int32_t(*secure_boot_api_f) (uint32_t a, uint32_t b, void *c);
+extern int32_t rcar_get_certificate(const int32_t name, uint32_t *cert_addr);
+
+#define RCAR_IMAGE_ID_MAX	(10)
+#define RCAR_CERT_MAGIC_NUM	(0xE291F358U)
+#define RCAR_BOOT_KEY_CERT	(0xE6300C00U)
+#define RCAR_BOOT_KEY_CERT_NEW	(0xE6300F00U)
+#define RST_BASE		(0xE6160000U)
+#define RST_MODEMR		(RST_BASE + 0x0060U)
+#define MFISOFTMDR		(0xE6260600U)
+#define MODEMR_MD5_MASK		(0x00000020U)
+#define MODEMR_MD5_SHIFT	(5U)
+#define SOFTMD_BOOTMODE_MASK	(0x00000001U)
+#define SOFTMD_NORMALBOOT	(0x1U)
+
+static secure_boot_api_f secure_boot_api;
+
+int auth_mod_get_parent_id(unsigned int img_id, unsigned int *parent_id)
+{
+	return 1;
+}
+
+int auth_mod_verify_img(unsigned int img_id, void *ptr, unsigned int len)
+{
+	int32_t ret = 0, index = 0;
+	uint32_t cert_addr = 0U;
+	static const struct img_to_cert_t {
+		uint32_t id;
+		int32_t cert;
+		const char *name;
+	} image[RCAR_IMAGE_ID_MAX] = {
+		{ BL31_IMAGE_ID, SOC_FW_CONTENT_CERT_ID, "BL31" },
+		{ BL32_IMAGE_ID, TRUSTED_OS_FW_CONTENT_CERT_ID, "BL32" },
+		{ BL33_IMAGE_ID, NON_TRUSTED_FW_CONTENT_CERT_ID, "BL33" },
+		{ BL332_IMAGE_ID, BL332_CERT_ID, "BL332" },
+		{ BL333_IMAGE_ID, BL333_CERT_ID, "BL333" },
+		{ BL334_IMAGE_ID, BL334_CERT_ID, "BL334" },
+		{ BL335_IMAGE_ID, BL335_CERT_ID, "BL335" },
+		{ BL336_IMAGE_ID, BL336_CERT_ID, "BL336" },
+		{ BL337_IMAGE_ID, BL337_CERT_ID, "BL337" },
+		{ BL338_IMAGE_ID, BL338_CERT_ID, "BL338" },
+	};
+
+#if IMAGE_BL2
+	switch (img_id) {
+	case TRUSTED_KEY_CERT_ID:
+	case SOC_FW_KEY_CERT_ID:
+	case TRUSTED_OS_FW_KEY_CERT_ID:
+	case NON_TRUSTED_FW_KEY_CERT_ID:
+	case BL332_KEY_CERT_ID:
+	case BL333_KEY_CERT_ID:
+	case BL334_KEY_CERT_ID:
+	case BL335_KEY_CERT_ID:
+	case BL336_KEY_CERT_ID:
+	case BL337_KEY_CERT_ID:
+	case BL338_KEY_CERT_ID:
+	case SOC_FW_CONTENT_CERT_ID:
+	case TRUSTED_OS_FW_CONTENT_CERT_ID:
+	case NON_TRUSTED_FW_CONTENT_CERT_ID:
+	case BL332_CERT_ID:
+	case BL333_CERT_ID:
+	case BL334_CERT_ID:
+	case BL335_CERT_ID:
+	case BL336_CERT_ID:
+	case BL337_CERT_ID:
+	case BL338_CERT_ID:
+		return ret;
+	case BL31_IMAGE_ID:
+	case BL32_IMAGE_ID:
+	case BL33_IMAGE_ID:
+	case BL332_IMAGE_ID:
+	case BL333_IMAGE_ID:
+	case BL334_IMAGE_ID:
+	case BL335_IMAGE_ID:
+	case BL336_IMAGE_ID:
+	case BL337_IMAGE_ID:
+	case BL338_IMAGE_ID:
+		goto verify_image;
+	default:
+		return -1;
+	}
+
+verify_image:
+	for (index = 0; index < RCAR_IMAGE_ID_MAX; index++) {
+		if (img_id != image[index].id)
+			continue;
+
+		ret = rcar_get_certificate(image[index].cert, &cert_addr);
+		break;
+	}
+
+	if (ret || (index == RCAR_IMAGE_ID_MAX)) {
+		ERROR("Verification Failed for image id = %d\n", img_id);
+		return ret;
+	}
+#if RCAR_BL2_DCACHE == 1
+	/* clean and disable */
+	write_sctlr_el3(read_sctlr_el3() & ~SCTLR_C_BIT);
+	dcsw_op_all(DCCISW);
+#endif
+	ret = (mmio_read_32(RCAR_BOOT_KEY_CERT_NEW) == RCAR_CERT_MAGIC_NUM) ?
+	    secure_boot_api(RCAR_BOOT_KEY_CERT_NEW, cert_addr, NULL) :
+	    secure_boot_api(RCAR_BOOT_KEY_CERT, cert_addr, NULL);
+	if (ret)
+		ERROR("Verification Failed 0x%x, %s\n", ret, image[index].name);
+
+#if RCAR_BL2_DCACHE == 1
+	/* enable */
+	write_sctlr_el3(read_sctlr_el3() | SCTLR_C_BIT);
+#endif /* RCAR_BL2_DCACHE */
+
+#endif /* IMAGE_BL2 */
+	return ret;
+}
+
+static int32_t normal_boot_verify(uint32_t a, uint32_t b, void *c)
+{
+	return 0;
+}
+
+void auth_mod_init(void)
+{
+#if RCAR_SECURE_BOOT
+	uint32_t soft_md = mmio_read_32(MFISOFTMDR) & SOFTMD_BOOTMODE_MASK;
+	uint32_t md = mmio_read_32(RST_MODEMR) & MODEMR_MD5_MASK;
+	uint32_t lcs, ret;
+
+	secure_boot_api = (secure_boot_api_f) &rcar_rom_secure_boot_api;
+
+	ret = rcar_rom_get_lcs(&lcs);
+	if (ret) {
+		ERROR("BL2: Failed to get the LCS. (%d)\n", ret);
+		panic();
+	}
+
+	switch (lcs) {
+	case LCS_SE:
+		if (soft_md == SOFTMD_NORMALBOOT)
+			secure_boot_api = &normal_boot_verify;
+		break;
+	case LCS_SD:
+		secure_boot_api = &normal_boot_verify;
+		break;
+	default:
+		if (md >> MODEMR_MD5_SHIFT)
+			secure_boot_api = &normal_boot_verify;
+	}
+
+	NOTICE("BL2: %s boot\n",
+	       secure_boot_api == &normal_boot_verify ? "Normal" : "Secure");
+#else
+	NOTICE("BL2: Normal boot\n");
+	secure_boot_api = &normal_boot_verify;
+#endif
+}
diff --git a/drivers/renesas/common/avs/avs_driver.c b/drivers/renesas/common/avs/avs_driver.c
new file mode 100644
index 0000000..2c939cd
--- /dev/null
+++ b/drivers/renesas/common/avs/avs_driver.c
@@ -0,0 +1,630 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+
+#include "avs_driver.h"
+#include "cpg_registers.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+
+#if (AVS_SETTING_ENABLE == 1)
+#if PMIC_ROHM_BD9571
+/* Read PMIC register for debug. 1:enable / 0:disable */
+#define AVS_READ_PMIC_REG_ENABLE	0
+/* The re-try number of times of the AVS setting. */
+#define AVS_RETRY_NUM			(1U)
+#endif /* PMIC_ROHM_BD9571 */
+
+/* Base address of Adaptive Voltage Scaling module registers*/
+#define AVS_BASE			(0xE60A0000U)
+/* Adaptive Dynamic Voltage ADJust Parameter2 registers */
+#define ADVADJP2			(AVS_BASE + 0x013CU)
+
+/* Mask VOLCOND bit in ADVADJP2 registers */
+#define ADVADJP2_VOLCOND_MASK		(0x000001FFU)	/* VOLCOND[8:0] */
+
+#if PMIC_ROHM_BD9571
+/* I2C for DVFS bit in CPG registers for module standby and software reset*/
+#define CPG_SYS_DVFS_BIT		(0x04000000U)
+#endif /* PMIC_ROHM_BD9571 */
+/* ADVFS Module bit in CPG registers for module standby and software reset*/
+#define CPG_SYS_ADVFS_BIT		(0x02000000U)
+
+#if PMIC_ROHM_BD9571
+/* Base address of IICDVFS registers*/
+#define IIC_DVFS_BASE			(0xE60B0000U)
+/* IIC bus data register */
+#define IIC_ICDR			(IIC_DVFS_BASE + 0x0000U)
+/* IIC bus control register */
+#define IIC_ICCR			(IIC_DVFS_BASE + 0x0004U)
+/* IIC bus status register */
+#define IIC_ICSR			(IIC_DVFS_BASE + 0x0008U)
+/* IIC interrupt control register */
+#define IIC_ICIC			(IIC_DVFS_BASE + 0x000CU)
+/* IIC clock control register low */
+#define IIC_ICCL			(IIC_DVFS_BASE + 0x0010U)
+/* IIC clock control register high */
+#define IIC_ICCH			(IIC_DVFS_BASE + 0x0014U)
+
+/* Bit in ICSR register */
+#define ICSR_BUSY			(0x10U)
+#define ICSR_AL				(0x08U)
+#define ICSR_TACK			(0x04U)
+#define ICSR_WAIT			(0x02U)
+#define ICSR_DTE			(0x01U)
+
+/* Bit in ICIC register */
+#define ICIC_TACKE			(0x04U)
+#define ICIC_WAITE			(0x02U)
+#define ICIC_DTEE			(0x01U)
+
+/* I2C bus interface enable */
+#define ICCR_ENABLE			(0x80U)
+/* Start condition */
+#define ICCR_START			(0x94U)
+/* Stop condition */
+#define ICCR_STOP			(0x90U)
+/* Restart condition with change to receive mode change */
+#define ICCR_START_RECV			(0x81U)
+/* Stop condition for receive mode */
+#define ICCR_STOP_RECV			(0xC0U)
+
+/* Low-level period of SCL */
+#define ICCL_FREQ_8p33M			(0x07U)	/* for CP Phy 8.3333MHz */
+#define ICCL_FREQ_10M			(0x09U)	/* for CP Phy 10MHz */
+#define ICCL_FREQ_12p5M			(0x0BU)	/* for CP Phy 12.5MHz */
+#define ICCL_FREQ_16p66M		(0x0EU)	/* for CP Phy 16.6666MHz */
+/* High-level period of SCL */
+#define ICCH_FREQ_8p33M			(0x01U)	/* for CP Phy 8.3333MHz */
+#define ICCH_FREQ_10M			(0x02U)	/* for CP Phy 10MHz */
+#define ICCH_FREQ_12p5M			(0x03U)	/* for CP Phy 12.5MHz */
+#define ICCH_FREQ_16p66M		(0x05U)	/* for CP Phy 16.6666MHz */
+
+/* PMIC */
+/* ROHM BD9571 slave address + (W) */
+#define PMIC_W_SLAVE_ADDRESS		(0x60U)
+/* ROHM BD9571 slave address + (R) */
+#define PMIC_R_SLAVE_ADDRESS		(0x61U)
+/* ROHM BD9571 DVFS SetVID register */
+#define PMIC_DVFS_SETVID		(0x54U)
+#endif /* PMIC_ROHM_BD9571  */
+
+/* Individual information */
+#define EFUSE_AVS0			(0U)
+#define EFUSE_AVS_NUM			ARRAY_SIZE(init_vol_tbl)
+
+typedef struct {
+	uint32_t avs;		/* AVS code */
+	uint8_t vol;		/* Voltage */
+} initial_voltage_t;
+
+static const initial_voltage_t init_vol_tbl[] = {
+	/* AVS code, ROHM BD9571 DVFS SetVID register */
+	{0x00U, 0x53U},		/* AVS0, 0.83V */
+	{0x01U, 0x52U},		/* AVS1, 0.82V */
+	{0x02U, 0x51U},		/* AVS2, 0.81V */
+	{0x04U, 0x50U},		/* AVS3, 0.80V */
+	{0x08U, 0x4FU},		/* AVS4, 0.79V */
+	{0x10U, 0x4EU},		/* AVS5, 0.78V */
+	{0x20U, 0x4DU},		/* AVS6, 0.77V */
+	{0x40U, 0x4CU}		/* AVS7, 0.76V */
+};
+
+#if PMIC_ROHM_BD9571
+/* Kind of AVS settings status */
+typedef enum {
+	avs_status_none = 0,
+	avs_status_init,
+	avs_status_start_condition,
+	avs_status_set_slave_addr,
+	avs_status_write_reg_addr,
+	avs_status_write_reg_data,
+	avs_status_stop_condition,
+	avs_status_end,
+	avs_status_complete,
+	avs_status_al_start,
+	avs_status_al_transfer,
+	avs_status_nack,
+	avs_status_error_stop,
+	ave_status_error_end
+} avs_status_t;
+
+/* Kind of AVS error */
+typedef enum {
+	avs_error_none = 0,
+	avs_error_al,
+	avs_error_nack
+} avs_error_t;
+
+static avs_status_t avs_status;
+static uint32_t avs_retry;
+#endif /* PMIC_ROHM_BD9571  */
+static uint32_t efuse_avs = EFUSE_AVS0;
+
+#if PMIC_ROHM_BD9571
+/* prototype */
+static avs_error_t avs_check_error(void);
+static void avs_set_iic_clock(void);
+#if AVS_READ_PMIC_REG_ENABLE == 1
+static uint8_t avs_read_pmic_reg(uint8_t addr);
+static void avs_poll(uint8_t bit_pos, uint8_t val);
+#endif
+#endif /* PMIC_ROHM_BD9571 */
+#endif /* (AVS_SETTING_ENABLE==1) */
+
+/*
+ * Initialize to enable the AVS setting.
+ */
+void rcar_avs_init(void)
+{
+#if (AVS_SETTING_ENABLE == 1)
+	uint32_t val;
+
+#if PMIC_ROHM_BD9571
+	/* Initialize AVS status */
+	avs_status = avs_status_init;
+#endif /* PMIC_ROHM_BD9571 */
+
+	/* Enable clock supply to ADVFS. */
+	mstpcr_write(CPG_SMSTPCR9, CPG_MSTPSR9, CPG_SYS_ADVFS_BIT);
+
+	/* Read AVS code (Initial values are derived from eFuse) */
+	val = mmio_read_32(ADVADJP2) & ADVADJP2_VOLCOND_MASK;
+
+	for (efuse_avs = 0U; efuse_avs < EFUSE_AVS_NUM; efuse_avs++) {
+		if (val == init_vol_tbl[efuse_avs].avs)
+			break;
+	}
+
+	if (efuse_avs >= EFUSE_AVS_NUM)
+		efuse_avs = EFUSE_AVS0;	/* Not applicable */
+#if PMIC_ROHM_BD9571
+	/* Enable clock supply to DVFS. */
+	mstpcr_write(CPG_SMSTPCR9, CPG_MSTPSR9, CPG_SYS_DVFS_BIT);
+
+	/* Disable I2C module and All internal registers initialized. */
+	mmio_write_8(IIC_ICCR, 0x00U);
+	while ((mmio_read_8(IIC_ICCR) & ICCR_ENABLE) != 0U) {
+		/* Disable I2C module and all internal registers initialized. */
+		mmio_write_8(IIC_ICCR, 0x00U);
+	}
+
+	/* Set next status */
+	avs_status = avs_status_start_condition;
+
+#endif /* PMIC_ROHM_BD9571 */
+#endif /* (AVS_SETTING_ENABLE==1) */
+}
+
+/*
+ * Set the value of register corresponding to the voltage
+ * by transfer of I2C to PIMC.
+ */
+void rcar_avs_setting(void)
+{
+#if (AVS_SETTING_ENABLE == 1)
+#if PMIC_ROHM_BD9571
+	avs_error_t err;
+
+	switch (avs_status) {
+	case avs_status_start_condition:
+		/* Set ICCR.ICE=1 to activate the I2C module. */
+		mmio_write_8(IIC_ICCR, mmio_read_8(IIC_ICCR) | ICCR_ENABLE);
+		/* Set frequency of 400kHz */
+		avs_set_iic_clock();
+		/* Set ICIC.TACKE=1, ICIC.WAITE=1, ICIC.DTEE=1 to */
+		/* enable interrupt control.                      */
+		mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
+			     | ICIC_TACKE | ICIC_WAITE | ICIC_DTEE);
+		/* Write H'94 in ICCR to issue start condition */
+		mmio_write_8(IIC_ICCR, ICCR_START);
+		/* Set next status */
+		avs_status = avs_status_set_slave_addr;
+		break;
+	case avs_status_set_slave_addr:
+		/* Check error. */
+		err = avs_check_error();
+		if (err == avs_error_al) {
+			/* Recovery sequence of just after start. */
+			avs_status = avs_status_al_start;
+		} else if (err == avs_error_nack) {
+			/* Recovery sequence of detected NACK */
+			avs_status = avs_status_nack;
+		} else {
+			/* Was data transmission enabled ? */
+			if ((mmio_read_8(IIC_ICSR) & ICSR_DTE) == ICSR_DTE) {
+				/* Clear ICIC.DTEE to disable a DTE interrupt */
+				mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
+					     & (uint8_t) (~ICIC_DTEE));
+				/* Send PMIC slave address + (W) */
+				mmio_write_8(IIC_ICDR, PMIC_W_SLAVE_ADDRESS);
+				/* Set next status */
+				avs_status = avs_status_write_reg_addr;
+			}
+		}
+		break;
+	case avs_status_write_reg_addr:
+		/* Check error. */
+		err = avs_check_error();
+		if (err == avs_error_al) {
+			/* Recovery sequence of during data transfer. */
+			avs_status = avs_status_al_transfer;
+		} else if (err == avs_error_nack) {
+			/* Recovery sequence of detected NACK */
+			avs_status = avs_status_nack;
+		} else {
+			/* If wait state after data transmission. */
+			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
+				/* Write PMIC DVFS_SetVID address */
+				mmio_write_8(IIC_ICDR, PMIC_DVFS_SETVID);
+				/* Clear ICSR.WAIT to exit from wait state. */
+				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
+					     & (uint8_t) (~ICSR_WAIT));
+				/* Set next status */
+				avs_status = avs_status_write_reg_data;
+			}
+		}
+		break;
+	case avs_status_write_reg_data:
+		/* Check error. */
+		err = avs_check_error();
+		if (err == avs_error_al) {
+			/* Recovery sequence of during data transfer. */
+			avs_status = avs_status_al_transfer;
+		} else if (err == avs_error_nack) {
+			/* Recovery sequence of detected NACK */
+			avs_status = avs_status_nack;
+		} else {
+			/* If wait state after data transmission. */
+			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
+				/* Dose efuse_avs exceed the number of */
+				/* the tables? */
+				if (efuse_avs >= EFUSE_AVS_NUM) {
+					ERROR("%s%s=%u\n", "AVS number of ",
+					      "eFuse is out of range. number",
+					      efuse_avs);
+					/* Infinite loop */
+					panic();
+				}
+				/* Write PMIC DVFS_SetVID value */
+				mmio_write_8(IIC_ICDR,
+					     init_vol_tbl[efuse_avs].vol);
+				/* Clear ICSR.WAIT to exit from wait state. */
+				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
+					     & (uint8_t) (~ICSR_WAIT));
+				/* Set next status */
+				avs_status = avs_status_stop_condition;
+			}
+		}
+		break;
+	case avs_status_stop_condition:
+		err = avs_check_error();
+		if (err == avs_error_al) {
+			/* Recovery sequence of during data transfer. */
+			avs_status = avs_status_al_transfer;
+		} else if (err == avs_error_nack) {
+			/* Recovery sequence of detected NACK */
+			avs_status = avs_status_nack;
+		} else {
+			/* If wait state after data transmission. */
+			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
+				/* Write H'90 in ICCR to issue stop condition */
+				mmio_write_8(IIC_ICCR, ICCR_STOP);
+				/* Clear ICSR.WAIT to exit from wait state. */
+				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
+					     & (uint8_t) (~ICSR_WAIT));
+				/* Set next status */
+				avs_status = avs_status_end;
+			}
+		}
+		break;
+	case avs_status_end:
+		/* Is this module not busy?. */
+		if ((mmio_read_8(IIC_ICSR) & ICSR_BUSY) == 0U) {
+			/* Set ICCR=H'00 to disable the I2C module. */
+			mmio_write_8(IIC_ICCR, 0x00U);
+			/* Set next status */
+			avs_status = avs_status_complete;
+		}
+		break;
+	case avs_status_al_start:
+		/* Clear ICSR.AL bit */
+		mmio_write_8(IIC_ICSR, (mmio_read_8(IIC_ICSR)
+					& (uint8_t) (~ICSR_AL)));
+		/* Transmit a clock pulse */
+		mmio_write_8(IIC_ICDR, init_vol_tbl[EFUSE_AVS0].vol);
+		/* Set next status */
+		avs_status = avs_status_error_stop;
+		break;
+	case avs_status_al_transfer:
+		/* Clear ICSR.AL bit */
+		mmio_write_8(IIC_ICSR, (mmio_read_8(IIC_ICSR)
+					& (uint8_t) (~ICSR_AL)));
+		/* Set next status */
+		avs_status = avs_status_error_stop;
+		break;
+	case avs_status_nack:
+		/* Write H'90 in ICCR to issue stop condition */
+		mmio_write_8(IIC_ICCR, ICCR_STOP);
+		/* Disable a WAIT and DTEE interrupt. */
+		mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
+			     & (uint8_t) (~(ICIC_WAITE | ICIC_DTEE)));
+		/* Clear ICSR.TACK bit */
+		mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
+			     & (uint8_t) (~ICSR_TACK));
+		/* Set next status */
+		avs_status = ave_status_error_end;
+		break;
+	case avs_status_error_stop:
+		/* If wait state after data transmission. */
+		if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
+			/* Write H'90 in ICCR to issue stop condition */
+			mmio_write_8(IIC_ICCR, ICCR_STOP);
+			/* Clear ICSR.WAIT to exit from wait state. */
+			mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
+				     & (uint8_t) (~ICSR_WAIT));
+			/* Set next status */
+			avs_status = ave_status_error_end;
+		}
+		break;
+	case ave_status_error_end:
+		/* Is this module not busy?. */
+		if ((mmio_read_8(IIC_ICSR) & ICSR_BUSY) == 0U) {
+			/* Set ICCR=H'00 to disable the I2C module. */
+			mmio_write_8(IIC_ICCR, 0x00U);
+			/* Increment the re-try number of times. */
+			avs_retry++;
+			/* Set start a re-try to status. */
+			avs_status = avs_status_start_condition;
+		}
+		break;
+	case avs_status_complete:
+		/* After "avs_status" became the "avs_status_complete", */
+		/* "avs_setting()" function may be called. */
+		break;
+	default:
+		/* This case is not possible. */
+		ERROR("AVS setting is in invalid status. status=%u\n",
+		      avs_status);
+		/* Infinite loop */
+		panic();
+		break;
+	}
+#endif /* PMIC_ROHM_BD9571 */
+#endif /* (AVS_SETTING_ENABLE==1) */
+}
+
+/*
+ * Finish the AVS setting.
+ */
+void rcar_avs_end(void)
+{
+#if (AVS_SETTING_ENABLE == 1)
+	uint32_t mstp;
+
+#if PMIC_ROHM_BD9571
+	/* While status is not completion, be repeated. */
+	while (avs_status != avs_status_complete)
+		rcar_avs_setting();
+
+	NOTICE("AVS setting succeeded. DVFS_SetVID=0x%x\n",
+	       init_vol_tbl[efuse_avs].vol);
+
+#if AVS_READ_PMIC_REG_ENABLE == 1
+	{
+		uint8_t addr = PMIC_DVFS_SETVID;
+		uint8_t value = avs_read_pmic_reg(addr);
+
+		NOTICE("Read PMIC register. address=0x%x value=0x%x\n",
+		       addr, value);
+	}
+#endif
+
+	/* Bit of the module which wants to disable clock supply. */
+	mstp = CPG_SYS_DVFS_BIT;
+	/* Disables the supply of clock signal to a module. */
+	cpg_write(CPG_SMSTPCR9, mmio_read_32(CPG_SMSTPCR9) | mstp);
+#endif /* PMIC_ROHM_BD9571 */
+
+	/* Bit of the module which wants to disable clock supply. */
+	mstp = CPG_SYS_ADVFS_BIT;
+	/* Disables the supply of clock signal to a module. */
+	cpg_write(CPG_SMSTPCR9, mmio_read_32(CPG_SMSTPCR9) | mstp);
+
+#endif /* (AVS_SETTING_ENABLE==1) */
+}
+
+#if (AVS_SETTING_ENABLE == 1)
+#if PMIC_ROHM_BD9571
+/*
+ * Check error and judge re-try.
+ */
+static avs_error_t avs_check_error(void)
+{
+	avs_error_t ret;
+
+	if ((mmio_read_8(IIC_ICSR) & ICSR_AL) == ICSR_AL) {
+		NOTICE("%s AVS status=%d Retry=%u\n",
+		       "Loss of arbitration is detected.", avs_status, avs_retry);
+		/* Check of retry number of times */
+		if (avs_retry >= AVS_RETRY_NUM) {
+			ERROR("AVS setting failed in retry. max=%u\n",
+			      AVS_RETRY_NUM);
+			/* Infinite loop */
+			panic();
+		}
+		/* Set the error detected to error status. */
+		ret = avs_error_al;
+	} else if ((mmio_read_8(IIC_ICSR) & ICSR_TACK) == ICSR_TACK) {
+		NOTICE("%s AVS status=%d Retry=%u\n",
+		       "Non-acknowledge is detected.", avs_status, avs_retry);
+		/* Check of retry number of times */
+		if (avs_retry >= AVS_RETRY_NUM) {
+			ERROR("AVS setting failed in retry. max=%u\n",
+			      AVS_RETRY_NUM);
+			/* Infinite loop */
+			panic();
+		}
+		/* Set the error detected to error status. */
+		ret = avs_error_nack;
+	} else {
+		/* Not error. */
+		ret = avs_error_none;
+	}
+	return ret;
+}
+
+/*
+ * Set I2C for DVFS clock.
+ */
+static void avs_set_iic_clock(void)
+{
+	uint32_t md_pin;
+
+	/* Read Mode pin register. */
+	md_pin = mmio_read_32(RCAR_MODEMR) & CHECK_MD13_MD14;
+	/* Set the module clock (CP phy) for the IIC-DVFS. */
+	/* CP phy is EXTAL / 2.                            */
+	switch (md_pin) {
+	case MD14_MD13_TYPE_0:	/* EXTAL = 16.6666MHz */
+		mmio_write_8(IIC_ICCL, ICCL_FREQ_8p33M);
+		mmio_write_8(IIC_ICCH, ICCH_FREQ_8p33M);
+		break;
+	case MD14_MD13_TYPE_1:	/* EXTAL = 20MHz */
+		mmio_write_8(IIC_ICCL, ICCL_FREQ_10M);
+		mmio_write_8(IIC_ICCH, ICCH_FREQ_10M);
+		break;
+	case MD14_MD13_TYPE_2:	/* EXTAL = 25MHz (H3/M3) */
+		mmio_write_8(IIC_ICCL, ICCL_FREQ_12p5M);
+		mmio_write_8(IIC_ICCH, ICCH_FREQ_12p5M);
+		break;
+	case MD14_MD13_TYPE_3:	/* EXTAL = 33.3333MHz */
+		mmio_write_8(IIC_ICCL, ICCL_FREQ_16p66M);
+		mmio_write_8(IIC_ICCH, ICCH_FREQ_16p66M);
+		break;
+	default:		/* This case is not possible. */
+		/* CP Phy frequency is to be set for the 16.66MHz */
+		mmio_write_8(IIC_ICCL, ICCL_FREQ_16p66M);
+		mmio_write_8(IIC_ICCH, ICCH_FREQ_16p66M);
+		break;
+	}
+}
+
+#if AVS_READ_PMIC_REG_ENABLE == 1
+/*
+ * Read the value of the register of PMIC.
+ */
+static uint8_t avs_read_pmic_reg(uint8_t addr)
+{
+	uint8_t reg;
+
+	/* Set ICCR.ICE=1 to activate the I2C module. */
+	mmio_write_8(IIC_ICCR, mmio_read_8(IIC_ICCR) | ICCR_ENABLE);
+
+	/* Set frequency of 400kHz */
+	avs_set_iic_clock();
+
+	/*
+	 * Set ICIC.WAITE=1, ICIC.DTEE=1 to enable data transmission
+	 * interrupt and wait interrupt.
+	 */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_WAITE | ICIC_DTEE);
+
+	/* Write H'94 in ICCR to issue start condition */
+	mmio_write_8(IIC_ICCR, ICCR_START);
+
+	/* Wait for a until ICSR.DTE becomes 1. */
+	avs_poll(ICSR_DTE, 1U);
+
+	/* Clear ICIC.DTEE to disable a DTE interrupt. */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
+	/* Send slave address of PMIC */
+	mmio_write_8(IIC_ICDR, PMIC_W_SLAVE_ADDRESS);
+
+	/* Wait for a until ICSR.WAIT becomes 1. */
+	avs_poll(ICSR_WAIT, 1U);
+
+	/* write PMIC address */
+	mmio_write_8(IIC_ICDR, addr);
+	/* Clear ICSR.WAIT to exit from WAIT status. */
+	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
+
+	/* Wait for a until ICSR.WAIT becomes 1. */
+	avs_poll(ICSR_WAIT, 1U);
+
+	/* Write H'94 in ICCR to issue restart condition */
+	mmio_write_8(IIC_ICCR, ICCR_START);
+	/* Clear ICSR.WAIT to exit from WAIT status. */
+	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
+	/* Set ICIC.DTEE=1 to enable data transmission interrupt. */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_DTEE);
+
+	/* Wait for a until ICSR.DTE becomes 1. */
+	avs_poll(ICSR_DTE, 1U);
+
+	/* Clear ICIC.DTEE to disable a DTE interrupt. */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
+	/* Send slave address of PMIC */
+	mmio_write_8(IIC_ICDR, PMIC_R_SLAVE_ADDRESS);
+
+	/* Wait for a until ICSR.WAIT becomes 1. */
+	avs_poll(ICSR_WAIT, 1U);
+
+	/* Write H'81 to ICCR to issue the repeated START condition     */
+	/* for changing the transmission mode to the receive mode.      */
+	mmio_write_8(IIC_ICCR, ICCR_START_RECV);
+	/* Clear ICSR.WAIT to exit from WAIT status. */
+	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
+
+	/* Wait for a until ICSR.WAIT becomes 1. */
+	avs_poll(ICSR_WAIT, 1U);
+
+	/* Set ICCR to H'C0 for the STOP condition */
+	mmio_write_8(IIC_ICCR, ICCR_STOP_RECV);
+	/* Clear ICSR.WAIT to exit from WAIT status. */
+	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
+	/* Set ICIC.DTEE=1 to enable data transmission interrupt. */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_DTEE);
+
+	/* Wait for a until ICSR.DTE becomes 1. */
+	avs_poll(ICSR_DTE, 1U);
+
+	/* Receive DVFS SetVID register */
+	/* Clear ICIC.DTEE to disable a DTE interrupt. */
+	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
+	/* Receive DVFS SetVID register */
+	reg = mmio_read_8(IIC_ICDR);
+
+	/* Wait until ICSR.BUSY is cleared. */
+	avs_poll(ICSR_BUSY, 0U);
+
+	/* Set ICCR=H'00 to disable the I2C module. */
+	mmio_write_8(IIC_ICCR, 0x00U);
+
+	return reg;
+}
+
+/*
+ * Wait processing by the polling.
+ */
+static void avs_poll(uint8_t bit_pos, uint8_t val)
+{
+	uint8_t bit_val = 0U;
+
+	if (val != 0U)
+		bit_val = bit_pos;
+
+	while (1) {
+		if ((mmio_read_8(IIC_ICSR) & bit_pos) == bit_val)
+			break;
+	}
+}
+#endif /* AVS_READ_PMIC_REG_ENABLE */
+#endif /* PMIC_ROHM_BD9571 */
+#endif /* (AVS_SETTING_ENABLE==1) */
diff --git a/drivers/renesas/rcar/avs/avs_driver.h b/drivers/renesas/common/avs/avs_driver.h
similarity index 100%
rename from drivers/renesas/rcar/avs/avs_driver.h
rename to drivers/renesas/common/avs/avs_driver.h
diff --git a/drivers/renesas/common/common.c b/drivers/renesas/common/common.c
new file mode 100644
index 0000000..a0aa480
--- /dev/null
+++ b/drivers/renesas/common/common.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/mmio.h>
+
+#include "cpg_registers.h"
+#include "rcar_private.h"
+
+#if IMAGE_BL31
+void __attribute__ ((section(".system_ram"))) cpg_write(uintptr_t regadr, uint32_t regval)
+#else
+void cpg_write(uintptr_t regadr, uint32_t regval)
+#endif
+{
+	uint32_t value = regval;
+
+	mmio_write_32(CPG_CPGWPR, ~value);
+	mmio_write_32(regadr, value);
+}
+
+#if IMAGE_BL31
+void __attribute__ ((section(".system_ram"))) mstpcr_write(uint32_t mstpcr, uint32_t mstpsr,
+							   uint32_t target_bit)
+#else
+void mstpcr_write(uint32_t mstpcr, uint32_t mstpsr, uint32_t target_bit)
+#endif
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(mstpcr);
+	reg &= ~target_bit;
+	cpg_write(mstpcr, reg);
+	while ((mmio_read_32(mstpsr) & target_bit) != 0U) {
+	}
+}
diff --git a/drivers/renesas/common/console/rcar_console.S b/drivers/renesas/common/console/rcar_console.S
new file mode 100644
index 0000000..b683d7b
--- /dev/null
+++ b/drivers/renesas/common/console/rcar_console.S
@@ -0,0 +1,93 @@
+/*
+ * Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <console_macros.S>
+#include <drivers/renesas/rcar/console/console.h>
+
+	.globl	console_rcar_register
+	.globl	console_rcar_init
+	.globl	console_rcar_putc
+	.globl	console_rcar_flush
+
+	.extern	rcar_log_init
+	.extern	rcar_set_log_data
+
+	/* -----------------------------------------------
+	 * int console_rcar_register(
+	 *      uintptr_t base, uint32_t clk, uint32_t baud,
+	 *      console_t *console)
+	 * Function to initialize and register a new rcar
+	 * console. Storage passed in for the console struct
+	 * *must* be persistent (i.e. not from the stack).
+	 * In: x0 - UART register base address
+	 *     w1 - UART clock in Hz
+	 *     w2 - Baud rate
+	 *     x3 - pointer to empty console_t struct
+	 * Out: return 1 on success, 0 on error
+	 * Clobber list : x0, x1, x2, x6, x7, x14
+	 * -----------------------------------------------
+	 */
+func console_rcar_register
+	mov	x7, x30
+	mov	x6, x3
+	cbz	x6, register_fail
+	str	x0, [x6, #CONSOLE_T_BASE]
+
+	bl	rcar_log_init
+	cbz	x0, register_fail
+
+	mov	x0, x6
+	mov	x30, x7
+	finish_console_register rcar, putc=1, getc=0, flush=1
+
+register_fail:
+	ret	x7
+endfunc console_rcar_register
+
+	/* ---------------------------------------------
+	 * int console_rcar_init(unsigned long base_addr,
+	 * unsigned int uart_clk, unsigned int baud_rate)
+	 * Function to initialize the console without a
+	 * C Runtime to print debug information. This
+	 * function will be accessed by crash reporting.
+	 * In: x0 - console base address
+	 *     w1 - Uart clock in Hz
+	 *     w2 - Baud rate
+	 * Out: return 1 on success
+	 * Clobber list : x1, x2
+	 * ---------------------------------------------
+	 */
+func console_rcar_init
+	mov	w0, #1
+	ret
+endfunc console_rcar_init
+
+	/* --------------------------------------------------------
+	 * int console_rcar_putc(int c, console_t *console)
+	 * Function to output a character over the console. It
+	 * returns the character printed on success or -1 on error.
+	 * In : w0 - character to be printed
+	 *      x1 - pointer to console_t structure
+	 * Out : return -1 on error else return character.
+	 * Clobber list : x2
+	 * --------------------------------------------------------
+	 */
+func console_rcar_putc
+	b	rcar_set_log_data
+endfunc console_rcar_putc
+
+	/* ---------------------------------------------
+	 * void console_rcar_flush(void)
+	 * Function to force a write of all buffered
+	 * data that hasn't been output. It returns void
+	 * Clobber list : x0, x1
+	 * ---------------------------------------------
+	 */
+func console_rcar_flush
+	ret
+endfunc console_rcar_flush
diff --git a/drivers/renesas/common/console/rcar_printf.c b/drivers/renesas/common/console/rcar_printf.c
new file mode 100644
index 0000000..ad074fe
--- /dev/null
+++ b/drivers/renesas/common/console/rcar_printf.c
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdarg.h>
+#include <stdint.h>
+
+#include <platform_def.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/bakery_lock.h>
+
+#include "rcar_def.h"
+#include "rcar_private.h"
+#include "rcar_printf.h"
+
+#define INDEX_TIMER_COUNT	(4U)
+
+#define RCAR_LOG_HEAD	(('T' << 0) | ('L' << 8) | ('O' << 16) | ('G' << 24))
+
+/*
+ * The log is initialized and used before BL31 xlat tables are initialized,
+ * therefore the log memory is a device memory at that point. Make sure the
+ * memory is correclty aligned and accessed only with up-to 32bit, aligned,
+ * writes.
+ */
+CASSERT((RCAR_BL31_LOG_BASE & 0x7) == 0, assert_bl31_log_base_unaligned);
+CASSERT((RCAR_BL31_LOG_MAX & 0x7) == 0, assert_bl31_log_max_unaligned);
+
+extern RCAR_INSTANTIATE_LOCK typedef struct log_head {
+	uint32_t head;
+	uint32_t index;
+	uint32_t size;
+	uint32_t res;
+} loghead_t;
+
+typedef struct log_map {
+	loghead_t header;
+	uint8_t log_data[RCAR_BL31_LOG_MAX];
+	uint8_t res_data[RCAR_LOG_RES_SIZE];
+} logmap_t;
+
+int32_t rcar_set_log_data(int32_t c)
+{
+	logmap_t *t_log;
+
+	t_log = (logmap_t *) RCAR_BL31_LOG_BASE;
+
+	rcar_lock_get();
+
+	/*
+	 * If index is broken, then index and size initialize
+	 */
+	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
+		t_log->header.index = 0U;
+		t_log->header.size = 0U;
+	}
+	/*
+	 * data store to log area then index and size renewal
+	 */
+	t_log->log_data[t_log->header.index] = (uint8_t) c;
+	t_log->header.index++;
+	if (t_log->header.size < t_log->header.index) {
+		t_log->header.size = t_log->header.index;
+	}
+	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
+		t_log->header.index = 0U;
+	}
+
+	rcar_lock_release();
+
+	return 1;
+}
+
+int32_t rcar_log_init(void)
+{
+	logmap_t *t_log = (logmap_t *)RCAR_BL31_LOG_BASE;
+	uint32_t *log_data = (uint32_t *)t_log->log_data;
+	int16_t init_flag = 0;
+	int i;
+
+	if (t_log->header.head != RCAR_LOG_HEAD) {
+		/*
+		 * Log header is not "TLOG", then log area initialize
+		 */
+		init_flag = 1;
+	}
+	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
+		/*
+		 * index is broken, then log area initialize
+		 */
+		init_flag = 1;
+	}
+	if (init_flag == 1) {
+		for (i = 0; i < RCAR_BL31_LOG_MAX; i += 4)
+			*log_data++ = 0;
+
+		t_log->header.head = RCAR_LOG_HEAD;
+		t_log->header.index = 0U;
+		t_log->header.size = 0U;
+	}
+	rcar_lock_init();
+
+	return 1;
+}
diff --git a/drivers/renesas/rcar/console/rcar_printf.h b/drivers/renesas/common/console/rcar_printf.h
similarity index 100%
rename from drivers/renesas/rcar/console/rcar_printf.h
rename to drivers/renesas/common/console/rcar_printf.h
diff --git a/drivers/renesas/rcar/ddr/boot_init_dram.h b/drivers/renesas/common/ddr/boot_init_dram.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/boot_init_dram.h
rename to drivers/renesas/common/ddr/boot_init_dram.h
diff --git a/drivers/renesas/common/ddr/ddr.mk b/drivers/renesas/common/ddr/ddr.mk
new file mode 100644
index 0000000..9483686
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr.mk
@@ -0,0 +1,17 @@
+#
+# Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq ($(RCAR_LSI),$(filter $(RCAR_LSI),${RCAR_E3} ${RZ_G2E}))
+    include drivers/renesas/common/ddr/ddr_a/ddr_a.mk
+    BL2_SOURCES += drivers/renesas/common/ddr/dram_sub_func.c
+else ifeq (${RCAR_LSI},${RCAR_D3})
+    include drivers/renesas/common/ddr/ddr_a/ddr_a.mk
+else ifeq (${RCAR_LSI},${RCAR_V3M})
+    include drivers/renesas/common/ddr/ddr_a/ddr_a.mk
+else
+    include drivers/renesas/common/ddr/ddr_b/ddr_b.mk
+    BL2_SOURCES += drivers/renesas/common/ddr/dram_sub_func.c
+endif
diff --git a/drivers/renesas/rcar/ddr/ddr_a/boot_init_dram_regdef.h b/drivers/renesas/common/ddr/ddr_a/boot_init_dram_regdef.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_a/boot_init_dram_regdef.h
rename to drivers/renesas/common/ddr/ddr_a/boot_init_dram_regdef.h
diff --git a/drivers/renesas/common/ddr/ddr_a/ddr_a.mk b/drivers/renesas/common/ddr/ddr_a/ddr_a.mk
new file mode 100644
index 0000000..cd6433d
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_a/ddr_a.mk
@@ -0,0 +1,13 @@
+#
+# Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq ($(RCAR_LSI),$(filter $(RCAR_LSI),${RCAR_E3} ${RZ_G2E}))
+BL2_SOURCES += drivers/renesas/common/ddr/ddr_a/ddr_init_e3.c
+else ifeq (${RCAR_LSI},${RCAR_D3})
+BL2_SOURCES += drivers/renesas/common/ddr/ddr_a/ddr_init_d3.c
+else
+BL2_SOURCES += drivers/renesas/common/ddr/ddr_a/ddr_init_v3m.c
+endif
diff --git a/drivers/renesas/common/ddr/ddr_a/ddr_init_d3.c b/drivers/renesas/common/ddr/ddr_a/ddr_init_d3.c
new file mode 100644
index 0000000..f0113f1
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_a/ddr_init_d3.c
@@ -0,0 +1,735 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation.
+ * All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+#include <lib/mmio.h>
+#include <common/debug.h>
+#include "rcar_def.h"
+#include "../ddr_regs.h"
+
+#define RCAR_DDR_VERSION	"rev.0.02"
+
+/* Average periodic refresh interval[ns]. Support 3900,7800 */
+#define REFRESH_RATE  3900
+
+
+#if RCAR_LSI != RCAR_D3
+#error "Don't have DDR initialize routine."
+#endif
+
+static void init_ddr_d3_1866(void)
+{
+	uint32_t i, r2, r3, r5, r6, r7, r12;
+
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
+	mmio_write_32(DBSC_DBKIND, 0x00000007);
+	mmio_write_32(DBSC_DBMEMCONF_0_0, 0x0f030a01);
+	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
+	mmio_write_32(DBSC_DBTR0, 0x0000000D);
+	mmio_write_32(DBSC_DBTR1, 0x00000009);
+	mmio_write_32(DBSC_DBTR2, 0x00000000);
+	mmio_write_32(DBSC_DBTR3, 0x0000000D);
+	mmio_write_32(DBSC_DBTR4, 0x000D000D);
+	mmio_write_32(DBSC_DBTR5, 0x0000002D);
+	mmio_write_32(DBSC_DBTR6, 0x00000020);
+	mmio_write_32(DBSC_DBTR7, 0x00060006);
+	mmio_write_32(DBSC_DBTR8, 0x00000021);
+	mmio_write_32(DBSC_DBTR9, 0x00000007);
+	mmio_write_32(DBSC_DBTR10, 0x0000000E);
+	mmio_write_32(DBSC_DBTR11, 0x0000000C);
+	mmio_write_32(DBSC_DBTR12, 0x00140014);
+	mmio_write_32(DBSC_DBTR13, 0x000000F2);
+	mmio_write_32(DBSC_DBTR14, 0x00170006);
+	mmio_write_32(DBSC_DBTR15, 0x00060005);
+	mmio_write_32(DBSC_DBTR16, 0x09210507);
+	mmio_write_32(DBSC_DBTR17, 0x040E0000);
+	mmio_write_32(DBSC_DBTR18, 0x00000200);
+	mmio_write_32(DBSC_DBTR19, 0x0129004B);
+	mmio_write_32(DBSC_DBTR20, 0x020000FB);
+	mmio_write_32(DBSC_DBTR21, 0x00040004);
+	mmio_write_32(DBSC_DBBL, 0x00000000);
+	mmio_write_32(DBSC_DBODT0, 0x00000001);
+	mmio_write_32(DBSC_DBADJ0, 0x00000001);
+	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
+	mmio_write_32(DBSC_DBDFICNT_0, 0x00000010);
+	mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
+	mmio_write_32(DBSC_DBSCHRW1, 0x00000046);
+	mmio_write_32(DBSC_SCFCTST0, 0x0C050B03);
+	mmio_write_32(DBSC_SCFCTST1, 0x0305030C);
+
+	mmio_write_32(DBSC_DBPDLK_0, 0x0000A55A);
+	mmio_write_32(DBSC_DBCMD, 0x01000001);
+	mmio_write_32(DBSC_DBCMD, 0x08000000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x80010000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000008);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000B8000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A04);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000091);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000095);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BBAD);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000099);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A00);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0024641E);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010073);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0C058A00);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A00);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0780C700);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(30)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000004);
+	mmio_write_32(DBSC_DBPDRGD_0,
+		(uint32_t) (REFRESH_RATE * 928 / 125) - 400
+			+ 0x0A300000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000022);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x1000040B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000023);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x35A00D77);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000024);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x2A8A2C28);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000025);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x30005E00);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000026);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0014CB49);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000027);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00000F14);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000028);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00000046);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000029);
+	if (REFRESH_RATE > 3900) {
+		mmio_write_32(DBSC_DBPDRGD_0, 0x00000020);
+	} else {
+		mmio_write_32(DBSC_DBPDRGD_0, 0x000000A0);
+	}
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x81003047);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000020);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00181884);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000001A);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x33C03C10);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A7);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A8);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A9);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C7);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C8);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C9);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000000E);
+	r2 = (mmio_read_32(DBSC_DBPDRGD_0) & 0x0000FF00) >> 0x9;
+	r3 = (r2 << 16) + (r2 << 8) + r2;
+	r6 = (r2 << 24) + (r2 << 16) + (r2 << 8) + r2;
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000011);
+	mmio_write_32(DBSC_DBPDRGD_0, r3);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000012);
+	mmio_write_32(DBSC_DBPDRGD_0, r3);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000016);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000017);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000018);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000019);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010181);
+	mmio_write_32(DBSC_DBCMD, 0x08000001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010601);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	for (i = 0; i < 2; i++) {
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
+		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
+		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
+		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
+
+		if (r6 > 0) {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | r6);
+		} else {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | r7);
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 |
+						     ((r6 + (r5 << 1)) & 0xFF));
+		}
+	}
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
+	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00C0);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010801);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
+	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00D8);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0001F001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
+	r2 = mmio_read_32(DBSC_DBPDRGD_0);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
+	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
+	r2 = mmio_read_32(DBSC_DBPDRGD_0);
+	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x81003087);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010401);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	for (i = 0; i < 2; i++) {
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
+		r5 = ((mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8);
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
+		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
+
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
+		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
+		r12 = (r5 >> 0x2);
+
+		if (r12 < r6) {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r6 - r12) & 0xFF));
+		} else {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | (r7 & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 |
+						     ((r6 + r5 +
+						      (r5 >> 1) + r12) & 0xFF));
+		}
+	}
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00015001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0380C700);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
+	while (mmio_read_32(DBSC_DBPDRGD_0) & BIT(30))
+		;
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0024643E);
+
+	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
+	mmio_write_32(DBSC_DBCALCNF,
+		(uint32_t) (64000000 / REFRESH_RATE) + 0x01000000);
+	mmio_write_32(DBSC_DBRFCNF1,
+		(uint32_t) (REFRESH_RATE * 116 / 125) + 0x00080000);
+	mmio_write_32(DBSC_DBRFCNF2, 0x00010000);
+	mmio_write_32(DBSC_DBDFICUPDCNF, 0x40100001);
+	mmio_write_32(DBSC_DBRFEN, 0x00000001);
+	mmio_write_32(DBSC_DBACEN, 0x00000001);
+	mmio_write_32(DBSC_DBPDLK_0, 0x00000000);
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
+
+#ifdef ddr_qos_init_setting // only for non qos_init
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
+	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
+	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
+	mmio_write_32(DBSC_DBSCHCNT0, 0x000f0037);
+	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
+	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
+	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
+	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00);
+	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00);
+	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000);
+	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000);
+	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300);
+	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0);
+	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200);
+	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS90, 0x00000300);
+	mmio_write_32(DBSC_DBSCHQOS91, 0x000002F0);
+	mmio_write_32(DBSC_DBSCHQOS92, 0x00000200);
+	mmio_write_32(DBSC_DBSCHQOS93, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0);
+	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0);
+	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0);
+	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0);
+	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080);
+	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030);
+	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020);
+	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010);
+	mmio_write_32(0xE67F0018, 0x00000001);
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
+#endif
+}
+
+static void init_ddr_d3_1600(void)
+{
+	uint32_t i, r2, r3, r5, r6, r7, r12;
+
+	mmio_write_32(CPG_CPGWPR, 0x5A5AFFFF);
+	mmio_write_32(CPG_CPGWPCR, 0xA5A50000);
+
+	mmio_write_32(CPG_SRCR4, 0x20000000);
+
+	mmio_write_32(0xE61500DC, 0xe2200000);
+	while (!(mmio_read_32(CPG_PLLECR) & BIT(11)))
+		;
+
+	mmio_write_32(CPG_SRSTCLR4, 0x20000000);
+
+	mmio_write_32(CPG_CPGWPCR, 0xA5A50001);
+
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
+	mmio_write_32(DBSC_DBKIND, 0x00000007);
+	mmio_write_32(DBSC_DBMEMCONF_0_0, 0x0f030a01);
+	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
+	mmio_write_32(DBSC_DBTR0, 0x0000000B);
+	mmio_write_32(DBSC_DBTR1, 0x00000008);
+	mmio_write_32(DBSC_DBTR2, 0x00000000);
+	mmio_write_32(DBSC_DBTR3, 0x0000000B);
+	mmio_write_32(DBSC_DBTR4, 0x000B000B);
+	mmio_write_32(DBSC_DBTR5, 0x00000027);
+	mmio_write_32(DBSC_DBTR6, 0x0000001C);
+	mmio_write_32(DBSC_DBTR7, 0x00060006);
+	mmio_write_32(DBSC_DBTR8, 0x00000020);
+	mmio_write_32(DBSC_DBTR9, 0x00000006);
+	mmio_write_32(DBSC_DBTR10, 0x0000000C);
+	mmio_write_32(DBSC_DBTR11, 0x0000000A);
+	mmio_write_32(DBSC_DBTR12, 0x00120012);
+	mmio_write_32(DBSC_DBTR13, 0x000000CE);
+	mmio_write_32(DBSC_DBTR14, 0x00140005);
+	mmio_write_32(DBSC_DBTR15, 0x00050004);
+	mmio_write_32(DBSC_DBTR16, 0x071F0305);
+	mmio_write_32(DBSC_DBTR17, 0x040C0000);
+	mmio_write_32(DBSC_DBTR18, 0x00000200);
+	mmio_write_32(DBSC_DBTR19, 0x01000040);
+	mmio_write_32(DBSC_DBTR20, 0x020000D6);
+	mmio_write_32(DBSC_DBTR21, 0x00040004);
+	mmio_write_32(DBSC_DBBL, 0x00000000);
+	mmio_write_32(DBSC_DBODT0, 0x00000001);
+	mmio_write_32(DBSC_DBADJ0, 0x00000001);
+	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
+	mmio_write_32(DBSC_DBDFICNT_0, 0x00000010);
+	mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
+	mmio_write_32(DBSC_DBSCHRW1, 0x00000046);
+	mmio_write_32(DBSC_SCFCTST0, 0x0D050B03);
+	mmio_write_32(DBSC_SCFCTST1, 0x0306030C);
+
+	mmio_write_32(DBSC_DBPDLK_0, 0x0000A55A);
+	mmio_write_32(DBSC_DBCMD, 0x01000001);
+	mmio_write_32(DBSC_DBCMD, 0x08000000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x80010000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000008);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000B8000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058904);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000091);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000095);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BBAD);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000099);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058900);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0024641E);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010073);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0C058900);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x04058900);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0780C700);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(30)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000004);
+	mmio_write_32(DBSC_DBPDRGD_0,
+		(uint32_t) (REFRESH_RATE * 792 / 125) - 400 + 0x08B00000);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000022);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x1000040B);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000023);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x2D9C0B66);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000024);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x2A88B400);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000025);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x30005200);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000026);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0014A9C9);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000027);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00000D70);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000028);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00000046);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000029);
+	if (REFRESH_RATE > 3900) {
+		mmio_write_32(DBSC_DBPDRGD_0, 0x00000018);
+	} else {
+		mmio_write_32(DBSC_DBPDRGD_0, 0x00000098);
+	}
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x81003047);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000020);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00181884);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000001A);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x33C03C10);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A7);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A8);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A9);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C7);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C8);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C9);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000000E);
+	r2 = (mmio_read_32(DBSC_DBPDRGD_0) & 0x0000FF00) >> 0x9;
+	r3 = (r2 << 16) + (r2 << 8) + r2;
+	r6 = (r2 << 24) + (r2 << 16) + (r2 << 8) + r2;
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000011);
+	mmio_write_32(DBSC_DBPDRGD_0, r3);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000012);
+	mmio_write_32(DBSC_DBPDRGD_0, r3);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000016);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000017);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000018);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000019);
+	mmio_write_32(DBSC_DBPDRGD_0, r6);
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010181);
+	mmio_write_32(DBSC_DBCMD, 0x08000001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010601);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	for (i = 0; i < 2; i++) {
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
+		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
+		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
+		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
+		if (r6 > 0) {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | r6);
+		} else {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | r7);
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 |
+						     ((r6 + (r5 << 1)) & 0xFF));
+		}
+	}
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
+	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00C0);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010801);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
+	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00D8);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0001F001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
+	r2 = mmio_read_32(DBSC_DBPDRGD_0);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
+	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
+	r2 = mmio_read_32(DBSC_DBPDRGD_0);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
+	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x81003087);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00010401);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	for (i = 0; i < 2; i++) {
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
+		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
+		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
+
+		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
+		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
+		r12 = (r5 >> 0x2);
+
+		if (r12 < r6) {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r6 - r12) & 0xFF));
+		} else {
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 | (r7 & 0x7));
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
+			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
+			mmio_write_32(DBSC_DBPDRGD_0, r2 |
+						     ((r6 + r5 +
+						      (r5 >> 1) + r12) & 0xFF));
+		}
+	}
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x00015001);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
+	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
+		;
+
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0380C700);
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
+	while (mmio_read_32(DBSC_DBPDRGD_0) & BIT(30))
+		;
+	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
+	mmio_write_32(DBSC_DBPDRGD_0, 0x0024643E);
+
+	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
+	mmio_write_32(DBSC_DBCALCNF,
+		(uint32_t) (64000000 / REFRESH_RATE) + 0x01000000);
+	mmio_write_32(DBSC_DBRFCNF1,
+		(uint32_t) (REFRESH_RATE * 99 / 125) + 0x00080000);
+	mmio_write_32(DBSC_DBRFCNF2, 0x00010000);
+	mmio_write_32(DBSC_DBDFICUPDCNF, 0x40100001);
+	mmio_write_32(DBSC_DBRFEN, 0x00000001);
+	mmio_write_32(DBSC_DBACEN, 0x00000001);
+	mmio_write_32(DBSC_DBPDLK_0, 0x00000000);
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
+
+#ifdef ddr_qos_init_setting // only for non qos_init
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
+	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
+	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
+	mmio_write_32(DBSC_DBSCHCNT0, 0x000f0037);
+	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
+	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
+	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
+	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00);
+	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00);
+	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000);
+	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000);
+	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300);
+	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0);
+	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200);
+	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS90, 0x00000300);
+	mmio_write_32(DBSC_DBSCHQOS91, 0x000002F0);
+	mmio_write_32(DBSC_DBSCHQOS92, 0x00000200);
+	mmio_write_32(DBSC_DBSCHQOS93, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100);
+	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0);
+	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0);
+	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0);
+	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0);
+	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080);
+	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040);
+	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030);
+	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020);
+	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010);
+	mmio_write_32(0xE67F0018, 0x00000001);
+	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
+#endif
+}
+
+#define PRR			0xFFF00044U
+#define PRR_PRODUCT_MASK	0x00007F00U
+#define PRR_PRODUCT_D3		0x00005800U
+
+#define	MODEMR_MD19		BIT(19)
+
+int32_t rcar_dram_init(void)
+{
+	uint32_t reg;
+	uint32_t ddr_mbps;
+
+	reg = mmio_read_32(PRR);
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_D3) {
+		ERROR("LSI Product ID (PRR=0x%x) DDR initialize not supported.\n",
+		      reg);
+		panic();
+	}
+
+	reg = mmio_read_32(RST_MODEMR);
+	if (reg & MODEMR_MD19) {
+		init_ddr_d3_1866();
+		ddr_mbps = 1866;
+	} else {
+		init_ddr_d3_1600();
+		ddr_mbps = 1600;
+	}
+
+	NOTICE("BL2: DDR%d(%s)\n", ddr_mbps, RCAR_DDR_VERSION);
+
+	return 0;
+}
diff --git a/drivers/renesas/rcar/ddr/ddr_a/ddr_init_e3.c b/drivers/renesas/common/ddr/ddr_a/ddr_init_e3.c
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_a/ddr_init_e3.c
rename to drivers/renesas/common/ddr/ddr_a/ddr_init_e3.c
diff --git a/drivers/renesas/rcar/ddr/ddr_a/ddr_init_v3m.c b/drivers/renesas/common/ddr/ddr_a/ddr_init_v3m.c
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_a/ddr_init_v3m.c
rename to drivers/renesas/common/ddr/ddr_a/ddr_init_v3m.c
diff --git a/drivers/renesas/common/ddr/ddr_b/boot_init_dram.c b/drivers/renesas/common/ddr/ddr_b/boot_init_dram.c
new file mode 100644
index 0000000..8d002de
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_b/boot_init_dram.c
@@ -0,0 +1,4484 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation.
+ * All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+#include <string.h>
+#include <stdio.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "ddr_regdef.h"
+#include "init_dram_tbl_h3.h"
+#include "init_dram_tbl_m3.h"
+#include "init_dram_tbl_h3ver2.h"
+#include "init_dram_tbl_m3n.h"
+#include "boot_init_dram_regdef.h"
+#include "boot_init_dram.h"
+#include "dram_sub_func.h"
+#include "micro_delay.h"
+#include "rcar_def.h"
+
+#define DDR_BACKUPMODE
+#define FATAL_MSG(x) NOTICE(x)
+
+/* variables */
+#ifdef RCAR_DDR_FIXED_LSI_TYPE
+#ifndef RCAR_AUTO
+#define RCAR_AUTO	99
+#define RCAR_H3		0
+#define RCAR_M3		1
+#define RCAR_M3N	2
+#define RCAR_E3		3	/* NON */
+#define RCAR_H3N	4
+
+#define RZ_G2M		100U
+#define RZ_G2H		101U
+#define RZ_G2N		102U
+
+#define RCAR_CUT_10	0
+#define RCAR_CUT_11	1
+#define RCAR_CUT_20	10
+#define RCAR_CUT_30	20
+#endif
+#ifndef RCAR_LSI
+#define RCAR_LSI	RCAR_AUTO
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO)
+static uint32_t prr_product;
+static uint32_t prr_cut;
+#else
+#if (RCAR_LSI == RCAR_H3)
+static const uint32_t prr_product = PRR_PRODUCT_H3;
+#elif(RCAR_LSI == RCAR_M3 || RCAR_LSI == RZ_G2M)
+static const uint32_t prr_product = PRR_PRODUCT_M3;
+#elif(RCAR_LSI == RCAR_M3N || RCAR_LSI == RZ_G2N)
+static const uint32_t prr_product = PRR_PRODUCT_M3N;
+#elif(RCAR_LSI == RCAR_H3N || RCAR_LSI == RZ_G2H)
+static const uint32_t prr_product = PRR_PRODUCT_H3;
+#endif /* RCAR_LSI */
+
+#ifndef RCAR_LSI_CUT
+static uint32_t prr_cut;
+#else /* RCAR_LSI_CUT */
+#if (RCAR_LSI_CUT == RCAR_CUT_10)
+static const uint32_t prr_cut = PRR_PRODUCT_10;
+#elif(RCAR_LSI_CUT == RCAR_CUT_11)
+static const uint32_t prr_cut = PRR_PRODUCT_11;
+#elif(RCAR_LSI_CUT == RCAR_CUT_20)
+static const uint32_t prr_cut = PRR_PRODUCT_20;
+#elif(RCAR_LSI_CUT == RCAR_CUT_30)
+static const uint32_t prr_cut = PRR_PRODUCT_30;
+#endif /* RCAR_LSI_CUT */
+#endif /* RCAR_LSI_CUT */
+#endif /* RCAR_AUTO_NON */
+#else /* RCAR_DDR_FIXED_LSI_TYPE */
+static uint32_t prr_product;
+static uint32_t prr_cut;
+#endif /* RCAR_DDR_FIXED_LSI_TYPE */
+
+static const uint32_t *p_ddr_regdef_tbl;
+static uint32_t brd_clk;
+static uint32_t brd_clkdiv;
+static uint32_t brd_clkdiva;
+static uint32_t ddr_mbps;
+static uint32_t ddr_mbpsdiv;
+static uint32_t ddr_tccd;
+static uint32_t ddr_phycaslice;
+static const struct _boardcnf *board_cnf;
+static uint32_t ddr_phyvalid;
+static uint32_t ddr_density[DRAM_CH_CNT][CS_CNT];
+static uint32_t ch_have_this_cs[CS_CNT] __aligned(64);
+static uint32_t rdqdm_dly[DRAM_CH_CNT][CSAB_CNT][SLICE_CNT * 2][9];
+static uint32_t max_density;
+static uint32_t ddr0800_mul;
+static uint32_t ddr_mul;
+static uint32_t DDR_PHY_SLICE_REGSET_OFS;
+static uint32_t DDR_PHY_ADR_V_REGSET_OFS;
+static uint32_t DDR_PHY_ADR_I_REGSET_OFS;
+static uint32_t DDR_PHY_ADR_G_REGSET_OFS;
+static uint32_t DDR_PI_REGSET_OFS;
+static uint32_t DDR_PHY_SLICE_REGSET_SIZE;
+static uint32_t DDR_PHY_ADR_V_REGSET_SIZE;
+static uint32_t DDR_PHY_ADR_I_REGSET_SIZE;
+static uint32_t DDR_PHY_ADR_G_REGSET_SIZE;
+static uint32_t DDR_PI_REGSET_SIZE;
+static uint32_t DDR_PHY_SLICE_REGSET_NUM;
+static uint32_t DDR_PHY_ADR_V_REGSET_NUM;
+static uint32_t DDR_PHY_ADR_I_REGSET_NUM;
+static uint32_t DDR_PHY_ADR_G_REGSET_NUM;
+static uint32_t DDR_PI_REGSET_NUM;
+static uint32_t DDR_PHY_ADR_I_NUM;
+#define DDR_PHY_REGSET_MAX 128
+#define DDR_PI_REGSET_MAX 320
+static uint32_t _cnf_DDR_PHY_SLICE_REGSET[DDR_PHY_REGSET_MAX];
+static uint32_t _cnf_DDR_PHY_ADR_V_REGSET[DDR_PHY_REGSET_MAX];
+static uint32_t _cnf_DDR_PHY_ADR_I_REGSET[DDR_PHY_REGSET_MAX];
+static uint32_t _cnf_DDR_PHY_ADR_G_REGSET[DDR_PHY_REGSET_MAX];
+static uint32_t _cnf_DDR_PI_REGSET[DDR_PI_REGSET_MAX];
+static uint32_t pll3_mode;
+static uint32_t loop_max;
+#ifdef DDR_BACKUPMODE
+uint32_t ddr_backup;
+/* #define DDR_BACKUPMODE_HALF           //for Half channel(ch0,1 only) */
+#endif
+
+#ifdef ddr_qos_init_setting	/*  only for non qos_init */
+#define OPERATING_FREQ			(400U)	/* Mhz */
+#define BASE_SUB_SLOT_NUM		(0x6U)
+#define SUB_SLOT_CYCLE			(0x7EU)	/* 126 */
+#define QOSWT_WTSET0_CYCLE		\
+	((SUB_SLOT_CYCLE * BASE_SUB_SLOT_NUM * 1000U) / \
+	OPERATING_FREQ)	/* unit:ns */
+
+uint32_t get_refperiod(void)
+{
+	return QOSWT_WTSET0_CYCLE;
+}
+#else /*  ddr_qos_init_setting // only for non qos_init */
+extern uint32_t get_refperiod(void);
+#endif /* ddr_qos_init_setting // only for non qos_init */
+
+#define _reg_PHY_RX_CAL_X_NUM 11
+static const uint32_t _reg_PHY_RX_CAL_X[_reg_PHY_RX_CAL_X_NUM] = {
+	_reg_PHY_RX_CAL_DQ0,
+	_reg_PHY_RX_CAL_DQ1,
+	_reg_PHY_RX_CAL_DQ2,
+	_reg_PHY_RX_CAL_DQ3,
+	_reg_PHY_RX_CAL_DQ4,
+	_reg_PHY_RX_CAL_DQ5,
+	_reg_PHY_RX_CAL_DQ6,
+	_reg_PHY_RX_CAL_DQ7,
+	_reg_PHY_RX_CAL_DM,
+	_reg_PHY_RX_CAL_DQS,
+	_reg_PHY_RX_CAL_FDBK
+};
+
+#define _reg_PHY_CLK_WRX_SLAVE_DELAY_NUM 10
+static const uint32_t _reg_PHY_CLK_WRX_SLAVE_DELAY
+	[_reg_PHY_CLK_WRX_SLAVE_DELAY_NUM] = {
+	_reg_PHY_CLK_WRDQ0_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ1_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ2_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ3_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ4_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ5_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ6_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQ7_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDM_SLAVE_DELAY,
+	_reg_PHY_CLK_WRDQS_SLAVE_DELAY
+};
+
+#define _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY_NUM 9
+static const uint32_t _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY
+	[_reg_PHY_RDDQS_X_FALL_SLAVE_DELAY_NUM] = {
+	_reg_PHY_RDDQS_DQ0_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ1_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ2_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ3_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ4_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ5_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ6_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ7_FALL_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DM_FALL_SLAVE_DELAY
+};
+
+#define _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY_NUM 9
+static const uint32_t _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
+	[_reg_PHY_RDDQS_X_RISE_SLAVE_DELAY_NUM] = {
+	_reg_PHY_RDDQS_DQ0_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ1_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ2_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ3_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ4_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ5_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ6_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DQ7_RISE_SLAVE_DELAY,
+	_reg_PHY_RDDQS_DM_RISE_SLAVE_DELAY
+};
+
+#define _reg_PHY_PAD_TERM_X_NUM 8
+static const uint32_t _reg_PHY_PAD_TERM_X[_reg_PHY_PAD_TERM_X_NUM] = {
+	_reg_PHY_PAD_FDBK_TERM,
+	_reg_PHY_PAD_DATA_TERM,
+	_reg_PHY_PAD_DQS_TERM,
+	_reg_PHY_PAD_ADDR_TERM,
+	_reg_PHY_PAD_CLK_TERM,
+	_reg_PHY_PAD_CKE_TERM,
+	_reg_PHY_PAD_RST_TERM,
+	_reg_PHY_PAD_CS_TERM
+};
+
+#define _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM 10
+static const uint32_t _reg_PHY_CLK_CACS_SLAVE_DELAY_X
+	[_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM] = {
+	_reg_PHY_ADR0_CLK_WR_SLAVE_DELAY,
+	_reg_PHY_ADR1_CLK_WR_SLAVE_DELAY,
+	_reg_PHY_ADR2_CLK_WR_SLAVE_DELAY,
+	_reg_PHY_ADR3_CLK_WR_SLAVE_DELAY,
+	_reg_PHY_ADR4_CLK_WR_SLAVE_DELAY,
+	_reg_PHY_ADR5_CLK_WR_SLAVE_DELAY,
+
+	_reg_PHY_GRP_SLAVE_DELAY_0,
+	_reg_PHY_GRP_SLAVE_DELAY_1,
+	_reg_PHY_GRP_SLAVE_DELAY_2,
+	_reg_PHY_GRP_SLAVE_DELAY_3
+};
+
+/* Prototypes */
+static inline uint32_t vch_nxt(uint32_t pos);
+static void cpg_write_32(uint32_t a, uint32_t v);
+static void pll3_control(uint32_t high);
+static inline void dsb_sev(void);
+static void wait_dbcmd(void);
+static void send_dbcmd(uint32_t cmd);
+static uint32_t reg_ddrphy_read(uint32_t phyno, uint32_t regadd);
+static void reg_ddrphy_write(uint32_t phyno, uint32_t regadd, uint32_t regdata);
+static void reg_ddrphy_write_a(uint32_t regadd, uint32_t regdata);
+static inline uint32_t ddr_regdef(uint32_t _regdef);
+static inline uint32_t ddr_regdef_adr(uint32_t _regdef);
+static inline uint32_t ddr_regdef_lsb(uint32_t _regdef);
+static void ddr_setval_s(uint32_t ch, uint32_t slice, uint32_t _regdef,
+			 uint32_t val);
+static uint32_t ddr_getval_s(uint32_t ch, uint32_t slice, uint32_t _regdef);
+static void ddr_setval(uint32_t ch, uint32_t regdef, uint32_t val);
+static void ddr_setval_ach_s(uint32_t slice, uint32_t regdef, uint32_t val);
+static void ddr_setval_ach(uint32_t regdef, uint32_t val);
+static void ddr_setval_ach_as(uint32_t regdef, uint32_t val);
+static uint32_t ddr_getval(uint32_t ch, uint32_t regdef);
+static uint32_t ddr_getval_ach(uint32_t regdef, uint32_t *p);
+static uint32_t ddr_getval_ach_as(uint32_t regdef, uint32_t *p);
+static void _tblcopy(uint32_t *to, const uint32_t *from, uint32_t size);
+static void ddrtbl_setval(uint32_t *tbl, uint32_t _regdef, uint32_t val);
+static uint32_t ddrtbl_getval(uint32_t *tbl, uint32_t _regdef);
+static uint32_t ddrphy_regif_chk(void);
+static inline void ddrphy_regif_idle(void);
+static uint16_t _f_scale(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv, uint32_t ps,
+			 uint16_t cyc);
+static void _f_scale_js2(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv,
+			 uint16_t *_js2);
+static int16_t _f_scale_adj(int16_t ps);
+static void ddrtbl_load(void);
+static void ddr_config_sub(void);
+static void get_ca_swizzle(uint32_t ch, uint32_t ddr_csn, uint32_t *p_swz);
+static void ddr_config_sub_h3v1x(void);
+static void ddr_config(void);
+static void dbsc_regset(void);
+static void dbsc_regset_post(void);
+static uint32_t dfi_init_start(void);
+static void change_lpddr4_en(uint32_t mode);
+static uint32_t set_term_code(void);
+static void ddr_register_set(void);
+static inline uint32_t wait_freqchgreq(uint32_t assert);
+static inline void set_freqchgack(uint32_t assert);
+static inline void set_dfifrequency(uint32_t freq);
+static uint32_t pll3_freq(uint32_t on);
+static void update_dly(void);
+static uint32_t pi_training_go(void);
+static uint32_t init_ddr(void);
+static uint32_t swlvl1(uint32_t ddr_csn, uint32_t reg_cs, uint32_t reg_kick);
+static uint32_t wdqdm_man1(void);
+static uint32_t wdqdm_man(void);
+static uint32_t rdqdm_man1(void);
+static uint32_t rdqdm_man(void);
+
+static int32_t _find_change(uint64_t val, uint32_t dir);
+static uint32_t _rx_offset_cal_updn(uint32_t code);
+static uint32_t rx_offset_cal(void);
+static uint32_t rx_offset_cal_hw(void);
+static void adjust_rddqs_latency(void);
+static void adjust_wpath_latency(void);
+
+struct ddrt_data {
+	int32_t init_temp;	/* Initial Temperature (do) */
+	uint32_t init_cal[4];	/* Initial io-code (4 is for H3) */
+	uint32_t tcomp_cal[4];	/* Temp. compensated io-code (4 is for H3) */
+};
+
+static struct ddrt_data tcal;
+
+static void pvtcode_update(void);
+static void pvtcode_update2(void);
+static void ddr_padcal_tcompensate_getinit(uint32_t override);
+
+/* load board configuration */
+#include "boot_init_dram_config.c"
+
+#ifndef DDR_FAST_INIT
+static uint32_t rdqdm_le[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
+static uint32_t rdqdm_te[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
+static uint32_t rdqdm_nw[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
+static uint32_t rdqdm_win[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
+static uint32_t rdqdm_st[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2];
+static void rdqdm_clr1(uint32_t ch, uint32_t ddr_csn);
+static uint32_t rdqdm_ana1(uint32_t ch, uint32_t ddr_csn);
+
+static uint32_t wdqdm_le[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
+static uint32_t wdqdm_te[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
+static uint32_t wdqdm_dly[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
+static uint32_t wdqdm_st[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
+static uint32_t wdqdm_win[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
+static void wdqdm_clr1(uint32_t ch, uint32_t ddr_csn);
+static uint32_t wdqdm_ana1(uint32_t ch, uint32_t ddr_csn);
+#endif/* DDR_FAST_INIT */
+
+/* macro for channel selection loop */
+static inline uint32_t vch_nxt(uint32_t pos)
+{
+	uint32_t posn;
+
+	for (posn = pos; posn < DRAM_CH_CNT; posn++) {
+		if (ddr_phyvalid & (1U << posn))
+			break;
+	}
+	return posn;
+}
+
+#define foreach_vch(ch) \
+for (ch = vch_nxt(0); ch < DRAM_CH_CNT; ch = vch_nxt(ch + 1))
+
+#define foreach_ech(ch) \
+for (ch = 0; ch < DRAM_CH_CNT; ch++)
+
+/* Printing functions */
+#define MSG_LF(...)
+
+/* clock settings, reset control */
+static void cpg_write_32(uint32_t a, uint32_t v)
+{
+	mmio_write_32(CPG_CPGWPR, ~v);
+	mmio_write_32(a, v);
+}
+
+static void pll3_control(uint32_t high)
+{
+	uint32_t data_l, data_div, data_mul, tmp_div;
+
+	if (high) {
+		tmp_div = 3999 * brd_clkdiv * (brd_clkdiva + 1) /
+			(brd_clk * ddr_mul) / 2;
+		data_mul = ((ddr_mul * tmp_div) - 1) << 24;
+		pll3_mode = 1;
+		loop_max = 2;
+	} else {
+		tmp_div = 3999 * brd_clkdiv * (brd_clkdiva + 1) /
+			(brd_clk * ddr0800_mul) / 2;
+		data_mul = ((ddr0800_mul * tmp_div) - 1) << 24;
+		pll3_mode = 0;
+		loop_max = 8;
+	}
+
+	switch (tmp_div) {
+	case 1:
+		data_div = 0;
+		break;
+	case 2:
+	case 3:
+	case 4:
+		data_div = tmp_div;
+		break;
+	default:
+		data_div = 6;
+		data_mul = (data_mul * tmp_div) / 3;
+		break;
+	}
+	data_mul = data_mul | (brd_clkdiva << 7);
+
+	/* PLL3 disable */
+	data_l = mmio_read_32(CPG_PLLECR) & ~CPG_PLLECR_PLL3E_BIT;
+	cpg_write_32(CPG_PLLECR, data_l);
+	dsb_sev();
+
+	if ((prr_product == PRR_PRODUCT_M3) ||
+	    ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_20))) {
+		/* PLL3 DIV resetting(Lowest value:3) */
+		data_l = 0x00030003 | (0xFF80FF80 & mmio_read_32(CPG_FRQCRD));
+		cpg_write_32(CPG_FRQCRD, data_l);
+		dsb_sev();
+
+		/* zb3 clk stop */
+		data_l = CPG_ZB3CKCR_ZB3ST_BIT | mmio_read_32(CPG_ZB3CKCR);
+		cpg_write_32(CPG_ZB3CKCR, data_l);
+		dsb_sev();
+
+		/* PLL3 enable */
+		data_l = CPG_PLLECR_PLL3E_BIT | mmio_read_32(CPG_PLLECR);
+		cpg_write_32(CPG_PLLECR, data_l);
+		dsb_sev();
+
+		do {
+			data_l = mmio_read_32(CPG_PLLECR);
+		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
+		dsb_sev();
+
+		/* PLL3 DIV resetting (Highest value:0) */
+		data_l = (0xFF80FF80 & mmio_read_32(CPG_FRQCRD));
+		cpg_write_32(CPG_FRQCRD, data_l);
+		dsb_sev();
+
+		/* DIV SET KICK */
+		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
+		cpg_write_32(CPG_FRQCRB, data_l);
+		dsb_sev();
+
+		/* PLL3 multiplie set */
+		cpg_write_32(CPG_PLL3CR, data_mul);
+		dsb_sev();
+
+		do {
+			data_l = mmio_read_32(CPG_PLLECR);
+		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
+		dsb_sev();
+
+		/* PLL3 DIV resetting(Target value) */
+		data_l = (data_div << 16) | data_div |
+			 (mmio_read_32(CPG_FRQCRD) & 0xFF80FF80);
+		cpg_write_32(CPG_FRQCRD, data_l);
+		dsb_sev();
+
+		/* DIV SET KICK */
+		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
+		cpg_write_32(CPG_FRQCRB, data_l);
+		dsb_sev();
+
+		do {
+			data_l = mmio_read_32(CPG_PLLECR);
+		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
+		dsb_sev();
+
+		/* zb3 clk start */
+		data_l = (~CPG_ZB3CKCR_ZB3ST_BIT) & mmio_read_32(CPG_ZB3CKCR);
+		cpg_write_32(CPG_ZB3CKCR, data_l);
+		dsb_sev();
+
+	} else { /*  H3Ver.3.0/M3N/V3H */
+
+		/* PLL3 multiplie set */
+		cpg_write_32(CPG_PLL3CR, data_mul);
+		dsb_sev();
+
+		/* PLL3 DIV set(Target value) */
+		data_l = (data_div << 16) | data_div |
+			 (mmio_read_32(CPG_FRQCRD) & 0xFF80FF80);
+		cpg_write_32(CPG_FRQCRD, data_l);
+
+		/* DIV SET KICK */
+		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
+		cpg_write_32(CPG_FRQCRB, data_l);
+		dsb_sev();
+
+		/* PLL3 enable */
+		data_l = CPG_PLLECR_PLL3E_BIT | mmio_read_32(CPG_PLLECR);
+		cpg_write_32(CPG_PLLECR, data_l);
+		dsb_sev();
+
+		do {
+			data_l = mmio_read_32(CPG_PLLECR);
+		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
+		dsb_sev();
+	}
+}
+
+/* barrier */
+static inline void dsb_sev(void)
+{
+	__asm__ __volatile__("dsb sy");
+}
+
+/* DDR memory register access */
+static void wait_dbcmd(void)
+{
+	uint32_t data_l;
+	/* dummy read */
+	data_l = mmio_read_32(DBSC_DBCMD);
+	dsb_sev();
+	while (1) {
+		/* wait DBCMD 1=busy, 0=ready */
+		data_l = mmio_read_32(DBSC_DBWAIT);
+		dsb_sev();
+		if ((data_l & 0x00000001) == 0x00)
+			break;
+	}
+}
+
+static void send_dbcmd(uint32_t cmd)
+{
+	/* dummy read */
+	wait_dbcmd();
+	mmio_write_32(DBSC_DBCMD, cmd);
+	dsb_sev();
+}
+
+static void dbwait_loop(uint32_t wait_loop)
+{
+	uint32_t i;
+
+	for (i = 0; i < wait_loop; i++)
+		wait_dbcmd();
+}
+
+/* DDRPHY register access (raw) */
+static uint32_t reg_ddrphy_read(uint32_t phyno, uint32_t regadd)
+{
+	uint32_t val;
+	uint32_t loop;
+
+	val = 0;
+	if ((prr_product != PRR_PRODUCT_M3N) &&
+	    (prr_product != PRR_PRODUCT_V3H)) {
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
+		dsb_sev();
+
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
+			dsb_sev();
+		}
+		dsb_sev();
+
+		for (loop = 0; loop < loop_max; loop++) {
+			val = mmio_read_32(DBSC_DBPDRGD(phyno));
+			dsb_sev();
+		}
+		(void)val;
+	} else {
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00004000);
+		dsb_sev();
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) !=
+		       (regadd | 0x0000C000)) {
+			dsb_sev();
+		};
+		val = mmio_read_32(DBSC_DBPDRGA(phyno));
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
+			dsb_sev();
+		};
+		dsb_sev();
+
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
+			dsb_sev();
+		};
+
+		dsb_sev();
+		val = mmio_read_32(DBSC_DBPDRGD(phyno));
+		dsb_sev();
+		(void)val;
+	}
+	return val;
+}
+
+static void reg_ddrphy_write(uint32_t phyno, uint32_t regadd, uint32_t regdata)
+{
+	uint32_t val;
+	uint32_t loop;
+
+	if ((prr_product != PRR_PRODUCT_M3N) &&
+	    (prr_product != PRR_PRODUCT_V3H)) {
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
+		dsb_sev();
+		for (loop = 0; loop < loop_max; loop++) {
+			val = mmio_read_32(DBSC_DBPDRGA(phyno));
+			dsb_sev();
+		}
+		mmio_write_32(DBSC_DBPDRGD(phyno), regdata);
+		dsb_sev();
+
+		for (loop = 0; loop < loop_max; loop++) {
+			val = mmio_read_32(DBSC_DBPDRGD(phyno));
+			dsb_sev();
+		}
+	} else {
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
+		dsb_sev();
+
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
+			dsb_sev();
+		};
+		dsb_sev();
+
+		mmio_write_32(DBSC_DBPDRGD(phyno), regdata);
+		dsb_sev();
+
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) !=
+		       (regadd | 0x00008000)) {
+			dsb_sev();
+		};
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
+
+		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
+			dsb_sev();
+		};
+		dsb_sev();
+
+		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
+	}
+	(void)val;
+}
+
+static void reg_ddrphy_write_a(uint32_t regadd, uint32_t regdata)
+{
+	uint32_t ch;
+	uint32_t val;
+	uint32_t loop;
+
+	if ((prr_product != PRR_PRODUCT_M3N) &&
+	    (prr_product != PRR_PRODUCT_V3H)) {
+		foreach_vch(ch) {
+			mmio_write_32(DBSC_DBPDRGA(ch), regadd);
+			dsb_sev();
+		}
+
+		foreach_vch(ch) {
+			mmio_write_32(DBSC_DBPDRGD(ch), regdata);
+			dsb_sev();
+		}
+
+		for (loop = 0; loop < loop_max; loop++) {
+			val = mmio_read_32(DBSC_DBPDRGD(0));
+			dsb_sev();
+		}
+		(void)val;
+	} else {
+		foreach_vch(ch) {
+			reg_ddrphy_write(ch, regadd, regdata);
+			dsb_sev();
+		}
+	}
+}
+
+static inline void ddrphy_regif_idle(void)
+{
+	uint32_t val;
+
+	val = reg_ddrphy_read(0, ddr_regdef_adr(_reg_PI_INT_STATUS));
+	dsb_sev();
+	(void)val;
+}
+
+/* DDRPHY register access (field modify) */
+static inline uint32_t ddr_regdef(uint32_t _regdef)
+{
+	return p_ddr_regdef_tbl[_regdef];
+}
+
+static inline uint32_t ddr_regdef_adr(uint32_t _regdef)
+{
+	return DDR_REGDEF_ADR(p_ddr_regdef_tbl[_regdef]);
+}
+
+static inline uint32_t ddr_regdef_lsb(uint32_t _regdef)
+{
+	return DDR_REGDEF_LSB(p_ddr_regdef_tbl[_regdef]);
+}
+
+static void ddr_setval_s(uint32_t ch, uint32_t slice, uint32_t _regdef,
+			 uint32_t val)
+{
+	uint32_t adr;
+	uint32_t lsb;
+	uint32_t len;
+	uint32_t msk;
+	uint32_t tmp;
+	uint32_t regdef;
+
+	regdef = ddr_regdef(_regdef);
+	adr = DDR_REGDEF_ADR(regdef) + 0x80 * slice;
+	len = DDR_REGDEF_LEN(regdef);
+	lsb = DDR_REGDEF_LSB(regdef);
+	if (len == 0x20)
+		msk = 0xffffffff;
+	else
+		msk = ((1U << len) - 1) << lsb;
+
+	tmp = reg_ddrphy_read(ch, adr);
+	tmp = (tmp & (~msk)) | ((val << lsb) & msk);
+	reg_ddrphy_write(ch, adr, tmp);
+}
+
+static uint32_t ddr_getval_s(uint32_t ch, uint32_t slice, uint32_t _regdef)
+{
+	uint32_t adr;
+	uint32_t lsb;
+	uint32_t len;
+	uint32_t msk;
+	uint32_t tmp;
+	uint32_t regdef;
+
+	regdef = ddr_regdef(_regdef);
+	adr = DDR_REGDEF_ADR(regdef) + 0x80 * slice;
+	len = DDR_REGDEF_LEN(regdef);
+	lsb = DDR_REGDEF_LSB(regdef);
+	if (len == 0x20)
+		msk = 0xffffffff;
+	else
+		msk = ((1U << len) - 1);
+
+	tmp = reg_ddrphy_read(ch, adr);
+	tmp = (tmp >> lsb) & msk;
+
+	return tmp;
+}
+
+static void ddr_setval(uint32_t ch, uint32_t regdef, uint32_t val)
+{
+	ddr_setval_s(ch, 0, regdef, val);
+}
+
+static void ddr_setval_ach_s(uint32_t slice, uint32_t regdef, uint32_t val)
+{
+	uint32_t ch;
+
+	foreach_vch(ch)
+	    ddr_setval_s(ch, slice, regdef, val);
+}
+
+static void ddr_setval_ach(uint32_t regdef, uint32_t val)
+{
+	ddr_setval_ach_s(0, regdef, val);
+}
+
+static void ddr_setval_ach_as(uint32_t regdef, uint32_t val)
+{
+	uint32_t slice;
+
+	for (slice = 0; slice < SLICE_CNT; slice++)
+		ddr_setval_ach_s(slice, regdef, val);
+}
+
+static uint32_t ddr_getval(uint32_t ch, uint32_t regdef)
+{
+	return ddr_getval_s(ch, 0, regdef);
+}
+
+static uint32_t ddr_getval_ach(uint32_t regdef, uint32_t *p)
+{
+	uint32_t ch;
+
+	foreach_vch(ch)
+	    p[ch] = ddr_getval_s(ch, 0, regdef);
+	return p[0];
+}
+
+static uint32_t ddr_getval_ach_as(uint32_t regdef, uint32_t *p)
+{
+	uint32_t ch, slice;
+	uint32_t *pp;
+
+	pp = p;
+	foreach_vch(ch)
+		for (slice = 0; slice < SLICE_CNT; slice++)
+			*pp++ = ddr_getval_s(ch, slice, regdef);
+	return p[0];
+}
+
+/* handling functions for setteing ddrphy value table */
+static void _tblcopy(uint32_t *to, const uint32_t *from, uint32_t size)
+{
+	uint32_t i;
+
+	for (i = 0; i < size; i++) {
+		to[i] = from[i];
+	}
+}
+
+static void ddrtbl_setval(uint32_t *tbl, uint32_t _regdef, uint32_t val)
+{
+	uint32_t adr;
+	uint32_t lsb;
+	uint32_t len;
+	uint32_t msk;
+	uint32_t tmp;
+	uint32_t adrmsk;
+	uint32_t regdef;
+
+	regdef = ddr_regdef(_regdef);
+	adr = DDR_REGDEF_ADR(regdef);
+	len = DDR_REGDEF_LEN(regdef);
+	lsb = DDR_REGDEF_LSB(regdef);
+	if (len == 0x20)
+		msk = 0xffffffff;
+	else
+		msk = ((1U << len) - 1) << lsb;
+
+	if (adr < 0x400) {
+		adrmsk = 0xff;
+	} else {
+		adrmsk = 0x7f;
+	}
+
+	tmp = tbl[adr & adrmsk];
+	tmp = (tmp & (~msk)) | ((val << lsb) & msk);
+	tbl[adr & adrmsk] = tmp;
+}
+
+static uint32_t ddrtbl_getval(uint32_t *tbl, uint32_t _regdef)
+{
+	uint32_t adr;
+	uint32_t lsb;
+	uint32_t len;
+	uint32_t msk;
+	uint32_t tmp;
+	uint32_t adrmsk;
+	uint32_t regdef;
+
+	regdef = ddr_regdef(_regdef);
+	adr = DDR_REGDEF_ADR(regdef);
+	len = DDR_REGDEF_LEN(regdef);
+	lsb = DDR_REGDEF_LSB(regdef);
+	if (len == 0x20)
+		msk = 0xffffffff;
+	else
+		msk = ((1U << len) - 1);
+
+	if (adr < 0x400) {
+		adrmsk = 0xff;
+	} else {
+		adrmsk = 0x7f;
+	}
+
+	tmp = tbl[adr & adrmsk];
+	tmp = (tmp >> lsb) & msk;
+
+	return tmp;
+}
+
+/* DDRPHY register access handling */
+static uint32_t ddrphy_regif_chk(void)
+{
+	uint32_t tmp_ach[DRAM_CH_CNT];
+	uint32_t ch;
+	uint32_t err;
+	uint32_t PI_VERSION_CODE;
+
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
+	    (prr_product == PRR_PRODUCT_M3)) {
+		PI_VERSION_CODE = 0x2041; /* H3 Ver.1.x/M3-W */
+	} else {
+		PI_VERSION_CODE = 0x2040; /* H3 Ver.2.0 or later/M3-N/V3H */
+	}
+
+	ddr_getval_ach(_reg_PI_VERSION, (uint32_t *)tmp_ach);
+	err = 0;
+	foreach_vch(ch) {
+		if (tmp_ach[ch] != PI_VERSION_CODE)
+			err = 1;
+	}
+	return err;
+}
+
+/* functions and parameters for timing setting */
+struct _jedec_spec1 {
+	uint16_t fx3;
+	uint8_t rlwodbi;
+	uint8_t rlwdbi;
+	uint8_t WL;
+	uint8_t nwr;
+	uint8_t nrtp;
+	uint8_t odtlon;
+	uint8_t MR1;
+	uint8_t MR2;
+};
+
+#define JS1_USABLEC_SPEC_LO 2
+#define JS1_USABLEC_SPEC_HI 5
+#define JS1_FREQ_TBL_NUM 8
+#define JS1_MR1(f) (0x04 | ((f) << 4))
+#define JS1_MR2(f) (0x00 | ((f) << 3) | (f))
+const struct _jedec_spec1 js1[JS1_FREQ_TBL_NUM] = {
+	/* 533.333Mbps */
+	{  800,  6,  6,  4,  6,  8, 0, JS1_MR1(0), JS1_MR2(0) | 0x40 },
+	/* 1066.666Mbps */
+	{ 1600, 10, 12,  8, 10,  8, 0, JS1_MR1(1), JS1_MR2(1) | 0x40 },
+	/* 1600.000Mbps */
+	{ 2400, 14, 16, 12, 16,  8, 6, JS1_MR1(2), JS1_MR2(2) | 0x40 },
+	/* 2133.333Mbps */
+	{ 3200, 20, 22, 10, 20,  8, 4, JS1_MR1(3), JS1_MR2(3) },
+	/* 2666.666Mbps */
+	{ 4000, 24, 28, 12, 24, 10, 4, JS1_MR1(4), JS1_MR2(4) },
+	/* 3200.000Mbps */
+	{ 4800, 28, 32, 14, 30, 12, 6, JS1_MR1(5), JS1_MR2(5) },
+	/* 3733.333Mbps */
+	{ 5600, 32, 36, 16, 34, 14, 6, JS1_MR1(6), JS1_MR2(6) },
+	/* 4266.666Mbps */
+	{ 6400, 36, 40, 18, 40, 16, 8, JS1_MR1(7), JS1_MR2(7) }
+};
+
+struct _jedec_spec2 {
+	uint16_t ps;
+	uint16_t cyc;
+};
+
+#define js2_tsr 0
+#define js2_txp 1
+#define js2_trtp 2
+#define js2_trcd 3
+#define js2_trppb 4
+#define js2_trpab 5
+#define js2_tras 6
+#define js2_twr 7
+#define js2_twtr 8
+#define js2_trrd 9
+#define js2_tppd 10
+#define js2_tfaw 11
+#define js2_tdqsck 12
+#define js2_tckehcmd 13
+#define js2_tckelcmd 14
+#define js2_tckelpd 15
+#define js2_tmrr 16
+#define js2_tmrw 17
+#define js2_tmrd 18
+#define js2_tzqcalns 19
+#define js2_tzqlat 20
+#define js2_tiedly 21
+#define js2_tODTon_min 22
+#define JS2_TBLCNT 23
+
+#define js2_trcpb (JS2_TBLCNT)
+#define js2_trcab (JS2_TBLCNT + 1)
+#define js2_trfcab (JS2_TBLCNT + 2)
+#define JS2_CNT (JS2_TBLCNT + 3)
+
+#ifndef JS2_DERATE
+#define JS2_DERATE 0
+#endif
+const struct _jedec_spec2 jedec_spec2[2][JS2_TBLCNT] = {
+	{
+/*tSR   */ {15000, 3},
+/*tXP   */ {7500, 3},
+/*tRTP  */ {7500, 8},
+/*tRCD  */ {18000, 4},
+/*tRPpb */ {18000, 3},
+/*tRPab */ {21000, 3},
+/*tRAS  */ {42000, 3},
+/*tWR   */ {18000, 4},
+/*tWTR  */ {10000, 8},
+/*tRRD  */ {10000, 4},
+/*tPPD  */ {0, 0},
+/*tFAW  */ {40000, 0},
+/*tDQSCK*/ {3500, 0},
+/*tCKEHCMD*/ {7500, 3},
+/*tCKELCMD*/ {7500, 3},
+/*tCKELPD*/ {7500, 3},
+/*tMRR*/ {0, 8},
+/*tMRW*/ {10000, 10},
+/*tMRD*/ {14000, 10},
+/*tZQCALns*/ {1000 * 10, 0},
+/*tZQLAT*/ {30000, 10},
+/*tIEdly*/ {12500, 0},
+/*tODTon_min*/ {1500, 0}
+	 }, {
+/*tSR   */ {15000, 3},
+/*tXP   */ {7500, 3},
+/*tRTP  */ {7500, 8},
+/*tRCD  */ {19875, 4},
+/*tRPpb */ {19875, 3},
+/*tRPab */ {22875, 3},
+/*tRAS  */ {43875, 3},
+/*tWR   */ {18000, 4},
+/*tWTR  */ {10000, 8},
+/*tRRD  */ {11875, 4},
+/*tPPD  */ {0, 0},
+/*tFAW  */ {40000, 0},
+/*tDQSCK*/ {3600, 0},
+/*tCKEHCMD*/ {7500, 3},
+/*tCKELCMD*/ {7500, 3},
+/*tCKELPD*/ {7500, 3},
+/*tMRR*/ {0, 8},
+/*tMRW*/ {10000, 10},
+/*tMRD*/ {14000, 10},
+/*tZQCALns*/ {1000 * 10, 0},
+/*tZQLAT*/ {30000, 10},
+/*tIEdly*/ {12500, 0},
+/*tODTon_min*/ {1500, 0}
+	}
+};
+
+const uint16_t jedec_spec2_trfc_ab[7] = {
+/*	4Gb, 6Gb, 8Gb,12Gb, 16Gb, 24Gb(non), 32Gb(non)	*/
+	 130, 180, 180, 280, 280, 560, 560
+};
+
+static uint32_t js1_ind;
+static uint16_t js2[JS2_CNT];
+static uint8_t RL;
+static uint8_t WL;
+
+static uint16_t _f_scale(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv, uint32_t ps,
+			 uint16_t cyc)
+{
+	uint32_t tmp;
+	uint32_t div;
+
+	tmp = (((uint32_t)(ps) + 9) / 10) * _ddr_mbps;
+	div = tmp / (200000 * _ddr_mbpsdiv);
+	if (tmp != (div * 200000 * _ddr_mbpsdiv))
+		div = div + 1;
+
+	if (div > cyc)
+		return (uint16_t)div;
+	return cyc;
+}
+
+static void _f_scale_js2(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv,
+			 uint16_t *_js2)
+{
+	int i;
+
+	for (i = 0; i < JS2_TBLCNT; i++) {
+		_js2[i] = _f_scale(_ddr_mbps, _ddr_mbpsdiv,
+				  1UL * jedec_spec2[JS2_DERATE][i].ps,
+				  jedec_spec2[JS2_DERATE][i].cyc);
+	}
+
+	_js2[js2_trcpb] = _js2[js2_tras] + _js2[js2_trppb];
+	_js2[js2_trcab] = _js2[js2_tras] + _js2[js2_trpab];
+}
+
+/* scaler for DELAY value */
+static int16_t _f_scale_adj(int16_t ps)
+{
+	int32_t tmp;
+	/*
+	 * tmp = (int32_t)512 * ps * ddr_mbps /2 / ddr_mbpsdiv / 1000 / 1000;
+	 *     = ps * ddr_mbps /2 / ddr_mbpsdiv *512 / 8 / 8 / 125 / 125
+	 *     = ps * ddr_mbps / ddr_mbpsdiv *4 / 125 / 125
+	 */
+	tmp =
+	    (int32_t)4 * (int32_t)ps * (int32_t)ddr_mbps /
+	    (int32_t)ddr_mbpsdiv;
+	tmp = (int32_t)tmp / (int32_t)15625;
+
+	return (int16_t)tmp;
+}
+
+static const uint32_t reg_pi_mr1_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR1_DATA_F0_0,
+	 _reg_PI_MR1_DATA_F0_1,
+	 _reg_PI_MR1_DATA_F0_2,
+	 _reg_PI_MR1_DATA_F0_3},
+	{
+	 _reg_PI_MR1_DATA_F1_0,
+	 _reg_PI_MR1_DATA_F1_1,
+	 _reg_PI_MR1_DATA_F1_2,
+	 _reg_PI_MR1_DATA_F1_3}
+};
+
+static const uint32_t reg_pi_mr2_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR2_DATA_F0_0,
+	 _reg_PI_MR2_DATA_F0_1,
+	 _reg_PI_MR2_DATA_F0_2,
+	 _reg_PI_MR2_DATA_F0_3},
+	{
+	 _reg_PI_MR2_DATA_F1_0,
+	 _reg_PI_MR2_DATA_F1_1,
+	 _reg_PI_MR2_DATA_F1_2,
+	 _reg_PI_MR2_DATA_F1_3}
+};
+
+static const uint32_t reg_pi_mr3_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR3_DATA_F0_0,
+	 _reg_PI_MR3_DATA_F0_1,
+	 _reg_PI_MR3_DATA_F0_2,
+	 _reg_PI_MR3_DATA_F0_3},
+	{
+	 _reg_PI_MR3_DATA_F1_0,
+	 _reg_PI_MR3_DATA_F1_1,
+	 _reg_PI_MR3_DATA_F1_2,
+	 _reg_PI_MR3_DATA_F1_3}
+};
+
+const uint32_t reg_pi_mr11_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR11_DATA_F0_0,
+	 _reg_PI_MR11_DATA_F0_1,
+	 _reg_PI_MR11_DATA_F0_2,
+	 _reg_PI_MR11_DATA_F0_3},
+	{
+	 _reg_PI_MR11_DATA_F1_0,
+	 _reg_PI_MR11_DATA_F1_1,
+	 _reg_PI_MR11_DATA_F1_2,
+	 _reg_PI_MR11_DATA_F1_3}
+};
+
+const uint32_t reg_pi_mr12_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR12_DATA_F0_0,
+	 _reg_PI_MR12_DATA_F0_1,
+	 _reg_PI_MR12_DATA_F0_2,
+	 _reg_PI_MR12_DATA_F0_3},
+	{
+	 _reg_PI_MR12_DATA_F1_0,
+	 _reg_PI_MR12_DATA_F1_1,
+	 _reg_PI_MR12_DATA_F1_2,
+	 _reg_PI_MR12_DATA_F1_3}
+};
+
+const uint32_t reg_pi_mr14_data_fx_csx[2][CSAB_CNT] = {
+	{
+	 _reg_PI_MR14_DATA_F0_0,
+	 _reg_PI_MR14_DATA_F0_1,
+	 _reg_PI_MR14_DATA_F0_2,
+	 _reg_PI_MR14_DATA_F0_3},
+	{
+	 _reg_PI_MR14_DATA_F1_0,
+	 _reg_PI_MR14_DATA_F1_1,
+	 _reg_PI_MR14_DATA_F1_2,
+	 _reg_PI_MR14_DATA_F1_3}
+};
+
+/*
+ * regif pll w/a   ( REGIF H3 Ver.2.0 or later/M3-N/V3H WA )
+ */
+static void regif_pll_wa(void)
+{
+	uint32_t ch;
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		// PLL setting for PHY : H3 Ver.1.x
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_WAIT),
+				   (0x0064U <<
+				    ddr_regdef_lsb(_reg_PHY_PLL_WAIT)));
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL),
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_PLL_CTRL));
+
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LP4_BOOT_PLL_CTRL),
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_LP4_BOOT_PLL_CTRL));
+
+	} else {
+		/*  PLL setting for PHY : M3-W/M3-N/V3H/H3 Ver.2.0 or later */
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_WAIT),
+				   (0x5064U <<
+				    ddr_regdef_lsb(_reg_PHY_PLL_WAIT)));
+
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL),
+				   (ddrtbl_getval
+				    (_cnf_DDR_PHY_ADR_G_REGSET,
+				     _reg_PHY_PLL_CTRL_TOP) << 16) |
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_PLL_CTRL));
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL_CA),
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_PLL_CTRL_CA));
+
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LP4_BOOT_PLL_CTRL),
+				   (ddrtbl_getval
+				    (_cnf_DDR_PHY_ADR_G_REGSET,
+				     _reg_PHY_LP4_BOOT_PLL_CTRL_CA) << 16) |
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_LP4_BOOT_PLL_CTRL));
+		reg_ddrphy_write_a(ddr_regdef_adr
+				   (_reg_PHY_LP4_BOOT_TOP_PLL_CTRL),
+				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+						 _reg_PHY_LP4_BOOT_TOP_PLL_CTRL
+						 ));
+	}
+
+	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LPDDR3_CS),
+			   _cnf_DDR_PHY_ADR_G_REGSET
+			   [ddr_regdef_adr(_reg_PHY_LPDDR3_CS) -
+			   DDR_PHY_ADR_G_REGSET_OFS]);
+
+	/* protect register interface */
+	ddrphy_regif_idle();
+	pll3_control(0);
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		/*  non */
+	} else {
+		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_DLL_RST_EN),
+				   (0x01U <<
+				    ddr_regdef_lsb(_reg_PHY_DLL_RST_EN)));
+		ddrphy_regif_idle();
+	}
+
+	/* init start */
+	/* dbdficnt0:
+	 * dfi_dram_clk_disable=1
+	 * dfi_frequency = 0
+	 * freq_ratio = 01 (2:1)
+	 * init_start =0
+	 */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F10);
+	dsb_sev();
+
+	/* dbdficnt0:
+	 * dfi_dram_clk_disable=1
+	 * dfi_frequency = 0
+	 * freq_ratio = 01 (2:1)
+	 * init_start =1
+	 */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F11);
+	dsb_sev();
+
+	foreach_ech(ch)
+	if ((board_cnf->phyvalid) & BIT(ch))
+		while ((mmio_read_32(DBSC_PLL_LOCK(ch)) & 0x1f) != 0x1f)
+			;
+	dsb_sev();
+}
+
+/* load table data into DDR registers */
+static void ddrtbl_load(void)
+{
+	uint32_t i;
+	uint32_t slice;
+	uint32_t csab;
+	uint32_t adr;
+	uint32_t data_l;
+	uint32_t tmp[3];
+	uint16_t dataS;
+
+	/* TIMING REGISTERS */
+	/* search jedec_spec1 index */
+	for (i = JS1_USABLEC_SPEC_LO; i < JS1_FREQ_TBL_NUM - 1; i++) {
+		if (js1[i].fx3 * 2U * ddr_mbpsdiv >= ddr_mbps * 3U)
+			break;
+	}
+	if (i > JS1_USABLEC_SPEC_HI)
+		js1_ind = JS1_USABLEC_SPEC_HI;
+	else
+		js1_ind = i;
+
+	if (board_cnf->dbi_en)
+		RL = js1[js1_ind].rlwdbi;
+	else
+		RL = js1[js1_ind].rlwodbi;
+
+	WL = js1[js1_ind].WL;
+
+	/* calculate jedec_spec2 */
+	_f_scale_js2(ddr_mbps, ddr_mbpsdiv, js2);
+
+	/* PREPARE TBL */
+	if (prr_product == PRR_PRODUCT_H3) {
+		if (prr_cut <= PRR_PRODUCT_11) {
+			/*  H3 Ver.1.x */
+			_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
+				 DDR_PHY_SLICE_REGSET_H3,
+				 DDR_PHY_SLICE_REGSET_NUM_H3);
+			_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
+				 DDR_PHY_ADR_V_REGSET_H3,
+				 DDR_PHY_ADR_V_REGSET_NUM_H3);
+			_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET,
+				 DDR_PHY_ADR_I_REGSET_H3,
+				 DDR_PHY_ADR_I_REGSET_NUM_H3);
+			_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
+				 DDR_PHY_ADR_G_REGSET_H3,
+				 DDR_PHY_ADR_G_REGSET_NUM_H3);
+			_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_H3,
+				 DDR_PI_REGSET_NUM_H3);
+
+			DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_H3;
+			DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_H3;
+			DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_H3;
+			DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_H3;
+			DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_H3;
+			DDR_PHY_SLICE_REGSET_SIZE =
+			    DDR_PHY_SLICE_REGSET_SIZE_H3;
+			DDR_PHY_ADR_V_REGSET_SIZE =
+			    DDR_PHY_ADR_V_REGSET_SIZE_H3;
+			DDR_PHY_ADR_I_REGSET_SIZE =
+			    DDR_PHY_ADR_I_REGSET_SIZE_H3;
+			DDR_PHY_ADR_G_REGSET_SIZE =
+			    DDR_PHY_ADR_G_REGSET_SIZE_H3;
+			DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_H3;
+			DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_H3;
+			DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_H3;
+			DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_H3;
+			DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_H3;
+			DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_H3;
+
+			DDR_PHY_ADR_I_NUM = 1;
+		} else {
+			/*  H3 Ver.2.0 or later */
+			_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
+				 DDR_PHY_SLICE_REGSET_H3VER2,
+				 DDR_PHY_SLICE_REGSET_NUM_H3VER2);
+			_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
+				 DDR_PHY_ADR_V_REGSET_H3VER2,
+				 DDR_PHY_ADR_V_REGSET_NUM_H3VER2);
+			_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
+				 DDR_PHY_ADR_G_REGSET_H3VER2,
+				 DDR_PHY_ADR_G_REGSET_NUM_H3VER2);
+			_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_H3VER2,
+				 DDR_PI_REGSET_NUM_H3VER2);
+
+			DDR_PHY_SLICE_REGSET_OFS =
+			    DDR_PHY_SLICE_REGSET_OFS_H3VER2;
+			DDR_PHY_ADR_V_REGSET_OFS =
+			    DDR_PHY_ADR_V_REGSET_OFS_H3VER2;
+			DDR_PHY_ADR_G_REGSET_OFS =
+			    DDR_PHY_ADR_G_REGSET_OFS_H3VER2;
+			DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_H3VER2;
+			DDR_PHY_SLICE_REGSET_SIZE =
+			    DDR_PHY_SLICE_REGSET_SIZE_H3VER2;
+			DDR_PHY_ADR_V_REGSET_SIZE =
+			    DDR_PHY_ADR_V_REGSET_SIZE_H3VER2;
+			DDR_PHY_ADR_G_REGSET_SIZE =
+			    DDR_PHY_ADR_G_REGSET_SIZE_H3VER2;
+			DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_H3VER2;
+			DDR_PHY_SLICE_REGSET_NUM =
+			    DDR_PHY_SLICE_REGSET_NUM_H3VER2;
+			DDR_PHY_ADR_V_REGSET_NUM =
+			    DDR_PHY_ADR_V_REGSET_NUM_H3VER2;
+			DDR_PHY_ADR_G_REGSET_NUM =
+			    DDR_PHY_ADR_G_REGSET_NUM_H3VER2;
+			DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_H3VER2;
+
+			DDR_PHY_ADR_I_NUM = 0;
+		}
+	} else if (prr_product == PRR_PRODUCT_M3) {
+		/*  M3-W */
+		_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
+			 DDR_PHY_SLICE_REGSET_M3, DDR_PHY_SLICE_REGSET_NUM_M3);
+		_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
+			 DDR_PHY_ADR_V_REGSET_M3, DDR_PHY_ADR_V_REGSET_NUM_M3);
+		_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET,
+			 DDR_PHY_ADR_I_REGSET_M3, DDR_PHY_ADR_I_REGSET_NUM_M3);
+		_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
+			 DDR_PHY_ADR_G_REGSET_M3, DDR_PHY_ADR_G_REGSET_NUM_M3);
+		_tblcopy(_cnf_DDR_PI_REGSET,
+			 DDR_PI_REGSET_M3, DDR_PI_REGSET_NUM_M3);
+
+		DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_M3;
+		DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_M3;
+		DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_M3;
+		DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_M3;
+		DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_M3;
+		DDR_PHY_SLICE_REGSET_SIZE = DDR_PHY_SLICE_REGSET_SIZE_M3;
+		DDR_PHY_ADR_V_REGSET_SIZE = DDR_PHY_ADR_V_REGSET_SIZE_M3;
+		DDR_PHY_ADR_I_REGSET_SIZE = DDR_PHY_ADR_I_REGSET_SIZE_M3;
+		DDR_PHY_ADR_G_REGSET_SIZE = DDR_PHY_ADR_G_REGSET_SIZE_M3;
+		DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_M3;
+		DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_M3;
+		DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_M3;
+		DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_M3;
+		DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_M3;
+		DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_M3;
+
+		DDR_PHY_ADR_I_NUM = 2;
+	} else {
+		/*  M3-N/V3H */
+		_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
+			 DDR_PHY_SLICE_REGSET_M3N,
+			 DDR_PHY_SLICE_REGSET_NUM_M3N);
+		_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET, DDR_PHY_ADR_V_REGSET_M3N,
+			 DDR_PHY_ADR_V_REGSET_NUM_M3N);
+		_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET, DDR_PHY_ADR_I_REGSET_M3N,
+			 DDR_PHY_ADR_I_REGSET_NUM_M3N);
+		_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET, DDR_PHY_ADR_G_REGSET_M3N,
+			 DDR_PHY_ADR_G_REGSET_NUM_M3N);
+		_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_M3N,
+			 DDR_PI_REGSET_NUM_M3N);
+
+		DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_M3N;
+		DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_M3N;
+		DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_M3N;
+		DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_M3N;
+		DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_M3N;
+		DDR_PHY_SLICE_REGSET_SIZE = DDR_PHY_SLICE_REGSET_SIZE_M3N;
+		DDR_PHY_ADR_V_REGSET_SIZE = DDR_PHY_ADR_V_REGSET_SIZE_M3N;
+		DDR_PHY_ADR_I_REGSET_SIZE = DDR_PHY_ADR_I_REGSET_SIZE_M3N;
+		DDR_PHY_ADR_G_REGSET_SIZE = DDR_PHY_ADR_G_REGSET_SIZE_M3N;
+		DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_M3N;
+		DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_M3N;
+		DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_M3N;
+		DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_M3N;
+		DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_M3N;
+		DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_M3N;
+
+		DDR_PHY_ADR_I_NUM = 2;
+	}
+
+	/* PLL CODE CHANGE */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_11)) {
+		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET, _reg_PHY_PLL_CTRL,
+			      0x1142);
+		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
+			      _reg_PHY_LP4_BOOT_PLL_CTRL, 0x1142);
+	}
+
+	/* on fly gate adjust */
+	if ((prr_product == PRR_PRODUCT_M3) && (prr_cut == PRR_PRODUCT_10)) {
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
+			      _reg_ON_FLY_GATE_ADJUST_EN, 0x00);
+	}
+
+	/* Adjust PI parameters */
+#ifdef _def_LPDDR4_ODT
+	for (i = 0; i < 2; i++) {
+		for (csab = 0; csab < CSAB_CNT; csab++) {
+			ddrtbl_setval(_cnf_DDR_PI_REGSET,
+				      reg_pi_mr11_data_fx_csx[i][csab],
+				      _def_LPDDR4_ODT);
+		}
+	}
+#endif /* _def_LPDDR4_ODT */
+
+#ifdef _def_LPDDR4_VREFCA
+	for (i = 0; i < 2; i++) {
+		for (csab = 0; csab < CSAB_CNT; csab++) {
+			ddrtbl_setval(_cnf_DDR_PI_REGSET,
+				      reg_pi_mr12_data_fx_csx[i][csab],
+				      _def_LPDDR4_VREFCA);
+		}
+	}
+#endif /* _def_LPDDR4_VREFCA */
+	if ((prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 7000, 0) + 7U;
+		if (js2[js2_tiedly] > (RL))
+			js2[js2_tiedly] = RL;
+	} else if ((prr_product == PRR_PRODUCT_H3) &&
+		   (prr_cut > PRR_PRODUCT_11)) {
+		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 9000, 0) + 4U;
+	} else if ((prr_product == PRR_PRODUCT_H3) &&
+		   (prr_cut <= PRR_PRODUCT_11)) {
+		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 10000, 0);
+	}
+
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
+	    (prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		if ((js2[js2_tiedly]) >= 0x1e)
+			dataS = 0x1e;
+		else
+			dataS = js2[js2_tiedly];
+	} else {
+		if ((js2[js2_tiedly]) >= 0x0e)
+			dataS = 0x0e;
+		else
+			dataS = js2[js2_tiedly];
+	}
+
+	ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_RDDATA_EN_DLY, dataS);
+	ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_RDDATA_EN_TSEL_DLY,
+		      (dataS - 2));
+	if ((prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
+			      _reg_PHY_RDDATA_EN_OE_DLY, dataS - 2);
+	}
+	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_RDLAT_ADJ_F1, RL - dataS);
+
+	if (ddrtbl_getval
+	    (_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_WRITE_PATH_LAT_ADD)) {
+		data_l = WL - 1;
+	} else {
+		data_l = WL;
+	}
+	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_ADJ_F1, data_l - 2);
+	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_F1, data_l);
+
+	if (board_cnf->dbi_en) {
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_DBI_MODE,
+			      0x01);
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
+			      _reg_PHY_WDQLVL_DATADM_MASK, 0x000);
+	} else {
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_DBI_MODE,
+			      0x00);
+		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
+			      _reg_PHY_WDQLVL_DATADM_MASK, 0x100);
+	}
+
+	tmp[0] = js1[js1_ind].MR1;
+	tmp[1] = js1[js1_ind].MR2;
+	data_l = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_MR3_DATA_F1_0);
+	if (board_cnf->dbi_en)
+		tmp[2] = data_l | 0xc0;
+	else
+		tmp[2] = data_l & (~0xc0);
+
+	for (i = 0; i < 2; i++) {
+		for (csab = 0; csab < CSAB_CNT; csab++) {
+			ddrtbl_setval(_cnf_DDR_PI_REGSET,
+				      reg_pi_mr1_data_fx_csx[i][csab], tmp[0]);
+			ddrtbl_setval(_cnf_DDR_PI_REGSET,
+				      reg_pi_mr2_data_fx_csx[i][csab], tmp[1]);
+			ddrtbl_setval(_cnf_DDR_PI_REGSET,
+				      reg_pi_mr3_data_fx_csx[i][csab], tmp[2]);
+		}
+	}
+
+	/* DDRPHY INT START */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		/* non */
+	} else {
+		regif_pll_wa();
+		dbwait_loop(5);
+	}
+
+	/* FREQ_SEL_MULTICAST & PER_CS_TRAINING_MULTICAST SET (for safety) */
+	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
+			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
+	ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_MULTICAST_EN, 0x01);
+
+	/* SET DATA SLICE TABLE */
+	for (slice = 0; slice < SLICE_CNT; slice++) {
+		adr =
+		    DDR_PHY_SLICE_REGSET_OFS +
+		    DDR_PHY_SLICE_REGSET_SIZE * slice;
+		for (i = 0; i < DDR_PHY_SLICE_REGSET_NUM; i++) {
+			reg_ddrphy_write_a(adr + i,
+					   _cnf_DDR_PHY_SLICE_REGSET[i]);
+		}
+	}
+
+	/* SET ADR SLICE TABLE */
+	adr = DDR_PHY_ADR_V_REGSET_OFS;
+	for (i = 0; i < DDR_PHY_ADR_V_REGSET_NUM; i++) {
+		reg_ddrphy_write_a(adr + i, _cnf_DDR_PHY_ADR_V_REGSET[i]);
+	}
+
+	if (((prr_product == PRR_PRODUCT_M3) ||
+	     (prr_product == PRR_PRODUCT_M3N)) &&
+	    ((0x00ffffff & (uint32_t)((board_cnf->ch[0].ca_swap) >> 40))
+	    != 0x00)) {
+		adr = DDR_PHY_ADR_I_REGSET_OFS + DDR_PHY_ADR_I_REGSET_SIZE;
+		for (i = 0; i < DDR_PHY_ADR_V_REGSET_NUM; i++) {
+			reg_ddrphy_write_a(adr + i,
+					   _cnf_DDR_PHY_ADR_V_REGSET[i]);
+		}
+		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
+			      _reg_PHY_ADR_DISABLE, 0x02);
+		DDR_PHY_ADR_I_NUM -= 1;
+		ddr_phycaslice = 1;
+
+#ifndef _def_LPDDR4_ODT
+		for (i = 0; i < 2; i++) {
+			for (csab = 0; csab < CSAB_CNT; csab++) {
+				ddrtbl_setval(_cnf_DDR_PI_REGSET,
+					      reg_pi_mr11_data_fx_csx[i][csab],
+					      0x66);
+			}
+		}
+#endif/* _def_LPDDR4_ODT */
+	} else {
+		ddr_phycaslice = 0;
+	}
+
+	if (DDR_PHY_ADR_I_NUM > 0) {
+		for (slice = 0; slice < DDR_PHY_ADR_I_NUM; slice++) {
+			adr =
+			    DDR_PHY_ADR_I_REGSET_OFS +
+			    DDR_PHY_ADR_I_REGSET_SIZE * slice;
+			for (i = 0; i < DDR_PHY_ADR_I_REGSET_NUM; i++) {
+				reg_ddrphy_write_a(adr + i,
+						   _cnf_DDR_PHY_ADR_I_REGSET
+						   [i]);
+			}
+		}
+	}
+
+	/* SET ADRCTRL SLICE TABLE */
+	adr = DDR_PHY_ADR_G_REGSET_OFS;
+	for (i = 0; i < DDR_PHY_ADR_G_REGSET_NUM; i++) {
+		reg_ddrphy_write_a(adr + i, _cnf_DDR_PHY_ADR_G_REGSET[i]);
+	}
+
+	/* SET PI REGISTERS */
+	adr = DDR_PI_REGSET_OFS;
+	for (i = 0; i < DDR_PI_REGSET_NUM; i++) {
+		reg_ddrphy_write_a(adr + i, _cnf_DDR_PI_REGSET[i]);
+	}
+}
+
+/* CONFIGURE DDR REGISTERS */
+static void ddr_config_sub(void)
+{
+	uint32_t i;
+	uint32_t ch, slice;
+	uint32_t data_l;
+	uint32_t tmp;
+	uint8_t high_byte[SLICE_CNT];
+	const uint32_t _par_CALVL_DEVICE_MAP = 1;
+
+	foreach_vch(ch) {
+	/* BOARD SETTINGS (DQ,DM,VREF_DRIVING) */
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			high_byte[slice] =
+			    (board_cnf->ch[ch].dqs_swap >> (4 * slice)) % 2;
+			ddr_setval_s(ch, slice, _reg_PHY_DQ_DM_SWIZZLE0,
+				     board_cnf->ch[ch].dq_swap[slice]);
+			ddr_setval_s(ch, slice, _reg_PHY_DQ_DM_SWIZZLE1,
+				     board_cnf->ch[ch].dm_swap[slice]);
+			if (high_byte[slice]) {
+				/* HIGHER 16 BYTE */
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
+					     0x00);
+			} else {
+				/* LOWER 16 BYTE */
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
+					     0x01);
+			}
+		}
+
+	/* BOARD SETTINGS (CA,ADDR_SEL) */
+		data_l = (0x00ffffff & (uint32_t)(board_cnf->ch[ch].ca_swap)) |
+			0x00888888;
+
+		/* --- ADR_CALVL_SWIZZLE --- */
+		if (prr_product == PRR_PRODUCT_M3) {
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_0, data_l);
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_0,
+				   0x00000000);
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_1, data_l);
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_1,
+				   0x00000000);
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_DEVICE_MAP,
+				   _par_CALVL_DEVICE_MAP);
+		} else {
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0, data_l);
+			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1, 0x00000000);
+			ddr_setval(ch, _reg_PHY_CALVL_DEVICE_MAP,
+				   _par_CALVL_DEVICE_MAP);
+		}
+
+		/* --- ADR_ADDR_SEL --- */
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut > PRR_PRODUCT_11)) {
+			data_l = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
+		} else {
+			data_l = 0;
+			tmp = board_cnf->ch[ch].ca_swap;
+			for (i = 0; i < 6; i++) {
+				data_l |= ((tmp & 0x0f) << (i * 5));
+				tmp = tmp >> 4;
+			}
+		}
+		ddr_setval(ch, _reg_PHY_ADR_ADDR_SEL, data_l);
+		if (ddr_phycaslice == 1) {
+			/* ----------- adr slice2 swap ----------- */
+			tmp  = (uint32_t)((board_cnf->ch[ch].ca_swap) >> 40);
+			data_l = (tmp & 0x00ffffff) | 0x00888888;
+
+			/* --- ADR_CALVL_SWIZZLE --- */
+			if (prr_product == PRR_PRODUCT_M3) {
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE0_0,
+					     data_l);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE1_0,
+					     0x00000000);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE0_1,
+					     data_l);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE1_1,
+					     0x00000000);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_DEVICE_MAP,
+					     _par_CALVL_DEVICE_MAP);
+			} else {
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE0,
+					     data_l);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_ADR_CALVL_SWIZZLE1,
+					     0x00000000);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_CALVL_DEVICE_MAP,
+					     _par_CALVL_DEVICE_MAP);
+			}
+
+			/* --- ADR_ADDR_SEL --- */
+			data_l = 0;
+			for (i = 0; i < 6; i++) {
+				data_l |= ((tmp & 0x0f) << (i * 5));
+				tmp = tmp >> 4;
+			}
+
+			ddr_setval_s(ch, 2, _reg_PHY_ADR_ADDR_SEL, data_l);
+		}
+
+	/* BOARD SETTINGS (BYTE_ORDER_SEL) */
+		if (prr_product == PRR_PRODUCT_M3) {
+			/* --- DATA_BYTE_SWAP --- */
+			data_l = 0;
+			tmp = board_cnf->ch[ch].dqs_swap;
+			for (i = 0; i < 4; i++) {
+				data_l |= ((tmp & 0x03) << (i * 2));
+				tmp = tmp >> 4;
+			}
+		} else {
+			/* --- DATA_BYTE_SWAP --- */
+			data_l = board_cnf->ch[ch].dqs_swap;
+			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_EN, 0x01);
+			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE0,
+				   (data_l) & 0x0f);
+			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE1,
+				   (data_l >> 4 * 1) & 0x0f);
+			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE2,
+				   (data_l >> 4 * 2) & 0x0f);
+			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE3,
+				   (data_l >> 4 * 3) & 0x0f);
+
+			ddr_setval(ch, _reg_PHY_DATA_BYTE_ORDER_SEL_HIGH, 0x00);
+		}
+		ddr_setval(ch, _reg_PHY_DATA_BYTE_ORDER_SEL, data_l);
+	}
+}
+
+static void get_ca_swizzle(uint32_t ch, uint32_t ddr_csn, uint32_t *p_swz)
+{
+	uint32_t slice;
+	uint32_t tmp;
+	uint32_t tgt;
+
+	if (ddr_csn / 2) {
+		tgt = 3;
+	} else {
+		tgt = 1;
+	}
+
+	for (slice = 0; slice < SLICE_CNT; slice++) {
+		tmp = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
+		if (tgt == tmp)
+			break;
+	}
+	tmp = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
+	if (slice % 2)
+		tmp |= 0x00888888;
+	*p_swz = tmp;
+}
+
+static void ddr_config_sub_h3v1x(void)
+{
+	uint32_t ch, slice;
+	uint32_t data_l;
+	uint32_t tmp;
+	uint8_t high_byte[SLICE_CNT];
+	uint32_t ca_swizzle;
+	uint32_t ca;
+	uint32_t csmap;
+	uint32_t o_inv;
+	uint32_t inv;
+	uint32_t bit_soc;
+	uint32_t bit_mem;
+	uint32_t j;
+
+	const uint8_t o_mr15 = 0x55;
+	const uint8_t o_mr20 = 0x55;
+	const uint16_t o_mr32_mr40 = 0x5a3c;
+
+	foreach_vch(ch) {
+	/* BOARD SETTINGS (DQ,DM,VREF_DRIVING) */
+		csmap = 0;
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			tmp = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) &
+			      0x0f;
+			high_byte[slice] = tmp % 2;
+			if (tmp == 1 && (slice >= 2))
+				csmap |= 0x05;
+			if (tmp == 3 && (slice >= 2))
+				csmap |= 0x50;
+			ddr_setval_s(ch, slice, _reg_PHY_DQ_SWIZZLING,
+				     board_cnf->ch[ch].dq_swap[slice]);
+			if (high_byte[slice]) {
+				/* HIGHER 16 BYTE */
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
+					     0x00);
+			} else {
+				/* LOWER 16 BYTE */
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
+					     0x01);
+			}
+		}
+	/* BOARD SETTINGS (CA,ADDR_SEL) */
+		ca = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
+		ddr_setval(ch, _reg_PHY_ADR_ADDR_SEL, ca);
+		ddr_setval(ch, _reg_PHY_CALVL_CS_MAP, csmap);
+
+		get_ca_swizzle(ch, 0, &ca_swizzle);
+
+		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_0, ca_swizzle);
+		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_0, 0x00000000);
+		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_1, 0x00000000);
+		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_1, 0x00000000);
+		ddr_setval(ch, _reg_PHY_ADR_CALVL_DEVICE_MAP, 0x01);
+
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			ddr_setval_s(ch, slice, _reg_PI_RDLVL_PATTERN_NUM,
+				     0x01);
+			ddr_setval_s(ch, slice, _reg_PI_RDLVL_PATTERN_START,
+				     0x08);
+
+			if (high_byte[slice])
+				o_inv = o_mr20;
+			else
+				o_inv = o_mr15;
+
+			tmp = board_cnf->ch[ch].dq_swap[slice];
+			inv = 0;
+			j = 0;
+			for (bit_soc = 0; bit_soc < 8; bit_soc++) {
+				bit_mem = (tmp >> (4 * bit_soc)) & 0x0f;
+				j |= (1U << bit_mem);
+				if (o_inv & (1U << bit_mem))
+					inv |= (1U << bit_soc);
+			}
+			data_l = o_mr32_mr40;
+			if (!high_byte[slice])
+				data_l |= (inv << 24);
+			if (high_byte[slice])
+				data_l |= (inv << 16);
+			ddr_setval_s(ch, slice, _reg_PHY_LP4_RDLVL_PATT8,
+				     data_l);
+		}
+	}
+}
+
+static void ddr_config(void)
+{
+	int32_t i;
+	uint32_t ch, slice;
+	uint32_t data_l;
+	uint32_t tmp;
+	int8_t _adj;
+	int16_t adj;
+	uint32_t dq;
+	union {
+		uint32_t ui32[4];
+		uint8_t ui8[16];
+	} patt;
+	uint16_t patm;
+
+	/* configure ddrphy registers */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		ddr_config_sub_h3v1x();
+	} else {	/*  H3 Ver.2.0 or later/M3-N/V3H is same as M3-W */
+		ddr_config_sub();
+	}
+
+	/* WDQ_USER_PATT */
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			patm = 0;
+			for (i = 0; i < 16; i++) {
+				tmp = board_cnf->ch[ch].wdqlvl_patt[i];
+				patt.ui8[i] = tmp & 0xff;
+				if (tmp & 0x100)
+					patm |= (1U << i);
+			}
+			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT0,
+				     patt.ui32[0]);
+			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT1,
+				     patt.ui32[1]);
+			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT2,
+				     patt.ui32[2]);
+			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT3,
+				     patt.ui32[3]);
+			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT4, patm);
+		}
+	}
+
+	/* CACS DLY */
+	data_l = board_cnf->cacs_dly + _f_scale_adj(board_cnf->cacs_dly_adj);
+	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
+			   0x00U);
+	foreach_vch(ch) {
+		for (i = 0; i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM - 4; i++) {
+			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
+			ddrtbl_setval(_cnf_DDR_PHY_ADR_V_REGSET,
+				      _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
+				      data_l + adj);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr
+					 (_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]),
+					_cnf_DDR_PHY_ADR_V_REGSET
+					[ddr_regdef_adr
+					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
+					DDR_PHY_ADR_V_REGSET_OFS]);
+		}
+
+		for (i = (_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM - 4);
+		     i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM; i++) {
+			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
+			ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
+				      _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
+				      data_l + adj);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr
+					 (_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]),
+					_cnf_DDR_PHY_ADR_G_REGSET
+					[ddr_regdef_adr
+					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
+					DDR_PHY_ADR_G_REGSET_OFS]);
+		}
+
+		if (ddr_phycaslice == 1) {
+			for (i = 0; i < 6; i++) {
+				adj = _f_scale_adj
+					(board_cnf->ch[ch].cacs_adj
+					[i +
+					_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM]);
+				ddrtbl_setval(_cnf_DDR_PHY_ADR_V_REGSET,
+					      _reg_PHY_CLK_CACS_SLAVE_DELAY_X
+					      [i],
+					      data_l + adj);
+				reg_ddrphy_write(ch,
+						 ddr_regdef_adr
+					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) +
+					0x0100,
+					_cnf_DDR_PHY_ADR_V_REGSET
+					[ddr_regdef_adr
+					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
+					DDR_PHY_ADR_V_REGSET_OFS]);
+			}
+		}
+	}
+
+	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
+			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
+
+	/* WDQDM DLY */
+	data_l = board_cnf->dqdm_dly_w;
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			for (i = 0; i <= 8; i++) {
+				dq = slice * 8 + i;
+				if (i == 8)
+					_adj = board_cnf->ch[ch].dm_adj_w[slice];
+				else
+					_adj = board_cnf->ch[ch].dq_adj_w[dq];
+				adj = _f_scale_adj(_adj);
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_CLK_WRX_SLAVE_DELAY[i],
+					     data_l + adj);
+			}
+		}
+	}
+
+	/* RDQDM DLY */
+	data_l = board_cnf->dqdm_dly_r;
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			for (i = 0; i <= 8; i++) {
+				dq = slice * 8 + i;
+				if (i == 8)
+					_adj = board_cnf->ch[ch].dm_adj_r[slice];
+				else
+					_adj = board_cnf->ch[ch].dq_adj_r[dq];
+				adj = _f_scale_adj(_adj);
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY
+					     [i], data_l + adj);
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
+					     [i], data_l + adj);
+			}
+		}
+	}
+}
+
+/* DBSC register setting functions */
+static void dbsc_regset_pre(void)
+{
+	uint32_t ch, csab;
+	uint32_t data_l;
+
+	/* PRIMARY SETTINGS */
+	/* LPDDR4, BL=16, DFI interface */
+	mmio_write_32(DBSC_DBKIND, 0x0000000a);
+	mmio_write_32(DBSC_DBBL, 0x00000002);
+	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
+
+	/* FREQRATIO=2 */
+	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
+
+	/* Chanel map (H3 Ver.1.x) */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11))
+		mmio_write_32(DBSC_DBSCHCNT1, 0x00001010);
+
+	/* DRAM SIZE REGISTER:
+	 * set all ranks as density=0(4Gb) for PHY initialization
+	 */
+	foreach_vch(ch) {
+		for (csab = 0; csab < 4; csab++) {
+			mmio_write_32(DBSC_DBMEMCONF(ch, csab),
+				      DBMEMCONF_REGD(0));
+		}
+	}
+
+	if (prr_product == PRR_PRODUCT_M3) {
+		data_l = 0xe4e4e4e4;
+		foreach_ech(ch) {
+			if ((ddr_phyvalid & (1U << ch)))
+				data_l = (data_l & (~(0x000000FF << (ch * 8))))
+				    | (((board_cnf->ch[ch].dqs_swap & 0x0003)
+					| ((board_cnf->ch[ch].dqs_swap & 0x0030)
+					   >> 2)
+					| ((board_cnf->ch[ch].dqs_swap & 0x0300)
+					   >> 4)
+					| ((board_cnf->ch[ch].dqs_swap & 0x3000)
+					   >> 6)) << (ch * 8));
+		}
+		mmio_write_32(DBSC_DBBSWAP, data_l);
+	}
+}
+
+static void dbsc_regset(void)
+{
+	int32_t i;
+	uint32_t ch;
+	uint32_t data_l;
+	uint32_t data_l2;
+	uint32_t tmp[4];
+
+	/* RFC */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_20) &&
+	    (max_density == 0)) {
+		js2[js2_trfcab] =
+		    _f_scale(ddr_mbps, ddr_mbpsdiv,
+			     1UL * jedec_spec2_trfc_ab[1] * 1000, 0);
+	} else {
+		js2[js2_trfcab] =
+		    _f_scale(ddr_mbps, ddr_mbpsdiv,
+			     1UL * jedec_spec2_trfc_ab[max_density] *
+			     1000, 0);
+	}
+
+	/* DBTR0.CL  : RL */
+	mmio_write_32(DBSC_DBTR(0), RL);
+
+	/* DBTR1.CWL : WL */
+	mmio_write_32(DBSC_DBTR(1), WL);
+
+	/* DBTR2.AL  : 0 */
+	mmio_write_32(DBSC_DBTR(2), 0);
+
+	/* DBTR3.TRCD: tRCD */
+	mmio_write_32(DBSC_DBTR(3), js2[js2_trcd]);
+
+	/* DBTR4.TRPA,TRP: tRPab,tRPpb */
+	mmio_write_32(DBSC_DBTR(4), (js2[js2_trpab] << 16) | js2[js2_trppb]);
+
+	/* DBTR5.TRC : use tRCpb */
+	mmio_write_32(DBSC_DBTR(5), js2[js2_trcpb]);
+
+	/* DBTR6.TRAS : tRAS */
+	mmio_write_32(DBSC_DBTR(6), js2[js2_tras]);
+
+	/* DBTR7.TRRD : tRRD */
+	mmio_write_32(DBSC_DBTR(7), (js2[js2_trrd] << 16) | js2[js2_trrd]);
+
+	/* DBTR8.TFAW : tFAW */
+	mmio_write_32(DBSC_DBTR(8), js2[js2_tfaw]);
+
+	/* DBTR9.TRDPR : tRTP */
+	mmio_write_32(DBSC_DBTR(9), js2[js2_trtp]);
+
+	/* DBTR10.TWR : nWR */
+	mmio_write_32(DBSC_DBTR(10), js1[js1_ind].nwr);
+
+	/*
+	 * DBTR11.TRDWR : RL +  BL / 2 + Rounddown(tRPST) + PHY_ODTLoff -
+	 * 		  odtlon + tDQSCK - tODTon,min +
+	 * 		  PCB delay (out+in) + tPHY_ODToff
+	 */
+	mmio_write_32(DBSC_DBTR(11),
+		      RL + (16 / 2) + 1 + 2 - js1[js1_ind].odtlon +
+		      js2[js2_tdqsck] - js2[js2_tODTon_min] +
+		      _f_scale(ddr_mbps, ddr_mbpsdiv, 1300, 0));
+
+	/* DBTR12.TWRRD : WL + 1 + BL/2 + tWTR */
+	data_l = WL + 1 + (16 / 2) + js2[js2_twtr];
+	mmio_write_32(DBSC_DBTR(12), (data_l << 16) | data_l);
+
+	/* DBTR13.TRFCAB : tRFCab */
+	mmio_write_32(DBSC_DBTR(13), (js2[js2_trfcab]));
+
+	/* DBTR14.TCKEHDLL,tCKEH : tCKEHCMD,tCKEHCMD */
+	mmio_write_32(DBSC_DBTR(14),
+		      (js2[js2_tckehcmd] << 16) | (js2[js2_tckehcmd]));
+
+	/* DBTR15.TCKESR,TCKEL : tSR,tCKELPD */
+	mmio_write_32(DBSC_DBTR(15), (js2[js2_tsr] << 16) | (js2[js2_tckelpd]));
+
+	/* DBTR16 */
+	/* WDQL : tphy_wrlat + tphy_wrdata */
+	tmp[0] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_F1);
+	/* DQENLTNCY : tphy_wrlat = WL-2 : PHY_WRITE_PATH_LAT_ADD == 0
+	 *             tphy_wrlat = WL-3 : PHY_WRITE_PATH_LAT_ADD != 0
+	 */
+	tmp[1] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_ADJ_F1);
+	/* DQL : tphy_rdlat + trdata_en */
+	/* it is not important for dbsc */
+	tmp[2] = RL + 16;
+	/* DQIENLTNCY : trdata_en */
+	tmp[3] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_RDLAT_ADJ_F1) - 1;
+	mmio_write_32(DBSC_DBTR(16),
+		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
+
+	/* DBTR24 */
+	/* WRCSLAT = WRLAT -5 */
+	tmp[0] -= 5;
+	/* WRCSGAP = 5 */
+	tmp[1] = 5;
+	/* RDCSLAT = RDLAT_ADJ +2 */
+	if (prr_product == PRR_PRODUCT_M3) {
+		tmp[2] = tmp[3];
+	} else {
+		tmp[2] = tmp[3] + 2;
+	}
+	/* RDCSGAP = 6 */
+	if (prr_product == PRR_PRODUCT_M3) {
+		tmp[3] = 4;
+	} else {
+		tmp[3] = 6;
+	}
+	mmio_write_32(DBSC_DBTR(24),
+		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
+
+	/* DBTR17.TMODRD,TMOD,TRDMR: tMRR,tMRD,(0) */
+	mmio_write_32(DBSC_DBTR(17),
+		      (js2[js2_tmrr] << 24) | (js2[js2_tmrd] << 16));
+
+	/* DBTR18.RODTL, RODTA, WODTL, WODTA : do not use in LPDDR4 */
+	mmio_write_32(DBSC_DBTR(18), 0);
+
+	/* DBTR19.TZQCL, TZQCS : do not use in LPDDR4 */
+	mmio_write_32(DBSC_DBTR(19), 0);
+
+	/* DBTR20.TXSDLL, TXS : tRFCab+tCKEHCMD */
+	data_l = js2[js2_trfcab] + js2[js2_tckehcmd];
+	mmio_write_32(DBSC_DBTR(20), (data_l << 16) | data_l);
+
+	/* DBTR21.TCCD */
+	/* DBTR23.TCCD */
+	/* H3 Ver.1.0 cannot use TBTR23 feature */
+	if (ddr_tccd == 8 &&
+	    !((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_10))
+	    ) {
+		data_l = 8;
+		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
+		mmio_write_32(DBSC_DBTR(23), 0x00000002);
+	} else if (ddr_tccd <= 11) {
+		data_l = 11;
+		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
+		mmio_write_32(DBSC_DBTR(23), 0x00000000);
+	} else {
+		data_l = ddr_tccd;
+		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
+		mmio_write_32(DBSC_DBTR(23), 0x00000000);
+	}
+
+	/* DBTR22.ZQLAT : */
+	data_l = js2[js2_tzqcalns] * 100;	/*  1000 * 1000 ps */
+	data_l = (data_l << 16) | (js2[js2_tzqlat] + 24 + 20);
+	mmio_write_32(DBSC_DBTR(22), data_l);
+
+	/* DBTR25 : do not use in LPDDR4 */
+	mmio_write_32(DBSC_DBTR(25), 0);
+
+	/* DBRNK : */
+	/*
+	 * DBSC_DBRNK2 rkrr
+	 * DBSC_DBRNK3 rkrw
+	 * DBSC_DBRNK4 rkwr
+	 * DBSC_DBRNK5 rkww
+	 */
+#define _par_DBRNK_VAL		(0x7007)
+
+	for (i = 0; i < 4; i++) {
+		data_l = (_par_DBRNK_VAL >> (i * 4)) & 0x0f;
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut > PRR_PRODUCT_11) && (i == 0)) {
+			data_l += 1;
+		}
+		data_l2 = 0;
+		foreach_vch(ch) {
+			data_l2 = data_l2 | (data_l << (4 * ch));
+		}
+		mmio_write_32(DBSC_DBRNK(2 + i), data_l2);
+	}
+	mmio_write_32(DBSC_DBADJ0, 0x00000000);
+
+	/* timing registers for Scheduler */
+	/* SCFCTST0 */
+	/* SCFCTST0 ACT-ACT */
+	tmp[3] = 1UL * js2[js2_trcpb] * 800 * ddr_mbpsdiv / ddr_mbps;
+	/* SCFCTST0 RDA-ACT */
+	tmp[2] =
+	    1UL * ((16 / 2) + js2[js2_trtp] - 8 +
+		   js2[js2_trppb]) * 800 * ddr_mbpsdiv / ddr_mbps;
+	/* SCFCTST0 WRA-ACT */
+	tmp[1] =
+	    1UL * (WL + 1 + (16 / 2) +
+		   js1[js1_ind].nwr) * 800 * ddr_mbpsdiv / ddr_mbps;
+	/* SCFCTST0 PRE-ACT */
+	tmp[0] = 1UL * js2[js2_trppb];
+	mmio_write_32(DBSC_SCFCTST0,
+		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
+
+	/* SCFCTST1 */
+	/* SCFCTST1 RD-WR */
+	tmp[3] =
+	    1UL * (mmio_read_32(DBSC_DBTR(11)) & 0xff) * 800 * ddr_mbpsdiv /
+	    ddr_mbps;
+	/* SCFCTST1 WR-RD */
+	tmp[2] =
+	    1UL * (mmio_read_32(DBSC_DBTR(12)) & 0xff) * 800 * ddr_mbpsdiv /
+	    ddr_mbps;
+	/* SCFCTST1 ACT-RD/WR */
+	tmp[1] = 1UL * js2[js2_trcd] * 800 * ddr_mbpsdiv / ddr_mbps;
+	/* SCFCTST1 ASYNCOFS */
+	tmp[0] = 12;
+	mmio_write_32(DBSC_SCFCTST1,
+		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
+
+	/* DBSCHRW1 */
+	/* DBSCHRW1 SCTRFCAB */
+	tmp[0] = 1UL * js2[js2_trfcab] * 800 * ddr_mbpsdiv / ddr_mbps;
+	data_l = (((mmio_read_32(DBSC_DBTR(16)) & 0x00FF0000) >> 16)
+		 + (mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
+		 + (0x28 * 2)) * 400 * 2 * ddr_mbpsdiv / ddr_mbps + 7;
+	if (tmp[0] < data_l)
+		tmp[0] = data_l;
+
+	if ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30)) {
+		mmio_write_32(DBSC_DBSCHRW1, tmp[0]
+			+ ((mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
+			* 400 * 2 * ddr_mbpsdiv + (ddr_mbps - 1)) /
+			ddr_mbps - 3);
+	} else {
+		mmio_write_32(DBSC_DBSCHRW1, tmp[0]
+			+ ((mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
+			* 400 * 2 * ddr_mbpsdiv + (ddr_mbps - 1)) /
+			ddr_mbps);
+	}
+
+	/* QOS and CAM */
+#ifdef ddr_qos_init_setting	/*  only for non qos_init */
+	/*wbkwait(0004), wbkmdhi(4,2),wbkmdlo(1,8) */
+	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
+	/*0(fillunit),8(dirtymax),4(dirtymin) */
+	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
+	/*stop_tolerance */
+	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
+	/*rd-wr/wr-rd toggle priority */
+	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
+	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
+	mmio_write_32(DBSC_DBSCHCNT0, 0x000F0037);
+
+	/* QoS Settings */
+	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00U);
+	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00U);
+	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000U);
+	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000U);
+	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300U);
+	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0U);
+	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200U);
+	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100U);
+	mmio_write_32(DBSC_DBSCHQOS90, 0x00000100U);
+	mmio_write_32(DBSC_DBSCHQOS91, 0x000000F0U);
+	mmio_write_32(DBSC_DBSCHQOS92, 0x000000A0U);
+	mmio_write_32(DBSC_DBSCHQOS93, 0x00000040U);
+	mmio_write_32(DBSC_DBSCHQOS120, 0x00000040U);
+	mmio_write_32(DBSC_DBSCHQOS121, 0x00000030U);
+	mmio_write_32(DBSC_DBSCHQOS122, 0x00000020U);
+	mmio_write_32(DBSC_DBSCHQOS123, 0x00000010U);
+	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100U);
+	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0U);
+	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0U);
+	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040U);
+	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0U);
+	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0U);
+	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080U);
+	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040U);
+	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040U);
+	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030U);
+	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020U);
+	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* ddr_qos_init_setting */
+	/* H3 Ver.1.1 need to set monitor function */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_11)) {
+		mmio_write_32(DBSC_DBMONCONF4, 0x00700000);
+	}
+
+	if (prr_product == PRR_PRODUCT_H3) {
+		if (prr_cut == PRR_PRODUCT_10) {
+			/* resrdis, simple mode, sc off */
+			mmio_write_32(DBSC_DBBCAMDIS, 0x00000007);
+		} else if (prr_cut == PRR_PRODUCT_11) {
+			/* resrdis, simple mode         */
+			mmio_write_32(DBSC_DBBCAMDIS, 0x00000005);
+		} else if (prr_cut < PRR_PRODUCT_30) {
+			/* H3 Ver.2.0                   */
+			/* resrdis                      */
+			mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
+		} else {	/* H3 Ver.3.0(include H3N)      */
+			/* exprespque                   */
+			mmio_write_32(DBSC_DBBCAMDIS, 0x00000010);
+		}
+	} else {		/* M3-W/M3-N/V3H                */
+		/* resrdis                      */
+		mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
+	}
+}
+
+static void dbsc_regset_post(void)
+{
+	uint32_t ch, cs;
+	uint32_t data_l;
+	uint32_t slice, rdlat_max, rdlat_min;
+
+	rdlat_max = 0;
+	rdlat_min = 0xffff;
+	foreach_vch(ch) {
+		for (cs = 0; cs < CS_CNT; cs++) {
+			if ((ch_have_this_cs[cs] & (1U << ch)) != 0) {
+				for (slice = 0; slice < SLICE_CNT; slice++) {
+					ddr_setval_s(ch, slice,
+						     _reg_PHY_PER_CS_TRAINING_INDEX,
+						     cs);
+					data_l = ddr_getval_s(ch, slice,
+							      _reg_PHY_RDDQS_LATENCY_ADJUST);
+					if (data_l > rdlat_max)
+						rdlat_max = data_l;
+					if (data_l < rdlat_min)
+						rdlat_min = data_l;
+				}
+			}
+		}
+	}
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) {
+#if RCAR_DRAM_SPLIT == 2
+		if (board_cnf->phyvalid == 0x05) {
+			mmio_write_32(DBSC_DBTR(24),
+				      (rdlat_max << 24) + (rdlat_min << 16) +
+				      mmio_read_32(DBSC_DBTR(24)));
+		} else {
+			mmio_write_32(DBSC_DBTR(24),
+				      ((rdlat_max * 2 - rdlat_min + 4) << 24) +
+				      ((rdlat_min + 2) << 16) +
+				      mmio_read_32(DBSC_DBTR(24)));
+		}
+#else /*RCAR_DRAM_SPLIT == 2 */
+		mmio_write_32(DBSC_DBTR(24),
+			      ((rdlat_max * 2 - rdlat_min + 4) << 24) +
+			      ((rdlat_min + 2) << 16) +
+			      mmio_read_32(DBSC_DBTR(24)));
+#endif /*RCAR_DRAM_SPLIT == 2 */
+	} else {
+		mmio_write_32(DBSC_DBTR(24),
+			      ((rdlat_max + 2) << 24) +
+			      ((rdlat_max + 2) << 16) +
+			      mmio_read_32(DBSC_DBTR(24)));
+	}
+
+	/* set ddr density information */
+	foreach_ech(ch) {
+		for (cs = 0; cs < CS_CNT; cs++) {
+			if (ddr_density[ch][cs] == 0xff) {
+				mmio_write_32(DBSC_DBMEMCONF(ch, cs), 0x00);
+			} else {
+				mmio_write_32(DBSC_DBMEMCONF(ch, cs),
+					      DBMEMCONF_REGD(ddr_density[ch]
+							     [cs]));
+			}
+		}
+		mmio_write_32(DBSC_DBMEMCONF(ch, 2), 0x00000000);
+		mmio_write_32(DBSC_DBMEMCONF(ch, 3), 0x00000000);
+	}
+
+	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
+
+	/*set DBI */
+	if (board_cnf->dbi_en)
+		mmio_write_32(DBSC_DBDBICNT, 0x00000003);
+
+	/* H3 Ver.2.0 or later/M3-N/V3H DBI wa */
+	if ((((prr_product == PRR_PRODUCT_H3) &&
+	      (prr_cut > PRR_PRODUCT_11)) ||
+	     (prr_product == PRR_PRODUCT_M3N) ||
+	     (prr_product == PRR_PRODUCT_V3H)) &&
+	    board_cnf->dbi_en)
+		reg_ddrphy_write_a(0x00001010, 0x01000000);
+
+	/*set REFCYCLE */
+	data_l = (get_refperiod()) * ddr_mbps / 2000 / ddr_mbpsdiv;
+	mmio_write_32(DBSC_DBRFCNF1, 0x00080000 | (data_l & 0x0000ffff));
+	mmio_write_32(DBSC_DBRFCNF2, 0x00010000 | DBSC_REFINTS);
+
+#if RCAR_REWT_TRAINING != 0
+	/* Periodic-WriteDQ Training seeting */
+	if (((prr_product == PRR_PRODUCT_H3) &&
+	     (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) &&
+	     (prr_cut == PRR_PRODUCT_10))) {
+		/* non : H3 Ver.1.x/M3-W Ver.1.0 not support */
+	} else {
+		/* H3 Ver.2.0 or later/M3-W Ver.1.1 or later/M3-N/V3H */
+		mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000000);
+
+		ddr_setval_ach_as(_reg_PHY_WDQLVL_PATT, 0x04);
+		ddr_setval_ach_as(_reg_PHY_WDQLVL_QTR_DLY_STEP, 0x0F);
+		ddr_setval_ach_as(_reg_PHY_WDQLVL_DLY_STEP, 0x50);
+		ddr_setval_ach_as(_reg_PHY_WDQLVL_DQDM_SLV_DLY_START, 0x0300);
+
+		ddr_setval_ach(_reg_PI_WDQLVL_CS_MAP,
+			       ddrtbl_getval(_cnf_DDR_PI_REGSET,
+					     _reg_PI_WDQLVL_CS_MAP));
+		ddr_setval_ach(_reg_PI_LONG_COUNT_MASK, 0x1f);
+		ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x00);
+		ddr_setval_ach(_reg_PI_WDQLVL_ROTATE, 0x01);
+		ddr_setval_ach(_reg_PI_TREF_F0, 0x0000);
+		ddr_setval_ach(_reg_PI_TREF_F1, 0x0000);
+		ddr_setval_ach(_reg_PI_TREF_F2, 0x0000);
+
+		if (prr_product == PRR_PRODUCT_M3) {
+			ddr_setval_ach(_reg_PI_WDQLVL_EN, 0x02);
+		} else {
+			ddr_setval_ach(_reg_PI_WDQLVL_EN_F1, 0x02);
+		}
+		ddr_setval_ach(_reg_PI_WDQLVL_PERIODIC, 0x01);
+
+		/* DFI_PHYMSTR_ACK , WTmode setting */
+		/* DFI_PHYMSTR_ACK: WTmode =b'01 */
+		mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000011);
+	}
+#endif /* RCAR_REWT_TRAINING */
+	/* periodic dram zqcal enable */
+	mmio_write_32(DBSC_DBCALCNF, 0x01000010);
+
+	/* periodic phy ctrl update enable */
+	if (((prr_product == PRR_PRODUCT_H3) &&
+	     (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) &&
+	     (prr_cut < PRR_PRODUCT_30))) {
+		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
+	} else {
+#if RCAR_DRAM_SPLIT == 2
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (board_cnf->phyvalid == 0x05))
+			mmio_write_32(DBSC_DBDFICUPDCNF, 0x2a240001);
+		else
+			mmio_write_32(DBSC_DBDFICUPDCNF, 0x28240001);
+#else /* RCAR_DRAM_SPLIT == 2 */
+		mmio_write_32(DBSC_DBDFICUPDCNF, 0x28240001);
+#endif /* RCAR_DRAM_SPLIT == 2 */
+	}
+
+#ifdef DDR_BACKUPMODE
+	/* SRX */
+	if (ddr_backup == DRAM_BOOT_STATUS_WARM) {
+#ifdef DDR_BACKUPMODE_HALF		/* for Half channel(ch0, 1 only) */
+		NOTICE("BL2: [DEBUG_MESS] DDR_BACKUPMODE_HALF\n");
+		send_dbcmd(0x0A040001);
+		if (Prr_Product == PRR_PRODUCT_H3)
+			send_dbcmd(0x0A140001);
+#else /* DDR_BACKUPMODE_HALF */		/* for All channels */
+		send_dbcmd(0x0A840001);
+#endif /* DDR_BACKUPMODE_HALF */
+	}
+#endif /* DDR_BACKUPMODE */
+
+	/* set Auto Refresh */
+	mmio_write_32(DBSC_DBRFEN, 0x00000001);
+
+#if RCAR_REWT_TRAINING != 0
+	/* Periodic WriteDQ Traning */
+	if (((prr_product == PRR_PRODUCT_H3) &&
+	     (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) &&
+	     (prr_cut == PRR_PRODUCT_10))) {
+		/* non : H3 Ver.1.x/M3-W Ver.1.0 not support */
+	} else {
+		/* H3 Ver.2.0 or later/M3-W Ver.1.1 or later/M3-N/V3H */
+		ddr_setval_ach(_reg_PI_WDQLVL_INTERVAL, 0x0100);
+	}
+#endif /* RCAR_REWT_TRAINING */
+
+	/* dram access enable */
+	mmio_write_32(DBSC_DBACEN, 0x00000001);
+
+	MSG_LF(__func__ "(done)");
+}
+
+/* DFI_INIT_START */
+static uint32_t dfi_init_start(void)
+{
+	uint32_t ch;
+	uint32_t phytrainingok;
+	uint32_t retry;
+	uint32_t data_l;
+	const uint32_t RETRY_MAX = 0x10000;
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		/* PLL3 Disable */
+		/* protect register interface */
+		ddrphy_regif_idle();
+
+		pll3_control(0);
+
+		/* init start */
+		/* dbdficnt0:
+		 * dfi_dram_clk_disable=1
+		 * dfi_frequency = 0
+		 * freq_ratio = 01 (2:1)
+		 * init_start =0
+		 */
+		foreach_vch(ch)
+		    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F10);
+		dsb_sev();
+
+		/* dbdficnt0:
+		 * dfi_dram_clk_disable=1
+		 * dfi_frequency = 0
+		 * freq_ratio = 01 (2:1)
+		 * init_start =1
+		 */
+		foreach_vch(ch)
+		    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F11);
+		dsb_sev();
+
+	} else {
+		ddr_setval_ach_as(_reg_PHY_DLL_RST_EN, 0x02);
+		dsb_sev();
+		ddrphy_regif_idle();
+	}
+
+	/* dll_rst negate */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDCNT3(ch), 0x0000CF01);
+	dsb_sev();
+
+	/* wait init_complete */
+	phytrainingok = 0;
+	retry = 0;
+	while (retry++ < RETRY_MAX) {
+		foreach_vch(ch) {
+			data_l = mmio_read_32(DBSC_DBDFISTAT(ch));
+			if (data_l & 0x00000001)
+				phytrainingok |= (1U << ch);
+		}
+		dsb_sev();
+		if (phytrainingok == ddr_phyvalid)
+			break;
+		if (retry % 256 == 0)
+			ddr_setval_ach_as(_reg_SC_PHY_RX_CAL_START, 0x01);
+	}
+
+	/* all ch ok? */
+	if ((phytrainingok & ddr_phyvalid) != ddr_phyvalid)
+		return 0xff;
+
+	/* dbdficnt0:
+	 * dfi_dram_clk_disable=0
+	 * dfi_frequency = 0
+	 * freq_ratio = 01 (2:1)
+	 * init_start =0
+	 */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000010);
+	dsb_sev();
+
+	return 0;
+}
+
+/* drivablity setting : CMOS MODE ON/OFF */
+static void change_lpddr4_en(uint32_t mode)
+{
+	uint32_t ch;
+	uint32_t i;
+	uint32_t data_l;
+	const uint32_t _reg_PHY_PAD_DRIVE_X[3] = {
+		_reg_PHY_PAD_ADDR_DRIVE,
+		_reg_PHY_PAD_CLK_DRIVE,
+		_reg_PHY_PAD_CS_DRIVE
+	};
+
+	foreach_vch(ch) {
+		for (i = 0; i < 3; i++) {
+			data_l = ddr_getval(ch, _reg_PHY_PAD_DRIVE_X[i]);
+			if (mode) {
+				data_l |= (1U << 14);
+			} else {
+				data_l &= ~(1U << 14);
+			}
+			ddr_setval(ch, _reg_PHY_PAD_DRIVE_X[i], data_l);
+		}
+	}
+}
+
+/* drivablity setting */
+static uint32_t set_term_code(void)
+{
+	int32_t i;
+	uint32_t ch, index;
+	uint32_t data_l;
+	uint32_t chip_id[2];
+	uint32_t term_code;
+	uint32_t override;
+	uint32_t pvtr;
+	uint32_t pvtp;
+	uint32_t pvtn;
+
+	term_code = ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+				  _reg_PHY_PAD_DATA_TERM);
+	override = 0;
+	for (i = 0; i < 2; i++)
+		chip_id[i] = mmio_read_32(LIFEC_CHIPID(i));
+
+	index = 0;
+	while (1) {
+		if (termcode_by_sample[index][0] == 0xffffffff) {
+			break;
+		}
+		if ((termcode_by_sample[index][0] == chip_id[0]) &&
+		    (termcode_by_sample[index][1] == chip_id[1])) {
+			term_code = termcode_by_sample[index][2];
+			override = 1;
+			break;
+		}
+		index++;
+	}
+
+	if (override) {
+		for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM; index++) {
+			data_l =
+			    ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
+					  _reg_PHY_PAD_TERM_X[index]);
+			data_l = (data_l & 0xfffe0000) | term_code;
+			ddr_setval_ach(_reg_PHY_PAD_TERM_X[index], data_l);
+		}
+	} else if ((prr_product == PRR_PRODUCT_M3) &&
+		   (prr_cut == PRR_PRODUCT_10)) {
+		/*  non */
+	} else {
+		ddr_setval_ach(_reg_PHY_PAD_TERM_X[0],
+			       (ddrtbl_getval
+				(_cnf_DDR_PHY_ADR_G_REGSET,
+				 _reg_PHY_PAD_TERM_X[0]) & 0xFFFE0000));
+		ddr_setval_ach(_reg_PHY_CAL_CLEAR_0, 0x01);
+		ddr_setval_ach(_reg_PHY_CAL_START_0, 0x01);
+		foreach_vch(ch) {
+			do {
+				data_l =
+				    ddr_getval(ch, _reg_PHY_CAL_RESULT2_OBS_0);
+			} while (!(data_l & 0x00800000));
+		}
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			foreach_vch(ch) {
+				data_l = ddr_getval(ch, _reg_PHY_PAD_TERM_X[0]);
+				pvtr = (data_l >> 12) & 0x1f;
+				pvtr += 8;
+				if (pvtr > 0x1f)
+					pvtr = 0x1f;
+				data_l =
+				    ddr_getval(ch, _reg_PHY_CAL_RESULT2_OBS_0);
+				pvtn = (data_l >> 6) & 0x03f;
+				pvtp = (data_l >> 0) & 0x03f;
+
+				for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM;
+				     index++) {
+					data_l =
+					    ddrtbl_getval
+					    (_cnf_DDR_PHY_ADR_G_REGSET,
+					     _reg_PHY_PAD_TERM_X[index]);
+					data_l = (data_l & 0xfffe0000)
+					    | (pvtr << 12)
+					    | (pvtn << 6)
+					    | (pvtp);
+					ddr_setval(ch,
+						   _reg_PHY_PAD_TERM_X[index],
+						   data_l);
+				}
+			}
+		} else {
+			/* M3-W Ver.1.1 or later/H3 Ver.2.0 or later/M3-N/V3H */
+			foreach_vch(ch) {
+				for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM;
+				     index++) {
+					data_l =
+					    ddr_getval(ch,
+						       _reg_PHY_PAD_TERM_X
+						       [index]);
+					ddr_setval(ch,
+						   _reg_PHY_PAD_TERM_X[index],
+						   (data_l & 0xFFFE0FFF) |
+						   0x00015000);
+				}
+			}
+		}
+	}
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		/* non */
+	} else {
+		ddr_padcal_tcompensate_getinit(override);
+	}
+
+	return 0;
+}
+
+/* DDR mode register setting */
+static void ddr_register_set(void)
+{
+	int32_t fspwp;
+	uint32_t tmp;
+
+	for (fspwp = 1; fspwp >= 0; fspwp--) {
+		/*MR13, fspwp */
+		send_dbcmd(0x0e840d08 | ((2 - fspwp) << 6));
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr1_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840100 | tmp);
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr2_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840200 | tmp);
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr3_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840300 | tmp);
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr11_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840b00 | tmp);
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr12_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840c00 | tmp);
+
+		tmp =
+		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
+				  reg_pi_mr14_data_fx_csx[fspwp][0]);
+		send_dbcmd(0x0e840e00 | tmp);
+		/* MR22 */
+		send_dbcmd(0x0e841616);
+
+		/* ZQCAL start */
+		send_dbcmd(0x0d84004F);
+
+		/* ZQLAT */
+		send_dbcmd(0x0d840051);
+	}
+
+	/* MR13, fspwp */
+	send_dbcmd(0x0e840d08);
+}
+
+/* Training handshake functions */
+static inline uint32_t wait_freqchgreq(uint32_t assert)
+{
+	uint32_t data_l;
+	uint32_t count;
+	uint32_t ch;
+
+	count = 100000;
+
+	/* H3 Ver.1.x cannot see frqchg_req */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		return 0;
+	}
+
+	if (assert) {
+		do {
+			data_l = 1;
+			foreach_vch(ch) {
+				data_l &= mmio_read_32(DBSC_DBPDSTAT(ch));
+			}
+			count = count - 1;
+		} while (((data_l & 0x01) != 0x01) & (count != 0));
+	} else {
+		do {
+			data_l = 0;
+			foreach_vch(ch) {
+				data_l |= mmio_read_32(DBSC_DBPDSTAT(ch));
+			}
+			count = count - 1;
+		} while (((data_l & 0x01) != 0x00) & (count != 0));
+	}
+
+	return (count == 0);
+}
+
+static inline void set_freqchgack(uint32_t assert)
+{
+	uint32_t ch;
+	uint32_t data_l;
+
+	if (assert)
+		data_l = 0x0CF20000;
+	else
+		data_l = 0x00000000;
+
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDCNT2(ch), data_l);
+}
+
+static inline void set_dfifrequency(uint32_t freq)
+{
+	uint32_t ch;
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		foreach_vch(ch)
+		    mmio_clrsetbits_32(DBSC_DBPDCNT1(ch), 0x1fU, freq);
+	} else {
+		foreach_vch(ch) {
+			mmio_clrsetbits_32(DBSC_DBDFICNT(ch), 0x1fU << 24,
+					   (freq << 24));
+		}
+	}
+	dsb_sev();
+}
+
+static uint32_t pll3_freq(uint32_t on)
+{
+	uint32_t timeout;
+
+	timeout = wait_freqchgreq(1);
+
+	if (timeout) {
+		return 1;
+	}
+
+	pll3_control(on);
+	set_dfifrequency(on);
+
+	set_freqchgack(1);
+	timeout = wait_freqchgreq(0);
+	set_freqchgack(0);
+
+	if (timeout) {
+		FATAL_MSG("BL2: Time out[2]\n");
+		return 1;
+	}
+	return 0;
+}
+
+/* update dly */
+static void update_dly(void)
+{
+	ddr_setval_ach(_reg_SC_PHY_MANUAL_UPDATE, 0x01);
+	ddr_setval_ach(_reg_PHY_ADRCTL_MANUAL_UPDATE, 0x01);
+}
+
+/* training by pi */
+static uint32_t pi_training_go(void)
+{
+	uint32_t flag;
+	uint32_t data_l;
+	uint32_t retry;
+	const uint32_t RETRY_MAX = 4096 * 16;
+	uint32_t ch;
+
+	uint32_t mst_ch;
+	uint32_t cur_frq;
+	uint32_t complete;
+	uint32_t frqchg_req;
+
+	/* pi_start */
+	ddr_setval_ach(_reg_PI_START, 0x01);
+	foreach_vch(ch)
+	    ddr_getval(ch, _reg_PI_INT_STATUS);
+
+	/* set dfi_phymstr_ack = 1 */
+	mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000001);
+	dsb_sev();
+
+	/* wait pi_int_status[0] */
+	mst_ch = 0;
+	flag = 0;
+	complete = 0;
+	cur_frq = 0;
+	retry = RETRY_MAX;
+	do {
+		frqchg_req = mmio_read_32(DBSC_DBPDSTAT(mst_ch)) & 0x01;
+
+		/* H3 Ver.1.x cannot see frqchg_req */
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			if ((retry % 4096) == 1) {
+				frqchg_req = 1;
+			} else {
+				frqchg_req = 0;
+			}
+		}
+
+		if (frqchg_req) {
+			if (cur_frq) {
+				/* Low frequency */
+				flag = pll3_freq(0);
+				cur_frq = 0;
+			} else {
+				/* High frequency */
+				flag = pll3_freq(1);
+				cur_frq = 1;
+			}
+			if (flag)
+				break;
+		} else {
+			if (cur_frq) {
+				foreach_vch(ch) {
+					if (complete & (1U << ch))
+						continue;
+					data_l =
+					    ddr_getval(ch, _reg_PI_INT_STATUS);
+					if (data_l & 0x01) {
+						complete |= (1U << ch);
+					}
+				}
+				if (complete == ddr_phyvalid)
+					break;
+			}
+		}
+	} while (--retry);
+	foreach_vch(ch) {
+		/* dummy read */
+		data_l = ddr_getval_s(ch, 0, _reg_PHY_CAL_RESULT2_OBS_0);
+		data_l = ddr_getval(ch, _reg_PI_INT_STATUS);
+		ddr_setval(ch, _reg_PI_INT_ACK, data_l);
+	}
+	if (ddrphy_regif_chk()) {
+		return 0xfd;
+	}
+	return complete;
+}
+
+/* Initialize DDR */
+static uint32_t init_ddr(void)
+{
+	int32_t i;
+	uint32_t data_l;
+	uint32_t phytrainingok;
+	uint32_t ch, slice;
+	uint32_t err;
+	int16_t adj;
+
+	MSG_LF(__func__ ":0\n");
+
+#ifdef DDR_BACKUPMODE
+	rcar_dram_get_boot_status(&ddr_backup);
+#endif
+
+	/* unlock phy */
+	/* Unlock DDRPHY register(AGAIN) */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDLK(ch), 0x0000A55A);
+	dsb_sev();
+
+	if ((((prr_product == PRR_PRODUCT_H3) &&
+	      (prr_cut > PRR_PRODUCT_11)) ||
+	     (prr_product == PRR_PRODUCT_M3N) ||
+	     (prr_product == PRR_PRODUCT_V3H)) && board_cnf->dbi_en)
+		reg_ddrphy_write_a(0x00001010, 0x01000001);
+	else
+		reg_ddrphy_write_a(0x00001010, 0x00000001);
+	/* DBSC register pre-setting */
+	dbsc_regset_pre();
+
+	/* load ddrphy registers */
+
+	ddrtbl_load();
+
+	/* configure ddrphy registers */
+	ddr_config();
+
+	/* dfi_reset assert */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDCNT0(ch), 0x01);
+	dsb_sev();
+
+	/* dbsc register set */
+	dbsc_regset();
+	MSG_LF(__func__ ":1\n");
+
+	/* dfi_reset negate */
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDCNT0(ch), 0x00);
+	dsb_sev();
+
+	/* dfi_init_start (start ddrphy) */
+	err = dfi_init_start();
+	if (err) {
+		return INITDRAM_ERR_I;
+	}
+	MSG_LF(__func__ ":2\n");
+
+	/* ddr backupmode end */
+#ifdef DDR_BACKUPMODE
+	if (ddr_backup) {
+		NOTICE("BL2: [WARM_BOOT]\n");
+	} else {
+		NOTICE("BL2: [COLD_BOOT]\n");
+	}
+	err = rcar_dram_update_boot_status(ddr_backup);
+	if (err) {
+		NOTICE("BL2: [BOOT_STATUS_UPDATE_ERROR]\n");
+		return INITDRAM_ERR_I;
+	}
+#endif
+	MSG_LF(__func__ ":3\n");
+
+	/* override term code after dfi_init_complete */
+	err = set_term_code();
+	if (err) {
+		return INITDRAM_ERR_I;
+	}
+	MSG_LF(__func__ ":4\n");
+
+	/* rx offset calibration */
+	if ((prr_cut > PRR_PRODUCT_11) || (prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		err = rx_offset_cal_hw();
+	} else {
+		err = rx_offset_cal();
+	}
+	if (err)
+		return INITDRAM_ERR_O;
+	MSG_LF(__func__ ":5\n");
+
+	/* Dummy PDE */
+	send_dbcmd(0x08840000);
+
+	/* PDX */
+	send_dbcmd(0x08840001);
+
+	/* check register i/f is alive */
+	err = ddrphy_regif_chk();
+	if (err) {
+		return INITDRAM_ERR_O;
+	}
+	MSG_LF(__func__ ":6\n");
+
+	/* phy initialize end */
+
+	/* setup DDR mode registers */
+	/* CMOS MODE */
+	change_lpddr4_en(0);
+
+	/* MRS */
+	ddr_register_set();
+
+	/* Thermal sensor setting */
+	/* THCTR Bit6: PONM=0 , Bit0: THSST=1  */
+	data_l = (mmio_read_32(THS1_THCTR) & 0xFFFFFFBF) | 0x00000001;
+	mmio_write_32(THS1_THCTR, data_l);
+
+	/* LPDDR4 MODE */
+	change_lpddr4_en(1);
+
+	MSG_LF(__func__ ":7\n");
+
+	/* mask CS_MAP if RANKx is not found */
+	foreach_vch(ch) {
+		data_l = ddr_getval(ch, _reg_PI_CS_MAP);
+		if (!(ch_have_this_cs[1] & (1U << ch)))
+			data_l = data_l & 0x05;
+		ddr_setval(ch, _reg_PI_CS_MAP, data_l);
+	}
+
+	/* exec pi_training */
+	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
+			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
+	ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_MULTICAST_EN, 0x00);
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_EN, 0x01);
+	} else {
+		foreach_vch(ch) {
+			for (slice = 0; slice < SLICE_CNT; slice++) {
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_PER_CS_TRAINING_EN,
+					     ((ch_have_this_cs[1]) >> ch)
+					     & 0x01);
+			}
+		}
+	}
+
+	phytrainingok = pi_training_go();
+
+	if (ddr_phyvalid != (phytrainingok & ddr_phyvalid)) {
+		return INITDRAM_ERR_T | phytrainingok;
+	}
+
+	MSG_LF(__func__ ":8\n");
+
+	/* CACS DLY ADJUST */
+	data_l = board_cnf->cacs_dly + _f_scale_adj(board_cnf->cacs_dly_adj);
+	foreach_vch(ch) {
+		for (i = 0; i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM; i++) {
+			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
+			ddr_setval(ch, _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
+				   data_l + adj);
+		}
+
+		if (ddr_phycaslice == 1) {
+			for (i = 0; i < 6; i++) {
+				adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj
+					[i +
+					_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM]);
+				ddr_setval_s(ch, 2,
+					     _reg_PHY_CLK_CACS_SLAVE_DELAY_X
+					     [i],
+					     data_l + adj
+				);
+			}
+		}
+	}
+
+	update_dly();
+	MSG_LF(__func__ ":9\n");
+
+	/* H3 fix rd latency to avoid bug in elasitic buffer */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11))
+		adjust_rddqs_latency();
+
+	/* Adjust Write path latency */
+	if (ddrtbl_getval
+	    (_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_WRITE_PATH_LAT_ADD))
+		adjust_wpath_latency();
+
+	/* RDQLVL Training */
+	if (!ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_IE_MODE))
+		ddr_setval_ach_as(_reg_PHY_IE_MODE, 0x01);
+
+	err = rdqdm_man();
+
+	if (!ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_IE_MODE))
+		ddr_setval_ach_as(_reg_PHY_IE_MODE, 0x00);
+
+	if (err) {
+		return INITDRAM_ERR_T;
+	}
+	update_dly();
+	MSG_LF(__func__ ":10\n");
+
+	/* WDQLVL Training */
+	err = wdqdm_man();
+	if (err) {
+		return INITDRAM_ERR_T;
+	}
+	update_dly();
+	MSG_LF(__func__ ":11\n");
+
+	/* training complete, setup DBSC */
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
+	    (prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		ddr_setval_ach_as(_reg_PHY_DFI40_POLARITY, 0x00);
+		ddr_setval_ach(_reg_PI_DFI40_POLARITY, 0x00);
+	}
+
+	dbsc_regset_post();
+	MSG_LF(__func__ ":12\n");
+
+	return phytrainingok;
+}
+
+/* SW LEVELING COMMON */
+static uint32_t swlvl1(uint32_t ddr_csn, uint32_t reg_cs, uint32_t reg_kick)
+{
+	uint32_t ch;
+	uint32_t data_l;
+	uint32_t retry;
+	uint32_t waiting;
+	uint32_t err;
+
+	const uint32_t RETRY_MAX = 0x1000;
+
+	err = 0;
+	/* set EXIT -> OP_DONE is cleared */
+	ddr_setval_ach(_reg_PI_SWLVL_EXIT, 0x01);
+
+	/* kick */
+	foreach_vch(ch) {
+		if (ch_have_this_cs[ddr_csn % 2] & (1U << ch)) {
+			ddr_setval(ch, reg_cs, ddr_csn);
+			ddr_setval(ch, reg_kick, 0x01);
+		}
+	}
+	foreach_vch(ch) {
+		/*PREPARE ADDR REGISTER (for SWLVL_OP_DONE) */
+		ddr_getval(ch, _reg_PI_SWLVL_OP_DONE);
+	}
+	waiting = ch_have_this_cs[ddr_csn % 2];
+	dsb_sev();
+	retry = RETRY_MAX;
+	do {
+		foreach_vch(ch) {
+			if (!(waiting & (1U << ch)))
+				continue;
+			data_l = ddr_getval(ch, _reg_PI_SWLVL_OP_DONE);
+			if (data_l & 0x01)
+				waiting &= ~(1U << ch);
+		}
+		retry--;
+	} while (waiting && (retry > 0));
+	if (retry == 0) {
+		err = 1;
+	}
+
+	dsb_sev();
+	/* set EXIT -> OP_DONE is cleared */
+	ddr_setval_ach(_reg_PI_SWLVL_EXIT, 0x01);
+	dsb_sev();
+
+	return err;
+}
+
+/* WDQ TRAINING */
+#ifndef DDR_FAST_INIT
+static void wdqdm_clr1(uint32_t ch, uint32_t ddr_csn)
+{
+	int32_t i, k;
+	uint32_t cs, slice;
+	uint32_t data_l;
+
+	/* clr of training results buffer */
+	cs = ddr_csn % 2;
+	data_l = board_cnf->dqdm_dly_w;
+	for (slice = 0; slice < SLICE_CNT; slice++) {
+		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
+		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
+			continue;
+
+		for (i = 0; i <= 8; i++) {
+			if (ch_have_this_cs[CS_CNT - 1 - cs] & (1U << ch))
+				wdqdm_dly[ch][cs][slice][i] =
+				    wdqdm_dly[ch][CS_CNT - 1 - cs][slice][i];
+			else
+				wdqdm_dly[ch][cs][slice][i] = data_l;
+			wdqdm_le[ch][cs][slice][i] = 0;
+			wdqdm_te[ch][cs][slice][i] = 0;
+		}
+		wdqdm_st[ch][cs][slice] = 0;
+		wdqdm_win[ch][cs][slice] = 0;
+	}
+}
+
+static uint32_t wdqdm_ana1(uint32_t ch, uint32_t ddr_csn)
+{
+	int32_t i, k;
+	uint32_t cs, slice;
+	uint32_t data_l;
+	uint32_t err;
+	const uint32_t _par_WDQLVL_RETRY_THRES = 0x7c0;
+
+	int32_t min_win;
+	int32_t win;
+	int8_t _adj;
+	int16_t adj;
+	uint32_t dq;
+
+	/* analysis of training results */
+	err = 0;
+	for (slice = 0; slice < SLICE_CNT; slice += 1) {
+		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
+		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
+			continue;
+
+		cs = ddr_csn % 2;
+		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, cs);
+		for (i = 0; i < 9; i++) {
+			dq = slice * 8 + i;
+			if (i == 8)
+				_adj = board_cnf->ch[ch].dm_adj_w[slice];
+			else
+				_adj = board_cnf->ch[ch].dq_adj_w[dq];
+			adj = _f_scale_adj(_adj);
+
+			data_l =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_CLK_WRX_SLAVE_DELAY[i]) + adj;
+			ddr_setval_s(ch, slice, _reg_PHY_CLK_WRX_SLAVE_DELAY[i],
+				     data_l);
+			wdqdm_dly[ch][cs][slice][i] = data_l;
+		}
+		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN, 0x00);
+		data_l = ddr_getval_s(ch, slice, _reg_PHY_WDQLVL_STATUS_OBS);
+		wdqdm_st[ch][cs][slice] = data_l;
+		min_win = INT_LEAST32_MAX;
+		for (i = 0; i <= 8; i++) {
+			ddr_setval_s(ch, slice, _reg_PHY_WDQLVL_DQDM_OBS_SELECT,
+				     i);
+
+			data_l =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_WDQLVL_DQDM_TE_DLY_OBS);
+			wdqdm_te[ch][cs][slice][i] = data_l;
+			data_l =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_WDQLVL_DQDM_LE_DLY_OBS);
+			wdqdm_le[ch][cs][slice][i] = data_l;
+			win =
+			    (int32_t)wdqdm_te[ch][cs][slice][i] -
+			    wdqdm_le[ch][cs][slice][i];
+			if (min_win > win)
+				min_win = win;
+			if (data_l >= _par_WDQLVL_RETRY_THRES)
+				err = 2;
+		}
+		wdqdm_win[ch][cs][slice] = min_win;
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN,
+				     0x01);
+		} else {
+			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN,
+				     ((ch_have_this_cs[1]) >> ch) & 0x01);
+		}
+	}
+	return err;
+}
+#endif/* DDR_FAST_INIT */
+
+static void wdqdm_cp(uint32_t ddr_csn, uint32_t restore)
+{
+	uint32_t i;
+	uint32_t ch, slice;
+	uint32_t tgt_cs, src_cs;
+	uint32_t tmp_r;
+
+	/* copy of training results */
+	foreach_vch(ch) {
+		for (tgt_cs = 0; tgt_cs < CS_CNT; tgt_cs++) {
+			for (slice = 0; slice < SLICE_CNT; slice++) {
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_PER_CS_TRAINING_INDEX,
+					     tgt_cs);
+				src_cs = ddr_csn % 2;
+				if (!(ch_have_this_cs[1] & (1U << ch)))
+					src_cs = 0;
+				for (i = 0; i <= 4; i += 4) {
+					if (restore)
+						tmp_r =
+						    rdqdm_dly[ch][tgt_cs][slice]
+						    [i];
+					else
+						tmp_r =
+						    rdqdm_dly[ch][src_cs][slice]
+						    [i];
+
+					ddr_setval_s(ch, slice,
+						     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
+						     [i], tmp_r);
+				}
+			}
+		}
+	}
+}
+
+static uint32_t wdqdm_man1(void)
+{
+	int32_t k;
+	uint32_t ch, cs, slice;
+	uint32_t ddr_csn;
+	uint32_t data_l;
+	uint32_t err;
+	uint32_t high_dq[DRAM_CH_CNT];
+	uint32_t mr14_csab0_bak[DRAM_CH_CNT];
+#ifndef DDR_FAST_INIT
+	uint32_t err_flg;
+#endif/* DDR_FAST_INIT */
+
+	/* manual execution of training */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		foreach_vch(ch) {
+			high_dq[ch] = 0;
+			for (slice = 0; slice < SLICE_CNT; slice++) {
+				k = (board_cnf->ch[ch].dqs_swap >>
+				    (4 * slice)) & 0x0f;
+				if (k >= 2)
+					high_dq[ch] |= (1U << slice);
+			}
+			ddr_setval(ch, _reg_PI_16BIT_DRAM_CONNECT, 0x00);
+		}
+	}
+	err = 0;
+	/* CLEAR PREV RESULT */
+	for (cs = 0; cs < CS_CNT; cs++) {
+		ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_INDEX, cs);
+		if (((prr_product == PRR_PRODUCT_H3) &&
+		     (prr_cut > PRR_PRODUCT_11)) ||
+		    (prr_product == PRR_PRODUCT_M3N) ||
+		    (prr_product == PRR_PRODUCT_V3H)) {
+			ddr_setval_ach_as(_reg_SC_PHY_WDQLVL_CLR_PREV_RESULTS,
+					  0x01);
+		} else {
+			ddr_setval_ach_as(_reg_PHY_WDQLVL_CLR_PREV_RESULTS,
+					  0x01);
+		}
+	}
+	ddrphy_regif_idle();
+
+#ifndef DDR_FAST_INIT
+	err_flg = 0;
+#endif/* DDR_FAST_INIT */
+	for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			foreach_vch(ch) {
+				data_l = mmio_read_32(DBSC_DBDFICNT(ch));
+				data_l &= ~(0x00ffU << 16);
+
+				if (ddr_csn >= 2)
+					k = (high_dq[ch] ^ 0x0f);
+				else
+					k = high_dq[ch];
+				data_l |= (k << 16);
+				mmio_write_32(DBSC_DBDFICNT(ch), data_l);
+				ddr_setval(ch, _reg_PI_WDQLVL_RESP_MASK, k);
+			}
+		}
+		if (((prr_product == PRR_PRODUCT_H3) &&
+		     (prr_cut <= PRR_PRODUCT_11)) ||
+		    ((prr_product == PRR_PRODUCT_M3) &&
+		     (prr_cut == PRR_PRODUCT_10))) {
+			wdqdm_cp(ddr_csn, 0);
+		}
+
+		foreach_vch(ch) {
+			data_l =
+			    ddr_getval(ch,
+				       reg_pi_mr14_data_fx_csx[1][ddr_csn]);
+			ddr_setval(ch, reg_pi_mr14_data_fx_csx[1][0], data_l);
+		}
+
+		/* KICK WDQLVL */
+		err = swlvl1(ddr_csn, _reg_PI_WDQLVL_CS, _reg_PI_WDQLVL_REQ);
+		if (err)
+			goto err_exit;
+
+		if (ddr_csn == 0)
+			foreach_vch(ch) {
+			mr14_csab0_bak[ch] =
+			    ddr_getval(ch, reg_pi_mr14_data_fx_csx[1][0]);
+		} else
+			foreach_vch(ch) {
+			ddr_setval(ch, reg_pi_mr14_data_fx_csx[1][0],
+				   mr14_csab0_bak[ch]);
+			}
+#ifndef DDR_FAST_INIT
+		foreach_vch(ch) {
+			if (!(ch_have_this_cs[ddr_csn % 2] & (1U << ch))) {
+				wdqdm_clr1(ch, ddr_csn);
+				continue;
+			}
+			err = wdqdm_ana1(ch, ddr_csn);
+			if (err)
+				err_flg |= (1U << (ddr_csn * 4 + ch));
+			ddrphy_regif_idle();
+		}
+#endif/* DDR_FAST_INIT */
+	}
+err_exit:
+#ifndef DDR_FAST_INIT
+	err |= err_flg;
+#endif/* DDR_FAST_INIT */
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		ddr_setval_ach(_reg_PI_16BIT_DRAM_CONNECT, 0x01);
+		foreach_vch(ch) {
+			data_l = mmio_read_32(DBSC_DBDFICNT(ch));
+			data_l &= ~(0x00ffU << 16);
+			mmio_write_32(DBSC_DBDFICNT(ch), data_l);
+			ddr_setval(ch, _reg_PI_WDQLVL_RESP_MASK, 0x00);
+		}
+	}
+	return err;
+}
+
+static uint32_t wdqdm_man(void)
+{
+	uint32_t err, retry_cnt;
+	const uint32_t retry_max = 0x10;
+	uint32_t datal, ch, ddr_csn, mr14_bkup[4][4];
+
+	datal = RL + js2[js2_tdqsck] + (16 / 2) + 1 - WL + 2 + 2 + 19;
+	if ((mmio_read_32(DBSC_DBTR(11)) & 0xFF) > datal)
+		datal = mmio_read_32(DBSC_DBTR(11)) & 0xFF;
+	ddr_setval_ach(_reg_PI_TDFI_WDQLVL_RW, datal);
+
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
+	    (prr_product == PRR_PRODUCT_M3N) ||
+	    (prr_product == PRR_PRODUCT_V3H)) {
+		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR_F0,
+			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
+		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR_F1,
+			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
+	} else {
+		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR,
+			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
+	}
+	ddr_setval_ach(_reg_PI_TRFC_F0, mmio_read_32(DBSC_DBTR(13)) & 0x1FF);
+	ddr_setval_ach(_reg_PI_TRFC_F1, mmio_read_32(DBSC_DBTR(13)) & 0x1FF);
+
+	retry_cnt = 0;
+	err = 0;
+	do {
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			err = wdqdm_man1();
+		} else {
+			ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x01);
+			ddr_setval_ach(_reg_PI_WDQLVL_VREF_NORMAL_STEPSIZE,
+				       0x01);
+			if ((prr_product == PRR_PRODUCT_M3N) ||
+			    (prr_product == PRR_PRODUCT_V3H)) {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
+					       0x0C);
+			} else {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x0C);
+			}
+			dsb_sev();
+			err = wdqdm_man1();
+			foreach_vch(ch) {
+				for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
+					mr14_bkup[ch][ddr_csn] =
+					    ddr_getval(ch,
+						       reg_pi_mr14_data_fx_csx
+						       [1][ddr_csn]);
+					dsb_sev();
+				}
+			}
+
+			if ((prr_product == PRR_PRODUCT_M3N) ||
+			    (prr_product == PRR_PRODUCT_V3H)) {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
+					       0x04);
+			} else {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x04);
+			}
+			pvtcode_update();
+			err = wdqdm_man1();
+			foreach_vch(ch) {
+				for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
+					mr14_bkup[ch][ddr_csn] =
+					    (mr14_bkup[ch][ddr_csn] +
+					     ddr_getval(ch,
+							reg_pi_mr14_data_fx_csx
+							[1][ddr_csn])) / 2;
+					ddr_setval(ch,
+						   reg_pi_mr14_data_fx_csx[1]
+						   [ddr_csn],
+						   mr14_bkup[ch][ddr_csn]);
+				}
+			}
+
+			ddr_setval_ach(_reg_PI_WDQLVL_VREF_NORMAL_STEPSIZE,
+				       0x00);
+			if ((prr_product == PRR_PRODUCT_M3N) ||
+			    (prr_product == PRR_PRODUCT_V3H)) {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
+					       0x00);
+				ddr_setval_ach
+				    (_reg_PI_WDQLVL_VREF_INITIAL_START_POINT_F1,
+				     0x00);
+				ddr_setval_ach
+				    (_reg_PI_WDQLVL_VREF_INITIAL_STOP_POINT_F1,
+				     0x00);
+			} else {
+				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x00);
+				ddr_setval_ach
+				    (_reg_PI_WDQLVL_VREF_INITIAL_START_POINT,
+				     0x00);
+				ddr_setval_ach
+				    (_reg_PI_WDQLVL_VREF_INITIAL_STOP_POINT,
+				     0x00);
+			}
+			ddr_setval_ach(_reg_PI_WDQLVL_VREF_INITIAL_STEPSIZE,
+				       0x00);
+
+			pvtcode_update2();
+			err = wdqdm_man1();
+			ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x00);
+		}
+	} while (err && (++retry_cnt < retry_max));
+
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut <= PRR_PRODUCT_10))) {
+		wdqdm_cp(0, 1);
+	}
+
+	return (retry_cnt >= retry_max);
+}
+
+/* RDQ TRAINING */
+#ifndef DDR_FAST_INIT
+static void rdqdm_clr1(uint32_t ch, uint32_t ddr_csn)
+{
+	int32_t i, k;
+	uint32_t cs, slice;
+	uint32_t data_l;
+
+	/* clr of training results buffer */
+	cs = ddr_csn % 2;
+	data_l = board_cnf->dqdm_dly_r;
+	for (slice = 0; slice < SLICE_CNT; slice++) {
+		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
+		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
+			continue;
+
+		for (i = 0; i <= 8; i++) {
+			if (ch_have_this_cs[CS_CNT - 1 - cs] & (1U << ch)) {
+				rdqdm_dly[ch][cs][slice][i] =
+				    rdqdm_dly[ch][CS_CNT - 1 - cs][slice][i];
+				rdqdm_dly[ch][cs][slice + SLICE_CNT][i] =
+				    rdqdm_dly[ch][CS_CNT - 1 - cs][slice +
+								   SLICE_CNT]
+				    [i];
+			} else {
+				rdqdm_dly[ch][cs][slice][i] = data_l;
+				rdqdm_dly[ch][cs][slice + SLICE_CNT][i] =
+					data_l;
+			}
+			rdqdm_le[ch][cs][slice][i] = 0;
+			rdqdm_le[ch][cs][slice + SLICE_CNT][i] = 0;
+			rdqdm_te[ch][cs][slice][i] = 0;
+			rdqdm_te[ch][cs][slice + SLICE_CNT][i] = 0;
+			rdqdm_nw[ch][cs][slice][i] = 0;
+			rdqdm_nw[ch][cs][slice + SLICE_CNT][i] = 0;
+		}
+		rdqdm_st[ch][cs][slice] = 0;
+		rdqdm_win[ch][cs][slice] = 0;
+	}
+}
+
+static uint32_t rdqdm_ana1(uint32_t ch, uint32_t ddr_csn)
+{
+	int32_t i, k;
+	uint32_t cs, slice;
+	uint32_t data_l;
+	uint32_t err;
+	int8_t _adj;
+	int16_t adj;
+	uint32_t dq;
+	int32_t min_win;
+	int32_t win;
+	uint32_t rdq_status_obs_select;
+
+	/* analysis of training results */
+	err = 0;
+	for (slice = 0; slice < SLICE_CNT; slice++) {
+		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
+		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
+			continue;
+
+		cs = ddr_csn % 2;
+		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, cs);
+		ddrphy_regif_idle();
+
+		ddr_getval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX);
+		ddrphy_regif_idle();
+
+		for (i = 0; i <= 8; i++) {
+			dq = slice * 8 + i;
+			if (i == 8)
+				_adj = board_cnf->ch[ch].dm_adj_r[slice];
+			else
+				_adj = board_cnf->ch[ch].dq_adj_r[dq];
+
+			adj = _f_scale_adj(_adj);
+
+			data_l =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i]) +
+			    adj;
+			ddr_setval_s(ch, slice,
+				     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i],
+				     data_l);
+			rdqdm_dly[ch][cs][slice][i] = data_l;
+
+			data_l =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i]) +
+			    adj;
+			ddr_setval_s(ch, slice,
+				     _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i],
+				     data_l);
+			rdqdm_dly[ch][cs][slice + SLICE_CNT][i] = data_l;
+		}
+		min_win = INT_LEAST32_MAX;
+		for (i = 0; i <= 8; i++) {
+			data_l =
+			    ddr_getval_s(ch, slice, _reg_PHY_RDLVL_STATUS_OBS);
+			rdqdm_st[ch][cs][slice] = data_l;
+			rdqdm_st[ch][cs][slice + SLICE_CNT] = data_l;
+			/* k : rise/fall */
+			for (k = 0; k < 2; k++) {
+				if (i == 8) {
+					rdq_status_obs_select = 16 + 8 * k;
+				} else {
+					rdq_status_obs_select = i + k * 8;
+				}
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_RDLVL_RDDQS_DQ_OBS_SELECT,
+					     rdq_status_obs_select);
+
+				data_l =
+				    ddr_getval_s(ch, slice,
+						 _reg_PHY_RDLVL_RDDQS_DQ_LE_DLY_OBS);
+				rdqdm_le[ch][cs][slice + SLICE_CNT * k][i] =
+				    data_l;
+
+				data_l =
+				    ddr_getval_s(ch, slice,
+						 _reg_PHY_RDLVL_RDDQS_DQ_TE_DLY_OBS);
+				rdqdm_te[ch][cs][slice + SLICE_CNT * k][i] =
+				    data_l;
+
+				data_l =
+				    ddr_getval_s(ch, slice,
+						 _reg_PHY_RDLVL_RDDQS_DQ_NUM_WINDOWS_OBS);
+				rdqdm_nw[ch][cs][slice + SLICE_CNT * k][i] =
+				    data_l;
+
+				win =
+				    (int32_t)rdqdm_te[ch][cs][slice +
+							      SLICE_CNT *
+							      k][i] -
+				    rdqdm_le[ch][cs][slice + SLICE_CNT * k][i];
+				if (i != 8) {
+					if (min_win > win)
+						min_win = win;
+				}
+			}
+		}
+		rdqdm_win[ch][cs][slice] = min_win;
+		if (min_win <= 0) {
+			err = 2;
+		}
+	}
+	return err;
+}
+#endif/* DDR_FAST_INIT */
+
+static uint32_t rdqdm_man1(void)
+{
+	uint32_t ch;
+	uint32_t ddr_csn;
+#ifdef DDR_FAST_INIT
+	uint32_t slice;
+	uint32_t i, adj, data_l;
+#endif/* DDR_FAST_INIT */
+	uint32_t err;
+
+	/* manual execution of training */
+	err = 0;
+
+	for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
+		/* KICK RDQLVL */
+		err = swlvl1(ddr_csn, _reg_PI_RDLVL_CS, _reg_PI_RDLVL_REQ);
+		if (err)
+			goto err_exit;
+#ifndef DDR_FAST_INIT
+		foreach_vch(ch) {
+			if (!(ch_have_this_cs[ddr_csn % 2] & (1U << ch))) {
+				rdqdm_clr1(ch, ddr_csn);
+				ddrphy_regif_idle();
+				continue;
+			}
+			err = rdqdm_ana1(ch, ddr_csn);
+			ddrphy_regif_idle();
+			if (err)
+				goto err_exit;
+		}
+#else/* DDR_FAST_INIT */
+		foreach_vch(ch) {
+			if (ch_have_this_cs[ddr_csn] & (1U << ch)) {
+				for (slice = 0; slice < SLICE_CNT; slice++) {
+					if (ddr_getval_s(ch, slice,
+							 _reg_PHY_RDLVL_STATUS_OBS) !=
+					    0x0D00FFFF) {
+						err = (1U << ch) |
+							(0x10U << slice);
+						goto err_exit;
+					}
+				}
+			}
+			if (((prr_product == PRR_PRODUCT_H3) &&
+			     (prr_cut <= PRR_PRODUCT_11)) ||
+			    ((prr_product == PRR_PRODUCT_M3) &&
+			     (prr_cut <= PRR_PRODUCT_10))) {
+				for (slice = 0; slice < SLICE_CNT; slice++) {
+					for (i = 0; i <= 8; i++) {
+						if (i == 8)
+							adj = _f_scale_adj(board_cnf->ch[ch].dm_adj_r[slice]);
+						else
+							adj = _f_scale_adj(board_cnf->ch[ch].dq_adj_r[slice * 8 + i]);
+						ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, ddr_csn);
+						data_l = ddr_getval_s(ch, slice, _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i]) + adj;
+						ddr_setval_s(ch, slice, _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i], data_l);
+						rdqdm_dly[ch][ddr_csn][slice][i] = data_l;
+						rdqdm_dly[ch][ddr_csn | 1][slice][i] = data_l;
+
+						data_l = ddr_getval_s(ch, slice, _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i]) + adj;
+						ddr_setval_s(ch, slice, _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i], data_l);
+						rdqdm_dly[ch][ddr_csn][slice + SLICE_CNT][i] = data_l;
+						rdqdm_dly[ch][ddr_csn | 1][slice + SLICE_CNT][i] = data_l;
+					}
+				}
+			}
+		}
+		ddrphy_regif_idle();
+
+#endif/* DDR_FAST_INIT */
+	}
+
+err_exit:
+	return err;
+}
+
+static uint32_t rdqdm_man(void)
+{
+	uint32_t err, retry_cnt;
+	const uint32_t retry_max = 0x01;
+
+	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_ENABLE,
+			  0x00000004 | ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+						     _reg_PHY_DQ_TSEL_ENABLE));
+	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_ENABLE,
+			  0x00000004 | ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+						     _reg_PHY_DQS_TSEL_ENABLE));
+	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_SELECT,
+			  0xFF0FFFFF & ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+						     _reg_PHY_DQ_TSEL_SELECT));
+	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_SELECT,
+			  0xFF0FFFFF & ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+						     _reg_PHY_DQS_TSEL_SELECT));
+
+	retry_cnt = 0;
+	do {
+		err = rdqdm_man1();
+		ddrphy_regif_idle();
+	} while (err && (++retry_cnt < retry_max));
+	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_ENABLE,
+			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+					_reg_PHY_DQ_TSEL_ENABLE));
+	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_ENABLE,
+			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+					_reg_PHY_DQS_TSEL_ENABLE));
+	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_SELECT,
+			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+					_reg_PHY_DQ_TSEL_SELECT));
+	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_SELECT,
+			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
+					_reg_PHY_DQS_TSEL_SELECT));
+
+	return (retry_cnt >= retry_max);
+}
+
+/* rx offset calibration */
+static int32_t _find_change(uint64_t val, uint32_t dir)
+{
+	int32_t i;
+	uint32_t startval;
+	uint32_t curval;
+	const int32_t VAL_END = 0x3f;
+
+	if (dir == 0) {
+		startval = (val & 0x01);
+		for (i = 1; i <= VAL_END; i++) {
+			curval = (val >> i) & 0x01;
+			if (curval != startval)
+				return i;
+		}
+		return VAL_END;
+	}
+
+	startval = (val >> dir) & 0x01;
+	for (i = dir - 1; i >= 0; i--) {
+		curval = (val >> i) & 0x01;
+		if (curval != startval)
+			return i;
+	}
+	return 0;
+}
+
+static uint32_t _rx_offset_cal_updn(uint32_t code)
+{
+	const uint32_t CODE_MAX = 0x40;
+	uint32_t tmp;
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
+		if (code == 0)
+			tmp = (1U << 6) | (CODE_MAX - 1);
+		else if (code <= 0x20)
+			tmp =
+			    ((CODE_MAX - 1 -
+			      (0x20 - code) * 2) << 6) | (CODE_MAX - 1);
+		else
+			tmp =
+			    ((CODE_MAX - 1) << 6) | (CODE_MAX - 1 -
+						     (code - 0x20) * 2);
+	} else {
+		if (code == 0)
+			tmp = (1U << 6) | (CODE_MAX - 1);
+		else
+			tmp = (code << 6) | (CODE_MAX - code);
+	}
+	return tmp;
+}
+
+static uint32_t rx_offset_cal(void)
+{
+	uint32_t index;
+	uint32_t code;
+	const uint32_t CODE_MAX = 0x40;
+	const uint32_t CODE_STEP = 2;
+	uint32_t ch, slice;
+	uint32_t tmp;
+	uint32_t tmp_ach_as[DRAM_CH_CNT][SLICE_CNT];
+	uint64_t val[DRAM_CH_CNT][SLICE_CNT][_reg_PHY_RX_CAL_X_NUM];
+	uint64_t tmpval;
+	int32_t lsb, msb;
+
+	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x01);
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			for (index = 0; index < _reg_PHY_RX_CAL_X_NUM; index++)
+				val[ch][slice][index] = 0;
+		}
+	}
+
+	for (code = 0; code < CODE_MAX / CODE_STEP; code++) {
+		tmp = _rx_offset_cal_updn(code * CODE_STEP);
+		for (index = 0; index < _reg_PHY_RX_CAL_X_NUM; index++) {
+			ddr_setval_ach_as(_reg_PHY_RX_CAL_X[index], tmp);
+		}
+		dsb_sev();
+		ddr_getval_ach_as(_reg_PHY_RX_CAL_OBS, (uint32_t *)tmp_ach_as);
+
+		foreach_vch(ch) {
+			for (slice = 0; slice < SLICE_CNT; slice++) {
+				tmp = tmp_ach_as[ch][slice];
+				for (index = 0; index < _reg_PHY_RX_CAL_X_NUM;
+				     index++) {
+					if (tmp & (1U << index)) {
+						val[ch][slice][index] |=
+						    (1ULL << code);
+					} else {
+						val[ch][slice][index] &=
+						    ~(1ULL << code);
+					}
+				}
+			}
+		}
+	}
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			for (index = 0; index < _reg_PHY_RX_CAL_X_NUM;
+			     index++) {
+				tmpval = val[ch][slice][index];
+				lsb = _find_change(tmpval, 0);
+				msb =
+				    _find_change(tmpval,
+						 (CODE_MAX / CODE_STEP) - 1);
+				tmp = (lsb + msb) >> 1;
+
+				tmp = _rx_offset_cal_updn(tmp * CODE_STEP);
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_RX_CAL_X[index], tmp);
+			}
+		}
+	}
+	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x00);
+
+	return 0;
+}
+
+static uint32_t rx_offset_cal_hw(void)
+{
+	uint32_t ch, slice;
+	uint32_t retry;
+	uint32_t complete;
+	uint32_t tmp;
+	uint32_t tmp_ach_as[DRAM_CH_CNT][SLICE_CNT];
+
+	ddr_setval_ach_as(_reg_PHY_RX_CAL_X[9], 0x00);
+	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x00);
+	ddr_setval_ach_as(_reg_PHY_RX_CAL_SAMPLE_WAIT, 0x0f);
+
+	retry = 0;
+	while (retry < 4096) {
+		if ((retry & 0xff) == 0) {
+			ddr_setval_ach_as(_reg_SC_PHY_RX_CAL_START, 0x01);
+		}
+		foreach_vch(ch)
+		for (slice = 0; slice < SLICE_CNT; slice++)
+			tmp_ach_as[ch][slice] =
+			    ddr_getval_s(ch, slice, _reg_PHY_RX_CAL_X[9]);
+
+		complete = 1;
+		foreach_vch(ch) {
+			for (slice = 0; slice < SLICE_CNT; slice++) {
+				tmp = tmp_ach_as[ch][slice];
+				tmp = (tmp & 0x3f) + ((tmp >> 6) & 0x3f);
+				if (((prr_product == PRR_PRODUCT_H3) &&
+				     (prr_cut > PRR_PRODUCT_11)) ||
+				    (prr_product == PRR_PRODUCT_M3N) ||
+				    (prr_product == PRR_PRODUCT_V3H)) {
+					if (tmp != 0x3E)
+						complete = 0;
+				} else {
+					if (tmp != 0x40)
+						complete = 0;
+				}
+			}
+		}
+		if (complete)
+			break;
+
+		retry++;
+	}
+
+	return (complete == 0);
+}
+
+/* adjust rddqs latency */
+static void adjust_rddqs_latency(void)
+{
+	uint32_t ch, slice;
+	uint32_t dly;
+	uint32_t maxlatx2;
+	uint32_t tmp;
+	uint32_t rdlat_adjx2[SLICE_CNT];
+
+	foreach_vch(ch) {
+		maxlatx2 = 0;
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX,
+				     0x00);
+
+			dly =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_RDDQS_GATE_SLAVE_DELAY);
+			tmp =
+			    ddr_getval_s(ch, slice,
+					 _reg_PHY_RDDQS_LATENCY_ADJUST);
+			/* note gate_slave_delay[9] is always 0 */
+			tmp = (tmp << 1) + (dly >> 8);
+			rdlat_adjx2[slice] = tmp;
+			if (maxlatx2 < tmp)
+				maxlatx2 = tmp;
+		}
+		maxlatx2 = ((maxlatx2 + 1) >> 1) << 1;
+		for (slice = 0; slice < SLICE_CNT; slice++) {
+			tmp = maxlatx2 - rdlat_adjx2[slice];
+			tmp = (tmp >> 1);
+			if (tmp) {
+				ddr_setval_s(ch, slice, _reg_PHY_RPTR_UPDATE,
+					     ddr_getval_s(ch, slice,
+							  _reg_PHY_RPTR_UPDATE)
+					     + 1);
+			}
+		}
+	}
+}
+
+/* adjust wpath latency */
+static void adjust_wpath_latency(void)
+{
+	uint32_t ch, cs, slice;
+	uint32_t dly;
+	uint32_t wpath_add;
+	const uint32_t _par_EARLY_THRESHOLD_VAL = 0x180;
+
+	foreach_vch(ch) {
+		for (slice = 0; slice < SLICE_CNT; slice += 1) {
+			for (cs = 0; cs < CS_CNT; cs++) {
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_PER_CS_TRAINING_INDEX,
+					     cs);
+				ddr_getval_s(ch, slice,
+					     _reg_PHY_PER_CS_TRAINING_INDEX);
+				dly =
+				    ddr_getval_s(ch, slice,
+						 _reg_PHY_CLK_WRDQS_SLAVE_DELAY);
+				if (dly <= _par_EARLY_THRESHOLD_VAL)
+					continue;
+
+				wpath_add =
+				    ddr_getval_s(ch, slice,
+						 _reg_PHY_WRITE_PATH_LAT_ADD);
+				ddr_setval_s(ch, slice,
+					     _reg_PHY_WRITE_PATH_LAT_ADD,
+					     wpath_add - 1);
+			}
+		}
+	}
+}
+
+/* DDR Initialize entry */
+int32_t rcar_dram_init(void)
+{
+	uint32_t ch, cs;
+	uint32_t data_l;
+	uint32_t bus_mbps, bus_mbpsdiv;
+	uint32_t tmp_tccd;
+	uint32_t failcount;
+	uint32_t cnf_boardtype;
+
+	/* Thermal sensor setting */
+	data_l = mmio_read_32(CPG_MSTPSR5);
+	if (data_l & BIT(22)) {	/*  case THS/TSC Standby */
+		data_l &= ~BIT(22);
+		cpg_write_32(CPG_SMSTPCR5, data_l);
+		while (mmio_read_32(CPG_MSTPSR5) & BIT(22))
+			;  /*  wait bit=0 */
+	}
+
+	/* THCTR Bit6: PONM=0 , Bit0: THSST=0   */
+	data_l = mmio_read_32(THS1_THCTR);
+	if (data_l & 0x00000040U) {
+		data_l = data_l & 0xFFFFFFBEU;
+	} else {
+		data_l = data_l | BIT(1);
+	}
+
+	mmio_write_32(THS1_THCTR, data_l);
+
+	/* Judge product and cut */
+#ifdef RCAR_DDR_FIXED_LSI_TYPE
+#if (RCAR_LSI == RCAR_AUTO)
+	prr_product = mmio_read_32(PRR) & PRR_PRODUCT_MASK;
+	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
+#else /* RCAR_LSI */
+#ifndef RCAR_LSI_CUT
+	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
+#endif /* RCAR_LSI_CUT */
+#endif /* RCAR_LSI */
+#else /* RCAR_DDR_FIXED_LSI_TYPE */
+	prr_product = mmio_read_32(PRR) & PRR_PRODUCT_MASK;
+	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
+#endif /* RCAR_DDR_FIXED_LSI_TYPE */
+
+	if (prr_product == PRR_PRODUCT_H3) {
+		if (prr_cut <= PRR_PRODUCT_11) {
+			p_ddr_regdef_tbl =
+				(const uint32_t *)&DDR_REGDEF_TBL[0][0];
+		} else {
+			p_ddr_regdef_tbl =
+				(const uint32_t *)&DDR_REGDEF_TBL[2][0];
+		}
+	} else if (prr_product == PRR_PRODUCT_M3) {
+		p_ddr_regdef_tbl =
+			(const uint32_t *)&DDR_REGDEF_TBL[1][0];
+	} else if ((prr_product == PRR_PRODUCT_M3N) ||
+		   (prr_product == PRR_PRODUCT_V3H)) {
+		p_ddr_regdef_tbl =
+			(const uint32_t *)&DDR_REGDEF_TBL[3][0];
+	} else {
+		FATAL_MSG("BL2: DDR:Unknown Product\n");
+		return 0xff;
+	}
+
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30))) {
+		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
+	} else {
+		mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
+	}
+
+	/* Judge board type */
+	cnf_boardtype = boardcnf_get_brd_type();
+	if (cnf_boardtype >= BOARDNUM) {
+		FATAL_MSG("BL2: DDR:Unknown Board\n");
+		return 0xff;
+	}
+	board_cnf = (const struct _boardcnf *)&boardcnfs[cnf_boardtype];
+
+/* RCAR_DRAM_SPLIT_2CH           (2U) */
+#if RCAR_DRAM_SPLIT == 2
+	/* H3(Test for future H3-N): Swap ch2 and ch1 for 2ch-split */
+	if ((prr_product == PRR_PRODUCT_H3) && (board_cnf->phyvalid == 0x05)) {
+		mmio_write_32(DBSC_DBMEMSWAPCONF0, 0x00000006);
+		ddr_phyvalid = 0x03;
+	} else {
+		ddr_phyvalid = board_cnf->phyvalid;
+	}
+#else /* RCAR_DRAM_SPLIT_2CH */
+	ddr_phyvalid = board_cnf->phyvalid;
+#endif /* RCAR_DRAM_SPLIT_2CH */
+
+	max_density = 0;
+
+	for (cs = 0; cs < CS_CNT; cs++) {
+		ch_have_this_cs[cs] = 0;
+	}
+
+	foreach_ech(ch)
+	for (cs = 0; cs < CS_CNT; cs++)
+		ddr_density[ch][cs] = 0xff;
+
+	foreach_vch(ch) {
+		for (cs = 0; cs < CS_CNT; cs++) {
+			data_l = board_cnf->ch[ch].ddr_density[cs];
+			ddr_density[ch][cs] = data_l;
+
+			if (data_l == 0xff)
+				continue;
+			if (data_l > max_density)
+				max_density = data_l;
+			if ((cs == 1) && (prr_product == PRR_PRODUCT_H3) &&
+			    (prr_cut <= PRR_PRODUCT_11))
+				continue;
+			ch_have_this_cs[cs] |= (1U << ch);
+		}
+	}
+
+	/* Judge board clock frequency (in MHz) */
+	boardcnf_get_brd_clk(cnf_boardtype, &brd_clk, &brd_clkdiv);
+	if ((brd_clk / brd_clkdiv) > 25) {
+		brd_clkdiva = 1;
+	} else {
+		brd_clkdiva = 0;
+	}
+
+	/* Judge ddr operating frequency clock(in Mbps) */
+	boardcnf_get_ddr_mbps(cnf_boardtype, &ddr_mbps, &ddr_mbpsdiv);
+
+	ddr0800_mul = CLK_DIV(800, 2, brd_clk, brd_clkdiv * (brd_clkdiva + 1));
+
+	ddr_mul = CLK_DIV(ddr_mbps, ddr_mbpsdiv * 2, brd_clk,
+			  brd_clkdiv * (brd_clkdiva + 1));
+
+	/* Adjust tccd */
+	data_l = (0x00006000 & mmio_read_32(RST_MODEMR)) >> 13;
+	bus_mbps = 0;
+	bus_mbpsdiv = 0;
+	switch (data_l) {
+	case 0:
+		bus_mbps = brd_clk * 0x60 * 2;
+		bus_mbpsdiv = brd_clkdiv * 1;
+		break;
+	case 1:
+		bus_mbps = brd_clk * 0x50 * 2;
+		bus_mbpsdiv = brd_clkdiv * 1;
+		break;
+	case 2:
+		bus_mbps = brd_clk * 0x40 * 2;
+		bus_mbpsdiv = brd_clkdiv * 1;
+		break;
+	case 3:
+		bus_mbps = brd_clk * 0x60 * 2;
+		bus_mbpsdiv = brd_clkdiv * 2;
+		break;
+	default:
+		bus_mbps = brd_clk * 0x60 * 2;
+		bus_mbpsdiv = brd_clkdiv * 2;
+		break;
+	}
+	tmp_tccd = CLK_DIV(ddr_mbps * 8, ddr_mbpsdiv, bus_mbps, bus_mbpsdiv);
+	if (8 * ddr_mbps * bus_mbpsdiv != tmp_tccd * bus_mbps * ddr_mbpsdiv)
+		tmp_tccd = tmp_tccd + 1;
+
+	if (tmp_tccd < 8)
+		ddr_tccd = 8;
+	else
+		ddr_tccd = tmp_tccd;
+
+	NOTICE("BL2: DDR%d(%s)\n", ddr_mbps / ddr_mbpsdiv, RCAR_DDR_VERSION);
+
+	MSG_LF("Start\n");
+
+	/* PLL Setting */
+	pll3_control(1);
+
+	/* initialize DDR */
+	data_l = init_ddr();
+	if (data_l == ddr_phyvalid) {
+		failcount = 0;
+	} else {
+		failcount = 1;
+	}
+
+	foreach_vch(ch)
+	    mmio_write_32(DBSC_DBPDLK(ch), 0x00000000);
+	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
+	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30))) {
+		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
+	} else {
+		mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
+	}
+
+	if (failcount == 0) {
+		return INITDRAM_OK;
+	} else {
+		return INITDRAM_NG;
+	}
+}
+
+void pvtcode_update(void)
+{
+	uint32_t ch;
+	uint32_t data_l;
+	uint32_t pvtp[4], pvtn[4], pvtp_init, pvtn_init;
+	int32_t pvtp_tmp, pvtn_tmp;
+
+	foreach_vch(ch) {
+		pvtn_init = (tcal.tcomp_cal[ch] & 0xFC0) >> 6;
+		pvtp_init = (tcal.tcomp_cal[ch] & 0x03F) >> 0;
+
+		if (8912 * pvtp_init > 44230) {
+			pvtp_tmp = (5000 + 8912 * pvtp_init - 44230) / 10000;
+		} else {
+			pvtp_tmp =
+			    -((-(5000 + 8912 * pvtp_init - 44230)) / 10000);
+		}
+		pvtn_tmp = (5000 + 5776 * pvtn_init + 30280) / 10000;
+
+		pvtn[ch] = pvtn_tmp + pvtn_init;
+		pvtp[ch] = pvtp_tmp + pvtp_init;
+
+		if (pvtn[ch] > 63) {
+			pvtn[ch] = 63;
+			pvtp[ch] =
+			    (pvtp_tmp) * (63 - 6 * pvtn_tmp -
+					  pvtn_init) / (pvtn_tmp) +
+			    6 * pvtp_tmp + pvtp_init;
+		}
+		if ((prr_product == PRR_PRODUCT_H3) &&
+		    (prr_cut <= PRR_PRODUCT_11)) {
+			data_l = pvtp[ch] | (pvtn[ch] << 6) |
+				 (tcal.tcomp_cal[ch] & 0xfffff000);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
+					 data_l | 0x00020000);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
+					 data_l);
+		} else {
+			data_l = pvtp[ch] | (pvtn[ch] << 6) | 0x00015000;
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
+					 data_l | 0x00020000);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
+					 data_l);
+			reg_ddrphy_write(ch,
+					 ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
+					 data_l);
+		}
+	}
+}
+
+void pvtcode_update2(void)
+{
+	uint32_t ch;
+
+	foreach_vch(ch) {
+		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
+				 tcal.init_cal[ch] | 0x00020000);
+		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
+				 tcal.init_cal[ch]);
+		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
+				 tcal.init_cal[ch]);
+		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
+				 tcal.init_cal[ch]);
+		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
+				 tcal.init_cal[ch]);
+	}
+}
+
+void ddr_padcal_tcompensate_getinit(uint32_t override)
+{
+	uint32_t ch;
+	uint32_t data_l;
+	uint32_t pvtp, pvtn;
+
+	tcal.init_temp = 0;
+	for (ch = 0; ch < 4; ch++) {
+		tcal.init_cal[ch] = 0;
+		tcal.tcomp_cal[ch] = 0;
+	}
+
+	foreach_vch(ch) {
+		tcal.init_cal[ch] = ddr_getval(ch, _reg_PHY_PAD_TERM_X[1]);
+		tcal.tcomp_cal[ch] = ddr_getval(ch, _reg_PHY_PAD_TERM_X[1]);
+	}
+
+	if (!override) {
+		data_l = mmio_read_32(THS1_TEMP);
+		if (data_l < 2800) {
+			tcal.init_temp =
+			    (143 * (int32_t)data_l - 359000) / 1000;
+		} else {
+			tcal.init_temp =
+			    (121 * (int32_t)data_l - 296300) / 1000;
+		}
+
+		foreach_vch(ch) {
+			pvtp = (tcal.init_cal[ch] >> 0) & 0x000003F;
+			pvtn = (tcal.init_cal[ch] >> 6) & 0x000003F;
+			if ((int32_t)pvtp >
+			    ((tcal.init_temp * 29 - 3625) / 1000))
+				pvtp =
+				    (int32_t)pvtp +
+				    ((3625 - tcal.init_temp * 29) / 1000);
+			else
+				pvtp = 0;
+
+			if ((int32_t)pvtn >
+			    ((tcal.init_temp * 54 - 6750) / 1000))
+				pvtn =
+				    (int32_t)pvtn +
+				    ((6750 - tcal.init_temp * 54) / 1000);
+			else
+				pvtn = 0;
+
+			if ((prr_product == PRR_PRODUCT_H3) &&
+			    (prr_cut <= PRR_PRODUCT_11)) {
+				tcal.init_cal[ch] =
+				    (tcal.init_cal[ch] & 0xfffff000) |
+				    (pvtn << 6) |
+				    pvtp;
+			} else {
+				tcal.init_cal[ch] =
+				    0x00015000 | (pvtn << 6) | pvtp;
+			}
+		}
+		tcal.init_temp = 125;
+	}
+}
+
+#ifndef ddr_qos_init_setting
+/* For QoS init */
+uint8_t get_boardcnf_phyvalid(void)
+{
+	return ddr_phyvalid;
+}
+#endif /* ddr_qos_init_setting */
diff --git a/drivers/renesas/common/ddr/ddr_b/boot_init_dram_config.c b/drivers/renesas/common/ddr/ddr_b/boot_init_dram_config.c
new file mode 100644
index 0000000..bbb0200
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_b/boot_init_dram_config.c
@@ -0,0 +1,2108 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation.
+ * All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RZG_SOC
+#define RZG_SOC		0
+#endif
+
+#if (RZG_SOC == 1)
+#define BOARDNUM 4
+#else
+
+#include <board.h>
+
+#define BOARDNUM 22
+#endif /* RZG_SOC == 1 */
+#define BOARD_JUDGE_AUTO
+
+#ifdef BOARD_JUDGE_AUTO
+static uint32_t _board_judge(void);
+
+static uint32_t boardcnf_get_brd_type(void)
+{
+	return _board_judge();
+}
+#else
+static uint32_t boardcnf_get_brd_type(void)
+{
+	return 1;
+}
+#endif
+
+#define DDR_FAST_INIT
+
+struct _boardcnf_ch {
+	uint8_t ddr_density[CS_CNT];
+	uint64_t ca_swap;
+	uint16_t dqs_swap;
+	uint32_t dq_swap[SLICE_CNT];
+	uint8_t dm_swap[SLICE_CNT];
+	uint16_t wdqlvl_patt[16];
+	int8_t cacs_adj[16];
+	int8_t dm_adj_w[SLICE_CNT];
+	int8_t dq_adj_w[SLICE_CNT * 8];
+	int8_t dm_adj_r[SLICE_CNT];
+	int8_t dq_adj_r[SLICE_CNT * 8];
+};
+
+struct _boardcnf {
+	uint8_t phyvalid;
+	uint8_t dbi_en;
+	uint16_t cacs_dly;
+	int16_t cacs_dly_adj;
+	uint16_t dqdm_dly_w;
+	uint16_t dqdm_dly_r;
+	struct _boardcnf_ch ch[DRAM_CH_CNT];
+};
+
+#define WDQLVL_PAT {\
+	0x00AA,\
+	0x0055,\
+	0x00AA,\
+	0x0155,\
+	0x01CC,\
+	0x0133,\
+	0x00CC,\
+	0x0033,\
+	0x00F0,\
+	0x010F,\
+	0x01F0,\
+	0x010F,\
+	0x00F0,\
+	0x00F0,\
+	0x000F,\
+	0x010F}
+
+#if (RZG_SOC == 1)
+static const struct _boardcnf boardcnfs[BOARDNUM] = {
+	{
+/* boardcnf[0] HopeRun HiHope RZ/G2M 16Gbit/1rank/2ch board with G2M SoC */
+	 .phyvalid = 0x03U,
+	 .dbi_en = 0x01U,
+	 .cacs_dly = 0x02c0U,
+	 .cacs_dly_adj = 0x0U,
+	 .dqdm_dly_w = 0x0300U,
+	 .dqdm_dly_r = 0x00a0U,
+	 .ch = {
+		{
+		 { 0x04U, 0xffU },
+		 0x00345201UL,
+		 0x3201U,
+		 { 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+		 { 0x08U, 0x08U, 0x08U, 0x08U },
+		 WDQLVL_PAT,
+		 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 }
+		},
+		{
+		 { 0x04U, 0xffU },
+		 0x00302154UL,
+		 0x2310U,
+		 { 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+		 { 0x08U, 0x08U, 0x08U, 0x08U },
+		 WDQLVL_PAT,
+		 { 0, 0, 0, 0, 0, 0, 0, 0,  0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 }
+		}
+		}
+	},
+/* boardcnf[1] HopeRun HiHope RZ/G2M 8Gbit/2rank/2ch board with G2M SoC */
+	{
+	 0x03U,
+	 0x01U,
+	 0x02c0U,
+	 0x0U,
+	 0x0300U,
+	 0x00a0U,
+	{
+		{
+		 { 0x02U, 0x02U },
+		 0x00345201UL,
+		 0x3201U,
+		 { 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+		 { 0x08U, 0x08U, 0x08U, 0x08U },
+		 WDQLVL_PAT,
+		 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 }
+		},
+		{
+		 { 0x02U, 0x02U },
+		 0x00302154UL,
+		 0x2310,
+		 { 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+		 { 0x08U, 0x08U, 0x08U, 0x08U },
+		 WDQLVL_PAT,
+		 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+		 { 0, 0, 0, 0 },
+		 { 0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0,
+		   0, 0, 0, 0, 0, 0, 0, 0 },
+		{ 0, 0, 0, 0 },
+		{ 0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0 }
+		}
+	}
+	},
+/* boardcnf[2] HopeRun HiHope RZ/G2H board 16Gbit/1rank/2ch */
+	{
+		0x05U,
+		0x01U,
+		0x0300U,
+		0,
+		0x0300U,
+		0x00a0U,
+		{
+			{
+				{ 0x04U, 0xffU },
+				0x00345201UL,
+				0x3201U,
+				{ 0x01672543U, 0x45367012U, 0x45632107U, 0x60715234U },
+				{ 0x08U, 0x08U, 0x08U, 0x08U },
+				WDQLVL_PAT,
+				{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 }
+			},
+			{
+				{ 0x04U, 0xffU },
+				0x00302154UL,
+				0x2310U,
+				{ 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+				{ 0x08U, 0x08U, 0x08U, 0x08U },
+				WDQLVL_PAT,
+				{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 }
+			},
+			{
+				{ 0x04U, 0xffU },
+				0x00302154UL,
+				0x2310U,
+				{ 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+				{ 0x08U, 0x08U, 0x08U, 0x08U },
+				WDQLVL_PAT,
+				{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 }
+			},
+			{
+				{ 0xffU, 0xffU },
+				0UL,
+				0U,
+				{ 0U, 0U, 0U, 0U },
+				{ 0U, 0U, 0U, 0U },
+				WDQLVL_PAT,
+				{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 }
+			}
+		}
+	},
+/* boardcnf[3] HopeRun HiHope RZ/G2N board 16Gbit/2rank/1ch */
+	{
+		0x01U,
+		0x01U,
+		0x0300U,
+		0,
+		0x0300U,
+		0x00a0U,
+		{
+			{
+				{ 0x04U, 0x04U },
+				0x00345201UL,
+				0x3201U,
+				{ 0x01672543U, 0x45361207U, 0x45632107U, 0x60715234U },
+				{ 0x08U, 0x08U, 0x08U, 0x08U },
+				WDQLVL_PAT,
+				{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 },
+				{ 0, 0, 0, 0 },
+				{ 0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0,
+				  0, 0, 0, 0, 0, 0, 0, 0 }
+			}
+		}
+	},
+};
+#else
+static const struct _boardcnf boardcnfs[BOARDNUM] = {
+	{
+/* boardcnf[0] RENESAS SALVATOR-X board with M3-W/SIP */
+	 .phyvalid = 0x03,
+	 .dbi_en = 0x01,
+	 .cacs_dly = 0x02c0,
+	 .cacs_dly_adj = 0,
+	 .dqdm_dly_w = 0x0300,
+	 .dqdm_dly_r = 0x00a0,
+	 .ch = {
+		{
+		 {0x02, 0x02},
+		 0x00543210U,
+		 0x3201U,
+		 {0x70612543, 0x43251670, 0x45326170, 0x10672534},
+		 {0x08, 0x08, 0x08, 0x08},
+		 WDQLVL_PAT,
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0},
+		 {0, 0, 0, 0},
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0},
+		 {0, 0, 0, 0},
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0}
+		 },
+
+		{
+		 {0x02, 0x02},
+		 0x00543210,
+		 0x2310,
+		 {0x01327654, 0x34526107, 0x35421670, 0x70615324},
+		 {0x08, 0x08, 0x08, 0x08},
+		 WDQLVL_PAT,
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0},
+		 {0, 0, 0, 0},
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0},
+		 {0, 0, 0, 0},
+		 {0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0,
+		  0, 0, 0, 0, 0, 0, 0, 0}
+		}
+		}
+	 },
+/* boardcnf[1] RENESAS KRIEK board with M3-W/SoC */
+	{
+	 0x03,
+	 0x01,
+	 0x2c0,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00345201,
+	   0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[2] RENESAS SALVATOR-X board with H3 Ver.1.x/SIP(8Gbit 1rank) */
+	{
+	 0x0f,
+	 0x00,
+	 0x300,
+	 -320,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x3210,
+	   {0x20741365, 0x34256107, 0x57460321, 0x70614532},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x3102,
+	   {0x23547610, 0x34526107, 0x67452310, 0x32106754},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x0213,
+	   {0x30216754, 0x67453210, 0x70165243, 0x07162345},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x0213,
+	   {0x01327654, 0x70615432, 0x54760123, 0x07162345},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[3] RENESAS Starter Kit board with M3-W/SIP(8Gbit 1rank) */
+	{
+	 0x03,
+	 0x01,
+	 0x02c0,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x02, 0xFF},
+	   0x00543210U,
+	   0x3201,
+	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xFF},
+	   0x00543210,
+	   0x2310,
+	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[4] RENESAS SALVATOR-M(1rank) board with H3 Ver.1.x/SoC */
+	{
+	 0x0f,
+	 0x00,
+	 0x2c0,
+	 -320,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0xff},
+	   0x00315024,
+	   0x3120,
+	   {0x30671254, 0x26541037, 0x17054623, 0x12307645},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00025143,
+	   0x3210,
+	   {0x70613542, 0x16245307, 0x30712645, 0x21706354},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00523104,
+	   0x2301,
+	   {0x70613542, 0x16245307, 0x30712645, 0x21706354},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00153402,
+	   0x2031,
+	   {0x30671254, 0x26541037, 0x17054623, 0x12307645},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[5] RENESAS KRIEK-1rank board with M3-W/SoC */
+	{
+	 0x03,
+	 0x01,
+	 0x2c0,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0xff},
+	   0x00345201,
+	   0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[6] RENESAS SALVATOR-X board with H3 Ver.1.x/SIP(8Gbit 2rank) */
+	{
+	 0x0f,
+	 0x00,
+	 0x300,
+	 -320,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x3210,
+	   {0x20741365, 0x34256107, 0x57460321, 0x70614532},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x3102,
+	   {0x23547610, 0x34526107, 0x67452310, 0x32106754},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x0213,
+	   {0x30216754, 0x67453210, 0x70165243, 0x07162345},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x0213,
+	   {0x01327654, 0x70615432, 0x54760123, 0x07162345},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/*
+ * boardcnf[7] RENESAS SALVATOR-X board with
+ * H3 Ver.2.0 or later/SIP(8Gbit 1rank)
+ */
+	{
+	 0x0f,
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x2310,
+	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00105432,
+	   0x3210,
+	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/*
+ * boardcnf[8] RENESAS SALVATOR-X board with
+ * H3 Ver.2.0 or later/SIP(8Gbit 2rank)
+ */
+	{
+#if RCAR_DRAM_CHANNEL == 5
+	 0x05,
+#else
+	 0x0f,
+#endif
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x2310,
+	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#if ((RCAR_DRAM_CHANNEL == 5) && (RCAR_DRAM_SPLIT == 2))
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x2301,
+	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#else
+	{
+	   {0x02, 0x02},
+	   0x00105432,
+	   0x3210,
+	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#endif
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x2301,
+	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00543210,
+	   0x2301,
+	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[9] RENESAS SALVATOR-MS(1rank) board with H3 Ver.2.0 or later/SoC */
+	{
+	 0x0f,
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x3210,
+	   {0x27645310, 0x75346210, 0x53467210, 0x23674510},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x23764510, 0x43257610, 0x43752610, 0x37652401},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {-128, -128, -128, -128, -128, -128, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00452103,
+	   0x3210,
+	   {0x32764510, 0x43257610, 0x43752610, 0x26573401},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0xff},
+	   0x00520413,
+	   0x2301,
+	   {0x47652301, 0x75346210, 0x53467210, 0x32674501},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {30, 30, 30, 30, 30, 30, 30, 30,
+	    30, 30},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[10] RENESAS Kriek(2rank) board with M3-N/SoC */
+	{
+	 0x01,
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00345201,
+	   0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[11] RENESAS SALVATOR-X board with M3-N/SIP(8Gbit 2rank) */
+	{
+	 0x01,
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+#if (RCAR_DRAM_LPDDR4_MEMCONF == 2)
+	   {0x04, 0x04},
+#else
+	   {0x02, 0x02},
+#endif
+	   0x00342501,
+	   0x3201,
+	   {0x10672534, 0x43257106, 0x34527601, 0x71605243},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[12] RENESAS CONDOR board with V3H/SoC */
+	{
+	 0x01,
+	 0x1,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00501342,
+	   0x3201,
+	   {0x70562134, 0x34526071, 0x23147506, 0x12430567},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[13] RENESAS KRIEK board with PM3/SoC */
+	{
+	 0x05,
+	 0x00,
+	 0x2c0,
+	 -320,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00345201,
+	   0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0xff, 0xff},
+	   0,
+	   0,
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[14] SALVATOR-X board with H3 Ver.2.0 or later/SIP(16Gbit 1rank) */
+	{
+#if RCAR_DRAM_CHANNEL == 5
+	 0x05,
+#else
+	 0x0f,
+#endif
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x04, 0xff},
+	   0x00543210,
+	   0x2310,
+	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#if ((RCAR_DRAM_CHANNEL == 5) && (RCAR_DRAM_SPLIT == 2))
+	{
+	   {0x04, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#else
+	{
+	   {0x04, 0xff},
+	   0x00105432,
+	   0x3210,
+	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+#endif
+	{
+	   {0x04, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0xff},
+	   0x00543210,
+	   0x2301,
+	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[15] RENESAS KRIEK board with H3N */
+	{
+	 0x05,
+	 0x01,
+	 0x300,
+	 0,
+	 0x300,
+	 0x0a0,
+	{
+	{
+	   {0x02, 0x02},
+	   0x00345201,
+	   0x3201,
+	   {0x01672543, 0x45367012, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x02, 0x02},
+	   0x00302154,
+	   0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0xff, 0xff},
+	   0,
+	   0,
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[16] RENESAS KRIEK-P2P board with M3-W/SoC */
+	{
+	 0x03,
+	 0x01,
+	 0x0320,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0x04},
+	    0x520314FFFF523041,
+	    0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	    WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0x04},
+	    0x314250FFFF312405,
+	    0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	    WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	 },
+/* boardcnf[17] RENESAS KRIEK-P2P board with M3-N/SoC */
+	{
+	 0x01,
+	 0x01,
+	 0x0300,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0x04},
+	    0x520314FFFF523041,
+	    0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	    WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	},
+/* boardcnf[18] RENESAS SALVATOR-X board with M3-W/SIP(16Gbit 2rank) */
+	{
+	 0x03,
+	 0x01,
+	 0x02c0,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0x04},
+	    0x00543210,
+	    0x3201,
+	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0x04},
+	    0x00543210,
+	    0x2310,
+	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	},
+/* boardcnf[19] RENESAS SALVATOR-X board with M3-W/SIP(16Gbit 1rank) */
+	{
+	 0x03,
+	 0x01,
+	 0x02c0,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0xff},
+	    0x00543210,
+	    0x3201,
+	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0xff},
+	    0x00543210,
+	    0x2310,
+	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	},
+/* boardcnf[20] RENESAS KRIEK 16Gbit/2rank/2ch board with M3-W/SoC */
+	{
+	 0x03,
+	 0x01,
+	 0x02c0,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0x04},
+	    0x00345201,
+	    0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	    WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0x04},
+	    0x00302154,
+	    0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	},
+/* boardcnf[21] RENESAS KRIEK 16Gbit/1rank/2ch board with M3-W/SoC */
+	{
+	 0x03,
+	 0x01,
+	 0x02c0,
+	 0,
+	 0x0300,
+	 0x00a0,
+	{
+	{
+	   {0x04, 0xff},
+	    0x00345201,
+	    0x3201,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	   },
+	{
+	   {0x04, 0xff},
+	    0x00302154,
+	    0x2310,
+	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
+	   {0x08, 0x08, 0x08, 0x08},
+	   WDQLVL_PAT,
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0},
+	   {0, 0, 0, 0},
+	   {0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0,
+	    0, 0, 0, 0, 0, 0, 0, 0}
+	}
+	}
+	}
+};
+#endif /* RZG_SOC == 1 */
+
+void boardcnf_get_brd_clk(uint32_t brd, uint32_t *clk, uint32_t *div)
+{
+	uint32_t md;
+
+	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_10)) {
+		*clk = 50;
+		*div = 3;
+	} else {
+		md = (mmio_read_32(RST_MODEMR) >> 13) & 0x3;
+		switch (md) {
+		case 0x0:
+			*clk = 50;
+			*div = 3;
+			break;
+		case 0x1:
+			*clk = 60;
+			*div = 3;
+			break;
+		case 0x2:
+			*clk = 75;
+			*div = 3;
+			break;
+		case 0x3:
+			*clk = 100;
+			*div = 3;
+			break;
+		}
+	}
+	(void)brd;
+}
+
+void boardcnf_get_ddr_mbps(uint32_t brd, uint32_t *mbps, uint32_t *div)
+{
+	uint32_t md;
+
+	if (prr_product == PRR_PRODUCT_V3H) {
+		md = (mmio_read_32(RST_MODEMR) >> 19) & 0x1;
+		md = (md | (md << 1)) & 0x3; /* 0 or 3 */
+	} else {
+		md = (mmio_read_32(RST_MODEMR) >> 17) & 0x5;
+		md = (md | (md >> 1)) & 0x3;
+	}
+	switch (md) {
+	case 0x0:
+		*mbps = 3200;
+		*div = 1;
+		break;
+	case 0x1:
+		*mbps = 2800;
+		*div = 1;
+		break;
+	case 0x2:
+		*mbps = 2400;
+		*div = 1;
+		break;
+	case 0x3:
+		*mbps = 1600;
+		*div = 1;
+		break;
+	}
+	(void)brd;
+}
+
+#define _def_REFPERIOD  1890
+
+#define M3_SAMPLE_TT_A84        0xB866CC10, 0x3B250421
+#define M3_SAMPLE_TT_A85        0xB866CC10, 0x3AA50421
+#define M3_SAMPLE_TT_A86        0xB866CC10, 0x3AA48421
+#define M3_SAMPLE_FF_B45        0xB866CC10, 0x3AB00C21
+#define M3_SAMPLE_FF_B49        0xB866CC10, 0x39B10C21
+#define M3_SAMPLE_FF_B56        0xB866CC10, 0x3AAF8C21
+#define M3_SAMPLE_SS_E24        0xB866CC10, 0x3BA39421
+#define M3_SAMPLE_SS_E28        0xB866CC10, 0x3C231421
+#define M3_SAMPLE_SS_E32        0xB866CC10, 0x3C241421
+
+static const uint32_t termcode_by_sample[20][3] = {
+	{M3_SAMPLE_TT_A84, 0x000158D5},
+	{M3_SAMPLE_TT_A85, 0x00015955},
+	{M3_SAMPLE_TT_A86, 0x00015955},
+	{M3_SAMPLE_FF_B45, 0x00015690},
+	{M3_SAMPLE_FF_B49, 0x00015753},
+	{M3_SAMPLE_FF_B56, 0x00015793},
+	{M3_SAMPLE_SS_E24, 0x00015996},
+	{M3_SAMPLE_SS_E28, 0x000159D7},
+	{M3_SAMPLE_SS_E32, 0x00015997},
+	{0xFFFFFFFF, 0xFFFFFFFF, 0x0001554F}
+};
+
+#ifdef BOARD_JUDGE_AUTO
+/*
+ * SAMPLE board detect function
+ */
+#define PFC_PMMR	0xE6060000U
+#define PFC_PUEN5	0xE6060414U
+#define PFC_PUEN6	0xE6060418U
+#define PFC_PUD5	0xE6060454U
+#define PFC_PUD6	0xE6060458U
+#define GPIO_INDT5	0xE605500CU
+#define GPIO_GPSR6	0xE6060118U
+
+#if (RCAR_GEN3_ULCB == 0) && (RZG_SOC == 0)
+static void pfc_write_and_poll(uint32_t a, uint32_t v)
+{
+	mmio_write_32(PFC_PMMR, ~v);
+	v = ~mmio_read_32(PFC_PMMR);
+	mmio_write_32(a, v);
+	while (v != mmio_read_32(a))
+		;
+	dsb_sev();
+}
+#endif
+
+#ifndef RCAR_GEN3_ULCB
+#define RCAR_GEN3_ULCB		0
+#endif
+
+#if (RCAR_GEN3_ULCB == 0) && (RZG_SOC == 0)	/* non Starter Kit */
+
+static uint32_t opencheck_SSI_WS6(void)
+{
+	uint32_t dataL, down, up;
+	uint32_t gpsr6_bak;
+	uint32_t puen5_bak;
+	uint32_t pud5_bak;
+
+	gpsr6_bak = mmio_read_32(GPIO_GPSR6);
+	puen5_bak = mmio_read_32(PFC_PUEN5);
+	pud5_bak = mmio_read_32(PFC_PUD5);
+	dsb_sev();
+
+	dataL = (gpsr6_bak & ~BIT(15));
+	pfc_write_and_poll(GPIO_GPSR6, dataL);
+
+	/* Pull-Up/Down Enable (PUEN5[22]=1) */
+	dataL = puen5_bak;
+	dataL |= (BIT(22));
+	pfc_write_and_poll(PFC_PUEN5, dataL);
+
+	/* Pull-Down-Enable (PUD5[22]=0, PUEN5[22]=1) */
+	dataL = pud5_bak;
+	dataL &= ~(BIT(22));
+	pfc_write_and_poll(PFC_PUD5, dataL);
+	/* GPSR6[15]=SSI_WS6 */
+	rcar_micro_delay(10);
+	down = (mmio_read_32(GPIO_INDT6) >> 15) & 0x1;
+	dsb_sev();
+
+	/* Pull-Up-Enable (PUD5[22]=1, PUEN5[22]=1) */
+	dataL = pud5_bak;
+	dataL |= (BIT(22));
+	pfc_write_and_poll(PFC_PUD5, dataL);
+
+	/* GPSR6[15]=SSI_WS6 */
+	rcar_micro_delay(10);
+	up = (mmio_read_32(GPIO_INDT6) >> 15) & 0x1;
+
+	dsb_sev();
+
+	pfc_write_and_poll(GPIO_GPSR6, gpsr6_bak);
+	pfc_write_and_poll(PFC_PUEN5, puen5_bak);
+	pfc_write_and_poll(PFC_PUD5, pud5_bak);
+
+	if (down == up) {
+		/* Same = Connect */
+		return 0;
+	}
+
+	/* Diff = Open */
+	return 1;
+}
+
+#endif
+
+#if (RZG_SOC == 1)
+#define LPDDR4_2RANK   (0x01U << 25U)
+
+static uint32_t rzg2_board_judge(void)
+{
+	uint32_t brd;
+
+	switch (prr_product) {
+	case PRR_PRODUCT_M3:
+		brd = 1U;
+		if ((mmio_read_32(PRR) & PRR_CUT_MASK) != RCAR_M3_CUT_VER11) {
+			if ((mmio_read_32(GPIO_INDT5) & LPDDR4_2RANK) == 0U) {
+				brd = 0U;
+			}
+		}
+		break;
+	case PRR_PRODUCT_H3:
+		brd = 2U;
+		break;
+	case PRR_PRODUCT_M3N:
+		brd = 3U;
+		break;
+	default:
+		brd = 99U;
+	}
+
+	return brd;
+}
+#endif /* RZG_SOC == 1 */
+
+#if (RZG_SOC == 0) && (RCAR_DRAM_LPDDR4_MEMCONF != 0)
+static uint32_t ddr_rank_judge(void)
+{
+	uint32_t brd;
+
+#if (RCAR_DRAM_MEMRANK == 0)
+	int32_t ret;
+	uint32_t type = 0U;
+	uint32_t rev = 0U;
+
+	brd = 99U;
+	ret = rcar_get_board_type(&type, &rev);
+	if ((ret == 0) && (rev != 0xFFU)) {
+		if (type == (uint32_t)BOARD_SALVATOR_XS) {
+			if (rev == 0x11U) {
+				brd = 14U;
+			} else {
+				brd = 8U;
+			}
+		} else if (type == (uint32_t)BOARD_STARTER_KIT_PRE) {
+			if (rev == 0x21U) {
+				brd = 14U;
+			} else {
+				brd = 8U;
+			}
+		}
+	}
+#elif (RCAR_DRAM_MEMRANK == 1)
+	brd = 14U;
+#elif (RCAR_DRAM_MEMRANK == 2)
+	brd = 8U;
+#else
+#error Invalid value was set to RCAR_DRAM_MEMRANK
+#endif /* (RCAR_DRAM_MEMRANK == 0) */
+	return brd;
+}
+#endif /* (RCAR_DRAM_LPDDR4_MEMCONF != 0) */
+
+static uint32_t _board_judge(void)
+{
+	uint32_t brd;
+
+#if (RZG_SOC == 1)
+	brd = rzg2_board_judge();
+#else
+#if (RCAR_GEN3_ULCB == 1)
+	/* Starter Kit */
+	if (prr_product == PRR_PRODUCT_H3) {
+		if (prr_cut <= PRR_PRODUCT_11) {
+			/* RENESAS Starter Kit(H3 Ver.1.x/SIP) board */
+			brd = 2;
+		} else {
+			/* RENESAS Starter Kit(H3 Ver.2.0 or later/SIP) board */
+#if (RCAR_DRAM_LPDDR4_MEMCONF == 0)
+			brd = 7;
+#else
+			brd = ddr_rank_judge();
+#endif
+		}
+	} else if (prr_product == PRR_PRODUCT_M3) {
+		if (prr_cut >= PRR_PRODUCT_30) {
+			/* RENESAS Starter Kit (M3-W Ver.3.0/SIP) */
+			brd = 18;
+		} else {
+			/* RENESAS Starter Kit(M3-W/SIP 8Gbit 1rank) board */
+			brd = 3;
+		}
+	} else {
+		/* RENESAS Starter Kit(M3-N/SIP) board */
+		brd = 11;
+	}
+#else
+	uint32_t usb2_ovc_open;
+
+	usb2_ovc_open = opencheck_SSI_WS6();
+
+	/* RENESAS Eva-board */
+	brd = 99;
+	if (prr_product == PRR_PRODUCT_V3H) {
+		/* RENESAS Condor board */
+		brd = 12;
+	} else if (usb2_ovc_open) {
+		if (prr_product == PRR_PRODUCT_M3N) {
+			/* RENESAS Kriek board with M3-N */
+			brd = 10;
+		} else if (prr_product == PRR_PRODUCT_M3) {
+			/* RENESAS Kriek board with M3-W */
+			brd = 1;
+		} else if ((prr_product == PRR_PRODUCT_H3) &&
+			   (prr_cut <= PRR_PRODUCT_11)) {
+			/* RENESAS Kriek board with PM3 */
+			brd = 13;
+		} else if ((prr_product == PRR_PRODUCT_H3) &&
+			   (prr_cut > PRR_PRODUCT_20)) {
+			/* RENESAS Kriek board with H3N */
+			brd = 15;
+		}
+	} else {
+		if (prr_product == PRR_PRODUCT_H3) {
+			if (prr_cut <= PRR_PRODUCT_11) {
+				/* RENESAS SALVATOR-X (H3 Ver.1.x/SIP) */
+				brd = 2;
+			} else if (prr_cut < PRR_PRODUCT_30) {
+				/* RENESAS SALVATOR-X (H3 Ver.2.0/SIP) */
+				brd = 7;	//  8Gbit/1rank
+			} else {
+				/* RENESAS SALVATOR-X (H3 Ver.3.0/SIP) */
+#if (RCAR_DRAM_LPDDR4_MEMCONF == 0)
+				brd = 7;
+#else
+				brd = ddr_rank_judge();
+#endif
+			}
+		} else if (prr_product == PRR_PRODUCT_M3N) {
+			/* RENESAS SALVATOR-X (M3-N/SIP) */
+			brd = 11;
+		} else if ((prr_product == PRR_PRODUCT_M3) &&
+			   (prr_cut <= PRR_PRODUCT_20)) {
+			/* RENESAS SALVATOR-X (M3-W/SIP) */
+			brd = 0;
+		} else if ((prr_product == PRR_PRODUCT_M3) &&
+			   (prr_cut < PRR_PRODUCT_30)) {
+			/* RENESAS SALVATOR-X (M3-W Ver.1.x/SIP) */
+			brd = 19;
+		} else if ((prr_product == PRR_PRODUCT_M3) &&
+			   (prr_cut >= PRR_PRODUCT_30)) {
+			/* RENESAS SALVATOR-X (M3-W ver.3.0/SIP) */
+			brd = 18;
+		}
+	}
+#endif
+#endif /* RZG_SOC == 1 */
+
+	return brd;
+}
+#endif
diff --git a/drivers/renesas/common/ddr/ddr_b/boot_init_dram_regdef.h b/drivers/renesas/common/ddr/ddr_b/boot_init_dram_regdef.h
new file mode 100644
index 0000000..3cb1975
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_b/boot_init_dram_regdef.h
@@ -0,0 +1,95 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation.
+ * All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#define RCAR_DDR_VERSION	"rev.0.41"
+#define DRAM_CH_CNT		0x04
+#define SLICE_CNT		0x04
+#define CS_CNT			0x02
+
+/* order : CS0A, CS0B, CS1A, CS1B */
+#define CSAB_CNT		(CS_CNT * 2)
+
+/* order : CH0A, CH0B, CH1A, CH1B, CH2A, CH2B, CH3A, CH3B */
+#define CHAB_CNT		(DRAM_CH_CNT * 2)
+
+/* pll setting */
+#define CLK_DIV(a, diva, b, divb) (((a) * (divb)) / ((b) * (diva)))
+#define CLK_MUL(a, diva, b, divb) (((a) * (b)) / ((diva) * (divb)))
+
+/* for ddr deisity setting */
+#define DBMEMCONF_REG(d3, row, bank, col, dw)	\
+	(((d3) << 30) | ((row) << 24) | ((bank) << 16) | ((col) << 8) | (dw))
+
+#define DBMEMCONF_REGD(density)		\
+	(DBMEMCONF_REG((density) % 2, ((density) + 1) / \
+	2 + (29 - 3 - 10 - 2), 3, 10, 2))
+
+#define DBMEMCONF_VAL(ch, cs) (DBMEMCONF_REGD(DBMEMCONF_DENS(ch, cs)))
+
+/* refresh mode */
+#define DBSC_REFINTS		(0x0)
+
+/* system registers */
+#define CPG_FRQCRB		(CPG_BASE + 0x0004U)
+
+#define CPG_PLLECR		(CPG_BASE + 0x00D0U)
+#define CPG_MSTPSR5		(CPG_BASE + 0x003CU)
+#define CPG_SRCR4		(CPG_BASE + 0x00BCU)
+#define CPG_PLL3CR		(CPG_BASE + 0x00DCU)
+#define CPG_ZB3CKCR		(CPG_BASE + 0x0380U)
+#define CPG_FRQCRD		(CPG_BASE + 0x00E4U)
+#define CPG_SMSTPCR5		(CPG_BASE + 0x0144U)
+#define CPG_CPGWPR		(CPG_BASE + 0x0900U)
+#define CPG_SRSTCLR4		(CPG_BASE + 0x0950U)
+
+#define CPG_FRQCRB_KICK_BIT	BIT(31)
+#define CPG_PLLECR_PLL3E_BIT	BIT(3)
+#define CPG_PLLECR_PLL3ST_BIT	BIT(11)
+#define CPG_ZB3CKCR_ZB3ST_BIT	BIT(11)
+
+#define RST_BASE		(0xE6160000U)
+#define RST_MODEMR		(RST_BASE + 0x0060U)
+
+#define LIFEC_CHIPID(x)		(0xE6110040U + 0x04U * (x))
+
+/* DBSC registers */
+#include "../ddr_regs.h"
+
+#define DBSC_DBMONCONF4		0xE6793010U
+
+#define DBSC_PLL_LOCK(ch)	(0xE6794054U + 0x100U * (ch))
+#define DBSC_PLL_LOCK_0		0xE6794054U
+#define DBSC_PLL_LOCK_1		0xE6794154U
+#define DBSC_PLL_LOCK_2		0xE6794254U
+#define DBSC_PLL_LOCK_3		0xE6794354U
+
+/* STAT registers */
+#define MSTAT_SL_INIT		0xE67E8000U
+#define MSTAT_REF_ARS		0xE67E8004U
+#define MSTATQ_STATQC		0xE67E8008U
+#define MSTATQ_WTENABLE		0xE67E8030U
+#define MSTATQ_WTREFRESH	0xE67E8034U
+#define MSTATQ_WTSETTING0	0xE67E8038U
+#define MSTATQ_WTSETTING1	0xE67E803CU
+
+#define QOS_BASE1		(0xE67F0000U)
+#define QOSCTRL_RAS		(QOS_BASE1 + 0x0000U)
+#define QOSCTRL_FIXTH		(QOS_BASE1 + 0x0004U)
+#define QOSCTRL_RAEN		(QOS_BASE1 + 0x0018U)
+#define QOSCTRL_REGGD		(QOS_BASE1 + 0x0020U)
+#define QOSCTRL_DANN		(QOS_BASE1 + 0x0030U)
+#define QOSCTRL_DANT		(QOS_BASE1 + 0x0038U)
+#define QOSCTRL_EC		(QOS_BASE1 + 0x003CU)
+#define QOSCTRL_EMS		(QOS_BASE1 + 0x0040U)
+#define QOSCTRL_INSFC		(QOS_BASE1 + 0x0050U)
+#define QOSCTRL_BERR		(QOS_BASE1 + 0x0054U)
+#define QOSCTRL_RACNT0		(QOS_BASE1 + 0x0080U)
+#define QOSCTRL_STATGEN0	(QOS_BASE1 + 0x0088U)
+
+/* other module */
+#define THS1_THCTR		0xE6198020U
+#define THS1_TEMP		0xE6198028U
diff --git a/drivers/renesas/common/ddr/ddr_b/ddr_b.mk b/drivers/renesas/common/ddr/ddr_b/ddr_b.mk
new file mode 100644
index 0000000..0334780
--- /dev/null
+++ b/drivers/renesas/common/ddr/ddr_b/ddr_b.mk
@@ -0,0 +1,7 @@
+#
+# Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+BL2_SOURCES += drivers/renesas/common/ddr/ddr_b/boot_init_dram.c
diff --git a/drivers/renesas/rcar/ddr/ddr_b/ddr_regdef.h b/drivers/renesas/common/ddr/ddr_b/ddr_regdef.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_b/ddr_regdef.h
rename to drivers/renesas/common/ddr/ddr_b/ddr_regdef.h
diff --git a/drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_h3.h b/drivers/renesas/common/ddr/ddr_b/init_dram_tbl_h3.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_h3.h
rename to drivers/renesas/common/ddr/ddr_b/init_dram_tbl_h3.h
diff --git a/drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_h3ver2.h b/drivers/renesas/common/ddr/ddr_b/init_dram_tbl_h3ver2.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_h3ver2.h
rename to drivers/renesas/common/ddr/ddr_b/init_dram_tbl_h3ver2.h
diff --git a/drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_m3.h b/drivers/renesas/common/ddr/ddr_b/init_dram_tbl_m3.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_m3.h
rename to drivers/renesas/common/ddr/ddr_b/init_dram_tbl_m3.h
diff --git a/drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_m3n.h b/drivers/renesas/common/ddr/ddr_b/init_dram_tbl_m3n.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_b/init_dram_tbl_m3n.h
rename to drivers/renesas/common/ddr/ddr_b/init_dram_tbl_m3n.h
diff --git a/drivers/renesas/rcar/ddr/dram_sub_func.c b/drivers/renesas/common/ddr/dram_sub_func.c
similarity index 100%
rename from drivers/renesas/rcar/ddr/dram_sub_func.c
rename to drivers/renesas/common/ddr/dram_sub_func.c
diff --git a/drivers/renesas/rcar/ddr/dram_sub_func.h b/drivers/renesas/common/ddr/dram_sub_func.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/dram_sub_func.h
rename to drivers/renesas/common/ddr/dram_sub_func.h
diff --git a/drivers/renesas/rcar/ddr/ddr_regs.h b/drivers/renesas/common/ddr_regs.h
similarity index 100%
rename from drivers/renesas/rcar/ddr/ddr_regs.h
rename to drivers/renesas/common/ddr_regs.h
diff --git a/drivers/renesas/common/delay/micro_delay.c b/drivers/renesas/common/delay/micro_delay.c
new file mode 100644
index 0000000..a5e2a69
--- /dev/null
+++ b/drivers/renesas/common/delay/micro_delay.c
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2018-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <arch_helpers.h>
+
+#include "micro_delay.h"
+
+#define RCAR_CONV_MICROSEC		1000000U
+
+void
+#if IMAGE_BL31
+	__attribute__ ((section(".system_ram")))
+#endif
+	rcar_micro_delay(uint64_t micro_sec)
+{
+	uint64_t freq;
+	uint64_t base_count;
+	uint64_t get_count;
+	uint64_t wait_time = 0U;
+
+	freq = read_cntfrq_el0();
+	base_count = read_cntpct_el0();
+	while (micro_sec > wait_time) {
+		get_count = read_cntpct_el0();
+		wait_time = ((get_count - base_count) * RCAR_CONV_MICROSEC) / freq;
+	}
+}
diff --git a/drivers/renesas/rcar/delay/micro_delay.h b/drivers/renesas/common/delay/micro_delay.h
similarity index 100%
rename from drivers/renesas/rcar/delay/micro_delay.h
rename to drivers/renesas/common/delay/micro_delay.h
diff --git a/drivers/renesas/common/dma/dma_driver.c b/drivers/renesas/common/dma/dma_driver.c
new file mode 100644
index 0000000..44ee985
--- /dev/null
+++ b/drivers/renesas/common/dma/dma_driver.c
@@ -0,0 +1,153 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "cpg_registers.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+
+/* DMA CHANNEL setting (0/16/32) */
+#if RCAR_LSI == RCAR_V3M
+#define DMA_CH		16
+#else
+#define DMA_CH		0
+#endif
+
+#if (DMA_CH == 0)
+#define SYS_DMAC_BIT	((uint32_t)1U << 19U)
+#define DMA_BASE	(0xE6700000U)
+#elif (DMA_CH == 16)
+#define SYS_DMAC_BIT	((uint32_t)1U << 18U)
+#define DMA_BASE	(0xE7300000U)
+#elif (DMA_CH == 32)
+#define SYS_DMAC_BIT	((uint32_t)1U << 17U)
+#define DMA_BASE	(0xE7320000U)
+#else
+#define SYS_DMAC_BIT	((uint32_t)1U << 19U)
+#define DMA_BASE	(0xE6700000U)
+#endif
+
+/* DMA operation */
+#define DMA_DMAOR	(DMA_BASE + 0x0060U)
+/* DMA secure control */
+#define DMA_DMASEC	(DMA_BASE + 0x0030U)
+/* DMA channel clear */
+#define DMA_DMACHCLR	(DMA_BASE + 0x0080U)
+/* DMA source address */
+#define DMA_DMASAR	(DMA_BASE + 0x8000U)
+/* DMA destination address */
+#define DMA_DMADAR	(DMA_BASE + 0x8004U)
+/* DMA transfer count */
+#define DMA_DMATCR	(DMA_BASE + 0x8008U)
+/* DMA channel control */
+#define DMA_DMACHCR	(DMA_BASE + 0x800CU)
+/* DMA fixed destination address */
+#define DMA_DMAFIXDAR	(DMA_BASE + 0x8014U)
+
+#define DMA_USE_CHANNEL		(0x00000001U)
+#define DMAOR_INITIAL		(0x0301U)
+#define DMACHCLR_CH_ALL		(0x0000FFFFU)
+#define DMAFIXDAR_32BIT_SHIFT	(32U)
+#define DMAFIXDAR_DAR_MASK	(0x000000FFU)
+#define DMADAR_BOUNDARY_ADDR	(0x100000000ULL)
+#define DMATCR_CNT_SHIFT	(6U)
+#define DMATCR_MAX		(0x00FFFFFFU)
+#define DMACHCR_TRN_MODE	(0x00105409U)
+#define DMACHCR_DE_BIT		(0x00000001U)
+#define DMACHCR_TE_BIT		(0x00000002U)
+#define DMACHCR_CHE_BIT		(0x80000000U)
+
+#define DMA_SIZE_UNIT		FLASH_TRANS_SIZE_UNIT
+#define DMA_FRACTION_MASK	(0xFFU)
+#define DMA_DST_LIMIT		(0x10000000000ULL)
+
+/* transfer length limit */
+#define DMA_LENGTH_LIMIT	((DMATCR_MAX * (1U << DMATCR_CNT_SHIFT)) \
+				& ~DMA_FRACTION_MASK)
+
+static void dma_enable(void)
+{
+	mstpcr_write(CPG_SMSTPCR2, CPG_MSTPSR2, SYS_DMAC_BIT);
+}
+
+static void dma_setup(void)
+{
+	mmio_write_16(DMA_DMAOR, 0);
+	mmio_write_32(DMA_DMACHCLR, DMACHCLR_CH_ALL);
+}
+
+static void dma_start(uintptr_t dst, uint32_t src, uint32_t len)
+{
+	mmio_write_16(DMA_DMAOR, DMAOR_INITIAL);
+	mmio_write_32(DMA_DMAFIXDAR, (dst >> DMAFIXDAR_32BIT_SHIFT) &
+		      DMAFIXDAR_DAR_MASK);
+	mmio_write_32(DMA_DMADAR, dst & UINT32_MAX);
+	mmio_write_32(DMA_DMASAR, src);
+	mmio_write_32(DMA_DMATCR, len >> DMATCR_CNT_SHIFT);
+	mmio_write_32(DMA_DMASEC, DMA_USE_CHANNEL);
+	mmio_write_32(DMA_DMACHCR, DMACHCR_TRN_MODE);
+}
+
+static void dma_end(void)
+{
+	while ((mmio_read_32(DMA_DMACHCR) & DMACHCR_TE_BIT) == 0) {
+		if ((mmio_read_32(DMA_DMACHCR) & DMACHCR_CHE_BIT) != 0U) {
+			ERROR("BL2: DMA - Channel Address Error\n");
+			panic();
+			break;
+		}
+	}
+	/* DMA transfer Disable */
+	mmio_clrbits_32(DMA_DMACHCR, DMACHCR_DE_BIT);
+	while ((mmio_read_32(DMA_DMACHCR) & DMACHCR_DE_BIT) != 0)
+		;
+
+	mmio_write_32(DMA_DMASEC, 0);
+	mmio_write_16(DMA_DMAOR, 0);
+	mmio_write_32(DMA_DMACHCLR, DMA_USE_CHANNEL);
+}
+
+void rcar_dma_exec(uintptr_t dst, uint32_t src, uint32_t len)
+{
+	uint32_t dma_len = len;
+
+	if (len & DMA_FRACTION_MASK)
+		dma_len = (len + DMA_SIZE_UNIT) & ~DMA_FRACTION_MASK;
+
+	if (!dma_len || dma_len > DMA_LENGTH_LIMIT) {
+		ERROR("BL2: DMA - size invalid, length (0x%x)\n", dma_len);
+		panic();
+	}
+
+	if (src & DMA_FRACTION_MASK) {
+		ERROR("BL2: DMA - src address invalid (0x%x), len=(0x%x)\n",
+		      src, dma_len);
+		panic();
+	}
+
+	if ((dst & UINT32_MAX) + dma_len > DMADAR_BOUNDARY_ADDR	||
+	    (dst + dma_len > DMA_DST_LIMIT) ||
+	    (dst & DMA_FRACTION_MASK)) {
+		ERROR("BL2: DMA - dest address invalid (0x%lx), len=(0x%x)\n",
+		      dst, dma_len);
+		panic();
+	}
+
+	dma_start(dst, src, dma_len);
+	dma_end();
+}
+
+void rcar_dma_init(void)
+{
+	dma_enable();
+	dma_setup();
+}
diff --git a/drivers/renesas/common/emmc/emmc_cmd.c b/drivers/renesas/common/emmc/emmc_cmd.c
new file mode 100644
index 0000000..d255bff
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_cmd.c
@@ -0,0 +1,493 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_registers.h"
+#include "emmc_std.h"
+#include "micro_delay.h"
+
+static void emmc_little_to_big(uint8_t *p, uint32_t value)
+{
+	if (p == NULL)
+		return;
+
+	p[0] = (uint8_t) (value >> 24);
+	p[1] = (uint8_t) (value >> 16);
+	p[2] = (uint8_t) (value >> 8);
+	p[3] = (uint8_t) value;
+
+}
+
+static void emmc_softreset(void)
+{
+	int32_t loop = 10000;
+	int32_t retry = 1000;
+
+	/* flag clear */
+	mmc_drv_obj.during_cmd_processing = FALSE;
+	mmc_drv_obj.during_transfer = FALSE;
+	mmc_drv_obj.during_dma_transfer = FALSE;
+	mmc_drv_obj.state_machine_blocking = FALSE;
+	mmc_drv_obj.force_terminate = FALSE;
+	mmc_drv_obj.dma_error_flag = FALSE;
+
+	/* during operation ? */
+	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) == 0)
+		goto reset;
+
+	/* wait CMDSEQ = 0 */
+	while (loop > 0) {
+		if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) == 0)
+			break;	/* ready */
+
+		loop--;
+		if ((loop == 0) && (retry > 0)) {
+			rcar_micro_delay(1000U);	/* wait 1ms */
+			loop = 10000;
+			retry--;
+		}
+	}
+
+reset:
+	/* reset */
+	SETR_32(SOFT_RST, (GETR_32(SOFT_RST) & (~SOFT_RST_SDRST)));
+	SETR_32(SOFT_RST, (GETR_32(SOFT_RST) | SOFT_RST_SDRST));
+
+	/* initialize */
+	SETR_32(SD_INFO1, 0x00000000U);
+	SETR_32(SD_INFO2, SD_INFO2_CLEAR);
+	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
+	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
+}
+
+static void emmc_read_response(uint32_t *response)
+{
+	uint8_t *p;
+
+	if (response == NULL)
+		return;
+
+	/* read response */
+	if (mmc_drv_obj.response_length != EMMC_MAX_RESPONSE_LENGTH) {
+		*response = GETR_32(SD_RSP10);	/* [39:8] */
+		return;
+	}
+
+	/* CSD or CID */
+	p = (uint8_t *) (response);
+	emmc_little_to_big(p, ((GETR_32(SD_RSP76) << 8)
+			| (GETR_32(SD_RSP54) >> 24)));	/* [127:96]     */
+	emmc_little_to_big(p + 4, ((GETR_32(SD_RSP54) << 8)
+			| (GETR_32(SD_RSP32) >> 24)));	/* [95:64]      */
+	emmc_little_to_big(p + 8, ((GETR_32(SD_RSP32) << 8)
+			| (GETR_32(SD_RSP10) >> 24)));	/* [63:32]      */
+	emmc_little_to_big(p + 12, (GETR_32(SD_RSP10) << 8));
+}
+
+static EMMC_ERROR_CODE emmc_response_check(uint32_t *response,
+					   uint32_t error_mask)
+{
+
+	HAL_MEMCARD_RESPONSE_TYPE response_type =
+	    ((HAL_MEMCARD_RESPONSE_TYPE)mmc_drv_obj.cmd_info.cmd & HAL_MEMCARD_RESPONSE_TYPE_MASK);
+
+	if (response == NULL)
+		return EMMC_ERR_PARAM;
+
+	if (response_type == HAL_MEMCARD_RESPONSE_NONE)
+		return EMMC_SUCCESS;
+
+
+	if (response_type <= HAL_MEMCARD_RESPONSE_R1b) {
+		/* R1 or R1b */
+		mmc_drv_obj.current_state =
+		    (EMMC_R1_STATE) ((*response & EMMC_R1_STATE_MASK) >>
+				     EMMC_R1_STATE_SHIFT);
+		if ((*response & error_mask) != 0) {
+			if ((0x80 & *response) != 0) {
+				ERROR("BL2: emmc SWITCH_ERROR\n");
+			}
+			return EMMC_ERR_CARD_STATUS_BIT;
+		}
+		return EMMC_SUCCESS;
+	}
+
+	if (response_type == HAL_MEMCARD_RESPONSE_R4) {
+		if ((*response & EMMC_R4_STATUS) != 0)
+			return EMMC_ERR_CARD_STATUS_BIT;
+	}
+
+	return EMMC_SUCCESS;
+}
+
+static void emmc_WaitCmd2Cmd_8Cycle(void)
+{
+	uint32_t dataL, wait = 0;
+
+	dataL = GETR_32(SD_CLK_CTRL);
+	dataL &= 0x000000FF;
+
+	switch (dataL) {
+	case 0xFF:
+	case 0x00:
+	case 0x01:
+	case 0x02:
+	case 0x04:
+	case 0x08:
+	case 0x10:
+	case 0x20:
+		wait = 10U;
+		break;
+	case 0x40:
+		wait = 20U;
+		break;
+	case 0x80:
+		wait = 30U;
+		break;
+	}
+
+	rcar_micro_delay(wait);
+}
+
+static void cmdErrSdInfo2Log(void)
+{
+	ERROR("BL2: emmc ERR SD_INFO2 = 0x%x\n", mmc_drv_obj.error_info.info2);
+}
+
+static void emmc_data_transfer_dma(void)
+{
+	mmc_drv_obj.during_dma_transfer = TRUE;
+	mmc_drv_obj.dma_error_flag = FALSE;
+
+	SETR_32(SD_INFO1_MASK, 0x00000000U);
+	SETR_32(SD_INFO2_MASK, (SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
+
+	/* DMAC setting */
+	if (mmc_drv_obj.cmd_info.dir == HAL_MEMCARD_WRITE) {
+		/* transfer complete interrupt enable */
+		SETR_32(DM_CM_INFO1_MASK,
+			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH0_ENABLE));
+		SETR_32(DM_CM_INFO2_MASK,
+			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH0_ENABLE));
+		/* BUFF --> FIFO */
+		SETR_32(DM_CM_DTRAN_MODE, (DM_CM_DTRAN_MODE_CH0 |
+					   DM_CM_DTRAN_MODE_BIT_WIDTH));
+	} else {
+		/* transfer complete interrupt enable */
+		SETR_32(DM_CM_INFO1_MASK,
+			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH1_ENABLE));
+		SETR_32(DM_CM_INFO2_MASK,
+			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH1_ENABLE));
+		/* FIFO --> BUFF */
+		SETR_32(DM_CM_DTRAN_MODE, (DM_CM_DTRAN_MODE_CH1
+					   | DM_CM_DTRAN_MODE_BIT_WIDTH));
+	}
+	SETR_32(DM_DTRAN_ADDR, (((uintptr_t) mmc_drv_obj.buff_address_virtual &
+				 DM_DTRAN_ADDR_WRITE_MASK)));
+
+	SETR_32(DM_CM_DTRAN_CTRL, DM_CM_DTRAN_CTRL_START);
+}
+
+EMMC_ERROR_CODE emmc_exec_cmd(uint32_t error_mask, uint32_t *response)
+{
+	EMMC_ERROR_CODE rtn_code = EMMC_SUCCESS;
+	HAL_MEMCARD_RESPONSE_TYPE response_type;
+	HAL_MEMCARD_COMMAND_TYPE cmd_type;
+	EMMC_INT_STATE state;
+	uint32_t err_not_care_flag = FALSE;
+
+	/* parameter check */
+	if (response == NULL) {
+		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* state check */
+	if (mmc_drv_obj.clock_enable != TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	if (mmc_drv_obj.state_machine_blocking == TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR);
+		return EMMC_ERR;
+	}
+
+	state = ESTATE_BEGIN;
+	response_type =
+	    ((HAL_MEMCARD_RESPONSE_TYPE)mmc_drv_obj.cmd_info.cmd &
+					HAL_MEMCARD_RESPONSE_TYPE_MASK);
+	cmd_type =
+	    ((HAL_MEMCARD_COMMAND_TYPE) mmc_drv_obj.cmd_info.cmd &
+					HAL_MEMCARD_COMMAND_TYPE_MASK);
+
+	/* state machine */
+	while ((mmc_drv_obj.force_terminate != TRUE) && (state != ESTATE_END)) {
+		/* The interrupt factor flag is observed. */
+		emmc_interrupt();
+
+		/* wait interrupt */
+		if (mmc_drv_obj.state_machine_blocking == TRUE)
+			continue;
+
+		switch (state) {
+		case ESTATE_BEGIN:
+			/* Busy check */
+			if ((mmc_drv_obj.error_info.info2 & SD_INFO2_CBSY) != 0) {
+				emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD,
+						      EMMC_ERR_CARD_BUSY);
+				return EMMC_ERR_CARD_BUSY;
+			}
+
+			/* clear register */
+			SETR_32(SD_INFO1, 0x00000000U);
+			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
+			SETR_32(SD_INFO1_MASK, SD_INFO1_INFO0);
+			SETR_32(SD_INFO2_MASK,
+				(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
+
+			state = ESTATE_ISSUE_CMD;
+			/* through */
+
+		case ESTATE_ISSUE_CMD:
+			/* ARG */
+			SETR_32(SD_ARG, mmc_drv_obj.cmd_info.arg);
+			/* issue cmd */
+			SETR_32(SD_CMD, mmc_drv_obj.cmd_info.hw);
+			/* Set driver flag */
+			mmc_drv_obj.during_cmd_processing = TRUE;
+			mmc_drv_obj.state_machine_blocking = TRUE;
+
+			if (response_type == HAL_MEMCARD_RESPONSE_NONE) {
+				state = ESTATE_NON_RESP_CMD;
+			} else {
+				state = ESTATE_RCV_RESP;
+			}
+
+			break;
+
+		case ESTATE_NON_RESP_CMD:
+			/* interrupt disable */
+			SETR_32(SD_INFO1_MASK, 0x00000000U);
+			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
+
+			/* check interrupt */
+			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
+				/* error interrupt */
+				cmdErrSdInfo2Log();
+				rtn_code = EMMC_ERR_INFO2;
+				state = ESTATE_ERROR;
+			} else if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO0) ==
+				   0) {
+				/* not receive expected interrupt */
+				rtn_code = EMMC_ERR_RESPONSE;
+				state = ESTATE_ERROR;
+			} else {
+				emmc_WaitCmd2Cmd_8Cycle();
+				state = ESTATE_END;
+			}
+			break;
+
+		case ESTATE_RCV_RESP:
+			/* interrupt disable */
+			SETR_32(SD_INFO1_MASK, 0x00000000U);
+			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
+
+			/* check interrupt */
+			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
+				if ((mmc_drv_obj.get_partition_access_flag ==
+				     TRUE)
+				    && ((mmc_drv_obj.int_event2 & SD_INFO2_ERR6)
+					!= 0U)) {
+					err_not_care_flag = TRUE;
+					rtn_code = EMMC_ERR_CMD_TIMEOUT;
+				} else {
+					/* error interrupt */
+					cmdErrSdInfo2Log();
+					rtn_code = EMMC_ERR_INFO2;
+				}
+				state = ESTATE_ERROR;
+				break;
+			} else if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO0) ==
+				   0) {
+				/* not receive expected interrupt */
+				rtn_code = EMMC_ERR_RESPONSE;
+				state = ESTATE_ERROR;
+				break;
+			}
+
+			/* read response */
+			emmc_read_response(response);
+
+			/* check response */
+			rtn_code = emmc_response_check(response, error_mask);
+			if (rtn_code != EMMC_SUCCESS) {
+				state = ESTATE_ERROR;
+				break;
+			}
+
+			if (response_type == HAL_MEMCARD_RESPONSE_R1b) {
+				/* R1b */
+				SETR_32(SD_INFO2_MASK,
+					(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
+				state = ESTATE_RCV_RESPONSE_BUSY;
+			} else {
+				state = ESTATE_CHECK_RESPONSE_COMPLETE;
+			}
+			break;
+
+		case ESTATE_RCV_RESPONSE_BUSY:
+			/* check interrupt */
+			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
+				/* error interrupt */
+				cmdErrSdInfo2Log();
+				rtn_code = EMMC_ERR_INFO2;
+				state = ESTATE_ERROR;
+				break;
+			}
+			/* DAT0 not Busy */
+			if ((SD_INFO2_DAT0 & mmc_drv_obj.error_info.info2) != 0) {
+				state = ESTATE_CHECK_RESPONSE_COMPLETE;
+				break;
+			}
+			break;
+
+		case ESTATE_CHECK_RESPONSE_COMPLETE:
+			if (cmd_type >= HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE) {
+				state = ESTATE_DATA_TRANSFER;
+			} else {
+				emmc_WaitCmd2Cmd_8Cycle();
+				state = ESTATE_END;
+			}
+			break;
+
+		case ESTATE_DATA_TRANSFER:
+			/* ADTC command  */
+			mmc_drv_obj.during_transfer = TRUE;
+			mmc_drv_obj.state_machine_blocking = TRUE;
+
+			if (mmc_drv_obj.transfer_mode == HAL_MEMCARD_DMA) {
+				/* DMA */
+				emmc_data_transfer_dma();
+			} else {
+				/* PIO */
+				/* interrupt enable (FIFO read/write enable) */
+				if (mmc_drv_obj.cmd_info.dir ==
+				    HAL_MEMCARD_WRITE) {
+					SETR_32(SD_INFO2_MASK,
+						(SD_INFO2_BWE | SD_INFO2_ALL_ERR
+						 | SD_INFO2_CLEAR));
+				} else {
+					SETR_32(SD_INFO2_MASK,
+						(SD_INFO2_BRE | SD_INFO2_ALL_ERR
+						 | SD_INFO2_CLEAR));
+				}
+			}
+			state = ESTATE_DATA_TRANSFER_COMPLETE;
+			break;
+
+		case ESTATE_DATA_TRANSFER_COMPLETE:
+			/* check interrupt */
+			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
+				/* error interrupt */
+				cmdErrSdInfo2Log();
+				rtn_code = EMMC_ERR_INFO2;
+				state = ESTATE_TRANSFER_ERROR;
+				break;
+			}
+
+			/* DMAC error ? */
+			if (mmc_drv_obj.dma_error_flag == TRUE) {
+				/* Error occurred in DMAC driver. */
+				rtn_code = EMMC_ERR_FROM_DMAC_TRANSFER;
+				state = ESTATE_TRANSFER_ERROR;
+			} else if (mmc_drv_obj.during_dma_transfer == TRUE) {
+				/* DMAC not finished. unknown error */
+				rtn_code = EMMC_ERR;
+				state = ESTATE_TRANSFER_ERROR;
+			} else {
+				SETR_32(SD_INFO1_MASK, SD_INFO1_INFO2);
+				SETR_32(SD_INFO2_MASK,
+					(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
+
+				mmc_drv_obj.state_machine_blocking = TRUE;
+
+				state = ESTATE_ACCESS_END;
+			}
+			break;
+
+		case ESTATE_ACCESS_END:
+
+			/* clear flag */
+			if (mmc_drv_obj.transfer_mode == HAL_MEMCARD_DMA) {
+				/* W (CC_EXT_MODE, H'0000_1010) SD_BUF DMA transfer disabled */
+				SETR_32(CC_EXT_MODE, CC_EXT_MODE_CLEAR);
+				SETR_32(SD_STOP, 0x00000000U);
+				mmc_drv_obj.during_dma_transfer = FALSE;
+			}
+
+			SETR_32(SD_INFO1_MASK, 0x00000000U);
+			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
+			SETR_32(SD_INFO1, 0x00000000U);
+			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
+
+			if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO2) != 0) {
+				emmc_WaitCmd2Cmd_8Cycle();
+				state = ESTATE_END;
+			} else {
+				state = ESTATE_ERROR;
+			}
+			break;
+
+		case ESTATE_TRANSFER_ERROR:
+			/* The error occurred in the Data transfer.  */
+			if (mmc_drv_obj.transfer_mode == HAL_MEMCARD_DMA) {
+				/* W (CC_EXT_MODE, H'0000_1010) SD_BUF DMA transfer disabled */
+				SETR_32(CC_EXT_MODE, CC_EXT_MODE_CLEAR);
+				SETR_32(SD_STOP, 0x00000000U);
+				mmc_drv_obj.during_dma_transfer = FALSE;
+			}
+			/* through */
+
+		case ESTATE_ERROR:
+			if (err_not_care_flag == TRUE) {
+				mmc_drv_obj.during_cmd_processing = FALSE;
+			} else {
+				emmc_softreset();
+				emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD,
+						      rtn_code);
+			}
+			return rtn_code;
+
+		default:
+			state = ESTATE_END;
+			break;
+		} /* switch (state) */
+	} /* while ( (mmc_drv_obj.force_terminate != TRUE) && (state != ESTATE_END) ) */
+
+	/* force terminate */
+	if (mmc_drv_obj.force_terminate == TRUE) {
+		/* timeout timer is expired. Or, PIO data transfer error. */
+		/* Timeout occurred in the DMA transfer. */
+		if (mmc_drv_obj.during_dma_transfer == TRUE) {
+			mmc_drv_obj.during_dma_transfer = FALSE;
+		}
+		ERROR("BL2: emmc exec_cmd:EMMC_ERR_FORCE_TERMINATE\n");
+		emmc_softreset();
+
+		return EMMC_ERR_FORCE_TERMINATE; /* error information has already been written. */
+	}
+
+	/* success */
+	mmc_drv_obj.during_cmd_processing = FALSE;
+	mmc_drv_obj.during_transfer = FALSE;
+
+	return EMMC_SUCCESS;
+}
diff --git a/drivers/renesas/common/emmc/emmc_config.h b/drivers/renesas/common/emmc/emmc_config.h
new file mode 100644
index 0000000..16b6b8a
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_config.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMMC_CONFIG_H
+#define EMMC_CONFIG_H
+
+/* RCA */
+#define EMMC_RCA		1UL
+/* 314ms (freq = 400KHz, timeout Counter = 0x04(SDCLK * 2^17)  */
+#define EMMC_RW_DATA_TIMEOUT	0x40UL
+/* how many times to try after fail. Don't change. */
+#define EMMC_RETRY_COUNT	0
+#define EMMC_CMD_MAX		60UL	/* Don't change. */
+
+#define LOADIMAGE_FLAGS_DMA_ENABLE	0x00000001UL
+
+#endif /* EMMC_CONFIG_H */
diff --git a/drivers/renesas/rcar/emmc/emmc_def.h b/drivers/renesas/common/emmc/emmc_def.h
similarity index 100%
rename from drivers/renesas/rcar/emmc/emmc_def.h
rename to drivers/renesas/common/emmc/emmc_def.h
diff --git a/drivers/renesas/common/emmc/emmc_hal.h b/drivers/renesas/common/emmc/emmc_hal.h
new file mode 100644
index 0000000..0a85517
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_hal.h
@@ -0,0 +1,535 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMMC_HAL_H
+#define EMMC_HAL_H
+
+/* memory card error/status types */
+#define HAL_MEMCARD_OUT_OF_RANGE		0x80000000L
+#define HAL_MEMCARD_ADDRESS_ERROR		0x40000000L
+#define HAL_MEMCARD_BLOCK_LEN_ERROR		0x20000000L
+#define HAL_MEMCARD_ERASE_SEQ_ERROR		0x10000000L
+#define HAL_MEMCARD_ERASE_PARAM			0x08000000L
+#define HAL_MEMCARD_WP_VIOLATION		0x04000000L
+#define HAL_MEMCARD_CARD_IS_LOCKED		0x02000000L
+#define HAL_MEMCARD_LOCK_UNLOCK_FAILED		0x01000000L
+#define HAL_MEMCARD_COM_CRC_ERROR		0x00800000L
+#define HAL_MEMCARD_ILEGAL_COMMAND		0x00400000L
+#define HAL_MEMCARD_CARD_ECC_FAILED		0x00200000L
+#define HAL_MEMCARD_CC_ERROR			0x00100000L
+#define HAL_MEMCARD_ERROR			0x00080000L
+#define HAL_MEMCARD_UNDERRUN			0x00040000L
+#define HAL_MEMCARD_OVERRUN			0x00020000L
+#define HAL_MEMCARD_CIDCSD_OVERWRITE		0x00010000L
+#define HAL_MEMCARD_WP_ERASE_SKIP		0x00008000L
+#define HAL_MEMCARD_CARD_ECC_DISABLED		0x00004000L
+#define HAL_MEMCARD_ERASE_RESET			0x00002000L
+#define HAL_MEMCARD_CARD_STATE			0x00001E00L
+#define HAL_MEMCARD_CARD_READY_FOR_DATA		0x00000100L
+#define HAL_MEMCARD_APP_CMD			0x00000020L
+#define HAL_MEMCARD_SWITCH_ERROR		0x00000080L
+#define HAL_MEMCARD_AKE_SEQ_ERROR		0x00000008L
+#define HAL_MEMCARD_NO_ERRORS			0x00000000L
+
+/* Memory card response types */
+#define HAL_MEMCARD_COMMAND_INDEX_MASK		0x0003f
+
+/* Type of the return value. */
+typedef enum {
+	HAL_MEMCARD_FAIL = 0U,
+	HAL_MEMCARD_OK = 1U,
+	HAL_MEMCARD_DMA_ALLOC_FAIL = 2U,     /* DMA channel allocation failed */
+	HAL_MEMCARD_DMA_TRANSFER_FAIL = 3U,  /* DMA transfer failed */
+	HAL_MEMCARD_CARD_STATUS_ERROR = 4U,  /* card status non-masked error */
+	HAL_MEMCARD_CMD_TIMEOUT = 5U,	     /* Command timeout occurred */
+	HAL_MEMCARD_DATA_TIMEOUT = 6U,	     /* Data timeout occurred */
+	HAL_MEMCARD_CMD_CRC_ERROR = 7U,	     /* Command CRC error occurred */
+	HAL_MEMCARD_DATA_CRC_ERROR = 8U	     /* Data CRC error occurred */
+} HAL_MEMCARD_RETURN;
+
+/* memory access operation */
+typedef enum {
+	HAL_MEMCARD_READ = 0U,	 /* read */
+	HAL_MEMCARD_WRITE = 1U	 /* write */
+} HAL_MEMCARD_OPERATION;
+
+/* Type of data width on memorycard bus */
+typedef enum {
+	HAL_MEMCARD_DATA_WIDTH_1_BIT = 0U,
+	HAL_MEMCARD_DATA_WIDTH_4_BIT = 1U,
+	HAL_MEMCARD_DATA_WIDTH_8_BIT = 2U
+} HAL_MEMCARD_DATA_WIDTH; /* data (bus) width types */
+
+/* Presence of the memory card */
+typedef enum {
+	HAL_MEMCARD_CARD_IS_IN = 0U,
+	HAL_MEMCARD_CARD_IS_OUT = 1U
+} HAL_MEMCARD_PRESENCE_STATUS;	/* presence status of the memory card */
+
+/* mode of data transfer */
+typedef enum {
+	HAL_MEMCARD_DMA = 0U,
+	HAL_MEMCARD_NOT_DMA = 1U
+} HAL_MEMCARD_DATA_TRANSFER_MODE;
+
+/* Memory card response types. */
+typedef enum hal_memcard_response_type {
+	HAL_MEMCARD_RESPONSE_NONE = 0x00000U,
+	HAL_MEMCARD_RESPONSE_R1 = 0x00100U,
+	HAL_MEMCARD_RESPONSE_R1b = 0x00200U,
+	HAL_MEMCARD_RESPONSE_R2 = 0x00300U,
+	HAL_MEMCARD_RESPONSE_R3 = 0x00400U,
+	HAL_MEMCARD_RESPONSE_R4 = 0x00500U,
+	HAL_MEMCARD_RESPONSE_R5 = 0x00600U,
+	HAL_MEMCARD_RESPONSE_R6 = 0x00700U,
+	HAL_MEMCARD_RESPONSE_R7 = 0x00800U,
+	HAL_MEMCARD_RESPONSE_TYPE_MASK = 0x00f00U
+} HAL_MEMCARD_RESPONSE_TYPE;
+
+/* Memory card command types. */
+typedef enum hal_memcard_command_type {
+	HAL_MEMCARD_COMMAND_TYPE_BC = 0x00000U,
+	HAL_MEMCARD_COMMAND_TYPE_BCR = 0x01000U,
+	HAL_MEMCARD_COMMAND_TYPE_AC = 0x02000U,
+	HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE = 0x03000U,
+	HAL_MEMCARD_COMMAND_TYPE_ADTC_READ = 0x04000U,
+	HAL_MEMCARD_COMMAND_TYPE_MASK = 0x07000U
+} HAL_MEMCARD_COMMAND_TYPE;
+
+/* Type of memory card */
+typedef enum hal_memcard_command_card_type {
+	HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON = 0x00000U,
+	HAL_MEMCARD_COMMAND_CARD_TYPE_MMC = 0x08000U,
+	HAL_MEMCARD_COMMAND_CARD_TYPE_SD = 0x10000U,
+	HAL_MEMCARD_COMMAND_CARD_TYPE_MASK = 0x18000U
+} HAL_MEMCARD_COMMAND_CARD_TYPE;
+
+/* Memory card application command. */
+typedef enum hal_memcard_command_app_norm {
+	HAL_MEMCARD_COMMAND_NORMAL = 0x00000U,
+	HAL_MEMCARD_COMMAND_APP = 0x20000U,
+	HAL_MEMCARD_COMMAND_APP_NORM_MASK = 0x20000U
+} HAL_MEMCARD_COMMAND_APP_NORM;
+
+/* Memory card command codes. */
+typedef enum {
+/* class 0 and class 1 */
+	/* CMD0 */
+	CMD0_GO_IDLE_STATE =
+	    0U | (uint32_t)HAL_MEMCARD_RESPONSE_NONE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BC |
+	    (uint32_t) HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD1 */
+	CMD1_SEND_OP_COND =
+	    1U | (uint32_t)HAL_MEMCARD_RESPONSE_R3 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD2 */
+	CMD2_ALL_SEND_CID_MMC =
+	    2U | (uint32_t)HAL_MEMCARD_RESPONSE_R2 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD2_ALL_SEND_CID_SD =
+	    2U | (uint32_t)HAL_MEMCARD_RESPONSE_R2 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD3 */
+	CMD3_SET_RELATIVE_ADDR =
+	    3U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD3_SEND_RELATIVE_ADDR =
+	    3U | (uint32_t)HAL_MEMCARD_RESPONSE_R6 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD4 */
+	CMD4_SET_DSR =
+	    4U | (uint32_t)HAL_MEMCARD_RESPONSE_NONE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD5 */
+	CMD5_SLEEP_AWAKE =
+	    5U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD6 */
+	CMD6_SWITCH =
+	    6U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD6_SWITCH_FUNC =
+	    6U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	ACMD6_SET_BUS_WIDTH =
+	    6U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+	/* CMD7 */
+	CMD7_SELECT_CARD =
+	    7U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD7(from Disconnected State to Programming State) */
+	CMD7_SELECT_CARD_PROG =
+	    7U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD7_DESELECT_CARD =
+	    7U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD8 */
+	CMD8_SEND_EXT_CSD =
+	    8U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD8_SEND_IF_COND =
+	    8U | (uint32_t)HAL_MEMCARD_RESPONSE_R7 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD9 */
+	CMD9_SEND_CSD =
+	    9U | (uint32_t)HAL_MEMCARD_RESPONSE_R2 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD10 */
+	CMD10_SEND_CID =
+	    10U | (uint32_t)HAL_MEMCARD_RESPONSE_R2 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD11 */
+	CMD11_READ_DAT_UNTIL_STOP =
+	    11U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD12 */
+	CMD12_STOP_TRANSMISSION =
+	    12U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD12(R1b : write case) */
+	CMD12_STOP_TRANSMISSION_WRITE =
+	    12U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD13 */
+	CMD13_SEND_STATUS =
+	    13U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	ACMD13_SD_STATUS =
+	    13U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+	/* CMD14 */
+	CMD14_BUSTEST_R =
+	    14U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD15 */
+	CMD15_GO_INACTIVE_STATE =
+	    15U | (uint32_t)HAL_MEMCARD_RESPONSE_NONE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+
+/* class 2 */
+	/* CMD16 */
+	CMD16_SET_BLOCKLEN =
+	    16U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD17 */
+	CMD17_READ_SINGLE_BLOCK =
+	     17U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	     (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	     (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	     (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD18 */
+	CMD18_READ_MULTIPLE_BLOCK =
+	    18U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD19 */
+	CMD19_BUS_TEST_W =
+	    19U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+
+/* class 3 */
+	/* CMD20 */
+	CMD20_WRITE_DAT_UNTIL_STOP =
+	    20U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD21 */
+	CMD21 = 21U,
+	/* CMD22 */
+	CMD22 = 22U,
+	ACMD22_SEND_NUM_WR_BLOCKS =
+	    22U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+
+/* class 4 */
+	/* CMD23 */
+	CMD23_SET_BLOCK_COUNT =
+	    23U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	ACMD23_SET_WR_BLK_ERASE_COUNT =
+	    23U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+	/* CMD24 */
+	CMD24_WRITE_BLOCK =
+	    24U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD25 */
+	CMD25_WRITE_MULTIPLE_BLOCK =
+	    25U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD26 */
+	CMD26_PROGRAM_CID =
+	    26U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD27 */
+	CMD27_PROGRAM_CSD =
+	    27U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+
+/* class 6 */
+	/* CMD28 */
+	CMD28_SET_WRITE_PROT =
+	    28U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD29 */
+	CMD29_CLR_WRITE_PROT =
+	    29U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD30 */
+	CMD30_SEND_WRITE_PROT =
+	    30U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD31 */
+	CMD30_SEND_WRITE_PROT_TYPE =
+	    31U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+
+/* class 5 */
+	/* CMD32 */
+	CMD32_ERASE_WR_BLK_START =
+	    32U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD33 */
+	CMD33_ERASE_WR_BLK_END =
+	    33U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD34 */
+	CMD34 = 34U,
+	/* CMD35 */
+	CMD35_ERASE_GROUP_START =
+	    35U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD36 */
+	CMD36_ERASE_GROUP_END =
+	    36U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD37 */
+	CMD37 = 37U,
+	/* CMD38 */
+	CMD38_ERASE =
+	    38U | (uint32_t)HAL_MEMCARD_RESPONSE_R1b |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+
+/* class 9 */
+	/* CMD39 */
+	CMD39_FASTIO =
+	    39U | (uint32_t)HAL_MEMCARD_RESPONSE_R4 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD40 */
+	CMD40_GO_IRQSTATE =
+	    40U | (uint32_t)HAL_MEMCARD_RESPONSE_R5 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_MMC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD41 */
+	CMD41 = 41,
+	ACMD41_SD_SEND_OP_COND =
+	     41U | (uint32_t)HAL_MEMCARD_RESPONSE_R3 |
+	     (uint32_t)HAL_MEMCARD_COMMAND_TYPE_BCR |
+	     (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	     (uint32_t)HAL_MEMCARD_COMMAND_APP,
+
+/* class 7 */
+	/* CMD42 */
+	CMD42_LOCK_UNLOCK =
+	    42U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	    (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	ACMD42_SET_CLR_CARD_DETECT =
+	    42U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+	CMD43 = 43U,		/* CMD43 */
+	CMD44 = 44U,		/* CMD44 */
+	CMD45 = 45U,		/* CMD45 */
+	CMD46 = 46U,		/* CMD46 */
+	CMD47 = 47U,		/* CMD47 */
+	CMD48 = 48U,		/* CMD48 */
+	CMD49 = 49U,		/* CMD49 */
+	CMD50 = 50U,		/* CMD50 */
+	CMD51 = 51U,		/* CMD51 */
+	ACMD51_SEND_SCR =
+	    51U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	    (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
+	    (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_SD |
+	    (uint32_t)HAL_MEMCARD_COMMAND_APP,
+	CMD52 = 52U,		/* CMD52 */
+	CMD53 = 53U,		/* CMD53 */
+	CMD54 = 54U,		/* CMD54 */
+
+/* class 8 */
+	/* CMD55 */
+	CMD55_APP_CMD =
+	   55U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	   (uint32_t)HAL_MEMCARD_COMMAND_TYPE_AC |
+	   (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	   (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	/* CMD56 */
+	CMD56_GEN_CMD =
+	   56U | (uint32_t)HAL_MEMCARD_RESPONSE_R1 |
+	   (uint32_t)HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE |
+	   (uint32_t)HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON |
+	   (uint32_t)HAL_MEMCARD_COMMAND_NORMAL,
+	CMD57 = 57U,		/* CMD57 */
+	CMD58 = 58U,		/* CMD58 */
+	CMD59 = 59U,		/* CMD59 */
+	CMD60 = 60U,		/* CMD60 */
+	CMD61 = 61U,		/* CMD61 */
+	CMD62 = 62U,		/* CMD62 */
+	CMD63 = 63U		/* CMD63 */
+} HAL_MEMCARD_COMMAND;
+
+/*
+ * Configuration structure from HAL layer.
+ *
+ * If some field is not available it should be filled with 0xFF.
+ * The API version is 32-bit unsigned integer telling the version of the API.
+ * The integer is divided to four sections which each can be treated as a 8-bit
+ * unsigned number:
+ * Bits 31-24 make the most significant part of the version number. This number
+ * starts from 1 i.e. the second version of the API will be 0x02xxxxxx. This
+ * number changes only, if the API itself changes so much that it is not
+ * compatible anymore with older releases.
+ * Bits 23-16 API minor version number. For example API version 2.1 would be
+ * 0x0201xxxx.
+ * Bits 15-8 are the number of the year when release is done. The 0 is year
+ * 2000, 1 is year 2001 and so on
+ * Bits 7- are the week number when release is done. First full week of the
+ * year is 1
+ *
+ * Example: let's assume that release 2.1 is done on week 10 year 2008
+ * the version will get the value 0x0201080A
+ */
+typedef struct {
+	/*
+	 * Version of the chipset API implementation
+	 *
+	 * bits [31:24] API specification major version number.<br>
+	 * bits [23:16] API specification minor version number.<br>
+	 * bits [15:8] API implementation year. (2000 = 0, 2001 = 1, ...)
+	 * bits [7:0] API implementation week.
+	 * Example: API spec version 4.0, implementation w46 2008 => 0x0400082E
+	 */
+	uint32_t api_version;
+
+	/* maximum block count which can be transferred at once */
+	uint32_t max_block_count;
+
+	/* maximum clock frequence in Hz supported by HW */
+	uint32_t max_clock_freq;
+
+	/* maximum data bus width supported by HW */
+	uint16_t max_data_width;
+
+	/* Is high-speed mode supported by HW (yes=1, no=0) */
+	uint8_t hs_mode_supported;
+
+	/* Is memory card removable (yes=1, no=0) */
+	uint8_t card_removable;
+
+} HAL_MEMCARD_HW_CONF;
+
+/* Configuration structure to HAL layer. */
+typedef struct {
+	/* how many times to try after fail, for instance sending command */
+	uint32_t retries_after_fail;
+} HAL_MEMCARD_INIT_CONF;
+
+#endif /* EMMC_HAL_H */
diff --git a/drivers/renesas/common/emmc/emmc_init.c b/drivers/renesas/common/emmc/emmc_init.c
new file mode 100644
index 0000000..c0ec600
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_init.c
@@ -0,0 +1,163 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <lib/mmio.h>
+
+#include "emmc_config.h"
+#include "emmc_hal.h"
+#include "emmc_std.h"
+#include "emmc_registers.h"
+#include "emmc_def.h"
+#include "rcar_private.h"
+#include "cpg_registers.h"
+
+st_mmc_base mmc_drv_obj;
+
+EMMC_ERROR_CODE rcar_emmc_memcard_power(uint8_t mode)
+{
+
+	if (mode == TRUE) {
+		/* power on (Vcc&Vccq is always power on) */
+		mmc_drv_obj.card_power_enable = TRUE;
+	} else {
+		/* power off (Vcc&Vccq is always power on) */
+		mmc_drv_obj.card_power_enable = FALSE;
+		mmc_drv_obj.mount = FALSE;
+		mmc_drv_obj.selected = FALSE;
+	}
+
+	return EMMC_SUCCESS;
+}
+static inline void emmc_set_retry_count(uint32_t retry)
+{
+	mmc_drv_obj.retries_after_fail = retry;
+}
+
+static inline void emmc_set_data_timeout(uint32_t data_timeout)
+{
+	mmc_drv_obj.data_timeout = data_timeout;
+}
+
+static void emmc_memset(uint8_t *buff, uint8_t data, uint32_t cnt)
+{
+	if (buff == NULL) {
+		return;
+	}
+
+	while (cnt > 0) {
+		*buff++ = data;
+		cnt--;
+	}
+}
+
+static void emmc_driver_config(void)
+{
+	emmc_set_retry_count(EMMC_RETRY_COUNT);
+	emmc_set_data_timeout(EMMC_RW_DATA_TIMEOUT);
+}
+
+static void emmc_drv_init(void)
+{
+	emmc_memset((uint8_t *) (&mmc_drv_obj), 0, sizeof(st_mmc_base));
+	mmc_drv_obj.card_present = HAL_MEMCARD_CARD_IS_IN;
+	mmc_drv_obj.data_timeout = EMMC_RW_DATA_TIMEOUT;
+	mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
+}
+
+static EMMC_ERROR_CODE emmc_dev_finalize(void)
+{
+	EMMC_ERROR_CODE result;
+	uint32_t dataL;
+
+	/*
+	 * MMC power off
+	 * the power supply of eMMC device is always turning on.
+	 * RST_n : Hi --> Low level.
+	 */
+	result = rcar_emmc_memcard_power(FALSE);
+
+	/* host controller reset */
+	SETR_32(SD_INFO1, 0x00000000U);		/* all interrupt clear */
+	SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* all interrupt clear */
+	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
+	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
+	SETR_32(SD_CLK_CTRL, 0x00000000U);	/* MMC clock stop */
+
+	dataL = mmio_read_32(SMSTPCR3);
+	if ((dataL & CPG_MSTP_MMC) == 0U) {
+		dataL |= (CPG_MSTP_MMC);
+		mmio_write_32(CPG_CPGWPR, (~dataL));
+		mmio_write_32(SMSTPCR3, dataL);
+	}
+
+	return result;
+}
+
+static EMMC_ERROR_CODE emmc_dev_init(void)
+{
+	/* Enable clock supply to eMMC. */
+	mstpcr_write(SMSTPCR3, CPG_MSTPSR3, CPG_MSTP_MMC);
+
+	/* Set SD clock */
+	mmio_write_32(CPG_CPGWPR, ~((uint32_t) (BIT9 | BIT0)));	/* SD phy 200MHz */
+
+	/* Stop SDnH clock & SDn=200MHz */
+	mmio_write_32(CPG_SDxCKCR, (BIT9 | BIT0));
+
+	/* MMCIF initialize */
+	SETR_32(SD_INFO1, 0x00000000U);		/* all interrupt clear */
+	SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* all interrupt clear */
+	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
+	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
+
+	SETR_32(HOST_MODE, 0x00000000U);	/* SD_BUF access width = 64-bit */
+	SETR_32(SD_OPTION, 0x0000C0EEU);	/* Bus width = 1bit, timeout=MAX */
+	SETR_32(SD_CLK_CTRL, 0x00000000U);	/* Disable Automatic Control & Clock Output */
+
+	return EMMC_SUCCESS;
+}
+
+static EMMC_ERROR_CODE emmc_reset_controller(void)
+{
+	EMMC_ERROR_CODE result;
+
+	/* initialize mmc driver */
+	emmc_drv_init();
+
+	/* initialize H/W */
+	result = emmc_dev_init();
+	if (result == EMMC_SUCCESS) {
+		mmc_drv_obj.initialize = TRUE;
+	}
+
+	return result;
+
+}
+
+EMMC_ERROR_CODE emmc_terminate(void)
+{
+	EMMC_ERROR_CODE result;
+
+	result = emmc_dev_finalize();
+
+	emmc_memset((uint8_t *) (&mmc_drv_obj), 0, sizeof(st_mmc_base));
+
+	return result;
+}
+
+EMMC_ERROR_CODE rcar_emmc_init(void)
+{
+	EMMC_ERROR_CODE result;
+
+	result = emmc_reset_controller();
+	if (result == EMMC_SUCCESS) {
+		emmc_driver_config();
+	}
+
+	return result;
+}
diff --git a/drivers/renesas/common/emmc/emmc_interrupt.c b/drivers/renesas/common/emmc/emmc_interrupt.c
new file mode 100644
index 0000000..092fdfb
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_interrupt.c
@@ -0,0 +1,217 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights
+ * reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <lib/mmio.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_registers.h"
+#include "emmc_std.h"
+#include "rcar_def.h"
+
+static EMMC_ERROR_CODE emmc_trans_sector(uint32_t *buff_address_virtual);
+
+uint32_t emmc_interrupt(void)
+{
+	EMMC_ERROR_CODE result;
+	uint32_t prr_data;
+	uint32_t cut_ver;
+	uint32_t end_bit;
+
+	prr_data = mmio_read_32((uintptr_t) RCAR_PRR);
+	cut_ver = prr_data & PRR_CUT_MASK;
+	if ((prr_data & PRR_PRODUCT_MASK) == PRR_PRODUCT_H3) {
+		if (cut_ver == PRR_PRODUCT_10) {
+			end_bit = BIT17;
+		} else if (cut_ver == PRR_PRODUCT_11) {
+			end_bit = BIT17;
+		} else {
+			end_bit = BIT20;
+		}
+	} else if ((prr_data & PRR_PRODUCT_MASK) == PRR_PRODUCT_M3) {
+		if (cut_ver == PRR_PRODUCT_10) {
+			end_bit = BIT17;
+		} else {
+			end_bit = BIT20;
+		}
+	} else {
+		end_bit = BIT20;
+	}
+
+	/* SD_INFO */
+	mmc_drv_obj.error_info.info1 = GETR_32(SD_INFO1);
+	mmc_drv_obj.error_info.info2 = GETR_32(SD_INFO2);
+
+	/* SD_INFO EVENT */
+	mmc_drv_obj.int_event1 =
+	    mmc_drv_obj.error_info.info1 & GETR_32(SD_INFO1_MASK);
+	mmc_drv_obj.int_event2 =
+	    mmc_drv_obj.error_info.info2 & GETR_32(SD_INFO2_MASK);
+
+	/* ERR_STS */
+	mmc_drv_obj.error_info.status1 = GETR_32(SD_ERR_STS1);
+	mmc_drv_obj.error_info.status2 = GETR_32(SD_ERR_STS2);
+
+	/* DM_CM_INFO */
+	mmc_drv_obj.error_info.dm_info1 = GETR_32(DM_CM_INFO1);
+	mmc_drv_obj.error_info.dm_info2 = GETR_32(DM_CM_INFO2);
+
+	/* DM_CM_INFO EVENT */
+	mmc_drv_obj.dm_event1 =
+	    mmc_drv_obj.error_info.dm_info1 & GETR_32(DM_CM_INFO1_MASK);
+	mmc_drv_obj.dm_event2 =
+	    mmc_drv_obj.error_info.dm_info2 & GETR_32(DM_CM_INFO2_MASK);
+
+	/* ERR SD_INFO2 */
+	if ((SD_INFO2_ALL_ERR & mmc_drv_obj.int_event2) != 0) {
+		SETR_32(SD_INFO1_MASK, 0x00000000U);	/* interrupt disable */
+		SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* interrupt disable */
+		SETR_32(SD_INFO1, 0x00000000U);	/* interrupt clear */
+		SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* interrupt clear */
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	}
+
+	/* PIO Transfer */
+	/* BWE/BRE */
+	else if (((SD_INFO2_BWE | SD_INFO2_BRE) & mmc_drv_obj.int_event2)) {
+		/* BWE */
+		if (SD_INFO2_BWE & mmc_drv_obj.int_event2) {
+			SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BWE));
+		}
+		/* BRE */
+		else {
+			SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BRE));
+		}
+
+		result = emmc_trans_sector(mmc_drv_obj.buff_address_virtual);
+		mmc_drv_obj.buff_address_virtual += EMMC_BLOCK_LENGTH;
+		mmc_drv_obj.remain_size -= EMMC_BLOCK_LENGTH;
+
+		if (result != EMMC_SUCCESS) {
+			/* data transfer error */
+			emmc_write_error_info(EMMC_FUNCNO_NONE, result);
+
+			/* Panic */
+			SETR_32(SD_INFO1_MASK, 0x00000000U);
+			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
+			SETR_32(SD_INFO1, 0x00000000U);
+			/* interrupt clear */
+			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
+			mmc_drv_obj.force_terminate = TRUE;
+		} else {
+			mmc_drv_obj.during_transfer = FALSE;
+		}
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	}
+
+	/* DMA_TRANSFER */
+	/* DM_CM_INFO1: DMA-ch0 transfer complete or error occurred */
+	else if ((BIT16 & mmc_drv_obj.dm_event1) != 0) {
+		SETR_32(DM_CM_INFO1, 0x00000000U);
+		SETR_32(DM_CM_INFO2, 0x00000000U);
+		/* interrupt clear */
+		SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BWE));
+		/* DM_CM_INFO2:  DMA-ch0 error occurred */
+		if ((BIT16 & mmc_drv_obj.dm_event2) != 0) {
+			mmc_drv_obj.dma_error_flag = TRUE;
+		} else {
+			mmc_drv_obj.during_dma_transfer = FALSE;
+			mmc_drv_obj.during_transfer = FALSE;
+		}
+		/* wait next interrupt */
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	}
+	/* DM_CM_INFO1: DMA-ch1 transfer complete or error occurred */
+	else if ((end_bit & mmc_drv_obj.dm_event1) != 0U) {
+		SETR_32(DM_CM_INFO1, 0x00000000U);
+		SETR_32(DM_CM_INFO2, 0x00000000U);
+		/* interrupt clear */
+		SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BRE));
+		/* DM_CM_INFO2: DMA-ch1 error occurred */
+		if ((BIT17 & mmc_drv_obj.dm_event2) != 0) {
+			mmc_drv_obj.dma_error_flag = TRUE;
+		} else {
+			mmc_drv_obj.during_dma_transfer = FALSE;
+			mmc_drv_obj.during_transfer = FALSE;
+		}
+		/* wait next interrupt */
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	}
+
+	/* Response end  */
+	else if ((SD_INFO1_INFO0 & mmc_drv_obj.int_event1) != 0) {
+		/* interrupt clear */
+		SETR_32(SD_INFO1, (GETR_32(SD_INFO1) & ~SD_INFO1_INFO0));
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	}
+	/* Access end  */
+	else if ((SD_INFO1_INFO2 & mmc_drv_obj.int_event1) != 0) {
+		/* interrupt clear */
+		SETR_32(SD_INFO1, (GETR_32(SD_INFO1) & ~SD_INFO1_INFO2));
+		mmc_drv_obj.state_machine_blocking = FALSE;
+	} else {
+		/* nothing to do. */
+	}
+
+	return (uint32_t) 0;
+}
+
+static EMMC_ERROR_CODE emmc_trans_sector(uint32_t *buff_address_virtual)
+{
+	uint32_t length, i;
+	uint64_t *bufPtrLL;
+
+	if (buff_address_virtual == NULL) {
+		return EMMC_ERR_PARAM;
+	}
+
+	if ((mmc_drv_obj.during_transfer != TRUE)
+	    || (mmc_drv_obj.remain_size == 0)) {
+		return EMMC_ERR_STATE;
+	}
+
+	bufPtrLL = (uint64_t *) buff_address_virtual;
+	length = mmc_drv_obj.remain_size;
+
+	/* data transefer */
+	for (i = 0; i < (length >> 3); i++) {
+		/* Write */
+		if (mmc_drv_obj.cmd_info.dir == HAL_MEMCARD_WRITE) {
+			SETR_64(SD_BUF0, *bufPtrLL);	/* buffer --> FIFO */
+		}
+		/* Read */
+		else {
+			/* Checks when the read data reaches SD_SIZE. */
+			/* The BRE bit is cleared at emmc_interrupt function. */
+			if (((i %
+			      (uint32_t) (EMMC_BLOCK_LENGTH >>
+					  EMMC_BUF_SIZE_SHIFT)) == 0U)
+			    && (i != 0U)) {
+				/* BRE check */
+				while (((GETR_32(SD_INFO2)) & SD_INFO2_BRE) ==
+				       0U) {
+					/* ERROR check */
+					if (((GETR_32(SD_INFO2)) &
+					     SD_INFO2_ALL_ERR) != 0U) {
+						return EMMC_ERR_TRANSFER;
+					}
+				}
+				/* BRE clear */
+				SETR_32(SD_INFO2,
+					(uint32_t) (GETR_32(SD_INFO2) &
+						    ~SD_INFO2_BRE));
+			}
+			*bufPtrLL = GETR_64(SD_BUF0);	/* FIFO --> buffer */
+		}
+		bufPtrLL++;
+	}
+
+	return EMMC_SUCCESS;
+}
diff --git a/drivers/renesas/common/emmc/emmc_mount.c b/drivers/renesas/common/emmc/emmc_mount.c
new file mode 100644
index 0000000..e04afd4
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_mount.c
@@ -0,0 +1,686 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_registers.h"
+#include "emmc_std.h"
+#include "micro_delay.h"
+#include "rcar_def.h"
+
+static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode);
+static EMMC_ERROR_CODE emmc_card_init(void);
+static EMMC_ERROR_CODE emmc_high_speed(void);
+static EMMC_ERROR_CODE emmc_bus_width(uint32_t width);
+static uint32_t emmc_set_timeout_register_value(uint32_t freq);
+static void set_sd_clk(uint32_t clkDiv);
+static uint32_t emmc_calc_tran_speed(uint32_t *freq);
+static void emmc_get_partition_access(void);
+static void emmc_set_bootpartition(void);
+
+static void emmc_set_bootpartition(void)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+	if (reg == PRR_PRODUCT_M3_CUT10) {
+		mmc_drv_obj.boot_partition_en =
+		    (EMMC_PARTITION_ID) ((mmc_drv_obj.ext_csd_data[179] &
+					  EMMC_BOOT_PARTITION_EN_MASK) >>
+					 EMMC_BOOT_PARTITION_EN_SHIFT);
+	} else if ((reg == PRR_PRODUCT_H3_CUT20)
+		   || (reg == PRR_PRODUCT_M3_CUT11)) {
+		mmc_drv_obj.boot_partition_en = mmc_drv_obj.partition_access;
+	} else {
+		if ((mmio_read_32(MFISBTSTSR) & MFISBTSTSR_BOOT_PARTITION) !=
+		    0U) {
+			mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_2;
+		} else {
+			mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_1;
+		}
+	}
+}
+
+static EMMC_ERROR_CODE emmc_card_init(void)
+{
+	int32_t retry;
+	uint32_t freq = MMC_400KHZ;	/* 390KHz */
+	EMMC_ERROR_CODE result;
+	uint32_t result_calc;
+
+	/* state check */
+	if ((mmc_drv_obj.initialize != TRUE)
+	    || (mmc_drv_obj.card_power_enable != TRUE)
+	    || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0)
+	    ) {
+		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* clock on (force change) */
+	mmc_drv_obj.current_freq = 0;
+	mmc_drv_obj.max_freq = MMC_20MHZ;
+	result = emmc_set_request_mmc_clock(&freq);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return EMMC_ERR;
+	}
+
+	rcar_micro_delay(1000U);	/* wait 1ms */
+
+	/* Get current access partition */
+	emmc_get_partition_access();
+
+	/* CMD0, arg=0x00000000 */
+	result = emmc_send_idle_cmd(0x00000000);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	rcar_micro_delay(200U);	/* wait 74clock 390kHz(189.74us) */
+
+	/* CMD1 */
+	emmc_make_nontrans_cmd(CMD1_SEND_OP_COND, EMMC_HOST_OCR_VALUE);
+	for (retry = 300; retry > 0; retry--) {
+		result =
+		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+		if (result != EMMC_SUCCESS) {
+			emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+			return result;
+		}
+
+		if ((mmc_drv_obj.r3_ocr & EMMC_OCR_STATUS_BIT) != 0) {
+			break;	/* card is ready. exit loop */
+		}
+		rcar_micro_delay(1000U);	/* wait 1ms */
+	}
+
+	if (retry == 0) {
+		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_TIMEOUT);
+		return EMMC_ERR_TIMEOUT;
+	}
+
+	switch (mmc_drv_obj.r3_ocr & EMMC_OCR_ACCESS_MODE_MASK) {
+	case EMMC_OCR_ACCESS_MODE_SECT:
+		mmc_drv_obj.access_mode = TRUE;	/* sector mode */
+		break;
+	default:
+		/* unknown value */
+		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR);
+		return EMMC_ERR;
+	}
+
+	/* CMD2 */
+	emmc_make_nontrans_cmd(CMD2_ALL_SEND_CID_MMC, 0x00000000);
+	mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.cid_data[0]);	/* use CID special buffer */
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	/* CMD3 */
+	emmc_make_nontrans_cmd(CMD3_SET_RELATIVE_ADDR, EMMC_RCA << 16);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	/* CMD9 (CSD) */
+	emmc_make_nontrans_cmd(CMD9_SEND_CSD, EMMC_RCA << 16);
+	mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.csd_data[0]);	/* use CSD special buffer */
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	/* card version check */
+	if (EMMC_CSD_SPEC_VARS() < 4) {
+		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT,
+				      EMMC_ERR_ILLEGAL_CARD);
+		return EMMC_ERR_ILLEGAL_CARD;
+	}
+
+	/* CMD7 (select card) */
+	emmc_make_nontrans_cmd(CMD7_SELECT_CARD, EMMC_RCA << 16);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	mmc_drv_obj.selected = TRUE;
+
+	/*
+	 * card speed check
+	 * Card spec is calculated from TRAN_SPEED(CSD)
+	 */
+	result_calc = emmc_calc_tran_speed(&freq);
+	if (result_calc == 0) {
+		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT,
+				      EMMC_ERR_ILLEGAL_CARD);
+		return EMMC_ERR_ILLEGAL_CARD;
+	}
+	mmc_drv_obj.max_freq = freq;	/* max frequency (card spec) */
+
+	result = emmc_set_request_mmc_clock(&freq);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return EMMC_ERR;
+	}
+
+	/* set read/write timeout */
+	mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq);
+	SETR_32(SD_OPTION,
+		((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) |
+		 mmc_drv_obj.data_timeout));
+
+	/* SET_BLOCKLEN(512byte) */
+	/* CMD16 */
+	emmc_make_nontrans_cmd(CMD16_SET_BLOCKLEN, EMMC_BLOCK_LENGTH);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	/* Transfer Data Length */
+	SETR_32(SD_SIZE, EMMC_BLOCK_LENGTH);
+
+	/* CMD8 (EXT_CSD) */
+	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
+			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
+			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
+			    HAL_MEMCARD_NOT_DMA);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		/*
+		 * CMD12 is not send.
+		 * If BUS initialization is failed, user must be execute Bus initialization again.
+		 * Bus initialization is start CMD0(soft reset command).
+		 */
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		return result;
+	}
+
+	/* Set boot partition */
+	emmc_set_bootpartition();
+
+	return EMMC_SUCCESS;
+}
+
+static EMMC_ERROR_CODE emmc_high_speed(void)
+{
+	uint32_t freq;	      /* High speed mode clock frequency */
+	EMMC_ERROR_CODE result;
+	uint8_t cardType;
+
+	/* state check */
+	if (mmc_drv_obj.selected != TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_HIGH_SPEED, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* max frequency */
+	cardType = (uint8_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_CARD_TYPE];
+	if ((cardType & EMMC_EXT_CSD_CARD_TYPE_52MHZ) != 0)
+		freq = MMC_52MHZ;
+	else if ((cardType & EMMC_EXT_CSD_CARD_TYPE_26MHZ) != 0)
+		freq = MMC_26MHZ;
+	else
+		freq = MMC_20MHZ;
+
+	/* Hi-Speed-mode selection */
+	if ((freq == MMC_52MHZ) || (freq == MMC_26MHZ)) {
+		/* CMD6 */
+		emmc_make_nontrans_cmd(CMD6_SWITCH, EMMC_SWITCH_HS_TIMING);
+		result =
+		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+		if (result != EMMC_SUCCESS) {
+			emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
+			return result;
+		}
+
+		mmc_drv_obj.hs_timing = TIMING_HIGH_SPEED;	/* High-Speed */
+	}
+
+	/* set mmc clock */
+	mmc_drv_obj.max_freq = freq;
+	result = emmc_set_request_mmc_clock(&freq);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
+		return EMMC_ERR;
+	}
+
+	/* set read/write timeout */
+	mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq);
+	SETR_32(SD_OPTION,
+		((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) |
+		 mmc_drv_obj.data_timeout));
+
+	/* CMD13 */
+	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
+	result =
+	    emmc_exec_cmd(EMMC_R1_ERROR_MASK_WITHOUT_CRC, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
+		return result;
+	}
+
+	return EMMC_SUCCESS;
+}
+
+static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode)
+{
+	uint32_t value;
+
+	/* busy check */
+	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) {
+		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK,
+				      EMMC_ERR_CARD_BUSY);
+		return EMMC_ERR;
+	}
+
+	if (mode == TRUE) {
+		/* clock ON */
+		value =
+		    ((GETR_32(SD_CLK_CTRL) | MMC_SD_CLK_START) &
+		     SD_CLK_WRITE_MASK);
+		SETR_32(SD_CLK_CTRL, value);	/* on  */
+		mmc_drv_obj.clock_enable = TRUE;
+	} else {
+		/* clock OFF */
+		value =
+		    ((GETR_32(SD_CLK_CTRL) & MMC_SD_CLK_STOP) &
+		     SD_CLK_WRITE_MASK);
+		SETR_32(SD_CLK_CTRL, value);	/* off */
+		mmc_drv_obj.clock_enable = FALSE;
+	}
+
+	return EMMC_SUCCESS;
+}
+
+static EMMC_ERROR_CODE emmc_bus_width(uint32_t width)
+{
+	EMMC_ERROR_CODE result = EMMC_ERR;
+
+	/* parameter check */
+	if ((width != 8) && (width != 4) && (width != 1)) {
+		emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* state check */
+	if (mmc_drv_obj.selected != TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* 2 = 8bit, 1 = 4bit, 0 =1bit */
+	mmc_drv_obj.bus_width = (HAL_MEMCARD_DATA_WIDTH) (width >> 2);
+
+	/* CMD6 */
+	emmc_make_nontrans_cmd(CMD6_SWITCH,
+			       (EMMC_SWITCH_BUS_WIDTH_1 |
+				(mmc_drv_obj.bus_width << 8)));
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		/* occurred error */
+		mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
+		goto EXIT;
+	}
+
+	switch (mmc_drv_obj.bus_width) {
+	case HAL_MEMCARD_DATA_WIDTH_1_BIT:
+		SETR_32(SD_OPTION,
+			((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT15));
+		break;
+	case HAL_MEMCARD_DATA_WIDTH_4_BIT:
+		SETR_32(SD_OPTION, (GETR_32(SD_OPTION) & ~(BIT15 | BIT13)));
+		break;
+	case HAL_MEMCARD_DATA_WIDTH_8_BIT:
+		SETR_32(SD_OPTION,
+			((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT13));
+		break;
+	default:
+		goto EXIT;
+	}
+
+	/* CMD13 */
+	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		goto EXIT;
+	}
+
+	/* CMD8 (EXT_CSD) */
+	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
+			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
+			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
+			    HAL_MEMCARD_NOT_DMA);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		goto EXIT;
+	}
+
+	return EMMC_SUCCESS;
+
+EXIT:
+	emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, result);
+	ERROR("BL2: emmc bus_width error end\n");
+	return result;
+}
+
+EMMC_ERROR_CODE emmc_select_partition(EMMC_PARTITION_ID id)
+{
+	EMMC_ERROR_CODE result;
+	uint32_t arg;
+	uint32_t partition_config;
+
+	/* state check */
+	if (mmc_drv_obj.mount != TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* id = PARTITION_ACCESS(Bit[2:0]) */
+	if ((id & ~PARTITION_ID_MASK) != 0) {
+		emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* EXT_CSD[179] value */
+	partition_config =
+	    (uint32_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_PARTITION_CONFIG];
+	if ((partition_config & PARTITION_ID_MASK) == id) {
+		result = EMMC_SUCCESS;
+	} else {
+
+		partition_config =
+		    (uint32_t) ((partition_config & ~PARTITION_ID_MASK) | id);
+		arg = EMMC_SWITCH_PARTITION_CONFIG | (partition_config << 8);
+
+		result = emmc_set_ext_csd(arg);
+	}
+
+	return result;
+}
+
+static void set_sd_clk(uint32_t clkDiv)
+{
+	uint32_t dataL;
+
+	dataL = (GETR_32(SD_CLK_CTRL) & (~SD_CLK_CTRL_CLKDIV_MASK));
+
+	switch (clkDiv) {
+	case 1:
+		dataL |= 0x000000FFU;
+		break;		/* 1/1   */
+	case 2:
+		dataL |= 0x00000000U;
+		break;		/* 1/2   */
+	case 4:
+		dataL |= 0x00000001U;
+		break;		/* 1/4   */
+	case 8:
+		dataL |= 0x00000002U;
+		break;		/* 1/8   */
+	case 16:
+		dataL |= 0x00000004U;
+		break;		/* 1/16  */
+	case 32:
+		dataL |= 0x00000008U;
+		break;		/* 1/32  */
+	case 64:
+		dataL |= 0x00000010U;
+		break;		/* 1/64  */
+	case 128:
+		dataL |= 0x00000020U;
+		break;		/* 1/128 */
+	case 256:
+		dataL |= 0x00000040U;
+		break;		/* 1/256 */
+	case 512:
+		dataL |= 0x00000080U;
+		break;		/* 1/512 */
+	}
+
+	SETR_32(SD_CLK_CTRL, dataL);
+	mmc_drv_obj.current_freq = (uint32_t) clkDiv;
+}
+
+static void emmc_get_partition_access(void)
+{
+	uint32_t reg;
+	EMMC_ERROR_CODE result;
+
+	reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+	if ((reg == PRR_PRODUCT_H3_CUT20) || (reg == PRR_PRODUCT_M3_CUT11)) {
+		SETR_32(SD_OPTION, 0x000060EEU);	/* 8 bits width */
+		/* CMD8 (EXT_CSD) */
+		emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000U,
+				    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
+				    EMMC_MAX_EXT_CSD_LENGTH,
+				    HAL_MEMCARD_READ, HAL_MEMCARD_NOT_DMA);
+		mmc_drv_obj.get_partition_access_flag = TRUE;
+		result =
+		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+		mmc_drv_obj.get_partition_access_flag = FALSE;
+		if (result == EMMC_SUCCESS) {
+			mmc_drv_obj.partition_access =
+			    (EMMC_PARTITION_ID) (mmc_drv_obj.ext_csd_data[179]
+						 & PARTITION_ID_MASK);
+		} else if (result == EMMC_ERR_CMD_TIMEOUT) {
+			mmc_drv_obj.partition_access = PARTITION_ID_BOOT_1;
+		} else {
+			emmc_write_error_info(EMMC_FUNCNO_GET_PERTITION_ACCESS,
+					      result);
+			panic();
+		}
+		SETR_32(SD_OPTION, 0x0000C0EEU);	/* Initialize */
+	}
+}
+
+static uint32_t emmc_calc_tran_speed(uint32_t *freq)
+{
+	const uint32_t unit[8] = { 10000U, 100000U, 1000000U, 10000000U,
+				   0U, 0U, 0U, 0U }; /* frequency unit (1/10) */
+	const uint32_t mult[16] = { 0U, 10U, 12U, 13U, 15U, 20U, 26U, 30U, 35U,
+				    40U, 45U, 52U, 55U, 60U, 70U, 80U };
+	uint32_t tran_speed = EMMC_CSD_TRAN_SPEED();
+	uint32_t max_freq;
+	uint32_t result;
+
+	/*
+	 * tran_speed = 0x32
+	 * unit[tran_speed&0x7] = uint[0x2] = 1000000
+	 * mult[(tran_speed&0x78)>>3] = mult[0x30>>3] = mult[6] = 26
+	 * 1000000 * 26 = 26000000 (26MHz)
+	 */
+
+	result = 1;
+	max_freq =
+	    unit[tran_speed & EMMC_TRANSPEED_FREQ_UNIT_MASK] *
+	    mult[(tran_speed & EMMC_TRANSPEED_MULT_MASK) >>
+		 EMMC_TRANSPEED_MULT_SHIFT];
+
+	if (max_freq == 0) {
+		result = 0;
+	} else if (max_freq >= MMC_FREQ_52MHZ) {
+		*freq = MMC_52MHZ;
+	} else if (max_freq >= MMC_FREQ_26MHZ) {
+		*freq = MMC_26MHZ;
+	} else if (max_freq >= MMC_FREQ_20MHZ) {
+		*freq = MMC_20MHZ;
+	} else {
+		*freq = MMC_400KHZ;
+	}
+
+	return result;
+}
+
+static uint32_t emmc_set_timeout_register_value(uint32_t freq)
+{
+	uint32_t timeout_cnt;	/* SD_OPTION   - Timeout Counter  */
+
+	switch (freq) {
+	case 1U:
+		timeout_cnt = 0xE0U;
+		break;		/* SDCLK * 2^27 */
+	case 2U:
+		timeout_cnt = 0xE0U;
+		break;		/* SDCLK * 2^27 */
+	case 4U:
+		timeout_cnt = 0xD0U;
+		break;		/* SDCLK * 2^26 */
+	case 8U:
+		timeout_cnt = 0xC0U;
+		break;		/* SDCLK * 2^25 */
+	case 16U:
+		timeout_cnt = 0xB0U;
+		break;		/* SDCLK * 2^24 */
+	case 32U:
+		timeout_cnt = 0xA0U;
+		break;		/* SDCLK * 2^23 */
+	case 64U:
+		timeout_cnt = 0x90U;
+		break;		/* SDCLK * 2^22 */
+	case 128U:
+		timeout_cnt = 0x80U;
+		break;		/* SDCLK * 2^21 */
+	case 256U:
+		timeout_cnt = 0x70U;
+		break;		/* SDCLK * 2^20 */
+	case 512U:
+		timeout_cnt = 0x70U;
+		break;		/* SDCLK * 2^20 */
+	default:
+		timeout_cnt = 0xE0U;
+		break;		/* SDCLK * 2^27 */
+	}
+
+	return timeout_cnt;
+}
+
+EMMC_ERROR_CODE emmc_set_ext_csd(uint32_t arg)
+{
+	EMMC_ERROR_CODE result;
+
+	/* CMD6 */
+	emmc_make_nontrans_cmd(CMD6_SWITCH, arg);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+
+	/* CMD13 */
+	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+
+	/* CMD8 (EXT_CSD) */
+	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
+			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
+			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
+			    HAL_MEMCARD_NOT_DMA);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+	return EMMC_SUCCESS;
+}
+
+EMMC_ERROR_CODE emmc_set_request_mmc_clock(uint32_t *freq)
+{
+	/* parameter check */
+	if (freq == NULL) {
+		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* state check */
+	if ((mmc_drv_obj.initialize != TRUE)
+	    || (mmc_drv_obj.card_power_enable != TRUE)) {
+		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* clock is already running in the desired frequency. */
+	if ((mmc_drv_obj.clock_enable == TRUE)
+	    && (mmc_drv_obj.current_freq == *freq)) {
+		return EMMC_SUCCESS;
+	}
+
+	/* busy check */
+	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) {
+		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK,
+				      EMMC_ERR_CARD_BUSY);
+		return EMMC_ERR;
+	}
+
+	set_sd_clk(*freq);
+	mmc_drv_obj.clock_enable = FALSE;
+
+	return emmc_clock_ctrl(TRUE);	/* clock on */
+}
+
+EMMC_ERROR_CODE rcar_emmc_mount(void)
+{
+	EMMC_ERROR_CODE result;
+
+	/* state check */
+	if ((mmc_drv_obj.initialize != TRUE)
+	    || (mmc_drv_obj.card_power_enable != TRUE)
+	    || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0)
+	    ) {
+		emmc_write_error_info(EMMC_FUNCNO_MOUNT, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* initialize card (IDLE state --> Transfer state) */
+	result = emmc_card_init();
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
+		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
+			/* nothing to do. */
+		}
+		return result;
+	}
+
+	/* Switching high speed mode */
+	result = emmc_high_speed();
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
+		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
+			/* nothing to do. */
+		}
+		return result;
+	}
+
+	/* Changing the data bus width */
+	result = emmc_bus_width(8);
+	if (result != EMMC_SUCCESS) {
+		emmc_write_error_info_func_no(EMMC_FUNCNO_BUS_WIDTH);
+		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
+			/* nothing to do. */
+		}
+		return result;
+	}
+
+	/* mount complete */
+	mmc_drv_obj.mount = TRUE;
+
+	return EMMC_SUCCESS;
+}
diff --git a/drivers/renesas/common/emmc/emmc_read.c b/drivers/renesas/common/emmc/emmc_read.c
new file mode 100644
index 0000000..96e73ca
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_read.c
@@ -0,0 +1,130 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_registers.h"
+#include "emmc_std.h"
+
+#define MIN_EMMC(a, b)	(((a) < (b)) ? (a) : (b))
+#define EMMC_RW_SECTOR_COUNT_MAX	0x0000ffffU
+
+static EMMC_ERROR_CODE emmc_multiple_block_read(uint32_t *buff_address_virtual,
+		uint32_t sector_number, uint32_t count,
+		HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode)
+{
+	EMMC_ERROR_CODE result;
+
+	/* parameter check */
+	if ((count > EMMC_RW_SECTOR_COUNT_MAX)
+	    || (count == 0)
+	    || ((transfer_mode != HAL_MEMCARD_DMA)
+		&& (transfer_mode != HAL_MEMCARD_NOT_DMA))
+	    ) {
+		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* CMD23 */
+	emmc_make_nontrans_cmd(CMD23_SET_BLOCK_COUNT, count);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+	SETR_32(SD_SECCNT, count);
+	SETR_32(SD_STOP, 0x00000100);
+	/* SD_BUF Read/Write DMA Transfer enable */
+	SETR_32(CC_EXT_MODE, (CC_EXT_MODE_CLEAR | CC_EXT_MODE_DMASDRW_ENABLE));
+
+	/* CMD18 */
+	emmc_make_trans_cmd(CMD18_READ_MULTIPLE_BLOCK, sector_number,
+			    buff_address_virtual,
+			    count << EMMC_SECTOR_SIZE_SHIFT, HAL_MEMCARD_READ,
+			    transfer_mode);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;	/* CMD18 error code */
+	}
+
+	/* CMD13 */
+	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+#if RCAR_BL2_DCACHE == 1
+	if (transfer_mode == HAL_MEMCARD_NOT_DMA) {
+		flush_dcache_range((uint64_t) buff_address_virtual,
+				   ((size_t) count << EMMC_SECTOR_SIZE_SHIFT));
+	}
+#endif /* RCAR_BL2_DCACHE == 1 */
+
+	/* ready status check */
+	if ((mmc_drv_obj.r1_card_status & EMMC_R1_READY) == 0) {
+		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR,
+				      EMMC_ERR_CARD_BUSY);
+		return EMMC_ERR_CARD_BUSY;
+	}
+
+	/* state check */
+	if (mmc_drv_obj.current_state != EMMC_R1_STATE_TRAN) {
+		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR,
+				      EMMC_ERR_CARD_STATE);
+		return EMMC_ERR_CARD_STATE;
+	}
+
+	return EMMC_SUCCESS;
+}
+
+EMMC_ERROR_CODE emmc_read_sector(uint32_t *buff_address_virtual,
+				 uint32_t sector_number,
+				 uint32_t count, uint32_t feature_flags)
+{
+	uint32_t trans_count;
+	uint32_t remain;
+	EMMC_ERROR_CODE result;
+	HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode;
+
+	/* parameter check */
+	if (count == 0) {
+		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_PARAM);
+		return EMMC_ERR_PARAM;
+	}
+
+	/* state check */
+	if (mmc_drv_obj.mount != TRUE) {
+		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_STATE);
+		return EMMC_ERR_STATE;
+	}
+
+	/* DMA? */
+	if ((feature_flags & LOADIMAGE_FLAGS_DMA_ENABLE) != 0) {
+		transfer_mode = HAL_MEMCARD_DMA;
+	} else {
+		transfer_mode = HAL_MEMCARD_NOT_DMA;
+	}
+
+	remain = count;
+	while (remain != 0) {
+		trans_count = MIN_EMMC(remain, EMMC_RW_SECTOR_COUNT_MAX);
+		result =
+		    emmc_multiple_block_read(buff_address_virtual,
+					     sector_number, trans_count,
+					     transfer_mode);
+		if (result != EMMC_SUCCESS) {
+			return result;
+		}
+
+		buff_address_virtual += (EMMC_BLOCK_LENGTH_DW * trans_count);
+		sector_number += trans_count;
+		remain -= trans_count;
+	}
+
+	return EMMC_SUCCESS;
+}
diff --git a/drivers/renesas/common/emmc/emmc_registers.h b/drivers/renesas/common/emmc/emmc_registers.h
new file mode 100644
index 0000000..67d285d
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_registers.h
@@ -0,0 +1,215 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMMC_REGISTERS_H
+#define EMMC_REGISTERS_H
+
+/* MMC channel select */
+#define MMC_CH0		(0U)	/* SDHI2/MMC0 */
+#define MMC_CH1		(1U)	/* SDHI3/MMC1 */
+
+#if (RCAR_LSI == RCAR_E3)  || (RCAR_LSI == RZ_G2M) || (RCAR_LSI == RZ_G2H) || (RCAR_LSI == RZ_G2N)
+#define USE_MMC_CH	(MMC_CH1)	/* R-Car E3 or RZ/G2{H,M,N} */
+#else /* RCAR_LSI == RCAR_E3 || RCAR_LSI == RZ_G2{H,M,N} */
+#define USE_MMC_CH	(MMC_CH0)	/* R-Car H3/M3/M3N */
+#endif /* RCAR_LSI == RCAR_E3 || RCAR_LSI == RZ_G2{H,M,N} */
+
+#define BIT0	(0x00000001U)
+#define BIT1	(0x00000002U)
+#define BIT2	(0x00000004U)
+#define BIT3	(0x00000008U)
+#define BIT4	(0x00000010U)
+#define BIT5	(0x00000020U)
+#define BIT6	(0x00000040U)
+#define BIT7	(0x00000080U)
+#define BIT8	(0x00000100U)
+#define BIT9	(0x00000200U)
+#define BIT10	(0x00000400U)
+#define BIT11	(0x00000800U)
+#define BIT12	(0x00001000U)
+#define BIT13	(0x00002000U)
+#define BIT14	(0x00004000U)
+#define BIT15	(0x00008000U)
+#define BIT16	(0x00010000U)
+#define BIT17	(0x00020000U)
+#define BIT18	(0x00040000U)
+#define BIT19	(0x00080000U)
+#define BIT20	(0x00100000U)
+#define BIT21	(0x00200000U)
+#define BIT22	(0x00400000U)
+#define BIT23	(0x00800000U)
+#define BIT24	(0x01000000U)
+#define BIT25	(0x02000000U)
+#define BIT26	(0x04000000U)
+#define BIT27	(0x08000000U)
+#define BIT28	(0x10000000U)
+#define BIT29	(0x20000000U)
+#define BIT30	(0x40000000U)
+#define BIT31	(0x80000000U)
+
+#if USE_MMC_CH == MMC_CH0
+#define CPG_SDxCKCR		(CPG_SD2CKCR)	/* SDHI2/MMC0 */
+#else /* USE_MMC_CH == MMC_CH0 */
+#define CPG_SDxCKCR		(CPG_SD3CKCR)	/* SDHI3/MMC1 */
+#endif /* USE_MMC_CH == MMC_CH0 */
+
+/* Boot Status register */
+#define  MFISBTSTSR			(0xE6260604U)
+
+#define  MFISBTSTSR_BOOT_PARTITION	(0x00000010U)
+
+/* eMMC registers */
+#define MMC0_SD_BASE		(0xEE140000U)
+#define MMC1_SD_BASE		(0xEE160000U)
+
+#if USE_MMC_CH == MMC_CH0
+#define MMC_SD_BASE		(MMC0_SD_BASE)
+#else /* USE_MMC_CH == MMC_CH0 */
+#define MMC_SD_BASE		(MMC1_SD_BASE)
+#endif /* USE_MMC_CH == MMC_CH0 */
+
+#define SD_CMD			(MMC_SD_BASE + 0x0000U)
+#define SD_PORTSEL		(MMC_SD_BASE + 0x0008U)
+#define SD_ARG			(MMC_SD_BASE + 0x0010U)
+#define SD_ARG1			(MMC_SD_BASE + 0x0018U)
+#define SD_STOP			(MMC_SD_BASE + 0x0020U)
+#define SD_SECCNT		(MMC_SD_BASE + 0x0028U)
+#define SD_RSP10		(MMC_SD_BASE + 0x0030U)
+#define SD_RSP1			(MMC_SD_BASE + 0x0038U)
+#define SD_RSP32		(MMC_SD_BASE + 0x0040U)
+#define SD_RSP3			(MMC_SD_BASE + 0x0048U)
+#define SD_RSP54		(MMC_SD_BASE + 0x0050U)
+#define SD_RSP5			(MMC_SD_BASE + 0x0058U)
+#define SD_RSP76		(MMC_SD_BASE + 0x0060U)
+#define SD_RSP7			(MMC_SD_BASE + 0x0068U)
+#define SD_INFO1		(MMC_SD_BASE + 0x0070U)
+#define SD_INFO2		(MMC_SD_BASE + 0x0078U)
+#define SD_INFO1_MASK		(MMC_SD_BASE + 0x0080U)
+#define SD_INFO2_MASK		(MMC_SD_BASE + 0x0088U)
+#define SD_CLK_CTRL		(MMC_SD_BASE + 0x0090U)
+#define SD_SIZE			(MMC_SD_BASE + 0x0098U)
+#define SD_OPTION		(MMC_SD_BASE + 0x00A0U)
+#define SD_ERR_STS1		(MMC_SD_BASE + 0x00B0U)
+#define SD_ERR_STS2		(MMC_SD_BASE + 0x00B8U)
+#define SD_BUF0			(MMC_SD_BASE + 0x00C0U)
+#define SDIO_MODE		(MMC_SD_BASE + 0x00D0U)
+#define SDIO_INFO1		(MMC_SD_BASE + 0x00D8U)
+#define SDIO_INFO1_MASK		(MMC_SD_BASE + 0x00E0U)
+#define CC_EXT_MODE		(MMC_SD_BASE + 0x0360U)
+#define SOFT_RST		(MMC_SD_BASE + 0x0380U)
+#define VERSION			(MMC_SD_BASE + 0x0388U)
+#define HOST_MODE		(MMC_SD_BASE + 0x0390U)
+#define DM_CM_DTRAN_MODE	(MMC_SD_BASE + 0x0820U)
+#define DM_CM_DTRAN_CTRL	(MMC_SD_BASE + 0x0828U)
+#define DM_CM_RST		(MMC_SD_BASE + 0x0830U)
+#define DM_CM_INFO1		(MMC_SD_BASE + 0x0840U)
+#define DM_CM_INFO1_MASK	(MMC_SD_BASE + 0x0848U)
+#define DM_CM_INFO2		(MMC_SD_BASE + 0x0850U)
+#define DM_CM_INFO2_MASK	(MMC_SD_BASE + 0x0858U)
+#define DM_DTRAN_ADDR		(MMC_SD_BASE + 0x0880U)
+
+/* SD_INFO1 Registers */
+#define SD_INFO1_HPIRES		0x00010000UL /* Response Reception Completion */
+#define SD_INFO1_INFO10		0x00000400UL /* Indicates the SDDAT3 state */
+#define SD_INFO1_INFO9		0x00000200UL /* SDDAT3 Card Insertion */
+#define SD_INFO1_INFO8		0x00000100UL /* SDDAT3 Card Removal */
+#define SD_INFO1_INFO7		0x00000080UL /* Write Protect */
+#define SD_INFO1_INFO5		0x00000020UL /* Indicates the ISDCD state */
+#define SD_INFO1_INFO4		0x00000010UL /* ISDCD Card Insertion */
+#define SD_INFO1_INFO3		0x00000008UL /* ISDCD Card Removal */
+#define SD_INFO1_INFO2		0x00000004UL /* Access end */
+#define SD_INFO1_INFO0		0x00000001UL /* Response end */
+
+/* SD_INFO2 Registers */
+#define SD_INFO2_ILA		0x00008000UL /* Illegal Access Error */
+#define SD_INFO2_CBSY		0x00004000UL /* Command Type Register Busy */
+#define SD_INFO2_SCLKDIVEN	0x00002000UL
+#define SD_INFO2_BWE		0x00000200UL /* SD_BUF Write Enable */
+#define SD_INFO2_BRE		0x00000100UL /* SD_BUF Read Enable */
+#define SD_INFO2_DAT0		0x00000080UL /* SDDAT0 */
+#define SD_INFO2_ERR6		0x00000040UL /* Response Timeout */
+#define SD_INFO2_ERR5		0x00000020UL /* SD_BUF Illegal Read Access */
+#define SD_INFO2_ERR4		0x00000010UL /* SD_BUF Illegal Write Access */
+#define SD_INFO2_ERR3		0x00000008UL /* Data Timeout */
+#define SD_INFO2_ERR2		0x00000004UL /* END Error */
+#define SD_INFO2_ERR1		0x00000002UL /* CRC Error */
+#define SD_INFO2_ERR0		0x00000001UL /* CMD Error */
+#define SD_INFO2_ALL_ERR	0x0000807FUL
+#define SD_INFO2_CLEAR		0x00000800UL /* BIT11 write value should always be 1. HWM_0003 */
+
+/* SOFT_RST */
+#define SOFT_RST_SDRST		0x00000001UL
+
+/* SD_CLK_CTRL */
+#define SD_CLK_CTRL_SDCLKOFFEN		0x00000200UL
+#define SD_CLK_CTRL_SCLKEN		0x00000100UL
+#define SD_CLK_CTRL_CLKDIV_MASK		0x000000FFUL
+#define SD_CLOCK_ENABLE			0x00000100UL
+#define SD_CLOCK_DISABLE		0x00000000UL
+#define SD_CLK_WRITE_MASK		0x000003FFUL
+#define SD_CLK_CLKDIV_CLEAR_MASK	0xFFFFFF0FUL
+
+/* SD_OPTION */
+#define SD_OPTION_TIMEOUT_CNT_MASK	0x000000F0UL
+
+/*
+ * MMC Clock Frequency
+ * 200MHz * 1/x = output clock
+ */
+#define MMC_CLK_OFF		0UL   /* Clock output is disabled */
+#define MMC_400KHZ		512UL /* 200MHz * 1/512 = 390 KHz */
+#define MMC_20MHZ		16UL  /* 200MHz * 1/16 = 12.5 MHz Normal speed mode */
+#define MMC_26MHZ		8UL   /* 200MHz * 1/8 = 25 MHz HS mode 26Mhz */
+#define MMC_52MHZ		4UL   /* 200MHz * 1/4 = 50 MHz HS mode 52Mhz */
+#define MMC_100MHZ		2UL   /* 200MHz * 1/2 = 100 MHz */
+#define MMC_200MHZ		1UL   /* 200MHz * 1/1 = 200 MHz */
+
+#define MMC_FREQ_52MHZ		52000000UL
+#define MMC_FREQ_26MHZ		26000000UL
+#define MMC_FREQ_20MHZ		20000000UL
+
+/* MMC Clock DIV */
+#define MMC_SD_CLK_START	0x00000100UL	/* CLOCK On */
+#define MMC_SD_CLK_STOP		(~0x00000100UL)	/* CLOCK stop */
+#define MMC_SD_CLK_DIV1		0x000000FFUL	/* 1/1 */
+#define MMC_SD_CLK_DIV2		0x00000000UL	/* 1/2 */
+#define MMC_SD_CLK_DIV4		0x00000001UL	/* 1/4 */
+#define MMC_SD_CLK_DIV8		0x00000002UL	/* 1/8 */
+#define MMC_SD_CLK_DIV16	0x00000004UL	/* 1/16 */
+#define MMC_SD_CLK_DIV32	0x00000008UL	/* 1/32 */
+#define MMC_SD_CLK_DIV64	0x00000010UL	/* 1/64 */
+#define MMC_SD_CLK_DIV128	0x00000020UL	/* 1/128 */
+#define MMC_SD_CLK_DIV256	0x00000040UL	/* 1/256 */
+#define MMC_SD_CLK_DIV512	0x00000080UL	/* 1/512 */
+
+/* DM_CM_DTRAN_MODE */
+#define DM_CM_DTRAN_MODE_CH0		0x00000000UL	/* CH0(downstream) */
+#define DM_CM_DTRAN_MODE_CH1		0x00010000UL	/* CH1(upstream)   */
+#define DM_CM_DTRAN_MODE_BIT_WIDTH	0x00000030UL
+
+/* CC_EXT_MODE */
+#define CC_EXT_MODE_DMASDRW_ENABLE	0x00000002UL	/* SD_BUF Read/Write DMA Transfer */
+#define CC_EXT_MODE_CLEAR		0x00001010UL	/* BIT 12 & 4 always 1. */
+
+/* DM_CM_INFO_MASK */
+#define DM_CM_INFO_MASK_CLEAR		0xFFFCFFFEUL
+#define DM_CM_INFO_CH0_ENABLE		0x00010001UL
+#define DM_CM_INFO_CH1_ENABLE		0x00020001UL
+
+/* DM_DTRAN_ADDR */
+#define DM_DTRAN_ADDR_WRITE_MASK	0xFFFFFFF8UL
+
+/* DM_CM_DTRAN_CTRL */
+#define DM_CM_DTRAN_CTRL_START		0x00000001UL
+
+/* SYSC Registers */
+#if USE_MMC_CH == MMC_CH0
+#define CPG_MSTP_MMC		(BIT12)	/* SDHI2/MMC0 */
+#else /* USE_MMC_CH == MMC_CH0 */
+#define CPG_MSTP_MMC		(BIT11)	/* SDHI3/MMC1 */
+#endif /* USE_MMC_CH == MMC_CH0 */
+
+#endif /* EMMC_REGISTERS_H */
diff --git a/drivers/renesas/common/emmc/emmc_std.h b/drivers/renesas/common/emmc/emmc_std.h
new file mode 100644
index 0000000..087c6e9
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_std.h
@@ -0,0 +1,475 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMMC_STD_H
+#define EMMC_STD_H
+
+#include "emmc_hal.h"
+
+#ifndef FALSE
+#define FALSE	0U
+#endif
+#ifndef TRUE
+#define TRUE	1U
+#endif
+
+/* 64bit registers */
+#define SETR_64(r, v)			(*(volatile uint64_t *)(r) = (v))
+#define GETR_64(r)			(*(volatile uint64_t *)(r))
+
+/* 32bit registers */
+#define SETR_32(r, v)			(*(volatile uint32_t *)(r) = (v))
+#define GETR_32(r)			(*(volatile uint32_t *)(r))
+
+/* 16bit registers */
+#define SETR_16(r, v)			(*(volatile uint16_t *)(r) = (v))
+#define GETR_16(r)			(*(volatile uint16_t *)(r))
+
+/* 8bit registers */
+#define SETR_8(r, v)			(*(volatile uint8_t *)(r) = (v))
+#define GETR_8(r)			(*(volatile uint8_t *)(r))
+
+/* CSD register Macros */
+#define EMMC_GET_CID(x, y)	(emmc_bit_field(mmc_drv_obj.cid_data, (x), (y)))
+
+#define EMMC_CID_MID()			(EMMC_GET_CID(127, 120))
+#define EMMC_CID_CBX()			(EMMC_GET_CID(113, 112))
+#define EMMC_CID_OID()			(EMMC_GET_CID(111, 104))
+#define EMMC_CID_PNM1()			(EMMC_GET_CID(103, 88))
+#define EMMC_CID_PNM2()			(EMMC_GET_CID(87, 56))
+#define EMMC_CID_PRV()			(EMMC_GET_CID(55, 48))
+#define EMMC_CID_PSN()			(EMMC_GET_CID(47, 16))
+#define EMMC_CID_MDT()			(EMMC_GET_CID(15, 8))
+#define EMMC_CID_CRC()			(EMMC_GET_CID(7, 1))
+
+/* CSD register Macros */
+#define EMMC_GET_CSD(x, y)	(emmc_bit_field(mmc_drv_obj.csd_data, (x), (y)))
+
+#define EMMC_CSD_CSD_STRUCTURE()	(EMMC_GET_CSD(127, 126))
+#define EMMC_CSD_SPEC_VARS()		(EMMC_GET_CSD(125, 122))
+#define EMMC_CSD_TAAC()			(EMMC_GET_CSD(119, 112))
+#define EMMC_CSD_NSAC()			(EMMC_GET_CSD(111, 104))
+#define EMMC_CSD_TRAN_SPEED()		(EMMC_GET_CSD(103, 96))
+#define EMMC_CSD_CCC()			(EMMC_GET_CSD(95, 84))
+#define EMMC_CSD_READ_BL_LEN()		(EMMC_GET_CSD(83, 80))
+#define EMMC_CSD_READ_BL_PARTIAL()	(EMMC_GET_CSD(79, 79))
+#define EMMC_CSD_WRITE_BLK_MISALIGN()	(EMMC_GET_CSD(78, 78))
+#define EMMC_CSD_READ_BLK_MISALIGN()	(EMMC_GET_CSD(77, 77))
+#define EMMC_CSD_DSR_IMP()		(EMMC_GET_CSD(76, 76))
+#define EMMC_CSD_C_SIZE()		(EMMC_GET_CSD(73, 62))
+#define EMMC_CSD_VDD_R_CURR_MIN()	(EMMC_GET_CSD(61, 59))
+#define EMMC_CSD_VDD_R_CURR_MAX()	(EMMC_GET_CSD(58, 56))
+#define EMMC_CSD_VDD_W_CURR_MIN()	(EMMC_GET_CSD(55, 53))
+#define EMMC_CSD_VDD_W_CURR_MAX()	(EMMC_GET_CSD(52, 50))
+#define EMMC_CSD_C_SIZE_MULT()		(EMMC_GET_CSD(49, 47))
+#define EMMC_CSD_ERASE_GRP_SIZE()	(EMMC_GET_CSD(46, 42))
+#define EMMC_CSD_ERASE_GRP_MULT()	(EMMC_GET_CSD(41, 37))
+#define EMMC_CSD_WP_GRP_SIZE()		(EMMC_GET_CSD(36, 32))
+#define EMMC_CSD_WP_GRP_ENABLE()	(EMMC_GET_CSD(31, 31))
+#define EMMC_CSD_DEFALT_ECC()		(EMMC_GET_CSD(30, 29))
+#define EMMC_CSD_R2W_FACTOR()		(EMMC_GET_CSD(28, 26))
+#define EMMC_CSD_WRITE_BL_LEN()		(EMMC_GET_CSD(25, 22))
+#define EMMC_CSD_WRITE_BL_PARTIAL()	(EMMC_GET_CSD(21, 21))
+#define EMMC_CSD_CONTENT_PROT_APP()	(EMMC_GET_CSD(16, 16))
+#define EMMC_CSD_FILE_FORMAT_GRP()	(EMMC_GET_CSD(15, 15))
+#define EMMC_CSD_COPY()			(EMMC_GET_CSD(14, 14))
+#define EMMC_CSD_PERM_WRITE_PROTECT()	(EMMC_GET_CSD(13, 13))
+#define EMMC_CSD_TMP_WRITE_PROTECT()	(EMMC_GET_CSD(12, 12))
+#define EMMC_CSD_FILE_FORMAT()		(EMMC_GET_CSD(11, 10))
+#define EMMC_CSD_ECC()			(EMMC_GET_CSD(9, 8))
+#define EMMC_CSD_CRC()			(EMMC_GET_CSD(7, 1))
+
+/* sector access */
+#define EMMC_4B_BOUNDARY_CHECK_MASK	0x00000003
+#define EMMC_SECTOR_SIZE_SHIFT		9U	/* 512 = 2^9 */
+#define EMMC_SECTOR_SIZE		512
+#define EMMC_BLOCK_LENGTH		512
+#define EMMC_BLOCK_LENGTH_DW		128
+#define EMMC_BUF_SIZE_SHIFT		3U	/* 8byte = 2^3 */
+
+/* eMMC specification clock */
+#define EMMC_CLOCK_SPEC_400K		400000UL	 /* initialize clock 400KHz */
+#define EMMC_CLOCK_SPEC_20M		20000000UL	 /* normal speed 20MHz */
+#define EMMC_CLOCK_SPEC_26M		26000000UL	 /* high speed 26MHz */
+#define EMMC_CLOCK_SPEC_52M		52000000UL	 /* high speed 52MHz */
+#define EMMC_CLOCK_SPEC_100M		100000000UL	 /* high speed 100MHz */
+
+/* EMMC driver error code. (extended HAL_MEMCARD_RETURN) */
+typedef enum {
+	EMMC_ERR = 0,				/* unknown error */
+	EMMC_SUCCESS,				/* OK */
+	EMMC_ERR_FROM_DMAC,			/* DMAC allocation error */
+	EMMC_ERR_FROM_DMAC_TRANSFER,		/* DMAC transfer error */
+	EMMC_ERR_CARD_STATUS_BIT,		/* card status error */
+	EMMC_ERR_CMD_TIMEOUT,			/* command timeout error */
+	EMMC_ERR_DATA_TIMEOUT,			/* data timeout error */
+	EMMC_ERR_CMD_CRC,			/* command CRC error */
+	EMMC_ERR_DATA_CRC,			/* data CRC error */
+	EMMC_ERR_PARAM,				/* parameter error */
+	EMMC_ERR_RESPONSE,			/* response error */
+	EMMC_ERR_RESPONSE_BUSY,			/* response busy error */
+	EMMC_ERR_TRANSFER,			/* data transfer error */
+	EMMC_ERR_READ_SECTOR,			/* read sector error */
+	EMMC_ERR_WRITE_SECTOR,			/* write sector error */
+	EMMC_ERR_STATE,				/* state error */
+	EMMC_ERR_TIMEOUT,			/* timeout error */
+	EMMC_ERR_ILLEGAL_CARD,			/* illegal card */
+	EMMC_ERR_CARD_BUSY,			/* Busy state */
+	EMMC_ERR_CARD_STATE,			/* card state error */
+	EMMC_ERR_SET_TRACE,			/* trace information error */
+	EMMC_ERR_FROM_TIMER,			/* Timer error */
+	EMMC_ERR_FORCE_TERMINATE,		/* Force terminate */
+	EMMC_ERR_CARD_POWER,			/* card power fail */
+	EMMC_ERR_ERASE_SECTOR,			/* erase sector error */
+	EMMC_ERR_INFO2				/* exec cmd error info2 */
+} EMMC_ERROR_CODE;
+
+/* Function number */
+#define EMMC_FUNCNO_NONE				0U
+#define EMMC_FUNCNO_DRIVER_INIT				1U
+#define EMMC_FUNCNO_CARD_POWER_ON			2U
+#define EMMC_FUNCNO_MOUNT				3U
+#define EMMC_FUNCNO_CARD_INIT				4U
+#define EMMC_FUNCNO_HIGH_SPEED				5U
+#define EMMC_FUNCNO_BUS_WIDTH				6U
+#define EMMC_FUNCNO_MULTI_BOOT_SELECT_PARTITION		7U
+#define EMMC_FUNCNO_MULTI_BOOT_READ_SECTOR		8U
+#define EMMC_FUNCNO_TRANS_DATA_READ_SECTOR		9U
+#define EMMC_FUNCNO_UBOOT_IMAGE_SELECT_PARTITION	10U
+#define EMMC_FUNCNO_UBOOT_IMAGE_READ_SECTOR		11U
+#define EMMC_FUNCNO_SET_CLOCK				12U
+#define EMMC_FUNCNO_EXEC_CMD				13U
+#define EMMC_FUNCNO_READ_SECTOR				14U
+#define EMMC_FUNCNO_WRITE_SECTOR			15U
+#define EMMC_FUNCNO_ERASE_SECTOR			16U
+#define EMMC_FUNCNO_GET_PERTITION_ACCESS		17U
+/*
+ * Response
+ * R1
+ * Type 'E' bit and bit14(must be 0). ignore bit22
+ */
+#define EMMC_R1_ERROR_MASK			0xFDBFE080U
+/* Ignore bit23 (Not check CRC error) */
+#define EMMC_R1_ERROR_MASK_WITHOUT_CRC		(0xFD3FE080U)
+#define EMMC_R1_STATE_MASK			0x00001E00U	/* [12:9] */
+#define EMMC_R1_READY				0x00000100U	/* bit8 */
+#define EMMC_R1_STATE_SHIFT			9
+
+/* R4 */
+#define EMMC_R4_RCA_MASK			0xFFFF0000UL
+#define EMMC_R4_STATUS				0x00008000UL
+
+/* CSD */
+#define EMMC_TRANSPEED_FREQ_UNIT_MASK		0x07	/* bit[2:0] */
+#define EMMC_TRANSPEED_FREQ_UNIT_SHIFT		0
+#define EMMC_TRANSPEED_MULT_MASK		0x78	/* bit[6:3] */
+#define EMMC_TRANSPEED_MULT_SHIFT		3
+
+/* OCR */
+#define EMMC_HOST_OCR_VALUE			0x40FF8080
+#define EMMC_OCR_STATUS_BIT			0x80000000L	/* Card power up status bit */
+#define EMMC_OCR_ACCESS_MODE_MASK		0x60000000L	/* bit[30:29] */
+#define EMMC_OCR_ACCESS_MODE_SECT		0x40000000L
+#define EMMC_OCR_ACCESS_MODE_BYTE		0x00000000L
+
+/* EXT_CSD */
+#define EMMC_EXT_CSD_S_CMD_SET				504
+#define EMMC_EXT_CSD_INI_TIMEOUT_AP			241
+#define EMMC_EXT_CSD_PWR_CL_DDR_52_360			239
+#define EMMC_EXT_CSD_PWR_CL_DDR_52_195			238
+#define EMMC_EXT_CSD_MIN_PERF_DDR_W_8_52		235
+#define EMMC_EXT_CSD_MIN_PERF_DDR_R_8_52		234
+#define EMMC_EXT_CSD_TRIM_MULT				232
+#define EMMC_EXT_CSD_SEC_FEATURE_SUPPORT		231
+#define EMMC_EXT_CSD_SEC_ERASE_MULT			229
+#define EMMC_EXT_CSD_BOOT_INFO				228
+#define EMMC_EXT_CSD_BOOT_SIZE_MULTI			226
+#define EMMC_EXT_CSD_ACC_SIZE				225
+#define EMMC_EXT_CSD_HC_ERASE_GRP_SIZE			224
+#define EMMC_EXT_CSD_ERASE_TIMEOUT_MULT			223
+#define EMMC_EXT_CSD_PEL_WR_SEC_C			222
+#define EMMC_EXT_CSD_HC_WP_GRP_SIZE			221
+#define EMMC_EXT_CSD_S_C_VCC				220
+#define EMMC_EXT_CSD_S_C_VCCQ				219
+#define EMMC_EXT_CSD_S_A_TIMEOUT			217
+#define EMMC_EXT_CSD_SEC_COUNT				215
+#define EMMC_EXT_CSD_MIN_PERF_W_8_52			210
+#define EMMC_EXT_CSD_MIN_PERF_R_8_52			209
+#define EMMC_EXT_CSD_MIN_PERF_W_8_26_4_52		208
+#define EMMC_EXT_CSD_MIN_PERF_R_8_26_4_52		207
+#define EMMC_EXT_CSD_MIN_PERF_W_4_26			206
+#define EMMC_EXT_CSD_MIN_PERF_R_4_26			205
+#define EMMC_EXT_CSD_PWR_CL_26_360			203
+#define EMMC_EXT_CSD_PWR_CL_52_360			202
+#define EMMC_EXT_CSD_PWR_CL_26_195			201
+#define EMMC_EXT_CSD_PWR_CL_52_195			200
+#define EMMC_EXT_CSD_CARD_TYPE				196
+#define EMMC_EXT_CSD_CSD_STRUCTURE			194
+#define EMMC_EXT_CSD_EXT_CSD_REV			192
+#define EMMC_EXT_CSD_CMD_SET				191
+#define EMMC_EXT_CSD_CMD_SET_REV			189
+#define EMMC_EXT_CSD_POWER_CLASS			187
+#define EMMC_EXT_CSD_HS_TIMING				185
+#define EMMC_EXT_CSD_BUS_WIDTH				183
+#define EMMC_EXT_CSD_ERASED_MEM_CONT			181
+#define EMMC_EXT_CSD_PARTITION_CONFIG			179
+#define EMMC_EXT_CSD_BOOT_CONFIG_PROT			178
+#define EMMC_EXT_CSD_BOOT_BUS_WIDTH			177
+#define EMMC_EXT_CSD_ERASE_GROUP_DEF			175
+#define EMMC_EXT_CSD_BOOT_WP				173
+#define EMMC_EXT_CSD_USER_WP				171
+#define EMMC_EXT_CSD_FW_CONFIG				169
+#define EMMC_EXT_CSD_RPMB_SIZE_MULT			168
+#define EMMC_EXT_CSD_RST_n_FUNCTION			162
+#define EMMC_EXT_CSD_PARTITIONING_SUPPORT		160
+#define EMMC_EXT_CSD_MAX_ENH_SIZE_MULT			159
+#define EMMC_EXT_CSD_PARTITIONS_ATTRIBUTE		156
+#define EMMC_EXT_CSD_PARTITION_SETTING_COMPLETED	155
+#define EMMC_EXT_CSD_GP_SIZE_MULT			154
+#define EMMC_EXT_CSD_ENH_SIZE_MULT			142
+#define EMMC_EXT_CSD_ENH_START_ADDR			139
+#define EMMC_EXT_CSD_SEC_BAD_BLK_MGMNT			134
+
+#define EMMC_EXT_CSD_CARD_TYPE_26MHZ			0x01
+#define EMMC_EXT_CSD_CARD_TYPE_52MHZ			0x02
+#define EMMC_EXT_CSD_CARD_TYPE_DDR_52MHZ_12V		0x04
+#define EMMC_EXT_CSD_CARD_TYPE_DDR_52MHZ_18V		0x08
+#define EMMC_EXT_CSD_CARD_TYPE_52MHZ_MASK		0x0e
+
+/* SWITCH (CMD6) argument */
+#define EXTCSD_ACCESS_BYTE	(BIT25 | BIT24)
+#define EXTCSD_SET_BITS		BIT24
+
+#define HS_TIMING_ADD		(185 << 16)	/* H'b9 */
+#define HS_TIMING_1		(1 << 8)
+#define HS_TIMING_HS200		(2 << 8)
+#define HS_TIMING_HS400		(3 << 8)
+
+#define BUS_WIDTH_ADD		(183 << 16)	/* H'b7 */
+#define BUS_WIDTH_1		(0 << 8)
+#define BUS_WIDTH_4		(1 << 8)
+#define BUS_WIDTH_8		(2 << 8)
+#define BUS_WIDTH_4DDR		(5 << 8)
+#define BUS_WIDTH_8DDR		(6 << 8)
+
+#define EMMC_SWITCH_HS_TIMING		(EXTCSD_ACCESS_BYTE | HS_TIMING_ADD |\
+					 HS_TIMING_1)		/* H'03b90100 */
+#define EMMC_SWITCH_HS_TIMING_OFF	(EXTCSD_ACCESS_BYTE |\
+					 HS_TIMING_ADD)		/* H'03b90000 */
+
+#define EMMC_SWITCH_BUS_WIDTH_1		(EXTCSD_ACCESS_BYTE | BUS_WIDTH_ADD |\
+					 BUS_WIDTH_1)		/* H'03b70000 */
+#define EMMC_SWITCH_BUS_WIDTH_4		(EXTCSD_ACCESS_BYTE | BUS_WIDTH_ADD |\
+					 BUS_WIDTH_4)		/* H'03b70100 */
+#define EMMC_SWITCH_BUS_WIDTH_8		(EXTCSD_ACCESS_BYTE | BUS_WIDTH_ADD |\
+					 BUS_WIDTH_8)		/* H'03b70200 */
+#define EMMC_SWITCH_BUS_WIDTH_4DDR	(EXTCSD_ACCESS_BYTE | BUS_WIDTH_ADD |\
+					 BUS_WIDTH_4DDR)	/* H'03b70500 */
+#define EMMC_SWITCH_BUS_WIDTH_8DDR	(EXTCSD_ACCESS_BYTE | BUS_WIDTH_ADD |\
+					 BUS_WIDTH_8DDR)	/* H'03b70600 */
+/* Partition config = 0x00 */
+#define EMMC_SWITCH_PARTITION_CONFIG	0x03B30000UL
+
+#define TIMING_HIGH_SPEED		1UL
+#define EMMC_BOOT_PARTITION_EN_MASK	0x38U
+#define EMMC_BOOT_PARTITION_EN_SHIFT	3U
+
+/* Bus width */
+#define EMMC_BUSWIDTH_1BIT		CE_CMD_SET_DATW_1BIT
+#define EMMC_BUSWIDTH_4BIT		CE_CMD_SET_DATW_4BIT
+#define EMMC_BUSWIDTH_8BIT		CE_CMD_SET_DATW_8BIT
+
+/* for st_mmc_base */
+#define EMMC_MAX_RESPONSE_LENGTH	17
+#define EMMC_MAX_CID_LENGTH		16
+#define EMMC_MAX_CSD_LENGTH		16
+#define EMMC_MAX_EXT_CSD_LENGTH		512U
+#define EMMC_RES_REG_ALIGNED		4U
+#define EMMC_BUF_REG_ALIGNED		8U
+
+/* TAAC mask */
+#define TAAC_TIME_UNIT_MASK		(0x07)
+#define TAAC_MULTIPLIER_FACTOR_MASK	(0x0F)
+
+/* Partition id */
+typedef enum {
+	PARTITION_ID_USER = 0x0,	/* User Area */
+	PARTITION_ID_BOOT_1 = 0x1,	/* boot partition 1 */
+	PARTITION_ID_BOOT_2 = 0x2,	/* boot partition 2 */
+	PARTITION_ID_RPMB = 0x3,	/* Replay Protected Memory Block */
+	PARTITION_ID_GP_1 = 0x4,	/* General Purpose partition 1 */
+	PARTITION_ID_GP_2 = 0x5,	/* General Purpose partition 2 */
+	PARTITION_ID_GP_3 = 0x6,	/* General Purpose partition 3 */
+	PARTITION_ID_GP_4 = 0x7,	/* General Purpose partition 4 */
+	PARTITION_ID_MASK = 0x7		/* [2:0] */
+} EMMC_PARTITION_ID;
+
+/* card state in R1 response [12:9] */
+typedef enum {
+	EMMC_R1_STATE_IDLE = 0,
+	EMMC_R1_STATE_READY,
+	EMMC_R1_STATE_IDENT,
+	EMMC_R1_STATE_STBY,
+	EMMC_R1_STATE_TRAN,
+	EMMC_R1_STATE_DATA,
+	EMMC_R1_STATE_RCV,
+	EMMC_R1_STATE_PRG,
+	EMMC_R1_STATE_DIS,
+	EMMC_R1_STATE_BTST,
+	EMMC_R1_STATE_SLEP
+} EMMC_R1_STATE;
+
+typedef enum {
+	ESTATE_BEGIN = 0,
+	ESTATE_ISSUE_CMD,
+	ESTATE_NON_RESP_CMD,
+	ESTATE_RCV_RESP,
+	ESTATE_RCV_RESPONSE_BUSY,
+	ESTATE_CHECK_RESPONSE_COMPLETE,
+	ESTATE_DATA_TRANSFER,
+	ESTATE_DATA_TRANSFER_COMPLETE,
+	ESTATE_ACCESS_END,
+	ESTATE_TRANSFER_ERROR,
+	ESTATE_ERROR,
+	ESTATE_END
+} EMMC_INT_STATE;
+
+/* eMMC boot driver error information */
+typedef struct {
+	uint16_t num;			/* error no */
+	uint16_t code;			/* error code */
+
+	volatile uint32_t info1;	/* SD_INFO1. (hw dependent) */
+	volatile uint32_t info2;	/* SD_INFO2. (hw dependent) */
+	volatile uint32_t status1;	/* SD_ERR_STS1. (hw dependent) */
+	volatile uint32_t status2;	/* SD_ERR_STS2. (hw dependent) */
+	volatile uint32_t dm_info1;	/* DM_CM_INFO1. (hw dependent) */
+	volatile uint32_t dm_info2;	/* DM_CM_INFO2. (hw dependent) */
+} st_error_info;
+
+/* Command information */
+typedef struct {
+	HAL_MEMCARD_COMMAND cmd;	/* Command information */
+	uint32_t arg;			/* argument */
+	HAL_MEMCARD_OPERATION dir;	/* direction */
+	uint32_t hw;			/* SD_CMD register value. */
+} st_command_info;
+
+/* MMC driver base */
+typedef struct {
+	st_error_info error_info;	/* error information */
+	st_command_info cmd_info;	/* command information */
+
+	/* for data transfer */
+	uint32_t *buff_address_virtual;		/* Dest or Src buff */
+	uint32_t *buff_address_physical;	/* Dest or Src buff */
+	HAL_MEMCARD_DATA_WIDTH bus_width;	/* bus width */
+
+	uint32_t trans_size;		/* transfer size for this command */
+	uint32_t remain_size;		/* remain size for this command */
+	uint32_t response_length;	/* response length for this command */
+	uint32_t sector_size;		/* sector_size */
+
+	/* clock */
+	uint32_t base_clock;		/* MMC host controller clock */
+	/*
+	 * Max freq (Card Spec)[Hz]. It changes dynamically by CSD and
+	 * EXT_CSD.
+	 */
+	uint32_t max_freq;
+	/* request freq [Hz] (400K, 26MHz, 52MHz, etc) */
+	uint32_t request_freq;
+	/* current MMC clock[Hz] (the closest frequency supported by HW) */
+	uint32_t current_freq;
+
+	/* state flag */
+	/* presence status of the memory card */
+	HAL_MEMCARD_PRESENCE_STATUS card_present;
+
+	uint32_t card_power_enable;
+	uint32_t clock_enable;
+	/* True : initialize complete. */
+	uint32_t initialize;
+	/* True : sector access, FALSE : byte access */
+	uint32_t access_mode;
+	/* True : mount complete. */
+	uint32_t mount;
+	/* True : selected card. */
+	uint32_t selected;
+	/* 0: DMA, 1:PIO */
+	HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode;
+
+	/* loaded ISSW image No. ISSW have copy image. */
+	uint32_t image_num;
+	/* card state */
+	EMMC_R1_STATE current_state;
+	/* True : during command processing */
+	volatile uint32_t during_cmd_processing;
+	/* True : during transfer */
+	volatile uint32_t during_transfer;
+	/* True : during transfer (DMA) */
+	volatile uint32_t during_dma_transfer;
+	/* True : occurred DMAC error */
+	volatile uint32_t dma_error_flag;
+	/* force terminate flag */
+	volatile uint32_t force_terminate;
+	/* state machine blocking flag : True or False */
+	volatile uint32_t state_machine_blocking;
+	/* True : get partition access processing */
+	volatile uint32_t get_partition_access_flag;
+
+	EMMC_PARTITION_ID boot_partition_en;	/* Boot partition */
+	EMMC_PARTITION_ID partition_access;	/* Current access partition */
+
+	/* timeout */
+	uint32_t hs_timing;
+
+	/* read and write data timeout */
+	uint32_t data_timeout;
+
+	/* retry */
+	uint32_t retries_after_fail;
+
+	/* interrupt */
+	volatile uint32_t int_event1;	/* interrupt SD_INFO1 Event */
+	volatile uint32_t int_event2;	/* interrupt SD_INFO2 Event */
+	volatile uint32_t dm_event1;	/* interrupt DM_CM_INFO1 Event */
+	volatile uint32_t dm_event2;	/* interrupt DM_CM_INFO2 Event */
+
+	/* response */
+	uint32_t *response;		/* buffer ptr for executing command. */
+	uint32_t r1_card_status;	/* R1 response data */
+	uint32_t r3_ocr;		/* R3 response data */
+	uint32_t r4_resp;		/* R4 response data */
+	uint32_t r5_resp;		/* R5 response data */
+
+	/* True : clock mode is low. (MMC clock = Max26MHz) */
+	uint32_t low_clock_mode_enable;
+
+	uint32_t reserved2;
+	uint32_t reserved3;
+	uint32_t reserved4;
+
+	/* CSD registers (4byte align) */
+	uint8_t csd_data[EMMC_MAX_CSD_LENGTH]			/* CSD */
+	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
+	/* CID registers (4byte align) */
+	uint8_t cid_data[EMMC_MAX_CID_LENGTH]			/* CID */
+	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
+	/* EXT CSD registers (8byte align) */
+	uint8_t ext_csd_data[EMMC_MAX_EXT_CSD_LENGTH]		/* EXT_CSD */
+	    __attribute__ ((aligned(EMMC_BUF_REG_ALIGNED)));
+	/* Response registers (4byte align) */
+	uint8_t response_data[EMMC_MAX_RESPONSE_LENGTH]		/* other response */
+	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
+} st_mmc_base;
+
+typedef int (*func) (void);
+
+uint32_t emmc_get_csd_time(void);
+
+#define MMC_DEBUG
+#endif /* EMMC_STD_H */
diff --git a/drivers/renesas/common/emmc/emmc_utility.c b/drivers/renesas/common/emmc/emmc_utility.c
new file mode 100644
index 0000000..2e88abc
--- /dev/null
+++ b/drivers/renesas/common/emmc/emmc_utility.c
@@ -0,0 +1,226 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_registers.h"
+#include "emmc_std.h"
+
+static const uint32_t cmd_reg_hw[EMMC_CMD_MAX + 1] = {
+	0x00000000,		/* CMD0 */
+	0x00000701,		/* CMD1 */
+	0x00000002,		/* CMD2 */
+	0x00000003,		/* CMD3 */
+	0x00000004,		/* CMD4 */
+	0x00000505,		/* CMD5 */
+	0x00000406,		/* CMD6 */
+	0x00000007,		/* CMD7 */
+	0x00001C08,		/* CMD8 */
+	0x00000009,		/* CMD9 */
+	0x0000000A,		/* CMD10 */
+	0x00000000,		/* reserved */
+	0x0000000C,		/* CMD12 */
+	0x0000000D,		/* CMD13 */
+	0x00001C0E,		/* CMD14 */
+	0x0000000F,		/* CMD15 */
+	0x00000010,		/* CMD16 */
+	0x00000011,		/* CMD17 */
+	0x00007C12,		/* CMD18 */
+	0x00000C13,		/* CMD19 */
+	0x00000000,
+	0x00001C15,		/* CMD21 */
+	0x00000000,
+	0x00000017,		/* CMD23 */
+	0x00000018,		/* CMD24 */
+	0x00006C19,		/* CMD25 */
+	0x00000C1A,		/* CMD26 */
+	0x0000001B,		/* CMD27 */
+	0x0000001C,		/* CMD28 */
+	0x0000001D,		/* CMD29 */
+	0x0000001E,		/* CMD30 */
+	0x00001C1F,		/* CMD31 */
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000423,		/* CMD35 */
+	0x00000424,		/* CMD36 */
+	0x00000000,
+	0x00000026,		/* CMD38 */
+	0x00000427,		/* CMD39 */
+	0x00000428,		/* CMD40(send cmd) */
+	0x00000000,
+	0x0000002A,		/* CMD42 */
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000C31,
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00007C35,
+	0x00006C36,
+	0x00000037,		/* CMD55 */
+	0x00000038,		/* CMD56(Read) */
+	0x00000000,
+	0x00000000,
+	0x00000000,
+	0x00000000
+};
+
+uint32_t emmc_bit_field(uint8_t *data, uint32_t top, uint32_t bottom)
+{
+	uint32_t value;
+
+	uint32_t index_top = (uint32_t) (15 - (top >> 3));
+	uint32_t index_bottom = (uint32_t) (15 - (bottom >> 3));
+
+	if (index_top == index_bottom) {
+		value = data[index_top];
+	} else if ((index_top + 1) == index_bottom) {
+		value =
+		    (uint32_t) ((data[index_top] << 8) | data[index_bottom]);
+	} else if ((index_top + 2) == index_bottom) {
+		value =
+		    (uint32_t) ((data[index_top] << 16) |
+				(data[index_top + 1] << 8) | data[index_top +
+								  2]);
+	} else {
+		value =
+		    (uint32_t) ((data[index_top] << 24) |
+				(data[index_top + 1] << 16) |
+				(data[index_top + 2] << 8) |
+				data[index_top + 3]);
+	}
+
+	value = ((value >> (bottom & 0x07)) & ((1 << (top - bottom + 1)) - 1));
+
+	return value;
+}
+
+void emmc_write_error_info(uint16_t func_no, EMMC_ERROR_CODE error_code)
+{
+
+	mmc_drv_obj.error_info.num = func_no;
+	mmc_drv_obj.error_info.code = (uint16_t) error_code;
+
+	ERROR("BL2: emmc err:func_no=0x%x code=0x%x\n", func_no, error_code);
+}
+
+void emmc_write_error_info_func_no(uint16_t func_no)
+{
+
+	mmc_drv_obj.error_info.num = func_no;
+
+	ERROR("BL2: emmc err:func_no=0x%x\n", func_no);
+}
+
+void emmc_make_nontrans_cmd(HAL_MEMCARD_COMMAND cmd, uint32_t arg)
+{
+	/* command information */
+	mmc_drv_obj.cmd_info.cmd = cmd;
+	mmc_drv_obj.cmd_info.arg = arg;
+	mmc_drv_obj.cmd_info.dir = HAL_MEMCARD_READ;
+	mmc_drv_obj.cmd_info.hw =
+	    cmd_reg_hw[cmd & HAL_MEMCARD_COMMAND_INDEX_MASK];
+
+	/* clear data transfer information */
+	mmc_drv_obj.trans_size = 0;
+	mmc_drv_obj.remain_size = 0;
+	mmc_drv_obj.buff_address_virtual = NULL;
+	mmc_drv_obj.buff_address_physical = NULL;
+
+	/* response information */
+	mmc_drv_obj.response_length = 6;
+
+	switch (mmc_drv_obj.cmd_info.cmd & HAL_MEMCARD_RESPONSE_TYPE_MASK) {
+	case HAL_MEMCARD_RESPONSE_NONE:
+		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
+		mmc_drv_obj.response_length = 0;
+		break;
+	case HAL_MEMCARD_RESPONSE_R1:
+		mmc_drv_obj.response = &mmc_drv_obj.r1_card_status;
+		break;
+	case HAL_MEMCARD_RESPONSE_R1b:
+		mmc_drv_obj.cmd_info.hw |= BIT10; /* bit10 = R1 busy bit */
+		mmc_drv_obj.response = &mmc_drv_obj.r1_card_status;
+		break;
+	case HAL_MEMCARD_RESPONSE_R2:
+		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
+		mmc_drv_obj.response_length = 17;
+		break;
+	case HAL_MEMCARD_RESPONSE_R3:
+		mmc_drv_obj.response = &mmc_drv_obj.r3_ocr;
+		break;
+	case HAL_MEMCARD_RESPONSE_R4:
+		mmc_drv_obj.response = &mmc_drv_obj.r4_resp;
+		break;
+	case HAL_MEMCARD_RESPONSE_R5:
+		mmc_drv_obj.response = &mmc_drv_obj.r5_resp;
+		break;
+	default:
+		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
+		break;
+	}
+}
+
+void emmc_make_trans_cmd(HAL_MEMCARD_COMMAND cmd, uint32_t arg,
+			 uint32_t *buff_address_virtual,
+			 uint32_t len,
+			 HAL_MEMCARD_OPERATION dir,
+			 HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode)
+{
+	emmc_make_nontrans_cmd(cmd, arg);	/* update common information */
+
+	/* for data transfer command */
+	mmc_drv_obj.cmd_info.dir = dir;
+	mmc_drv_obj.buff_address_virtual = buff_address_virtual;
+	mmc_drv_obj.buff_address_physical = buff_address_virtual;
+	mmc_drv_obj.trans_size = len;
+	mmc_drv_obj.remain_size = len;
+	mmc_drv_obj.transfer_mode = transfer_mode;
+}
+
+EMMC_ERROR_CODE emmc_send_idle_cmd(uint32_t arg)
+{
+	EMMC_ERROR_CODE result;
+	uint32_t freq;
+
+	/* initialize state */
+	mmc_drv_obj.mount = FALSE;
+	mmc_drv_obj.selected = FALSE;
+	mmc_drv_obj.during_transfer = FALSE;
+	mmc_drv_obj.during_cmd_processing = FALSE;
+	mmc_drv_obj.during_dma_transfer = FALSE;
+	mmc_drv_obj.dma_error_flag = FALSE;
+	mmc_drv_obj.force_terminate = FALSE;
+	mmc_drv_obj.state_machine_blocking = FALSE;
+
+	mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
+	mmc_drv_obj.max_freq = MMC_20MHZ;	/* 20MHz */
+	mmc_drv_obj.current_state = EMMC_R1_STATE_IDLE;
+
+	/* CMD0 (MMC clock is current frequency. if Data transfer mode, 20MHz or higher.) */
+	emmc_make_nontrans_cmd(CMD0_GO_IDLE_STATE, arg);	/* CMD0 */
+	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+
+	/* change MMC clock(400KHz) */
+	freq = MMC_400KHZ;
+	result = emmc_set_request_mmc_clock(&freq);
+	if (result != EMMC_SUCCESS) {
+		return result;
+	}
+
+	return EMMC_SUCCESS;
+}
diff --git a/drivers/renesas/common/iic_dvfs/iic_dvfs.c b/drivers/renesas/common/iic_dvfs/iic_dvfs.c
new file mode 100644
index 0000000..bf80697
--- /dev/null
+++ b/drivers/renesas/common/iic_dvfs/iic_dvfs.c
@@ -0,0 +1,600 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "cpg_registers.h"
+#include "iic_dvfs.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+
+#define DVFS_RETRY_MAX				(2U)
+
+#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_0		(0x07U)
+#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_1		(0x09U)
+#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_2		(0x0BU)
+#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_3		(0x0EU)
+#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_E		(0x15U)
+
+#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_0		(0x01U)
+#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_1		(0x02U)
+#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_2		(0x03U)
+#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_3		(0x05U)
+#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_E		(0x07U)
+
+#define CPG_BIT_SMSTPCR9_DVFS			(0x04000000U)
+
+#define IIC_DVFS_REG_BASE			(0xE60B0000U)
+#define IIC_DVFS_REG_ICDR			(IIC_DVFS_REG_BASE + 0x0000U)
+#define IIC_DVFS_REG_ICCR			(IIC_DVFS_REG_BASE + 0x0004U)
+#define IIC_DVFS_REG_ICSR			(IIC_DVFS_REG_BASE + 0x0008U)
+#define IIC_DVFS_REG_ICIC			(IIC_DVFS_REG_BASE + 0x000CU)
+#define IIC_DVFS_REG_ICCL			(IIC_DVFS_REG_BASE + 0x0010U)
+#define IIC_DVFS_REG_ICCH			(IIC_DVFS_REG_BASE + 0x0014U)
+
+#define IIC_DVFS_BIT_ICSR_BUSY			(0x10U)
+#define IIC_DVFS_BIT_ICSR_AL			(0x08U)
+#define IIC_DVFS_BIT_ICSR_TACK			(0x04U)
+#define IIC_DVFS_BIT_ICSR_WAIT			(0x02U)
+#define IIC_DVFS_BIT_ICSR_DTE			(0x01U)
+
+#define IIC_DVFS_BIT_ICCR_ENABLE		(0x80U)
+#define IIC_DVFS_SET_ICCR_START			(0x94U)
+#define IIC_DVFS_SET_ICCR_STOP			(0x90U)
+#define IIC_DVFS_SET_ICCR_RETRANSMISSION	(0x94U)
+#define IIC_DVFS_SET_ICCR_CHANGE		(0x81U)
+#define IIC_DVFS_SET_ICCR_STOP_READ		(0xC0U)
+
+#define IIC_DVFS_BIT_ICIC_TACKE			(0x04U)
+#define IIC_DVFS_BIT_ICIC_WAITE			(0x02U)
+#define IIC_DVFS_BIT_ICIC_DTEE			(0x01U)
+
+#define DVFS_READ_MODE				(0x01U)
+#define DVFS_WRITE_MODE				(0x00U)
+
+#define IIC_DVFS_SET_DUMMY			(0x52U)
+#define IIC_DVFS_SET_BUSY_LOOP			(500000000U)
+
+enum dvfs_state_t {
+	DVFS_START = 0,
+	DVFS_STOP,
+	DVFS_RETRANSMIT,
+	DVFS_READ,
+	DVFS_STOP_READ,
+	DVFS_SET_SLAVE_READ,
+	DVFS_SET_SLAVE,
+	DVFS_WRITE_ADDR,
+	DVFS_WRITE_DATA,
+	DVFS_CHANGE_SEND_TO_RECEIVE,
+	DVFS_DONE,
+};
+
+#define DVFS_PROCESS			(1)
+#define DVFS_COMPLETE			(0)
+#define DVFS_ERROR			(-1)
+
+#if IMAGE_BL31
+#define IIC_DVFS_FUNC(__name, ...)					\
+static int32_t	__attribute__ ((section(".system_ram")))		\
+dvfs_ ##__name(__VA_ARGS__)
+
+#define RCAR_DVFS_API(__name, ...)					\
+int32_t __attribute__ ((section(".system_ram")))			\
+rcar_iic_dvfs_ ##__name(__VA_ARGS__)
+
+#else
+#define IIC_DVFS_FUNC(__name, ...)					\
+static int32_t dvfs_ ##__name(__VA_ARGS__)
+
+#define RCAR_DVFS_API(__name, ...)					\
+int32_t rcar_iic_dvfs_ ##__name(__VA_ARGS__)
+#endif
+
+IIC_DVFS_FUNC(check_error, enum dvfs_state_t *state, uint32_t *err, uint8_t mode)
+{
+	uint8_t icsr_al = 0U, icsr_tack = 0U;
+	uint8_t reg, stop;
+	uint32_t i = 0U;
+
+	stop = mode == DVFS_READ_MODE ? IIC_DVFS_SET_ICCR_STOP_READ :
+	    IIC_DVFS_SET_ICCR_STOP;
+
+	reg = mmio_read_8(IIC_DVFS_REG_ICSR);
+	icsr_al = (reg & IIC_DVFS_BIT_ICSR_AL) == IIC_DVFS_BIT_ICSR_AL;
+	icsr_tack = (reg & IIC_DVFS_BIT_ICSR_TACK) == IIC_DVFS_BIT_ICSR_TACK;
+
+	if (icsr_al == 0U && icsr_tack == 0U) {
+		return DVFS_PROCESS;
+	}
+
+	if (icsr_al) {
+		reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_AL;
+		mmio_write_8(IIC_DVFS_REG_ICSR, reg);
+
+		if (*state == DVFS_SET_SLAVE) {
+			mmio_write_8(IIC_DVFS_REG_ICDR, IIC_DVFS_SET_DUMMY);
+		}
+
+		do {
+			reg = mmio_read_8(IIC_DVFS_REG_ICSR) &
+			    IIC_DVFS_BIT_ICSR_WAIT;
+		} while (reg == 0U);
+
+		mmio_write_8(IIC_DVFS_REG_ICCR, stop);
+
+		reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+		mmio_write_8(IIC_DVFS_REG_ICSR, reg);
+
+		i = 0U;
+		do {
+			reg = mmio_read_8(IIC_DVFS_REG_ICSR) &
+			    IIC_DVFS_BIT_ICSR_BUSY;
+			if (reg == 0U) {
+				break;
+			}
+
+			if (i++ > IIC_DVFS_SET_BUSY_LOOP) {
+				panic();
+			}
+
+		} while (true);
+
+		mmio_write_8(IIC_DVFS_REG_ICCR, 0x00U);
+
+		(*err)++;
+		if (*err > DVFS_RETRY_MAX) {
+			return DVFS_ERROR;
+		}
+
+		*state = DVFS_START;
+
+		return DVFS_PROCESS;
+
+	}
+
+	/* icsr_tack */
+	mmio_write_8(IIC_DVFS_REG_ICCR, stop);
+
+	reg = mmio_read_8(IIC_DVFS_REG_ICIC);
+	reg &= ~(IIC_DVFS_BIT_ICIC_WAITE | IIC_DVFS_BIT_ICIC_DTEE);
+	mmio_write_8(IIC_DVFS_REG_ICIC, reg);
+
+	reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_TACK;
+	mmio_write_8(IIC_DVFS_REG_ICSR, reg);
+
+	i = 0U;
+	while ((mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_BUSY) != 0U) {
+		if (i++ > IIC_DVFS_SET_BUSY_LOOP) {
+			panic();
+		}
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICCR, 0U);
+	(*err)++;
+
+	if (*err > DVFS_RETRY_MAX) {
+		return DVFS_ERROR;
+	}
+
+	*state = DVFS_START;
+
+	return DVFS_PROCESS;
+}
+
+IIC_DVFS_FUNC(start, enum dvfs_state_t *state)
+{
+	uint8_t iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_E;
+	uint8_t icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_E;
+	int32_t result = DVFS_PROCESS;
+	uint32_t reg, lsi_product;
+	uint8_t mode;
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICCR) | IIC_DVFS_BIT_ICCR_ENABLE;
+	mmio_write_8(IIC_DVFS_REG_ICCR, mode);
+
+	lsi_product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
+	if (lsi_product == PRR_PRODUCT_E3) {
+		goto start;
+	}
+
+	reg = mmio_read_32(RCAR_MODEMR) & CHECK_MD13_MD14;
+	switch (reg) {
+	case MD14_MD13_TYPE_0:
+		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_0;
+		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_0;
+		break;
+	case MD14_MD13_TYPE_1:
+		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_1;
+		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_1;
+		break;
+	case MD14_MD13_TYPE_2:
+		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_2;
+		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_2;
+		break;
+	default:
+		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_3;
+		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_3;
+		break;
+	}
+start:
+	mmio_write_8(IIC_DVFS_REG_ICCL, iccl);
+	mmio_write_8(IIC_DVFS_REG_ICCH, icch);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC)
+	    | IIC_DVFS_BIT_ICIC_TACKE
+	    | IIC_DVFS_BIT_ICIC_WAITE | IIC_DVFS_BIT_ICIC_DTEE;
+
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_START);
+
+	*state = DVFS_SET_SLAVE;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(set_slave, enum dvfs_state_t *state, uint32_t *err, uint8_t slave)
+{
+	uint8_t mode;
+	int32_t result;
+	uint8_t address;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
+	if (mode != IIC_DVFS_BIT_ICSR_DTE) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+
+	address = slave << 1;
+	mmio_write_8(IIC_DVFS_REG_ICDR, address);
+
+	*state = DVFS_WRITE_ADDR;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(write_addr, enum dvfs_state_t *state, uint32_t *err, uint8_t reg_addr)
+{
+	uint8_t mode;
+	int32_t result;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICDR, reg_addr);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	*state = DVFS_WRITE_DATA;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(write_data, enum dvfs_state_t *state, uint32_t *err,
+	      uint8_t reg_data)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICDR, reg_data);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	*state = DVFS_STOP;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(stop, enum dvfs_state_t *state, uint32_t *err)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_STOP);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	*state = DVFS_DONE;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(done, void)
+{
+	uint32_t i;
+
+	for (i = 0U; i < IIC_DVFS_SET_BUSY_LOOP; i++) {
+		if ((mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_BUSY) != 0U) {
+			continue;
+		}
+		goto done;
+	}
+
+	panic();
+done:
+	mmio_write_8(IIC_DVFS_REG_ICCR, 0U);
+
+	return DVFS_COMPLETE;
+}
+
+IIC_DVFS_FUNC(write_reg_addr_read, enum dvfs_state_t *state, uint32_t *err,
+	      uint8_t reg_addr)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICDR, reg_addr);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	*state = DVFS_RETRANSMIT;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(retransmit, enum dvfs_state_t *state, uint32_t *err)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_RETRANSMISSION);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC) | IIC_DVFS_BIT_ICIC_DTEE;
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+
+	*state = DVFS_SET_SLAVE_READ;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(set_slave_read, enum dvfs_state_t *state, uint32_t *err,
+	      uint8_t slave)
+{
+	uint8_t address;
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
+	if (mode != IIC_DVFS_BIT_ICSR_DTE) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+
+	address = ((uint8_t) (slave << 1) + DVFS_READ_MODE);
+	mmio_write_8(IIC_DVFS_REG_ICDR, address);
+
+	*state = DVFS_CHANGE_SEND_TO_RECEIVE;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(change_send_to_receive, enum dvfs_state_t *state, uint32_t *err)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_CHANGE);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	*state = DVFS_STOP_READ;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(stop_read, enum dvfs_state_t *state, uint32_t *err)
+{
+	int32_t result;
+	uint8_t mode;
+
+	result = dvfs_check_error(state, err, DVFS_READ_MODE);
+	if (result == DVFS_ERROR) {
+		return result;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
+	if (mode != IIC_DVFS_BIT_ICSR_WAIT) {
+		return result;
+	}
+
+	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_STOP_READ);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
+	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC) | IIC_DVFS_BIT_ICIC_DTEE;
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+
+	*state = DVFS_READ;
+
+	return result;
+}
+
+IIC_DVFS_FUNC(read, enum dvfs_state_t *state, uint8_t *reg_data)
+{
+	uint8_t mode;
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
+	if (mode != IIC_DVFS_BIT_ICSR_DTE) {
+		return DVFS_PROCESS;
+	}
+
+	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
+	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
+
+	*reg_data = mmio_read_8(IIC_DVFS_REG_ICDR);
+	*state = DVFS_DONE;
+
+	return DVFS_PROCESS;
+}
+
+RCAR_DVFS_API(send, uint8_t slave, uint8_t reg_addr, uint8_t reg_data)
+{
+	enum dvfs_state_t state = DVFS_START;
+	int32_t result = DVFS_PROCESS;
+	uint32_t err = 0U;
+
+	mstpcr_write(SCMSTPCR9, CPG_MSTPSR9, CPG_BIT_SMSTPCR9_DVFS);
+	mmio_write_8(IIC_DVFS_REG_ICCR, 1U);
+again:
+	switch (state) {
+	case DVFS_START:
+		result = dvfs_start(&state);
+		break;
+	case DVFS_SET_SLAVE:
+		result = dvfs_set_slave(&state, &err, slave);
+		break;
+	case DVFS_WRITE_ADDR:
+		result = dvfs_write_addr(&state, &err, reg_addr);
+		break;
+	case DVFS_WRITE_DATA:
+		result = dvfs_write_data(&state, &err, reg_data);
+		break;
+	case DVFS_STOP:
+		result = dvfs_stop(&state, &err);
+		break;
+	case DVFS_DONE:
+		result = dvfs_done();
+		break;
+	default:
+		panic();
+		break;
+	}
+
+	if (result == DVFS_PROCESS) {
+		goto again;
+	}
+
+	return result;
+}
+
+RCAR_DVFS_API(receive, uint8_t slave, uint8_t reg, uint8_t *data)
+{
+	enum dvfs_state_t state = DVFS_START;
+	int32_t result = DVFS_PROCESS;
+	uint32_t err = 0U;
+
+	mstpcr_write(SCMSTPCR9, CPG_MSTPSR9, CPG_BIT_SMSTPCR9_DVFS);
+	mmio_write_8(IIC_DVFS_REG_ICCR, 1U);
+again:
+	switch (state) {
+	case DVFS_START:
+		result = dvfs_start(&state);
+		break;
+	case DVFS_SET_SLAVE:
+		result = dvfs_set_slave(&state, &err, slave);
+		break;
+	case DVFS_WRITE_ADDR:
+		result = dvfs_write_reg_addr_read(&state, &err, reg);
+		break;
+	case DVFS_RETRANSMIT:
+		result = dvfs_retransmit(&state, &err);
+		break;
+	case DVFS_SET_SLAVE_READ:
+		result = dvfs_set_slave_read(&state, &err, slave);
+		break;
+	case DVFS_CHANGE_SEND_TO_RECEIVE:
+		result = dvfs_change_send_to_receive(&state, &err);
+		break;
+	case DVFS_STOP_READ:
+		result = dvfs_stop_read(&state, &err);
+		break;
+	case DVFS_READ:
+		result = dvfs_read(&state, data);
+		break;
+	case DVFS_DONE:
+		result = dvfs_done();
+		break;
+	default:
+		panic();
+		break;
+	}
+
+	if (result == DVFS_PROCESS) {
+		goto again;
+	}
+
+	return result;
+}
diff --git a/drivers/renesas/common/iic_dvfs/iic_dvfs.h b/drivers/renesas/common/iic_dvfs/iic_dvfs.h
new file mode 100644
index 0000000..244c06c
--- /dev/null
+++ b/drivers/renesas/common/iic_dvfs/iic_dvfs.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef IIC_DVFS_H
+#define IIC_DVFS_H
+
+/* PMIC slave */
+#define PMIC			(0x30U)
+#define BKUP_MODE_CNT		(0x20U)
+#define DVFS_SET_VID		(0x54U)
+#define REG_KEEP10		(0x79U)
+
+/* EEPROM slave */
+#define EEPROM			(0x50U)
+#define BOARD_ID		(0x70U)
+
+int32_t rcar_iic_dvfs_receive(uint8_t slave, uint8_t reg, uint8_t *data);
+int32_t rcar_iic_dvfs_send(uint8_t slave, uint8_t regr, uint8_t data);
+
+#endif /* IIC_DVFS_H */
diff --git a/drivers/renesas/rcar/io/io_common.h b/drivers/renesas/common/io/io_common.h
similarity index 100%
rename from drivers/renesas/rcar/io/io_common.h
rename to drivers/renesas/common/io/io_common.h
diff --git a/drivers/renesas/common/io/io_emmcdrv.c b/drivers/renesas/common/io/io_emmcdrv.c
new file mode 100644
index 0000000..c2b5f7c
--- /dev/null
+++ b/drivers/renesas/common/io/io_emmcdrv.c
@@ -0,0 +1,179 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_storage.h>
+
+#include "emmc_config.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_std.h"
+#include "io_common.h"
+#include "io_emmcdrv.h"
+#include "io_private.h"
+
+static int32_t emmcdrv_dev_open(const uintptr_t spec __attribute__ ((unused)),
+				io_dev_info_t **dev_info);
+static int32_t emmcdrv_dev_close(io_dev_info_t *dev_info);
+
+typedef struct {
+	uint32_t in_use;
+	uintptr_t base;
+	signed long long file_pos;
+	EMMC_PARTITION_ID partition;
+} file_state_t;
+
+static file_state_t current_file = { 0 };
+
+static EMMC_PARTITION_ID emmcdrv_bootpartition = PARTITION_ID_USER;
+
+static io_type_t device_type_emmcdrv(void)
+{
+	return IO_TYPE_MEMMAP;
+}
+
+static int32_t emmcdrv_block_seek(io_entity_t *entity, int32_t mode,
+				  signed long long offset)
+{
+	if (mode != IO_SEEK_SET) {
+		return IO_FAIL;
+	}
+
+	((file_state_t *) entity->info)->file_pos = offset;
+
+	return IO_SUCCESS;
+}
+
+static int32_t emmcdrv_block_read(io_entity_t *entity, uintptr_t buffer,
+				  size_t length, size_t *length_read)
+{
+	file_state_t *fp = (file_state_t *) entity->info;
+	uint32_t sector_add, sector_num, emmc_dma = 0;
+	int32_t result = IO_SUCCESS;
+
+	sector_add = current_file.file_pos >> EMMC_SECTOR_SIZE_SHIFT;
+	sector_num = (length + EMMC_SECTOR_SIZE - 1U) >> EMMC_SECTOR_SIZE_SHIFT;
+
+	NOTICE("BL2: Load dst=0x%lx src=(p:%d)0x%llx(%d) len=0x%lx(%d)\n",
+	       buffer,
+	       current_file.partition, current_file.file_pos,
+	       sector_add, length, sector_num);
+
+	if ((buffer + length - 1U) <= (uintptr_t)UINT32_MAX) {
+		emmc_dma = LOADIMAGE_FLAGS_DMA_ENABLE;
+	}
+
+	if (emmc_read_sector((uint32_t *) buffer, sector_add, sector_num,
+			     emmc_dma) != EMMC_SUCCESS) {
+		result = IO_FAIL;
+	}
+
+	*length_read = length;
+	fp->file_pos += (signed long long)length;
+
+	return result;
+}
+
+static int32_t emmcdrv_block_open(io_dev_info_t *dev_info,
+				  const uintptr_t spec, io_entity_t *entity)
+{
+	const io_drv_spec_t *block_spec = (io_drv_spec_t *) spec;
+
+	if (current_file.in_use != 0U) {
+		WARN("mmc_block: Only one open spec at a time\n");
+		return IO_RESOURCES_EXHAUSTED;
+	}
+
+	current_file.file_pos = 0;
+	current_file.in_use = 1;
+
+	if (emmcdrv_bootpartition == PARTITION_ID_USER) {
+		emmcdrv_bootpartition = mmc_drv_obj.boot_partition_en;
+		if ((emmcdrv_bootpartition == PARTITION_ID_BOOT_1) ||
+		    (emmcdrv_bootpartition == PARTITION_ID_BOOT_2)) {
+			current_file.partition = emmcdrv_bootpartition;
+
+			NOTICE("BL2: eMMC boot from partition %d\n",
+			       emmcdrv_bootpartition);
+			goto done;
+		}
+		return IO_FAIL;
+	}
+
+	if ((block_spec->partition == PARTITION_ID_USER) ||
+	    (block_spec->partition == PARTITION_ID_BOOT_1) ||
+	    (block_spec->partition == PARTITION_ID_BOOT_2)) {
+		current_file.partition = block_spec->partition;
+	} else {
+		current_file.partition = emmcdrv_bootpartition;
+	}
+
+done:
+	if (emmc_select_partition(current_file.partition) != EMMC_SUCCESS) {
+		return IO_FAIL;
+	}
+
+	entity->info = (uintptr_t) &current_file;
+
+	return IO_SUCCESS;
+}
+
+static int32_t emmcdrv_block_close(io_entity_t *entity)
+{
+	memset((void *)&current_file, 0, sizeof(current_file));
+	entity->info = 0U;
+
+	return IO_SUCCESS;
+}
+
+static const io_dev_funcs_t emmcdrv_dev_funcs = {
+	.type = &device_type_emmcdrv,
+	.open = &emmcdrv_block_open,
+	.seek = &emmcdrv_block_seek,
+	.size = NULL,
+	.read = &emmcdrv_block_read,
+	.write = NULL,
+	.close = &emmcdrv_block_close,
+	.dev_init = NULL,
+	.dev_close = &emmcdrv_dev_close
+};
+
+static const io_dev_info_t emmcdrv_dev_info = {
+	.funcs = &emmcdrv_dev_funcs,
+	.info = (uintptr_t) 0
+};
+
+static const io_dev_connector_t emmcdrv_dev_connector = {
+	&emmcdrv_dev_open,
+};
+
+static int32_t emmcdrv_dev_open(const uintptr_t spec __attribute__ ((unused)),
+				io_dev_info_t **dev_info)
+{
+	*dev_info = (io_dev_info_t *) &emmcdrv_dev_info;
+
+	return IO_SUCCESS;
+}
+
+static int32_t emmcdrv_dev_close(io_dev_info_t *dev_info)
+{
+	return IO_SUCCESS;
+}
+
+int32_t rcar_register_io_dev_emmcdrv(const io_dev_connector_t **dev_con)
+{
+	int32_t rc;
+
+	rc = io_register_device(&emmcdrv_dev_info);
+	if (rc == IO_SUCCESS) {
+		*dev_con = &emmcdrv_dev_connector;
+	}
+
+	return rc;
+}
diff --git a/drivers/renesas/rcar/io/io_emmcdrv.h b/drivers/renesas/common/io/io_emmcdrv.h
similarity index 100%
rename from drivers/renesas/rcar/io/io_emmcdrv.h
rename to drivers/renesas/common/io/io_emmcdrv.h
diff --git a/drivers/renesas/common/io/io_memdrv.c b/drivers/renesas/common/io/io_memdrv.c
new file mode 100644
index 0000000..1f31c0f
--- /dev/null
+++ b/drivers/renesas/common/io/io_memdrv.c
@@ -0,0 +1,154 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_storage.h>
+
+#include "io_common.h"
+#include "io_memdrv.h"
+#include "io_private.h"
+#include "rcar_def.h"
+
+extern void rcar_dma_exec(uintptr_t dst, uint32_t src, uint32_t len);
+
+static int32_t memdrv_dev_open(const uintptr_t dev __attribute__ ((unused)),
+			       io_dev_info_t **dev_info);
+static int32_t memdrv_dev_close(io_dev_info_t *dev_info);
+
+/*
+ * As we need to be able to keep state for seek, only one file can be open
+ * at a time. Make this a structure and point to the entity->info. When we
+ * can malloc memory we can change this to support more open files.
+ */
+typedef struct {
+	uint32_t in_use;
+	uintptr_t base;
+	signed long long file_pos;
+} file_state_t;
+
+static file_state_t current_file = { 0 };
+
+static io_type_t device_type_memdrv(void)
+{
+	return IO_TYPE_MEMMAP;
+}
+
+static int32_t memdrv_block_open(io_dev_info_t *dev_info, const uintptr_t spec,
+				 io_entity_t *entity)
+{
+	const io_drv_spec_t *block_spec = (io_drv_spec_t *) spec;
+
+	/*
+	 * Since we need to track open state for seek() we only allow one open
+	 * spec at a time. When we have dynamic memory we can malloc and set
+	 * entity->info.
+	 */
+	if (current_file.in_use != 0U) {
+		return IO_RESOURCES_EXHAUSTED;
+	}
+
+	/* File cursor offset for seek and incremental reads etc. */
+	current_file.base = block_spec->offset;
+	current_file.file_pos = 0;
+	current_file.in_use = 1;
+
+	entity->info = (uintptr_t) &current_file;
+
+	return IO_SUCCESS;
+}
+
+static int32_t memdrv_block_seek(io_entity_t *entity, int32_t mode,
+				 signed long long offset)
+{
+	if (mode != IO_SEEK_SET) {
+		return IO_FAIL;
+	}
+
+	((file_state_t *) entity->info)->file_pos = offset;
+
+	return IO_SUCCESS;
+}
+
+static int32_t memdrv_block_read(io_entity_t *entity, uintptr_t buffer,
+				 size_t length, size_t *cnt)
+{
+	file_state_t *fp;
+
+	fp = (file_state_t *) entity->info;
+
+	NOTICE("BL2: dst=0x%lx src=0x%llx len=%ld(0x%lx)\n",
+	       buffer, (unsigned long long)fp->base +
+	       (unsigned long long)fp->file_pos, length, length);
+
+	if (FLASH_MEMORY_SIZE < (fp->file_pos + (signed long long)length)) {
+		ERROR("BL2: check load image (source address)\n");
+		return IO_FAIL;
+	}
+
+	rcar_dma_exec(buffer, fp->base + (uintptr_t)fp->file_pos, length);
+	fp->file_pos += (signed long long)length;
+	*cnt = length;
+
+	return IO_SUCCESS;
+}
+
+static int32_t memdrv_block_close(io_entity_t *entity)
+{
+	entity->info = 0U;
+
+	memset((void *)&current_file, 0, sizeof(current_file));
+
+	return IO_SUCCESS;
+}
+
+static const io_dev_funcs_t memdrv_dev_funcs = {
+	.type = &device_type_memdrv,
+	.open = &memdrv_block_open,
+	.seek = &memdrv_block_seek,
+	.size = NULL,
+	.read = &memdrv_block_read,
+	.write = NULL,
+	.close = &memdrv_block_close,
+	.dev_init = NULL,
+	.dev_close = &memdrv_dev_close,
+};
+
+static const io_dev_info_t memdrv_dev_info = {
+	.funcs = &memdrv_dev_funcs,
+	.info = 0,
+};
+
+static const io_dev_connector_t memdrv_dev_connector = {
+	.dev_open = &memdrv_dev_open
+};
+
+static int32_t memdrv_dev_open(const uintptr_t dev __attribute__ ((unused)),
+			       io_dev_info_t **dev_info)
+{
+	*dev_info = (io_dev_info_t *) &memdrv_dev_info;
+
+	return IO_SUCCESS;
+}
+
+static int32_t memdrv_dev_close(io_dev_info_t *dev_info)
+{
+	return IO_SUCCESS;
+}
+
+int32_t rcar_register_io_dev_memdrv(const io_dev_connector_t **dev_con)
+{
+	int32_t result;
+
+	result = io_register_device(&memdrv_dev_info);
+	if (result == IO_SUCCESS) {
+		*dev_con = &memdrv_dev_connector;
+	}
+
+	return result;
+}
diff --git a/drivers/renesas/rcar/io/io_memdrv.h b/drivers/renesas/common/io/io_memdrv.h
similarity index 100%
rename from drivers/renesas/rcar/io/io_memdrv.h
rename to drivers/renesas/common/io/io_memdrv.h
diff --git a/drivers/renesas/rcar/io/io_private.h b/drivers/renesas/common/io/io_private.h
similarity index 100%
rename from drivers/renesas/rcar/io/io_private.h
rename to drivers/renesas/common/io/io_private.h
diff --git a/drivers/renesas/common/io/io_rcar.c b/drivers/renesas/common/io/io_rcar.c
new file mode 100644
index 0000000..45ef386
--- /dev/null
+++ b/drivers/renesas/common/io/io_rcar.c
@@ -0,0 +1,665 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/auth/auth_mod.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_storage.h>
+#include <lib/mmio.h>
+#include <plat/common/platform.h>
+#include <tools_share/firmware_image_package.h>
+#include <tools_share/uuid.h>
+
+#include "io_rcar.h"
+#include "io_common.h"
+#include "io_private.h"
+#include <platform_def.h>
+
+extern int32_t plat_get_drv_source(uint32_t id, uintptr_t *dev,
+				   uintptr_t *image_spec);
+
+static int32_t rcar_dev_open(const uintptr_t dev_spec __attribute__ ((unused)),
+			     io_dev_info_t **dev_info);
+static int32_t rcar_dev_close(io_dev_info_t *dev_info);
+
+typedef struct {
+	const int32_t name;
+	const uint32_t offset;
+	const uint32_t attr;
+} plat_rcar_name_offset_t;
+
+typedef struct {
+	/*
+	 * Put position above the struct to allow {0} on static init.
+	 * It is a workaround for a known bug in GCC
+	 * http://gcc.gnu.org/bugzilla/show_bug.cgi?id=53119
+	 */
+	uint32_t position;
+	uint32_t no_load;
+	uintptr_t offset;
+	uint32_t size;
+	uintptr_t dst;
+	uintptr_t partition;	/* for eMMC */
+	/* RCAR_EMMC_PARTITION_BOOT_0 */
+	/* RCAR_EMMC_PARTITION_BOOT_1 */
+	/* RCAR_EMMC_PARTITION_USER   */
+} file_state_t;
+
+#define RCAR_GET_FLASH_ADR(a, b)	((uint32_t)((0x40000U * (a)) + (b)))
+#define RCAR_ATTR_SET_CALCADDR(a)	((a) & 0xF)
+#define RCAR_ATTR_SET_ISNOLOAD(a)	(((a) & 0x1) << 16U)
+#define RCAR_ATTR_SET_CERTOFF(a)	(((a) & 0xF) << 8U)
+#define RCAR_ATTR_SET_ALL(a, b, c)	((uint32_t)(RCAR_ATTR_SET_CALCADDR(a) |\
+					RCAR_ATTR_SET_ISNOLOAD(b) |\
+					RCAR_ATTR_SET_CERTOFF(c)))
+
+#define RCAR_ATTR_GET_CALCADDR(a)	((a) & 0xFU)
+#define RCAR_ATTR_GET_ISNOLOAD(a)	(((a) >> 16) & 0x1U)
+#define RCAR_ATTR_GET_CERTOFF(a)	((uint32_t)(((a) >> 8) & 0xFU))
+
+#define RCAR_MAX_BL3X_IMAGE		(8U)
+#define RCAR_SECTOR6_CERT_OFFSET	(0x400U)
+#define RCAR_SDRAM_certESS		(0x43F00000U)
+#define RCAR_CERT_SIZE			(0x800U)
+#define RCAR_CERT_INFO_SIZE_OFFSET	(0x264U)
+#define RCAR_CERT_INFO_DST_OFFSET	(0x154U)
+#define RCAR_CERT_INFO_SIZE_OFFSET1	(0x364U)
+#define RCAR_CERT_INFO_DST_OFFSET1	(0x1D4U)
+#define RCAR_CERT_INFO_SIZE_OFFSET2	(0x464U)
+#define RCAR_CERT_INFO_DST_OFFSET2	(0x254U)
+#define RCAR_CERT_LOAD			(1U)
+
+#define RCAR_FLASH_CERT_HEADER		RCAR_GET_FLASH_ADR(6U, 0U)
+#define RCAR_EMMC_CERT_HEADER		(0x00030000U)
+
+#define RCAR_COUNT_LOAD_BL33		(2U)
+#define RCAR_COUNT_LOAD_BL33X		(3U)
+
+static const plat_rcar_name_offset_t name_offset[] = {
+	{BL31_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(0, 0, 0)},
+
+	/* BL3-2 is optional in the platform */
+	{BL32_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(1, 0, 1)},
+	{BL33_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(2, 0, 2)},
+	{BL332_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(3, 0, 3)},
+	{BL333_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(4, 0, 4)},
+	{BL334_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(5, 0, 5)},
+	{BL335_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(6, 0, 6)},
+	{BL336_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(7, 0, 7)},
+	{BL337_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(8, 0, 8)},
+	{BL338_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(9, 0, 9)},
+};
+
+#if TRUSTED_BOARD_BOOT
+static const plat_rcar_name_offset_t cert_offset[] = {
+	/* Certificates */
+	{TRUSTED_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
+	{SOC_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
+	{TRUSTED_OS_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
+	{NON_TRUSTED_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
+	{SOC_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
+	{TRUSTED_OS_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 1)},
+	{NON_TRUSTED_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 2)},
+	{BL332_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 3)},
+	{BL333_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 4)},
+	{BL334_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 5)},
+	{BL335_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 6)},
+	{BL336_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 7)},
+	{BL337_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 8)},
+	{BL338_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 9)},
+};
+#endif /* TRUSTED_BOARD_BOOT */
+
+static file_state_t current_file = { 0 };
+
+static uintptr_t rcar_handle, rcar_spec;
+static uint64_t rcar_image_header[RCAR_MAX_BL3X_IMAGE + 2U] = { 0U };
+static uint64_t rcar_image_header_prttn[RCAR_MAX_BL3X_IMAGE + 2U] = { 0U };
+static uint64_t rcar_image_number = { 0U };
+static uint32_t rcar_cert_load = { 0U };
+
+static io_type_t device_type_rcar(void)
+{
+	return IO_TYPE_FIRMWARE_IMAGE_PACKAGE;
+}
+
+int32_t rcar_get_certificate(const int32_t name, uint32_t *cert)
+{
+#if TRUSTED_BOARD_BOOT
+	int32_t i;
+
+	for (i = 0; i < ARRAY_SIZE(cert_offset); i++) {
+		if (name != cert_offset[i].name) {
+			continue;
+		}
+
+		*cert = RCAR_CERT_SIZE;
+		*cert *= RCAR_ATTR_GET_CERTOFF(cert_offset[i].attr);
+		*cert += RCAR_SDRAM_certESS;
+		return 0;
+	}
+#endif
+	return -EINVAL;
+}
+
+#define MFISBTSTSR			(0xE6260604U)
+#define MFISBTSTSR_BOOT_PARTITION	(0x00000010U)
+
+static int32_t file_to_offset(const int32_t name, uintptr_t *offset,
+			      uint32_t *cert, uint32_t *no_load,
+			      uintptr_t *partition)
+{
+	uint32_t addr;
+	int32_t i;
+
+	for (i = 0; i < ARRAY_SIZE(name_offset); i++) {
+		if (name != name_offset[i].name) {
+			continue;
+		}
+
+		addr = RCAR_ATTR_GET_CALCADDR(name_offset[i].attr);
+		if (rcar_image_number + 2U < addr) {
+			continue;
+		}
+
+		*offset = rcar_image_header[addr];
+
+		if (mmio_read_32(MFISBTSTSR) & MFISBTSTSR_BOOT_PARTITION)
+			*offset += 0x800000;
+		*cert = RCAR_CERT_SIZE;
+		*cert *= RCAR_ATTR_GET_CERTOFF(name_offset[i].attr);
+		*cert += RCAR_SDRAM_certESS;
+		*no_load = RCAR_ATTR_GET_ISNOLOAD(name_offset[i].attr);
+		*partition = rcar_image_header_prttn[addr];
+		return IO_SUCCESS;
+	}
+
+#if TRUSTED_BOARD_BOOT
+	for (i = 0; i < ARRAY_SIZE(cert_offset); i++) {
+		if (name != cert_offset[i].name) {
+			continue;
+		}
+
+		*no_load = RCAR_ATTR_GET_ISNOLOAD(cert_offset[i].attr);
+		*partition = 0U;
+		*offset = 0U;
+		*cert = 0U;
+		return IO_SUCCESS;
+	}
+#endif
+	return -EINVAL;
+}
+
+#define RCAR_BOOT_KEY_CERT_NEW	(0xE6300F00U)
+#define	RCAR_CERT_MAGIC_NUM	(0xE291F358U)
+
+void rcar_read_certificate(uint64_t cert, uint32_t *len, uintptr_t *dst)
+{
+	uint32_t seed, val, info_1, info_2;
+	uintptr_t size, dsth, dstl;
+
+	cert &= 0xFFFFFFFFU;
+
+	seed = mmio_read_32(RCAR_BOOT_KEY_CERT_NEW);
+	val = mmio_read_32(RCAR_BOOT_KEY_CERT_NEW + 0xC);
+	info_1 = (val >> 18) & 0x3U;
+	val = mmio_read_32(cert + 0xC);
+	info_2 = (val >> 21) & 0x3;
+
+	if (seed == RCAR_CERT_MAGIC_NUM) {
+		if (info_1 != 1) {
+			ERROR("BL2: Cert is invalid.\n");
+			*dst = 0;
+			*len = 0;
+			return;
+		}
+
+		if (info_2 > 2) {
+			ERROR("BL2: Cert is invalid.\n");
+			*dst = 0;
+			*len = 0;
+			return;
+		}
+
+		switch (info_2) {
+		case 2:
+			size = cert + RCAR_CERT_INFO_SIZE_OFFSET2;
+			dstl = cert + RCAR_CERT_INFO_DST_OFFSET2;
+			break;
+		case 1:
+			size = cert + RCAR_CERT_INFO_SIZE_OFFSET1;
+			dstl = cert + RCAR_CERT_INFO_DST_OFFSET1;
+			break;
+		case 0:
+			size = cert + RCAR_CERT_INFO_SIZE_OFFSET;
+			dstl = cert + RCAR_CERT_INFO_DST_OFFSET;
+			break;
+		}
+
+		*len = mmio_read_32(size) * 4U;
+		dsth = dstl + 4U;
+		*dst = ((uintptr_t) mmio_read_32(dsth) << 32) +
+		    ((uintptr_t) mmio_read_32(dstl));
+		return;
+	}
+
+	size = cert + RCAR_CERT_INFO_SIZE_OFFSET;
+	*len = mmio_read_32(size) * 4U;
+	dstl = cert + RCAR_CERT_INFO_DST_OFFSET;
+	dsth = dstl + 4U;
+	*dst = ((uintptr_t) mmio_read_32(dsth) << 32) +
+	    ((uintptr_t) mmio_read_32(dstl));
+}
+
+static int32_t check_load_area(uintptr_t dst, uintptr_t len)
+{
+	uint32_t legacy = dst + len <= UINT32_MAX - 1 ? 1 : 0;
+	uintptr_t dram_start, dram_end;
+	uintptr_t prot_start, prot_end;
+	int32_t result = IO_SUCCESS;
+
+	dram_start = legacy ? DRAM1_BASE : DRAM_40BIT_BASE;
+
+	dram_end = legacy ? DRAM1_BASE + DRAM1_SIZE :
+	    DRAM_40BIT_BASE + DRAM_40BIT_SIZE;
+
+	prot_start = legacy ? DRAM_PROTECTED_BASE : DRAM_40BIT_PROTECTED_BASE;
+
+	prot_end = prot_start + DRAM_PROTECTED_SIZE;
+
+	if (dst < dram_start || dst > dram_end - len) {
+		ERROR("BL2: dst address is on the protected area.\n");
+		result = IO_FAIL;
+		goto done;
+	}
+
+	/* load image is within SDRAM protected area */
+	if (dst >= prot_start && dst < prot_end) {
+		ERROR("BL2: dst address is on the protected area.\n");
+		result = IO_FAIL;
+	}
+
+	if (dst < prot_start && dst > prot_start - len) {
+		ERROR("BL2: loaded data is on the protected area.\n");
+		result = IO_FAIL;
+	}
+done:
+	if (result == IO_FAIL) {
+		ERROR("BL2: Out of range : dst=0x%lx len=0x%lx\n", dst, len);
+	}
+
+	return result;
+}
+
+static int32_t load_bl33x(void)
+{
+	static int32_t loaded = IO_NOT_SUPPORTED;
+	uintptr_t dst, partition, handle;
+	uint32_t noload, cert, len, i;
+	uintptr_t offset;
+	int32_t rc;
+	size_t cnt;
+	const int32_t img[] = {
+		BL33_IMAGE_ID,
+		BL332_IMAGE_ID,
+		BL333_IMAGE_ID,
+		BL334_IMAGE_ID,
+		BL335_IMAGE_ID,
+		BL336_IMAGE_ID,
+		BL337_IMAGE_ID,
+		BL338_IMAGE_ID
+	};
+
+	if (loaded != IO_NOT_SUPPORTED) {
+		return loaded;
+	}
+
+	for (i = 1; i < rcar_image_number; i++) {
+		rc = file_to_offset(img[i], &offset, &cert, &noload,
+				    &partition);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: failed to get offset\n", __func__);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+
+		rcar_read_certificate((uint64_t) cert, &len, &dst);
+		((io_drv_spec_t *) rcar_spec)->partition = partition;
+
+		rc = io_open(rcar_handle, rcar_spec, &handle);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: Failed to open FIP (%i)\n", __func__, rc);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+
+		rc = io_seek(handle, IO_SEEK_SET, offset);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: failed to seek\n", __func__);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+
+		rc = check_load_area(dst, len);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: check load area\n", __func__);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+
+		rc = io_read(handle, dst, len, &cnt);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: failed to read\n", __func__);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+#if TRUSTED_BOARD_BOOT
+		rc = auth_mod_verify_img(img[i], (void *)dst, len);
+		if (rc != 0) {
+			memset((void *)dst, 0x00, len);
+			loaded = IO_FAIL;
+			return loaded;
+		}
+#endif
+		io_close(handle);
+	}
+
+	loaded = IO_SUCCESS;
+
+	return loaded;
+}
+
+static int32_t rcar_dev_init(io_dev_info_t *dev_info, const uintptr_t name)
+{
+	static uint64_t header[64] __aligned(FLASH_TRANS_SIZE_UNIT) = {0UL};
+	uintptr_t handle;
+	ssize_t offset;
+	uint32_t i;
+	int32_t rc;
+	size_t cnt;
+
+	/* Obtain a reference to the image by querying the platform layer */
+	rc = plat_get_drv_source(name, &rcar_handle, &rcar_spec);
+	if (rc != IO_SUCCESS) {
+		WARN("Failed to obtain reference to img %ld (%i)\n", name, rc);
+		return IO_FAIL;
+	}
+
+	if (rcar_cert_load == RCAR_CERT_LOAD) {
+		return IO_SUCCESS;
+	}
+
+	rc = io_open(rcar_handle, rcar_spec, &handle);
+	if (rc != IO_SUCCESS) {
+		WARN("Failed to access img %ld (%i)\n", name, rc);
+		return IO_FAIL;
+	}
+
+	/*
+	 * get start address list
+	 * [0] address num
+	 * [1] BL33-1 image address
+	 * [2] BL33-2 image address
+	 * [3] BL33-3 image address
+	 * [4] BL33-4 image address
+	 * [5] BL33-5 image address
+	 * [6] BL33-6 image address
+	 * [7] BL33-7 image address
+	 * [8] BL33-8 image address
+	 */
+	offset = name == EMMC_DEV_ID ? RCAR_EMMC_CERT_HEADER :
+	    RCAR_FLASH_CERT_HEADER;
+	rc = io_seek(handle, IO_SEEK_SET, offset);
+	if (rc != IO_SUCCESS) {
+		WARN("Firmware Image Package header failed to seek\n");
+		goto error;
+	}
+
+	rc = io_read(handle, (uintptr_t) &header, sizeof(header), &cnt);
+	if (rc != IO_SUCCESS) {
+		WARN("Firmware Image Package header failed to read\n");
+		goto error;
+	}
+
+#if RCAR_BL2_DCACHE == 1
+	inv_dcache_range((uint64_t) header, sizeof(header));
+#endif
+
+	rcar_image_number = header[0];
+	for (i = 0; i < rcar_image_number + 2; i++) {
+		rcar_image_header[i] = header[i * 2 + 1];
+		rcar_image_header_prttn[i] = header[i * 2 + 2];
+	}
+
+	if (rcar_image_number == 0 || rcar_image_number > RCAR_MAX_BL3X_IMAGE) {
+		WARN("Firmware Image Package header check failed.\n");
+		rc = IO_FAIL;
+		goto error;
+	}
+
+	rc = io_seek(handle, IO_SEEK_SET, offset + RCAR_SECTOR6_CERT_OFFSET);
+	if (rc != IO_SUCCESS) {
+		WARN("Firmware Image Package header failed to seek cert\n");
+		goto error;
+	}
+
+	rc = io_read(handle, RCAR_SDRAM_certESS,
+		     RCAR_CERT_SIZE * (2 + rcar_image_number), &cnt);
+	if (rc != IO_SUCCESS) {
+		WARN("cert file read error.\n");
+		goto error;
+	}
+
+#if RCAR_BL2_DCACHE == 1
+	inv_dcache_range(RCAR_SDRAM_certESS,
+			 RCAR_CERT_SIZE * (2 + rcar_image_number));
+#endif
+
+	rcar_cert_load = RCAR_CERT_LOAD;
+error:
+
+	if (rc != IO_SUCCESS) {
+		rc = IO_FAIL;
+	}
+
+	io_close(handle);
+
+	return rc;
+
+}
+
+static int32_t rcar_file_open(io_dev_info_t *info, const uintptr_t file_spec,
+			      io_entity_t *entity)
+{
+	const io_drv_spec_t *spec = (io_drv_spec_t *) file_spec;
+	uintptr_t partition, offset, dst;
+	uint32_t noload, cert, len;
+	int32_t rc;
+
+	/*
+	 * Only one file open at a time. We need to  track state (ie, file
+	 * cursor position). Since the header lives at offset zero, this entry
+	 * should never be zero in an active file.
+	 * Once the system supports dynamic memory allocation we will allow more
+	 * than one open file at a time.
+	 */
+	if (current_file.offset != 0U) {
+		WARN("%s: Only one open file at a time.\n", __func__);
+		return IO_RESOURCES_EXHAUSTED;
+	}
+
+	rc = file_to_offset(spec->offset, &offset, &cert, &noload, &partition);
+	if (rc != IO_SUCCESS) {
+		WARN("Failed to open file name %ld (%i)\n", spec->offset, rc);
+		return IO_FAIL;
+	}
+
+	if (noload != 0U) {
+		current_file.offset = 1;
+		current_file.dst = 0;
+		current_file.size = 1;
+		current_file.position = 0;
+		current_file.no_load = noload;
+		current_file.partition = 0;
+		entity->info = (uintptr_t) &current_file;
+
+		return IO_SUCCESS;
+	}
+
+	rcar_read_certificate((uint64_t) cert, &len, &dst);
+
+	/* Baylibre: HACK */
+	if (spec->offset == BL31_IMAGE_ID && len < RCAR_TRUSTED_SRAM_SIZE) {
+		WARN("%s,%s\n", "r-car ignoring the BL31 size from certificate",
+		     "using RCAR_TRUSTED_SRAM_SIZE instead");
+		len = RCAR_TRUSTED_SRAM_SIZE;
+	}
+
+	current_file.partition = partition;
+	current_file.no_load = noload;
+	current_file.offset = offset;
+	current_file.position = 0;
+	current_file.size = len;
+	current_file.dst = dst;
+	entity->info = (uintptr_t) &current_file;
+
+	return IO_SUCCESS;
+}
+
+static int32_t rcar_file_len(io_entity_t *entity, size_t *length)
+{
+	*length = ((file_state_t *) entity->info)->size;
+
+	NOTICE("%s: len: 0x%08lx\n", __func__, *length);
+
+	return IO_SUCCESS;
+}
+
+static int32_t rcar_file_read(io_entity_t *entity, uintptr_t buffer,
+			      size_t length, size_t *cnt)
+{
+	file_state_t *fp = (file_state_t *) entity->info;
+	ssize_t offset = fp->offset + fp->position;
+	uintptr_t handle;
+	int32_t rc;
+
+#ifdef SPD_NONE
+	static uint32_t load_bl33x_counter = 1;
+#else
+	static uint32_t load_bl33x_counter;
+#endif
+	if (current_file.no_load != 0U) {
+		*cnt = length;
+		return IO_SUCCESS;
+	}
+
+	((io_drv_spec_t *) rcar_spec)->partition = fp->partition;
+
+	rc = io_open(rcar_handle, rcar_spec, &handle);
+	if (rc != IO_SUCCESS) {
+		WARN("Failed to open FIP (%i)\n", rc);
+		return IO_FAIL;
+	}
+
+	rc = io_seek(handle, IO_SEEK_SET, offset);
+	if (rc != IO_SUCCESS) {
+		WARN("%s: failed to seek\n", __func__);
+		goto error;
+	}
+
+	if (load_bl33x_counter == RCAR_COUNT_LOAD_BL33) {
+		rc = check_load_area(buffer, length);
+		if (rc != IO_SUCCESS) {
+			WARN("%s: load area err\n", __func__);
+			goto error;
+		}
+	}
+
+	rc = io_read(handle, buffer, length, cnt);
+	if (rc != IO_SUCCESS) {
+		WARN("Failed to read payload (%i)\n", rc);
+		goto error;
+	}
+
+	fp->position += *cnt;
+	io_close(handle);
+
+	load_bl33x_counter += 1;
+	if (load_bl33x_counter == RCAR_COUNT_LOAD_BL33X) {
+		return load_bl33x();
+	}
+
+	return IO_SUCCESS;
+error:
+	io_close(handle);
+	return IO_FAIL;
+}
+
+static int32_t rcar_file_close(io_entity_t *entity)
+{
+	if (current_file.offset != 0U) {
+		memset(&current_file, 0, sizeof(current_file));
+	}
+
+	entity->info = 0U;
+
+	return IO_SUCCESS;
+}
+
+static const io_dev_funcs_t rcar_dev_funcs = {
+	.type = &device_type_rcar,
+	.open = &rcar_file_open,
+	.seek = NULL,
+	.size = &rcar_file_len,
+	.read = &rcar_file_read,
+	.write = NULL,
+	.close = &rcar_file_close,
+	.dev_init = &rcar_dev_init,
+	.dev_close = &rcar_dev_close,
+};
+
+static const io_dev_info_t rcar_dev_info = {
+	.funcs = &rcar_dev_funcs,
+	.info = (uintptr_t) 0
+};
+
+static const io_dev_connector_t rcar_dev_connector = {
+	.dev_open = &rcar_dev_open
+};
+
+static int32_t rcar_dev_open(const uintptr_t dev_spec __attribute__ ((unused)),
+			     io_dev_info_t **dev_info)
+{
+	*dev_info = (io_dev_info_t *) &rcar_dev_info;
+
+	return IO_SUCCESS;
+}
+
+static int32_t rcar_dev_close(io_dev_info_t *dev_info)
+{
+	rcar_handle = 0;
+	rcar_spec = 0;
+
+	return IO_SUCCESS;
+}
+
+int32_t rcar_register_io_dev(const io_dev_connector_t **dev_con)
+{
+	int32_t result;
+
+	result = io_register_device(&rcar_dev_info);
+	if (result == IO_SUCCESS) {
+		*dev_con = &rcar_dev_connector;
+	}
+
+	return result;
+}
diff --git a/drivers/renesas/rcar/io/io_rcar.h b/drivers/renesas/common/io/io_rcar.h
similarity index 100%
rename from drivers/renesas/rcar/io/io_rcar.h
rename to drivers/renesas/common/io/io_rcar.h
diff --git a/drivers/renesas/rcar/pfc/pfc_regs.h b/drivers/renesas/common/pfc_regs.h
similarity index 100%
rename from drivers/renesas/rcar/pfc/pfc_regs.h
rename to drivers/renesas/common/pfc_regs.h
diff --git a/drivers/renesas/rcar/pwrc/call_sram.S b/drivers/renesas/common/pwrc/call_sram.S
similarity index 100%
rename from drivers/renesas/rcar/pwrc/call_sram.S
rename to drivers/renesas/common/pwrc/call_sram.S
diff --git a/drivers/renesas/common/pwrc/pwrc.c b/drivers/renesas/common/pwrc/pwrc.c
new file mode 100644
index 0000000..4e175eb
--- /dev/null
+++ b/drivers/renesas/common/pwrc/pwrc.c
@@ -0,0 +1,894 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/bakery_lock.h>
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <plat/common/platform.h>
+
+#include "iic_dvfs.h"
+#include "micro_delay.h"
+#include "pwrc.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+#include "cpg_registers.h"
+
+/*
+ * Someday there will be a generic power controller api. At the moment each
+ * platform has its own pwrc so just exporting functions should be acceptable.
+ */
+RCAR_INSTANTIATE_LOCK
+
+#define WUP_IRQ_SHIFT				(0U)
+#define WUP_FIQ_SHIFT				(8U)
+#define WUP_CSD_SHIFT				(16U)
+#define BIT_SOFTRESET				(1U << 15)
+#define BIT_CA53_SCU				(1U << 21)
+#define BIT_CA57_SCU				(1U << 12)
+#define REQ_RESUME				(1U << 1)
+#define REQ_OFF					(1U << 0)
+#define STATUS_PWRUP				(1U << 4)
+#define STATUS_PWRDOWN				(1U << 0)
+#define STATE_CA57_CPU				(27U)
+#define STATE_CA53_CPU				(22U)
+#define MODE_L2_DOWN				(0x00000002U)
+#define CPU_PWR_OFF				(0x00000003U)
+#define RCAR_PSTR_MASK				(0x00000003U)
+#define ST_ALL_STANDBY				(0x00003333U)
+#define SYSCEXTMASK_EXTMSK0			(0x00000001U)
+/* Suspend to ram	*/
+#define DBSC4_REG_BASE				(0xE6790000U)
+#define DBSC4_REG_DBSYSCNT0			(DBSC4_REG_BASE + 0x0100U)
+#define DBSC4_REG_DBACEN			(DBSC4_REG_BASE + 0x0200U)
+#define DBSC4_REG_DBCMD				(DBSC4_REG_BASE + 0x0208U)
+#define DBSC4_REG_DBRFEN			(DBSC4_REG_BASE + 0x0204U)
+#define DBSC4_REG_DBWAIT			(DBSC4_REG_BASE + 0x0210U)
+#define DBSC4_REG_DBCALCNF			(DBSC4_REG_BASE + 0x0424U)
+#define DBSC4_REG_DBDFIPMSTRCNF			(DBSC4_REG_BASE + 0x0520U)
+#define DBSC4_REG_DBPDLK0			(DBSC4_REG_BASE + 0x0620U)
+#define DBSC4_REG_DBPDRGA0			(DBSC4_REG_BASE + 0x0624U)
+#define DBSC4_REG_DBPDRGD0			(DBSC4_REG_BASE + 0x0628U)
+#define DBSC4_REG_DBCAM0CTRL0			(DBSC4_REG_BASE + 0x0940U)
+#define DBSC4_REG_DBCAM0STAT0			(DBSC4_REG_BASE + 0x0980U)
+#define DBSC4_REG_DBCAM1STAT0			(DBSC4_REG_BASE + 0x0990U)
+#define DBSC4_REG_DBCAM2STAT0			(DBSC4_REG_BASE + 0x09A0U)
+#define DBSC4_REG_DBCAM3STAT0			(DBSC4_REG_BASE + 0x09B0U)
+#define DBSC4_BIT_DBACEN_ACCEN			((uint32_t)(1U << 0))
+#define DBSC4_BIT_DBRFEN_ARFEN			((uint32_t)(1U << 0))
+#define DBSC4_BIT_DBCAMxSTAT0			(0x00000001U)
+#define DBSC4_BIT_DBDFIPMSTRCNF_PMSTREN		(0x00000001U)
+#define DBSC4_SET_DBCMD_OPC_PRE			(0x04000000U)
+#define DBSC4_SET_DBCMD_OPC_SR			(0x0A000000U)
+#define DBSC4_SET_DBCMD_OPC_PD			(0x08000000U)
+#define DBSC4_SET_DBCMD_OPC_MRW			(0x0E000000U)
+#define DBSC4_SET_DBCMD_CH_ALL			(0x00800000U)
+#define DBSC4_SET_DBCMD_RANK_ALL		(0x00040000U)
+#define DBSC4_SET_DBCMD_ARG_ALL			(0x00000010U)
+#define DBSC4_SET_DBCMD_ARG_ENTER		(0x00000000U)
+#define DBSC4_SET_DBCMD_ARG_MRW_ODTC		(0x00000B00U)
+#define DBSC4_SET_DBSYSCNT0_WRITE_ENABLE	(0x00001234U)
+#define DBSC4_SET_DBSYSCNT0_WRITE_DISABLE	(0x00000000U)
+#define DBSC4_SET_DBPDLK0_PHY_ACCESS		(0x0000A55AU)
+#define DBSC4_SET_DBPDRGA0_ACIOCR0		(0x0000001AU)
+#define DBSC4_SET_DBPDRGD0_ACIOCR0		(0x33C03C11U)
+#define DBSC4_SET_DBPDRGA0_DXCCR		(0x00000020U)
+#define DBSC4_SET_DBPDRGD0_DXCCR		(0x00181006U)
+#define DBSC4_SET_DBPDRGA0_PGCR1		(0x00000003U)
+#define DBSC4_SET_DBPDRGD0_PGCR1		(0x0380C600U)
+#define DBSC4_SET_DBPDRGA0_ACIOCR1		(0x0000001BU)
+#define DBSC4_SET_DBPDRGD0_ACIOCR1		(0xAAAAAAAAU)
+#define DBSC4_SET_DBPDRGA0_ACIOCR3		(0x0000001DU)
+#define DBSC4_SET_DBPDRGD0_ACIOCR3		(0xAAAAAAAAU)
+#define DBSC4_SET_DBPDRGA0_ACIOCR5		(0x0000001FU)
+#define DBSC4_SET_DBPDRGD0_ACIOCR5		(0x000000AAU)
+#define DBSC4_SET_DBPDRGA0_DX0GCR2		(0x000000A2U)
+#define DBSC4_SET_DBPDRGD0_DX0GCR2		(0xAAAA0000U)
+#define DBSC4_SET_DBPDRGA0_DX1GCR2		(0x000000C2U)
+#define DBSC4_SET_DBPDRGD0_DX1GCR2		(0xAAAA0000U)
+#define DBSC4_SET_DBPDRGA0_DX2GCR2		(0x000000E2U)
+#define DBSC4_SET_DBPDRGD0_DX2GCR2		(0xAAAA0000U)
+#define DBSC4_SET_DBPDRGA0_DX3GCR2		(0x00000102U)
+#define DBSC4_SET_DBPDRGD0_DX3GCR2		(0xAAAA0000U)
+#define DBSC4_SET_DBPDRGA0_ZQCR			(0x00000090U)
+#define DBSC4_SET_DBPDRGD0_ZQCR_MD19_0		(0x04058904U)
+#define DBSC4_SET_DBPDRGD0_ZQCR_MD19_1		(0x04058A04U)
+#define DBSC4_SET_DBPDRGA0_DX0GCR0		(0x000000A0U)
+#define DBSC4_SET_DBPDRGD0_DX0GCR0		(0x7C0002E5U)
+#define DBSC4_SET_DBPDRGA0_DX1GCR0		(0x000000C0U)
+#define DBSC4_SET_DBPDRGD0_DX1GCR0		(0x7C0002E5U)
+#define DBSC4_SET_DBPDRGA0_DX2GCR0		(0x000000E0U)
+#define DBSC4_SET_DBPDRGD0_DX2GCR0		(0x7C0002E5U)
+#define DBSC4_SET_DBPDRGA0_DX3GCR0		(0x00000100U)
+#define DBSC4_SET_DBPDRGD0_DX3GCR0		(0x7C0002E5U)
+#define DBSC4_SET_DBPDRGA0_DX0GCR1		(0x000000A1U)
+#define DBSC4_SET_DBPDRGD0_DX0GCR1		(0x55550000U)
+#define DBSC4_SET_DBPDRGA0_DX1GCR1		(0x000000C1U)
+#define DBSC4_SET_DBPDRGD0_DX1GCR1		(0x55550000U)
+#define DBSC4_SET_DBPDRGA0_DX2GCR1		(0x000000E1U)
+#define DBSC4_SET_DBPDRGD0_DX2GCR1		(0x55550000U)
+#define DBSC4_SET_DBPDRGA0_DX3GCR1		(0x00000101U)
+#define DBSC4_SET_DBPDRGD0_DX3GCR1		(0x55550000U)
+#define DBSC4_SET_DBPDRGA0_DX0GCR3		(0x000000A3U)
+#define DBSC4_SET_DBPDRGD0_DX0GCR3		(0x00008484U)
+#define DBSC4_SET_DBPDRGA0_DX1GCR3		(0x000000C3U)
+#define DBSC4_SET_DBPDRGD0_DX1GCR3		(0x00008484U)
+#define DBSC4_SET_DBPDRGA0_DX2GCR3		(0x000000E3U)
+#define DBSC4_SET_DBPDRGD0_DX2GCR3		(0x00008484U)
+#define DBSC4_SET_DBPDRGA0_DX3GCR3		(0x00000103U)
+#define DBSC4_SET_DBPDRGD0_DX3GCR3		(0x00008484U)
+#define RST_BASE				(0xE6160000U)
+#define RST_MODEMR				(RST_BASE + 0x0060U)
+#define RST_MODEMR_BIT0				(0x00000001U)
+
+#define RCAR_CNTCR_OFF				(0x00U)
+#define RCAR_CNTCVL_OFF				(0x08U)
+#define RCAR_CNTCVU_OFF				(0x0CU)
+#define RCAR_CNTFID_OFF				(0x20U)
+
+#define RCAR_CNTCR_EN				((uint32_t)1U << 0U)
+#define RCAR_CNTCR_FCREQ(x)			((uint32_t)(x) << 8U)
+
+#if PMIC_ROHM_BD9571
+#define BIT_BKUP_CTRL_OUT			((uint8_t)(1U << 4))
+#define PMIC_BKUP_MODE_CNT			(0x20U)
+#define PMIC_QLLM_CNT				(0x27U)
+#define PMIC_RETRY_MAX				(100U)
+#endif /* PMIC_ROHM_BD9571 */
+#define SCTLR_EL3_M_BIT				((uint32_t)1U << 0)
+#define RCAR_CA53CPU_NUM_MAX			(4U)
+#define RCAR_CA57CPU_NUM_MAX			(4U)
+#define IS_A53A57(c)	((c) == RCAR_CLUSTER_A53A57)
+#define IS_CA57(c)	((c) == RCAR_CLUSTER_CA57)
+#define IS_CA53(c)	((c) == RCAR_CLUSTER_CA53)
+
+#ifndef __ASSEMBLER__
+IMPORT_SYM(unsigned long, __system_ram_start__, SYSTEM_RAM_START);
+IMPORT_SYM(unsigned long, __system_ram_end__, SYSTEM_RAM_END);
+IMPORT_SYM(unsigned long, __SRAM_COPY_START__, SRAM_COPY_START);
+#endif
+
+uint32_t rcar_pwrc_status(uint64_t mpidr)
+{
+	uint32_t ret = 0;
+	uint64_t cm, cpu;
+	uint32_t reg;
+	uint32_t c;
+
+	rcar_lock_get();
+
+	c = rcar_pwrc_get_cluster();
+	cm = mpidr & MPIDR_CLUSTER_MASK;
+
+	if (!IS_A53A57(c) && cm != 0) {
+		ret = RCAR_INVALID;
+		goto done;
+	}
+
+	reg = mmio_read_32(RCAR_PRR);
+	cpu = mpidr & MPIDR_CPU_MASK;
+
+	if (IS_CA53(c))
+		if (reg & (1 << (STATE_CA53_CPU + cpu)))
+			ret = RCAR_INVALID;
+	if (IS_CA57(c))
+		if (reg & (1 << (STATE_CA57_CPU + cpu)))
+			ret = RCAR_INVALID;
+done:
+	rcar_lock_release();
+
+	return ret;
+}
+
+static void scu_power_up(uint64_t mpidr)
+{
+	uintptr_t reg_pwrsr, reg_cpumcr, reg_pwron, reg_pwrer;
+	uint32_t c, sysc_reg_bit;
+	uint32_t lsi_product;
+	uint32_t lsi_cut;
+
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	reg_cpumcr = IS_CA57(c) ? RCAR_CA57CPUCMCR : RCAR_CA53CPUCMCR;
+	sysc_reg_bit = IS_CA57(c) ? BIT_CA57_SCU : BIT_CA53_SCU;
+	reg_pwron = IS_CA57(c) ? RCAR_PWRONCR5 : RCAR_PWRONCR3;
+	reg_pwrer = IS_CA57(c) ? RCAR_PWRER5 : RCAR_PWRER3;
+	reg_pwrsr = IS_CA57(c) ? RCAR_PWRSR5 : RCAR_PWRSR3;
+
+	if ((mmio_read_32(reg_pwrsr) & STATUS_PWRDOWN) == 0)
+		return;
+
+	if (mmio_read_32(reg_cpumcr) != 0)
+		mmio_write_32(reg_cpumcr, 0);
+
+	lsi_product = mmio_read_32((uintptr_t)RCAR_PRR);
+	lsi_cut = lsi_product & PRR_CUT_MASK;
+	lsi_product &= PRR_PRODUCT_MASK;
+
+	if ((lsi_product == PRR_PRODUCT_M3 && lsi_cut >= PRR_PRODUCT_30) ||
+	    lsi_product == PRR_PRODUCT_H3 ||
+	    lsi_product == PRR_PRODUCT_M3N ||
+	    lsi_product == PRR_PRODUCT_E3) {
+		mmio_setbits_32(RCAR_SYSCEXTMASK, SYSCEXTMASK_EXTMSK0);
+	}
+
+	mmio_setbits_32(RCAR_SYSCIER, sysc_reg_bit);
+	mmio_setbits_32(RCAR_SYSCIMR, sysc_reg_bit);
+
+	do {
+		while ((mmio_read_32(RCAR_SYSCSR) & REQ_RESUME) == 0)
+			;
+		mmio_write_32(reg_pwron, 1);
+	} while (mmio_read_32(reg_pwrer) & 1);
+
+	while ((mmio_read_32(RCAR_SYSCISR) & sysc_reg_bit) == 0)
+		;
+	mmio_write_32(RCAR_SYSCISCR, sysc_reg_bit);
+
+	if ((lsi_product == PRR_PRODUCT_M3 && lsi_cut >= PRR_PRODUCT_30) ||
+	    lsi_product == PRR_PRODUCT_H3 ||
+	    lsi_product == PRR_PRODUCT_M3N ||
+	    lsi_product == PRR_PRODUCT_E3) {
+		mmio_clrbits_32(RCAR_SYSCEXTMASK, SYSCEXTMASK_EXTMSK0);
+	}
+
+	while ((mmio_read_32(reg_pwrsr) & STATUS_PWRUP) == 0)
+		;
+}
+
+void rcar_pwrc_cpuon(uint64_t mpidr)
+{
+	uint32_t res_data, on_data;
+	uintptr_t res_reg, on_reg;
+	uint32_t limit, c;
+	uint64_t cpu;
+
+	rcar_lock_get();
+
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	res_reg = IS_CA53(c) ? RCAR_CA53RESCNT : RCAR_CA57RESCNT;
+	on_reg = IS_CA53(c) ? RCAR_CA53WUPCR : RCAR_CA57WUPCR;
+	limit = IS_CA53(c) ? 0x5A5A0000 : 0xA5A50000;
+
+	res_data = mmio_read_32(res_reg) | limit;
+	scu_power_up(mpidr);
+	cpu = mpidr & MPIDR_CPU_MASK;
+	on_data = 1 << cpu;
+	mmio_write_32(CPG_CPGWPR, ~on_data);
+	mmio_write_32(on_reg, on_data);
+	mmio_write_32(res_reg, res_data & (~(1 << (3 - cpu))));
+
+	rcar_lock_release();
+}
+
+void rcar_pwrc_cpuoff(uint64_t mpidr)
+{
+	uint32_t c;
+	uintptr_t reg;
+	uint64_t cpu;
+
+	rcar_lock_get();
+
+	cpu = mpidr & MPIDR_CPU_MASK;
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	reg = IS_CA53(c) ? RCAR_CA53CPU0CR : RCAR_CA57CPU0CR;
+
+	if (read_mpidr_el1() != mpidr)
+		panic();
+
+	mmio_write_32(CPG_CPGWPR, ~CPU_PWR_OFF);
+	mmio_write_32(reg + cpu * 0x0010, CPU_PWR_OFF);
+
+	rcar_lock_release();
+}
+
+void rcar_pwrc_enable_interrupt_wakeup(uint64_t mpidr)
+{
+	uint32_t c, shift_irq, shift_fiq;
+	uintptr_t reg;
+	uint64_t cpu;
+
+	rcar_lock_get();
+
+	cpu = mpidr & MPIDR_CPU_MASK;
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	reg = IS_CA53(c) ? RCAR_WUPMSKCA53 : RCAR_WUPMSKCA57;
+
+	shift_irq = WUP_IRQ_SHIFT + cpu;
+	shift_fiq = WUP_FIQ_SHIFT + cpu;
+
+	mmio_write_32(reg, ~((uint32_t) 1 << shift_irq) &
+		      ~((uint32_t) 1 << shift_fiq));
+	rcar_lock_release();
+}
+
+void rcar_pwrc_disable_interrupt_wakeup(uint64_t mpidr)
+{
+	uint32_t c, shift_irq, shift_fiq;
+	uintptr_t reg;
+	uint64_t cpu;
+
+	rcar_lock_get();
+
+	cpu = mpidr & MPIDR_CPU_MASK;
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	reg = IS_CA53(c) ? RCAR_WUPMSKCA53 : RCAR_WUPMSKCA57;
+
+	shift_irq = WUP_IRQ_SHIFT + cpu;
+	shift_fiq = WUP_FIQ_SHIFT + cpu;
+
+	mmio_write_32(reg, ((uint32_t) 1 << shift_irq) |
+		      ((uint32_t) 1 << shift_fiq));
+	rcar_lock_release();
+}
+
+void rcar_pwrc_clusteroff(uint64_t mpidr)
+{
+	uint32_t c, product, cut, reg;
+	uintptr_t dst;
+
+	rcar_lock_get();
+
+	reg = mmio_read_32(RCAR_PRR);
+	product = reg & PRR_PRODUCT_MASK;
+	cut = reg & PRR_CUT_MASK;
+
+	c = rcar_pwrc_get_mpidr_cluster(mpidr);
+	dst = IS_CA53(c) ? RCAR_CA53CPUCMCR : RCAR_CA57CPUCMCR;
+
+	if (product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30) {
+		goto done;
+	}
+
+	if (product == PRR_PRODUCT_H3 && cut <= PRR_PRODUCT_20) {
+		goto done;
+	}
+
+	/* all of the CPUs in the cluster is in the CoreStandby mode */
+	mmio_write_32(dst, MODE_L2_DOWN);
+done:
+	rcar_lock_release();
+}
+
+static uint64_t rcar_pwrc_saved_cntpct_el0;
+static uint32_t rcar_pwrc_saved_cntfid;
+
+#if RCAR_SYSTEM_SUSPEND
+static void rcar_pwrc_save_timer_state(void)
+{
+	rcar_pwrc_saved_cntpct_el0 = read_cntpct_el0();
+
+	rcar_pwrc_saved_cntfid =
+		mmio_read_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTFID_OFF));
+}
+#endif /* RCAR_SYSTEM_SUSPEND */
+
+void rcar_pwrc_restore_timer_state(void)
+{
+	/* Stop timer before restoring counter value */
+	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCR_OFF), 0U);
+
+	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCVL_OFF),
+		(uint32_t)(rcar_pwrc_saved_cntpct_el0 & 0xFFFFFFFFU));
+	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCVU_OFF),
+		(uint32_t)(rcar_pwrc_saved_cntpct_el0 >> 32U));
+
+	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTFID_OFF),
+		rcar_pwrc_saved_cntfid);
+
+	/* Start generic timer back */
+	write_cntfrq_el0((u_register_t)plat_get_syscnt_freq2());
+
+	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCR_OFF),
+		(RCAR_CNTCR_FCREQ(0U) | RCAR_CNTCR_EN));
+}
+
+#if !PMIC_ROHM_BD9571
+void rcar_pwrc_system_reset(void)
+{
+	mmio_write_32(RCAR_SRESCR, 0x5AA50000U | BIT_SOFTRESET);
+}
+#endif /* PMIC_ROHM_BD9571 */
+
+#define RST_CA53_CPU0_BARH		(0xE6160080U)
+#define RST_CA53_CPU0_BARL		(0xE6160084U)
+#define RST_CA57_CPU0_BARH		(0xE61600C0U)
+#define RST_CA57_CPU0_BARL		(0xE61600C4U)
+
+void rcar_pwrc_setup(void)
+{
+	uintptr_t rst_barh;
+	uintptr_t rst_barl;
+	uint32_t i, j;
+	uint64_t reset = (uint64_t) (&plat_secondary_reset) & 0xFFFFFFFF;
+
+	const uint32_t cluster[PLATFORM_CLUSTER_COUNT] = {
+		RCAR_CLUSTER_CA53,
+		RCAR_CLUSTER_CA57
+	};
+	const uintptr_t reg_barh[PLATFORM_CLUSTER_COUNT] = {
+		RST_CA53_CPU0_BARH,
+		RST_CA57_CPU0_BARH
+	};
+	const uintptr_t reg_barl[PLATFORM_CLUSTER_COUNT] = {
+		RST_CA53_CPU0_BARL,
+		RST_CA57_CPU0_BARL
+	};
+
+	for (i = 0; i < PLATFORM_CLUSTER_COUNT; i++) {
+		rst_barh = reg_barh[i];
+		rst_barl = reg_barl[i];
+		for (j = 0; j < rcar_pwrc_get_cpu_num(cluster[i]); j++) {
+			mmio_write_32(rst_barh, 0);
+			mmio_write_32(rst_barl, (uint32_t) reset);
+			rst_barh += 0x10;
+			rst_barl += 0x10;
+		}
+	}
+
+	rcar_lock_init();
+}
+
+#if RCAR_SYSTEM_SUSPEND
+#define DBCAM_FLUSH(__bit)		\
+do {					\
+	;				\
+} while (!(mmio_read_32(DBSC4_REG_DBCAM##__bit##STAT0) & DBSC4_BIT_DBCAMxSTAT0))
+
+
+static void __attribute__ ((section(".system_ram")))
+	rcar_pwrc_set_self_refresh(void)
+{
+	uint32_t reg = mmio_read_32(RCAR_PRR);
+	uint32_t cut, product;
+
+	product = reg & PRR_PRODUCT_MASK;
+	cut = reg & PRR_CUT_MASK;
+
+	if (product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30) {
+		goto self_refresh;
+	}
+
+	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20) {
+		goto self_refresh;
+	}
+
+	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_ENABLE);
+
+self_refresh:
+
+	/* DFI_PHYMSTR_ACK setting */
+	mmio_write_32(DBSC4_REG_DBDFIPMSTRCNF,
+			mmio_read_32(DBSC4_REG_DBDFIPMSTRCNF) &
+			(~DBSC4_BIT_DBDFIPMSTRCNF_PMSTREN));
+
+	/* Set the Self-Refresh mode */
+	mmio_write_32(DBSC4_REG_DBACEN, 0);
+
+	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20)
+		rcar_micro_delay(100);
+	else if (product == PRR_PRODUCT_H3) {
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
+		DBCAM_FLUSH(0);
+		DBCAM_FLUSH(1);
+		DBCAM_FLUSH(2);
+		DBCAM_FLUSH(3);
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
+	} else if (product == PRR_PRODUCT_M3) {
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
+		DBCAM_FLUSH(0);
+		DBCAM_FLUSH(1);
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
+	} else {
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
+		DBCAM_FLUSH(0);
+		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
+	}
+
+	/* Set the SDRAM calibration configuration register */
+	mmio_write_32(DBSC4_REG_DBCALCNF, 0);
+
+	reg = DBSC4_SET_DBCMD_OPC_PRE | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ALL;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	/* Self-Refresh entry command   */
+	reg = DBSC4_SET_DBCMD_OPC_SR | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	/* Mode Register Write command. (ODT disabled)  */
+	reg = DBSC4_SET_DBCMD_OPC_MRW | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_MRW_ODTC;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	/* Power Down entry command     */
+	reg = DBSC4_SET_DBCMD_OPC_PD | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	/* Set the auto-refresh enable register */
+	mmio_write_32(DBSC4_REG_DBRFEN, 0U);
+	rcar_micro_delay(1U);
+
+	if (product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30)
+		return;
+
+	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20)
+		return;
+
+	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_DISABLE);
+}
+
+static void __attribute__ ((section(".system_ram")))
+rcar_pwrc_set_self_refresh_e3(void)
+{
+	uint32_t ddr_md;
+	uint32_t reg;
+
+	ddr_md = (mmio_read_32(RST_MODEMR) >> 19) & RST_MODEMR_BIT0;
+
+	/* Write enable */
+	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_ENABLE);
+	mmio_write_32(DBSC4_REG_DBACEN, 0);
+	DBCAM_FLUSH(0);
+
+	reg = DBSC4_SET_DBCMD_OPC_PRE | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ALL;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	reg = DBSC4_SET_DBCMD_OPC_SR | DBSC4_SET_DBCMD_CH_ALL |
+	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
+	mmio_write_32(DBSC4_REG_DBCMD, reg);
+	while (mmio_read_32(DBSC4_REG_DBWAIT))
+		;
+
+	/*
+	 * Set the auto-refresh enable register
+	 * Set the ARFEN bit to 0 in the DBRFEN
+	 */
+	mmio_write_32(DBSC4_REG_DBRFEN, 0);
+
+	mmio_write_32(DBSC4_REG_DBPDLK0, DBSC4_SET_DBPDLK0_PHY_ACCESS);
+
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR0);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR0);
+
+	/* DDR_DXCCR */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DXCCR);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DXCCR);
+
+	/* DDR_PGCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_PGCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_PGCR1);
+
+	/* DDR_ACIOCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR1);
+
+	/* DDR_ACIOCR3 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR3);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR3);
+
+	/* DDR_ACIOCR5 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR5);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR5);
+
+	/* DDR_DX0GCR2 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR2);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR2);
+
+	/* DDR_DX1GCR2 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR2);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR2);
+
+	/* DDR_DX2GCR2 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR2);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR2);
+
+	/* DDR_DX3GCR2 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR2);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR2);
+
+	/* DDR_ZQCR */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ZQCR);
+
+	mmio_write_32(DBSC4_REG_DBPDRGD0, ddr_md == 0 ?
+		      DBSC4_SET_DBPDRGD0_ZQCR_MD19_0 :
+		      DBSC4_SET_DBPDRGD0_ZQCR_MD19_1);
+
+	/* DDR_DX0GCR0 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR0);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR0);
+
+	/* DDR_DX1GCR0 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR0);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR0);
+
+	/* DDR_DX2GCR0 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR0);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR0);
+
+	/* DDR_DX3GCR0 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR0);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR0);
+
+	/* DDR_DX0GCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR1);
+
+	/* DDR_DX1GCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR1);
+
+	/* DDR_DX2GCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR1);
+
+	/* DDR_DX3GCR1 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR1);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR1);
+
+	/* DDR_DX0GCR3 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR3);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR3);
+
+	/* DDR_DX1GCR3 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR3);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR3);
+
+	/* DDR_DX2GCR3 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR3);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR3);
+
+	/* DDR_DX3GCR3 */
+	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR3);
+	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR3);
+
+	/* Write disable */
+	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_DISABLE);
+}
+
+void __attribute__ ((section(".system_ram"))) __attribute__ ((noinline))
+rcar_pwrc_go_suspend_to_ram(void)
+{
+#if PMIC_ROHM_BD9571
+	int32_t rc = -1, qllm = -1;
+	uint8_t mode;
+	uint32_t i;
+#endif
+	uint32_t reg, product;
+
+	reg = mmio_read_32(RCAR_PRR);
+	product = reg & PRR_PRODUCT_MASK;
+
+	if (product != PRR_PRODUCT_E3)
+		rcar_pwrc_set_self_refresh();
+	else
+		rcar_pwrc_set_self_refresh_e3();
+
+#if PMIC_ROHM_BD9571
+	/* Set QLLM Cnt Disable */
+	for (i = 0; (i < PMIC_RETRY_MAX) && (qllm != 0); i++)
+		qllm = rcar_iic_dvfs_send(PMIC, PMIC_QLLM_CNT, 0);
+
+	/* Set trigger of power down to PMIV */
+	for (i = 0; (i < PMIC_RETRY_MAX) && (rc != 0) && (qllm == 0); i++) {
+		rc = rcar_iic_dvfs_receive(PMIC, PMIC_BKUP_MODE_CNT, &mode);
+		if (rc == 0) {
+			mode |= BIT_BKUP_CTRL_OUT;
+			rc = rcar_iic_dvfs_send(PMIC, PMIC_BKUP_MODE_CNT, mode);
+		}
+	}
+#endif
+	wfi();
+
+	while (1)
+		;
+}
+
+void rcar_pwrc_set_suspend_to_ram(void)
+{
+	uintptr_t jump = (uintptr_t) &rcar_pwrc_go_suspend_to_ram;
+	uintptr_t stack = (uintptr_t) (DEVICE_SRAM_STACK_BASE +
+				       DEVICE_SRAM_STACK_SIZE);
+	uint32_t sctlr;
+
+	rcar_pwrc_save_timer_state();
+
+	/* disable MMU */
+	sctlr = (uint32_t) read_sctlr_el3();
+	sctlr &= (uint32_t) ~SCTLR_EL3_M_BIT;
+	write_sctlr_el3((uint64_t) sctlr);
+
+	rcar_pwrc_switch_stack(jump, stack, NULL);
+}
+
+void rcar_pwrc_init_suspend_to_ram(void)
+{
+#if PMIC_ROHM_BD9571
+	uint8_t mode;
+
+	if (rcar_iic_dvfs_receive(PMIC, PMIC_BKUP_MODE_CNT, &mode))
+		panic();
+
+	mode &= (uint8_t) (~BIT_BKUP_CTRL_OUT);
+	if (rcar_iic_dvfs_send(PMIC, PMIC_BKUP_MODE_CNT, mode))
+		panic();
+#endif
+}
+
+void rcar_pwrc_suspend_to_ram(void)
+{
+#if RCAR_SYSTEM_RESET_KEEPON_DDR
+	int32_t error;
+
+	error = rcar_iic_dvfs_send(PMIC, REG_KEEP10, 0);
+	if (error) {
+		ERROR("Failed send KEEP10 init ret=%d\n", error);
+		return;
+	}
+#endif
+	rcar_pwrc_set_suspend_to_ram();
+}
+#endif
+
+void rcar_pwrc_code_copy_to_system_ram(void)
+{
+	int ret __attribute__ ((unused));	/* in assert */
+	uint32_t attr;
+	struct device_sram_t {
+		uintptr_t base;
+		size_t len;
+	} sram = {
+		.base = (uintptr_t) DEVICE_SRAM_BASE,
+		.len = DEVICE_SRAM_SIZE,
+	};
+	struct ddr_code_t {
+		void *base;
+		size_t len;
+	} code = {
+		.base = (void *) SRAM_COPY_START,
+		.len = SYSTEM_RAM_END - SYSTEM_RAM_START,
+	};
+
+	attr = MT_MEMORY | MT_RW | MT_SECURE | MT_EXECUTE_NEVER;
+	ret = xlat_change_mem_attributes(sram.base, sram.len, attr);
+	assert(ret == 0);
+
+	memcpy((void *)sram.base, code.base, code.len);
+	flush_dcache_range((uint64_t) sram.base, code.len);
+
+	attr = MT_MEMORY | MT_RO | MT_SECURE | MT_EXECUTE;
+	ret = xlat_change_mem_attributes(sram.base, sram.len, attr);
+	assert(ret == 0);
+
+	/* Invalidate instruction cache */
+	plat_invalidate_icache();
+	dsb();
+	isb();
+}
+
+uint32_t rcar_pwrc_get_cluster(void)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(RCAR_PRR);
+
+	if (reg & (1U << (STATE_CA53_CPU + RCAR_CA53CPU_NUM_MAX)))
+		return RCAR_CLUSTER_CA57;
+
+	if (reg & (1U << (STATE_CA57_CPU + RCAR_CA57CPU_NUM_MAX)))
+		return RCAR_CLUSTER_CA53;
+
+	return RCAR_CLUSTER_A53A57;
+}
+
+uint32_t rcar_pwrc_get_mpidr_cluster(uint64_t mpidr)
+{
+	uint32_t c = rcar_pwrc_get_cluster();
+
+	if (IS_A53A57(c)) {
+		if (mpidr & MPIDR_CLUSTER_MASK)
+			return RCAR_CLUSTER_CA53;
+
+		return RCAR_CLUSTER_CA57;
+	}
+
+	return c;
+}
+
+#if RCAR_LSI == RCAR_D3
+uint32_t rcar_pwrc_get_cpu_num(uint32_t c)
+{
+	return 1;
+}
+#else
+uint32_t rcar_pwrc_get_cpu_num(uint32_t c)
+{
+	uint32_t reg = mmio_read_32(RCAR_PRR);
+	uint32_t count = 0, i;
+
+	if (IS_A53A57(c) || IS_CA53(c)) {
+		if (reg & (1 << (STATE_CA53_CPU + RCAR_CA53CPU_NUM_MAX)))
+			goto count_ca57;
+
+		for (i = 0; i < RCAR_CA53CPU_NUM_MAX; i++) {
+			if (reg & (1 << (STATE_CA53_CPU + i)))
+				continue;
+			count++;
+		}
+	}
+
+count_ca57:
+	if (IS_A53A57(c) || IS_CA57(c)) {
+		if (reg & (1U << (STATE_CA57_CPU + RCAR_CA57CPU_NUM_MAX)))
+			goto done;
+
+		for (i = 0; i < RCAR_CA57CPU_NUM_MAX; i++) {
+			if (reg & (1 << (STATE_CA57_CPU + i)))
+				continue;
+			count++;
+		}
+	}
+
+done:
+	return count;
+}
+#endif
+
+int32_t rcar_pwrc_cpu_on_check(uint64_t mpidr)
+{
+	uint64_t i;
+	uint64_t j;
+	uint64_t cpu_count;
+	uintptr_t reg_PSTR;
+	uint32_t status;
+	uint64_t my_cpu;
+	int32_t rtn;
+	uint32_t my_cluster_type;
+	const uint32_t cluster_type[PLATFORM_CLUSTER_COUNT] = {
+			RCAR_CLUSTER_CA53,
+			RCAR_CLUSTER_CA57
+	};
+	const uintptr_t registerPSTR[PLATFORM_CLUSTER_COUNT] = {
+			RCAR_CA53PSTR,
+			RCAR_CA57PSTR
+	};
+
+	my_cluster_type = rcar_pwrc_get_cluster();
+
+	rtn = 0;
+	my_cpu = mpidr & ((uint64_t)(MPIDR_CPU_MASK));
+	for (i = 0U; i < ((uint64_t)(PLATFORM_CLUSTER_COUNT)); i++) {
+		cpu_count = rcar_pwrc_get_cpu_num(cluster_type[i]);
+		reg_PSTR = registerPSTR[i];
+		for (j = 0U; j < cpu_count; j++) {
+			if ((my_cluster_type != cluster_type[i]) || (my_cpu != j)) {
+				status = mmio_read_32(reg_PSTR) >> (j * 4U);
+				if ((status & 0x00000003U) == 0U) {
+					rtn--;
+				}
+			}
+		}
+	}
+
+	return rtn;
+}
diff --git a/drivers/renesas/common/pwrc/pwrc.h b/drivers/renesas/common/pwrc/pwrc.h
new file mode 100644
index 0000000..f73099b
--- /dev/null
+++ b/drivers/renesas/common/pwrc/pwrc.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PWRC_H
+#define PWRC_H
+
+#define PPOFFR_OFF		0x0
+#define PPONR_OFF		0x4
+#define PCOFFR_OFF		0x8
+#define PWKUPR_OFF		0xc
+#define PSYSR_OFF		0x10
+
+#define PWKUPR_WEN		(1ull << 31)
+
+#define PSYSR_AFF_L2		(1U << 31)
+#define PSYSR_AFF_L1		(1 << 30)
+#define PSYSR_AFF_L0		(1 << 29)
+#define PSYSR_WEN		(1 << 28)
+#define PSYSR_PC		(1 << 27)
+#define PSYSR_PP		(1 << 26)
+
+#define PSYSR_WK_SHIFT		(24)
+#define PSYSR_WK_MASK		(0x3)
+#define PSYSR_WK(x)		(((x) >> PSYSR_WK_SHIFT) & PSYSR_WK_MASK)
+
+#define WKUP_COLD		0x0
+#define WKUP_RESET		0x1
+#define WKUP_PPONR		0x2
+#define WKUP_GICREQ		0x3
+
+#define RCAR_INVALID		(0xffffffffU)
+#define PSYSR_INVALID		0xffffffff
+
+#define RCAR_CLUSTER_A53A57	(0U)
+#define RCAR_CLUSTER_CA53	(1U)
+#define RCAR_CLUSTER_CA57	(2U)
+
+#ifndef __ASSEMBLER__
+void rcar_pwrc_disable_interrupt_wakeup(uint64_t mpidr);
+void rcar_pwrc_enable_interrupt_wakeup(uint64_t mpidr);
+void rcar_pwrc_clusteroff(uint64_t mpidr);
+void rcar_pwrc_cpuoff(uint64_t mpidr);
+void rcar_pwrc_cpuon(uint64_t mpidr);
+int32_t rcar_pwrc_cpu_on_check(uint64_t mpidr);
+void rcar_pwrc_setup(void);
+
+uint32_t rcar_pwrc_get_cpu_wkr(uint64_t mpidr);
+uint32_t rcar_pwrc_status(uint64_t mpidr);
+uint32_t rcar_pwrc_get_cluster(void);
+uint32_t rcar_pwrc_get_mpidr_cluster(uint64_t mpidr);
+uint32_t rcar_pwrc_get_cpu_num(uint32_t cluster_type);
+void rcar_pwrc_restore_timer_state(void);
+void plat_secondary_reset(void);
+
+void rcar_pwrc_code_copy_to_system_ram(void);
+
+#if !PMIC_ROHM_BD9571
+void rcar_pwrc_system_reset(void);
+#endif
+
+#if RCAR_SYSTEM_SUSPEND
+void rcar_pwrc_go_suspend_to_ram(void);
+void rcar_pwrc_set_suspend_to_ram(void);
+void rcar_pwrc_init_suspend_to_ram(void);
+void rcar_pwrc_suspend_to_ram(void);
+#endif
+
+extern uint32_t rcar_pwrc_switch_stack(uintptr_t jump, uintptr_t stack,
+				       void *arg);
+#endif
+
+#endif /* PWRC_H */
diff --git a/drivers/renesas/rcar/qos/qos_reg.h b/drivers/renesas/common/qos_reg.h
similarity index 100%
rename from drivers/renesas/rcar/qos/qos_reg.h
rename to drivers/renesas/common/qos_reg.h
diff --git a/drivers/renesas/rcar/rom/rom_api.c b/drivers/renesas/common/rom/rom_api.c
similarity index 100%
rename from drivers/renesas/rcar/rom/rom_api.c
rename to drivers/renesas/common/rom/rom_api.c
diff --git a/drivers/renesas/rcar/rom/rom_api.h b/drivers/renesas/common/rom/rom_api.h
similarity index 100%
rename from drivers/renesas/rcar/rom/rom_api.h
rename to drivers/renesas/common/rom/rom_api.h
diff --git a/drivers/renesas/rcar/rpc/rpc_driver.c b/drivers/renesas/common/rpc/rpc_driver.c
similarity index 100%
rename from drivers/renesas/rcar/rpc/rpc_driver.c
rename to drivers/renesas/common/rpc/rpc_driver.c
diff --git a/drivers/renesas/rcar/rpc/rpc_registers.h b/drivers/renesas/common/rpc/rpc_registers.h
similarity index 100%
rename from drivers/renesas/rcar/rpc/rpc_registers.h
rename to drivers/renesas/common/rpc/rpc_registers.h
diff --git a/drivers/renesas/common/scif/scif.S b/drivers/renesas/common/scif/scif.S
new file mode 100644
index 0000000..72b5b4b
--- /dev/null
+++ b/drivers/renesas/common/scif/scif.S
@@ -0,0 +1,341 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <console_macros.S>
+#include <drivers/renesas/rcar/console/console.h>
+
+#define SCIF_INTERNAL_CLK	0
+#define SCIF_EXTARNAL_CLK	1
+#define SCIF_CLK		SCIF_INTERNAL_CLK
+
+/* product register */
+#define PRR			(0xFFF00044)
+#define PRR_PRODUCT_MASK	(0x00007F00)
+#define PRR_CUT_MASK		(0x000000FF)
+#define PRR_PRODUCT_H3_VER_10	(0x00004F00)
+#define PRR_PRODUCT_E3		(0x00005700)
+#define PRR_PRODUCT_D3		(0x00005800)
+
+/* module stop */
+#define CPG_BASE		(0xE6150000)
+#define CPG_SMSTPCR2		(0x0138)
+#define CPG_SMSTPCR3		(0x013C)
+#define CPG_MSTPSR2		(0x0040)
+#define CPG_MSTPSR3		(0x0048)
+#define MSTP207			(1 << 7)
+#define MSTP310			(1 << 10)
+#define CPG_CPGWPR		(0x0900)
+
+/* scif */
+#define SCIF0_BASE		(0xE6E60000)
+#define SCIF2_BASE		(0xE6E88000)
+#define SCIF_SCSMR		(0x00)
+#define SCIF_SCBRR		(0x04)
+#define SCIF_SCSCR		(0x08)
+#define SCIF_SCFTDR		(0x0C)
+#define SCIF_SCFSR		(0x10)
+#define SCIF_SCFRDR		(0x14)
+#define SCIF_SCFCR		(0x18)
+#define SCIF_SCFDR		(0x1C)
+#define SCIF_SCSPTR		(0x20)
+#define SCIF_SCLSR		(0x24)
+#define SCIF_DL			(0x30)
+#define SCIF_CKS		(0x34)
+
+#if RCAR_LSI == RCAR_V3M
+#define SCIF_BASE		SCIF0_BASE
+#define CPG_SMSTPCR		CPG_SMSTPCR2
+#define CPG_MSTPSR		CPG_MSTPSR2
+#define MSTP			MSTP207
+#else
+#define SCIF_BASE		SCIF2_BASE
+#define CPG_SMSTPCR		CPG_SMSTPCR3
+#define CPG_MSTPSR		CPG_MSTPSR3
+#define MSTP			MSTP310
+#endif
+
+/* mode pin */
+#define RST_MODEMR		(0xE6160060)
+#define MODEMR_MD12		(0x00001000)
+
+#define SCSMR_CA_MASK		(1 << 7)
+#define SCSMR_CA_ASYNC		(0x0000)
+#define SCSMR_CHR_MASK		(1 << 6)
+#define SCSMR_CHR_8		(0x0000)
+#define SCSMR_PE_MASK		(1 << 5)
+#define SCSMR_PE_DIS		(0x0000)
+#define SCSMR_STOP_MASK		(1 << 3)
+#define SCSMR_STOP_1		(0x0000)
+#define SCSMR_CKS_MASK		(3 << 0)
+#define SCSMR_CKS_DIV1		(0x0000)
+#define SCSMR_INIT_DATA		(SCSMR_CA_ASYNC +	\
+					 SCSMR_CHR_8 +		\
+					 SCSMR_PE_DIS +		\
+					 SCSMR_STOP_1 +		\
+					 SCSMR_CKS_DIV1)
+#define SCBRR_115200BPS		(17)
+#define SCBRR_115200BPS_D3_SSCG	(16)
+#define SCBRR_115200BPS_E3_SSCG	(15)
+#define SCBRR_230400BPS		(8)
+
+#define SCSCR_TE_MASK		(1 << 5)
+#define SCSCR_TE_DIS		(0x0000)
+#define SCSCR_TE_EN		(0x0020)
+#define SCSCR_RE_MASK		(1 << 4)
+#define SCSCR_RE_DIS		(0x0000)
+#define SCSCR_RE_EN		(0x0010)
+#define SCSCR_CKE_MASK		(3 << 0)
+#define SCSCR_CKE_INT		(0x0000)
+#define SCSCR_CKE_BRG		(0x0002)
+#if SCIF_CLK == SCIF_EXTARNAL_CLK
+#define SCSCR_CKE_INT_CLK	(SCSCR_CKE_BRG)
+#else
+#define SCFSR_TEND_MASK		(1 << 6)
+#define SCFSR_TEND_TRANS_END	(0x0040)
+#define SCSCR_CKE_INT_CLK	(SCSCR_CKE_INT)
+#endif
+#define SCFSR_INIT_DATA		(0x0000)
+#define SCFCR_TTRG_MASK		(3 << 4)
+#define SCFCR_TTRG_8		(0x0000)
+#define SCFCR_TTRG_0		(0x0030)
+#define SCFCR_TFRST_MASK	(1 << 2)
+#define SCFCR_TFRST_DIS		(0x0000)
+#define SCFCR_TFRST_EN		(0x0004)
+#define SCFCR_RFRS_MASK		(1 << 1)
+#define SCFCR_RFRS_DIS		(0x0000)
+#define SCFCR_RFRS_EN		(0x0002)
+#define SCFCR_INIT_DATA		(SCFCR_TTRG_8)
+#define SCFDR_T_MASK		(0x1f << 8)
+#define DL_INIT_DATA		(8)
+#define CKS_CKS_DIV_MASK	(1 << 15)
+#define CKS_CKS_DIV_CLK		(0x0000)
+#define CKS_XIN_MASK		(1 << 14)
+#define CKS_XIN_SCIF_CLK	(0x0000)
+#define CKS_INIT_DATA		(CKS_CKS_DIV_CLK + CKS_XIN_SCIF_CLK)
+
+	.globl	console_rcar_register
+	.globl	console_rcar_init
+	.globl	console_rcar_putc
+	.globl	console_rcar_flush
+
+	/*
+	 * -----------------------------------------------
+	 * int console_rcar_register(
+	 *      uintptr_t base, uint32_t clk, uint32_t baud,
+	 *      console_t *console)
+	 * Function to initialize and register a new rcar
+	 * console. Storage passed in for the console struct
+	 * *must* be persistent (i.e. not from the stack).
+	 * In: x0 - UART register base address
+	 *     w1 - UART clock in Hz
+	 *     w2 - Baud rate
+	 *     x3 - pointer to empty console_t struct
+	 * Out: return 1 on success, 0 on error
+	 * Clobber list : x0, x1, x2, x6, x7, x14
+	 * -----------------------------------------------
+	 */
+func console_rcar_register
+	mov	x7, x30
+	mov	x6, x3
+	cbz	x6, register_fail
+	str	x0, [x6, #CONSOLE_T_BASE]
+
+	bl	console_rcar_init
+
+	mov	x0, x6
+	mov	x30, x7
+	finish_console_register rcar, putc=1, getc=0, flush=1
+
+register_fail:
+	ret	x7
+endfunc console_rcar_register
+
+	/*
+	 * int console_rcar_init(unsigned long base_addr,
+	 * unsigned int uart_clk, unsigned int baud_rate)
+	 * Function to initialize the console without a
+	 * C Runtime to print debug information. This
+	 * function will be accessed by console_rcar_register
+	 * and crash reporting.
+	 * In: x0 - console base address
+	 *     w1 - Uart clock in Hz
+	 *     w2 - Baud rate
+	 * Out: return 1 on success
+	 * Clobber list : x1, x2
+	 */
+func console_rcar_init
+	ldr	x0, =CPG_BASE
+	ldr	w1, [x0, #CPG_SMSTPCR]
+	and	w1, w1, #~MSTP
+	mvn	w2, w1
+	str	w2, [x0, #CPG_CPGWPR]
+	str	w1, [x0, #CPG_SMSTPCR]
+5:
+	ldr w1, [x0, #CPG_MSTPSR]
+	and w1, w1, #MSTP
+	cbnz w1, 5b
+
+	ldr	x0, =SCIF_BASE
+	/* Clear bits TE and RE in SCSCR to 0 */
+	mov	w1, #(SCSCR_TE_DIS + SCSCR_RE_DIS)
+	strh	w1, [x0, #SCIF_SCSCR]
+	/* Set bits TFRST and RFRST in SCFCR to 1 */
+	ldrh	w1, [x0, #SCIF_SCFCR]
+	orr	w1, w1, #(SCFCR_TFRST_EN + SCFCR_RFRS_EN)
+	strh	w1, [x0, #SCIF_SCFCR]
+	/*
+	 * Read flags of ER, DR, BRK, and RDF in SCFSR and those of TO and ORER
+	 * in SCLSR, then clear them to 0
+	 */
+	mov	w1, #SCFSR_INIT_DATA
+	strh	w1, [x0, #SCIF_SCFSR]
+	mov	w1, #0
+	strh	w1, [x0, #SCIF_SCLSR]
+	/* Set bits CKE[1:0] in SCSCR */
+	ldrh	w1, [x0, #SCIF_SCSCR]
+	and	w1, w1, #~SCSCR_CKE_MASK
+	mov	w2, #SCSCR_CKE_INT_CLK
+	orr	w1, w1, w2
+	strh	w1, [x0, #SCIF_SCSCR]
+	/* Set data transfer format in SCSMR */
+	mov	w1, #SCSMR_INIT_DATA
+	strh	w1, [x0, #SCIF_SCSMR]
+	/* Set value in SCBRR */
+#if SCIF_CLK == SCIF_INTERNAL_CLK
+	ldr	x1, =PRR
+	ldr	w1, [x1]
+	and	w1, w1, #(PRR_PRODUCT_MASK | PRR_CUT_MASK)
+	mov	w2, #PRR_PRODUCT_H3_VER_10
+	cmp	w1, w2
+	beq	3f
+	and	w1, w1, #PRR_PRODUCT_MASK
+	mov	w2, #PRR_PRODUCT_D3
+	cmp	w1, w2
+	beq	5f
+	and	w1, w1, #PRR_PRODUCT_MASK
+	mov	w2, #PRR_PRODUCT_E3
+	cmp	w1, w2
+	bne	4f
+
+	/* When SSCG(MD12) on (E3) */
+	ldr	x1, =RST_MODEMR
+	ldr	w1, [x1]
+	and	w1, w1, #MODEMR_MD12
+	mov	w2, #MODEMR_MD12
+	cmp	w1, w2
+	bne	4f
+
+	/* When SSCG(MD12) on (E3) */
+	mov	w1, #SCBRR_115200BPS_E3_SSCG
+	b	2f
+5:
+	/* In case of D3 */
+	ldr	x1, =RST_MODEMR
+	ldr	w1, [x1]
+	and	w1, w1, #MODEMR_MD12
+	mov	w2, #MODEMR_MD12
+	cmp	w1, w2
+	bne	4f
+
+	/* When SSCG(MD12) on (D3) */
+	mov	w1, #SCBRR_115200BPS_D3_SSCG
+	b	2f
+4:
+	/* In case of H3/M3/M3N or when SSCG(MD12) is off in E3/D3 */
+	mov	w1, #SCBRR_115200BPS
+	b	2f
+3:
+	mov	w1, #SCBRR_230400BPS
+2:
+	strb	w1, [x0, SCIF_SCBRR]
+#else
+	mov	w1, #DL_INIT_DATA
+	strh	w1, [x0, #SCIF_DL]
+	mov	w1, #CKS_INIT_DATA
+	strh	w1, [x0, #SCIF_CKS]
+#endif
+	/* 1-bit interval elapsed */
+	mov	w1, #100
+1:
+	subs	w1, w1, #1
+	cbnz	w1, 1b
+	/*
+	 * Set bits RTRG[1:0], TTRG[1:0], and MCE in SCFCR
+	 * Clear bits FRST and RFRST to 0
+	 */
+	mov	w1, #SCFCR_INIT_DATA
+	strh	w1, [x0, #SCIF_SCFCR]
+	/* Set bits TE and RE in SCSCR to 1 */
+	ldrh	w1, [x0, #SCIF_SCSCR]
+	orr	w1, w1, #(SCSCR_TE_EN + SCSCR_RE_EN)
+	strh	w1, [x0, #SCIF_SCSCR]
+	mov	x0, #1
+
+	ret
+endfunc console_rcar_init
+
+	/*
+	 * int console_rcar_putc(int c, unsigned int base_addr)
+	 * Function to output a character over the console. It
+	 * returns the character printed on success or -1 on error.
+	 * In : w0 - character to be printed
+	 *      x1 - pointer to console_t structure
+	 * Out : return -1 on error else return character.
+	 * Clobber list : x2
+	 */
+func console_rcar_putc
+	ldr	x1, =SCIF_BASE
+	cmp	w0, #0xA
+	/* Prepend '\r' to '\n' */
+	bne	2f
+1:
+	/* Check if the transmit FIFO is full */
+	ldrh	w2, [x1, #SCIF_SCFDR]
+	ubfx	w2, w2, #8, #5
+	cmp	w2, #16
+	bcs	1b
+	mov	w2, #0x0D
+	strb	w2, [x1, #SCIF_SCFTDR]
+2:
+	/* Check if the transmit FIFO is full */
+	ldrh	w2, [x1, #SCIF_SCFDR]
+	ubfx	w2, w2, #8, #5
+	cmp	w2, #16
+	bcs	2b
+	strb	w0, [x1, #SCIF_SCFTDR]
+
+	/* Clear TEND flag */
+	ldrh	w2, [x1, #SCIF_SCFSR]
+	and	w2, w2, #~SCFSR_TEND_MASK
+	strh	w2, [x1, #SCIF_SCFSR]
+
+	ret
+endfunc console_rcar_putc
+
+	/*
+	 * void console_rcar_flush(void)
+	 * Function to force a write of all buffered
+	 * data that hasn't been output. It returns void
+	 * Clobber list : x0, x1
+	 */
+func console_rcar_flush
+	ldr	x0, =SCIF_BASE
+1:
+	/* Check TEND flag */
+	ldrh	w1, [x0, #SCIF_SCFSR]
+	and	w1, w1, #SCFSR_TEND_MASK
+	cmp	w1, #SCFSR_TEND_TRANS_END
+	bne	1b
+
+	ldr	x0, =SCIF_BASE
+	ldrh	w1, [x0, #SCIF_SCSCR]
+	and	w1, w1, #~(SCSCR_TE_EN + SCSCR_RE_EN)
+	strh	w1, [x0, #SCIF_SCSCR]
+
+	ret
+endfunc console_rcar_flush
diff --git a/drivers/renesas/common/watchdog/swdt.c b/drivers/renesas/common/watchdog/swdt.c
new file mode 100644
index 0000000..29ef6f4
--- /dev/null
+++ b/drivers/renesas/common/watchdog/swdt.c
@@ -0,0 +1,169 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/arm/gicv2.h>
+#include <lib/mmio.h>
+
+#include "rcar_def.h"
+
+extern void gicd_set_icenabler(uintptr_t base, unsigned int id);
+
+#define RST_BASE			(0xE6160000U)
+#define RST_WDTRSTCR			(RST_BASE + 0x0054U)
+#define SWDT_BASE			(0xE6030000U)
+#define SWDT_WTCNT			(SWDT_BASE + 0x0000U)
+#define SWDT_WTCSRA			(SWDT_BASE + 0x0004U)
+#define SWDT_WTCSRB			(SWDT_BASE + 0x0008U)
+#define SWDT_GICD_BASE			(0xF1010000U)
+#define SWDT_GICC_BASE			(0xF1020000U)
+#define SWDT_GICD_CTLR			(SWDT_GICD_BASE + 0x0000U)
+#define SWDT_GICD_IGROUPR		(SWDT_GICD_BASE + 0x0080U)
+#define SWDT_GICD_ISPRIORITYR		(SWDT_GICD_BASE + 0x0400U)
+#define SWDT_GICC_CTLR			(SWDT_GICC_BASE + 0x0000U)
+#define SWDT_GICC_PMR			(SWDT_GICC_BASE + 0x0004U)
+#define SWDT_GICD_ITARGETSR		(SWDT_GICD_BASE + 0x0800U)
+#define IGROUPR_NUM			(16U)
+#define ISPRIORITY_NUM			(128U)
+#define ITARGET_MASK			(0x03U)
+
+#define WDTRSTCR_UPPER_BYTE		(0xA55A0000U)
+#define WTCSRA_UPPER_BYTE		(0xA5A5A500U)
+#define WTCSRB_UPPER_BYTE		(0xA5A5A500U)
+#define WTCNT_UPPER_BYTE		(0x5A5A0000U)
+#define WTCNT_RESET_VALUE		(0xF488U)
+#define WTCSRA_BIT_CKS			(0x0007U)
+#define WTCSRB_BIT_CKS			(0x003FU)
+#define SWDT_RSTMSK			(1U << 1U)
+#define WTCSRA_WOVFE			(1U << 3U)
+#define WTCSRA_WRFLG			(1U << 5U)
+#define SWDT_ENABLE			(1U << 7U)
+
+#define WDTRSTCR_MASK_ALL		(0x0000FFFFU)
+#define WTCSRA_MASK_ALL			(0x000000FFU)
+#define WTCNT_INIT_DATA			(WTCNT_UPPER_BYTE + WTCNT_RESET_VALUE)
+#define WTCSRA_INIT_DATA		(WTCSRA_UPPER_BYTE + 0x0FU)
+#define WTCSRB_INIT_DATA		(WTCSRB_UPPER_BYTE + 0x21U)
+
+#if RCAR_LSI == RCAR_D3
+#define WTCNT_COUNT_8p13k		(0x10000U - 40760U)
+#else
+#define WTCNT_COUNT_8p13k		(0x10000U - 40687U)
+#endif
+#define WTCNT_COUNT_8p13k_H3VER10	(0x10000U - 20343U)
+#define WTCNT_COUNT_8p22k		(0x10000U - 41115U)
+#define WTCNT_COUNT_7p81k		(0x10000U - 39062U)
+#define WTCSRA_CKS_DIV16		(0x00000002U)
+
+static void swdt_disable(void)
+{
+	uint32_t rmsk;
+
+	rmsk = mmio_read_32(RST_WDTRSTCR) & WDTRSTCR_MASK_ALL;
+	rmsk |= SWDT_RSTMSK;
+	mmio_write_32(RST_WDTRSTCR, WDTRSTCR_UPPER_BYTE | rmsk);
+
+	mmio_write_32(SWDT_WTCNT, WTCNT_INIT_DATA);
+	mmio_write_32(SWDT_WTCSRA, WTCSRA_INIT_DATA);
+	mmio_write_32(SWDT_WTCSRB, WTCSRB_INIT_DATA);
+
+	/* Set the interrupt clear enable register */
+	gicd_set_icenabler(RCAR_GICD_BASE, ARM_IRQ_SEC_WDT);
+}
+
+void rcar_swdt_init(void)
+{
+	uint32_t rmsk, sr;
+#if (RCAR_LSI != RCAR_E3) && (RCAR_LSI != RCAR_D3) && (RCAR_LSI != RZ_G2E)
+	uint32_t reg, val, product_cut, chk_data;
+
+	reg = mmio_read_32(RCAR_PRR);
+	product_cut = reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+
+	reg = mmio_read_32(RCAR_MODEMR);
+	chk_data = reg & CHECK_MD13_MD14;
+#endif
+	/* stop watchdog */
+	if (mmio_read_32(SWDT_WTCSRA) & SWDT_ENABLE)
+		mmio_write_32(SWDT_WTCSRA, WTCSRA_UPPER_BYTE);
+
+	mmio_write_32(SWDT_WTCSRA, WTCSRA_UPPER_BYTE |
+		      WTCSRA_WOVFE | WTCSRA_CKS_DIV16);
+
+#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RZ_G2E)
+	mmio_write_32(SWDT_WTCNT, WTCNT_UPPER_BYTE | WTCNT_COUNT_7p81k);
+#elif (RCAR_LSI == RCAR_D3)
+	mmio_write_32(SWDT_WTCNT, WTCNT_UPPER_BYTE | WTCNT_COUNT_8p13k);
+#else
+	val = WTCNT_UPPER_BYTE;
+
+	switch (chk_data) {
+	case MD14_MD13_TYPE_0:
+	case MD14_MD13_TYPE_2:
+		val |= WTCNT_COUNT_8p13k;
+		break;
+	case MD14_MD13_TYPE_1:
+		val |= WTCNT_COUNT_8p22k;
+		break;
+	case MD14_MD13_TYPE_3:
+		val |= product_cut == (PRR_PRODUCT_H3 | PRR_PRODUCT_10) ?
+		    WTCNT_COUNT_8p13k_H3VER10 : WTCNT_COUNT_8p13k;
+		break;
+	default:
+		ERROR("MODEMR ERROR value = %x\n", chk_data);
+		panic();
+		break;
+	}
+
+	mmio_write_32(SWDT_WTCNT, val);
+#endif
+	rmsk = mmio_read_32(RST_WDTRSTCR) & WDTRSTCR_MASK_ALL;
+	rmsk |= SWDT_RSTMSK | WDTRSTCR_UPPER_BYTE;
+	mmio_write_32(RST_WDTRSTCR, rmsk);
+
+	while ((mmio_read_8(SWDT_WTCSRA) & WTCSRA_WRFLG) != 0U)
+		;
+
+	/* Start the System WatchDog Timer */
+	sr = mmio_read_32(SWDT_WTCSRA) & WTCSRA_MASK_ALL;
+	mmio_write_32(SWDT_WTCSRA, (WTCSRA_UPPER_BYTE | sr | SWDT_ENABLE));
+}
+
+void rcar_swdt_release(void)
+{
+	uintptr_t itarget = SWDT_GICD_ITARGETSR +
+	    (ARM_IRQ_SEC_WDT & ~ITARGET_MASK);
+	uint32_t i;
+
+	/* Disable FIQ interrupt */
+	write_daifset(DAIF_FIQ_BIT);
+	/* FIQ interrupts are not taken to EL3 */
+	write_scr_el3(read_scr_el3() & ~SCR_FIQ_BIT);
+
+	swdt_disable();
+	gicv2_cpuif_disable();
+
+	for (i = 0; i < IGROUPR_NUM; i++)
+		mmio_write_32(SWDT_GICD_IGROUPR + i * 4, 0U);
+
+	for (i = 0; i < ISPRIORITY_NUM; i++)
+		mmio_write_32(SWDT_GICD_ISPRIORITYR + i * 4, 0U);
+
+	mmio_write_32(itarget, 0U);
+	mmio_write_32(SWDT_GICD_CTLR, 0U);
+	mmio_write_32(SWDT_GICC_CTLR, 0U);
+	mmio_write_32(SWDT_GICC_PMR, 0U);
+}
+
+void rcar_swdt_exec(uint64_t p)
+{
+	gicv2_end_of_interrupt(ARM_IRQ_SEC_WDT);
+	rcar_swdt_release();
+	ERROR("\n");
+	ERROR("System WDT overflow, occurred address is %p\n", (void *)p);
+	panic();
+}
diff --git a/drivers/renesas/rcar/auth/auth_mod.c b/drivers/renesas/rcar/auth/auth_mod.c
deleted file mode 100644
index ece3462..0000000
--- a/drivers/renesas/rcar/auth/auth_mod.c
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights
- * reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stddef.h>
-
-#include <platform_def.h>
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <lib/mmio.h>
-#include <plat/common/platform.h>
-
-#include "rom_api.h"
-
-typedef int32_t(*secure_boot_api_f) (uint32_t a, uint32_t b, void *c);
-extern int32_t rcar_get_certificate(const int32_t name, uint32_t *cert_addr);
-
-#define	RCAR_IMAGE_ID_MAX	(10)
-#define	RCAR_CERT_MAGIC_NUM	(0xE291F358U)
-#define RCAR_BOOT_KEY_CERT	(0xE6300C00U)
-#define RCAR_BOOT_KEY_CERT_NEW	(0xE6300F00U)
-#define	RST_BASE		(0xE6160000U)
-#define	RST_MODEMR		(RST_BASE + 0x0060U)
-#define	MFISOFTMDR		(0xE6260600U)
-#define	MODEMR_MD5_MASK		(0x00000020U)
-#define	MODEMR_MD5_SHIFT	(5U)
-#define	SOFTMD_BOOTMODE_MASK	(0x00000001U)
-#define	SOFTMD_NORMALBOOT	(0x1U)
-
-static secure_boot_api_f secure_boot_api;
-
-int auth_mod_get_parent_id(unsigned int img_id, unsigned int *parent_id)
-{
-	return 1;
-}
-
-int auth_mod_verify_img(unsigned int img_id, void *ptr, unsigned int len)
-{
-	int32_t ret = 0, index = 0;
-	uint32_t cert_addr = 0U;
-	static const struct img_to_cert_t {
-		uint32_t id;
-		int32_t cert;
-		const char *name;
-	} image[RCAR_IMAGE_ID_MAX] = {
-		{ BL31_IMAGE_ID, SOC_FW_CONTENT_CERT_ID, "BL31" },
-		{ BL32_IMAGE_ID, TRUSTED_OS_FW_CONTENT_CERT_ID, "BL32" },
-		{ BL33_IMAGE_ID, NON_TRUSTED_FW_CONTENT_CERT_ID, "BL33" },
-		{ BL332_IMAGE_ID, BL332_CERT_ID, "BL332" },
-		{ BL333_IMAGE_ID, BL333_CERT_ID, "BL333" },
-		{ BL334_IMAGE_ID, BL334_CERT_ID, "BL334" },
-		{ BL335_IMAGE_ID, BL335_CERT_ID, "BL335" },
-		{ BL336_IMAGE_ID, BL336_CERT_ID, "BL336" },
-		{ BL337_IMAGE_ID, BL337_CERT_ID, "BL337" },
-		{ BL338_IMAGE_ID, BL338_CERT_ID, "BL338" },
-	};
-
-#if IMAGE_BL2
-	switch (img_id) {
-	case TRUSTED_KEY_CERT_ID:
-	case SOC_FW_KEY_CERT_ID:
-	case TRUSTED_OS_FW_KEY_CERT_ID:
-	case NON_TRUSTED_FW_KEY_CERT_ID:
-	case BL332_KEY_CERT_ID:
-	case BL333_KEY_CERT_ID:
-	case BL334_KEY_CERT_ID:
-	case BL335_KEY_CERT_ID:
-	case BL336_KEY_CERT_ID:
-	case BL337_KEY_CERT_ID:
-	case BL338_KEY_CERT_ID:
-	case SOC_FW_CONTENT_CERT_ID:
-	case TRUSTED_OS_FW_CONTENT_CERT_ID:
-	case NON_TRUSTED_FW_CONTENT_CERT_ID:
-	case BL332_CERT_ID:
-	case BL333_CERT_ID:
-	case BL334_CERT_ID:
-	case BL335_CERT_ID:
-	case BL336_CERT_ID:
-	case BL337_CERT_ID:
-	case BL338_CERT_ID:
-		return ret;
-	case BL31_IMAGE_ID:
-	case BL32_IMAGE_ID:
-	case BL33_IMAGE_ID:
-	case BL332_IMAGE_ID:
-	case BL333_IMAGE_ID:
-	case BL334_IMAGE_ID:
-	case BL335_IMAGE_ID:
-	case BL336_IMAGE_ID:
-	case BL337_IMAGE_ID:
-	case BL338_IMAGE_ID:
-		goto verify_image;
-	default:
-		return -1;
-	}
-
-verify_image:
-	for (index = 0; index < RCAR_IMAGE_ID_MAX; index++) {
-		if (img_id != image[index].id)
-			continue;
-
-		ret = rcar_get_certificate(image[index].cert, &cert_addr);
-		break;
-	}
-
-	if (ret || (index == RCAR_IMAGE_ID_MAX)) {
-		ERROR("Verification Failed for image id = %d\n", img_id);
-		return ret;
-	}
-#if RCAR_BL2_DCACHE == 1
-	/* clean and disable */
-	write_sctlr_el3(read_sctlr_el3() & ~SCTLR_C_BIT);
-	dcsw_op_all(DCCISW);
-#endif
-	ret = (mmio_read_32(RCAR_BOOT_KEY_CERT_NEW) == RCAR_CERT_MAGIC_NUM) ?
-	    secure_boot_api(RCAR_BOOT_KEY_CERT_NEW, cert_addr, NULL) :
-	    secure_boot_api(RCAR_BOOT_KEY_CERT, cert_addr, NULL);
-	if (ret)
-		ERROR("Verification Failed 0x%x, %s\n", ret, image[index].name);
-
-#if RCAR_BL2_DCACHE == 1
-	/* enable */
-	write_sctlr_el3(read_sctlr_el3() | SCTLR_C_BIT);
-#endif
-
-#endif
-	return ret;
-}
-
-static int32_t normal_boot_verify(uint32_t a, uint32_t b, void *c)
-{
-	return 0;
-}
-
-void auth_mod_init(void)
-{
-#if RCAR_SECURE_BOOT
-	uint32_t soft_md = mmio_read_32(MFISOFTMDR) & SOFTMD_BOOTMODE_MASK;
-	uint32_t md = mmio_read_32(RST_MODEMR) & MODEMR_MD5_MASK;
-	uint32_t lcs, ret;
-
-	secure_boot_api = (secure_boot_api_f) &rcar_rom_secure_boot_api;
-
-	ret = rcar_rom_get_lcs(&lcs);
-	if (ret) {
-		ERROR("BL2: Failed to get the LCS. (%d)\n", ret);
-		panic();
-	}
-
-	switch (lcs) {
-	case LCS_SE:
-		if (soft_md == SOFTMD_NORMALBOOT)
-			secure_boot_api = &normal_boot_verify;
-		break;
-	case LCS_SD:
-		secure_boot_api = &normal_boot_verify;
-		break;
-	default:
-		if (md >> MODEMR_MD5_SHIFT)
-			secure_boot_api = &normal_boot_verify;
-	}
-
-	NOTICE("BL2: %s boot\n",
-	       secure_boot_api == &normal_boot_verify ? "Normal" : "Secure");
-#else
-	NOTICE("BL2: Normal boot\n");
-	secure_boot_api = &normal_boot_verify;
-#endif
-}
diff --git a/drivers/renesas/rcar/avs/avs_driver.c b/drivers/renesas/rcar/avs/avs_driver.c
deleted file mode 100644
index 647869e..0000000
--- a/drivers/renesas/rcar/avs/avs_driver.c
+++ /dev/null
@@ -1,624 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <lib/mmio.h>
-#include <lib/utils_def.h>
-
-#include "cpg_registers.h"
-#include "avs_driver.h"
-#include "rcar_def.h"
-#include "rcar_private.h"
-
-#if (AVS_SETTING_ENABLE == 1)
-#if PMIC_ROHM_BD9571
-/* Read PMIC register for debug. 1:enable / 0:disable */
-#define AVS_READ_PMIC_REG_ENABLE	0
-/* The re-try number of times of the AVS setting. */
-#define AVS_RETRY_NUM			(1U)
-#endif /* PMIC_ROHM_BD9571 */
-
-/* Base address of Adaptive Voltage Scaling module registers*/
-#define	AVS_BASE			(0xE60A0000U)
-/* Adaptive Dynamic Voltage ADJust Parameter2 registers */
-#define	ADVADJP2			(AVS_BASE + 0x013CU)
-
-/* Mask VOLCOND bit in ADVADJP2 registers */
-#define	ADVADJP2_VOLCOND_MASK		(0x000001FFU)	/* VOLCOND[8:0] */
-
-#if PMIC_ROHM_BD9571
-/* I2C for DVFS bit in CPG registers for module standby and software reset*/
-#define CPG_SYS_DVFS_BIT		(0x04000000U)
-#endif /* PMIC_ROHM_BD9571 */
-/* ADVFS Module bit in CPG registers for module standby and software reset*/
-#define CPG_SYS_ADVFS_BIT		(0x02000000U)
-
-#if PMIC_ROHM_BD9571
-/* Base address of IICDVFS registers*/
-#define	IIC_DVFS_BASE			(0xE60B0000U)
-/* IIC bus data register */
-#define	IIC_ICDR			(IIC_DVFS_BASE + 0x0000U)
-/* IIC bus control register */
-#define	IIC_ICCR			(IIC_DVFS_BASE + 0x0004U)
-/* IIC bus status register */
-#define	IIC_ICSR			(IIC_DVFS_BASE + 0x0008U)
-/* IIC interrupt control register */
-#define	IIC_ICIC			(IIC_DVFS_BASE + 0x000CU)
-/* IIC clock control register low */
-#define	IIC_ICCL			(IIC_DVFS_BASE + 0x0010U)
-/* IIC clock control register high */
-#define	IIC_ICCH			(IIC_DVFS_BASE + 0x0014U)
-
-/* Bit in ICSR register */
-#define ICSR_BUSY			(0x10U)
-#define ICSR_AL				(0x08U)
-#define ICSR_TACK			(0x04U)
-#define ICSR_WAIT			(0x02U)
-#define ICSR_DTE			(0x01U)
-
-/* Bit in ICIC register */
-#define ICIC_TACKE			(0x04U)
-#define ICIC_WAITE			(0x02U)
-#define ICIC_DTEE			(0x01U)
-
-/* I2C bus interface enable */
-#define ICCR_ENABLE			(0x80U)
-/* Start condition */
-#define ICCR_START			(0x94U)
-/* Stop condition */
-#define ICCR_STOP			(0x90U)
-/* Restart condition with change to receive mode change */
-#define ICCR_START_RECV			(0x81U)
-/* Stop condition for receive mode */
-#define ICCR_STOP_RECV			(0xC0U)
-
-/* Low-level period of SCL */
-#define	ICCL_FREQ_8p33M			(0x07U)	/* for CP Phy 8.3333MHz */
-#define	ICCL_FREQ_10M			(0x09U)	/* for CP Phy 10MHz */
-#define	ICCL_FREQ_12p5M			(0x0BU)	/* for CP Phy 12.5MHz */
-#define	ICCL_FREQ_16p66M		(0x0EU)	/* for CP Phy 16.6666MHz */
-/* High-level period of SCL */
-#define	ICCH_FREQ_8p33M			(0x01U)	/* for CP Phy 8.3333MHz */
-#define	ICCH_FREQ_10M			(0x02U)	/* for CP Phy 10MHz */
-#define	ICCH_FREQ_12p5M			(0x03U)	/* for CP Phy 12.5MHz */
-#define	ICCH_FREQ_16p66M		(0x05U)	/* for CP Phy 16.6666MHz */
-
-/* PMIC */
-#define	PMIC_W_SLAVE_ADDRESS		(0x60U)	/* ROHM BD9571 slave address + (W) */
-#define	PMIC_R_SLAVE_ADDRESS		(0x61U)	/* ROHM BD9571 slave address + (R) */
-#define	PMIC_DVFS_SETVID		(0x54U)	/* ROHM BD9571 DVFS SetVID register */
-#endif /* PMIC_ROHM_BD9571  */
-
-/* Individual information */
-#define EFUSE_AVS0			(0U)
-#define EFUSE_AVS_NUM			ARRAY_SIZE(init_vol_tbl)
-
-typedef struct {
-	uint32_t avs;		/* AVS code */
-	uint8_t vol;		/* Voltage */
-} initial_voltage_t;
-
-static const initial_voltage_t init_vol_tbl[] = {
-	/*      AVS code,       RHOM BD9571 DVFS SetVID register */
-	{0x00U, 0x53U},		/* AVS0, 0.83V */
-	{0x01U, 0x52U},		/* AVS1, 0.82V */
-	{0x02U, 0x51U},		/* AVS2, 0.81V */
-	{0x04U, 0x50U},		/* AVS3, 0.80V */
-	{0x08U, 0x4FU},		/* AVS4, 0.79V */
-	{0x10U, 0x4EU},		/* AVS5, 0.78V */
-	{0x20U, 0x4DU},		/* AVS6, 0.77V */
-	{0x40U, 0x4CU}		/* AVS7, 0.76V */
-};
-
-#if PMIC_ROHM_BD9571
-/* Kind of AVS settings status */
-typedef enum {
-	avs_status_none = 0,
-	avs_status_init,
-	avs_status_start_condition,
-	avs_status_set_slave_addr,
-	avs_status_write_reg_addr,
-	avs_status_write_reg_data,
-	avs_status_stop_condition,
-	avs_status_end,
-	avs_status_complete,
-	avs_status_al_start,
-	avs_status_al_transfer,
-	avs_status_nack,
-	avs_status_error_stop,
-	ave_status_error_end
-} avs_status_t;
-
-/* Kind of AVS error */
-typedef enum {
-	avs_error_none = 0,
-	avs_error_al,
-	avs_error_nack
-} avs_error_t;
-
-static avs_status_t avs_status;
-static uint32_t avs_retry;
-#endif /* PMIC_ROHM_BD9571  */
-static uint32_t efuse_avs = EFUSE_AVS0;
-
-#if PMIC_ROHM_BD9571
-/* prototype */
-static avs_error_t avs_check_error(void);
-static void avs_set_iic_clock(void);
-#if AVS_READ_PMIC_REG_ENABLE == 1
-static uint8_t avs_read_pmic_reg(uint8_t addr);
-static void avs_poll(uint8_t bit_pos, uint8_t val);
-#endif
-#endif /* PMIC_ROHM_BD9571 */
-#endif /* (AVS_SETTING_ENABLE==1) */
-
-/*
- * Initialize to enable the AVS setting.
- */
-void rcar_avs_init(void)
-{
-#if (AVS_SETTING_ENABLE == 1)
-	uint32_t val;
-
-#if PMIC_ROHM_BD9571
-	/* Initialize AVS status */
-	avs_status = avs_status_init;
-#endif /* PMIC_ROHM_BD9571 */
-
-	/* Enable clock supply to ADVFS. */
-	mstpcr_write(CPG_SMSTPCR9, CPG_MSTPSR9, CPG_SYS_ADVFS_BIT);
-
-	/* Read AVS code (Initial values are derived from eFuse) */
-	val = mmio_read_32(ADVADJP2) & ADVADJP2_VOLCOND_MASK;
-
-	for (efuse_avs = 0U; efuse_avs < EFUSE_AVS_NUM; efuse_avs++) {
-		if (val == init_vol_tbl[efuse_avs].avs)
-			break;
-	}
-
-	if (efuse_avs >= EFUSE_AVS_NUM)
-		efuse_avs = EFUSE_AVS0;	/* Not applicable */
-#if PMIC_ROHM_BD9571
-	/* Enable clock supply to DVFS. */
-	mstpcr_write(CPG_SMSTPCR9, CPG_MSTPSR9, CPG_SYS_DVFS_BIT);
-
-	/* Disable I2C module and All internal registers initialized. */
-	mmio_write_8(IIC_ICCR, 0x00U);
-	while ((mmio_read_8(IIC_ICCR) & ICCR_ENABLE) != 0U) {
-		/* Disable I2C module and All internal registers initialized. */
-		mmio_write_8(IIC_ICCR, 0x00U);
-	}
-
-	/* Set next status */
-	avs_status = avs_status_start_condition;
-
-#endif /* PMIC_ROHM_BD9571 */
-#endif /* (AVS_SETTING_ENABLE==1) */
-}
-
-/*
- * Set the value of register corresponding to the voltage
- * by transfer of I2C to PIMC.
- */
-void rcar_avs_setting(void)
-{
-#if (AVS_SETTING_ENABLE == 1)
-#if PMIC_ROHM_BD9571
-	avs_error_t err;
-
-	switch (avs_status) {
-	case avs_status_start_condition:
-		/* Set ICCR.ICE=1 to activate the I2C module. */
-		mmio_write_8(IIC_ICCR, mmio_read_8(IIC_ICCR) | ICCR_ENABLE);
-		/* Set frequency of 400kHz */
-		avs_set_iic_clock();
-		/* Set ICIC.TACKE=1, ICIC.WAITE=1, ICIC.DTEE=1 to */
-		/* enable interrupt control.                      */
-		mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
-			     | ICIC_TACKE | ICIC_WAITE | ICIC_DTEE);
-		/* Write H'94 in ICCR to issue start condition */
-		mmio_write_8(IIC_ICCR, ICCR_START);
-		/* Set next status */
-		avs_status = avs_status_set_slave_addr;
-		break;
-	case avs_status_set_slave_addr:
-		/* Check error. */
-		err = avs_check_error();
-		if (err == avs_error_al) {
-			/* Recovery sequence of just after start. */
-			avs_status = avs_status_al_start;
-		} else if (err == avs_error_nack) {
-			/* Recovery sequence of detected NACK */
-			avs_status = avs_status_nack;
-		} else {
-			/* Was data transmission enabled ? */
-			if ((mmio_read_8(IIC_ICSR) & ICSR_DTE) == ICSR_DTE) {
-				/* Clear ICIC.DTEE to disable a DTE interrupt */
-				mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
-					     & (uint8_t) (~ICIC_DTEE));
-				/* Send PMIC slave address + (W) */
-				mmio_write_8(IIC_ICDR, PMIC_W_SLAVE_ADDRESS);
-				/* Set next status */
-				avs_status = avs_status_write_reg_addr;
-			}
-		}
-		break;
-	case avs_status_write_reg_addr:
-		/* Check error. */
-		err = avs_check_error();
-		if (err == avs_error_al) {
-			/* Recovery sequence of during data transfer. */
-			avs_status = avs_status_al_transfer;
-		} else if (err == avs_error_nack) {
-			/* Recovery sequence of detected NACK */
-			avs_status = avs_status_nack;
-		} else {
-			/* If wait state after data transmission. */
-			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
-				/* Write PMIC DVFS_SetVID address */
-				mmio_write_8(IIC_ICDR, PMIC_DVFS_SETVID);
-				/* Clear ICSR.WAIT to exit from wait state. */
-				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
-					     & (uint8_t) (~ICSR_WAIT));
-				/* Set next status */
-				avs_status = avs_status_write_reg_data;
-			}
-		}
-		break;
-	case avs_status_write_reg_data:
-		/* Check error. */
-		err = avs_check_error();
-		if (err == avs_error_al) {
-			/* Recovery sequence of during data transfer. */
-			avs_status = avs_status_al_transfer;
-		} else if (err == avs_error_nack) {
-			/* Recovery sequence of detected NACK */
-			avs_status = avs_status_nack;
-		} else {
-			/* If wait state after data transmission. */
-			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
-				/* Dose efuse_avs exceed the number of */
-				/* the tables? */
-				if (efuse_avs >= EFUSE_AVS_NUM) {
-					ERROR("AVS number of eFuse is out "
-					      "of a range. number=%u\n",
-					      efuse_avs);
-					/* Infinite loop */
-					panic();
-				}
-				/* Write PMIC DVFS_SetVID value */
-				mmio_write_8(IIC_ICDR,
-					     init_vol_tbl[efuse_avs].vol);
-				/* Clear ICSR.WAIT to exit from wait state. */
-				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
-					     & (uint8_t) (~ICSR_WAIT));
-				/* Set next status */
-				avs_status = avs_status_stop_condition;
-			}
-		}
-		break;
-	case avs_status_stop_condition:
-		err = avs_check_error();
-		if (err == avs_error_al) {
-			/* Recovery sequence of during data transfer. */
-			avs_status = avs_status_al_transfer;
-		} else if (err == avs_error_nack) {
-			/* Recovery sequence of detected NACK */
-			avs_status = avs_status_nack;
-		} else {
-			/* If wait state after data transmission. */
-			if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
-				/* Write H'90 in ICCR to issue stop condition */
-				mmio_write_8(IIC_ICCR, ICCR_STOP);
-				/* Clear ICSR.WAIT to exit from wait state. */
-				mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
-					     & (uint8_t) (~ICSR_WAIT));
-				/* Set next status */
-				avs_status = avs_status_end;
-			}
-		}
-		break;
-	case avs_status_end:
-		/* Is this module not busy?. */
-		if ((mmio_read_8(IIC_ICSR) & ICSR_BUSY) == 0U) {
-			/* Set ICCR=H'00 to disable the I2C module. */
-			mmio_write_8(IIC_ICCR, 0x00U);
-			/* Set next status */
-			avs_status = avs_status_complete;
-		}
-		break;
-	case avs_status_al_start:
-		/* Clear ICSR.AL bit */
-		mmio_write_8(IIC_ICSR, (mmio_read_8(IIC_ICSR)
-					& (uint8_t) (~ICSR_AL)));
-		/* Transmit a clock pulse */
-		mmio_write_8(IIC_ICDR, init_vol_tbl[EFUSE_AVS0].vol);
-		/* Set next status */
-		avs_status = avs_status_error_stop;
-		break;
-	case avs_status_al_transfer:
-		/* Clear ICSR.AL bit */
-		mmio_write_8(IIC_ICSR, (mmio_read_8(IIC_ICSR)
-					& (uint8_t) (~ICSR_AL)));
-		/* Set next status */
-		avs_status = avs_status_error_stop;
-		break;
-	case avs_status_nack:
-		/* Write H'90 in ICCR to issue stop condition */
-		mmio_write_8(IIC_ICCR, ICCR_STOP);
-		/* Disable a WAIT and DTEE interrupt. */
-		mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC)
-			     & (uint8_t) (~(ICIC_WAITE | ICIC_DTEE)));
-		/* Clear ICSR.TACK bit */
-		mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
-			     & (uint8_t) (~ICSR_TACK));
-		/* Set next status */
-		avs_status = ave_status_error_end;
-		break;
-	case avs_status_error_stop:
-		/* If wait state after data transmission. */
-		if ((mmio_read_8(IIC_ICSR) & ICSR_WAIT) == ICSR_WAIT) {
-			/* Write H'90 in ICCR to issue stop condition */
-			mmio_write_8(IIC_ICCR, ICCR_STOP);
-			/* Clear ICSR.WAIT to exit from wait state. */
-			mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR)
-				     & (uint8_t) (~ICSR_WAIT));
-			/* Set next status */
-			avs_status = ave_status_error_end;
-		}
-		break;
-	case ave_status_error_end:
-		/* Is this module not busy?. */
-		if ((mmio_read_8(IIC_ICSR) & ICSR_BUSY) == 0U) {
-			/* Set ICCR=H'00 to disable the I2C module. */
-			mmio_write_8(IIC_ICCR, 0x00U);
-			/* Increment the re-try number of times. */
-			avs_retry++;
-			/* Set start a re-try to status. */
-			avs_status = avs_status_start_condition;
-		}
-		break;
-	case avs_status_complete:
-		/* After "avs_status" became the "avs_status_complete", */
-		/* "avs_setting()" function may be called. */
-		break;
-	default:
-		/* This case is not possible. */
-		ERROR("AVS setting is in invalid status. status=%u\n",
-		      avs_status);
-		/* Infinite loop */
-		panic();
-		break;
-	}
-#endif /* PMIC_ROHM_BD9571 */
-#endif /* (AVS_SETTING_ENABLE==1) */
-}
-
-/*
- * Finish the AVS setting.
- */
-void rcar_avs_end(void)
-{
-#if (AVS_SETTING_ENABLE == 1)
-	uint32_t mstp;
-
-#if PMIC_ROHM_BD9571
-	/* While status is not completion, be repeated. */
-	while (avs_status != avs_status_complete)
-		rcar_avs_setting();
-
-	NOTICE("AVS setting succeeded. DVFS_SetVID=0x%x\n",
-	       init_vol_tbl[efuse_avs].vol);
-
-#if AVS_READ_PMIC_REG_ENABLE == 1
-	{
-		uint8_t addr = PMIC_DVFS_SETVID;
-		uint8_t value = avs_read_pmic_reg(addr);
-		NOTICE("Read PMIC register. address=0x%x value=0x%x \n",
-		       addr, value);
-	}
-#endif
-
-	/* Bit of the module which wants to disable clock supply. */
-	mstp = CPG_SYS_DVFS_BIT;
-	/* Disables the supply of clock signal to a module. */
-	cpg_write(CPG_SMSTPCR9, mmio_read_32(CPG_SMSTPCR9) | mstp);
-#endif /* PMIC_ROHM_BD9571 */
-
-	/* Bit of the module which wants to disable clock supply. */
-	mstp = CPG_SYS_ADVFS_BIT;
-	/* Disables the supply of clock signal to a module. */
-	cpg_write(CPG_SMSTPCR9, mmio_read_32(CPG_SMSTPCR9) | mstp);
-
-#endif /* (AVS_SETTING_ENABLE==1) */
-}
-
-#if (AVS_SETTING_ENABLE == 1)
-#if PMIC_ROHM_BD9571
-/*
- * Check error and judge re-try.
- */
-static avs_error_t avs_check_error(void)
-{
-	avs_error_t ret;
-
-	if ((mmio_read_8(IIC_ICSR) & ICSR_AL) == ICSR_AL) {
-		NOTICE("Loss of arbitration is detected. "
-		       "AVS status=%d Retry=%u\n", avs_status, avs_retry);
-		/* Check of retry number of times */
-		if (avs_retry >= AVS_RETRY_NUM) {
-			ERROR("AVS setting failed in retry. max=%u\n",
-			      AVS_RETRY_NUM);
-			/* Infinite loop */
-			panic();
-		}
-		/* Set the error detected to error status. */
-		ret = avs_error_al;
-	} else if ((mmio_read_8(IIC_ICSR) & ICSR_TACK) == ICSR_TACK) {
-		NOTICE("Non-acknowledge is detected. "
-		       "AVS status=%d Retry=%u\n", avs_status, avs_retry);
-		/* Check of retry number of times */
-		if (avs_retry >= AVS_RETRY_NUM) {
-			ERROR("AVS setting failed in retry. max=%u\n",
-			      AVS_RETRY_NUM);
-			/* Infinite loop */
-			panic();
-		}
-		/* Set the error detected to error status. */
-		ret = avs_error_nack;
-	} else {
-		/* Not error. */
-		ret = avs_error_none;
-	}
-	return ret;
-}
-
-/*
- * Set I2C for DVFS clock.
- */
-static void avs_set_iic_clock(void)
-{
-	uint32_t md_pin;
-
-	/* Read Mode pin register. */
-	md_pin = mmio_read_32(RCAR_MODEMR) & CHECK_MD13_MD14;
-	/* Set the module clock (CP phy) for the IIC-DVFS. */
-	/* CP phy is EXTAL / 2.                            */
-	switch (md_pin) {
-	case MD14_MD13_TYPE_0:	/* EXTAL = 16.6666MHz */
-		mmio_write_8(IIC_ICCL, ICCL_FREQ_8p33M);
-		mmio_write_8(IIC_ICCH, ICCH_FREQ_8p33M);
-		break;
-	case MD14_MD13_TYPE_1:	/* EXTAL = 20MHz */
-		mmio_write_8(IIC_ICCL, ICCL_FREQ_10M);
-		mmio_write_8(IIC_ICCH, ICCH_FREQ_10M);
-		break;
-	case MD14_MD13_TYPE_2:	/* EXTAL = 25MHz (H3/M3) */
-		mmio_write_8(IIC_ICCL, ICCL_FREQ_12p5M);
-		mmio_write_8(IIC_ICCH, ICCH_FREQ_12p5M);
-		break;
-	case MD14_MD13_TYPE_3:	/* EXTAL = 33.3333MHz */
-		mmio_write_8(IIC_ICCL, ICCL_FREQ_16p66M);
-		mmio_write_8(IIC_ICCH, ICCH_FREQ_16p66M);
-		break;
-	default:		/* This case is not possible. */
-		/* CP Phy frequency is to be set for the 16.66MHz */
-		mmio_write_8(IIC_ICCL, ICCL_FREQ_16p66M);
-		mmio_write_8(IIC_ICCH, ICCH_FREQ_16p66M);
-		break;
-	}
-}
-
-#if AVS_READ_PMIC_REG_ENABLE == 1
-/*
- * Read the value of the register of PMIC.
- */
-static uint8_t avs_read_pmic_reg(uint8_t addr)
-{
-	uint8_t reg;
-
-	/* Set ICCR.ICE=1 to activate the I2C module. */
-	mmio_write_8(IIC_ICCR, mmio_read_8(IIC_ICCR) | ICCR_ENABLE);
-
-	/* Set frequency of 400kHz */
-	avs_set_iic_clock();
-
-	/* Set ICIC.WAITE=1, ICIC.DTEE=1 to enable data transmission    */
-	/* interrupt and wait interrupt.                                */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_WAITE | ICIC_DTEE);
-
-	/* Write H'94 in ICCR to issue start condition */
-	mmio_write_8(IIC_ICCR, ICCR_START);
-
-	/* Wait for a until ICSR.DTE becomes 1. */
-	avs_poll(ICSR_DTE, 1U);
-
-	/* Clear ICIC.DTEE to disable a DTE interrupt. */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
-	/* Send slave address of PMIC */
-	mmio_write_8(IIC_ICDR, PMIC_W_SLAVE_ADDRESS);
-
-	/* Wait for a until ICSR.WAIT becomes 1. */
-	avs_poll(ICSR_WAIT, 1U);
-
-	/* write PMIC address */
-	mmio_write_8(IIC_ICDR, addr);
-	/* Clear ICSR.WAIT to exit from WAIT status. */
-	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
-
-	/* Wait for a until ICSR.WAIT becomes 1. */
-	avs_poll(ICSR_WAIT, 1U);
-
-	/* Write H'94 in ICCR to issue restart condition */
-	mmio_write_8(IIC_ICCR, ICCR_START);
-	/* Clear ICSR.WAIT to exit from WAIT status. */
-	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
-	/* Set ICIC.DTEE=1 to enable data transmission interrupt. */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_DTEE);
-
-	/* Wait for a until ICSR.DTE becomes 1. */
-	avs_poll(ICSR_DTE, 1U);
-
-	/* Clear ICIC.DTEE to disable a DTE interrupt. */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
-	/* Send slave address of PMIC */
-	mmio_write_8(IIC_ICDR, PMIC_R_SLAVE_ADDRESS);
-
-	/* Wait for a until ICSR.WAIT becomes 1. */
-	avs_poll(ICSR_WAIT, 1U);
-
-	/* Write H'81 to ICCR to issue the repeated START condition     */
-	/* for changing the transmission mode to the receive mode.      */
-	mmio_write_8(IIC_ICCR, ICCR_START_RECV);
-	/* Clear ICSR.WAIT to exit from WAIT status. */
-	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
-
-	/* Wait for a until ICSR.WAIT becomes 1. */
-	avs_poll(ICSR_WAIT, 1U);
-
-	/* Set ICCR to H'C0 for the STOP condition */
-	mmio_write_8(IIC_ICCR, ICCR_STOP_RECV);
-	/* Clear ICSR.WAIT to exit from WAIT status. */
-	mmio_write_8(IIC_ICSR, mmio_read_8(IIC_ICSR) & (uint8_t) (~ICSR_WAIT));
-	/* Set ICIC.DTEE=1 to enable data transmission interrupt. */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) | ICIC_DTEE);
-
-	/* Wait for a until ICSR.DTE becomes 1. */
-	avs_poll(ICSR_DTE, 1U);
-
-	/* Receive DVFS SetVID register */
-	/* Clear ICIC.DTEE to disable a DTE interrupt. */
-	mmio_write_8(IIC_ICIC, mmio_read_8(IIC_ICIC) & (uint8_t) (~ICIC_DTEE));
-	/* Receive DVFS SetVID register */
-	reg = mmio_read_8(IIC_ICDR);
-
-	/* Wait until ICSR.BUSY is cleared. */
-	avs_poll(ICSR_BUSY, 0U);
-
-	/* Set ICCR=H'00 to disable the I2C module. */
-	mmio_write_8(IIC_ICCR, 0x00U);
-
-	return reg;
-}
-
-/*
- * Wait processing by the polling.
- */
-static void avs_poll(uint8_t bit_pos, uint8_t val)
-{
-	uint8_t bit_val = 0U;
-
-	if (val != 0U)
-		bit_val = bit_pos;
-
-	while (1) {
-		if ((mmio_read_8(IIC_ICSR) & bit_pos) == bit_val)
-			break;
-	}
-}
-#endif /* AVS_READ_PMIC_REG_ENABLE */
-#endif /* PMIC_ROHM_BD9571 */
-#endif /* (AVS_SETTING_ENABLE==1) */
diff --git a/drivers/renesas/rcar/board/board.c b/drivers/renesas/rcar/board/board.c
index cd194ff..dbbaed6 100644
--- a/drivers/renesas/rcar/board/board.c
+++ b/drivers/renesas/rcar/board/board.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights
  * reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
@@ -30,9 +30,9 @@
 #define BOARD_CODE_SHIFT	(0x03)
 #define BOARD_ID_UNKNOWN	(0xFF)
 
-#define SXS_ID	{ 0x10U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
+#define SXS_ID	{ 0x10U, 0x11U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
 #define SX_ID	{ 0x10U, 0x11U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
-#define SKP_ID	{ 0x10U, 0x10U, 0x20U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
+#define SKP_ID	{ 0x10U, 0x10U, 0x20U, 0x21U, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
 #define SK_ID	{ 0x10U, 0x30U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
 #define EB4_ID	{ 0x10U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
 #define EB_ID	{ 0x10U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
diff --git a/drivers/renesas/rcar/common.c b/drivers/renesas/rcar/common.c
deleted file mode 100644
index 42bdce5..0000000
--- a/drivers/renesas/rcar/common.c
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (c) 2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <lib/mmio.h>
-
-#include "rcar_private.h"
-
-void
-#if IMAGE_BL31
-    __attribute__ ((section(".system_ram")))
-#endif
-    cpg_write(uintptr_t regadr, uint32_t regval)
-{
-	uint32_t value = (regval);
-	mmio_write_32((uintptr_t) RCAR_CPGWPR, ~value);
-	mmio_write_32(regadr, value);
-}
-
-void
-#if IMAGE_BL31
-    __attribute__ ((section(".system_ram")))
-#endif
-    mstpcr_write(uint32_t mstpcr, uint32_t mstpsr, uint32_t target_bit)
-{
-	uint32_t reg;
-	reg = mmio_read_32(mstpcr);
-	reg &= ~target_bit;
-	cpg_write(mstpcr, reg);
-	while ((mmio_read_32(mstpsr) & target_bit) != 0U) {
-	}
-}
diff --git a/drivers/renesas/rcar/console/rcar_console.S b/drivers/renesas/rcar/console/rcar_console.S
deleted file mode 100644
index 29baa67..0000000
--- a/drivers/renesas/rcar/console/rcar_console.S
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright (c) 2018-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <console_macros.S>
-#include <drivers/renesas/rcar/console/console.h>
-
-	.globl	console_rcar_register
-	.globl	console_rcar_init
-	.globl	console_rcar_putc
-	.globl	console_rcar_flush
-
-	.extern	rcar_log_init
-	.extern	rcar_set_log_data
-
-	/* -----------------------------------------------
-	 * int console_rcar_register(
-	 *      uintptr_t base, uint32_t clk, uint32_t baud,
-	 *      console_t *console)
-	 * Function to initialize and register a new rcar
-	 * console. Storage passed in for the console struct
-	 * *must* be persistent (i.e. not from the stack).
-	 * In: x0 - UART register base address
-	 *     w1 - UART clock in Hz
-	 *     w2 - Baud rate
-	 *     x3 - pointer to empty console_t struct
-	 * Out: return 1 on success, 0 on error
-	 * Clobber list : x0, x1, x2, x6, x7, x14
-	 * -----------------------------------------------
-	 */
-func console_rcar_register
-	mov	x7, x30
-	mov	x6, x3
-	cbz	x6, register_fail
-	str	x0, [x6, #CONSOLE_T_BASE]
-
-	bl	rcar_log_init
-	cbz	x0, register_fail
-
-	mov	x0, x6
-	mov	x30, x7
-	finish_console_register rcar, putc=1, getc=0, flush=1
-
-register_fail:
-	ret	x7
-endfunc console_rcar_register
-
-	/* ---------------------------------------------
-	 * int console_rcar_init(unsigned long base_addr,
-	 * unsigned int uart_clk, unsigned int baud_rate)
-	 * Function to initialize the console without a
-	 * C Runtime to print debug information. This
-	 * function will be accessed by crash reporting.
-	 * In: x0 - console base address
-	 *     w1 - Uart clock in Hz
-	 *     w2 - Baud rate
-	 * Out: return 1 on success
-	 * Clobber list : x1, x2
-	 * ---------------------------------------------
-	 */
-func console_rcar_init
-	mov	w0, #0
-	ret
-endfunc console_rcar_init
-
-	/* --------------------------------------------------------
-	 * int console_rcar_putc(int c, console_t *console)
-	 * Function to output a character over the console. It
-	 * returns the character printed on success or -1 on error.
-	 * In : w0 - character to be printed
-	 *      x1 - pointer to console_t structure
-	 * Out : return -1 on error else return character.
-	 * Clobber list : x2
-	 * --------------------------------------------------------
-	 */
-func console_rcar_putc
-	b	rcar_set_log_data
-endfunc console_rcar_putc
-
-	/* ---------------------------------------------
-	 * void console_rcar_flush(void)
-	 * Function to force a write of all buffered
-	 * data that hasn't been output. It returns void
-	 * Clobber list : x0, x1
-	 * ---------------------------------------------
-	 */
-func console_rcar_flush
-	ret
-endfunc console_rcar_flush
diff --git a/drivers/renesas/rcar/console/rcar_printf.c b/drivers/renesas/rcar/console/rcar_printf.c
deleted file mode 100644
index e75b9f4..0000000
--- a/drivers/renesas/rcar/console/rcar_printf.c
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stdarg.h>
-#include <stdint.h>
-
-#include <platform_def.h>
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <lib/bakery_lock.h>
-
-#include "rcar_def.h"
-#include "rcar_private.h"
-#include "rcar_printf.h"
-
-#define INDEX_TIMER_COUNT	(4U)
-
-extern RCAR_INSTANTIATE_LOCK typedef struct log_head {
-	uint8_t head[4];
-	uint32_t index;
-	uint32_t size;
-	uint8_t res[4];
-} loghead_t;
-
-typedef struct log_map {
-	loghead_t header;
-	uint8_t log_data[RCAR_BL31_LOG_MAX];
-	uint8_t res_data[RCAR_LOG_RES_SIZE];
-} logmap_t;
-
-int32_t rcar_set_log_data(int32_t c)
-{
-	logmap_t *t_log;
-
-	t_log = (logmap_t *) RCAR_BL31_LOG_BASE;
-
-	rcar_lock_get();
-
-	/*
-	 * If index is broken, then index and size initialize
-	 */
-	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
-		t_log->header.index = 0U;
-		t_log->header.size = 0U;
-	}
-	/*
-	 * data store to log area then index and size renewal
-	 */
-	t_log->log_data[t_log->header.index] = (uint8_t) c;
-	t_log->header.index++;
-	if (t_log->header.size < t_log->header.index) {
-		t_log->header.size = t_log->header.index;
-	}
-	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
-		t_log->header.index = 0U;
-	}
-
-	rcar_lock_release();
-
-	return 1;
-}
-
-int32_t rcar_log_init(void)
-{
-
-	static const uint8_t const_header[] = "TLOG";
-	logmap_t *t_log;
-	int16_t init_flag = 0;
-
-	t_log = (logmap_t *) RCAR_BL31_LOG_BASE;
-	if (memcmp
-	    ((const void *)t_log->header.head, (const void *)const_header,
-	     sizeof(t_log->header.head)) != 0) {
-		/*
-		 * Log header is not "TLOG", then log area initialize
-		 */
-		init_flag = 1;
-	}
-	if (t_log->header.index >= (uint32_t) RCAR_BL31_LOG_MAX) {
-		/*
-		 * index is broken, then log area initialize
-		 */
-		init_flag = 1;
-	}
-	if (init_flag == 1) {
-		(void)memset((void *)t_log->log_data, 0,
-			     (size_t) RCAR_BL31_LOG_MAX);
-		(void)memcpy((void *)t_log->header.head,
-			     (const void *)const_header,
-			     sizeof(t_log->header.head));
-		t_log->header.index = 0U;
-		t_log->header.size = 0U;
-	}
-	rcar_lock_init();
-
-	return 1;
-}
diff --git a/drivers/renesas/rcar/ddr/ddr.mk b/drivers/renesas/rcar/ddr/ddr.mk
deleted file mode 100644
index c26993d..0000000
--- a/drivers/renesas/rcar/ddr/ddr.mk
+++ /dev/null
@@ -1,17 +0,0 @@
-#
-# Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-ifeq (${RCAR_LSI},${RCAR_E3})
-    include drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk
-    BL2_SOURCES += drivers/renesas/rcar/ddr/dram_sub_func.c
-else ifeq (${RCAR_LSI},${RCAR_D3})
-    include drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk
-else ifeq (${RCAR_LSI},${RCAR_V3M})
-    include drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk
-else
-    include drivers/renesas/rcar/ddr/ddr_b/ddr_b.mk
-    BL2_SOURCES += drivers/renesas/rcar/ddr/dram_sub_func.c
-endif
diff --git a/drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk b/drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk
deleted file mode 100644
index 7882558..0000000
--- a/drivers/renesas/rcar/ddr/ddr_a/ddr_a.mk
+++ /dev/null
@@ -1,13 +0,0 @@
-#
-# Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-ifeq (${RCAR_LSI},${RCAR_E3})
-BL2_SOURCES += drivers/renesas/rcar/ddr/ddr_a/ddr_init_e3.c
-else ifeq (${RCAR_LSI},${RCAR_D3})
-BL2_SOURCES += drivers/renesas/rcar/ddr/ddr_a/ddr_init_d3.c
-else
-BL2_SOURCES += drivers/renesas/rcar/ddr/ddr_a/ddr_init_v3m.c
-endif
diff --git a/drivers/renesas/rcar/ddr/ddr_a/ddr_init_d3.c b/drivers/renesas/rcar/ddr/ddr_a/ddr_init_d3.c
deleted file mode 100644
index a49510e..0000000
--- a/drivers/renesas/rcar/ddr/ddr_a/ddr_init_d3.c
+++ /dev/null
@@ -1,699 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation.
- * All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stdint.h>
-#include <lib/mmio.h>
-#include <common/debug.h>
-#include "rcar_def.h"
-#include "../ddr_regs.h"
-
-#define RCAR_DDR_VERSION	"rev.0.01"
-
-#if RCAR_LSI != RCAR_D3
-#error "Don't have DDR initialize routine."
-#endif
-
-static void init_ddr_d3_1866(void)
-{
-	uint32_t i, r2, r3, r5, r6, r7, r12;
-
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
-	mmio_write_32(DBSC_DBKIND, 0x00000007);
-	mmio_write_32(DBSC_DBMEMCONF_0_0, 0x0f030a01);
-	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
-	mmio_write_32(DBSC_DBTR0, 0x0000000D);
-	mmio_write_32(DBSC_DBTR1, 0x00000009);
-	mmio_write_32(DBSC_DBTR2, 0x00000000);
-	mmio_write_32(DBSC_DBTR3, 0x0000000D);
-	mmio_write_32(DBSC_DBTR4, 0x000D000D);
-	mmio_write_32(DBSC_DBTR5, 0x0000002D);
-	mmio_write_32(DBSC_DBTR6, 0x00000020);
-	mmio_write_32(DBSC_DBTR7, 0x00060006);
-	mmio_write_32(DBSC_DBTR8, 0x00000021);
-	mmio_write_32(DBSC_DBTR9, 0x00000007);
-	mmio_write_32(DBSC_DBTR10, 0x0000000E);
-	mmio_write_32(DBSC_DBTR11, 0x0000000C);
-	mmio_write_32(DBSC_DBTR12, 0x00140014);
-	mmio_write_32(DBSC_DBTR13, 0x000000F2);
-	mmio_write_32(DBSC_DBTR14, 0x00170006);
-	mmio_write_32(DBSC_DBTR15, 0x00060005);
-	mmio_write_32(DBSC_DBTR16, 0x09210507);
-	mmio_write_32(DBSC_DBTR17, 0x040E0000);
-	mmio_write_32(DBSC_DBTR18, 0x00000200);
-	mmio_write_32(DBSC_DBTR19, 0x012B004B);
-	mmio_write_32(DBSC_DBTR20, 0x020000FB);
-	mmio_write_32(DBSC_DBTR21, 0x00040004);
-	mmio_write_32(DBSC_DBBL, 0x00000000);
-	mmio_write_32(DBSC_DBODT0, 0x00000001);
-	mmio_write_32(DBSC_DBADJ0, 0x00000001);
-	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
-	mmio_write_32(DBSC_DBDFICNT_0, 0x00000010);
-	mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
-	mmio_write_32(DBSC_DBSCHRW1, 0x00000046);
-	mmio_write_32(DBSC_SCFCTST0, 0x0D020D04);
-	mmio_write_32(DBSC_SCFCTST1, 0x0306040C);
-
-	mmio_write_32(DBSC_DBPDLK_0, 0x0000A55A);
-	mmio_write_32(DBSC_DBCMD, 0x01000001);
-	mmio_write_32(DBSC_DBCMD, 0x08000000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x80010000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000008);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000B8000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A04);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000091);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000095);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BBAD);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000099);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A00);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0024641E);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010073);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0C058A00);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058A00);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0780C700);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(30)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000004);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0A206F89);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000022);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x1000040B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000023);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x35A00D77);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000024);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x2A8A2C28);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000025);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x30005E00);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000026);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0014CB49);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000027);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00000F14);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000028);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00000046);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000029);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x81003047);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000020);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00181884);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000001A);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x33C03C10);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A7);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A8);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A9);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C7);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C8);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C9);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000000E);
-	r2 = (mmio_read_32(DBSC_DBPDRGD_0) & 0x0000FF00) >> 0x9;
-	r3 = (r2 << 16) + (r2 << 8) + r2;
-	r6 = (r2 << 24) + (r2 << 16) + (r2 << 8) + r2;
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000011);
-	mmio_write_32(DBSC_DBPDRGD_0, r3);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000012);
-	mmio_write_32(DBSC_DBPDRGD_0, r3);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000016);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000017);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000018);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000019);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010181);
-	mmio_write_32(DBSC_DBCMD, 0x08000001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010601);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	for (i = 0; i < 2; i++) {
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
-		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
-		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
-		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
-
-		if (r6 > 0) {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | r6);
-		} else {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | r7);
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 |
-						     ((r6 + (r5 << 1)) & 0xFF));
-		}
-	}
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
-	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00C0);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010801);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
-	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00D8);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0001F001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
-	r2 = mmio_read_32(DBSC_DBPDRGD_0);
-	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
-	r2 = mmio_read_32(DBSC_DBPDRGD_0);
-	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x81003087);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010401);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	for (i = 0; i < 2; i++) {
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
-		r5 = ((mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8);
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
-		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
-
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
-		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
-		r12 = (r5 >> 0x2);
-
-		if (r12 < r6) {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r6 - r12) & 0xFF));
-		} else {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | (r7 & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 |
-						     ((r6 + r5 +
-						      (r5 >> 1) + r12) & 0xFF));
-		}
-	}
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00015001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0380C700);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
-	while (mmio_read_32(DBSC_DBPDRGD_0) & BIT(30))
-		;
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0024643E);
-
-	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
-	mmio_write_32(DBSC_DBCALCNF, 0x0100401B);
-	mmio_write_32(DBSC_DBRFCNF1, 0x00080E23);
-	mmio_write_32(DBSC_DBRFCNF2, 0x00010000);
-	mmio_write_32(DBSC_DBDFICUPDCNF, 0x40100001);
-	mmio_write_32(DBSC_DBRFEN, 0x00000001);
-	mmio_write_32(DBSC_DBACEN, 0x00000001);
-	mmio_write_32(DBSC_DBPDLK_0, 0x00000000);
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
-
-#ifdef ddr_qos_init_setting // only for non qos_init
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
-	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
-	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
-	mmio_write_32(DBSC_DBSCHCNT0, 0x000f0037);
-	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
-	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
-	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
-	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00);
-	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00);
-	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000);
-	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000);
-	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300);
-	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0);
-	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200);
-	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS90, 0x00000300);
-	mmio_write_32(DBSC_DBSCHQOS91, 0x000002F0);
-	mmio_write_32(DBSC_DBSCHQOS92, 0x00000200);
-	mmio_write_32(DBSC_DBSCHQOS93, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0);
-	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0);
-	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0);
-	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0);
-	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080);
-	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030);
-	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020);
-	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010);
-	mmio_write_32(0xE67F0018, 0x00000001);
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
-#endif
-}
-
-static void init_ddr_d3_1600(void)
-{
-	uint32_t i, r2, r3, r5, r6, r7, r12;
-
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
-	mmio_write_32(DBSC_DBKIND, 0x00000007);
-	mmio_write_32(DBSC_DBMEMCONF_0_0, 0x0f030a01);
-	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
-	mmio_write_32(DBSC_DBTR0, 0x0000000B);
-	mmio_write_32(DBSC_DBTR1, 0x00000008);
-	mmio_write_32(DBSC_DBTR2, 0x00000000);
-	mmio_write_32(DBSC_DBTR3, 0x0000000B);
-	mmio_write_32(DBSC_DBTR4, 0x000B000B);
-	mmio_write_32(DBSC_DBTR5, 0x00000027);
-	mmio_write_32(DBSC_DBTR6, 0x0000001C);
-	mmio_write_32(DBSC_DBTR7, 0x00060006);
-	mmio_write_32(DBSC_DBTR8, 0x00000020);
-	mmio_write_32(DBSC_DBTR9, 0x00000006);
-	mmio_write_32(DBSC_DBTR10, 0x0000000C);
-	mmio_write_32(DBSC_DBTR11, 0x0000000A);
-	mmio_write_32(DBSC_DBTR12, 0x00120012);
-	mmio_write_32(DBSC_DBTR13, 0x000000D0);
-	mmio_write_32(DBSC_DBTR14, 0x00140005);
-	mmio_write_32(DBSC_DBTR15, 0x00050004);
-	mmio_write_32(DBSC_DBTR16, 0x071F0305);
-	mmio_write_32(DBSC_DBTR17, 0x040C0000);
-	mmio_write_32(DBSC_DBTR18, 0x00000200);
-	mmio_write_32(DBSC_DBTR19, 0x01000040);
-	mmio_write_32(DBSC_DBTR20, 0x020000D8);
-	mmio_write_32(DBSC_DBTR21, 0x00040004);
-	mmio_write_32(DBSC_DBBL, 0x00000000);
-	mmio_write_32(DBSC_DBODT0, 0x00000001);
-	mmio_write_32(DBSC_DBADJ0, 0x00000001);
-	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
-	mmio_write_32(DBSC_DBDFICNT_0, 0x00000010);
-	mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
-	mmio_write_32(DBSC_DBSCHRW1, 0x00000046);
-	mmio_write_32(DBSC_SCFCTST0, 0x0D020C04);
-	mmio_write_32(DBSC_SCFCTST1, 0x0305040C);
-
-	mmio_write_32(DBSC_DBPDLK_0, 0x0000A55A);
-	mmio_write_32(DBSC_DBCMD, 0x01000001);
-	mmio_write_32(DBSC_DBCMD, 0x08000000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x80010000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000008);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000B8000);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058904);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000091);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000095);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BBAD);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000099);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0007BB6B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058900);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0024641E);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010073);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0C058900);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000090);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x04058900);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0780C700);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(30)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000004);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x08C05FF0);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000022);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x1000040B);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000023);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x2D9C0B66);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000024);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x2A88C400);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000025);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x30005200);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000026);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0014A9C9);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000027);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00000D70);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000028);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00000046);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000029);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00000098);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x81003047);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000020);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00181884);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000001A);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x33C03C10);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A7);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A8);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A9);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C7);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C8);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0D0D0D0D);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C9);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x000D0D0D);
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000000E);
-	r2 = (mmio_read_32(DBSC_DBPDRGD_0) & 0x0000FF00) >> 0x9;
-	r3 = (r2 << 16) + (r2 << 8) + r2;
-	r6 = (r2 << 24) + (r2 << 16) + (r2 << 8) + r2;
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000011);
-	mmio_write_32(DBSC_DBPDRGD_0, r3);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000012);
-	mmio_write_32(DBSC_DBPDRGD_0, r3);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000016);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000017);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000018);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000019);
-	mmio_write_32(DBSC_DBPDRGD_0, r6);
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010181);
-	mmio_write_32(DBSC_DBCMD, 0x08000001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010601);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	for (i = 0; i < 2; i++) {
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
-		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
-		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
-		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
-		if (r6 > 0) {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | r6);
-		} else {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | r7);
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 |
-						     ((r6 + (r5 << 1)) & 0xFF));
-		}
-	}
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
-	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00C0);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010801);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000005);
-	mmio_write_32(DBSC_DBPDRGD_0, 0xC1AA00D8);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0001F001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000AF);
-	r2 = mmio_read_32(DBSC_DBPDRGD_0);
-	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000CF);
-	r2 = mmio_read_32(DBSC_DBPDRGD_0);
-	mmio_write_32(DBSC_DBPDRGD_0, ((r2 + 0x1) & 0xFF) | (r2 & 0xFFFFFF00));
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C000285);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x0000002C);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x81003087);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00010401);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	for (i = 0; i < 2; i++) {
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB1 + i * 0x20);
-		r5 = (mmio_read_32(DBSC_DBPDRGD_0) & 0xFF00) >> 0x8;
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB4 + i * 0x20);
-		r6 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFF;
-
-		mmio_write_32(DBSC_DBPDRGA_0, 0xB3 + i * 0x20);
-		r7 = mmio_read_32(DBSC_DBPDRGD_0) & 0x7;
-		r12 = (r5 >> 0x2);
-
-		if (r12 < r6) {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r7 + 0x1) & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | ((r6 - r12) & 0xFF));
-		} else {
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFFF8;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB2 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 | (r7 & 0x7));
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			r2 = mmio_read_32(DBSC_DBPDRGD_0) & 0xFFFFFF00;
-			mmio_write_32(DBSC_DBPDRGA_0, 0xB0 + i * 0x20);
-			mmio_write_32(DBSC_DBPDRGD_0, r2 |
-						     ((r6 + r5 +
-						      (r5 >> 1) + r12) & 0xFF));
-		}
-	}
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000A0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x000000C0);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x7C0002C5);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000001);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x00015001);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000006);
-	while (!(mmio_read_32(DBSC_DBPDRGD_0) & BIT(0)))
-		;
-
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000003);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0380C700);
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000007);
-	while (mmio_read_32(DBSC_DBPDRGD_0) & BIT(30))
-		;
-	mmio_write_32(DBSC_DBPDRGA_0, 0x00000021);
-	mmio_write_32(DBSC_DBPDRGD_0, 0x0024643E);
-
-	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
-	mmio_write_32(DBSC_DBCALCNF, 0x0100401B);
-	mmio_write_32(DBSC_DBRFCNF1, 0x00080C30);
-	mmio_write_32(DBSC_DBRFCNF2, 0x00010000);
-	mmio_write_32(DBSC_DBDFICUPDCNF, 0x40100001);
-	mmio_write_32(DBSC_DBRFEN, 0x00000001);
-	mmio_write_32(DBSC_DBACEN, 0x00000001);
-	mmio_write_32(DBSC_DBPDLK_0, 0x00000000);
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
-
-#ifdef ddr_qos_init_setting // only for non qos_init
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
-	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
-	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
-	mmio_write_32(DBSC_DBSCHCNT0, 0x000f0037);
-	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
-	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
-	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
-	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00);
-	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00);
-	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000);
-	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000);
-	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300);
-	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0);
-	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200);
-	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS90, 0x00000300);
-	mmio_write_32(DBSC_DBSCHQOS91, 0x000002F0);
-	mmio_write_32(DBSC_DBSCHQOS92, 0x00000200);
-	mmio_write_32(DBSC_DBSCHQOS93, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100);
-	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0);
-	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0);
-	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0);
-	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0);
-	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080);
-	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040);
-	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030);
-	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020);
-	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010);
-	mmio_write_32(0xE67F0018, 0x00000001);
-	mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
-#endif
-}
-
-#define PRR			0xFFF00044U
-#define PRR_PRODUCT_MASK	0x00007F00U
-#define PRR_PRODUCT_D3		0x00005800U
-
-#define	MODEMR_MD19		BIT(19)
-
-int32_t rcar_dram_init(void)
-{
-	uint32_t reg;
-	uint32_t ddr_mbps;
-
-	reg = mmio_read_32(PRR);
-	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_D3) {
-		ERROR("LSI Product ID (PRR=0x%x) DDR initialize not supported.\n",
-		      reg);
-		panic();
-	}
-
-	reg = mmio_read_32(RST_MODEMR);
-	if (reg & MODEMR_MD19) {
-		init_ddr_d3_1866();
-		ddr_mbps = 1866;
-	} else {
-		init_ddr_d3_1600();
-		ddr_mbps = 1600;
-	}
-
-	NOTICE("BL2: DDR%d\n", ddr_mbps);
-
-	return 0;
-}
diff --git a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram.c b/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram.c
deleted file mode 100644
index ac83c9a..0000000
--- a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram.c
+++ /dev/null
@@ -1,4474 +0,0 @@
-/*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation.
- * All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stdint.h>
-#include <string.h>
-#include <stdio.h>
-
-#include <common/debug.h>
-#include <lib/mmio.h>
-
-#include "ddr_regdef.h"
-#include "init_dram_tbl_h3.h"
-#include "init_dram_tbl_m3.h"
-#include "init_dram_tbl_h3ver2.h"
-#include "init_dram_tbl_m3n.h"
-#include "boot_init_dram_regdef.h"
-#include "boot_init_dram.h"
-#include "dram_sub_func.h"
-#include "micro_delay.h"
-#include "rcar_def.h"
-
-#define DDR_BACKUPMODE
-#define FATAL_MSG(x) NOTICE(x)
-
-/* variables */
-#ifdef RCAR_DDR_FIXED_LSI_TYPE
-#ifndef RCAR_AUTO
-#define RCAR_AUTO	99
-#define RCAR_H3		0
-#define RCAR_M3		1
-#define RCAR_M3N	2
-#define RCAR_E3		3	/* NON */
-#define RCAR_H3N	4
-
-#define RCAR_CUT_10	0
-#define RCAR_CUT_11	1
-#define RCAR_CUT_20	10
-#define RCAR_CUT_30	20
-#endif
-#ifndef RCAR_LSI
-#define RCAR_LSI	RCAR_AUTO
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO)
-static uint32_t prr_product;
-static uint32_t prr_cut;
-#else
-#if (RCAR_LSI == RCAR_H3)
-static const uint32_t prr_product = PRR_PRODUCT_H3;
-#elif(RCAR_LSI == RCAR_M3)
-static const uint32_t prr_product = PRR_PRODUCT_M3;
-#elif(RCAR_LSI == RCAR_M3N)
-static const uint32_t prr_product = PRR_PRODUCT_M3N;
-#elif(RCAR_LSI == RCAR_H3N)
-static const uint32_t prr_product = PRR_PRODUCT_H3;
-#endif /* RCAR_LSI */
-
-#ifndef RCAR_LSI_CUT
-static uint32_t prr_cut;
-#else /* RCAR_LSI_CUT */
-#if (RCAR_LSI_CUT == RCAR_CUT_10)
-static const uint32_t prr_cut = PRR_PRODUCT_10;
-#elif(RCAR_LSI_CUT == RCAR_CUT_11)
-static const uint32_t prr_cut = PRR_PRODUCT_11;
-#elif(RCAR_LSI_CUT == RCAR_CUT_20)
-static const uint32_t prr_cut = PRR_PRODUCT_20;
-#elif(RCAR_LSI_CUT == RCAR_CUT_30)
-static const uint32_t prr_cut = PRR_PRODUCT_30;
-#endif /* RCAR_LSI_CUT */
-#endif /* RCAR_LSI_CUT */
-#endif /* RCAR_AUTO_NON */
-#else /* RCAR_DDR_FIXED_LSI_TYPE */
-static uint32_t prr_product;
-static uint32_t prr_cut;
-#endif /* RCAR_DDR_FIXED_LSI_TYPE */
-
-static const uint32_t *p_ddr_regdef_tbl;
-static uint32_t brd_clk;
-static uint32_t brd_clkdiv;
-static uint32_t brd_clkdiva;
-static uint32_t ddr_mbps;
-static uint32_t ddr_mbpsdiv;
-static uint32_t ddr_tccd;
-static uint32_t ddr_phycaslice;
-static const struct _boardcnf *board_cnf;
-static uint32_t ddr_phyvalid;
-static uint32_t ddr_density[DRAM_CH_CNT][CS_CNT];
-static uint32_t ch_have_this_cs[CS_CNT] __aligned(64);
-static uint32_t rdqdm_dly[DRAM_CH_CNT][CSAB_CNT][SLICE_CNT * 2][9];
-static uint32_t max_density;
-static uint32_t ddr0800_mul;
-static uint32_t ddr_mul;
-static uint32_t DDR_PHY_SLICE_REGSET_OFS;
-static uint32_t DDR_PHY_ADR_V_REGSET_OFS;
-static uint32_t DDR_PHY_ADR_I_REGSET_OFS;
-static uint32_t DDR_PHY_ADR_G_REGSET_OFS;
-static uint32_t DDR_PI_REGSET_OFS;
-static uint32_t DDR_PHY_SLICE_REGSET_SIZE;
-static uint32_t DDR_PHY_ADR_V_REGSET_SIZE;
-static uint32_t DDR_PHY_ADR_I_REGSET_SIZE;
-static uint32_t DDR_PHY_ADR_G_REGSET_SIZE;
-static uint32_t DDR_PI_REGSET_SIZE;
-static uint32_t DDR_PHY_SLICE_REGSET_NUM;
-static uint32_t DDR_PHY_ADR_V_REGSET_NUM;
-static uint32_t DDR_PHY_ADR_I_REGSET_NUM;
-static uint32_t DDR_PHY_ADR_G_REGSET_NUM;
-static uint32_t DDR_PI_REGSET_NUM;
-static uint32_t DDR_PHY_ADR_I_NUM;
-#define DDR_PHY_REGSET_MAX 128
-#define DDR_PI_REGSET_MAX 320
-static uint32_t _cnf_DDR_PHY_SLICE_REGSET[DDR_PHY_REGSET_MAX];
-static uint32_t _cnf_DDR_PHY_ADR_V_REGSET[DDR_PHY_REGSET_MAX];
-static uint32_t _cnf_DDR_PHY_ADR_I_REGSET[DDR_PHY_REGSET_MAX];
-static uint32_t _cnf_DDR_PHY_ADR_G_REGSET[DDR_PHY_REGSET_MAX];
-static uint32_t _cnf_DDR_PI_REGSET[DDR_PI_REGSET_MAX];
-static uint32_t pll3_mode;
-static uint32_t loop_max;
-#ifdef DDR_BACKUPMODE
-uint32_t ddr_backup;
-/* #define DDR_BACKUPMODE_HALF           //for Half channel(ch0,1 only) */
-#endif
-
-#ifdef ddr_qos_init_setting	/*  only for non qos_init */
-#define OPERATING_FREQ			(400U)	/* Mhz */
-#define BASE_SUB_SLOT_NUM		(0x6U)
-#define SUB_SLOT_CYCLE			(0x7EU)	/* 126 */
-#define QOSWT_WTSET0_CYCLE		\
-	((SUB_SLOT_CYCLE * BASE_SUB_SLOT_NUM * 1000U) / \
-	OPERATING_FREQ)	/* unit:ns */
-
-uint32_t get_refperiod(void)
-{
-	return QOSWT_WTSET0_CYCLE;
-}
-#else /*  ddr_qos_init_setting // only for non qos_init */
-extern uint32_t get_refperiod(void);
-#endif /* ddr_qos_init_setting // only for non qos_init */
-
-#define _reg_PHY_RX_CAL_X_NUM 11
-static const uint32_t _reg_PHY_RX_CAL_X[_reg_PHY_RX_CAL_X_NUM] = {
-	_reg_PHY_RX_CAL_DQ0,
-	_reg_PHY_RX_CAL_DQ1,
-	_reg_PHY_RX_CAL_DQ2,
-	_reg_PHY_RX_CAL_DQ3,
-	_reg_PHY_RX_CAL_DQ4,
-	_reg_PHY_RX_CAL_DQ5,
-	_reg_PHY_RX_CAL_DQ6,
-	_reg_PHY_RX_CAL_DQ7,
-	_reg_PHY_RX_CAL_DM,
-	_reg_PHY_RX_CAL_DQS,
-	_reg_PHY_RX_CAL_FDBK
-};
-
-#define _reg_PHY_CLK_WRX_SLAVE_DELAY_NUM 10
-static const uint32_t _reg_PHY_CLK_WRX_SLAVE_DELAY
-	[_reg_PHY_CLK_WRX_SLAVE_DELAY_NUM] = {
-	_reg_PHY_CLK_WRDQ0_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ1_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ2_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ3_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ4_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ5_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ6_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQ7_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDM_SLAVE_DELAY,
-	_reg_PHY_CLK_WRDQS_SLAVE_DELAY
-};
-
-#define _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY_NUM 9
-static const uint32_t _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY
-	[_reg_PHY_RDDQS_X_FALL_SLAVE_DELAY_NUM] = {
-	_reg_PHY_RDDQS_DQ0_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ1_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ2_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ3_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ4_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ5_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ6_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ7_FALL_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DM_FALL_SLAVE_DELAY
-};
-
-#define _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY_NUM 9
-static const uint32_t _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
-	[_reg_PHY_RDDQS_X_RISE_SLAVE_DELAY_NUM] = {
-	_reg_PHY_RDDQS_DQ0_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ1_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ2_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ3_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ4_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ5_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ6_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DQ7_RISE_SLAVE_DELAY,
-	_reg_PHY_RDDQS_DM_RISE_SLAVE_DELAY
-};
-
-#define _reg_PHY_PAD_TERM_X_NUM 8
-static const uint32_t _reg_PHY_PAD_TERM_X[_reg_PHY_PAD_TERM_X_NUM] = {
-	_reg_PHY_PAD_FDBK_TERM,
-	_reg_PHY_PAD_DATA_TERM,
-	_reg_PHY_PAD_DQS_TERM,
-	_reg_PHY_PAD_ADDR_TERM,
-	_reg_PHY_PAD_CLK_TERM,
-	_reg_PHY_PAD_CKE_TERM,
-	_reg_PHY_PAD_RST_TERM,
-	_reg_PHY_PAD_CS_TERM
-};
-
-#define _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM 10
-static const uint32_t _reg_PHY_CLK_CACS_SLAVE_DELAY_X
-	[_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM] = {
-	_reg_PHY_ADR0_CLK_WR_SLAVE_DELAY,
-	_reg_PHY_ADR1_CLK_WR_SLAVE_DELAY,
-	_reg_PHY_ADR2_CLK_WR_SLAVE_DELAY,
-	_reg_PHY_ADR3_CLK_WR_SLAVE_DELAY,
-	_reg_PHY_ADR4_CLK_WR_SLAVE_DELAY,
-	_reg_PHY_ADR5_CLK_WR_SLAVE_DELAY,
-
-	_reg_PHY_GRP_SLAVE_DELAY_0,
-	_reg_PHY_GRP_SLAVE_DELAY_1,
-	_reg_PHY_GRP_SLAVE_DELAY_2,
-	_reg_PHY_GRP_SLAVE_DELAY_3
-};
-
-/* Prototypes */
-static inline uint32_t vch_nxt(uint32_t pos);
-static void cpg_write_32(uint32_t a, uint32_t v);
-static void pll3_control(uint32_t high);
-static inline void dsb_sev(void);
-static void wait_dbcmd(void);
-static void send_dbcmd(uint32_t cmd);
-static uint32_t reg_ddrphy_read(uint32_t phyno, uint32_t regadd);
-static void reg_ddrphy_write(uint32_t phyno, uint32_t regadd, uint32_t regdata);
-static void reg_ddrphy_write_a(uint32_t regadd, uint32_t regdata);
-static inline uint32_t ddr_regdef(uint32_t _regdef);
-static inline uint32_t ddr_regdef_adr(uint32_t _regdef);
-static inline uint32_t ddr_regdef_lsb(uint32_t _regdef);
-static void ddr_setval_s(uint32_t ch, uint32_t slice, uint32_t _regdef,
-			 uint32_t val);
-static uint32_t ddr_getval_s(uint32_t ch, uint32_t slice, uint32_t _regdef);
-static void ddr_setval(uint32_t ch, uint32_t regdef, uint32_t val);
-static void ddr_setval_ach_s(uint32_t slice, uint32_t regdef, uint32_t val);
-static void ddr_setval_ach(uint32_t regdef, uint32_t val);
-static void ddr_setval_ach_as(uint32_t regdef, uint32_t val);
-static uint32_t ddr_getval(uint32_t ch, uint32_t regdef);
-static uint32_t ddr_getval_ach(uint32_t regdef, uint32_t *p);
-static uint32_t ddr_getval_ach_as(uint32_t regdef, uint32_t *p);
-static void _tblcopy(uint32_t *to, const uint32_t *from, uint32_t size);
-static void ddrtbl_setval(uint32_t *tbl, uint32_t _regdef, uint32_t val);
-static uint32_t ddrtbl_getval(uint32_t *tbl, uint32_t _regdef);
-static uint32_t ddrphy_regif_chk(void);
-static inline void ddrphy_regif_idle(void);
-static uint16_t _f_scale(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv, uint32_t ps,
-			 uint16_t cyc);
-static void _f_scale_js2(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv,
-			 uint16_t *_js2);
-static int16_t _f_scale_adj(int16_t ps);
-static void ddrtbl_load(void);
-static void ddr_config_sub(void);
-static void get_ca_swizzle(uint32_t ch, uint32_t ddr_csn, uint32_t *p_swz);
-static void ddr_config_sub_h3v1x(void);
-static void ddr_config(void);
-static void dbsc_regset(void);
-static void dbsc_regset_post(void);
-static uint32_t dfi_init_start(void);
-static void change_lpddr4_en(uint32_t mode);
-static uint32_t set_term_code(void);
-static void ddr_register_set(void);
-static inline uint32_t wait_freqchgreq(uint32_t assert);
-static inline void set_freqchgack(uint32_t assert);
-static inline void set_dfifrequency(uint32_t freq);
-static uint32_t pll3_freq(uint32_t on);
-static void update_dly(void);
-static uint32_t pi_training_go(void);
-static uint32_t init_ddr(void);
-static uint32_t swlvl1(uint32_t ddr_csn, uint32_t reg_cs, uint32_t reg_kick);
-static uint32_t wdqdm_man1(void);
-static uint32_t wdqdm_man(void);
-static uint32_t rdqdm_man1(void);
-static uint32_t rdqdm_man(void);
-
-static int32_t _find_change(uint64_t val, uint32_t dir);
-static uint32_t _rx_offset_cal_updn(uint32_t code);
-static uint32_t rx_offset_cal(void);
-static uint32_t rx_offset_cal_hw(void);
-static void adjust_rddqs_latency(void);
-static void adjust_wpath_latency(void);
-
-struct ddrt_data {
-	int32_t init_temp;	/* Initial Temperature (do) */
-	uint32_t init_cal[4];	/* Initial io-code (4 is for H3) */
-	uint32_t tcomp_cal[4];	/* Temp. compensated io-code (4 is for H3) */
-};
-
-static struct ddrt_data tcal;
-
-static void pvtcode_update(void);
-static void pvtcode_update2(void);
-static void ddr_padcal_tcompensate_getinit(uint32_t override);
-
-/* load board configuration */
-#include "boot_init_dram_config.c"
-
-#ifndef DDR_FAST_INIT
-static uint32_t rdqdm_le[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
-static uint32_t rdqdm_te[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
-static uint32_t rdqdm_nw[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2][9];
-static uint32_t rdqdm_win[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
-static uint32_t rdqdm_st[DRAM_CH_CNT][CS_CNT][SLICE_CNT * 2];
-static void rdqdm_clr1(uint32_t ch, uint32_t ddr_csn);
-static uint32_t rdqdm_ana1(uint32_t ch, uint32_t ddr_csn);
-
-static uint32_t wdqdm_le[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
-static uint32_t wdqdm_te[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
-static uint32_t wdqdm_dly[DRAM_CH_CNT][CS_CNT][SLICE_CNT][9];
-static uint32_t wdqdm_st[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
-static uint32_t wdqdm_win[DRAM_CH_CNT][CS_CNT][SLICE_CNT];
-static void wdqdm_clr1(uint32_t ch, uint32_t ddr_csn);
-static uint32_t wdqdm_ana1(uint32_t ch, uint32_t ddr_csn);
-#endif/* DDR_FAST_INIT */
-
-/* macro for channel selection loop */
-static inline uint32_t vch_nxt(uint32_t pos)
-{
-	uint32_t posn;
-
-	for (posn = pos; posn < DRAM_CH_CNT; posn++) {
-		if (ddr_phyvalid & (1U << posn))
-			break;
-	}
-	return posn;
-}
-
-#define foreach_vch(ch) \
-for (ch = vch_nxt(0); ch < DRAM_CH_CNT; ch = vch_nxt(ch + 1))
-
-#define foreach_ech(ch) \
-for (ch = 0; ch < DRAM_CH_CNT; ch++)
-
-/* Printing functions */
-#define MSG_LF(...)
-
-/* clock settings, reset control */
-static void cpg_write_32(uint32_t a, uint32_t v)
-{
-	mmio_write_32(CPG_CPGWPR, ~v);
-	mmio_write_32(a, v);
-}
-
-static void pll3_control(uint32_t high)
-{
-	uint32_t data_l, data_div, data_mul, tmp_div;
-
-	if (high) {
-		tmp_div = 3999 * brd_clkdiv * (brd_clkdiva + 1) /
-			(brd_clk * ddr_mul) / 2;
-		data_mul = ((ddr_mul * tmp_div) - 1) << 24;
-		pll3_mode = 1;
-		loop_max = 2;
-	} else {
-		tmp_div = 3999 * brd_clkdiv * (brd_clkdiva + 1) /
-			(brd_clk * ddr0800_mul) / 2;
-		data_mul = ((ddr0800_mul * tmp_div) - 1) << 24;
-		pll3_mode = 0;
-		loop_max = 8;
-	}
-
-	switch (tmp_div) {
-	case 1:
-		data_div = 0;
-		break;
-	case 2:
-	case 3:
-	case 4:
-		data_div = tmp_div;
-		break;
-	default:
-		data_div = 6;
-		data_mul = (data_mul * tmp_div) / 3;
-		break;
-	}
-	data_mul = data_mul | (brd_clkdiva << 7);
-
-	/* PLL3 disable */
-	data_l = mmio_read_32(CPG_PLLECR) & ~CPG_PLLECR_PLL3E_BIT;
-	cpg_write_32(CPG_PLLECR, data_l);
-	dsb_sev();
-
-	if ((prr_product == PRR_PRODUCT_M3) ||
-	    ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_20))) {
-		/* PLL3 DIV resetting(Lowest value:3) */
-		data_l = 0x00030003 | (0xFF80FF80 & mmio_read_32(CPG_FRQCRD));
-		cpg_write_32(CPG_FRQCRD, data_l);
-		dsb_sev();
-
-		/* zb3 clk stop */
-		data_l = CPG_ZB3CKCR_ZB3ST_BIT | mmio_read_32(CPG_ZB3CKCR);
-		cpg_write_32(CPG_ZB3CKCR, data_l);
-		dsb_sev();
-
-		/* PLL3 enable */
-		data_l = CPG_PLLECR_PLL3E_BIT | mmio_read_32(CPG_PLLECR);
-		cpg_write_32(CPG_PLLECR, data_l);
-		dsb_sev();
-
-		do {
-			data_l = mmio_read_32(CPG_PLLECR);
-		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
-		dsb_sev();
-
-		/* PLL3 DIV resetting (Highest value:0) */
-		data_l = (0xFF80FF80 & mmio_read_32(CPG_FRQCRD));
-		cpg_write_32(CPG_FRQCRD, data_l);
-		dsb_sev();
-
-		/* DIV SET KICK */
-		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
-		cpg_write_32(CPG_FRQCRB, data_l);
-		dsb_sev();
-
-		/* PLL3 multiplie set */
-		cpg_write_32(CPG_PLL3CR, data_mul);
-		dsb_sev();
-
-		do {
-			data_l = mmio_read_32(CPG_PLLECR);
-		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
-		dsb_sev();
-
-		/* PLL3 DIV resetting(Target value) */
-		data_l = (data_div << 16) | data_div |
-			 (mmio_read_32(CPG_FRQCRD) & 0xFF80FF80);
-		cpg_write_32(CPG_FRQCRD, data_l);
-		dsb_sev();
-
-		/* DIV SET KICK */
-		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
-		cpg_write_32(CPG_FRQCRB, data_l);
-		dsb_sev();
-
-		do {
-			data_l = mmio_read_32(CPG_PLLECR);
-		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
-		dsb_sev();
-
-		/* zb3 clk start */
-		data_l = (~CPG_ZB3CKCR_ZB3ST_BIT) & mmio_read_32(CPG_ZB3CKCR);
-		cpg_write_32(CPG_ZB3CKCR, data_l);
-		dsb_sev();
-
-	} else { /*  H3Ver.3.0/M3N/V3H */
-
-		/* PLL3 multiplie set */
-		cpg_write_32(CPG_PLL3CR, data_mul);
-		dsb_sev();
-
-		/* PLL3 DIV set(Target value) */
-		data_l = (data_div << 16) | data_div |
-			 (mmio_read_32(CPG_FRQCRD) & 0xFF80FF80);
-		cpg_write_32(CPG_FRQCRD, data_l);
-
-		/* DIV SET KICK */
-		data_l = CPG_FRQCRB_KICK_BIT | mmio_read_32(CPG_FRQCRB);
-		cpg_write_32(CPG_FRQCRB, data_l);
-		dsb_sev();
-
-		/* PLL3 enable */
-		data_l = CPG_PLLECR_PLL3E_BIT | mmio_read_32(CPG_PLLECR);
-		cpg_write_32(CPG_PLLECR, data_l);
-		dsb_sev();
-
-		do {
-			data_l = mmio_read_32(CPG_PLLECR);
-		} while ((data_l & CPG_PLLECR_PLL3ST_BIT) == 0);
-		dsb_sev();
-	}
-}
-
-/* barrier */
-static inline void dsb_sev(void)
-{
-	__asm__ __volatile__("dsb sy");
-}
-
-/* DDR memory register access */
-static void wait_dbcmd(void)
-{
-	uint32_t data_l;
-	/* dummy read */
-	data_l = mmio_read_32(DBSC_DBCMD);
-	dsb_sev();
-	while (1) {
-		/* wait DBCMD 1=busy, 0=ready */
-		data_l = mmio_read_32(DBSC_DBWAIT);
-		dsb_sev();
-		if ((data_l & 0x00000001) == 0x00)
-			break;
-	}
-}
-
-static void send_dbcmd(uint32_t cmd)
-{
-	/* dummy read */
-	wait_dbcmd();
-	mmio_write_32(DBSC_DBCMD, cmd);
-	dsb_sev();
-}
-
-static void dbwait_loop(uint32_t wait_loop)
-{
-	uint32_t i;
-
-	for (i = 0; i < wait_loop; i++)
-		wait_dbcmd();
-}
-
-/* DDRPHY register access (raw) */
-static uint32_t reg_ddrphy_read(uint32_t phyno, uint32_t regadd)
-{
-	uint32_t val;
-	uint32_t loop;
-
-	val = 0;
-	if ((prr_product != PRR_PRODUCT_M3N) &&
-	    (prr_product != PRR_PRODUCT_V3H)) {
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
-		dsb_sev();
-
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
-			dsb_sev();
-		}
-		dsb_sev();
-
-		for (loop = 0; loop < loop_max; loop++) {
-			val = mmio_read_32(DBSC_DBPDRGD(phyno));
-			dsb_sev();
-		}
-		(void)val;
-	} else {
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00004000);
-		dsb_sev();
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) !=
-		       (regadd | 0x0000C000)) {
-			dsb_sev();
-		};
-		val = mmio_read_32(DBSC_DBPDRGA(phyno));
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
-			dsb_sev();
-		};
-		dsb_sev();
-
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
-			dsb_sev();
-		};
-
-		dsb_sev();
-		val = mmio_read_32(DBSC_DBPDRGD(phyno));
-		dsb_sev();
-		(void)val;
-	}
-	return val;
-}
-
-static void reg_ddrphy_write(uint32_t phyno, uint32_t regadd, uint32_t regdata)
-{
-	uint32_t val;
-	uint32_t loop;
-
-	if ((prr_product != PRR_PRODUCT_M3N) &&
-	    (prr_product != PRR_PRODUCT_V3H)) {
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
-		dsb_sev();
-		for (loop = 0; loop < loop_max; loop++) {
-			val = mmio_read_32(DBSC_DBPDRGA(phyno));
-			dsb_sev();
-		}
-		mmio_write_32(DBSC_DBPDRGD(phyno), regdata);
-		dsb_sev();
-
-		for (loop = 0; loop < loop_max; loop++) {
-			val = mmio_read_32(DBSC_DBPDRGD(phyno));
-			dsb_sev();
-		}
-	} else {
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
-		dsb_sev();
-
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
-			dsb_sev();
-		};
-		dsb_sev();
-
-		mmio_write_32(DBSC_DBPDRGD(phyno), regdata);
-		dsb_sev();
-
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) !=
-		       (regadd | 0x00008000)) {
-			dsb_sev();
-		};
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd | 0x00008000);
-
-		while (mmio_read_32(DBSC_DBPDRGA(phyno)) != regadd) {
-			dsb_sev();
-		};
-		dsb_sev();
-
-		mmio_write_32(DBSC_DBPDRGA(phyno), regadd);
-	}
-	(void)val;
-}
-
-static void reg_ddrphy_write_a(uint32_t regadd, uint32_t regdata)
-{
-	uint32_t ch;
-	uint32_t val;
-	uint32_t loop;
-
-	if ((prr_product != PRR_PRODUCT_M3N) &&
-	    (prr_product != PRR_PRODUCT_V3H)) {
-		foreach_vch(ch) {
-			mmio_write_32(DBSC_DBPDRGA(ch), regadd);
-			dsb_sev();
-		}
-
-		foreach_vch(ch) {
-			mmio_write_32(DBSC_DBPDRGD(ch), regdata);
-			dsb_sev();
-		}
-
-		for (loop = 0; loop < loop_max; loop++) {
-			val = mmio_read_32(DBSC_DBPDRGD(0));
-			dsb_sev();
-		}
-		(void)val;
-	} else {
-		foreach_vch(ch) {
-			reg_ddrphy_write(ch, regadd, regdata);
-			dsb_sev();
-		}
-	}
-}
-
-static inline void ddrphy_regif_idle(void)
-{
-	uint32_t val;
-
-	val = reg_ddrphy_read(0, ddr_regdef_adr(_reg_PI_INT_STATUS));
-	dsb_sev();
-	(void)val;
-}
-
-/* DDRPHY register access (field modify) */
-static inline uint32_t ddr_regdef(uint32_t _regdef)
-{
-	return p_ddr_regdef_tbl[_regdef];
-}
-
-static inline uint32_t ddr_regdef_adr(uint32_t _regdef)
-{
-	return DDR_REGDEF_ADR(p_ddr_regdef_tbl[_regdef]);
-}
-
-static inline uint32_t ddr_regdef_lsb(uint32_t _regdef)
-{
-	return DDR_REGDEF_LSB(p_ddr_regdef_tbl[_regdef]);
-}
-
-static void ddr_setval_s(uint32_t ch, uint32_t slice, uint32_t _regdef,
-			 uint32_t val)
-{
-	uint32_t adr;
-	uint32_t lsb;
-	uint32_t len;
-	uint32_t msk;
-	uint32_t tmp;
-	uint32_t regdef;
-
-	regdef = ddr_regdef(_regdef);
-	adr = DDR_REGDEF_ADR(regdef) + 0x80 * slice;
-	len = DDR_REGDEF_LEN(regdef);
-	lsb = DDR_REGDEF_LSB(regdef);
-	if (len == 0x20)
-		msk = 0xffffffff;
-	else
-		msk = ((1U << len) - 1) << lsb;
-
-	tmp = reg_ddrphy_read(ch, adr);
-	tmp = (tmp & (~msk)) | ((val << lsb) & msk);
-	reg_ddrphy_write(ch, adr, tmp);
-}
-
-static uint32_t ddr_getval_s(uint32_t ch, uint32_t slice, uint32_t _regdef)
-{
-	uint32_t adr;
-	uint32_t lsb;
-	uint32_t len;
-	uint32_t msk;
-	uint32_t tmp;
-	uint32_t regdef;
-
-	regdef = ddr_regdef(_regdef);
-	adr = DDR_REGDEF_ADR(regdef) + 0x80 * slice;
-	len = DDR_REGDEF_LEN(regdef);
-	lsb = DDR_REGDEF_LSB(regdef);
-	if (len == 0x20)
-		msk = 0xffffffff;
-	else
-		msk = ((1U << len) - 1);
-
-	tmp = reg_ddrphy_read(ch, adr);
-	tmp = (tmp >> lsb) & msk;
-
-	return tmp;
-}
-
-static void ddr_setval(uint32_t ch, uint32_t regdef, uint32_t val)
-{
-	ddr_setval_s(ch, 0, regdef, val);
-}
-
-static void ddr_setval_ach_s(uint32_t slice, uint32_t regdef, uint32_t val)
-{
-	uint32_t ch;
-
-	foreach_vch(ch)
-	    ddr_setval_s(ch, slice, regdef, val);
-}
-
-static void ddr_setval_ach(uint32_t regdef, uint32_t val)
-{
-	ddr_setval_ach_s(0, regdef, val);
-}
-
-static void ddr_setval_ach_as(uint32_t regdef, uint32_t val)
-{
-	uint32_t slice;
-
-	for (slice = 0; slice < SLICE_CNT; slice++)
-		ddr_setval_ach_s(slice, regdef, val);
-}
-
-static uint32_t ddr_getval(uint32_t ch, uint32_t regdef)
-{
-	return ddr_getval_s(ch, 0, regdef);
-}
-
-static uint32_t ddr_getval_ach(uint32_t regdef, uint32_t *p)
-{
-	uint32_t ch;
-
-	foreach_vch(ch)
-	    p[ch] = ddr_getval_s(ch, 0, regdef);
-	return p[0];
-}
-
-static uint32_t ddr_getval_ach_as(uint32_t regdef, uint32_t *p)
-{
-	uint32_t ch, slice;
-	uint32_t *pp;
-
-	pp = p;
-	foreach_vch(ch)
-		for (slice = 0; slice < SLICE_CNT; slice++)
-			*pp++ = ddr_getval_s(ch, slice, regdef);
-	return p[0];
-}
-
-/* handling functions for setteing ddrphy value table */
-static void _tblcopy(uint32_t *to, const uint32_t *from, uint32_t size)
-{
-	uint32_t i;
-
-	for (i = 0; i < size; i++) {
-		to[i] = from[i];
-	}
-}
-
-static void ddrtbl_setval(uint32_t *tbl, uint32_t _regdef, uint32_t val)
-{
-	uint32_t adr;
-	uint32_t lsb;
-	uint32_t len;
-	uint32_t msk;
-	uint32_t tmp;
-	uint32_t adrmsk;
-	uint32_t regdef;
-
-	regdef = ddr_regdef(_regdef);
-	adr = DDR_REGDEF_ADR(regdef);
-	len = DDR_REGDEF_LEN(regdef);
-	lsb = DDR_REGDEF_LSB(regdef);
-	if (len == 0x20)
-		msk = 0xffffffff;
-	else
-		msk = ((1U << len) - 1) << lsb;
-
-	if (adr < 0x400) {
-		adrmsk = 0xff;
-	} else {
-		adrmsk = 0x7f;
-	}
-
-	tmp = tbl[adr & adrmsk];
-	tmp = (tmp & (~msk)) | ((val << lsb) & msk);
-	tbl[adr & adrmsk] = tmp;
-}
-
-static uint32_t ddrtbl_getval(uint32_t *tbl, uint32_t _regdef)
-{
-	uint32_t adr;
-	uint32_t lsb;
-	uint32_t len;
-	uint32_t msk;
-	uint32_t tmp;
-	uint32_t adrmsk;
-	uint32_t regdef;
-
-	regdef = ddr_regdef(_regdef);
-	adr = DDR_REGDEF_ADR(regdef);
-	len = DDR_REGDEF_LEN(regdef);
-	lsb = DDR_REGDEF_LSB(regdef);
-	if (len == 0x20)
-		msk = 0xffffffff;
-	else
-		msk = ((1U << len) - 1);
-
-	if (adr < 0x400) {
-		adrmsk = 0xff;
-	} else {
-		adrmsk = 0x7f;
-	}
-
-	tmp = tbl[adr & adrmsk];
-	tmp = (tmp >> lsb) & msk;
-
-	return tmp;
-}
-
-/* DDRPHY register access handling */
-static uint32_t ddrphy_regif_chk(void)
-{
-	uint32_t tmp_ach[DRAM_CH_CNT];
-	uint32_t ch;
-	uint32_t err;
-	uint32_t PI_VERSION_CODE;
-
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
-	    (prr_product == PRR_PRODUCT_M3)) {
-		PI_VERSION_CODE = 0x2041; /* H3 Ver.1.x/M3-W */
-	} else {
-		PI_VERSION_CODE = 0x2040; /* H3 Ver.2.0 or later/M3-N/V3H */
-	}
-
-	ddr_getval_ach(_reg_PI_VERSION, (uint32_t *)tmp_ach);
-	err = 0;
-	foreach_vch(ch) {
-		if (tmp_ach[ch] != PI_VERSION_CODE)
-			err = 1;
-	}
-	return err;
-}
-
-/* functions and parameters for timing setting */
-struct _jedec_spec1 {
-	uint16_t fx3;
-	uint8_t rlwodbi;
-	uint8_t rlwdbi;
-	uint8_t WL;
-	uint8_t nwr;
-	uint8_t nrtp;
-	uint8_t odtlon;
-	uint8_t MR1;
-	uint8_t MR2;
-};
-
-#define JS1_USABLEC_SPEC_LO 2
-#define JS1_USABLEC_SPEC_HI 5
-#define JS1_FREQ_TBL_NUM 8
-#define JS1_MR1(f) (0x04 | ((f) << 4))
-#define JS1_MR2(f) (0x00 | ((f) << 3) | (f))
-const struct _jedec_spec1 js1[JS1_FREQ_TBL_NUM] = {
-	/* 533.333Mbps */
-	{  800,  6,  6,  4,  6,  8, 0, JS1_MR1(0), JS1_MR2(0) | 0x40 },
-	/* 1066.666Mbps */
-	{ 1600, 10, 12,  8, 10,  8, 0, JS1_MR1(1), JS1_MR2(1) | 0x40 },
-	/* 1600.000Mbps */
-	{ 2400, 14, 16, 12, 16,  8, 6, JS1_MR1(2), JS1_MR2(2) | 0x40 },
-	/* 2133.333Mbps */
-	{ 3200, 20, 22, 10, 20,  8, 4, JS1_MR1(3), JS1_MR2(3) },
-	/* 2666.666Mbps */
-	{ 4000, 24, 28, 12, 24, 10, 4, JS1_MR1(4), JS1_MR2(4) },
-	/* 3200.000Mbps */
-	{ 4800, 28, 32, 14, 30, 12, 6, JS1_MR1(5), JS1_MR2(5) },
-	/* 3733.333Mbps */
-	{ 5600, 32, 36, 16, 34, 14, 6, JS1_MR1(6), JS1_MR2(6) },
-	/* 4266.666Mbps */
-	{ 6400, 36, 40, 18, 40, 16, 8, JS1_MR1(7), JS1_MR2(7) }
-};
-
-struct _jedec_spec2 {
-	uint16_t ps;
-	uint16_t cyc;
-};
-
-#define js2_tsr 0
-#define js2_txp 1
-#define js2_trtp 2
-#define js2_trcd 3
-#define js2_trppb 4
-#define js2_trpab 5
-#define js2_tras 6
-#define js2_twr 7
-#define js2_twtr 8
-#define js2_trrd 9
-#define js2_tppd 10
-#define js2_tfaw 11
-#define js2_tdqsck 12
-#define js2_tckehcmd 13
-#define js2_tckelcmd 14
-#define js2_tckelpd 15
-#define js2_tmrr 16
-#define js2_tmrw 17
-#define js2_tmrd 18
-#define js2_tzqcalns 19
-#define js2_tzqlat 20
-#define js2_tiedly 21
-#define js2_tODTon_min 22
-#define JS2_TBLCNT 23
-
-#define js2_trcpb (JS2_TBLCNT)
-#define js2_trcab (JS2_TBLCNT + 1)
-#define js2_trfcab (JS2_TBLCNT + 2)
-#define JS2_CNT (JS2_TBLCNT + 3)
-
-#ifndef JS2_DERATE
-#define JS2_DERATE 0
-#endif
-const struct _jedec_spec2 jedec_spec2[2][JS2_TBLCNT] = {
-	{
-/*tSR   */ {15000, 3},
-/*tXP   */ {7500, 3},
-/*tRTP  */ {7500, 8},
-/*tRCD  */ {18000, 4},
-/*tRPpb */ {18000, 3},
-/*tRPab */ {21000, 3},
-/*tRAS  */ {42000, 3},
-/*tWR   */ {18000, 4},
-/*tWTR  */ {10000, 8},
-/*tRRD  */ {10000, 4},
-/*tPPD  */ {0, 0},
-/*tFAW  */ {40000, 0},
-/*tDQSCK*/ {3500, 0},
-/*tCKEHCMD*/ {7500, 3},
-/*tCKELCMD*/ {7500, 3},
-/*tCKELPD*/ {7500, 3},
-/*tMRR*/ {0, 8},
-/*tMRW*/ {10000, 10},
-/*tMRD*/ {14000, 10},
-/*tZQCALns*/ {1000 * 10, 0},
-/*tZQLAT*/ {30000, 10},
-/*tIEdly*/ {12500, 0},
-/*tODTon_min*/ {1500, 0}
-	 }, {
-/*tSR   */ {15000, 3},
-/*tXP   */ {7500, 3},
-/*tRTP  */ {7500, 8},
-/*tRCD  */ {19875, 4},
-/*tRPpb */ {19875, 3},
-/*tRPab */ {22875, 3},
-/*tRAS  */ {43875, 3},
-/*tWR   */ {18000, 4},
-/*tWTR  */ {10000, 8},
-/*tRRD  */ {11875, 4},
-/*tPPD  */ {0, 0},
-/*tFAW  */ {40000, 0},
-/*tDQSCK*/ {3600, 0},
-/*tCKEHCMD*/ {7500, 3},
-/*tCKELCMD*/ {7500, 3},
-/*tCKELPD*/ {7500, 3},
-/*tMRR*/ {0, 8},
-/*tMRW*/ {10000, 10},
-/*tMRD*/ {14000, 10},
-/*tZQCALns*/ {1000 * 10, 0},
-/*tZQLAT*/ {30000, 10},
-/*tIEdly*/ {12500, 0},
-/*tODTon_min*/ {1500, 0}
-	}
-};
-
-const uint16_t jedec_spec2_trfc_ab[7] = {
-/*	4Gb, 6Gb, 8Gb,12Gb, 16Gb, 24Gb(non), 32Gb(non)	*/
-	 130, 180, 180, 280, 280, 560, 560
-};
-
-static uint32_t js1_ind;
-static uint16_t js2[JS2_CNT];
-static uint8_t RL;
-static uint8_t WL;
-
-static uint16_t _f_scale(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv, uint32_t ps,
-			 uint16_t cyc)
-{
-	uint32_t tmp;
-	uint32_t div;
-
-	tmp = (((uint32_t)(ps) + 9) / 10) * _ddr_mbps;
-	div = tmp / (200000 * _ddr_mbpsdiv);
-	if (tmp != (div * 200000 * _ddr_mbpsdiv))
-		div = div + 1;
-
-	if (div > cyc)
-		return (uint16_t)div;
-	return cyc;
-}
-
-static void _f_scale_js2(uint32_t _ddr_mbps, uint32_t _ddr_mbpsdiv,
-			 uint16_t *_js2)
-{
-	int i;
-
-	for (i = 0; i < JS2_TBLCNT; i++) {
-		_js2[i] = _f_scale(_ddr_mbps, _ddr_mbpsdiv,
-				  1UL * jedec_spec2[JS2_DERATE][i].ps,
-				  jedec_spec2[JS2_DERATE][i].cyc);
-	}
-
-	_js2[js2_trcpb] = _js2[js2_tras] + _js2[js2_trppb];
-	_js2[js2_trcab] = _js2[js2_tras] + _js2[js2_trpab];
-}
-
-/* scaler for DELAY value */
-static int16_t _f_scale_adj(int16_t ps)
-{
-	int32_t tmp;
-	/*
-	 * tmp = (int32_t)512 * ps * ddr_mbps /2 / ddr_mbpsdiv / 1000 / 1000;
-	 *     = ps * ddr_mbps /2 / ddr_mbpsdiv *512 / 8 / 8 / 125 / 125
-	 *     = ps * ddr_mbps / ddr_mbpsdiv *4 / 125 / 125
-	 */
-	tmp =
-	    (int32_t)4 * (int32_t)ps * (int32_t)ddr_mbps /
-	    (int32_t)ddr_mbpsdiv;
-	tmp = (int32_t)tmp / (int32_t)15625;
-
-	return (int16_t)tmp;
-}
-
-static const uint32_t reg_pi_mr1_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR1_DATA_F0_0,
-	 _reg_PI_MR1_DATA_F0_1,
-	 _reg_PI_MR1_DATA_F0_2,
-	 _reg_PI_MR1_DATA_F0_3},
-	{
-	 _reg_PI_MR1_DATA_F1_0,
-	 _reg_PI_MR1_DATA_F1_1,
-	 _reg_PI_MR1_DATA_F1_2,
-	 _reg_PI_MR1_DATA_F1_3}
-};
-
-static const uint32_t reg_pi_mr2_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR2_DATA_F0_0,
-	 _reg_PI_MR2_DATA_F0_1,
-	 _reg_PI_MR2_DATA_F0_2,
-	 _reg_PI_MR2_DATA_F0_3},
-	{
-	 _reg_PI_MR2_DATA_F1_0,
-	 _reg_PI_MR2_DATA_F1_1,
-	 _reg_PI_MR2_DATA_F1_2,
-	 _reg_PI_MR2_DATA_F1_3}
-};
-
-static const uint32_t reg_pi_mr3_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR3_DATA_F0_0,
-	 _reg_PI_MR3_DATA_F0_1,
-	 _reg_PI_MR3_DATA_F0_2,
-	 _reg_PI_MR3_DATA_F0_3},
-	{
-	 _reg_PI_MR3_DATA_F1_0,
-	 _reg_PI_MR3_DATA_F1_1,
-	 _reg_PI_MR3_DATA_F1_2,
-	 _reg_PI_MR3_DATA_F1_3}
-};
-
-const uint32_t reg_pi_mr11_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR11_DATA_F0_0,
-	 _reg_PI_MR11_DATA_F0_1,
-	 _reg_PI_MR11_DATA_F0_2,
-	 _reg_PI_MR11_DATA_F0_3},
-	{
-	 _reg_PI_MR11_DATA_F1_0,
-	 _reg_PI_MR11_DATA_F1_1,
-	 _reg_PI_MR11_DATA_F1_2,
-	 _reg_PI_MR11_DATA_F1_3}
-};
-
-const uint32_t reg_pi_mr12_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR12_DATA_F0_0,
-	 _reg_PI_MR12_DATA_F0_1,
-	 _reg_PI_MR12_DATA_F0_2,
-	 _reg_PI_MR12_DATA_F0_3},
-	{
-	 _reg_PI_MR12_DATA_F1_0,
-	 _reg_PI_MR12_DATA_F1_1,
-	 _reg_PI_MR12_DATA_F1_2,
-	 _reg_PI_MR12_DATA_F1_3}
-};
-
-const uint32_t reg_pi_mr14_data_fx_csx[2][CSAB_CNT] = {
-	{
-	 _reg_PI_MR14_DATA_F0_0,
-	 _reg_PI_MR14_DATA_F0_1,
-	 _reg_PI_MR14_DATA_F0_2,
-	 _reg_PI_MR14_DATA_F0_3},
-	{
-	 _reg_PI_MR14_DATA_F1_0,
-	 _reg_PI_MR14_DATA_F1_1,
-	 _reg_PI_MR14_DATA_F1_2,
-	 _reg_PI_MR14_DATA_F1_3}
-};
-
-/*
- * regif pll w/a   ( REGIF H3 Ver.2.0 or later/M3-N/V3H WA )
- */
-static void regif_pll_wa(void)
-{
-	uint32_t ch;
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		// PLL setting for PHY : H3 Ver.1.x
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_WAIT),
-				   (0x0064U <<
-				    ddr_regdef_lsb(_reg_PHY_PLL_WAIT)));
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL),
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_PLL_CTRL));
-
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LP4_BOOT_PLL_CTRL),
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_LP4_BOOT_PLL_CTRL));
-
-	} else {
-		/*  PLL setting for PHY : M3-W/M3-N/V3H/H3 Ver.2.0 or later */
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_WAIT),
-				   (0x5064U <<
-				    ddr_regdef_lsb(_reg_PHY_PLL_WAIT)));
-
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL),
-				   (ddrtbl_getval
-				    (_cnf_DDR_PHY_ADR_G_REGSET,
-				     _reg_PHY_PLL_CTRL_TOP) << 16) |
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_PLL_CTRL));
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_PLL_CTRL_CA),
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_PLL_CTRL_CA));
-
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LP4_BOOT_PLL_CTRL),
-				   (ddrtbl_getval
-				    (_cnf_DDR_PHY_ADR_G_REGSET,
-				     _reg_PHY_LP4_BOOT_PLL_CTRL_CA) << 16) |
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_LP4_BOOT_PLL_CTRL));
-		reg_ddrphy_write_a(ddr_regdef_adr
-				   (_reg_PHY_LP4_BOOT_TOP_PLL_CTRL),
-				   ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-						 _reg_PHY_LP4_BOOT_TOP_PLL_CTRL
-						 ));
-	}
-
-	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_LPDDR3_CS),
-			   _cnf_DDR_PHY_ADR_G_REGSET
-			   [ddr_regdef_adr(_reg_PHY_LPDDR3_CS) -
-			   DDR_PHY_ADR_G_REGSET_OFS]);
-
-	/* protect register interface */
-	ddrphy_regif_idle();
-	pll3_control(0);
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		/*  non */
-	} else {
-		reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_DLL_RST_EN),
-				   (0x01U <<
-				    ddr_regdef_lsb(_reg_PHY_DLL_RST_EN)));
-		ddrphy_regif_idle();
-	}
-
-	/* init start */
-	/* dbdficnt0:
-	 * dfi_dram_clk_disable=1
-	 * dfi_frequency = 0
-	 * freq_ratio = 01 (2:1)
-	 * init_start =0
-	 */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F10);
-	dsb_sev();
-
-	/* dbdficnt0:
-	 * dfi_dram_clk_disable=1
-	 * dfi_frequency = 0
-	 * freq_ratio = 01 (2:1)
-	 * init_start =1
-	 */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F11);
-	dsb_sev();
-
-	foreach_ech(ch)
-	if ((board_cnf->phyvalid) & BIT(ch))
-		while ((mmio_read_32(DBSC_PLL_LOCK(ch)) & 0x1f) != 0x1f)
-			;
-	dsb_sev();
-}
-
-/* load table data into DDR registers */
-static void ddrtbl_load(void)
-{
-	uint32_t i;
-	uint32_t slice;
-	uint32_t csab;
-	uint32_t adr;
-	uint32_t data_l;
-	uint32_t tmp[3];
-	uint16_t dataS;
-
-	/* TIMING REGISTERS */
-	/* search jedec_spec1 index */
-	for (i = JS1_USABLEC_SPEC_LO; i < JS1_FREQ_TBL_NUM - 1; i++) {
-		if (js1[i].fx3 * 2U * ddr_mbpsdiv >= ddr_mbps * 3U)
-			break;
-	}
-	if (i > JS1_USABLEC_SPEC_HI)
-		js1_ind = JS1_USABLEC_SPEC_HI;
-	else
-		js1_ind = i;
-
-	if (board_cnf->dbi_en)
-		RL = js1[js1_ind].rlwdbi;
-	else
-		RL = js1[js1_ind].rlwodbi;
-
-	WL = js1[js1_ind].WL;
-
-	/* calculate jedec_spec2 */
-	_f_scale_js2(ddr_mbps, ddr_mbpsdiv, js2);
-
-	/* PREPARE TBL */
-	if (prr_product == PRR_PRODUCT_H3) {
-		if (prr_cut <= PRR_PRODUCT_11) {
-			/*  H3 Ver.1.x */
-			_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
-				 DDR_PHY_SLICE_REGSET_H3,
-				 DDR_PHY_SLICE_REGSET_NUM_H3);
-			_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
-				 DDR_PHY_ADR_V_REGSET_H3,
-				 DDR_PHY_ADR_V_REGSET_NUM_H3);
-			_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET,
-				 DDR_PHY_ADR_I_REGSET_H3,
-				 DDR_PHY_ADR_I_REGSET_NUM_H3);
-			_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
-				 DDR_PHY_ADR_G_REGSET_H3,
-				 DDR_PHY_ADR_G_REGSET_NUM_H3);
-			_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_H3,
-				 DDR_PI_REGSET_NUM_H3);
-
-			DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_H3;
-			DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_H3;
-			DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_H3;
-			DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_H3;
-			DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_H3;
-			DDR_PHY_SLICE_REGSET_SIZE =
-			    DDR_PHY_SLICE_REGSET_SIZE_H3;
-			DDR_PHY_ADR_V_REGSET_SIZE =
-			    DDR_PHY_ADR_V_REGSET_SIZE_H3;
-			DDR_PHY_ADR_I_REGSET_SIZE =
-			    DDR_PHY_ADR_I_REGSET_SIZE_H3;
-			DDR_PHY_ADR_G_REGSET_SIZE =
-			    DDR_PHY_ADR_G_REGSET_SIZE_H3;
-			DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_H3;
-			DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_H3;
-			DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_H3;
-			DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_H3;
-			DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_H3;
-			DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_H3;
-
-			DDR_PHY_ADR_I_NUM = 1;
-		} else {
-			/*  H3 Ver.2.0 or later */
-			_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
-				 DDR_PHY_SLICE_REGSET_H3VER2,
-				 DDR_PHY_SLICE_REGSET_NUM_H3VER2);
-			_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
-				 DDR_PHY_ADR_V_REGSET_H3VER2,
-				 DDR_PHY_ADR_V_REGSET_NUM_H3VER2);
-			_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
-				 DDR_PHY_ADR_G_REGSET_H3VER2,
-				 DDR_PHY_ADR_G_REGSET_NUM_H3VER2);
-			_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_H3VER2,
-				 DDR_PI_REGSET_NUM_H3VER2);
-
-			DDR_PHY_SLICE_REGSET_OFS =
-			    DDR_PHY_SLICE_REGSET_OFS_H3VER2;
-			DDR_PHY_ADR_V_REGSET_OFS =
-			    DDR_PHY_ADR_V_REGSET_OFS_H3VER2;
-			DDR_PHY_ADR_G_REGSET_OFS =
-			    DDR_PHY_ADR_G_REGSET_OFS_H3VER2;
-			DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_H3VER2;
-			DDR_PHY_SLICE_REGSET_SIZE =
-			    DDR_PHY_SLICE_REGSET_SIZE_H3VER2;
-			DDR_PHY_ADR_V_REGSET_SIZE =
-			    DDR_PHY_ADR_V_REGSET_SIZE_H3VER2;
-			DDR_PHY_ADR_G_REGSET_SIZE =
-			    DDR_PHY_ADR_G_REGSET_SIZE_H3VER2;
-			DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_H3VER2;
-			DDR_PHY_SLICE_REGSET_NUM =
-			    DDR_PHY_SLICE_REGSET_NUM_H3VER2;
-			DDR_PHY_ADR_V_REGSET_NUM =
-			    DDR_PHY_ADR_V_REGSET_NUM_H3VER2;
-			DDR_PHY_ADR_G_REGSET_NUM =
-			    DDR_PHY_ADR_G_REGSET_NUM_H3VER2;
-			DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_H3VER2;
-
-			DDR_PHY_ADR_I_NUM = 0;
-		}
-	} else if (prr_product == PRR_PRODUCT_M3) {
-		/*  M3-W */
-		_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
-			 DDR_PHY_SLICE_REGSET_M3, DDR_PHY_SLICE_REGSET_NUM_M3);
-		_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET,
-			 DDR_PHY_ADR_V_REGSET_M3, DDR_PHY_ADR_V_REGSET_NUM_M3);
-		_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET,
-			 DDR_PHY_ADR_I_REGSET_M3, DDR_PHY_ADR_I_REGSET_NUM_M3);
-		_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET,
-			 DDR_PHY_ADR_G_REGSET_M3, DDR_PHY_ADR_G_REGSET_NUM_M3);
-		_tblcopy(_cnf_DDR_PI_REGSET,
-			 DDR_PI_REGSET_M3, DDR_PI_REGSET_NUM_M3);
-
-		DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_M3;
-		DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_M3;
-		DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_M3;
-		DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_M3;
-		DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_M3;
-		DDR_PHY_SLICE_REGSET_SIZE = DDR_PHY_SLICE_REGSET_SIZE_M3;
-		DDR_PHY_ADR_V_REGSET_SIZE = DDR_PHY_ADR_V_REGSET_SIZE_M3;
-		DDR_PHY_ADR_I_REGSET_SIZE = DDR_PHY_ADR_I_REGSET_SIZE_M3;
-		DDR_PHY_ADR_G_REGSET_SIZE = DDR_PHY_ADR_G_REGSET_SIZE_M3;
-		DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_M3;
-		DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_M3;
-		DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_M3;
-		DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_M3;
-		DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_M3;
-		DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_M3;
-
-		DDR_PHY_ADR_I_NUM = 2;
-	} else {
-		/*  M3-N/V3H */
-		_tblcopy(_cnf_DDR_PHY_SLICE_REGSET,
-			 DDR_PHY_SLICE_REGSET_M3N,
-			 DDR_PHY_SLICE_REGSET_NUM_M3N);
-		_tblcopy(_cnf_DDR_PHY_ADR_V_REGSET, DDR_PHY_ADR_V_REGSET_M3N,
-			 DDR_PHY_ADR_V_REGSET_NUM_M3N);
-		_tblcopy(_cnf_DDR_PHY_ADR_I_REGSET, DDR_PHY_ADR_I_REGSET_M3N,
-			 DDR_PHY_ADR_I_REGSET_NUM_M3N);
-		_tblcopy(_cnf_DDR_PHY_ADR_G_REGSET, DDR_PHY_ADR_G_REGSET_M3N,
-			 DDR_PHY_ADR_G_REGSET_NUM_M3N);
-		_tblcopy(_cnf_DDR_PI_REGSET, DDR_PI_REGSET_M3N,
-			 DDR_PI_REGSET_NUM_M3N);
-
-		DDR_PHY_SLICE_REGSET_OFS = DDR_PHY_SLICE_REGSET_OFS_M3N;
-		DDR_PHY_ADR_V_REGSET_OFS = DDR_PHY_ADR_V_REGSET_OFS_M3N;
-		DDR_PHY_ADR_I_REGSET_OFS = DDR_PHY_ADR_I_REGSET_OFS_M3N;
-		DDR_PHY_ADR_G_REGSET_OFS = DDR_PHY_ADR_G_REGSET_OFS_M3N;
-		DDR_PI_REGSET_OFS = DDR_PI_REGSET_OFS_M3N;
-		DDR_PHY_SLICE_REGSET_SIZE = DDR_PHY_SLICE_REGSET_SIZE_M3N;
-		DDR_PHY_ADR_V_REGSET_SIZE = DDR_PHY_ADR_V_REGSET_SIZE_M3N;
-		DDR_PHY_ADR_I_REGSET_SIZE = DDR_PHY_ADR_I_REGSET_SIZE_M3N;
-		DDR_PHY_ADR_G_REGSET_SIZE = DDR_PHY_ADR_G_REGSET_SIZE_M3N;
-		DDR_PI_REGSET_SIZE = DDR_PI_REGSET_SIZE_M3N;
-		DDR_PHY_SLICE_REGSET_NUM = DDR_PHY_SLICE_REGSET_NUM_M3N;
-		DDR_PHY_ADR_V_REGSET_NUM = DDR_PHY_ADR_V_REGSET_NUM_M3N;
-		DDR_PHY_ADR_I_REGSET_NUM = DDR_PHY_ADR_I_REGSET_NUM_M3N;
-		DDR_PHY_ADR_G_REGSET_NUM = DDR_PHY_ADR_G_REGSET_NUM_M3N;
-		DDR_PI_REGSET_NUM = DDR_PI_REGSET_NUM_M3N;
-
-		DDR_PHY_ADR_I_NUM = 2;
-	}
-
-	/* PLL CODE CHANGE */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_11)) {
-		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET, _reg_PHY_PLL_CTRL,
-			      0x1142);
-		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
-			      _reg_PHY_LP4_BOOT_PLL_CTRL, 0x1142);
-	}
-
-	/* on fly gate adjust */
-	if ((prr_product == PRR_PRODUCT_M3) && (prr_cut == PRR_PRODUCT_10)) {
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
-			      _reg_ON_FLY_GATE_ADJUST_EN, 0x00);
-	}
-
-	/* Adjust PI parameters */
-#ifdef _def_LPDDR4_ODT
-	for (i = 0; i < 2; i++) {
-		for (csab = 0; csab < CSAB_CNT; csab++) {
-			ddrtbl_setval(_cnf_DDR_PI_REGSET,
-				      reg_pi_mr11_data_fx_csx[i][csab],
-				      _def_LPDDR4_ODT);
-		}
-	}
-#endif /* _def_LPDDR4_ODT */
-
-#ifdef _def_LPDDR4_VREFCA
-	for (i = 0; i < 2; i++) {
-		for (csab = 0; csab < CSAB_CNT; csab++) {
-			ddrtbl_setval(_cnf_DDR_PI_REGSET,
-				      reg_pi_mr12_data_fx_csx[i][csab],
-				      _def_LPDDR4_VREFCA);
-		}
-	}
-#endif /* _def_LPDDR4_VREFCA */
-	if ((prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 7000, 0) + 7U;
-		if (js2[js2_tiedly] > (RL))
-			js2[js2_tiedly] = RL;
-	} else if ((prr_product == PRR_PRODUCT_H3) &&
-		   (prr_cut > PRR_PRODUCT_11)) {
-		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 9000, 0) + 4U;
-	} else if ((prr_product == PRR_PRODUCT_H3) &&
-		   (prr_cut <= PRR_PRODUCT_11)) {
-		js2[js2_tiedly] = _f_scale(ddr_mbps, ddr_mbpsdiv, 10000, 0);
-	}
-
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
-	    (prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		if ((js2[js2_tiedly]) >= 0x1e)
-			dataS = 0x1e;
-		else
-			dataS = js2[js2_tiedly];
-	} else {
-		if ((js2[js2_tiedly]) >= 0x0e)
-			dataS = 0x0e;
-		else
-			dataS = js2[js2_tiedly];
-	}
-
-	ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_RDDATA_EN_DLY, dataS);
-	ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_RDDATA_EN_TSEL_DLY,
-		      (dataS - 2));
-	if ((prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
-			      _reg_PHY_RDDATA_EN_OE_DLY, dataS - 2);
-	}
-	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_RDLAT_ADJ_F1, RL - dataS);
-
-	if (ddrtbl_getval
-	    (_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_WRITE_PATH_LAT_ADD)) {
-		data_l = WL - 1;
-	} else {
-		data_l = WL;
-	}
-	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_ADJ_F1, data_l - 2);
-	ddrtbl_setval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_F1, data_l);
-
-	if (board_cnf->dbi_en) {
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_DBI_MODE,
-			      0x01);
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
-			      _reg_PHY_WDQLVL_DATADM_MASK, 0x000);
-	} else {
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_DBI_MODE,
-			      0x00);
-		ddrtbl_setval(_cnf_DDR_PHY_SLICE_REGSET,
-			      _reg_PHY_WDQLVL_DATADM_MASK, 0x100);
-	}
-
-	tmp[0] = js1[js1_ind].MR1;
-	tmp[1] = js1[js1_ind].MR2;
-	data_l = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_MR3_DATA_F1_0);
-	if (board_cnf->dbi_en)
-		tmp[2] = data_l | 0xc0;
-	else
-		tmp[2] = data_l & (~0xc0);
-
-	for (i = 0; i < 2; i++) {
-		for (csab = 0; csab < CSAB_CNT; csab++) {
-			ddrtbl_setval(_cnf_DDR_PI_REGSET,
-				      reg_pi_mr1_data_fx_csx[i][csab], tmp[0]);
-			ddrtbl_setval(_cnf_DDR_PI_REGSET,
-				      reg_pi_mr2_data_fx_csx[i][csab], tmp[1]);
-			ddrtbl_setval(_cnf_DDR_PI_REGSET,
-				      reg_pi_mr3_data_fx_csx[i][csab], tmp[2]);
-		}
-	}
-
-	/* DDRPHY INT START */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		/* non */
-	} else {
-		regif_pll_wa();
-		dbwait_loop(5);
-	}
-
-	/* FREQ_SEL_MULTICAST & PER_CS_TRAINING_MULTICAST SET (for safety) */
-	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
-			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
-	ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_MULTICAST_EN, 0x01);
-
-	/* SET DATA SLICE TABLE */
-	for (slice = 0; slice < SLICE_CNT; slice++) {
-		adr =
-		    DDR_PHY_SLICE_REGSET_OFS +
-		    DDR_PHY_SLICE_REGSET_SIZE * slice;
-		for (i = 0; i < DDR_PHY_SLICE_REGSET_NUM; i++) {
-			reg_ddrphy_write_a(adr + i,
-					   _cnf_DDR_PHY_SLICE_REGSET[i]);
-		}
-	}
-
-	/* SET ADR SLICE TABLE */
-	adr = DDR_PHY_ADR_V_REGSET_OFS;
-	for (i = 0; i < DDR_PHY_ADR_V_REGSET_NUM; i++) {
-		reg_ddrphy_write_a(adr + i, _cnf_DDR_PHY_ADR_V_REGSET[i]);
-	}
-
-	if (((prr_product == PRR_PRODUCT_M3) ||
-	     (prr_product == PRR_PRODUCT_M3N)) &&
-	    ((0x00ffffff & (uint32_t)((board_cnf->ch[0].ca_swap) >> 40))
-	    != 0x00)) {
-		adr = DDR_PHY_ADR_I_REGSET_OFS + DDR_PHY_ADR_I_REGSET_SIZE;
-		for (i = 0; i < DDR_PHY_ADR_V_REGSET_NUM; i++) {
-			reg_ddrphy_write_a(adr + i,
-					   _cnf_DDR_PHY_ADR_V_REGSET[i]);
-		}
-		ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
-			      _reg_PHY_ADR_DISABLE, 0x02);
-		DDR_PHY_ADR_I_NUM -= 1;
-		ddr_phycaslice = 1;
-
-#ifndef _def_LPDDR4_ODT
-		for (i = 0; i < 2; i++) {
-			for (csab = 0; csab < CSAB_CNT; csab++) {
-				ddrtbl_setval(_cnf_DDR_PI_REGSET,
-					      reg_pi_mr11_data_fx_csx[i][csab],
-					      0x66);
-			}
-		}
-#endif/* _def_LPDDR4_ODT */
-	} else {
-		ddr_phycaslice = 0;
-	}
-
-	if (DDR_PHY_ADR_I_NUM > 0) {
-		for (slice = 0; slice < DDR_PHY_ADR_I_NUM; slice++) {
-			adr =
-			    DDR_PHY_ADR_I_REGSET_OFS +
-			    DDR_PHY_ADR_I_REGSET_SIZE * slice;
-			for (i = 0; i < DDR_PHY_ADR_I_REGSET_NUM; i++) {
-				reg_ddrphy_write_a(adr + i,
-						   _cnf_DDR_PHY_ADR_I_REGSET
-						   [i]);
-			}
-		}
-	}
-
-	/* SET ADRCTRL SLICE TABLE */
-	adr = DDR_PHY_ADR_G_REGSET_OFS;
-	for (i = 0; i < DDR_PHY_ADR_G_REGSET_NUM; i++) {
-		reg_ddrphy_write_a(adr + i, _cnf_DDR_PHY_ADR_G_REGSET[i]);
-	}
-
-	/* SET PI REGISTERS */
-	adr = DDR_PI_REGSET_OFS;
-	for (i = 0; i < DDR_PI_REGSET_NUM; i++) {
-		reg_ddrphy_write_a(adr + i, _cnf_DDR_PI_REGSET[i]);
-	}
-}
-
-/* CONFIGURE DDR REGISTERS */
-static void ddr_config_sub(void)
-{
-	uint32_t i;
-	uint32_t ch, slice;
-	uint32_t data_l;
-	uint32_t tmp;
-	uint8_t high_byte[SLICE_CNT];
-	const uint32_t _par_CALVL_DEVICE_MAP = 1;
-
-	foreach_vch(ch) {
-	/* BOARD SETTINGS (DQ,DM,VREF_DRIVING) */
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			high_byte[slice] =
-			    (board_cnf->ch[ch].dqs_swap >> (4 * slice)) % 2;
-			ddr_setval_s(ch, slice, _reg_PHY_DQ_DM_SWIZZLE0,
-				     board_cnf->ch[ch].dq_swap[slice]);
-			ddr_setval_s(ch, slice, _reg_PHY_DQ_DM_SWIZZLE1,
-				     board_cnf->ch[ch].dm_swap[slice]);
-			if (high_byte[slice]) {
-				/* HIGHER 16 BYTE */
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
-					     0x00);
-			} else {
-				/* LOWER 16 BYTE */
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
-					     0x01);
-			}
-		}
-
-	/* BOARD SETTINGS (CA,ADDR_SEL) */
-		data_l = (0x00ffffff & (uint32_t)(board_cnf->ch[ch].ca_swap)) |
-			0x00888888;
-
-		/* --- ADR_CALVL_SWIZZLE --- */
-		if (prr_product == PRR_PRODUCT_M3) {
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_0, data_l);
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_0,
-				   0x00000000);
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_1, data_l);
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_1,
-				   0x00000000);
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_DEVICE_MAP,
-				   _par_CALVL_DEVICE_MAP);
-		} else {
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0, data_l);
-			ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1, 0x00000000);
-			ddr_setval(ch, _reg_PHY_CALVL_DEVICE_MAP,
-				   _par_CALVL_DEVICE_MAP);
-		}
-
-		/* --- ADR_ADDR_SEL --- */
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut > PRR_PRODUCT_11)) {
-			data_l = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
-		} else {
-			data_l = 0;
-			tmp = board_cnf->ch[ch].ca_swap;
-			for (i = 0; i < 6; i++) {
-				data_l |= ((tmp & 0x0f) << (i * 5));
-				tmp = tmp >> 4;
-			}
-		}
-		ddr_setval(ch, _reg_PHY_ADR_ADDR_SEL, data_l);
-		if (ddr_phycaslice == 1) {
-			/* ----------- adr slice2 swap ----------- */
-			tmp  = (uint32_t)((board_cnf->ch[ch].ca_swap) >> 40);
-			data_l = (tmp & 0x00ffffff) | 0x00888888;
-
-			/* --- ADR_CALVL_SWIZZLE --- */
-			if (prr_product == PRR_PRODUCT_M3) {
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE0_0,
-					     data_l);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE1_0,
-					     0x00000000);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE0_1,
-					     data_l);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE1_1,
-					     0x00000000);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_DEVICE_MAP,
-					     _par_CALVL_DEVICE_MAP);
-			} else {
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE0,
-					     data_l);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_ADR_CALVL_SWIZZLE1,
-					     0x00000000);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_CALVL_DEVICE_MAP,
-					     _par_CALVL_DEVICE_MAP);
-			}
-
-			/* --- ADR_ADDR_SEL --- */
-			data_l = 0;
-			for (i = 0; i < 6; i++) {
-				data_l |= ((tmp & 0x0f) << (i * 5));
-				tmp = tmp >> 4;
-			}
-
-			ddr_setval_s(ch, 2, _reg_PHY_ADR_ADDR_SEL, data_l);
-		}
-
-	/* BOARD SETTINGS (BYTE_ORDER_SEL) */
-		if (prr_product == PRR_PRODUCT_M3) {
-			/* --- DATA_BYTE_SWAP --- */
-			data_l = 0;
-			tmp = board_cnf->ch[ch].dqs_swap;
-			for (i = 0; i < 4; i++) {
-				data_l |= ((tmp & 0x03) << (i * 2));
-				tmp = tmp >> 4;
-			}
-		} else {
-			/* --- DATA_BYTE_SWAP --- */
-			data_l = board_cnf->ch[ch].dqs_swap;
-			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_EN, 0x01);
-			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE0,
-				   (data_l) & 0x0f);
-			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE1,
-				   (data_l >> 4 * 1) & 0x0f);
-			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE2,
-				   (data_l >> 4 * 2) & 0x0f);
-			ddr_setval(ch, _reg_PI_DATA_BYTE_SWAP_SLICE3,
-				   (data_l >> 4 * 3) & 0x0f);
-
-			ddr_setval(ch, _reg_PHY_DATA_BYTE_ORDER_SEL_HIGH, 0x00);
-		}
-		ddr_setval(ch, _reg_PHY_DATA_BYTE_ORDER_SEL, data_l);
-	}
-}
-
-static void get_ca_swizzle(uint32_t ch, uint32_t ddr_csn, uint32_t *p_swz)
-{
-	uint32_t slice;
-	uint32_t tmp;
-	uint32_t tgt;
-
-	if (ddr_csn / 2) {
-		tgt = 3;
-	} else {
-		tgt = 1;
-	}
-
-	for (slice = 0; slice < SLICE_CNT; slice++) {
-		tmp = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
-		if (tgt == tmp)
-			break;
-	}
-	tmp = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
-	if (slice % 2)
-		tmp |= 0x00888888;
-	*p_swz = tmp;
-}
-
-static void ddr_config_sub_h3v1x(void)
-{
-	uint32_t ch, slice;
-	uint32_t data_l;
-	uint32_t tmp;
-	uint8_t high_byte[SLICE_CNT];
-	uint32_t ca_swizzle;
-	uint32_t ca;
-	uint32_t csmap;
-	uint32_t o_inv;
-	uint32_t inv;
-	uint32_t bit_soc;
-	uint32_t bit_mem;
-	uint32_t j;
-
-	const uint8_t o_mr15 = 0x55;
-	const uint8_t o_mr20 = 0x55;
-	const uint16_t o_mr32_mr40 = 0x5a3c;
-
-	foreach_vch(ch) {
-	/* BOARD SETTINGS (DQ,DM,VREF_DRIVING) */
-		csmap = 0;
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			tmp = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) &
-			      0x0f;
-			high_byte[slice] = tmp % 2;
-			if (tmp == 1 && (slice >= 2))
-				csmap |= 0x05;
-			if (tmp == 3 && (slice >= 2))
-				csmap |= 0x50;
-			ddr_setval_s(ch, slice, _reg_PHY_DQ_SWIZZLING,
-				     board_cnf->ch[ch].dq_swap[slice]);
-			if (high_byte[slice]) {
-				/* HIGHER 16 BYTE */
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
-					     0x00);
-			} else {
-				/* LOWER 16 BYTE */
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_CALVL_VREF_DRIVING_SLICE,
-					     0x01);
-			}
-		}
-	/* BOARD SETTINGS (CA,ADDR_SEL) */
-		ca = 0x00FFFFFF & board_cnf->ch[ch].ca_swap;
-		ddr_setval(ch, _reg_PHY_ADR_ADDR_SEL, ca);
-		ddr_setval(ch, _reg_PHY_CALVL_CS_MAP, csmap);
-
-		get_ca_swizzle(ch, 0, &ca_swizzle);
-
-		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_0, ca_swizzle);
-		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_0, 0x00000000);
-		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE0_1, 0x00000000);
-		ddr_setval(ch, _reg_PHY_ADR_CALVL_SWIZZLE1_1, 0x00000000);
-		ddr_setval(ch, _reg_PHY_ADR_CALVL_DEVICE_MAP, 0x01);
-
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			ddr_setval_s(ch, slice, _reg_PI_RDLVL_PATTERN_NUM,
-				     0x01);
-			ddr_setval_s(ch, slice, _reg_PI_RDLVL_PATTERN_START,
-				     0x08);
-
-			if (high_byte[slice])
-				o_inv = o_mr20;
-			else
-				o_inv = o_mr15;
-
-			tmp = board_cnf->ch[ch].dq_swap[slice];
-			inv = 0;
-			j = 0;
-			for (bit_soc = 0; bit_soc < 8; bit_soc++) {
-				bit_mem = (tmp >> (4 * bit_soc)) & 0x0f;
-				j |= (1U << bit_mem);
-				if (o_inv & (1U << bit_mem))
-					inv |= (1U << bit_soc);
-			}
-			data_l = o_mr32_mr40;
-			if (!high_byte[slice])
-				data_l |= (inv << 24);
-			if (high_byte[slice])
-				data_l |= (inv << 16);
-			ddr_setval_s(ch, slice, _reg_PHY_LP4_RDLVL_PATT8,
-				     data_l);
-		}
-	}
-}
-
-static void ddr_config(void)
-{
-	int32_t i;
-	uint32_t ch, slice;
-	uint32_t data_l;
-	uint32_t tmp;
-	int8_t _adj;
-	int16_t adj;
-	uint32_t dq;
-	union {
-		uint32_t ui32[4];
-		uint8_t ui8[16];
-	} patt;
-	uint16_t patm;
-
-	/* configure ddrphy registers */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		ddr_config_sub_h3v1x();
-	} else {	/*  H3 Ver.2.0 or later/M3-N/V3H is same as M3-W */
-		ddr_config_sub();
-	}
-
-	/* WDQ_USER_PATT */
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			patm = 0;
-			for (i = 0; i < 16; i++) {
-				tmp = board_cnf->ch[ch].wdqlvl_patt[i];
-				patt.ui8[i] = tmp & 0xff;
-				if (tmp & 0x100)
-					patm |= (1U << i);
-			}
-			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT0,
-				     patt.ui32[0]);
-			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT1,
-				     patt.ui32[1]);
-			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT2,
-				     patt.ui32[2]);
-			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT3,
-				     patt.ui32[3]);
-			ddr_setval_s(ch, slice, _reg_PHY_USER_PATT4, patm);
-		}
-	}
-
-	/* CACS DLY */
-	data_l = board_cnf->cacs_dly + _f_scale_adj(board_cnf->cacs_dly_adj);
-	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
-			   0x00U);
-	foreach_vch(ch) {
-		for (i = 0; i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM - 4; i++) {
-			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
-			ddrtbl_setval(_cnf_DDR_PHY_ADR_V_REGSET,
-				      _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
-				      data_l + adj);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr
-					 (_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]),
-					_cnf_DDR_PHY_ADR_V_REGSET
-					[ddr_regdef_adr
-					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
-					DDR_PHY_ADR_V_REGSET_OFS]);
-		}
-
-		for (i = (_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM - 4);
-		     i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM; i++) {
-			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
-			ddrtbl_setval(_cnf_DDR_PHY_ADR_G_REGSET,
-				      _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
-				      data_l + adj);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr
-					 (_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]),
-					_cnf_DDR_PHY_ADR_G_REGSET
-					[ddr_regdef_adr
-					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
-					DDR_PHY_ADR_G_REGSET_OFS]);
-		}
-
-		if (ddr_phycaslice == 1) {
-			for (i = 0; i < 6; i++) {
-				adj = _f_scale_adj
-					(board_cnf->ch[ch].cacs_adj
-					[i +
-					_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM]);
-				ddrtbl_setval(_cnf_DDR_PHY_ADR_V_REGSET,
-					      _reg_PHY_CLK_CACS_SLAVE_DELAY_X
-					      [i],
-					      data_l + adj);
-				reg_ddrphy_write(ch,
-						 ddr_regdef_adr
-					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) +
-					0x0100,
-					_cnf_DDR_PHY_ADR_V_REGSET
-					[ddr_regdef_adr
-					(_reg_PHY_CLK_CACS_SLAVE_DELAY_X[i]) -
-					DDR_PHY_ADR_V_REGSET_OFS]);
-			}
-		}
-	}
-
-	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
-			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
-
-	/* WDQDM DLY */
-	data_l = board_cnf->dqdm_dly_w;
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			for (i = 0; i <= 8; i++) {
-				dq = slice * 8 + i;
-				if (i == 8)
-					_adj = board_cnf->ch[ch].dm_adj_w[slice];
-				else
-					_adj = board_cnf->ch[ch].dq_adj_w[dq];
-				adj = _f_scale_adj(_adj);
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_CLK_WRX_SLAVE_DELAY[i],
-					     data_l + adj);
-			}
-		}
-	}
-
-	/* RDQDM DLY */
-	data_l = board_cnf->dqdm_dly_r;
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			for (i = 0; i <= 8; i++) {
-				dq = slice * 8 + i;
-				if (i == 8)
-					_adj = board_cnf->ch[ch].dm_adj_r[slice];
-				else
-					_adj = board_cnf->ch[ch].dq_adj_r[dq];
-				adj = _f_scale_adj(_adj);
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY
-					     [i], data_l + adj);
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
-					     [i], data_l + adj);
-			}
-		}
-	}
-}
-
-/* DBSC register setting functions */
-static void dbsc_regset_pre(void)
-{
-	uint32_t ch, csab;
-	uint32_t data_l;
-
-	/* PRIMARY SETTINGS */
-	/* LPDDR4, BL=16, DFI interface */
-	mmio_write_32(DBSC_DBKIND, 0x0000000a);
-	mmio_write_32(DBSC_DBBL, 0x00000002);
-	mmio_write_32(DBSC_DBPHYCONF0, 0x00000001);
-
-	/* FREQRATIO=2 */
-	mmio_write_32(DBSC_DBSYSCONF1, 0x00000002);
-
-	/* Chanel map (H3 Ver.1.x) */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11))
-		mmio_write_32(DBSC_DBSCHCNT1, 0x00001010);
-
-	/* DRAM SIZE REGISTER:
-	 * set all ranks as density=0(4Gb) for PHY initialization
-	 */
-	foreach_vch(ch) {
-		for (csab = 0; csab < 4; csab++) {
-			mmio_write_32(DBSC_DBMEMCONF(ch, csab),
-				      DBMEMCONF_REGD(0));
-		}
-	}
-
-	if (prr_product == PRR_PRODUCT_M3) {
-		data_l = 0xe4e4e4e4;
-		foreach_ech(ch) {
-			if ((ddr_phyvalid & (1U << ch)))
-				data_l = (data_l & (~(0x000000FF << (ch * 8))))
-				    | (((board_cnf->ch[ch].dqs_swap & 0x0003)
-					| ((board_cnf->ch[ch].dqs_swap & 0x0030)
-					   >> 2)
-					| ((board_cnf->ch[ch].dqs_swap & 0x0300)
-					   >> 4)
-					| ((board_cnf->ch[ch].dqs_swap & 0x3000)
-					   >> 6)) << (ch * 8));
-		}
-		mmio_write_32(DBSC_DBBSWAP, data_l);
-	}
-}
-
-static void dbsc_regset(void)
-{
-	int32_t i;
-	uint32_t ch;
-	uint32_t data_l;
-	uint32_t data_l2;
-	uint32_t tmp[4];
-
-	/* RFC */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_20) &&
-	    (max_density == 0)) {
-		js2[js2_trfcab] =
-		    _f_scale(ddr_mbps, ddr_mbpsdiv,
-			     1UL * jedec_spec2_trfc_ab[1] * 1000, 0);
-	} else {
-		js2[js2_trfcab] =
-		    _f_scale(ddr_mbps, ddr_mbpsdiv,
-			     1UL * jedec_spec2_trfc_ab[max_density] *
-			     1000, 0);
-	}
-
-	/* DBTR0.CL  : RL */
-	mmio_write_32(DBSC_DBTR(0), RL);
-
-	/* DBTR1.CWL : WL */
-	mmio_write_32(DBSC_DBTR(1), WL);
-
-	/* DBTR2.AL  : 0 */
-	mmio_write_32(DBSC_DBTR(2), 0);
-
-	/* DBTR3.TRCD: tRCD */
-	mmio_write_32(DBSC_DBTR(3), js2[js2_trcd]);
-
-	/* DBTR4.TRPA,TRP: tRPab,tRPpb */
-	mmio_write_32(DBSC_DBTR(4), (js2[js2_trpab] << 16) | js2[js2_trppb]);
-
-	/* DBTR5.TRC : use tRCpb */
-	mmio_write_32(DBSC_DBTR(5), js2[js2_trcpb]);
-
-	/* DBTR6.TRAS : tRAS */
-	mmio_write_32(DBSC_DBTR(6), js2[js2_tras]);
-
-	/* DBTR7.TRRD : tRRD */
-	mmio_write_32(DBSC_DBTR(7), (js2[js2_trrd] << 16) | js2[js2_trrd]);
-
-	/* DBTR8.TFAW : tFAW */
-	mmio_write_32(DBSC_DBTR(8), js2[js2_tfaw]);
-
-	/* DBTR9.TRDPR : tRTP */
-	mmio_write_32(DBSC_DBTR(9), js2[js2_trtp]);
-
-	/* DBTR10.TWR : nWR */
-	mmio_write_32(DBSC_DBTR(10), js1[js1_ind].nwr);
-
-	/*
-	 * DBTR11.TRDWR : RL +  BL / 2 + Rounddown(tRPST) + PHY_ODTLoff -
-	 * 		  odtlon + tDQSCK - tODTon,min +
-	 * 		  PCB delay (out+in) + tPHY_ODToff
-	 */
-	mmio_write_32(DBSC_DBTR(11),
-		      RL + (16 / 2) + 1 + 2 - js1[js1_ind].odtlon +
-		      js2[js2_tdqsck] - js2[js2_tODTon_min] +
-		      _f_scale(ddr_mbps, ddr_mbpsdiv, 1300, 0));
-
-	/* DBTR12.TWRRD : WL + 1 + BL/2 + tWTR */
-	data_l = WL + 1 + (16 / 2) + js2[js2_twtr];
-	mmio_write_32(DBSC_DBTR(12), (data_l << 16) | data_l);
-
-	/* DBTR13.TRFCAB : tRFCab */
-	mmio_write_32(DBSC_DBTR(13), (js2[js2_trfcab]));
-
-	/* DBTR14.TCKEHDLL,tCKEH : tCKEHCMD,tCKEHCMD */
-	mmio_write_32(DBSC_DBTR(14),
-		      (js2[js2_tckehcmd] << 16) | (js2[js2_tckehcmd]));
-
-	/* DBTR15.TCKESR,TCKEL : tSR,tCKELPD */
-	mmio_write_32(DBSC_DBTR(15), (js2[js2_tsr] << 16) | (js2[js2_tckelpd]));
-
-	/* DBTR16 */
-	/* WDQL : tphy_wrlat + tphy_wrdata */
-	tmp[0] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_F1);
-	/* DQENLTNCY : tphy_wrlat = WL-2 : PHY_WRITE_PATH_LAT_ADD == 0
-	 *             tphy_wrlat = WL-3 : PHY_WRITE_PATH_LAT_ADD != 0
-	 */
-	tmp[1] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_WRLAT_ADJ_F1);
-	/* DQL : tphy_rdlat + trdata_en */
-	/* it is not important for dbsc */
-	tmp[2] = RL + 16;
-	/* DQIENLTNCY : trdata_en */
-	tmp[3] = ddrtbl_getval(_cnf_DDR_PI_REGSET, _reg_PI_RDLAT_ADJ_F1) - 1;
-	mmio_write_32(DBSC_DBTR(16),
-		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
-
-	/* DBTR24 */
-	/* WRCSLAT = WRLAT -5 */
-	tmp[0] -= 5;
-	/* WRCSGAP = 5 */
-	tmp[1] = 5;
-	/* RDCSLAT = RDLAT_ADJ +2 */
-	if (prr_product == PRR_PRODUCT_M3) {
-		tmp[2] = tmp[3];
-	} else {
-		tmp[2] = tmp[3] + 2;
-	}
-	/* RDCSGAP = 6 */
-	if (prr_product == PRR_PRODUCT_M3) {
-		tmp[3] = 4;
-	} else {
-		tmp[3] = 6;
-	}
-	mmio_write_32(DBSC_DBTR(24),
-		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
-
-	/* DBTR17.TMODRD,TMOD,TRDMR: tMRR,tMRD,(0) */
-	mmio_write_32(DBSC_DBTR(17),
-		      (js2[js2_tmrr] << 24) | (js2[js2_tmrd] << 16));
-
-	/* DBTR18.RODTL, RODTA, WODTL, WODTA : do not use in LPDDR4 */
-	mmio_write_32(DBSC_DBTR(18), 0);
-
-	/* DBTR19.TZQCL, TZQCS : do not use in LPDDR4 */
-	mmio_write_32(DBSC_DBTR(19), 0);
-
-	/* DBTR20.TXSDLL, TXS : tRFCab+tCKEHCMD */
-	data_l = js2[js2_trfcab] + js2[js2_tckehcmd];
-	mmio_write_32(DBSC_DBTR(20), (data_l << 16) | data_l);
-
-	/* DBTR21.TCCD */
-	/* DBTR23.TCCD */
-	/* H3 Ver.1.0 cannot use TBTR23 feature */
-	if (ddr_tccd == 8 &&
-	    !((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_10))
-	    ) {
-		data_l = 8;
-		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
-		mmio_write_32(DBSC_DBTR(23), 0x00000002);
-	} else if (ddr_tccd <= 11) {
-		data_l = 11;
-		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
-		mmio_write_32(DBSC_DBTR(23), 0x00000000);
-	} else {
-		data_l = ddr_tccd;
-		mmio_write_32(DBSC_DBTR(21), (data_l << 16) | data_l);
-		mmio_write_32(DBSC_DBTR(23), 0x00000000);
-	}
-
-	/* DBTR22.ZQLAT : */
-	data_l = js2[js2_tzqcalns] * 100;	/*  1000 * 1000 ps */
-	data_l = (data_l << 16) | (js2[js2_tzqlat] + 24 + 20);
-	mmio_write_32(DBSC_DBTR(22), data_l);
-
-	/* DBTR25 : do not use in LPDDR4 */
-	mmio_write_32(DBSC_DBTR(25), 0);
-
-	/* DBRNK : */
-	/*
-	 * DBSC_DBRNK2 rkrr
-	 * DBSC_DBRNK3 rkrw
-	 * DBSC_DBRNK4 rkwr
-	 * DBSC_DBRNK5 rkww
-	 */
-#define _par_DBRNK_VAL		(0x7007)
-
-	for (i = 0; i < 4; i++) {
-		data_l = (_par_DBRNK_VAL >> (i * 4)) & 0x0f;
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut > PRR_PRODUCT_11) && (i == 0)) {
-			data_l += 1;
-		}
-		data_l2 = 0;
-		foreach_vch(ch) {
-			data_l2 = data_l2 | (data_l << (4 * ch));
-		}
-		mmio_write_32(DBSC_DBRNK(2 + i), data_l2);
-	}
-	mmio_write_32(DBSC_DBADJ0, 0x00000000);
-
-	/* timing registers for Scheduler */
-	/* SCFCTST0 */
-	/* SCFCTST0 ACT-ACT */
-	tmp[3] = 1UL * js2[js2_trcpb] * 800 * ddr_mbpsdiv / ddr_mbps;
-	/* SCFCTST0 RDA-ACT */
-	tmp[2] =
-	    1UL * ((16 / 2) + js2[js2_trtp] - 8 +
-		   js2[js2_trppb]) * 800 * ddr_mbpsdiv / ddr_mbps;
-	/* SCFCTST0 WRA-ACT */
-	tmp[1] =
-	    1UL * (WL + 1 + (16 / 2) +
-		   js1[js1_ind].nwr) * 800 * ddr_mbpsdiv / ddr_mbps;
-	/* SCFCTST0 PRE-ACT */
-	tmp[0] = 1UL * js2[js2_trppb];
-	mmio_write_32(DBSC_SCFCTST0,
-		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
-
-	/* SCFCTST1 */
-	/* SCFCTST1 RD-WR */
-	tmp[3] =
-	    1UL * (mmio_read_32(DBSC_DBTR(11)) & 0xff) * 800 * ddr_mbpsdiv /
-	    ddr_mbps;
-	/* SCFCTST1 WR-RD */
-	tmp[2] =
-	    1UL * (mmio_read_32(DBSC_DBTR(12)) & 0xff) * 800 * ddr_mbpsdiv /
-	    ddr_mbps;
-	/* SCFCTST1 ACT-RD/WR */
-	tmp[1] = 1UL * js2[js2_trcd] * 800 * ddr_mbpsdiv / ddr_mbps;
-	/* SCFCTST1 ASYNCOFS */
-	tmp[0] = 12;
-	mmio_write_32(DBSC_SCFCTST1,
-		      (tmp[3] << 24) | (tmp[2] << 16) | (tmp[1] << 8) | tmp[0]);
-
-	/* DBSCHRW1 */
-	/* DBSCHRW1 SCTRFCAB */
-	tmp[0] = 1UL * js2[js2_trfcab] * 800 * ddr_mbpsdiv / ddr_mbps;
-	data_l = (((mmio_read_32(DBSC_DBTR(16)) & 0x00FF0000) >> 16)
-		 + (mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
-		 + (0x28 * 2)) * 400 * 2 * ddr_mbpsdiv / ddr_mbps + 7;
-	if (tmp[0] < data_l)
-		tmp[0] = data_l;
-
-	if ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30)) {
-		mmio_write_32(DBSC_DBSCHRW1, tmp[0]
-			+ ((mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
-			* 400 * 2 * ddr_mbpsdiv + (ddr_mbps - 1)) /
-			ddr_mbps - 3);
-	} else {
-		mmio_write_32(DBSC_DBSCHRW1, tmp[0]
-			+ ((mmio_read_32(DBSC_DBTR(22)) & 0x0000FFFF)
-			* 400 * 2 * ddr_mbpsdiv + (ddr_mbps - 1)) /
-			ddr_mbps);
-	}
-
-	/* QOS and CAM */
-#ifdef ddr_qos_init_setting	/*  only for non qos_init */
-	/*wbkwait(0004), wbkmdhi(4,2),wbkmdlo(1,8) */
-	mmio_write_32(DBSC_DBCAM0CNF1, 0x00043218);
-	/*0(fillunit),8(dirtymax),4(dirtymin) */
-	mmio_write_32(DBSC_DBCAM0CNF2, 0x000000F4);
-	/*stop_tolerance */
-	mmio_write_32(DBSC_DBSCHRW0, 0x22421111);
-	/*rd-wr/wr-rd toggle priority */
-	mmio_write_32(DBSC_SCFCTST2, 0x012F1123);
-	mmio_write_32(DBSC_DBSCHSZ0, 0x00000001);
-	mmio_write_32(DBSC_DBSCHCNT0, 0x000F0037);
-
-	/* QoS Settings */
-	mmio_write_32(DBSC_DBSCHQOS00, 0x00000F00U);
-	mmio_write_32(DBSC_DBSCHQOS01, 0x00000B00U);
-	mmio_write_32(DBSC_DBSCHQOS02, 0x00000000U);
-	mmio_write_32(DBSC_DBSCHQOS03, 0x00000000U);
-	mmio_write_32(DBSC_DBSCHQOS40, 0x00000300U);
-	mmio_write_32(DBSC_DBSCHQOS41, 0x000002F0U);
-	mmio_write_32(DBSC_DBSCHQOS42, 0x00000200U);
-	mmio_write_32(DBSC_DBSCHQOS43, 0x00000100U);
-	mmio_write_32(DBSC_DBSCHQOS90, 0x00000100U);
-	mmio_write_32(DBSC_DBSCHQOS91, 0x000000F0U);
-	mmio_write_32(DBSC_DBSCHQOS92, 0x000000A0U);
-	mmio_write_32(DBSC_DBSCHQOS93, 0x00000040U);
-	mmio_write_32(DBSC_DBSCHQOS120, 0x00000040U);
-	mmio_write_32(DBSC_DBSCHQOS121, 0x00000030U);
-	mmio_write_32(DBSC_DBSCHQOS122, 0x00000020U);
-	mmio_write_32(DBSC_DBSCHQOS123, 0x00000010U);
-	mmio_write_32(DBSC_DBSCHQOS130, 0x00000100U);
-	mmio_write_32(DBSC_DBSCHQOS131, 0x000000F0U);
-	mmio_write_32(DBSC_DBSCHQOS132, 0x000000A0U);
-	mmio_write_32(DBSC_DBSCHQOS133, 0x00000040U);
-	mmio_write_32(DBSC_DBSCHQOS140, 0x000000C0U);
-	mmio_write_32(DBSC_DBSCHQOS141, 0x000000B0U);
-	mmio_write_32(DBSC_DBSCHQOS142, 0x00000080U);
-	mmio_write_32(DBSC_DBSCHQOS143, 0x00000040U);
-	mmio_write_32(DBSC_DBSCHQOS150, 0x00000040U);
-	mmio_write_32(DBSC_DBSCHQOS151, 0x00000030U);
-	mmio_write_32(DBSC_DBSCHQOS152, 0x00000020U);
-	mmio_write_32(DBSC_DBSCHQOS153, 0x00000010U);
-
-	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
-#endif /* ddr_qos_init_setting */
-	/* H3 Ver.1.1 need to set monitor function */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_11)) {
-		mmio_write_32(DBSC_DBMONCONF4, 0x00700000);
-	}
-
-	if (prr_product == PRR_PRODUCT_H3) {
-		if (prr_cut == PRR_PRODUCT_10) {
-			/* resrdis, simple mode, sc off */
-			mmio_write_32(DBSC_DBBCAMDIS, 0x00000007);
-		} else if (prr_cut == PRR_PRODUCT_11) {
-			/* resrdis, simple mode         */
-			mmio_write_32(DBSC_DBBCAMDIS, 0x00000005);
-		} else if (prr_cut < PRR_PRODUCT_30) {
-			/* H3 Ver.2.0                   */
-			/* resrdis                      */
-			mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
-		} else {	/* H3 Ver.3.0(include H3N)      */
-			/* exprespque                   */
-			mmio_write_32(DBSC_DBBCAMDIS, 0x00000010);
-		}
-	} else {		/* M3-W/M3-N/V3H                */
-		/* resrdis                      */
-		mmio_write_32(DBSC_DBBCAMDIS, 0x00000001);
-	}
-}
-
-static void dbsc_regset_post(void)
-{
-	uint32_t ch, cs;
-	uint32_t data_l;
-	uint32_t slice, rdlat_max, rdlat_min;
-
-	rdlat_max = 0;
-	rdlat_min = 0xffff;
-	foreach_vch(ch) {
-		for (cs = 0; cs < CS_CNT; cs++) {
-			if ((ch_have_this_cs[cs] & (1U << ch)) != 0) {
-				for (slice = 0; slice < SLICE_CNT; slice++) {
-					ddr_setval_s(ch, slice,
-						     _reg_PHY_PER_CS_TRAINING_INDEX,
-						     cs);
-					data_l = ddr_getval_s(ch, slice,
-							      _reg_PHY_RDDQS_LATENCY_ADJUST);
-					if (data_l > rdlat_max)
-						rdlat_max = data_l;
-					if (data_l < rdlat_min)
-						rdlat_min = data_l;
-				}
-			}
-		}
-	}
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) {
-#if RCAR_DRAM_SPLIT == 2
-		if (board_cnf->phyvalid == 0x05) {
-			mmio_write_32(DBSC_DBTR(24),
-				      (rdlat_max << 24) + (rdlat_min << 16) +
-				      mmio_read_32(DBSC_DBTR(24)));
-		} else {
-			mmio_write_32(DBSC_DBTR(24),
-				      ((rdlat_max * 2 - rdlat_min + 4) << 24) +
-				      ((rdlat_min + 2) << 16) +
-				      mmio_read_32(DBSC_DBTR(24)));
-		}
-#else /*RCAR_DRAM_SPLIT == 2 */
-		mmio_write_32(DBSC_DBTR(24),
-			      ((rdlat_max * 2 - rdlat_min + 4) << 24) +
-			      ((rdlat_min + 2) << 16) +
-			      mmio_read_32(DBSC_DBTR(24)));
-#endif /*RCAR_DRAM_SPLIT == 2 */
-	} else {
-		mmio_write_32(DBSC_DBTR(24),
-			      ((rdlat_max + 2) << 24) +
-			      ((rdlat_max + 2) << 16) +
-			      mmio_read_32(DBSC_DBTR(24)));
-	}
-
-	/* set ddr density information */
-	foreach_ech(ch) {
-		for (cs = 0; cs < CS_CNT; cs++) {
-			if (ddr_density[ch][cs] == 0xff) {
-				mmio_write_32(DBSC_DBMEMCONF(ch, cs), 0x00);
-			} else {
-				mmio_write_32(DBSC_DBMEMCONF(ch, cs),
-					      DBMEMCONF_REGD(ddr_density[ch]
-							     [cs]));
-			}
-		}
-		mmio_write_32(DBSC_DBMEMCONF(ch, 2), 0x00000000);
-		mmio_write_32(DBSC_DBMEMCONF(ch, 3), 0x00000000);
-	}
-
-	mmio_write_32(DBSC_DBBUS0CNF1, 0x00000010);
-
-	/*set DBI */
-	if (board_cnf->dbi_en)
-		mmio_write_32(DBSC_DBDBICNT, 0x00000003);
-
-	/* H3 Ver.2.0 or later/M3-N/V3H DBI wa */
-	if ((((prr_product == PRR_PRODUCT_H3) &&
-	      (prr_cut > PRR_PRODUCT_11)) ||
-	     (prr_product == PRR_PRODUCT_M3N) ||
-	     (prr_product == PRR_PRODUCT_V3H)) &&
-	    board_cnf->dbi_en)
-		reg_ddrphy_write_a(0x00001010, 0x01000000);
-
-	/*set REFCYCLE */
-	data_l = (get_refperiod()) * ddr_mbps / 2000 / ddr_mbpsdiv;
-	mmio_write_32(DBSC_DBRFCNF1, 0x00080000 | (data_l & 0x0000ffff));
-	mmio_write_32(DBSC_DBRFCNF2, 0x00010000 | DBSC_REFINTS);
-
-#if RCAR_REWT_TRAINING != 0
-	/* Periodic-WriteDQ Training seeting */
-	if (((prr_product == PRR_PRODUCT_H3) &&
-	     (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) &&
-	     (prr_cut == PRR_PRODUCT_10))) {
-		/* non : H3 Ver.1.x/M3-W Ver.1.0 not support */
-	} else {
-		/* H3 Ver.2.0 or later/M3-W Ver.1.1 or later/M3-N/V3H */
-		mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000000);
-
-		ddr_setval_ach_as(_reg_PHY_WDQLVL_PATT, 0x04);
-		ddr_setval_ach_as(_reg_PHY_WDQLVL_QTR_DLY_STEP, 0x0F);
-		ddr_setval_ach_as(_reg_PHY_WDQLVL_DLY_STEP, 0x50);
-		ddr_setval_ach_as(_reg_PHY_WDQLVL_DQDM_SLV_DLY_START, 0x0300);
-
-		ddr_setval_ach(_reg_PI_WDQLVL_CS_MAP,
-			       ddrtbl_getval(_cnf_DDR_PI_REGSET,
-					     _reg_PI_WDQLVL_CS_MAP));
-		ddr_setval_ach(_reg_PI_LONG_COUNT_MASK, 0x1f);
-		ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x00);
-		ddr_setval_ach(_reg_PI_WDQLVL_ROTATE, 0x01);
-		ddr_setval_ach(_reg_PI_TREF_F0, 0x0000);
-		ddr_setval_ach(_reg_PI_TREF_F1, 0x0000);
-		ddr_setval_ach(_reg_PI_TREF_F2, 0x0000);
-
-		if (prr_product == PRR_PRODUCT_M3) {
-			ddr_setval_ach(_reg_PI_WDQLVL_EN, 0x02);
-		} else {
-			ddr_setval_ach(_reg_PI_WDQLVL_EN_F1, 0x02);
-		}
-		ddr_setval_ach(_reg_PI_WDQLVL_PERIODIC, 0x01);
-
-		/* DFI_PHYMSTR_ACK , WTmode setting */
-		/* DFI_PHYMSTR_ACK: WTmode =b'01 */
-		mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000011);
-	}
-#endif /* RCAR_REWT_TRAINING */
-	/* periodic dram zqcal enable */
-	mmio_write_32(DBSC_DBCALCNF, 0x01000010);
-
-	/* periodic phy ctrl update enable */
-	if (((prr_product == PRR_PRODUCT_H3) &&
-	     (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) &&
-	     (prr_cut < PRR_PRODUCT_30))) {
-		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
-	} else {
-#if RCAR_DRAM_SPLIT == 2
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (board_cnf->phyvalid == 0x05))
-			mmio_write_32(DBSC_DBDFICUPDCNF, 0x2a240001);
-		else
-			mmio_write_32(DBSC_DBDFICUPDCNF, 0x28240001);
-#else /* RCAR_DRAM_SPLIT == 2 */
-		mmio_write_32(DBSC_DBDFICUPDCNF, 0x28240001);
-#endif /* RCAR_DRAM_SPLIT == 2 */
-	}
-
-#ifdef DDR_BACKUPMODE
-	/* SRX */
-	if (ddr_backup == DRAM_BOOT_STATUS_WARM) {
-#ifdef DDR_BACKUPMODE_HALF		/* for Half channel(ch0, 1 only) */
-		NOTICE("BL2: [DEBUG_MESS] DDR_BACKUPMODE_HALF\n");
-		send_dbcmd(0x0A040001);
-		if (Prr_Product == PRR_PRODUCT_H3)
-			send_dbcmd(0x0A140001);
-#else /* DDR_BACKUPMODE_HALF */		/* for All channels */
-		send_dbcmd(0x0A840001);
-#endif /* DDR_BACKUPMODE_HALF */
-	}
-#endif /* DDR_BACKUPMODE */
-
-	/* set Auto Refresh */
-	mmio_write_32(DBSC_DBRFEN, 0x00000001);
-
-#if RCAR_REWT_TRAINING != 0
-	/* Periodic WriteDQ Traning */
-	if (((prr_product == PRR_PRODUCT_H3) &&
-	     (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) &&
-	     (prr_cut == PRR_PRODUCT_10))) {
-		/* non : H3 Ver.1.x/M3-W Ver.1.0 not support */
-	} else {
-		/* H3 Ver.2.0 or later/M3-W Ver.1.1 or later/M3-N/V3H */
-		ddr_setval_ach(_reg_PI_WDQLVL_INTERVAL, 0x0100);
-	}
-#endif /* RCAR_REWT_TRAINING */
-
-	/* dram access enable */
-	mmio_write_32(DBSC_DBACEN, 0x00000001);
-
-	MSG_LF(__func__ "(done)");
-}
-
-/* DFI_INIT_START */
-static uint32_t dfi_init_start(void)
-{
-	uint32_t ch;
-	uint32_t phytrainingok;
-	uint32_t retry;
-	uint32_t data_l;
-	const uint32_t RETRY_MAX = 0x10000;
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		/* PLL3 Disable */
-		/* protect register interface */
-		ddrphy_regif_idle();
-
-		pll3_control(0);
-
-		/* init start */
-		/* dbdficnt0:
-		 * dfi_dram_clk_disable=1
-		 * dfi_frequency = 0
-		 * freq_ratio = 01 (2:1)
-		 * init_start =0
-		 */
-		foreach_vch(ch)
-		    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F10);
-		dsb_sev();
-
-		/* dbdficnt0:
-		 * dfi_dram_clk_disable=1
-		 * dfi_frequency = 0
-		 * freq_ratio = 01 (2:1)
-		 * init_start =1
-		 */
-		foreach_vch(ch)
-		    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000F11);
-		dsb_sev();
-
-	} else {
-		ddr_setval_ach_as(_reg_PHY_DLL_RST_EN, 0x02);
-		dsb_sev();
-		ddrphy_regif_idle();
-	}
-
-	/* dll_rst negate */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDCNT3(ch), 0x0000CF01);
-	dsb_sev();
-
-	/* wait init_complete */
-	phytrainingok = 0;
-	retry = 0;
-	while (retry++ < RETRY_MAX) {
-		foreach_vch(ch) {
-			data_l = mmio_read_32(DBSC_DBDFISTAT(ch));
-			if (data_l & 0x00000001)
-				phytrainingok |= (1U << ch);
-		}
-		dsb_sev();
-		if (phytrainingok == ddr_phyvalid)
-			break;
-		if (retry % 256 == 0)
-			ddr_setval_ach_as(_reg_SC_PHY_RX_CAL_START, 0x01);
-	}
-
-	/* all ch ok? */
-	if ((phytrainingok & ddr_phyvalid) != ddr_phyvalid)
-		return 0xff;
-
-	/* dbdficnt0:
-	 * dfi_dram_clk_disable=0
-	 * dfi_frequency = 0
-	 * freq_ratio = 01 (2:1)
-	 * init_start =0
-	 */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBDFICNT(ch), 0x00000010);
-	dsb_sev();
-
-	return 0;
-}
-
-/* drivablity setting : CMOS MODE ON/OFF */
-static void change_lpddr4_en(uint32_t mode)
-{
-	uint32_t ch;
-	uint32_t i;
-	uint32_t data_l;
-	const uint32_t _reg_PHY_PAD_DRIVE_X[3] = {
-		_reg_PHY_PAD_ADDR_DRIVE,
-		_reg_PHY_PAD_CLK_DRIVE,
-		_reg_PHY_PAD_CS_DRIVE
-	};
-
-	foreach_vch(ch) {
-		for (i = 0; i < 3; i++) {
-			data_l = ddr_getval(ch, _reg_PHY_PAD_DRIVE_X[i]);
-			if (mode) {
-				data_l |= (1U << 14);
-			} else {
-				data_l &= ~(1U << 14);
-			}
-			ddr_setval(ch, _reg_PHY_PAD_DRIVE_X[i], data_l);
-		}
-	}
-}
-
-/* drivablity setting */
-static uint32_t set_term_code(void)
-{
-	int32_t i;
-	uint32_t ch, index;
-	uint32_t data_l;
-	uint32_t chip_id[2];
-	uint32_t term_code;
-	uint32_t override;
-	uint32_t pvtr;
-	uint32_t pvtp;
-	uint32_t pvtn;
-
-	term_code = ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-				  _reg_PHY_PAD_DATA_TERM);
-	override = 0;
-	for (i = 0; i < 2; i++)
-		chip_id[i] = mmio_read_32(LIFEC_CHIPID(i));
-
-	index = 0;
-	while (1) {
-		if (termcode_by_sample[index][0] == 0xffffffff) {
-			break;
-		}
-		if ((termcode_by_sample[index][0] == chip_id[0]) &&
-		    (termcode_by_sample[index][1] == chip_id[1])) {
-			term_code = termcode_by_sample[index][2];
-			override = 1;
-			break;
-		}
-		index++;
-	}
-
-	if (override) {
-		for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM; index++) {
-			data_l =
-			    ddrtbl_getval(_cnf_DDR_PHY_ADR_G_REGSET,
-					  _reg_PHY_PAD_TERM_X[index]);
-			data_l = (data_l & 0xfffe0000) | term_code;
-			ddr_setval_ach(_reg_PHY_PAD_TERM_X[index], data_l);
-		}
-	} else if ((prr_product == PRR_PRODUCT_M3) &&
-		   (prr_cut == PRR_PRODUCT_10)) {
-		/*  non */
-	} else {
-		ddr_setval_ach(_reg_PHY_PAD_TERM_X[0],
-			       (ddrtbl_getval
-				(_cnf_DDR_PHY_ADR_G_REGSET,
-				 _reg_PHY_PAD_TERM_X[0]) & 0xFFFE0000));
-		ddr_setval_ach(_reg_PHY_CAL_CLEAR_0, 0x01);
-		ddr_setval_ach(_reg_PHY_CAL_START_0, 0x01);
-		foreach_vch(ch) {
-			do {
-				data_l =
-				    ddr_getval(ch, _reg_PHY_CAL_RESULT2_OBS_0);
-			} while (!(data_l & 0x00800000));
-		}
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			foreach_vch(ch) {
-				data_l = ddr_getval(ch, _reg_PHY_PAD_TERM_X[0]);
-				pvtr = (data_l >> 12) & 0x1f;
-				pvtr += 8;
-				if (pvtr > 0x1f)
-					pvtr = 0x1f;
-				data_l =
-				    ddr_getval(ch, _reg_PHY_CAL_RESULT2_OBS_0);
-				pvtn = (data_l >> 6) & 0x03f;
-				pvtp = (data_l >> 0) & 0x03f;
-
-				for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM;
-				     index++) {
-					data_l =
-					    ddrtbl_getval
-					    (_cnf_DDR_PHY_ADR_G_REGSET,
-					     _reg_PHY_PAD_TERM_X[index]);
-					data_l = (data_l & 0xfffe0000)
-					    | (pvtr << 12)
-					    | (pvtn << 6)
-					    | (pvtp);
-					ddr_setval(ch,
-						   _reg_PHY_PAD_TERM_X[index],
-						   data_l);
-				}
-			}
-		} else {
-			/* M3-W Ver.1.1 or later/H3 Ver.2.0 or later/M3-N/V3H */
-			foreach_vch(ch) {
-				for (index = 0; index < _reg_PHY_PAD_TERM_X_NUM;
-				     index++) {
-					data_l =
-					    ddr_getval(ch,
-						       _reg_PHY_PAD_TERM_X
-						       [index]);
-					ddr_setval(ch,
-						   _reg_PHY_PAD_TERM_X[index],
-						   (data_l & 0xFFFE0FFF) |
-						   0x00015000);
-				}
-			}
-		}
-	}
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		/* non */
-	} else {
-		ddr_padcal_tcompensate_getinit(override);
-	}
-
-	return 0;
-}
-
-/* DDR mode register setting */
-static void ddr_register_set(void)
-{
-	int32_t fspwp;
-	uint32_t tmp;
-
-	for (fspwp = 1; fspwp >= 0; fspwp--) {
-		/*MR13, fspwp */
-		send_dbcmd(0x0e840d08 | ((2 - fspwp) << 6));
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr1_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840100 | tmp);
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr2_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840200 | tmp);
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr3_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840300 | tmp);
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr11_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840b00 | tmp);
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr12_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840c00 | tmp);
-
-		tmp =
-		    ddrtbl_getval(_cnf_DDR_PI_REGSET,
-				  reg_pi_mr14_data_fx_csx[fspwp][0]);
-		send_dbcmd(0x0e840e00 | tmp);
-		/* MR22 */
-		send_dbcmd(0x0e841616);
-
-		/* ZQCAL start */
-		send_dbcmd(0x0d84004F);
-
-		/* ZQLAT */
-		send_dbcmd(0x0d840051);
-	}
-
-	/* MR13, fspwp */
-	send_dbcmd(0x0e840d08);
-}
-
-/* Training handshake functions */
-static inline uint32_t wait_freqchgreq(uint32_t assert)
-{
-	uint32_t data_l;
-	uint32_t count;
-	uint32_t ch;
-
-	count = 100000;
-
-	/* H3 Ver.1.x cannot see frqchg_req */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		return 0;
-	}
-
-	if (assert) {
-		do {
-			data_l = 1;
-			foreach_vch(ch) {
-				data_l &= mmio_read_32(DBSC_DBPDSTAT(ch));
-			}
-			count = count - 1;
-		} while (((data_l & 0x01) != 0x01) & (count != 0));
-	} else {
-		do {
-			data_l = 0;
-			foreach_vch(ch) {
-				data_l |= mmio_read_32(DBSC_DBPDSTAT(ch));
-			}
-			count = count - 1;
-		} while (((data_l & 0x01) != 0x00) & (count != 0));
-	}
-
-	return (count == 0);
-}
-
-static inline void set_freqchgack(uint32_t assert)
-{
-	uint32_t ch;
-	uint32_t data_l;
-
-	if (assert)
-		data_l = 0x0CF20000;
-	else
-		data_l = 0x00000000;
-
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDCNT2(ch), data_l);
-}
-
-static inline void set_dfifrequency(uint32_t freq)
-{
-	uint32_t ch;
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		foreach_vch(ch)
-		    mmio_clrsetbits_32(DBSC_DBPDCNT1(ch), 0x1fU, freq);
-	} else {
-		foreach_vch(ch) {
-			mmio_clrsetbits_32(DBSC_DBDFICNT(ch), 0x1fU << 24,
-					   (freq << 24));
-		}
-	}
-	dsb_sev();
-}
-
-static uint32_t pll3_freq(uint32_t on)
-{
-	uint32_t timeout;
-
-	timeout = wait_freqchgreq(1);
-
-	if (timeout) {
-		return 1;
-	}
-
-	pll3_control(on);
-	set_dfifrequency(on);
-
-	set_freqchgack(1);
-	timeout = wait_freqchgreq(0);
-	set_freqchgack(0);
-
-	if (timeout) {
-		FATAL_MSG("BL2: Time out[2]\n");
-		return 1;
-	}
-	return 0;
-}
-
-/* update dly */
-static void update_dly(void)
-{
-	ddr_setval_ach(_reg_SC_PHY_MANUAL_UPDATE, 0x01);
-	ddr_setval_ach(_reg_PHY_ADRCTL_MANUAL_UPDATE, 0x01);
-}
-
-/* training by pi */
-static uint32_t pi_training_go(void)
-{
-	uint32_t flag;
-	uint32_t data_l;
-	uint32_t retry;
-	const uint32_t RETRY_MAX = 4096 * 16;
-	uint32_t ch;
-
-	uint32_t mst_ch;
-	uint32_t cur_frq;
-	uint32_t complete;
-	uint32_t frqchg_req;
-
-	/* pi_start */
-	ddr_setval_ach(_reg_PI_START, 0x01);
-	foreach_vch(ch)
-	    ddr_getval(ch, _reg_PI_INT_STATUS);
-
-	/* set dfi_phymstr_ack = 1 */
-	mmio_write_32(DBSC_DBDFIPMSTRCNF, 0x00000001);
-	dsb_sev();
-
-	/* wait pi_int_status[0] */
-	mst_ch = 0;
-	flag = 0;
-	complete = 0;
-	cur_frq = 0;
-	retry = RETRY_MAX;
-	do {
-		frqchg_req = mmio_read_32(DBSC_DBPDSTAT(mst_ch)) & 0x01;
-
-		/* H3 Ver.1.x cannot see frqchg_req */
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			if ((retry % 4096) == 1) {
-				frqchg_req = 1;
-			} else {
-				frqchg_req = 0;
-			}
-		}
-
-		if (frqchg_req) {
-			if (cur_frq) {
-				/* Low frequency */
-				flag = pll3_freq(0);
-				cur_frq = 0;
-			} else {
-				/* High frequency */
-				flag = pll3_freq(1);
-				cur_frq = 1;
-			}
-			if (flag)
-				break;
-		} else {
-			if (cur_frq) {
-				foreach_vch(ch) {
-					if (complete & (1U << ch))
-						continue;
-					data_l =
-					    ddr_getval(ch, _reg_PI_INT_STATUS);
-					if (data_l & 0x01) {
-						complete |= (1U << ch);
-					}
-				}
-				if (complete == ddr_phyvalid)
-					break;
-			}
-		}
-	} while (--retry);
-	foreach_vch(ch) {
-		/* dummy read */
-		data_l = ddr_getval_s(ch, 0, _reg_PHY_CAL_RESULT2_OBS_0);
-		data_l = ddr_getval(ch, _reg_PI_INT_STATUS);
-		ddr_setval(ch, _reg_PI_INT_ACK, data_l);
-	}
-	if (ddrphy_regif_chk()) {
-		return 0xfd;
-	}
-	return complete;
-}
-
-/* Initialize DDR */
-static uint32_t init_ddr(void)
-{
-	int32_t i;
-	uint32_t data_l;
-	uint32_t phytrainingok;
-	uint32_t ch, slice;
-	uint32_t err;
-	int16_t adj;
-
-	MSG_LF(__func__ ":0\n");
-
-#ifdef DDR_BACKUPMODE
-	rcar_dram_get_boot_status(&ddr_backup);
-#endif
-
-	/* unlock phy */
-	/* Unlock DDRPHY register(AGAIN) */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDLK(ch), 0x0000A55A);
-	dsb_sev();
-
-	if ((((prr_product == PRR_PRODUCT_H3) &&
-	      (prr_cut > PRR_PRODUCT_11)) ||
-	     (prr_product == PRR_PRODUCT_M3N) ||
-	     (prr_product == PRR_PRODUCT_V3H)) && board_cnf->dbi_en)
-		reg_ddrphy_write_a(0x00001010, 0x01000001);
-	else
-		reg_ddrphy_write_a(0x00001010, 0x00000001);
-	/* DBSC register pre-setting */
-	dbsc_regset_pre();
-
-	/* load ddrphy registers */
-
-	ddrtbl_load();
-
-	/* configure ddrphy registers */
-	ddr_config();
-
-	/* dfi_reset assert */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDCNT0(ch), 0x01);
-	dsb_sev();
-
-	/* dbsc register set */
-	dbsc_regset();
-	MSG_LF(__func__ ":1\n");
-
-	/* dfi_reset negate */
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDCNT0(ch), 0x00);
-	dsb_sev();
-
-	/* dfi_init_start (start ddrphy) */
-	err = dfi_init_start();
-	if (err) {
-		return INITDRAM_ERR_I;
-	}
-	MSG_LF(__func__ ":2\n");
-
-	/* ddr backupmode end */
-#ifdef DDR_BACKUPMODE
-	if (ddr_backup) {
-		NOTICE("BL2: [WARM_BOOT]\n");
-	} else {
-		NOTICE("BL2: [COLD_BOOT]\n");
-	}
-	err = rcar_dram_update_boot_status(ddr_backup);
-	if (err) {
-		NOTICE("BL2: [BOOT_STATUS_UPDATE_ERROR]\n");
-		return INITDRAM_ERR_I;
-	}
-#endif
-	MSG_LF(__func__ ":3\n");
-
-	/* override term code after dfi_init_complete */
-	err = set_term_code();
-	if (err) {
-		return INITDRAM_ERR_I;
-	}
-	MSG_LF(__func__ ":4\n");
-
-	/* rx offset calibration */
-	if ((prr_cut > PRR_PRODUCT_11) || (prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		err = rx_offset_cal_hw();
-	} else {
-		err = rx_offset_cal();
-	}
-	if (err)
-		return INITDRAM_ERR_O;
-	MSG_LF(__func__ ":5\n");
-
-	/* Dummy PDE */
-	send_dbcmd(0x08840000);
-
-	/* PDX */
-	send_dbcmd(0x08840001);
-
-	/* check register i/f is alive */
-	err = ddrphy_regif_chk();
-	if (err) {
-		return INITDRAM_ERR_O;
-	}
-	MSG_LF(__func__ ":6\n");
-
-	/* phy initialize end */
-
-	/* setup DDR mode registers */
-	/* CMOS MODE */
-	change_lpddr4_en(0);
-
-	/* MRS */
-	ddr_register_set();
-
-	/* Thermal sensor setting */
-	/* THCTR Bit6: PONM=0 , Bit0: THSST=1  */
-	data_l = (mmio_read_32(THS1_THCTR) & 0xFFFFFFBF) | 0x00000001;
-	mmio_write_32(THS1_THCTR, data_l);
-
-	/* LPDDR4 MODE */
-	change_lpddr4_en(1);
-
-	MSG_LF(__func__ ":7\n");
-
-	/* mask CS_MAP if RANKx is not found */
-	foreach_vch(ch) {
-		data_l = ddr_getval(ch, _reg_PI_CS_MAP);
-		if (!(ch_have_this_cs[1] & (1U << ch)))
-			data_l = data_l & 0x05;
-		ddr_setval(ch, _reg_PI_CS_MAP, data_l);
-	}
-
-	/* exec pi_training */
-	reg_ddrphy_write_a(ddr_regdef_adr(_reg_PHY_FREQ_SEL_MULTICAST_EN),
-			   BIT(ddr_regdef_lsb(_reg_PHY_FREQ_SEL_MULTICAST_EN)));
-	ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_MULTICAST_EN, 0x00);
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_EN, 0x01);
-	} else {
-		foreach_vch(ch) {
-			for (slice = 0; slice < SLICE_CNT; slice++) {
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_PER_CS_TRAINING_EN,
-					     ((ch_have_this_cs[1]) >> ch)
-					     & 0x01);
-			}
-		}
-	}
-
-	phytrainingok = pi_training_go();
-
-	if (ddr_phyvalid != (phytrainingok & ddr_phyvalid)) {
-		return INITDRAM_ERR_T | phytrainingok;
-	}
-
-	MSG_LF(__func__ ":8\n");
-
-	/* CACS DLY ADJUST */
-	data_l = board_cnf->cacs_dly + _f_scale_adj(board_cnf->cacs_dly_adj);
-	foreach_vch(ch) {
-		for (i = 0; i < _reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM; i++) {
-			adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj[i]);
-			ddr_setval(ch, _reg_PHY_CLK_CACS_SLAVE_DELAY_X[i],
-				   data_l + adj);
-		}
-
-		if (ddr_phycaslice == 1) {
-			for (i = 0; i < 6; i++) {
-				adj = _f_scale_adj(board_cnf->ch[ch].cacs_adj
-					[i +
-					_reg_PHY_CLK_CACS_SLAVE_DELAY_X_NUM]);
-				ddr_setval_s(ch, 2,
-					     _reg_PHY_CLK_CACS_SLAVE_DELAY_X
-					     [i],
-					     data_l + adj
-				);
-			}
-		}
-	}
-
-	update_dly();
-	MSG_LF(__func__ ":9\n");
-
-	/* H3 fix rd latency to avoid bug in elasitic buffer */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11))
-		adjust_rddqs_latency();
-
-	/* Adjust Write path latency */
-	if (ddrtbl_getval
-	    (_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_WRITE_PATH_LAT_ADD))
-		adjust_wpath_latency();
-
-	/* RDQLVL Training */
-	if (!ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_IE_MODE))
-		ddr_setval_ach_as(_reg_PHY_IE_MODE, 0x01);
-
-	err = rdqdm_man();
-
-	if (!ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET, _reg_PHY_IE_MODE))
-		ddr_setval_ach_as(_reg_PHY_IE_MODE, 0x00);
-
-	if (err) {
-		return INITDRAM_ERR_T;
-	}
-	update_dly();
-	MSG_LF(__func__ ":10\n");
-
-	/* WDQLVL Training */
-	err = wdqdm_man();
-	if (err) {
-		return INITDRAM_ERR_T;
-	}
-	update_dly();
-	MSG_LF(__func__ ":11\n");
-
-	/* training complete, setup DBSC */
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
-	    (prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		ddr_setval_ach_as(_reg_PHY_DFI40_POLARITY, 0x00);
-		ddr_setval_ach(_reg_PI_DFI40_POLARITY, 0x00);
-	}
-
-	dbsc_regset_post();
-	MSG_LF(__func__ ":12\n");
-
-	return phytrainingok;
-}
-
-/* SW LEVELING COMMON */
-static uint32_t swlvl1(uint32_t ddr_csn, uint32_t reg_cs, uint32_t reg_kick)
-{
-	uint32_t ch;
-	uint32_t data_l;
-	uint32_t retry;
-	uint32_t waiting;
-	uint32_t err;
-
-	const uint32_t RETRY_MAX = 0x1000;
-
-	err = 0;
-	/* set EXIT -> OP_DONE is cleared */
-	ddr_setval_ach(_reg_PI_SWLVL_EXIT, 0x01);
-
-	/* kick */
-	foreach_vch(ch) {
-		if (ch_have_this_cs[ddr_csn % 2] & (1U << ch)) {
-			ddr_setval(ch, reg_cs, ddr_csn);
-			ddr_setval(ch, reg_kick, 0x01);
-		}
-	}
-	foreach_vch(ch) {
-		/*PREPARE ADDR REGISTER (for SWLVL_OP_DONE) */
-		ddr_getval(ch, _reg_PI_SWLVL_OP_DONE);
-	}
-	waiting = ch_have_this_cs[ddr_csn % 2];
-	dsb_sev();
-	retry = RETRY_MAX;
-	do {
-		foreach_vch(ch) {
-			if (!(waiting & (1U << ch)))
-				continue;
-			data_l = ddr_getval(ch, _reg_PI_SWLVL_OP_DONE);
-			if (data_l & 0x01)
-				waiting &= ~(1U << ch);
-		}
-		retry--;
-	} while (waiting && (retry > 0));
-	if (retry == 0) {
-		err = 1;
-	}
-
-	dsb_sev();
-	/* set EXIT -> OP_DONE is cleared */
-	ddr_setval_ach(_reg_PI_SWLVL_EXIT, 0x01);
-	dsb_sev();
-
-	return err;
-}
-
-/* WDQ TRAINING */
-#ifndef DDR_FAST_INIT
-static void wdqdm_clr1(uint32_t ch, uint32_t ddr_csn)
-{
-	int32_t i, k;
-	uint32_t cs, slice;
-	uint32_t data_l;
-
-	/* clr of training results buffer */
-	cs = ddr_csn % 2;
-	data_l = board_cnf->dqdm_dly_w;
-	for (slice = 0; slice < SLICE_CNT; slice++) {
-		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
-		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
-			continue;
-
-		for (i = 0; i <= 8; i++) {
-			if (ch_have_this_cs[CS_CNT - 1 - cs] & (1U << ch))
-				wdqdm_dly[ch][cs][slice][i] =
-				    wdqdm_dly[ch][CS_CNT - 1 - cs][slice][i];
-			else
-				wdqdm_dly[ch][cs][slice][i] = data_l;
-			wdqdm_le[ch][cs][slice][i] = 0;
-			wdqdm_te[ch][cs][slice][i] = 0;
-		}
-		wdqdm_st[ch][cs][slice] = 0;
-		wdqdm_win[ch][cs][slice] = 0;
-	}
-}
-
-static uint32_t wdqdm_ana1(uint32_t ch, uint32_t ddr_csn)
-{
-	int32_t i, k;
-	uint32_t cs, slice;
-	uint32_t data_l;
-	uint32_t err;
-	const uint32_t _par_WDQLVL_RETRY_THRES = 0x7c0;
-
-	int32_t min_win;
-	int32_t win;
-	int8_t _adj;
-	int16_t adj;
-	uint32_t dq;
-
-	/* analysis of training results */
-	err = 0;
-	for (slice = 0; slice < SLICE_CNT; slice += 1) {
-		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
-		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
-			continue;
-
-		cs = ddr_csn % 2;
-		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, cs);
-		for (i = 0; i < 9; i++) {
-			dq = slice * 8 + i;
-			if (i == 8)
-				_adj = board_cnf->ch[ch].dm_adj_w[slice];
-			else
-				_adj = board_cnf->ch[ch].dq_adj_w[dq];
-			adj = _f_scale_adj(_adj);
-
-			data_l =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_CLK_WRX_SLAVE_DELAY[i]) + adj;
-			ddr_setval_s(ch, slice, _reg_PHY_CLK_WRX_SLAVE_DELAY[i],
-				     data_l);
-			wdqdm_dly[ch][cs][slice][i] = data_l;
-		}
-		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN, 0x00);
-		data_l = ddr_getval_s(ch, slice, _reg_PHY_WDQLVL_STATUS_OBS);
-		wdqdm_st[ch][cs][slice] = data_l;
-		min_win = INT_LEAST32_MAX;
-		for (i = 0; i <= 8; i++) {
-			ddr_setval_s(ch, slice, _reg_PHY_WDQLVL_DQDM_OBS_SELECT,
-				     i);
-
-			data_l =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_WDQLVL_DQDM_TE_DLY_OBS);
-			wdqdm_te[ch][cs][slice][i] = data_l;
-			data_l =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_WDQLVL_DQDM_LE_DLY_OBS);
-			wdqdm_le[ch][cs][slice][i] = data_l;
-			win =
-			    (int32_t)wdqdm_te[ch][cs][slice][i] -
-			    wdqdm_le[ch][cs][slice][i];
-			if (min_win > win)
-				min_win = win;
-			if (data_l >= _par_WDQLVL_RETRY_THRES)
-				err = 2;
-		}
-		wdqdm_win[ch][cs][slice] = min_win;
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN,
-				     0x01);
-		} else {
-			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_EN,
-				     ((ch_have_this_cs[1]) >> ch) & 0x01);
-		}
-	}
-	return err;
-}
-#endif/* DDR_FAST_INIT */
-
-static void wdqdm_cp(uint32_t ddr_csn, uint32_t restore)
-{
-	uint32_t i;
-	uint32_t ch, slice;
-	uint32_t tgt_cs, src_cs;
-	uint32_t tmp_r;
-
-	/* copy of training results */
-	foreach_vch(ch) {
-		for (tgt_cs = 0; tgt_cs < CS_CNT; tgt_cs++) {
-			for (slice = 0; slice < SLICE_CNT; slice++) {
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_PER_CS_TRAINING_INDEX,
-					     tgt_cs);
-				src_cs = ddr_csn % 2;
-				if (!(ch_have_this_cs[1] & (1U << ch)))
-					src_cs = 0;
-				for (i = 0; i <= 4; i += 4) {
-					if (restore)
-						tmp_r =
-						    rdqdm_dly[ch][tgt_cs][slice]
-						    [i];
-					else
-						tmp_r =
-						    rdqdm_dly[ch][src_cs][slice]
-						    [i];
-
-					ddr_setval_s(ch, slice,
-						     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY
-						     [i], tmp_r);
-				}
-			}
-		}
-	}
-}
-
-static uint32_t wdqdm_man1(void)
-{
-	int32_t k;
-	uint32_t ch, cs, slice;
-	uint32_t ddr_csn;
-	uint32_t data_l;
-	uint32_t err;
-	uint32_t high_dq[DRAM_CH_CNT];
-	uint32_t mr14_csab0_bak[DRAM_CH_CNT];
-#ifndef DDR_FAST_INIT
-	uint32_t err_flg;
-#endif/* DDR_FAST_INIT */
-
-	/* manual execution of training */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		foreach_vch(ch) {
-			high_dq[ch] = 0;
-			for (slice = 0; slice < SLICE_CNT; slice++) {
-				k = (board_cnf->ch[ch].dqs_swap >>
-				    (4 * slice)) & 0x0f;
-				if (k >= 2)
-					high_dq[ch] |= (1U << slice);
-			}
-			ddr_setval(ch, _reg_PI_16BIT_DRAM_CONNECT, 0x00);
-		}
-	}
-	err = 0;
-	/* CLEAR PREV RESULT */
-	for (cs = 0; cs < CS_CNT; cs++) {
-		ddr_setval_ach_as(_reg_PHY_PER_CS_TRAINING_INDEX, cs);
-		if (((prr_product == PRR_PRODUCT_H3) &&
-		     (prr_cut > PRR_PRODUCT_11)) ||
-		    (prr_product == PRR_PRODUCT_M3N) ||
-		    (prr_product == PRR_PRODUCT_V3H)) {
-			ddr_setval_ach_as(_reg_SC_PHY_WDQLVL_CLR_PREV_RESULTS,
-					  0x01);
-		} else {
-			ddr_setval_ach_as(_reg_PHY_WDQLVL_CLR_PREV_RESULTS,
-					  0x01);
-		}
-	}
-	ddrphy_regif_idle();
-
-#ifndef DDR_FAST_INIT
-	err_flg = 0;
-#endif/* DDR_FAST_INIT */
-	for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			foreach_vch(ch) {
-				data_l = mmio_read_32(DBSC_DBDFICNT(ch));
-				data_l &= ~(0x00ffU << 16);
-
-				if (ddr_csn >= 2)
-					k = (high_dq[ch] ^ 0x0f);
-				else
-					k = high_dq[ch];
-				data_l |= (k << 16);
-				mmio_write_32(DBSC_DBDFICNT(ch), data_l);
-				ddr_setval(ch, _reg_PI_WDQLVL_RESP_MASK, k);
-			}
-		}
-		if (((prr_product == PRR_PRODUCT_H3) &&
-		     (prr_cut <= PRR_PRODUCT_11)) ||
-		    ((prr_product == PRR_PRODUCT_M3) &&
-		     (prr_cut == PRR_PRODUCT_10))) {
-			wdqdm_cp(ddr_csn, 0);
-		}
-
-		foreach_vch(ch) {
-			data_l =
-			    ddr_getval(ch,
-				       reg_pi_mr14_data_fx_csx[1][ddr_csn]);
-			ddr_setval(ch, reg_pi_mr14_data_fx_csx[1][0], data_l);
-		}
-
-		/* KICK WDQLVL */
-		err = swlvl1(ddr_csn, _reg_PI_WDQLVL_CS, _reg_PI_WDQLVL_REQ);
-		if (err)
-			goto err_exit;
-
-		if (ddr_csn == 0)
-			foreach_vch(ch) {
-			mr14_csab0_bak[ch] =
-			    ddr_getval(ch, reg_pi_mr14_data_fx_csx[1][0]);
-		} else
-			foreach_vch(ch) {
-			ddr_setval(ch, reg_pi_mr14_data_fx_csx[1][0],
-				   mr14_csab0_bak[ch]);
-			}
-#ifndef DDR_FAST_INIT
-		foreach_vch(ch) {
-			if (!(ch_have_this_cs[ddr_csn % 2] & (1U << ch))) {
-				wdqdm_clr1(ch, ddr_csn);
-				continue;
-			}
-			err = wdqdm_ana1(ch, ddr_csn);
-			if (err)
-				err_flg |= (1U << (ddr_csn * 4 + ch));
-			ddrphy_regif_idle();
-		}
-#endif/* DDR_FAST_INIT */
-	}
-err_exit:
-#ifndef DDR_FAST_INIT
-	err |= err_flg;
-#endif/* DDR_FAST_INIT */
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		ddr_setval_ach(_reg_PI_16BIT_DRAM_CONNECT, 0x01);
-		foreach_vch(ch) {
-			data_l = mmio_read_32(DBSC_DBDFICNT(ch));
-			data_l &= ~(0x00ffU << 16);
-			mmio_write_32(DBSC_DBDFICNT(ch), data_l);
-			ddr_setval(ch, _reg_PI_WDQLVL_RESP_MASK, 0x00);
-		}
-	}
-	return err;
-}
-
-static uint32_t wdqdm_man(void)
-{
-	uint32_t err, retry_cnt;
-	const uint32_t retry_max = 0x10;
-	uint32_t datal, ch, ddr_csn, mr14_bkup[4][4];
-
-	datal = RL + js2[js2_tdqsck] + (16 / 2) + 1 - WL + 2 + 2 + 19;
-	if ((mmio_read_32(DBSC_DBTR(11)) & 0xFF) > datal)
-		datal = mmio_read_32(DBSC_DBTR(11)) & 0xFF;
-	ddr_setval_ach(_reg_PI_TDFI_WDQLVL_RW, datal);
-
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut > PRR_PRODUCT_11)) ||
-	    (prr_product == PRR_PRODUCT_M3N) ||
-	    (prr_product == PRR_PRODUCT_V3H)) {
-		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR_F0,
-			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
-		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR_F1,
-			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
-	} else {
-		ddr_setval_ach(_reg_PI_TDFI_WDQLVL_WR,
-			       (mmio_read_32(DBSC_DBTR(12)) & 0xFF) + 10);
-	}
-	ddr_setval_ach(_reg_PI_TRFC_F0, mmio_read_32(DBSC_DBTR(13)) & 0x1FF);
-	ddr_setval_ach(_reg_PI_TRFC_F1, mmio_read_32(DBSC_DBTR(13)) & 0x1FF);
-
-	retry_cnt = 0;
-	err = 0;
-	do {
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			err = wdqdm_man1();
-		} else {
-			ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x01);
-			ddr_setval_ach(_reg_PI_WDQLVL_VREF_NORMAL_STEPSIZE,
-				       0x01);
-			if ((prr_product == PRR_PRODUCT_M3N) ||
-			    (prr_product == PRR_PRODUCT_V3H)) {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
-					       0x0C);
-			} else {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x0C);
-			}
-			dsb_sev();
-			err = wdqdm_man1();
-			foreach_vch(ch) {
-				for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
-					mr14_bkup[ch][ddr_csn] =
-					    ddr_getval(ch,
-						       reg_pi_mr14_data_fx_csx
-						       [1][ddr_csn]);
-					dsb_sev();
-				}
-			}
-
-			if ((prr_product == PRR_PRODUCT_M3N) ||
-			    (prr_product == PRR_PRODUCT_V3H)) {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
-					       0x04);
-			} else {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x04);
-			}
-			pvtcode_update();
-			err = wdqdm_man1();
-			foreach_vch(ch) {
-				for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
-					mr14_bkup[ch][ddr_csn] =
-					    (mr14_bkup[ch][ddr_csn] +
-					     ddr_getval(ch,
-							reg_pi_mr14_data_fx_csx
-							[1][ddr_csn])) / 2;
-					ddr_setval(ch,
-						   reg_pi_mr14_data_fx_csx[1]
-						   [ddr_csn],
-						   mr14_bkup[ch][ddr_csn]);
-				}
-			}
-
-			ddr_setval_ach(_reg_PI_WDQLVL_VREF_NORMAL_STEPSIZE,
-				       0x00);
-			if ((prr_product == PRR_PRODUCT_M3N) ||
-			    (prr_product == PRR_PRODUCT_V3H)) {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA_F1,
-					       0x00);
-				ddr_setval_ach
-				    (_reg_PI_WDQLVL_VREF_INITIAL_START_POINT_F1,
-				     0x00);
-				ddr_setval_ach
-				    (_reg_PI_WDQLVL_VREF_INITIAL_STOP_POINT_F1,
-				     0x00);
-			} else {
-				ddr_setval_ach(_reg_PI_WDQLVL_VREF_DELTA, 0x00);
-				ddr_setval_ach
-				    (_reg_PI_WDQLVL_VREF_INITIAL_START_POINT,
-				     0x00);
-				ddr_setval_ach
-				    (_reg_PI_WDQLVL_VREF_INITIAL_STOP_POINT,
-				     0x00);
-			}
-			ddr_setval_ach(_reg_PI_WDQLVL_VREF_INITIAL_STEPSIZE,
-				       0x00);
-
-			pvtcode_update2();
-			err = wdqdm_man1();
-			ddr_setval_ach(_reg_PI_WDQLVL_VREF_EN, 0x00);
-		}
-	} while (err && (++retry_cnt < retry_max));
-
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut <= PRR_PRODUCT_10))) {
-		wdqdm_cp(0, 1);
-	}
-
-	return (retry_cnt >= retry_max);
-}
-
-/* RDQ TRAINING */
-#ifndef DDR_FAST_INIT
-static void rdqdm_clr1(uint32_t ch, uint32_t ddr_csn)
-{
-	int32_t i, k;
-	uint32_t cs, slice;
-	uint32_t data_l;
-
-	/* clr of training results buffer */
-	cs = ddr_csn % 2;
-	data_l = board_cnf->dqdm_dly_r;
-	for (slice = 0; slice < SLICE_CNT; slice++) {
-		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
-		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
-			continue;
-
-		for (i = 0; i <= 8; i++) {
-			if (ch_have_this_cs[CS_CNT - 1 - cs] & (1U << ch)) {
-				rdqdm_dly[ch][cs][slice][i] =
-				    rdqdm_dly[ch][CS_CNT - 1 - cs][slice][i];
-				rdqdm_dly[ch][cs][slice + SLICE_CNT][i] =
-				    rdqdm_dly[ch][CS_CNT - 1 - cs][slice +
-								   SLICE_CNT]
-				    [i];
-			} else {
-				rdqdm_dly[ch][cs][slice][i] = data_l;
-				rdqdm_dly[ch][cs][slice + SLICE_CNT][i] =
-					data_l;
-			}
-			rdqdm_le[ch][cs][slice][i] = 0;
-			rdqdm_le[ch][cs][slice + SLICE_CNT][i] = 0;
-			rdqdm_te[ch][cs][slice][i] = 0;
-			rdqdm_te[ch][cs][slice + SLICE_CNT][i] = 0;
-			rdqdm_nw[ch][cs][slice][i] = 0;
-			rdqdm_nw[ch][cs][slice + SLICE_CNT][i] = 0;
-		}
-		rdqdm_st[ch][cs][slice] = 0;
-		rdqdm_win[ch][cs][slice] = 0;
-	}
-}
-
-static uint32_t rdqdm_ana1(uint32_t ch, uint32_t ddr_csn)
-{
-	int32_t i, k;
-	uint32_t cs, slice;
-	uint32_t data_l;
-	uint32_t err;
-	int8_t _adj;
-	int16_t adj;
-	uint32_t dq;
-	int32_t min_win;
-	int32_t win;
-	uint32_t rdq_status_obs_select;
-
-	/* analysis of training results */
-	err = 0;
-	for (slice = 0; slice < SLICE_CNT; slice++) {
-		k = (board_cnf->ch[ch].dqs_swap >> (4 * slice)) & 0x0f;
-		if (((k >= 2) && (ddr_csn < 2)) || ((k < 2) && (ddr_csn >= 2)))
-			continue;
-
-		cs = ddr_csn % 2;
-		ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, cs);
-		ddrphy_regif_idle();
-
-		ddr_getval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX);
-		ddrphy_regif_idle();
-
-		for (i = 0; i <= 8; i++) {
-			dq = slice * 8 + i;
-			if (i == 8)
-				_adj = board_cnf->ch[ch].dm_adj_r[slice];
-			else
-				_adj = board_cnf->ch[ch].dq_adj_r[dq];
-
-			adj = _f_scale_adj(_adj);
-
-			data_l =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i]) +
-			    adj;
-			ddr_setval_s(ch, slice,
-				     _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i],
-				     data_l);
-			rdqdm_dly[ch][cs][slice][i] = data_l;
-
-			data_l =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i]) +
-			    adj;
-			ddr_setval_s(ch, slice,
-				     _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i],
-				     data_l);
-			rdqdm_dly[ch][cs][slice + SLICE_CNT][i] = data_l;
-		}
-		min_win = INT_LEAST32_MAX;
-		for (i = 0; i <= 8; i++) {
-			data_l =
-			    ddr_getval_s(ch, slice, _reg_PHY_RDLVL_STATUS_OBS);
-			rdqdm_st[ch][cs][slice] = data_l;
-			rdqdm_st[ch][cs][slice + SLICE_CNT] = data_l;
-			/* k : rise/fall */
-			for (k = 0; k < 2; k++) {
-				if (i == 8) {
-					rdq_status_obs_select = 16 + 8 * k;
-				} else {
-					rdq_status_obs_select = i + k * 8;
-				}
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_RDLVL_RDDQS_DQ_OBS_SELECT,
-					     rdq_status_obs_select);
-
-				data_l =
-				    ddr_getval_s(ch, slice,
-						 _reg_PHY_RDLVL_RDDQS_DQ_LE_DLY_OBS);
-				rdqdm_le[ch][cs][slice + SLICE_CNT * k][i] =
-				    data_l;
-
-				data_l =
-				    ddr_getval_s(ch, slice,
-						 _reg_PHY_RDLVL_RDDQS_DQ_TE_DLY_OBS);
-				rdqdm_te[ch][cs][slice + SLICE_CNT * k][i] =
-				    data_l;
-
-				data_l =
-				    ddr_getval_s(ch, slice,
-						 _reg_PHY_RDLVL_RDDQS_DQ_NUM_WINDOWS_OBS);
-				rdqdm_nw[ch][cs][slice + SLICE_CNT * k][i] =
-				    data_l;
-
-				win =
-				    (int32_t)rdqdm_te[ch][cs][slice +
-							      SLICE_CNT *
-							      k][i] -
-				    rdqdm_le[ch][cs][slice + SLICE_CNT * k][i];
-				if (i != 8) {
-					if (min_win > win)
-						min_win = win;
-				}
-			}
-		}
-		rdqdm_win[ch][cs][slice] = min_win;
-		if (min_win <= 0) {
-			err = 2;
-		}
-	}
-	return err;
-}
-#endif/* DDR_FAST_INIT */
-
-static uint32_t rdqdm_man1(void)
-{
-	uint32_t ch;
-	uint32_t ddr_csn;
-#ifdef DDR_FAST_INIT
-	uint32_t slice;
-	uint32_t i, adj, data_l;
-#endif/* DDR_FAST_INIT */
-	uint32_t err;
-
-	/* manual execution of training */
-	err = 0;
-
-	for (ddr_csn = 0; ddr_csn < CSAB_CNT; ddr_csn++) {
-		/* KICK RDQLVL */
-		err = swlvl1(ddr_csn, _reg_PI_RDLVL_CS, _reg_PI_RDLVL_REQ);
-		if (err)
-			goto err_exit;
-#ifndef DDR_FAST_INIT
-		foreach_vch(ch) {
-			if (!(ch_have_this_cs[ddr_csn % 2] & (1U << ch))) {
-				rdqdm_clr1(ch, ddr_csn);
-				ddrphy_regif_idle();
-				continue;
-			}
-			err = rdqdm_ana1(ch, ddr_csn);
-			ddrphy_regif_idle();
-			if (err)
-				goto err_exit;
-		}
-#else/* DDR_FAST_INIT */
-		foreach_vch(ch) {
-			if (ch_have_this_cs[ddr_csn] & (1U << ch)) {
-				for (slice = 0; slice < SLICE_CNT; slice++) {
-					if (ddr_getval_s(ch, slice,
-							 _reg_PHY_RDLVL_STATUS_OBS) !=
-					    0x0D00FFFF) {
-						err = (1U << ch) |
-							(0x10U << slice);
-						goto err_exit;
-					}
-				}
-			}
-			if (((prr_product == PRR_PRODUCT_H3) &&
-			     (prr_cut <= PRR_PRODUCT_11)) ||
-			    ((prr_product == PRR_PRODUCT_M3) &&
-			     (prr_cut <= PRR_PRODUCT_10))) {
-				for (slice = 0; slice < SLICE_CNT; slice++) {
-					for (i = 0; i <= 8; i++) {
-						if (i == 8)
-							adj = _f_scale_adj(board_cnf->ch[ch].dm_adj_r[slice]);
-						else
-							adj = _f_scale_adj(board_cnf->ch[ch].dq_adj_r[slice * 8 + i]);
-						ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX, ddr_csn);
-						data_l = ddr_getval_s(ch, slice, _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i]) + adj;
-						ddr_setval_s(ch, slice, _reg_PHY_RDDQS_X_RISE_SLAVE_DELAY[i], data_l);
-						rdqdm_dly[ch][ddr_csn][slice][i] = data_l;
-						rdqdm_dly[ch][ddr_csn | 1][slice][i] = data_l;
-
-						data_l = ddr_getval_s(ch, slice, _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i]) + adj;
-						ddr_setval_s(ch, slice, _reg_PHY_RDDQS_X_FALL_SLAVE_DELAY[i], data_l);
-						rdqdm_dly[ch][ddr_csn][slice + SLICE_CNT][i] = data_l;
-						rdqdm_dly[ch][ddr_csn | 1][slice + SLICE_CNT][i] = data_l;
-					}
-				}
-			}
-		}
-		ddrphy_regif_idle();
-
-#endif/* DDR_FAST_INIT */
-	}
-
-err_exit:
-	return err;
-}
-
-static uint32_t rdqdm_man(void)
-{
-	uint32_t err, retry_cnt;
-	const uint32_t retry_max = 0x01;
-
-	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_ENABLE,
-			  0x00000004 | ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-						     _reg_PHY_DQ_TSEL_ENABLE));
-	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_ENABLE,
-			  0x00000004 | ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-						     _reg_PHY_DQS_TSEL_ENABLE));
-	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_SELECT,
-			  0xFF0FFFFF & ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-						     _reg_PHY_DQ_TSEL_SELECT));
-	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_SELECT,
-			  0xFF0FFFFF & ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-						     _reg_PHY_DQS_TSEL_SELECT));
-
-	retry_cnt = 0;
-	do {
-		err = rdqdm_man1();
-		ddrphy_regif_idle();
-	} while (err && (++retry_cnt < retry_max));
-	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_ENABLE,
-			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-					_reg_PHY_DQ_TSEL_ENABLE));
-	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_ENABLE,
-			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-					_reg_PHY_DQS_TSEL_ENABLE));
-	ddr_setval_ach_as(_reg_PHY_DQ_TSEL_SELECT,
-			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-					_reg_PHY_DQ_TSEL_SELECT));
-	ddr_setval_ach_as(_reg_PHY_DQS_TSEL_SELECT,
-			  ddrtbl_getval(_cnf_DDR_PHY_SLICE_REGSET,
-					_reg_PHY_DQS_TSEL_SELECT));
-
-	return (retry_cnt >= retry_max);
-}
-
-/* rx offset calibration */
-static int32_t _find_change(uint64_t val, uint32_t dir)
-{
-	int32_t i;
-	uint32_t startval;
-	uint32_t curval;
-	const int32_t VAL_END = 0x3f;
-
-	if (dir == 0) {
-		startval = (val & 0x01);
-		for (i = 1; i <= VAL_END; i++) {
-			curval = (val >> i) & 0x01;
-			if (curval != startval)
-				return i;
-		}
-		return VAL_END;
-	}
-
-	startval = (val >> dir) & 0x01;
-	for (i = dir - 1; i >= 0; i--) {
-		curval = (val >> i) & 0x01;
-		if (curval != startval)
-			return i;
-	}
-	return 0;
-}
-
-static uint32_t _rx_offset_cal_updn(uint32_t code)
-{
-	const uint32_t CODE_MAX = 0x40;
-	uint32_t tmp;
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) {
-		if (code == 0)
-			tmp = (1U << 6) | (CODE_MAX - 1);
-		else if (code <= 0x20)
-			tmp =
-			    ((CODE_MAX - 1 -
-			      (0x20 - code) * 2) << 6) | (CODE_MAX - 1);
-		else
-			tmp =
-			    ((CODE_MAX - 1) << 6) | (CODE_MAX - 1 -
-						     (code - 0x20) * 2);
-	} else {
-		if (code == 0)
-			tmp = (1U << 6) | (CODE_MAX - 1);
-		else
-			tmp = (code << 6) | (CODE_MAX - code);
-	}
-	return tmp;
-}
-
-static uint32_t rx_offset_cal(void)
-{
-	uint32_t index;
-	uint32_t code;
-	const uint32_t CODE_MAX = 0x40;
-	const uint32_t CODE_STEP = 2;
-	uint32_t ch, slice;
-	uint32_t tmp;
-	uint32_t tmp_ach_as[DRAM_CH_CNT][SLICE_CNT];
-	uint64_t val[DRAM_CH_CNT][SLICE_CNT][_reg_PHY_RX_CAL_X_NUM];
-	uint64_t tmpval;
-	int32_t lsb, msb;
-
-	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x01);
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			for (index = 0; index < _reg_PHY_RX_CAL_X_NUM; index++)
-				val[ch][slice][index] = 0;
-		}
-	}
-
-	for (code = 0; code < CODE_MAX / CODE_STEP; code++) {
-		tmp = _rx_offset_cal_updn(code * CODE_STEP);
-		for (index = 0; index < _reg_PHY_RX_CAL_X_NUM; index++) {
-			ddr_setval_ach_as(_reg_PHY_RX_CAL_X[index], tmp);
-		}
-		dsb_sev();
-		ddr_getval_ach_as(_reg_PHY_RX_CAL_OBS, (uint32_t *)tmp_ach_as);
-
-		foreach_vch(ch) {
-			for (slice = 0; slice < SLICE_CNT; slice++) {
-				tmp = tmp_ach_as[ch][slice];
-				for (index = 0; index < _reg_PHY_RX_CAL_X_NUM;
-				     index++) {
-					if (tmp & (1U << index)) {
-						val[ch][slice][index] |=
-						    (1ULL << code);
-					} else {
-						val[ch][slice][index] &=
-						    ~(1ULL << code);
-					}
-				}
-			}
-		}
-	}
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			for (index = 0; index < _reg_PHY_RX_CAL_X_NUM;
-			     index++) {
-				tmpval = val[ch][slice][index];
-				lsb = _find_change(tmpval, 0);
-				msb =
-				    _find_change(tmpval,
-						 (CODE_MAX / CODE_STEP) - 1);
-				tmp = (lsb + msb) >> 1;
-
-				tmp = _rx_offset_cal_updn(tmp * CODE_STEP);
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_RX_CAL_X[index], tmp);
-			}
-		}
-	}
-	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x00);
-
-	return 0;
-}
-
-static uint32_t rx_offset_cal_hw(void)
-{
-	uint32_t ch, slice;
-	uint32_t retry;
-	uint32_t complete;
-	uint32_t tmp;
-	uint32_t tmp_ach_as[DRAM_CH_CNT][SLICE_CNT];
-
-	ddr_setval_ach_as(_reg_PHY_RX_CAL_X[9], 0x00);
-	ddr_setval_ach_as(_reg_PHY_RX_CAL_OVERRIDE, 0x00);
-	ddr_setval_ach_as(_reg_PHY_RX_CAL_SAMPLE_WAIT, 0x0f);
-
-	retry = 0;
-	while (retry < 4096) {
-		if ((retry & 0xff) == 0) {
-			ddr_setval_ach_as(_reg_SC_PHY_RX_CAL_START, 0x01);
-		}
-		foreach_vch(ch)
-		for (slice = 0; slice < SLICE_CNT; slice++)
-			tmp_ach_as[ch][slice] =
-			    ddr_getval_s(ch, slice, _reg_PHY_RX_CAL_X[9]);
-
-		complete = 1;
-		foreach_vch(ch) {
-			for (slice = 0; slice < SLICE_CNT; slice++) {
-				tmp = tmp_ach_as[ch][slice];
-				tmp = (tmp & 0x3f) + ((tmp >> 6) & 0x3f);
-				if (((prr_product == PRR_PRODUCT_H3) &&
-				     (prr_cut > PRR_PRODUCT_11)) ||
-				    (prr_product == PRR_PRODUCT_M3N) ||
-				    (prr_product == PRR_PRODUCT_V3H)) {
-					if (tmp != 0x3E)
-						complete = 0;
-				} else {
-					if (tmp != 0x40)
-						complete = 0;
-				}
-			}
-		}
-		if (complete)
-			break;
-
-		retry++;
-	}
-
-	return (complete == 0);
-}
-
-/* adjust rddqs latency */
-static void adjust_rddqs_latency(void)
-{
-	uint32_t ch, slice;
-	uint32_t dly;
-	uint32_t maxlatx2;
-	uint32_t tmp;
-	uint32_t rdlat_adjx2[SLICE_CNT];
-
-	foreach_vch(ch) {
-		maxlatx2 = 0;
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			ddr_setval_s(ch, slice, _reg_PHY_PER_CS_TRAINING_INDEX,
-				     0x00);
-
-			dly =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_RDDQS_GATE_SLAVE_DELAY);
-			tmp =
-			    ddr_getval_s(ch, slice,
-					 _reg_PHY_RDDQS_LATENCY_ADJUST);
-			/* note gate_slave_delay[9] is always 0 */
-			tmp = (tmp << 1) + (dly >> 8);
-			rdlat_adjx2[slice] = tmp;
-			if (maxlatx2 < tmp)
-				maxlatx2 = tmp;
-		}
-		maxlatx2 = ((maxlatx2 + 1) >> 1) << 1;
-		for (slice = 0; slice < SLICE_CNT; slice++) {
-			tmp = maxlatx2 - rdlat_adjx2[slice];
-			tmp = (tmp >> 1);
-			if (tmp) {
-				ddr_setval_s(ch, slice, _reg_PHY_RPTR_UPDATE,
-					     ddr_getval_s(ch, slice,
-							  _reg_PHY_RPTR_UPDATE)
-					     + 1);
-			}
-		}
-	}
-}
-
-/* adjust wpath latency */
-static void adjust_wpath_latency(void)
-{
-	uint32_t ch, cs, slice;
-	uint32_t dly;
-	uint32_t wpath_add;
-	const uint32_t _par_EARLY_THRESHOLD_VAL = 0x180;
-
-	foreach_vch(ch) {
-		for (slice = 0; slice < SLICE_CNT; slice += 1) {
-			for (cs = 0; cs < CS_CNT; cs++) {
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_PER_CS_TRAINING_INDEX,
-					     cs);
-				ddr_getval_s(ch, slice,
-					     _reg_PHY_PER_CS_TRAINING_INDEX);
-				dly =
-				    ddr_getval_s(ch, slice,
-						 _reg_PHY_CLK_WRDQS_SLAVE_DELAY);
-				if (dly <= _par_EARLY_THRESHOLD_VAL)
-					continue;
-
-				wpath_add =
-				    ddr_getval_s(ch, slice,
-						 _reg_PHY_WRITE_PATH_LAT_ADD);
-				ddr_setval_s(ch, slice,
-					     _reg_PHY_WRITE_PATH_LAT_ADD,
-					     wpath_add - 1);
-			}
-		}
-	}
-}
-
-/* DDR Initialize entry */
-int32_t rcar_dram_init(void)
-{
-	uint32_t ch, cs;
-	uint32_t data_l;
-	uint32_t bus_mbps, bus_mbpsdiv;
-	uint32_t tmp_tccd;
-	uint32_t failcount;
-	uint32_t cnf_boardtype;
-
-	/* Thermal sensor setting */
-	data_l = mmio_read_32(CPG_MSTPSR5);
-	if (data_l & BIT(22)) {	/*  case THS/TSC Standby */
-		data_l &= ~BIT(22);
-		cpg_write_32(CPG_SMSTPCR5, data_l);
-		while (mmio_read_32(CPG_MSTPSR5) & BIT(22))
-			;  /*  wait bit=0 */
-	}
-
-	/* THCTR Bit6: PONM=0 , Bit0: THSST=0   */
-	data_l = mmio_read_32(THS1_THCTR) & 0xFFFFFFBE;
-	mmio_write_32(THS1_THCTR, data_l);
-
-	/* Judge product and cut */
-#ifdef RCAR_DDR_FIXED_LSI_TYPE
-#if (RCAR_LSI == RCAR_AUTO)
-	prr_product = mmio_read_32(PRR) & PRR_PRODUCT_MASK;
-	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
-#else /* RCAR_LSI */
-#ifndef RCAR_LSI_CUT
-	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
-#endif /* RCAR_LSI_CUT */
-#endif /* RCAR_LSI */
-#else /* RCAR_DDR_FIXED_LSI_TYPE */
-	prr_product = mmio_read_32(PRR) & PRR_PRODUCT_MASK;
-	prr_cut = mmio_read_32(PRR) & PRR_CUT_MASK;
-#endif /* RCAR_DDR_FIXED_LSI_TYPE */
-
-	if (prr_product == PRR_PRODUCT_H3) {
-		if (prr_cut <= PRR_PRODUCT_11) {
-			p_ddr_regdef_tbl =
-				(const uint32_t *)&DDR_REGDEF_TBL[0][0];
-		} else {
-			p_ddr_regdef_tbl =
-				(const uint32_t *)&DDR_REGDEF_TBL[2][0];
-		}
-	} else if (prr_product == PRR_PRODUCT_M3) {
-		p_ddr_regdef_tbl =
-			(const uint32_t *)&DDR_REGDEF_TBL[1][0];
-	} else if ((prr_product == PRR_PRODUCT_M3N) ||
-		   (prr_product == PRR_PRODUCT_V3H)) {
-		p_ddr_regdef_tbl =
-			(const uint32_t *)&DDR_REGDEF_TBL[3][0];
-	} else {
-		FATAL_MSG("BL2: DDR:Unknown Product\n");
-		return 0xff;
-	}
-
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30))) {
-		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
-	} else {
-		mmio_write_32(DBSC_DBSYSCNT0, 0x00001234);
-	}
-
-	/* Judge board type */
-	cnf_boardtype = boardcnf_get_brd_type();
-	if (cnf_boardtype >= BOARDNUM) {
-		FATAL_MSG("BL2: DDR:Unknown Board\n");
-		return 0xff;
-	}
-	board_cnf = (const struct _boardcnf *)&boardcnfs[cnf_boardtype];
-
-/* RCAR_DRAM_SPLIT_2CH           (2U) */
-#if RCAR_DRAM_SPLIT == 2
-	/* H3(Test for future H3-N): Swap ch2 and ch1 for 2ch-split */
-	if ((prr_product == PRR_PRODUCT_H3) && (board_cnf->phyvalid == 0x05)) {
-		mmio_write_32(DBSC_DBMEMSWAPCONF0, 0x00000006);
-		ddr_phyvalid = 0x03;
-	} else {
-		ddr_phyvalid = board_cnf->phyvalid;
-	}
-#else /* RCAR_DRAM_SPLIT_2CH */
-	ddr_phyvalid = board_cnf->phyvalid;
-#endif /* RCAR_DRAM_SPLIT_2CH */
-
-	max_density = 0;
-
-	for (cs = 0; cs < CS_CNT; cs++) {
-		ch_have_this_cs[cs] = 0;
-	}
-
-	foreach_ech(ch)
-	for (cs = 0; cs < CS_CNT; cs++)
-		ddr_density[ch][cs] = 0xff;
-
-	foreach_vch(ch) {
-		for (cs = 0; cs < CS_CNT; cs++) {
-			data_l = board_cnf->ch[ch].ddr_density[cs];
-			ddr_density[ch][cs] = data_l;
-
-			if (data_l == 0xff)
-				continue;
-			if (data_l > max_density)
-				max_density = data_l;
-			if ((cs == 1) && (prr_product == PRR_PRODUCT_H3) &&
-			    (prr_cut <= PRR_PRODUCT_11))
-				continue;
-			ch_have_this_cs[cs] |= (1U << ch);
-		}
-	}
-
-	/* Judge board clock frequency (in MHz) */
-	boardcnf_get_brd_clk(cnf_boardtype, &brd_clk, &brd_clkdiv);
-	if ((brd_clk / brd_clkdiv) > 25) {
-		brd_clkdiva = 1;
-	} else {
-		brd_clkdiva = 0;
-	}
-
-	/* Judge ddr operating frequency clock(in Mbps) */
-	boardcnf_get_ddr_mbps(cnf_boardtype, &ddr_mbps, &ddr_mbpsdiv);
-
-	ddr0800_mul = CLK_DIV(800, 2, brd_clk, brd_clkdiv * (brd_clkdiva + 1));
-
-	ddr_mul = CLK_DIV(ddr_mbps, ddr_mbpsdiv * 2, brd_clk,
-			  brd_clkdiv * (brd_clkdiva + 1));
-
-	/* Adjust tccd */
-	data_l = (0x00006000 & mmio_read_32(RST_MODEMR)) >> 13;
-	bus_mbps = 0;
-	bus_mbpsdiv = 0;
-	switch (data_l) {
-	case 0:
-		bus_mbps = brd_clk * 0x60 * 2;
-		bus_mbpsdiv = brd_clkdiv * 1;
-		break;
-	case 1:
-		bus_mbps = brd_clk * 0x50 * 2;
-		bus_mbpsdiv = brd_clkdiv * 1;
-		break;
-	case 2:
-		bus_mbps = brd_clk * 0x40 * 2;
-		bus_mbpsdiv = brd_clkdiv * 1;
-		break;
-	case 3:
-		bus_mbps = brd_clk * 0x60 * 2;
-		bus_mbpsdiv = brd_clkdiv * 2;
-		break;
-	default:
-		bus_mbps = brd_clk * 0x60 * 2;
-		bus_mbpsdiv = brd_clkdiv * 2;
-		break;
-	}
-	tmp_tccd = CLK_DIV(ddr_mbps * 8, ddr_mbpsdiv, bus_mbps, bus_mbpsdiv);
-	if (8 * ddr_mbps * bus_mbpsdiv != tmp_tccd * bus_mbps * ddr_mbpsdiv)
-		tmp_tccd = tmp_tccd + 1;
-
-	if (tmp_tccd < 8)
-		ddr_tccd = 8;
-	else
-		ddr_tccd = tmp_tccd;
-
-	NOTICE("BL2: DDR%d(%s)\n", ddr_mbps / ddr_mbpsdiv, RCAR_DDR_VERSION);
-
-	MSG_LF("Start\n");
-
-	/* PLL Setting */
-	pll3_control(1);
-
-	/* initialize DDR */
-	data_l = init_ddr();
-	if (data_l == ddr_phyvalid) {
-		failcount = 0;
-	} else {
-		failcount = 1;
-	}
-
-	foreach_vch(ch)
-	    mmio_write_32(DBSC_DBPDLK(ch), 0x00000000);
-	if (((prr_product == PRR_PRODUCT_H3) && (prr_cut <= PRR_PRODUCT_11)) ||
-	    ((prr_product == PRR_PRODUCT_M3) && (prr_cut < PRR_PRODUCT_30))) {
-		/* non : H3 Ver.1.x/M3-W Ver.1.x not support */
-	} else {
-		mmio_write_32(DBSC_DBSYSCNT0, 0x00000000);
-	}
-
-	if (failcount == 0) {
-		return INITDRAM_OK;
-	} else {
-		return INITDRAM_NG;
-	}
-}
-
-void pvtcode_update(void)
-{
-	uint32_t ch;
-	uint32_t data_l;
-	uint32_t pvtp[4], pvtn[4], pvtp_init, pvtn_init;
-	int32_t pvtp_tmp, pvtn_tmp;
-
-	foreach_vch(ch) {
-		pvtn_init = (tcal.tcomp_cal[ch] & 0xFC0) >> 6;
-		pvtp_init = (tcal.tcomp_cal[ch] & 0x03F) >> 0;
-
-		if (8912 * pvtp_init > 44230) {
-			pvtp_tmp = (5000 + 8912 * pvtp_init - 44230) / 10000;
-		} else {
-			pvtp_tmp =
-			    -((-(5000 + 8912 * pvtp_init - 44230)) / 10000);
-		}
-		pvtn_tmp = (5000 + 5776 * pvtn_init + 30280) / 10000;
-
-		pvtn[ch] = pvtn_tmp + pvtn_init;
-		pvtp[ch] = pvtp_tmp + pvtp_init;
-
-		if (pvtn[ch] > 63) {
-			pvtn[ch] = 63;
-			pvtp[ch] =
-			    (pvtp_tmp) * (63 - 6 * pvtn_tmp -
-					  pvtn_init) / (pvtn_tmp) +
-			    6 * pvtp_tmp + pvtp_init;
-		}
-		if ((prr_product == PRR_PRODUCT_H3) &&
-		    (prr_cut <= PRR_PRODUCT_11)) {
-			data_l = pvtp[ch] | (pvtn[ch] << 6) |
-				 (tcal.tcomp_cal[ch] & 0xfffff000);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
-					 data_l | 0x00020000);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
-					 data_l);
-		} else {
-			data_l = pvtp[ch] | (pvtn[ch] << 6) | 0x00015000;
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
-					 data_l | 0x00020000);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
-					 data_l);
-			reg_ddrphy_write(ch,
-					 ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
-					 data_l);
-		}
-	}
-}
-
-void pvtcode_update2(void)
-{
-	uint32_t ch;
-
-	foreach_vch(ch) {
-		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_FDBK_TERM),
-				 tcal.init_cal[ch] | 0x00020000);
-		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_DATA_TERM),
-				 tcal.init_cal[ch]);
-		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_DQS_TERM),
-				 tcal.init_cal[ch]);
-		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_ADDR_TERM),
-				 tcal.init_cal[ch]);
-		reg_ddrphy_write(ch, ddr_regdef_adr(_reg_PHY_PAD_CS_TERM),
-				 tcal.init_cal[ch]);
-	}
-}
-
-void ddr_padcal_tcompensate_getinit(uint32_t override)
-{
-	uint32_t ch;
-	uint32_t data_l;
-	uint32_t pvtp, pvtn;
-
-	tcal.init_temp = 0;
-	for (ch = 0; ch < 4; ch++) {
-		tcal.init_cal[ch] = 0;
-		tcal.tcomp_cal[ch] = 0;
-	}
-
-	foreach_vch(ch) {
-		tcal.init_cal[ch] = ddr_getval(ch, _reg_PHY_PAD_TERM_X[1]);
-		tcal.tcomp_cal[ch] = ddr_getval(ch, _reg_PHY_PAD_TERM_X[1]);
-	}
-
-	if (!override) {
-		data_l = mmio_read_32(THS1_TEMP);
-		if (data_l < 2800) {
-			tcal.init_temp =
-			    (143 * (int32_t)data_l - 359000) / 1000;
-		} else {
-			tcal.init_temp =
-			    (121 * (int32_t)data_l - 296300) / 1000;
-		}
-
-		foreach_vch(ch) {
-			pvtp = (tcal.init_cal[ch] >> 0) & 0x000003F;
-			pvtn = (tcal.init_cal[ch] >> 6) & 0x000003F;
-			if ((int32_t)pvtp >
-			    ((tcal.init_temp * 29 - 3625) / 1000))
-				pvtp =
-				    (int32_t)pvtp +
-				    ((3625 - tcal.init_temp * 29) / 1000);
-			else
-				pvtp = 0;
-
-			if ((int32_t)pvtn >
-			    ((tcal.init_temp * 54 - 6750) / 1000))
-				pvtn =
-				    (int32_t)pvtn +
-				    ((6750 - tcal.init_temp * 54) / 1000);
-			else
-				pvtn = 0;
-
-			if ((prr_product == PRR_PRODUCT_H3) &&
-			    (prr_cut <= PRR_PRODUCT_11)) {
-				tcal.init_cal[ch] =
-				    (tcal.init_cal[ch] & 0xfffff000) |
-				    (pvtn << 6) |
-				    pvtp;
-			} else {
-				tcal.init_cal[ch] =
-				    0x00015000 | (pvtn << 6) | pvtp;
-			}
-		}
-		tcal.init_temp = 125;
-	}
-}
-
-#ifndef ddr_qos_init_setting
-/* For QoS init */
-uint8_t get_boardcnf_phyvalid(void)
-{
-	return ddr_phyvalid;
-}
-#endif /* ddr_qos_init_setting */
diff --git a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_config.c b/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_config.c
deleted file mode 100644
index de126de..0000000
--- a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_config.c
+++ /dev/null
@@ -1,1804 +0,0 @@
-/*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation.
- * All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#define BOARDNUM 22
-#define BOARD_JUDGE_AUTO
-
-#ifdef BOARD_JUDGE_AUTO
-static uint32_t _board_judge(void);
-
-static uint32_t boardcnf_get_brd_type(void)
-{
-	return _board_judge();
-}
-#else
-static uint32_t boardcnf_get_brd_type(void)
-{
-	return 1;
-}
-#endif
-
-#define DDR_FAST_INIT
-
-struct _boardcnf_ch {
-	uint8_t ddr_density[CS_CNT];
-	uint64_t ca_swap;
-	uint16_t dqs_swap;
-	uint32_t dq_swap[SLICE_CNT];
-	uint8_t dm_swap[SLICE_CNT];
-	uint16_t wdqlvl_patt[16];
-	int8_t cacs_adj[16];
-	int8_t dm_adj_w[SLICE_CNT];
-	int8_t dq_adj_w[SLICE_CNT * 8];
-	int8_t dm_adj_r[SLICE_CNT];
-	int8_t dq_adj_r[SLICE_CNT * 8];
-};
-
-struct _boardcnf {
-	uint8_t phyvalid;
-	uint8_t dbi_en;
-	uint16_t cacs_dly;
-	int16_t cacs_dly_adj;
-	uint16_t dqdm_dly_w;
-	uint16_t dqdm_dly_r;
-	struct _boardcnf_ch ch[DRAM_CH_CNT];
-};
-
-#define WDQLVL_PAT {\
-	0x00AA,\
-	0x0055,\
-	0x00AA,\
-	0x0155,\
-	0x01CC,\
-	0x0133,\
-	0x00CC,\
-	0x0033,\
-	0x00F0,\
-	0x010F,\
-	0x01F0,\
-	0x010F,\
-	0x00F0,\
-	0x00F0,\
-	0x000F,\
-	0x010F}
-
-static const struct _boardcnf boardcnfs[BOARDNUM] = {
-	{
-/* boardcnf[0] RENESAS SALVATOR-X board with M3-W/SIP */
-	 .phyvalid = 0x03,
-	 .dbi_en = 0x01,
-	 .cacs_dly = 0x02c0,
-	 .cacs_dly_adj = 0,
-	 .dqdm_dly_w = 0x0300,
-	 .dqdm_dly_r = 0x00a0,
-	 .ch = {
-		{
-		 {0x02, 0x02},
-		 0x00543210U,
-		 0x3201U,
-		 {0x70612543, 0x43251670, 0x45326170, 0x10672534},
-		 {0x08, 0x08, 0x08, 0x08},
-		 WDQLVL_PAT,
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0},
-		 {0, 0, 0, 0},
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0},
-		 {0, 0, 0, 0},
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0}
-		 },
-
-		{
-		 {0x02, 0x02},
-		 0x00543210,
-		 0x2310,
-		 {0x01327654, 0x34526107, 0x35421670, 0x70615324},
-		 {0x08, 0x08, 0x08, 0x08},
-		 WDQLVL_PAT,
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0},
-		 {0, 0, 0, 0},
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0},
-		 {0, 0, 0, 0},
-		 {0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0,
-		  0, 0, 0, 0, 0, 0, 0, 0}
-		}
-		}
-	 },
-/* boardcnf[1] RENESAS KRIEK board with M3-W/SoC */
-	{
-	 0x03,
-	 0x01,
-	 0x2c0,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00345201,
-	   0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[2] RENESAS SALVATOR-X board with H3 Ver.1.x/SIP(8Gbit 1rank) */
-	{
-	 0x0f,
-	 0x00,
-	 0x300,
-	 -320,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x3210,
-	   {0x20741365, 0x34256107, 0x57460321, 0x70614532},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x3102,
-	   {0x23547610, 0x34526107, 0x67452310, 0x32106754},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x0213,
-	   {0x30216754, 0x67453210, 0x70165243, 0x07162345},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x0213,
-	   {0x01327654, 0x70615432, 0x54760123, 0x07162345},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[3] RENESAS Starter Kit board with M3-W/SIP(8Gbit 1rank) */
-	{
-	 0x03,
-	 0x01,
-	 0x02c0,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x02, 0xFF},
-	   0x00543210U,
-	   0x3201,
-	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xFF},
-	   0x00543210,
-	   0x2310,
-	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[4] RENESAS SALVATOR-M(1rank) board with H3 Ver.1.x/SoC */
-	{
-	 0x0f,
-	 0x00,
-	 0x2c0,
-	 -320,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0xff},
-	   0x00315024,
-	   0x3120,
-	   {0x30671254, 0x26541037, 0x17054623, 0x12307645},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00025143,
-	   0x3210,
-	   {0x70613542, 0x16245307, 0x30712645, 0x21706354},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00523104,
-	   0x2301,
-	   {0x70613542, 0x16245307, 0x30712645, 0x21706354},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00153402,
-	   0x2031,
-	   {0x30671254, 0x26541037, 0x17054623, 0x12307645},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[5] RENESAS KRIEK-1rank board with M3-W/SoC */
-	{
-	 0x03,
-	 0x01,
-	 0x2c0,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0xff},
-	   0x00345201,
-	   0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[6] RENESAS SALVATOR-X board with H3 Ver.1.x/SIP(8Gbit 2rank) */
-	{
-	 0x0f,
-	 0x00,
-	 0x300,
-	 -320,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x3210,
-	   {0x20741365, 0x34256107, 0x57460321, 0x70614532},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x3102,
-	   {0x23547610, 0x34526107, 0x67452310, 0x32106754},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x0213,
-	   {0x30216754, 0x67453210, 0x70165243, 0x07162345},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x0213,
-	   {0x01327654, 0x70615432, 0x54760123, 0x07162345},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/*
- * boardcnf[7] RENESAS SALVATOR-X board with
- * H3 Ver.2.0 or later/SIP(8Gbit 1rank)
- */
-	{
-	 0x0f,
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x2310,
-	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00105432,
-	   0x3210,
-	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/*
- * boardcnf[8] RENESAS SALVATOR-X board with
- * H3 Ver.2.0 or later/SIP(8Gbit 2rank)
- */
-	{
-#if RCAR_DRAM_CHANNEL == 5
-	 0x05,
-#else
-	 0x0f,
-#endif
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x2310,
-	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#if ((RCAR_DRAM_CHANNEL == 5) && (RCAR_DRAM_SPLIT == 2))
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x2301,
-	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#else
-	{
-	   {0x02, 0x02},
-	   0x00105432,
-	   0x3210,
-	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#endif
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x2301,
-	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00543210,
-	   0x2301,
-	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[9] RENESAS SALVATOR-MS(1rank) board with H3 Ver.2.0 or later/SoC */
-	{
-	 0x0f,
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x3210,
-	   {0x27645310, 0x75346210, 0x53467210, 0x23674510},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x23764510, 0x43257610, 0x43752610, 0x37652401},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {-128, -128, -128, -128, -128, -128, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00452103,
-	   0x3210,
-	   {0x32764510, 0x43257610, 0x43752610, 0x26573401},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0xff},
-	   0x00520413,
-	   0x2301,
-	   {0x47652301, 0x75346210, 0x53467210, 0x32674501},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {30, 30, 30, 30, 30, 30, 30, 30,
-	    30, 30},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[10] RENESAS Kriek(2rank) board with M3-N/SoC */
-	{
-	 0x01,
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00345201,
-	   0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[11] RENESAS SALVATOR-X board with M3-N/SIP(8Gbit 2rank) */
-	{
-	 0x01,
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-#if (RCAR_DRAM_LPDDR4_MEMCONF == 2)
-	   {0x04, 0x04},
-#else
-	   {0x02, 0x02},
-#endif
-	   0x00342501,
-	   0x3201,
-	   {0x10672534, 0x43257106, 0x34527601, 0x71605243},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[12] RENESAS CONDOR board with V3H/SoC */
-	{
-	 0x01,
-	 0x1,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00501342,
-	   0x3201,
-	   {0x70562134, 0x34526071, 0x23147506, 0x12430567},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[13] RENESAS KRIEK board with PM3/SoC */
-	{
-	 0x05,
-	 0x00,
-	 0x2c0,
-	 -320,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00345201,
-	   0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0xff, 0xff},
-	   0,
-	   0,
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[14] SALVATOR-X board with H3 Ver.2.0 or later/SIP(16Gbit 1rank) */
-	{
-#if RCAR_DRAM_CHANNEL == 5
-	 0x05,
-#else
-	 0x0f,
-#endif
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x04, 0xff},
-	   0x00543210,
-	   0x2310,
-	   {0x70631425, 0x34527016, 0x43527610, 0x32104567},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#if ((RCAR_DRAM_CHANNEL == 5) && (RCAR_DRAM_SPLIT == 2))
-	{
-	   {0x04, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#else
-	{
-	   {0x04, 0xff},
-	   0x00105432,
-	   0x3210,
-	   {0x43256107, 0x07162354, 0x10234567, 0x01235467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-#endif
-	{
-	   {0x04, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x01327654, 0x02316457, 0x10234567, 0x01325467},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0xff},
-	   0x00543210,
-	   0x2301,
-	   {0x12034765, 0x23105467, 0x23017645, 0x32106745},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[15] RENESAS KRIEK board with H3N */
-	{
-	 0x05,
-	 0x01,
-	 0x300,
-	 0,
-	 0x300,
-	 0x0a0,
-	{
-	{
-	   {0x02, 0x02},
-	   0x00345201,
-	   0x3201,
-	   {0x01672543, 0x45367012, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x02, 0x02},
-	   0x00302154,
-	   0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0xff, 0xff},
-	   0,
-	   0,
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[16] RENESAS KRIEK-P2P board with M3-W/SoC */
-	{
-	 0x03,
-	 0x01,
-	 0x0320,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0x04},
-	    0x520314FFFF523041,
-	    0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	    WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0x04},
-	    0x314250FFFF312405,
-	    0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	    WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	 },
-/* boardcnf[17] RENESAS KRIEK-P2P board with M3-N/SoC */
-	{
-	 0x01,
-	 0x01,
-	 0x0300,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0x04},
-	    0x520314FFFF523041,
-	    0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	    WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	},
-/* boardcnf[18] RENESAS SALVATOR-X board with M3-W/SIP(16Gbit 2rank) */
-	{
-	 0x03,
-	 0x01,
-	 0x02c0,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0x04},
-	    0x00543210,
-	    0x3201,
-	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0x04},
-	    0x00543210,
-	    0x2310,
-	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	},
-/* boardcnf[19] RENESAS SALVATOR-X board with M3-W/SIP(16Gbit 1rank) */
-	{
-	 0x03,
-	 0x01,
-	 0x02c0,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0xff},
-	    0x00543210,
-	    0x3201,
-	   {0x70612543, 0x43251670, 0x45326170, 0x10672534},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0xff},
-	    0x00543210,
-	    0x2310,
-	   {0x01327654, 0x34526107, 0x35421670, 0x70615324},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	},
-/* boardcnf[20] RENESAS KRIEK 16Gbit/2rank/2ch board with M3-W/SoC */
-	{
-	 0x03,
-	 0x01,
-	 0x02c0,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0x04},
-	    0x00345201,
-	    0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	    WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0x04},
-	    0x00302154,
-	    0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	},
-/* boardcnf[21] RENESAS KRIEK 16Gbit/1rank/2ch board with M3-W/SoC */
-	{
-	 0x03,
-	 0x01,
-	 0x02c0,
-	 0,
-	 0x0300,
-	 0x00a0,
-	{
-	{
-	   {0x04, 0xff},
-	    0x00345201,
-	    0x3201,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	   },
-	{
-	   {0x04, 0xff},
-	    0x00302154,
-	    0x2310,
-	   {0x01672543, 0x45361207, 0x45632107, 0x60715234},
-	   {0x08, 0x08, 0x08, 0x08},
-	   WDQLVL_PAT,
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0},
-	   {0, 0, 0, 0},
-	   {0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0,
-	    0, 0, 0, 0, 0, 0, 0, 0}
-	}
-	}
-	}
-};
-
-void boardcnf_get_brd_clk(uint32_t brd, uint32_t *clk, uint32_t *div)
-{
-	uint32_t md;
-
-	if ((prr_product == PRR_PRODUCT_H3) && (prr_cut == PRR_PRODUCT_10)) {
-		*clk = 50;
-		*div = 3;
-	} else {
-		md = (mmio_read_32(RST_MODEMR) >> 13) & 0x3;
-		switch (md) {
-		case 0x0:
-			*clk = 50;
-			*div = 3;
-			break;
-		case 0x1:
-			*clk = 60;
-			*div = 3;
-			break;
-		case 0x2:
-			*clk = 75;
-			*div = 3;
-			break;
-		case 0x3:
-			*clk = 100;
-			*div = 3;
-			break;
-		}
-	}
-	(void)brd;
-}
-
-void boardcnf_get_ddr_mbps(uint32_t brd, uint32_t *mbps, uint32_t *div)
-{
-	uint32_t md;
-
-	if (prr_product == PRR_PRODUCT_V3H) {
-		md = (mmio_read_32(RST_MODEMR) >> 19) & 0x1;
-		md = (md | (md << 1)) & 0x3; /* 0 or 3 */
-	} else {
-		md = (mmio_read_32(RST_MODEMR) >> 17) & 0x5;
-		md = (md | (md >> 1)) & 0x3;
-	}
-	switch (md) {
-	case 0x0:
-		*mbps = 3200;
-		*div = 1;
-		break;
-	case 0x1:
-		*mbps = 2800;
-		*div = 1;
-		break;
-	case 0x2:
-		*mbps = 2400;
-		*div = 1;
-		break;
-	case 0x3:
-		*mbps = 1600;
-		*div = 1;
-		break;
-	}
-	(void)brd;
-}
-
-#define _def_REFPERIOD  1890
-
-#define M3_SAMPLE_TT_A84        0xB866CC10, 0x3B250421
-#define M3_SAMPLE_TT_A85        0xB866CC10, 0x3AA50421
-#define M3_SAMPLE_TT_A86        0xB866CC10, 0x3AA48421
-#define M3_SAMPLE_FF_B45        0xB866CC10, 0x3AB00C21
-#define M3_SAMPLE_FF_B49        0xB866CC10, 0x39B10C21
-#define M3_SAMPLE_FF_B56        0xB866CC10, 0x3AAF8C21
-#define M3_SAMPLE_SS_E24        0xB866CC10, 0x3BA39421
-#define M3_SAMPLE_SS_E28        0xB866CC10, 0x3C231421
-#define M3_SAMPLE_SS_E32        0xB866CC10, 0x3C241421
-
-static const uint32_t termcode_by_sample[20][3] = {
-	{M3_SAMPLE_TT_A84, 0x000158D5},
-	{M3_SAMPLE_TT_A85, 0x00015955},
-	{M3_SAMPLE_TT_A86, 0x00015955},
-	{M3_SAMPLE_FF_B45, 0x00015690},
-	{M3_SAMPLE_FF_B49, 0x00015753},
-	{M3_SAMPLE_FF_B56, 0x00015793},
-	{M3_SAMPLE_SS_E24, 0x00015996},
-	{M3_SAMPLE_SS_E28, 0x000159D7},
-	{M3_SAMPLE_SS_E32, 0x00015997},
-	{0xFFFFFFFF, 0xFFFFFFFF, 0x0001554F}
-};
-
-#ifdef BOARD_JUDGE_AUTO
-/*
- * SAMPLE board detect function
- */
-#define PFC_PMMR	0xE6060000U
-#define PFC_PUEN5	0xE6060414U
-#define PFC_PUEN6	0xE6060418U
-#define PFC_PUD5	0xE6060454U
-#define PFC_PUD6	0xE6060458U
-#define GPIO_INDT5	0xE605500CU
-#define GPIO_GPSR6	0xE6060118U
-
-#if (RCAR_GEN3_ULCB == 0)
-static void pfc_write_and_poll(uint32_t a, uint32_t v)
-{
-	mmio_write_32(PFC_PMMR, ~v);
-	v = ~mmio_read_32(PFC_PMMR);
-	mmio_write_32(a, v);
-	while (v != mmio_read_32(a))
-		;
-	dsb_sev();
-}
-#endif
-
-#ifndef RCAR_GEN3_ULCB
-#define RCAR_GEN3_ULCB		0
-#endif
-
-#if (RCAR_GEN3_ULCB == 0)	/* non Starter Kit */
-
-static uint32_t opencheck_SSI_WS6(void)
-{
-	uint32_t dataL, down, up;
-	uint32_t gpsr6_bak;
-	uint32_t puen5_bak;
-	uint32_t pud5_bak;
-
-	gpsr6_bak = mmio_read_32(GPIO_GPSR6);
-	puen5_bak = mmio_read_32(PFC_PUEN5);
-	pud5_bak = mmio_read_32(PFC_PUD5);
-	dsb_sev();
-
-	dataL = (gpsr6_bak & ~BIT(15));
-	pfc_write_and_poll(GPIO_GPSR6, dataL);
-
-	/* Pull-Up/Down Enable (PUEN5[22]=1) */
-	dataL = puen5_bak;
-	dataL |= (BIT(22));
-	pfc_write_and_poll(PFC_PUEN5, dataL);
-
-	/* Pull-Down-Enable (PUD5[22]=0, PUEN5[22]=1) */
-	dataL = pud5_bak;
-	dataL &= ~(BIT(22));
-	pfc_write_and_poll(PFC_PUD5, dataL);
-	/* GPSR6[15]=SSI_WS6 */
-	rcar_micro_delay(10);
-	down = (mmio_read_32(GPIO_INDT6) >> 15) & 0x1;
-	dsb_sev();
-
-	/* Pull-Up-Enable (PUD5[22]=1, PUEN5[22]=1) */
-	dataL = pud5_bak;
-	dataL |= (BIT(22));
-	pfc_write_and_poll(PFC_PUD5, dataL);
-
-	/* GPSR6[15]=SSI_WS6 */
-	rcar_micro_delay(10);
-	up = (mmio_read_32(GPIO_INDT6) >> 15) & 0x1;
-
-	dsb_sev();
-
-	pfc_write_and_poll(GPIO_GPSR6, gpsr6_bak);
-	pfc_write_and_poll(PFC_PUEN5, puen5_bak);
-	pfc_write_and_poll(PFC_PUD5, pud5_bak);
-
-	if (down == up) {
-		/* Same = Connect */
-		return 0;
-	}
-
-	/* Diff = Open */
-	return 1;
-}
-
-#endif
-
-static uint32_t _board_judge(void)
-{
-	uint32_t brd;
-#if (RCAR_GEN3_ULCB == 1)
-	/* Starter Kit */
-	if (prr_product == PRR_PRODUCT_H3) {
-		if (prr_cut <= PRR_PRODUCT_11) {
-			/* RENESAS Starter Kit(H3 Ver.1.x/SIP) board */
-			brd = 2;
-		} else {
-			/* RENESAS Starter Kit(H3 Ver.2.0 or later/SIP) board */
-#if (RCAR_DRAM_LPDDR4_MEMCONF == 0)
-			brd = 7;
-#else
-			brd = 8;
-#endif
-		}
-	} else if (prr_product == PRR_PRODUCT_M3) {
-		if (prr_cut >= PRR_PRODUCT_30) {
-			/* RENESAS Starter Kit (M3-W Ver.3.0/SIP) */
-			brd = 18;
-		} else {
-			/* RENESAS Starter Kit(M3-W/SIP 8Gbit 1rank) board */
-			brd = 3;
-		}
-	} else {
-		/* RENESAS Starter Kit(M3-N/SIP) board */
-		brd = 11;
-	}
-#else
-	uint32_t usb2_ovc_open;
-
-	usb2_ovc_open = opencheck_SSI_WS6();
-
-	/* RENESAS Eva-board */
-	brd = 99;
-	if (prr_product == PRR_PRODUCT_V3H) {
-		/* RENESAS Condor board */
-		brd = 12;
-	} else if (usb2_ovc_open) {
-		if (prr_product == PRR_PRODUCT_M3N) {
-			/* RENESAS Kriek board with M3-N */
-			brd = 10;
-		} else if (prr_product == PRR_PRODUCT_M3) {
-			/* RENESAS Kriek board with M3-W */
-			brd = 1;
-		} else if ((prr_product == PRR_PRODUCT_H3) &&
-			   (prr_cut <= PRR_PRODUCT_11)) {
-			/* RENESAS Kriek board with PM3 */
-			brd = 13;
-		} else if ((prr_product == PRR_PRODUCT_H3) &&
-			   (prr_cut > PRR_PRODUCT_20)) {
-			/* RENESAS Kriek board with H3N */
-			brd = 15;
-		}
-	} else {
-		if (prr_product == PRR_PRODUCT_H3) {
-			if (prr_cut <= PRR_PRODUCT_11) {
-				/* RENESAS SALVATOR-X (H3 Ver.1.x/SIP) */
-				brd = 2;
-			} else if (prr_cut < PRR_PRODUCT_30) {
-				/* RENESAS SALVATOR-X (H3 Ver.2.0/SIP) */
-				brd = 7;	//  8Gbit/1rank
-			} else {
-				/* RENESAS SALVATOR-X (H3 Ver.3.0/SIP) */
-#if (RCAR_DRAM_LPDDR4_MEMCONF == 0)
-				brd = 7;
-#else
-				brd = 8;
-#endif
-			}
-		} else if (prr_product == PRR_PRODUCT_M3N) {
-			/* RENESAS SALVATOR-X (M3-N/SIP) */
-			brd = 11;
-		} else if ((prr_product == PRR_PRODUCT_M3) &&
-			   (prr_cut <= PRR_PRODUCT_20)) {
-			/* RENESAS SALVATOR-X (M3-W/SIP) */
-			brd = 0;
-		} else if ((prr_product == PRR_PRODUCT_M3) &&
-			   (prr_cut < PRR_PRODUCT_30)) {
-			/* RENESAS SALVATOR-X (M3-W Ver.1.x/SIP) */
-			brd = 19;
-		} else if ((prr_product == PRR_PRODUCT_M3) &&
-			   (prr_cut >= PRR_PRODUCT_30)) {
-			/* RENESAS SALVATOR-X (M3-W ver.3.0/SIP) */
-			brd = 18;
-		}
-	}
-#endif
-
-	return brd;
-}
-#endif
diff --git a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_regdef.h b/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_regdef.h
deleted file mode 100644
index 56363eb..0000000
--- a/drivers/renesas/rcar/ddr/ddr_b/boot_init_dram_regdef.h
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation.
- * All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#define RCAR_DDR_VERSION	"rev.0.40"
-#define DRAM_CH_CNT		0x04
-#define SLICE_CNT		0x04
-#define CS_CNT			0x02
-
-/* order : CS0A, CS0B, CS1A, CS1B */
-#define CSAB_CNT		(CS_CNT * 2)
-
-/* order : CH0A, CH0B, CH1A, CH1B, CH2A, CH2B, CH3A, CH3B */
-#define CHAB_CNT		(DRAM_CH_CNT * 2)
-
-/* pll setting */
-#define CLK_DIV(a, diva, b, divb) (((a) * (divb)) / ((b) * (diva)))
-#define CLK_MUL(a, diva, b, divb) (((a) * (b)) / ((diva) * (divb)))
-
-/* for ddr deisity setting */
-#define DBMEMCONF_REG(d3, row, bank, col, dw)	\
-	(((d3) << 30) | ((row) << 24) | ((bank) << 16) | ((col) << 8) | (dw))
-
-#define DBMEMCONF_REGD(density)		\
-	(DBMEMCONF_REG((density) % 2, ((density) + 1) / \
-	2 + (29 - 3 - 10 - 2), 3, 10, 2))
-
-#define DBMEMCONF_VAL(ch, cs) (DBMEMCONF_REGD(DBMEMCONF_DENS(ch, cs)))
-
-/* refresh mode */
-#define DBSC_REFINTS		(0x0)
-
-/* system registers */
-#define CPG_FRQCRB		(CPG_BASE + 0x0004U)
-
-#define CPG_PLLECR		(CPG_BASE + 0x00D0U)
-#define CPG_MSTPSR5		(CPG_BASE + 0x003CU)
-#define CPG_SRCR4		(CPG_BASE + 0x00BCU)
-#define CPG_PLL3CR		(CPG_BASE + 0x00DCU)
-#define CPG_ZB3CKCR		(CPG_BASE + 0x0380U)
-#define CPG_FRQCRD		(CPG_BASE + 0x00E4U)
-#define CPG_SMSTPCR5		(CPG_BASE + 0x0144U)
-#define CPG_CPGWPR		(CPG_BASE + 0x0900U)
-#define CPG_SRSTCLR4		(CPG_BASE + 0x0950U)
-
-#define CPG_FRQCRB_KICK_BIT	BIT(31)
-#define CPG_PLLECR_PLL3E_BIT	BIT(3)
-#define CPG_PLLECR_PLL3ST_BIT	BIT(11)
-#define CPG_ZB3CKCR_ZB3ST_BIT	BIT(11)
-
-#define RST_BASE		(0xE6160000U)
-#define RST_MODEMR		(RST_BASE + 0x0060U)
-
-#define LIFEC_CHIPID(x)		(0xE6110040U + 0x04U * (x))
-
-/* DBSC registers */
-#include "../ddr_regs.h"
-
-#define DBSC_DBMONCONF4		0xE6793010U
-
-#define DBSC_PLL_LOCK(ch)	(0xE6794054U + 0x100U * (ch))
-#define DBSC_PLL_LOCK_0		0xE6794054U
-#define DBSC_PLL_LOCK_1		0xE6794154U
-#define DBSC_PLL_LOCK_2		0xE6794254U
-#define DBSC_PLL_LOCK_3		0xE6794354U
-
-/* STAT registers */
-#define MSTAT_SL_INIT		0xE67E8000U
-#define MSTAT_REF_ARS		0xE67E8004U
-#define MSTATQ_STATQC		0xE67E8008U
-#define MSTATQ_WTENABLE		0xE67E8030U
-#define MSTATQ_WTREFRESH	0xE67E8034U
-#define MSTATQ_WTSETTING0	0xE67E8038U
-#define MSTATQ_WTSETTING1	0xE67E803CU
-
-#define QOS_BASE1		(0xE67F0000U)
-#define QOSCTRL_RAS		(QOS_BASE1 + 0x0000U)
-#define QOSCTRL_FIXTH		(QOS_BASE1 + 0x0004U)
-#define QOSCTRL_RAEN		(QOS_BASE1 + 0x0018U)
-#define QOSCTRL_REGGD		(QOS_BASE1 + 0x0020U)
-#define QOSCTRL_DANN		(QOS_BASE1 + 0x0030U)
-#define QOSCTRL_DANT		(QOS_BASE1 + 0x0038U)
-#define QOSCTRL_EC		(QOS_BASE1 + 0x003CU)
-#define QOSCTRL_EMS		(QOS_BASE1 + 0x0040U)
-#define QOSCTRL_INSFC		(QOS_BASE1 + 0x0050U)
-#define QOSCTRL_BERR		(QOS_BASE1 + 0x0054U)
-#define QOSCTRL_RACNT0		(QOS_BASE1 + 0x0080U)
-#define QOSCTRL_STATGEN0	(QOS_BASE1 + 0x0088U)
-
-/* other module */
-#define THS1_THCTR		0xE6198020U
-#define THS1_TEMP		0xE6198028U
diff --git a/drivers/renesas/rcar/ddr/ddr_b/ddr_b.mk b/drivers/renesas/rcar/ddr/ddr_b/ddr_b.mk
deleted file mode 100644
index 2bcc292..0000000
--- a/drivers/renesas/rcar/ddr/ddr_b/ddr_b.mk
+++ /dev/null
@@ -1,7 +0,0 @@
-#
-# Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-BL2_SOURCES += drivers/renesas/rcar/ddr/ddr_b/boot_init_dram.c
diff --git a/drivers/renesas/rcar/delay/micro_delay.c b/drivers/renesas/rcar/delay/micro_delay.c
deleted file mode 100644
index aced589..0000000
--- a/drivers/renesas/rcar/delay/micro_delay.c
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (c) 2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <arch_helpers.h>
-#include "micro_delay.h"
-
-#define RCAR_CONV_MICROSEC		1000000U
-
-void
-#if IMAGE_BL31
-	__attribute__ ((section (".system_ram")))
-#endif
-	rcar_micro_delay(uint64_t micro_sec)
-{
-	uint64_t freq;
-	uint64_t base_count;
-	uint64_t get_count;
-	uint64_t wait_time = 0U;
-
-	freq = read_cntfrq_el0();
-	base_count = read_cntpct_el0();
-	while (micro_sec > wait_time) {
-		get_count = read_cntpct_el0();
-		wait_time = ((get_count - base_count) * RCAR_CONV_MICROSEC) / freq;
-	}
-}
diff --git a/drivers/renesas/rcar/dma/dma_driver.c b/drivers/renesas/rcar/dma/dma_driver.c
deleted file mode 100644
index e0be46e..0000000
--- a/drivers/renesas/rcar/dma/dma_driver.c
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stdint.h>
-#include <string.h>
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <lib/mmio.h>
-
-#include "rcar_def.h"
-#include "cpg_registers.h"
-#include "rcar_private.h"
-
-/* DMA CHANNEL setting (0/16/32) */
-#if RCAR_LSI == RCAR_V3M
-#define	DMA_CH		16
-#else
-#define	DMA_CH		0
-#endif
-
-#if (DMA_CH == 0)
-#define SYS_DMAC_BIT	((uint32_t)1U << 19U)
-#define DMA_BASE	(0xE6700000U)
-#elif (DMA_CH == 16)
-#define SYS_DMAC_BIT	((uint32_t)1U << 18U)
-#define DMA_BASE	(0xE7300000U)
-#elif (DMA_CH == 32)
-#define SYS_DMAC_BIT	((uint32_t)1U << 17U)
-#define DMA_BASE	(0xE7320000U)
-#else
-#define SYS_DMAC_BIT	((uint32_t)1U << 19U)
-#define DMA_BASE	(0xE6700000U)
-#endif
-
-/* DMA operation */
-#define DMA_DMAOR	(DMA_BASE + 0x0060U)
-/* DMA secure control */
-#define	DMA_DMASEC	(DMA_BASE + 0x0030U)
-/* DMA channel clear */
-#define DMA_DMACHCLR	(DMA_BASE + 0x0080U)
-/* DMA source address */
-#define DMA_DMASAR	(DMA_BASE + 0x8000U)
-/* DMA destination address */
-#define DMA_DMADAR	(DMA_BASE + 0x8004U)
-/* DMA transfer count */
-#define DMA_DMATCR	(DMA_BASE + 0x8008U)
-/* DMA channel control */
-#define DMA_DMACHCR	(DMA_BASE + 0x800CU)
-/* DMA fixed destination address */
-#define DMA_DMAFIXDAR	(DMA_BASE + 0x8014U)
-
-#define	DMA_USE_CHANNEL		(0x00000001U)
-#define	DMAOR_INITIAL		(0x0301U)
-#define	DMACHCLR_CH_ALL		(0x0000FFFFU)
-#define	DMAFIXDAR_32BIT_SHIFT	(32U)
-#define	DMAFIXDAR_DAR_MASK	(0x000000FFU)
-#define	DMADAR_BOUNDARY_ADDR	(0x100000000ULL)
-#define	DMATCR_CNT_SHIFT	(6U)
-#define	DMATCR_MAX		(0x00FFFFFFU)
-#define	DMACHCR_TRN_MODE	(0x00105409U)
-#define	DMACHCR_DE_BIT		(0x00000001U)
-#define	DMACHCR_TE_BIT		(0x00000002U)
-#define	DMACHCR_CHE_BIT		(0x80000000U)
-
-#define	DMA_SIZE_UNIT		FLASH_TRANS_SIZE_UNIT
-#define	DMA_FRACTION_MASK	(0xFFU)
-#define DMA_DST_LIMIT		(0x10000000000ULL)
-
-/* transfer length limit */
-#define DMA_LENGTH_LIMIT	((DMATCR_MAX * (1U << DMATCR_CNT_SHIFT)) \
-				& ~DMA_FRACTION_MASK)
-
-static void dma_enable(void)
-{
-	mstpcr_write(CPG_SMSTPCR2, CPG_MSTPSR2, SYS_DMAC_BIT);
-}
-
-static void dma_setup(void)
-{
-	mmio_write_16(DMA_DMAOR, 0);
-	mmio_write_32(DMA_DMACHCLR, DMACHCLR_CH_ALL);
-}
-
-static void dma_start(uintptr_t dst, uint32_t src, uint32_t len)
-{
-	mmio_write_16(DMA_DMAOR, DMAOR_INITIAL);
-	mmio_write_32(DMA_DMAFIXDAR, (dst >> DMAFIXDAR_32BIT_SHIFT) &
-		      DMAFIXDAR_DAR_MASK);
-	mmio_write_32(DMA_DMADAR, dst & UINT32_MAX);
-	mmio_write_32(DMA_DMASAR, src);
-	mmio_write_32(DMA_DMATCR, len >> DMATCR_CNT_SHIFT);
-	mmio_write_32(DMA_DMASEC, DMA_USE_CHANNEL);
-	mmio_write_32(DMA_DMACHCR, DMACHCR_TRN_MODE);
-}
-
-static void dma_end(void)
-{
-	while ((mmio_read_32(DMA_DMACHCR) & DMACHCR_TE_BIT) == 0) {
-		if ((mmio_read_32(DMA_DMACHCR) & DMACHCR_CHE_BIT) != 0U) {
-			ERROR("BL2: DMA - Channel Address Error\n");
-			panic();
-			break;
-		}
-	}
-	/* DMA transfer Disable */
-	mmio_clrbits_32(DMA_DMACHCR, DMACHCR_DE_BIT);
-	while ((mmio_read_32(DMA_DMACHCR) & DMACHCR_DE_BIT) != 0)
-		;
-
-	mmio_write_32(DMA_DMASEC, 0);
-	mmio_write_16(DMA_DMAOR, 0);
-	mmio_write_32(DMA_DMACHCLR, DMA_USE_CHANNEL);
-}
-
-void rcar_dma_exec(uintptr_t dst, uint32_t src, uint32_t len)
-{
-	uint32_t dma_len = len;
-
-	if (len & DMA_FRACTION_MASK)
-		dma_len = (len + DMA_SIZE_UNIT) & ~DMA_FRACTION_MASK;
-
-	if (!dma_len || dma_len > DMA_LENGTH_LIMIT) {
-		ERROR("BL2: DMA - size invalid, length (0x%x)\n", dma_len);
-		panic();
-	}
-
-	if (src & DMA_FRACTION_MASK) {
-		ERROR("BL2: DMA - source address invalid (0x%x), "
-			"length (0x%x)\n", src, dma_len);
-		panic();
-	}
-
-	if ((dst & UINT32_MAX) + dma_len > DMADAR_BOUNDARY_ADDR	||
-	    (dst + dma_len > DMA_DST_LIMIT)			||
-	    (dst & DMA_FRACTION_MASK)) {
-		ERROR("BL2: DMA - destination address invalid (0x%lx), "
-		      "length (0x%x)\n", dst, dma_len);
-		panic();
-	}
-
-	dma_start(dst, src, dma_len);
-	dma_end();
-}
-
-void rcar_dma_init(void)
-{
-	dma_enable();
-	dma_setup();
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_cmd.c b/drivers/renesas/rcar/emmc/emmc_cmd.c
deleted file mode 100644
index a2e25e3..0000000
--- a/drivers/renesas/rcar/emmc/emmc_cmd.c
+++ /dev/null
@@ -1,492 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_registers.h"
-#include "emmc_def.h"
-#include "micro_delay.h"
-
-static void emmc_little_to_big(uint8_t *p, uint32_t value)
-{
-	if (p == NULL)
-		return;
-
-	p[0] = (uint8_t) (value >> 24);
-	p[1] = (uint8_t) (value >> 16);
-	p[2] = (uint8_t) (value >> 8);
-	p[3] = (uint8_t) value;
-}
-
-static void emmc_softreset(void)
-{
-	int32_t loop = 10000;
-	int32_t retry = 1000;
-
-	/* flag clear */
-	mmc_drv_obj.during_cmd_processing = FALSE;
-	mmc_drv_obj.during_transfer = FALSE;
-	mmc_drv_obj.during_dma_transfer = FALSE;
-	mmc_drv_obj.state_machine_blocking = FALSE;
-	mmc_drv_obj.force_terminate = FALSE;
-	mmc_drv_obj.dma_error_flag = FALSE;
-
-	/* during operation ? */
-	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) == 0)
-		goto reset;
-
-	/* wait CMDSEQ = 0 */
-	while (loop > 0) {
-		if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) == 0)
-			break;	/* ready */
-
-		loop--;
-		if ((loop == 0) && (retry > 0)) {
-			rcar_micro_delay(1000U);	/* wait 1ms */
-			loop = 10000;
-			retry--;
-		}
-	}
-
-reset:
-	/* reset */
-	SETR_32(SOFT_RST, (GETR_32(SOFT_RST) & (~SOFT_RST_SDRST)));
-	SETR_32(SOFT_RST, (GETR_32(SOFT_RST) | SOFT_RST_SDRST));
-
-	/* initialize */
-	SETR_32(SD_INFO1, 0x00000000U);
-	SETR_32(SD_INFO2, SD_INFO2_CLEAR);
-	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
-	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
-
-}
-
-static void emmc_read_response(uint32_t *response)
-{
-	uint8_t *p;
-
-	if (response == NULL)
-		return;
-
-	/* read response */
-	if (mmc_drv_obj.response_length != EMMC_MAX_RESPONSE_LENGTH) {
-		*response = GETR_32(SD_RSP10);	/* [39:8] */
-		return;
-	}
-
-	/* CSD or CID */
-	p = (uint8_t *) (response);
-	emmc_little_to_big(p, ((GETR_32(SD_RSP76) << 8)
-			| (GETR_32(SD_RSP54) >> 24)));	/* [127:96]     */
-	emmc_little_to_big(p + 4, ((GETR_32(SD_RSP54) << 8)
-			| (GETR_32(SD_RSP32) >> 24)));	/* [95:64]      */
-	emmc_little_to_big(p + 8, ((GETR_32(SD_RSP32) << 8)
-			| (GETR_32(SD_RSP10) >> 24)));	/* [63:32]      */
-	emmc_little_to_big(p + 12, (GETR_32(SD_RSP10) << 8));
-}
-
-static EMMC_ERROR_CODE emmc_response_check(uint32_t *response,
-					   uint32_t error_mask)
-{
-
-	HAL_MEMCARD_RESPONSE_TYPE response_type =
-	    (HAL_MEMCARD_RESPONSE_TYPE) (mmc_drv_obj.cmd_info.
-					 cmd & HAL_MEMCARD_RESPONSE_TYPE_MASK);
-
-	if (response == NULL)
-		return EMMC_ERR_PARAM;
-
-	if (response_type == HAL_MEMCARD_RESPONSE_NONE)
-		return EMMC_SUCCESS;
-
-
-	if (response_type <= HAL_MEMCARD_RESPONSE_R1b) {
-		/* R1 or R1b */
-		mmc_drv_obj.current_state =
-		    (EMMC_R1_STATE) ((*response & EMMC_R1_STATE_MASK) >>
-				     EMMC_R1_STATE_SHIFT);
-		if ((*response & error_mask) != 0) {
-			if ((0x80 & *response) != 0) {
-				ERROR("BL2: emmc SWITCH_ERROR\n");
-			}
-			return EMMC_ERR_CARD_STATUS_BIT;
-		}
-		return EMMC_SUCCESS;;
-	}
-
-	if (response_type == HAL_MEMCARD_RESPONSE_R4) {
-		if ((*response & EMMC_R4_STATUS) != 0)
-			return EMMC_ERR_CARD_STATUS_BIT;
-	}
-
-	return EMMC_SUCCESS;
-}
-
-static void emmc_WaitCmd2Cmd_8Cycle(void)
-{
-	uint32_t dataL, wait = 0;
-
-	dataL = GETR_32(SD_CLK_CTRL);
-	dataL &= 0x000000FF;
-
-	switch (dataL) {
-	case 0xFF:
-	case 0x00:
-	case 0x01:
-	case 0x02:
-	case 0x04:
-	case 0x08:
-	case 0x10:
-	case 0x20:
-		wait = 10U;
-		break;
-	case 0x40:
-		wait = 20U;
-		break;
-	case 0x80:
-		wait = 30U;
-		break;
-	}
-
-	rcar_micro_delay(wait);
-}
-
-static void cmdErrSdInfo2Log(void)
-{
-	ERROR("BL2: emmc ERR SD_INFO2 = 0x%x\n", mmc_drv_obj.error_info.info2);
-}
-
-static void emmc_data_transfer_dma(void)
-{
-	mmc_drv_obj.during_dma_transfer = TRUE;
-	mmc_drv_obj.dma_error_flag = FALSE;
-
-	SETR_32(SD_INFO1_MASK, 0x00000000U);
-	SETR_32(SD_INFO2_MASK, (SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
-
-	/* DMAC setting */
-	if (mmc_drv_obj.cmd_info.dir == HAL_MEMCARD_WRITE) {
-		/* transfer complete interrupt enable */
-		SETR_32(DM_CM_INFO1_MASK,
-			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH0_ENABLE));
-		SETR_32(DM_CM_INFO2_MASK,
-			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH0_ENABLE));
-		/* BUFF --> FIFO */
-		SETR_32(DM_CM_DTRAN_MODE, (DM_CM_DTRAN_MODE_CH0 |
-					   DM_CM_DTRAN_MODE_BIT_WIDTH));
-	} else {
-		/* transfer complete interrupt enable */
-		SETR_32(DM_CM_INFO1_MASK,
-			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH1_ENABLE));
-		SETR_32(DM_CM_INFO2_MASK,
-			(DM_CM_INFO_MASK_CLEAR | DM_CM_INFO_CH1_ENABLE));
-		/* FIFO --> BUFF */
-		SETR_32(DM_CM_DTRAN_MODE, (DM_CM_DTRAN_MODE_CH1
-					   | DM_CM_DTRAN_MODE_BIT_WIDTH));
-	}
-	SETR_32(DM_DTRAN_ADDR, (((uintptr_t) mmc_drv_obj.buff_address_virtual &
-				 DM_DTRAN_ADDR_WRITE_MASK)));
-
-	SETR_32(DM_CM_DTRAN_CTRL, DM_CM_DTRAN_CTRL_START);
-}
-
-EMMC_ERROR_CODE emmc_exec_cmd(uint32_t error_mask, uint32_t *response)
-{
-	EMMC_ERROR_CODE rtn_code = EMMC_SUCCESS;
-	HAL_MEMCARD_RESPONSE_TYPE response_type;
-	HAL_MEMCARD_COMMAND_TYPE cmd_type;
-	EMMC_INT_STATE state;
-	uint32_t err_not_care_flag = FALSE;
-
-	/* parameter check */
-	if (response == NULL) {
-		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* state check */
-	if (mmc_drv_obj.clock_enable != TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	if (mmc_drv_obj.state_machine_blocking == TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD, EMMC_ERR);
-		return EMMC_ERR;
-	}
-
-	state = ESTATE_BEGIN;
-	response_type =
-	    (HAL_MEMCARD_RESPONSE_TYPE) (mmc_drv_obj.cmd_info.
-					 cmd & HAL_MEMCARD_RESPONSE_TYPE_MASK);
-	cmd_type =
-	    (HAL_MEMCARD_COMMAND_TYPE) (mmc_drv_obj.cmd_info.
-					cmd & HAL_MEMCARD_COMMAND_TYPE_MASK);
-
-	/* state machine */
-	while ((mmc_drv_obj.force_terminate != TRUE) && (state != ESTATE_END)) {
-		/* The interrupt factor flag is observed. */
-		emmc_interrupt();
-
-		/* wait interrupt */
-		if (mmc_drv_obj.state_machine_blocking == TRUE)
-			continue;
-
-		switch (state) {
-		case ESTATE_BEGIN:
-			/* Busy check */
-			if ((mmc_drv_obj.error_info.info2 & SD_INFO2_CBSY) != 0) {
-				emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD,
-						      EMMC_ERR_CARD_BUSY);
-				return EMMC_ERR_CARD_BUSY;
-			}
-
-			/* clear register */
-			SETR_32(SD_INFO1, 0x00000000U);
-			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
-			SETR_32(SD_INFO1_MASK, SD_INFO1_INFO0);
-			SETR_32(SD_INFO2_MASK,
-				(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
-
-			state = ESTATE_ISSUE_CMD;
-			/* through */
-
-		case ESTATE_ISSUE_CMD:
-			/* ARG */
-			SETR_32(SD_ARG, mmc_drv_obj.cmd_info.arg);
-			/* issue cmd */
-			SETR_32(SD_CMD, mmc_drv_obj.cmd_info.hw);
-			/* Set driver flag */
-			mmc_drv_obj.during_cmd_processing = TRUE;
-			mmc_drv_obj.state_machine_blocking = TRUE;
-
-			if (response_type == HAL_MEMCARD_RESPONSE_NONE) {
-				state = ESTATE_NON_RESP_CMD;
-			} else {
-				state = ESTATE_RCV_RESP;
-			}
-
-			break;
-
-		case ESTATE_NON_RESP_CMD:
-			/* interrupt disable */
-			SETR_32(SD_INFO1_MASK, 0x00000000U);
-			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
-
-			/* check interrupt */
-			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
-				/* error interrupt */
-				cmdErrSdInfo2Log();
-				rtn_code = EMMC_ERR_INFO2;
-				state = ESTATE_ERROR;
-			} else if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO0) ==
-				   0) {
-				/* not receive expected interrupt */
-				rtn_code = EMMC_ERR_RESPONSE;
-				state = ESTATE_ERROR;
-			} else {
-				emmc_WaitCmd2Cmd_8Cycle();
-				state = ESTATE_END;
-			}
-			break;
-
-		case ESTATE_RCV_RESP:
-			/* interrupt disable */
-			SETR_32(SD_INFO1_MASK, 0x00000000U);
-			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
-
-			/* check interrupt */
-			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
-				if ((mmc_drv_obj.get_partition_access_flag ==
-				     TRUE)
-				    && ((mmc_drv_obj.int_event2 & SD_INFO2_ERR6)
-					!= 0U)) {
-					err_not_care_flag = TRUE;
-					rtn_code = EMMC_ERR_CMD_TIMEOUT;
-				} else {
-					/* error interrupt */
-					cmdErrSdInfo2Log();
-					rtn_code = EMMC_ERR_INFO2;
-				}
-				state = ESTATE_ERROR;
-				break;
-			} else if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO0) ==
-				   0) {
-				/* not receive expected interrupt */
-				rtn_code = EMMC_ERR_RESPONSE;
-				state = ESTATE_ERROR;
-				break;
-			}
-
-			/* read response */
-			emmc_read_response(response);
-
-			/* check response */
-			rtn_code = emmc_response_check(response, error_mask);
-			if (rtn_code != EMMC_SUCCESS) {
-				state = ESTATE_ERROR;
-				break;
-			}
-
-			if (response_type == HAL_MEMCARD_RESPONSE_R1b) {
-				/* R1b */
-				SETR_32(SD_INFO2_MASK,
-					(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
-				state = ESTATE_RCV_RESPONSE_BUSY;
-			} else {
-				state = ESTATE_CHECK_RESPONSE_COMPLETE;
-			}
-			break;
-
-		case ESTATE_RCV_RESPONSE_BUSY:
-			/* check interrupt */
-			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
-				/* error interrupt */
-				cmdErrSdInfo2Log();
-				rtn_code = EMMC_ERR_INFO2;
-				state = ESTATE_ERROR;
-				break;
-			}
-			/* DAT0 not Busy */
-			if ((SD_INFO2_DAT0 & mmc_drv_obj.error_info.info2) != 0) {
-				state = ESTATE_CHECK_RESPONSE_COMPLETE;
-				break;
-			}
-			break;
-
-		case ESTATE_CHECK_RESPONSE_COMPLETE:
-			if (cmd_type >= HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE) {
-				state = ESTATE_DATA_TRANSFER;
-			} else {
-				emmc_WaitCmd2Cmd_8Cycle();
-				state = ESTATE_END;
-			}
-			break;
-
-		case ESTATE_DATA_TRANSFER:
-			/* ADTC command  */
-			mmc_drv_obj.during_transfer = TRUE;
-			mmc_drv_obj.state_machine_blocking = TRUE;
-
-			if (mmc_drv_obj.transfer_mode == HAL_MEMCARD_DMA) {
-				/* DMA */
-				emmc_data_transfer_dma();
-			} else {
-				/* PIO */
-				/* interrupt enable (FIFO read/write enable) */
-				if (mmc_drv_obj.cmd_info.dir ==
-				    HAL_MEMCARD_WRITE) {
-					SETR_32(SD_INFO2_MASK,
-						(SD_INFO2_BWE | SD_INFO2_ALL_ERR
-						 | SD_INFO2_CLEAR));
-				} else {
-					SETR_32(SD_INFO2_MASK,
-						(SD_INFO2_BRE | SD_INFO2_ALL_ERR
-						 | SD_INFO2_CLEAR));
-				}
-			}
-			state = ESTATE_DATA_TRANSFER_COMPLETE;
-			break;
-
-		case ESTATE_DATA_TRANSFER_COMPLETE:
-			/* check interrupt */
-			if ((mmc_drv_obj.int_event2 & SD_INFO2_ALL_ERR) != 0) {
-				/* error interrupt */
-				cmdErrSdInfo2Log();
-				rtn_code = EMMC_ERR_INFO2;
-				state = ESTATE_TRANSFER_ERROR;
-				break;
-			}
-
-			/* DMAC error ? */
-			if (mmc_drv_obj.dma_error_flag == TRUE) {
-				/* Error occurred in DMAC driver. */
-				rtn_code = EMMC_ERR_FROM_DMAC_TRANSFER;
-				state = ESTATE_TRANSFER_ERROR;
-			} else if (mmc_drv_obj.during_dma_transfer == TRUE) {
-				/* DMAC not finished. unknown error */
-				rtn_code = EMMC_ERR;
-				state = ESTATE_TRANSFER_ERROR;
-			} else {
-				SETR_32(SD_INFO1_MASK, SD_INFO1_INFO2);
-				SETR_32(SD_INFO2_MASK,
-					(SD_INFO2_ALL_ERR | SD_INFO2_CLEAR));
-
-				mmc_drv_obj.state_machine_blocking = TRUE;
-
-				state = ESTATE_ACCESS_END;
-			}
-			break;
-
-		case ESTATE_ACCESS_END:
-
-			/* clear flag */
-			if (HAL_MEMCARD_DMA == mmc_drv_obj.transfer_mode) {
-				SETR_32(CC_EXT_MODE, CC_EXT_MODE_CLEAR);	/* W (CC_EXT_MODE, H'0000_1010) SD_BUF DMA transfer disabled */
-				SETR_32(SD_STOP, 0x00000000U);
-				mmc_drv_obj.during_dma_transfer = FALSE;
-			}
-
-			SETR_32(SD_INFO1_MASK, 0x00000000U);
-			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
-			SETR_32(SD_INFO1, 0x00000000U);
-			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
-
-			if ((mmc_drv_obj.int_event1 & SD_INFO1_INFO2) != 0) {
-				emmc_WaitCmd2Cmd_8Cycle();
-				state = ESTATE_END;
-			} else {
-				state = ESTATE_ERROR;
-			}
-			break;
-
-		case ESTATE_TRANSFER_ERROR:
-			/* The error occurred in the Data transfer.  */
-			if (HAL_MEMCARD_DMA == mmc_drv_obj.transfer_mode) {
-				SETR_32(CC_EXT_MODE, CC_EXT_MODE_CLEAR);	/* W (CC_EXT_MODE, H'0000_1010) SD_BUF DMA transfer disabled */
-				SETR_32(SD_STOP, 0x00000000U);
-				mmc_drv_obj.during_dma_transfer = FALSE;
-			}
-			/* through */
-
-		case ESTATE_ERROR:
-			if (err_not_care_flag == TRUE) {
-				mmc_drv_obj.during_cmd_processing = FALSE;
-			} else {
-				emmc_softreset();
-				emmc_write_error_info(EMMC_FUNCNO_EXEC_CMD,
-						      rtn_code);
-			}
-			return rtn_code;
-
-		default:
-			state = ESTATE_END;
-			break;
-		}		/* switch (state) */
-	}			/*  while ( (mmc_drv_obj.force_terminate != TRUE) && (state != ESTATE_END) ) */
-
-	/* force terminate */
-	if (mmc_drv_obj.force_terminate == TRUE) {
-		/* timeout timer is expired. Or, PIO data transfer error. */
-		/* Timeout occurred in the DMA transfer. */
-		if (mmc_drv_obj.during_dma_transfer == TRUE) {
-			mmc_drv_obj.during_dma_transfer = FALSE;
-		}
-		ERROR("BL2: emmc exec_cmd:EMMC_ERR_FORCE_TERMINATE\n");
-		emmc_softreset();
-
-		return EMMC_ERR_FORCE_TERMINATE;	/* error information has already been written. */
-	}
-
-	/* success */
-	mmc_drv_obj.during_cmd_processing = FALSE;
-	mmc_drv_obj.during_transfer = FALSE;
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_config.h b/drivers/renesas/rcar/emmc/emmc_config.h
deleted file mode 100644
index 686ccb9..0000000
--- a/drivers/renesas/rcar/emmc/emmc_config.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/**
- * @file  emmc_config.h
- * @brief Configuration file
- *
- */
-
-#ifndef EMMC_CONFIG_H
-#define EMMC_CONFIG_H
-
-/* ************************ HEADER (INCLUDE) SECTION *********************** */
-
-/* ***************** MACROS, CONSTANTS, COMPILATION FLAGS ****************** */
-
-/** @brief MMC driver config
- */
-#define EMMC_RCA                1UL	/* RCA  */
-#define EMMC_RW_DATA_TIMEOUT    0x40UL	/* 314ms (freq = 400KHz, timeout Counter = 0x04(SDCLK * 2^17)  */
-#define EMMC_RETRY_COUNT        0	/* how many times to try after fail. Don't change. */
-#define EMMC_CMD_MAX            60UL	/* Don't change. */
-
-/** @brief etc
- */
-#define LOADIMAGE_FLAGS_DMA_ENABLE              0x00000001UL
-
-/* ********************** STRUCTURES, TYPE DEFINITIONS ********************* */
-
-/* ********************** DECLARATION OF EXTERNAL DATA ********************* */
-
-/* ************************** FUNCTION PROTOTYPES ************************** */
-
-/* ********************************* CODE ********************************** */
-
-#endif /* EMMC_CONFIG_H */
-/* ******************************** END ************************************ */
diff --git a/drivers/renesas/rcar/emmc/emmc_hal.h b/drivers/renesas/rcar/emmc/emmc_hal.h
deleted file mode 100644
index f0b7e9d..0000000
--- a/drivers/renesas/rcar/emmc/emmc_hal.h
+++ /dev/null
@@ -1,318 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/**
- * @file  emmc_hal.h
- * @brief emmc boot driver is expecting this header file
- *
- */
-
-#ifndef EMMC_HAL_H
-#define EMMC_HAL_H
-/* ************************ HEADER (INCLUDE) SECTION *********************** */
-#include <stdint.h>
-/* ***************** MACROS, CONSTANTS, COMPILATION FLAGS ****************** */
-
-/** @brief memory card error/status types
- */
-#define HAL_MEMCARD_OUT_OF_RANGE            0x80000000L
-#define HAL_MEMCARD_ADDRESS_ERROR           0x40000000L
-#define HAL_MEMCARD_BLOCK_LEN_ERROR         0x20000000L
-#define HAL_MEMCARD_ERASE_SEQ_ERROR         0x10000000L
-#define HAL_MEMCARD_ERASE_PARAM             0x08000000L
-#define HAL_MEMCARD_WP_VIOLATION            0x04000000L
-#define HAL_MEMCARD_CARD_IS_LOCKED          0x02000000L
-#define HAL_MEMCARD_LOCK_UNLOCK_FAILED      0x01000000L
-#define HAL_MEMCARD_COM_CRC_ERROR           0x00800000L
-#define HAL_MEMCARD_ILEGAL_COMMAND          0x00400000L
-#define HAL_MEMCARD_CARD_ECC_FAILED         0x00200000L
-#define HAL_MEMCARD_CC_ERROR                0x00100000L
-#define HAL_MEMCARD_ERROR                   0x00080000L
-#define HAL_MEMCARD_UNDERRUN                0x00040000L
-#define HAL_MEMCARD_OVERRUN                 0x00020000L
-#define HAL_MEMCARD_CIDCSD_OVERWRITE        0x00010000L
-#define HAL_MEMCARD_WP_ERASE_SKIP           0x00008000L
-#define HAL_MEMCARD_CARD_ECC_DISABLED       0x00004000L
-#define HAL_MEMCARD_ERASE_RESET             0x00002000L
-#define HAL_MEMCARD_CARD_STATE              0x00001E00L
-#define HAL_MEMCARD_CARD_READY_FOR_DATA     0x00000100L
-#define HAL_MEMCARD_APP_CMD                 0x00000020L
-#define HAL_MEMCARD_SWITCH_ERROR            0x00000080L
-#define HAL_MEMCARD_AKE_SEQ_ERROR           0x00000008L
-#define HAL_MEMCARD_NO_ERRORS               0x00000000L
-
-/** @brief Memory card response types
- */
-#define HAL_MEMCARD_COMMAND_INDEX_MASK      0x0003f
-
-/* ********************** STRUCTURES, TYPE DEFINITIONS ********************* */
-
-/** @brief Type of the return value.
- */
-typedef enum {
-	HAL_MEMCARD_FAIL = 0U,
-	HAL_MEMCARD_OK = 1U,
-	HAL_MEMCARD_DMA_ALLOC_FAIL = 2U,     /**< DMA channel allocation failed */
-	HAL_MEMCARD_DMA_TRANSFER_FAIL = 3U,  /**< DMA transfer failed */
-	HAL_MEMCARD_CARD_STATUS_ERROR = 4U,  /**< A non-masked error bit was set in the card status */
-	HAL_MEMCARD_CMD_TIMEOUT = 5U,	     /**< Command timeout occurred */
-	HAL_MEMCARD_DATA_TIMEOUT = 6U,	     /**< Data timeout occurred */
-	HAL_MEMCARD_CMD_CRC_ERROR = 7U,	     /**< Command CRC error occurred */
-	HAL_MEMCARD_DATA_CRC_ERROR = 8U	     /**< Data CRC error occurred */
-} HAL_MEMCARD_RETURN;
-
-/** @brief memory access operation
- */
-typedef enum {
-	HAL_MEMCARD_READ = 0U,	 /**< read */
-	HAL_MEMCARD_WRITE = 1U	 /**< write */
-} HAL_MEMCARD_OPERATION;
-
-/** @brief Type of data width on memorycard bus
- */
-typedef enum {
-	HAL_MEMCARD_DATA_WIDTH_1_BIT = 0U,
-	HAL_MEMCARD_DATA_WIDTH_4_BIT = 1U,
-	HAL_MEMCARD_DATA_WIDTH_8_BIT = 2U
-} HAL_MEMCARD_DATA_WIDTH; /**< data (bus) width types */
-
-/** @brief Presence of the memory card
- */
-typedef enum {
-	HAL_MEMCARD_CARD_IS_IN = 0U,
-	HAL_MEMCARD_CARD_IS_OUT = 1U
-} HAL_MEMCARD_PRESENCE_STATUS;	/* presence status of the memory card */
-
-/** @brief mode of data transfer
- */
-typedef enum {
-	HAL_MEMCARD_DMA = 0U,
-	HAL_MEMCARD_NOT_DMA = 1U
-} HAL_MEMCARD_DATA_TRANSFER_MODE;
-
-/** @brief Memory card response types.
- */
-typedef enum hal_memcard_response_type {
-	HAL_MEMCARD_RESPONSE_NONE = 0x00000U,
-	HAL_MEMCARD_RESPONSE_R1 = 0x00100U,
-	HAL_MEMCARD_RESPONSE_R1b = 0x00200U,
-	HAL_MEMCARD_RESPONSE_R2 = 0x00300U,
-	HAL_MEMCARD_RESPONSE_R3 = 0x00400U,
-	HAL_MEMCARD_RESPONSE_R4 = 0x00500U,
-	HAL_MEMCARD_RESPONSE_R5 = 0x00600U,
-	HAL_MEMCARD_RESPONSE_R6 = 0x00700U,
-	HAL_MEMCARD_RESPONSE_R7 = 0x00800U,
-	HAL_MEMCARD_RESPONSE_TYPE_MASK = 0x00f00U
-} HAL_MEMCARD_RESPONSE_TYPE;
-
-/** @brief Memory card command types.
- */
-typedef enum hal_memcard_command_type {
-	HAL_MEMCARD_COMMAND_TYPE_BC = 0x00000U,
-	HAL_MEMCARD_COMMAND_TYPE_BCR = 0x01000U,
-	HAL_MEMCARD_COMMAND_TYPE_AC = 0x02000U,
-	HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE = 0x03000U,
-	HAL_MEMCARD_COMMAND_TYPE_ADTC_READ = 0x04000U,
-	HAL_MEMCARD_COMMAND_TYPE_MASK = 0x07000U
-} HAL_MEMCARD_COMMAND_TYPE;
-
-/** @brief Type of memory card
- */
-typedef enum hal_memcard_command_card_type {
-	HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON = 0x00000U,
-	HAL_MEMCARD_COMMAND_CARD_TYPE_MMC = 0x08000U,
-	HAL_MEMCARD_COMMAND_CARD_TYPE_SD = 0x10000U,
-	HAL_MEMCARD_COMMAND_CARD_TYPE_MASK = 0x18000U
-} HAL_MEMCARD_COMMAND_CARD_TYPE;
-
-/** @brief Memory card application command.
- */
-typedef enum hal_memcard_command_app_norm {
-	HAL_MEMCARD_COMMAND_NORMAL = 0x00000U,
-	HAL_MEMCARD_COMMAND_APP = 0x20000U,
-	HAL_MEMCARD_COMMAND_APP_NORM_MASK = 0x20000U
-} HAL_MEMCARD_COMMAND_APP_NORM;
-
-/** @brief Memory card command codes.
- */
-typedef enum {
-/* class 0 and class 1 */
-	CMD0_GO_IDLE_STATE = 0 | HAL_MEMCARD_RESPONSE_NONE | HAL_MEMCARD_COMMAND_TYPE_BC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD0 */
-	CMD1_SEND_OP_COND = 1 | HAL_MEMCARD_RESPONSE_R3 | HAL_MEMCARD_COMMAND_TYPE_BCR | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD1 */
-	CMD2_ALL_SEND_CID_MMC = 2 | HAL_MEMCARD_RESPONSE_R2 | HAL_MEMCARD_COMMAND_TYPE_BCR | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD2 */
-	CMD2_ALL_SEND_CID_SD =
-	    2 | HAL_MEMCARD_RESPONSE_R2 | HAL_MEMCARD_COMMAND_TYPE_BCR |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,
-	CMD3_SET_RELATIVE_ADDR = 3 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD3 */
-	CMD3_SEND_RELATIVE_ADDR =
-	    3 | HAL_MEMCARD_RESPONSE_R6 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,
-	CMD4_SET_DSR = 4 | HAL_MEMCARD_RESPONSE_NONE | HAL_MEMCARD_COMMAND_TYPE_BC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD4 */
-	CMD5_SLEEP_AWAKE = 5 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD5 */
-	CMD6_SWITCH = 6 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD6 */
-	CMD6_SWITCH_FUNC =
-	    6 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,
-	ACMD6_SET_BUS_WIDTH =
-	    6 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-	CMD7_SELECT_CARD = 7 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD7 */
-	CMD7_SELECT_CARD_PROG = 7 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD7(from Disconnected State to Programming State) */
-	CMD7_DESELECT_CARD =
-	    7 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,
-	CMD8_SEND_EXT_CSD = 8 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD8 */
-	CMD8_SEND_IF_COND =
-	    8 | HAL_MEMCARD_RESPONSE_R7 | HAL_MEMCARD_COMMAND_TYPE_BCR |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,
-	CMD9_SEND_CSD = 9 | HAL_MEMCARD_RESPONSE_R2 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD9 */
-	CMD10_SEND_CID = 10 | HAL_MEMCARD_RESPONSE_R2 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD10 */
-	CMD11_READ_DAT_UNTIL_STOP = 11 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD11 */
-	CMD12_STOP_TRANSMISSION = 12 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD12 */
-	CMD12_STOP_TRANSMISSION_WRITE = 12 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD12(R1b : write case) */
-	CMD13_SEND_STATUS = 13 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD13 */
-	ACMD13_SD_STATUS =
-	    13 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-	CMD14_BUSTEST_R = 14 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD14 */
-	CMD15_GO_INACTIVE_STATE = 15 | HAL_MEMCARD_RESPONSE_NONE | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD15 */
-
-/* class 2 */
-	CMD16_SET_BLOCKLEN = 16 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD16 */
-	CMD17_READ_SINGLE_BLOCK = 17 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD17 */
-	CMD18_READ_MULTIPLE_BLOCK = 18 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD18 */
-	CMD19_BUS_TEST_W = 19 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD19 */
-
-/* class 3 */
-	CMD20_WRITE_DAT_UNTIL_STOP = 20 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD20 */
-	CMD21 = 21,		/* CMD21 */
-	CMD22 = 22,		/* CMD22 */
-	ACMD22_SEND_NUM_WR_BLOCKS =
-	    22 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-
-/* class 4 */
-	CMD23_SET_BLOCK_COUNT = 23 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD23 */
-	ACMD23_SET_WR_BLK_ERASE_COUNT =
-	    23 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-	CMD24_WRITE_BLOCK = 24 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD24 */
-	CMD25_WRITE_MULTIPLE_BLOCK = 25 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD25 */
-	CMD26_PROGRAM_CID = 26 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD26 */
-	CMD27_PROGRAM_CSD = 27 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD27 */
-
-/* class 6 */
-	CMD28_SET_WRITE_PROT = 28 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD28 */
-	CMD29_CLR_WRITE_PROT = 29 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD29 */
-	CMD30_SEND_WRITE_PROT = 30 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD30 */
-	CMD30_SEND_WRITE_PROT_TYPE = 31 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD31 */
-
-/* class 5 */
-	CMD32_ERASE_WR_BLK_START = 32 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD32 */
-	CMD33_ERASE_WR_BLK_END = 33 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD33 */
-	CMD34 = 34,		/* CMD34 */
-	CMD35_ERASE_GROUP_START = 35 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD35 */
-	CMD36_ERASE_GROUP_END = 36 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD36 */
-	CMD37 = 37,		/* CMD37 */
-	CMD38_ERASE = 38 | HAL_MEMCARD_RESPONSE_R1b | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD38 */
-
-/* class 9 */
-	CMD39_FASTIO = 39 | HAL_MEMCARD_RESPONSE_R4 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD39 */
-	CMD40_GO_IRQSTATE = 40 | HAL_MEMCARD_RESPONSE_R5 | HAL_MEMCARD_COMMAND_TYPE_BCR | HAL_MEMCARD_COMMAND_CARD_TYPE_MMC | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD40 */
-	CMD41 = 41,		/* CMD41 */
-	ACMD41_SD_SEND_OP_COND =
-	    41 | HAL_MEMCARD_RESPONSE_R3 | HAL_MEMCARD_COMMAND_TYPE_BCR |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-
-/* class 7 */
-	CMD42_LOCK_UNLOCK = 42 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD42 */
-	ACMD42_SET_CLR_CARD_DETECT =
-	    42 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-	CMD43 = 43,		/* CMD43 */
-	CMD44 = 44,		/* CMD44 */
-	CMD45 = 45,		/* CMD45 */
-	CMD46 = 46,		/* CMD46 */
-	CMD47 = 47,		/* CMD47 */
-	CMD48 = 48,		/* CMD48 */
-	CMD49 = 49,		/* CMD49 */
-	CMD50 = 50,		/* CMD50 */
-	CMD51 = 51,		/* CMD51 */
-	ACMD51_SEND_SCR =
-	    51 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_READ |
-	    HAL_MEMCARD_COMMAND_CARD_TYPE_SD | HAL_MEMCARD_COMMAND_APP,
-	CMD52 = 52,		/* CMD52 */
-	CMD53 = 53,		/* CMD53 */
-	CMD54 = 54,		/* CMD54 */
-
-/* class 8 */
-	CMD55_APP_CMD = 55 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_AC | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD55 */
-	CMD56_GEN_CMD = 56 | HAL_MEMCARD_RESPONSE_R1 | HAL_MEMCARD_COMMAND_TYPE_ADTC_WRITE | HAL_MEMCARD_COMMAND_CARD_TYPE_COMMON | HAL_MEMCARD_COMMAND_NORMAL,	/* CMD56 */
-	CMD57 = 57,		/* CMD57 */
-	CMD58 = 58,		/* CMD58 */
-	CMD59 = 59,		/* CMD59 */
-	CMD60 = 60,		/* CMD60 */
-	CMD61 = 61,		/* CMD61 */
-	CMD62 = 62,		/* CMD62 */
-	CMD63 = 63		/* CMD63 */
-} HAL_MEMCARD_COMMAND;
-
-/** @brief Configuration structure from HAL layer.
- *
- * If some field is not available it should be filled with 0xFF.
- * The API version is 32-bit unsigned integer telling the version of the API. The integer is divided to four sections which each can be treated as a 8-bit unsigned number:
- * Bits 31-24 make the most significant part of the version number. This number starts from 1 i.e. the second version of the API will be 0x02xxxxxx. This number changes only, if the API itself changes so much that it is not compatible anymore with older releases.
- * Bits 23-16 API minor version number. For example API version 2.1 would be 0x0201xxxx.
- * Bits 15-8 are the number of the year when release is done. The 0 is year 2000, 1 is year 2001 and so on
- * Bits 7- are the week number when release is done. First full week of the year is 1
- *
- * @note Example: let's assume that release 2.1 is done on week 10 year 2008 the version will get the value 0x0201080A
- */
-typedef struct {
-    /**
-    * Version of the chipset API implementation
-    *
-    * bits [31:24] API specification major version number.<br>
-    * bits [23:16] API specification minor version number.<br>
-    * bits [15:8] API implemention year. (2000 = 0, 2001 = 1, ...)<br>
-    * bits [7:0] API implemention week.<br>
-    * Example: API specification version 4.0, implementation w46 2008 => 0x0400082E
-    */
-	uint32_t api_version;
-
-    /** maximum block count which can be transferred at once */
-	uint32_t max_block_count;
-
-    /** maximum clock frequence in Hz supported by HW */
-	uint32_t max_clock_freq;
-
-    /** maximum data bus width supported by HW */
-	uint16_t max_data_width;
-
-    /** Is high-speed mode supported by HW (yes=1, no=0) */
-	uint8_t hs_mode_supported;
-
-    /** Is memory card removable (yes=1, no=0) */
-	uint8_t card_removable;
-
-} HAL_MEMCARD_HW_CONF;
-
-/** @brief Configuration structure to HAL layer.
- */
-typedef struct {
-    /** how many times to try after fail, for instance sending command */
-	uint32_t retries_after_fail;
-} HAL_MEMCARD_INIT_CONF;
-
-/* ********************** DECLARATION OF EXTERNAL DATA ********************* */
-
-/* ************************** FUNCTION PROTOTYPES ************************** */
-
-/* ********************************* CODE ********************************** */
-
-#endif /* EMMC_HAL_H */
-
-/* ******************************** END ************************************ */
diff --git a/drivers/renesas/rcar/emmc/emmc_init.c b/drivers/renesas/rcar/emmc/emmc_init.c
deleted file mode 100644
index b27e165..0000000
--- a/drivers/renesas/rcar/emmc/emmc_init.c
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stddef.h>
-
-#include <lib/mmio.h>
-
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_registers.h"
-#include "emmc_def.h"
-#include "rcar_private.h"
-
-st_mmc_base mmc_drv_obj;
-
-EMMC_ERROR_CODE rcar_emmc_memcard_power(uint8_t mode)
-{
-
-	if (mode == TRUE) {
-		/* power on (Vcc&Vccq is always power on) */
-		mmc_drv_obj.card_power_enable = TRUE;
-	} else {
-		/* power off (Vcc&Vccq is always power on) */
-		mmc_drv_obj.card_power_enable = FALSE;
-		mmc_drv_obj.mount = FALSE;
-		mmc_drv_obj.selected = FALSE;
-	}
-
-	return EMMC_SUCCESS;
-}
-static __inline void emmc_set_retry_count(uint32_t retry)
-{
-	mmc_drv_obj.retries_after_fail = retry;
-}
-
-static __inline void emmc_set_data_timeout(uint32_t data_timeout)
-{
-	mmc_drv_obj.data_timeout = data_timeout;
-}
-
-static void emmc_memset(uint8_t *buff, uint8_t data, uint32_t cnt)
-{
-	if (buff == NULL) {
-		return;
-	}
-
-	while (cnt > 0) {
-		*buff++ = data;
-		cnt--;
-	}
-}
-
-static void emmc_driver_config(void)
-{
-	emmc_set_retry_count(EMMC_RETRY_COUNT);
-	emmc_set_data_timeout(EMMC_RW_DATA_TIMEOUT);
-}
-
-static void emmc_drv_init(void)
-{
-	emmc_memset((uint8_t *) (&mmc_drv_obj), 0, sizeof(st_mmc_base));
-	mmc_drv_obj.card_present = HAL_MEMCARD_CARD_IS_IN;
-	mmc_drv_obj.data_timeout = EMMC_RW_DATA_TIMEOUT;
-	mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
-}
-
-static EMMC_ERROR_CODE emmc_dev_finalize(void)
-{
-	EMMC_ERROR_CODE result;
-	uint32_t dataL;
-
-	/* MMC power off
-	 * the power supply of eMMC device is always turning on.
-	 * RST_n : Hi --> Low level.
-	 */
-	result = rcar_emmc_memcard_power(FALSE);
-
-	/* host controller reset */
-	SETR_32(SD_INFO1, 0x00000000U);		/* all interrupt clear */
-	SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* all interrupt clear */
-	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
-	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
-	SETR_32(SD_CLK_CTRL, 0x00000000U);	/* MMC clock stop */
-
-	dataL = mmio_read_32(CPG_SMSTPCR3);
-	if ((dataL & CPG_MSTP_MMC) == 0U) {
-		dataL |= (CPG_MSTP_MMC);
-		mmio_write_32(CPG_CPGWPR, (~dataL));
-		mmio_write_32(CPG_SMSTPCR3, dataL);
-	}
-
-	return result;
-}
-
-static EMMC_ERROR_CODE emmc_dev_init(void)
-{
-	/* Enable clock supply to eMMC. */
-	mstpcr_write(CPG_SMSTPCR3, CPG_MSTPSR3, CPG_MSTP_MMC);
-
-	/* Set SD clock */
-	mmio_write_32(CPG_CPGWPR, ~((uint32_t) (BIT9 | BIT0)));	/* SD phy 200MHz */
-
-	/* Stop SDnH clock & SDn=200MHz */
-	mmio_write_32(CPG_SDxCKCR, (BIT9 | BIT0));
-
-	/* MMCIF initialize */
-	SETR_32(SD_INFO1, 0x00000000U);		/* all interrupt clear */
-	SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* all interrupt clear */
-	SETR_32(SD_INFO1_MASK, 0x00000000U);	/* all interrupt disable */
-	SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* all interrupt disable */
-
-	SETR_32(HOST_MODE, 0x00000000U);	/* SD_BUF access width = 64-bit */
-	SETR_32(SD_OPTION, 0x0000C0EEU);	/* Bus width = 1bit, timeout=MAX */
-	SETR_32(SD_CLK_CTRL, 0x00000000U);	/* Automatic Control=Disable, Clock Output=Disable */
-
-	return EMMC_SUCCESS;
-}
-
-static EMMC_ERROR_CODE emmc_reset_controller(void)
-{
-	EMMC_ERROR_CODE retult;
-
-	/* initialize mmc driver */
-	emmc_drv_init();
-
-	/* initialize H/W */
-	retult = emmc_dev_init();
-	if (EMMC_SUCCESS != retult) {
-		return retult;
-	}
-
-	mmc_drv_obj.initialize = TRUE;
-
-	return retult;
-
-}
-
-EMMC_ERROR_CODE emmc_terminate(void)
-{
-	EMMC_ERROR_CODE result;
-
-	result = emmc_dev_finalize();
-
-	emmc_memset((uint8_t *) (&mmc_drv_obj), 0, sizeof(st_mmc_base));
-
-	return result;
-}
-
-EMMC_ERROR_CODE rcar_emmc_init(void)
-{
-	EMMC_ERROR_CODE retult;
-
-	retult = emmc_reset_controller();
-	if (EMMC_SUCCESS != retult) {
-		return retult;
-	}
-
-	emmc_driver_config();
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_interrupt.c b/drivers/renesas/rcar/emmc/emmc_interrupt.c
deleted file mode 100644
index 2557280..0000000
--- a/drivers/renesas/rcar/emmc/emmc_interrupt.c
+++ /dev/null
@@ -1,217 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights
- * reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stddef.h>
-
-#include <lib/mmio.h>
-
-#include "emmc_config.h"
-#include "emmc_def.h"
-#include "emmc_hal.h"
-#include "emmc_registers.h"
-#include "emmc_std.h"
-#include "rcar_def.h"
-
-static EMMC_ERROR_CODE emmc_trans_sector(uint32_t *buff_address_virtual);
-
-uint32_t emmc_interrupt(void)
-{
-	EMMC_ERROR_CODE result;
-	uint32_t prr_data;
-	uint32_t cut_ver;
-	uint32_t end_bit;
-
-	prr_data = mmio_read_32((uintptr_t) RCAR_PRR);
-	cut_ver = prr_data & PRR_CUT_MASK;
-	if ((prr_data & PRR_PRODUCT_MASK) == PRR_PRODUCT_H3) {
-		if (cut_ver == PRR_PRODUCT_10) {
-			end_bit = BIT17;
-		} else if (cut_ver == PRR_PRODUCT_11) {
-			end_bit = BIT17;
-		} else {
-			end_bit = BIT20;
-		}
-	} else if ((prr_data & PRR_PRODUCT_MASK) == PRR_PRODUCT_M3) {
-		if (cut_ver == PRR_PRODUCT_10) {
-			end_bit = BIT17;
-		} else {
-			end_bit = BIT20;
-		}
-	} else {
-		end_bit = BIT20;
-	}
-
-	/* SD_INFO */
-	mmc_drv_obj.error_info.info1 = GETR_32(SD_INFO1);
-	mmc_drv_obj.error_info.info2 = GETR_32(SD_INFO2);
-
-	/* SD_INFO EVENT */
-	mmc_drv_obj.int_event1 =
-	    mmc_drv_obj.error_info.info1 & GETR_32(SD_INFO1_MASK);
-	mmc_drv_obj.int_event2 =
-	    mmc_drv_obj.error_info.info2 & GETR_32(SD_INFO2_MASK);
-
-	/* ERR_STS */
-	mmc_drv_obj.error_info.status1 = GETR_32(SD_ERR_STS1);
-	mmc_drv_obj.error_info.status2 = GETR_32(SD_ERR_STS2);
-
-	/* DM_CM_INFO */
-	mmc_drv_obj.error_info.dm_info1 = GETR_32(DM_CM_INFO1);
-	mmc_drv_obj.error_info.dm_info2 = GETR_32(DM_CM_INFO2);
-
-	/* DM_CM_INFO EVENT */
-	mmc_drv_obj.dm_event1 =
-	    mmc_drv_obj.error_info.dm_info1 & GETR_32(DM_CM_INFO1_MASK);
-	mmc_drv_obj.dm_event2 =
-	    mmc_drv_obj.error_info.dm_info2 & GETR_32(DM_CM_INFO2_MASK);
-
-	/* ERR SD_INFO2 */
-	if ((SD_INFO2_ALL_ERR & mmc_drv_obj.int_event2) != 0) {
-		SETR_32(SD_INFO1_MASK, 0x00000000U);	/* interrupt disable */
-		SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);	/* interrupt disable */
-		SETR_32(SD_INFO1, 0x00000000U);	/* interrupt clear */
-		SETR_32(SD_INFO2, SD_INFO2_CLEAR);	/* interrupt clear */
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	}
-
-	/* PIO Transfer */
-	/* BWE/BRE */
-	else if (((SD_INFO2_BWE | SD_INFO2_BRE) & mmc_drv_obj.int_event2)) {
-		/* BWE */
-		if (SD_INFO2_BWE & mmc_drv_obj.int_event2) {
-			SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BWE));
-		}
-		/* BRE */
-		else {
-			SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BRE));
-		}
-
-		result = emmc_trans_sector(mmc_drv_obj.buff_address_virtual);
-		mmc_drv_obj.buff_address_virtual += EMMC_BLOCK_LENGTH;
-		mmc_drv_obj.remain_size -= EMMC_BLOCK_LENGTH;
-
-		if (result != EMMC_SUCCESS) {
-			/* data transfer error */
-			emmc_write_error_info(EMMC_FUNCNO_NONE, result);
-
-			/* Panic */
-			SETR_32(SD_INFO1_MASK, 0x00000000U);
-			SETR_32(SD_INFO2_MASK, SD_INFO2_CLEAR);
-			SETR_32(SD_INFO1, 0x00000000U);
-			/* interrupt clear */
-			SETR_32(SD_INFO2, SD_INFO2_CLEAR);
-			mmc_drv_obj.force_terminate = TRUE;
-		} else {
-			mmc_drv_obj.during_transfer = FALSE;
-		}
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	}
-
-	/* DMA_TRANSFER */
-	/* DM_CM_INFO1: DMA-ch0 transfer complete or error occurred */
-	else if ((BIT16 & mmc_drv_obj.dm_event1) != 0) {
-		SETR_32(DM_CM_INFO1, 0x00000000U);
-		SETR_32(DM_CM_INFO2, 0x00000000U);
-		/* interrupt clear */
-		SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BWE));
-		/* DM_CM_INFO2:  DMA-ch0 error occured */
-		if ((BIT16 & mmc_drv_obj.dm_event2) != 0) {
-			mmc_drv_obj.dma_error_flag = TRUE;
-		} else {
-			mmc_drv_obj.during_dma_transfer = FALSE;
-			mmc_drv_obj.during_transfer = FALSE;
-		}
-		/* wait next interrupt */
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	}
-	/* DM_CM_INFO1: DMA-ch1 transfer complete or error occured */
-	else if ((end_bit & mmc_drv_obj.dm_event1) != 0U) {
-		SETR_32(DM_CM_INFO1, 0x00000000U);
-		SETR_32(DM_CM_INFO2, 0x00000000U);
-		/* interrupt clear */
-		SETR_32(SD_INFO2, (GETR_32(SD_INFO2) & ~SD_INFO2_BRE));
-		/* DM_CM_INFO2: DMA-ch1 error occured */
-		if ((BIT17 & mmc_drv_obj.dm_event2) != 0) {
-			mmc_drv_obj.dma_error_flag = TRUE;
-		} else {
-			mmc_drv_obj.during_dma_transfer = FALSE;
-			mmc_drv_obj.during_transfer = FALSE;
-		}
-		/* wait next interrupt */
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	}
-
-	/* Response end  */
-	else if ((SD_INFO1_INFO0 & mmc_drv_obj.int_event1) != 0) {
-		/* interrupt clear */
-		SETR_32(SD_INFO1, (GETR_32(SD_INFO1) & ~SD_INFO1_INFO0));
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	}
-	/* Access end  */
-	else if ((SD_INFO1_INFO2 & mmc_drv_obj.int_event1) != 0) {
-		/* interrupt clear */
-		SETR_32(SD_INFO1, (GETR_32(SD_INFO1) & ~SD_INFO1_INFO2));
-		mmc_drv_obj.state_machine_blocking = FALSE;
-	} else {
-		/* nothing to do. */
-	}
-
-	return (uint32_t) 0;
-}
-
-static EMMC_ERROR_CODE emmc_trans_sector(uint32_t *buff_address_virtual)
-{
-	uint32_t length, i;
-	uint64_t *bufPtrLL;
-
-	if (buff_address_virtual == NULL) {
-		return EMMC_ERR_PARAM;
-	}
-
-	if ((mmc_drv_obj.during_transfer != TRUE)
-	    || (mmc_drv_obj.remain_size == 0)) {
-		return EMMC_ERR_STATE;
-	}
-
-	bufPtrLL = (uint64_t *) buff_address_virtual;
-	length = mmc_drv_obj.remain_size;
-
-	/* data transefer */
-	for (i = 0; i < (length >> 3); i++) {
-		/* Write */
-		if (mmc_drv_obj.cmd_info.dir == HAL_MEMCARD_WRITE) {
-			SETR_64(SD_BUF0, *bufPtrLL);	/* buffer --> FIFO */
-		}
-		/* Read */
-		else {
-			/* Checks when the read data reaches SD_SIZE. */
-			/* The BRE bit is cleared at emmc_interrupt function. */
-			if (((i %
-			      (uint32_t) (EMMC_BLOCK_LENGTH >>
-					  EMMC_BUF_SIZE_SHIFT)) == 0U)
-			    && (i != 0U)) {
-				/* BRE check */
-				while (((GETR_32(SD_INFO2)) & SD_INFO2_BRE) ==
-				       0U) {
-					/* ERROR check */
-					if (((GETR_32(SD_INFO2)) &
-					     SD_INFO2_ALL_ERR) != 0U) {
-						return EMMC_ERR_TRANSFER;
-					}
-				}
-				/* BRE clear */
-				SETR_32(SD_INFO2,
-					(uint32_t) (GETR_32(SD_INFO2) &
-						    ~SD_INFO2_BRE));
-			}
-			*bufPtrLL = GETR_64(SD_BUF0);	/* FIFO --> buffer */
-		}
-		bufPtrLL++;
-	}
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_mount.c b/drivers/renesas/rcar/emmc/emmc_mount.c
deleted file mode 100644
index df8203e..0000000
--- a/drivers/renesas/rcar/emmc/emmc_mount.c
+++ /dev/null
@@ -1,681 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <lib/mmio.h>
-
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_registers.h"
-#include "emmc_def.h"
-#include "micro_delay.h"
-#include "rcar_def.h"
-
-static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode);
-static EMMC_ERROR_CODE emmc_card_init(void);
-static EMMC_ERROR_CODE emmc_high_speed(void);
-static EMMC_ERROR_CODE emmc_bus_width(uint32_t width);
-static uint32_t emmc_set_timeout_register_value(uint32_t freq);
-static void set_sd_clk(uint32_t clkDiv);
-static uint32_t emmc_calc_tran_speed(uint32_t *freq);
-static void emmc_get_partition_access(void);
-static void emmc_set_bootpartition(void);
-
-static void emmc_set_bootpartition(void)
-{
-	uint32_t reg;
-
-	reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
-	if (reg == PRR_PRODUCT_M3_CUT10) {
-		mmc_drv_obj.boot_partition_en =
-		    (EMMC_PARTITION_ID) ((mmc_drv_obj.ext_csd_data[179] &
-					  EMMC_BOOT_PARTITION_EN_MASK) >>
-					 EMMC_BOOT_PARTITION_EN_SHIFT);
-	} else if ((reg == PRR_PRODUCT_H3_CUT20)
-		   || (reg == PRR_PRODUCT_M3_CUT11)) {
-		mmc_drv_obj.boot_partition_en = mmc_drv_obj.partition_access;
-	} else {
-		if ((mmio_read_32(MFISBTSTSR) & MFISBTSTSR_BOOT_PARTITION) !=
-		    0U) {
-			mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_2;
-		} else {
-			mmc_drv_obj.boot_partition_en = PARTITION_ID_BOOT_1;
-		}
-	}
-}
-
-static EMMC_ERROR_CODE emmc_card_init(void)
-{
-	int32_t retry;
-	uint32_t freq = MMC_400KHZ;	/* 390KHz */
-	EMMC_ERROR_CODE result;
-	uint32_t resultCalc;
-
-	/* state check */
-	if ((mmc_drv_obj.initialize != TRUE)
-	    || (mmc_drv_obj.card_power_enable != TRUE)
-	    || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0)
-	    ) {
-		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* clock on (force change) */
-	mmc_drv_obj.current_freq = 0;
-	mmc_drv_obj.max_freq = MMC_20MHZ;
-	result = emmc_set_request_mmc_clock(&freq);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return EMMC_ERR;
-	}
-
-	rcar_micro_delay(1000U);	/* wait 1ms */
-
-	/* Get current access partition */
-	emmc_get_partition_access();
-
-	/* CMD0, arg=0x00000000 */
-	result = emmc_send_idle_cmd(0x00000000);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	rcar_micro_delay(200U);	/* wait 74clock 390kHz(189.74us) */
-
-	/* CMD1 */
-	emmc_make_nontrans_cmd(CMD1_SEND_OP_COND, EMMC_HOST_OCR_VALUE);
-	for (retry = 300; retry > 0; retry--) {
-		result =
-		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-		if (result != EMMC_SUCCESS) {
-			emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-			return result;
-		}
-
-		if ((mmc_drv_obj.r3_ocr & EMMC_OCR_STATUS_BIT) != 0) {
-			break;	/* card is ready. exit loop */
-		}
-		rcar_micro_delay(1000U);	/* wait 1ms */
-	}
-
-	if (retry == 0) {
-		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR_TIMEOUT);
-		return EMMC_ERR_TIMEOUT;
-	}
-
-	switch (mmc_drv_obj.r3_ocr & EMMC_OCR_ACCESS_MODE_MASK) {
-	case EMMC_OCR_ACCESS_MODE_SECT:
-		mmc_drv_obj.access_mode = TRUE;	/* sector mode */
-		break;
-	default:
-		/* unknown value */
-		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT, EMMC_ERR);
-		return EMMC_ERR;
-	}
-
-	/* CMD2 */
-	emmc_make_nontrans_cmd(CMD2_ALL_SEND_CID_MMC, 0x00000000);
-	mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.cid_data[0]);	/* use CID special buffer */
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	/* CMD3 */
-	emmc_make_nontrans_cmd(CMD3_SET_RELATIVE_ADDR, EMMC_RCA << 16);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	/* CMD9 (CSD) */
-	emmc_make_nontrans_cmd(CMD9_SEND_CSD, EMMC_RCA << 16);
-	mmc_drv_obj.response = (uint32_t *) (&mmc_drv_obj.csd_data[0]);	/* use CSD special buffer */
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	/* card version check */
-	if (EMMC_CSD_SPEC_VARS() < 4) {
-		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT,
-				      EMMC_ERR_ILLEGAL_CARD);
-		return EMMC_ERR_ILLEGAL_CARD;
-	}
-
-	/* CMD7 (select card) */
-	emmc_make_nontrans_cmd(CMD7_SELECT_CARD, EMMC_RCA << 16);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	mmc_drv_obj.selected = TRUE;
-
-	/* card speed check */
-	resultCalc = emmc_calc_tran_speed(&freq);	/* Card spec is calculated from TRAN_SPEED(CSD).  */
-	if (resultCalc == 0) {
-		emmc_write_error_info(EMMC_FUNCNO_CARD_INIT,
-				      EMMC_ERR_ILLEGAL_CARD);
-		return EMMC_ERR_ILLEGAL_CARD;
-	}
-	mmc_drv_obj.max_freq = freq;	/* max frequency (card spec) */
-
-	result = emmc_set_request_mmc_clock(&freq);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return EMMC_ERR;
-	}
-
-	/* set read/write timeout */
-	mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq);
-	SETR_32(SD_OPTION,
-		((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) |
-		 mmc_drv_obj.data_timeout));
-
-	/* SET_BLOCKLEN(512byte) */
-	/* CMD16 */
-	emmc_make_nontrans_cmd(CMD16_SET_BLOCKLEN, EMMC_BLOCK_LENGTH);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	/* Transfer Data Length */
-	SETR_32(SD_SIZE, EMMC_BLOCK_LENGTH);
-
-	/* CMD8 (EXT_CSD) */
-	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
-			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
-			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
-			    HAL_MEMCARD_NOT_DMA);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		/* CMD12 is not send.
-		 * If BUS initialization is failed, user must be execute Bus initialization again.
-		 * Bus initialization is start CMD0(soft reset command).
-		 */
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		return result;
-	}
-
-	/* Set boot partition */
-	emmc_set_bootpartition();
-
-	return EMMC_SUCCESS;
-}
-
-static EMMC_ERROR_CODE emmc_high_speed(void)
-{
-	uint32_t freq;	      /**< High speed mode clock frequency */
-	EMMC_ERROR_CODE result;
-	uint8_t cardType;
-
-	/* state check */
-	if (mmc_drv_obj.selected != TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_HIGH_SPEED, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* max frequency */
-	cardType = (uint8_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_CARD_TYPE];
-	if ((cardType & EMMC_EXT_CSD_CARD_TYPE_52MHZ) != 0)
-		freq = MMC_52MHZ;
-	else if ((cardType & EMMC_EXT_CSD_CARD_TYPE_26MHZ) != 0)
-		freq = MMC_26MHZ;
-	else
-		freq = MMC_20MHZ;
-
-	/* Hi-Speed-mode selction */
-	if ((MMC_52MHZ == freq) || (MMC_26MHZ == freq)) {
-		/* CMD6 */
-		emmc_make_nontrans_cmd(CMD6_SWITCH, EMMC_SWITCH_HS_TIMING);
-		result =
-		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-		if (result != EMMC_SUCCESS) {
-			emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
-			return result;
-		}
-
-		mmc_drv_obj.hs_timing = TIMING_HIGH_SPEED;	/* High-Speed */
-	}
-
-	/* set mmc clock */
-	mmc_drv_obj.max_freq = freq;
-	result = emmc_set_request_mmc_clock(&freq);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
-		return EMMC_ERR;
-	}
-
-	/* set read/write timeout */
-	mmc_drv_obj.data_timeout = emmc_set_timeout_register_value(freq);
-	SETR_32(SD_OPTION,
-		((GETR_32(SD_OPTION) & ~(SD_OPTION_TIMEOUT_CNT_MASK)) |
-		 mmc_drv_obj.data_timeout));
-
-	/* CMD13 */
-	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
-	result =
-	    emmc_exec_cmd(EMMC_R1_ERROR_MASK_WITHOUT_CRC, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
-		return result;
-	}
-
-	return EMMC_SUCCESS;
-}
-
-static EMMC_ERROR_CODE emmc_clock_ctrl(uint8_t mode)
-{
-	uint32_t value;
-
-	/* busy check */
-	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) {
-		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK,
-				      EMMC_ERR_CARD_BUSY);
-		return EMMC_ERR;
-	}
-
-	if (mode == TRUE) {
-		/* clock ON */
-		value =
-		    ((GETR_32(SD_CLK_CTRL) | MMC_SD_CLK_START) &
-		     SD_CLK_WRITE_MASK);
-		SETR_32(SD_CLK_CTRL, value);	/* on  */
-		mmc_drv_obj.clock_enable = TRUE;
-	} else {
-		/* clock OFF */
-		value =
-		    ((GETR_32(SD_CLK_CTRL) & MMC_SD_CLK_STOP) &
-		     SD_CLK_WRITE_MASK);
-		SETR_32(SD_CLK_CTRL, value);	/* off */
-		mmc_drv_obj.clock_enable = FALSE;
-	}
-
-	return EMMC_SUCCESS;
-}
-
-static EMMC_ERROR_CODE emmc_bus_width(uint32_t width)
-{
-	EMMC_ERROR_CODE result = EMMC_ERR;
-
-	/* parameter check */
-	if ((width != 8) && (width != 4) && (width != 1)) {
-		emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* state check */
-	if (mmc_drv_obj.selected != TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	mmc_drv_obj.bus_width = (HAL_MEMCARD_DATA_WIDTH) (width >> 2);	/* 2 = 8bit, 1 = 4bit, 0 =1bit */
-
-	/* CMD6 */
-	emmc_make_nontrans_cmd(CMD6_SWITCH,
-			       (EMMC_SWITCH_BUS_WIDTH_1 |
-				(mmc_drv_obj.bus_width << 8)));
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		/* occurred error */
-		mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
-		goto EXIT;
-	}
-
-	switch (mmc_drv_obj.bus_width) {
-	case HAL_MEMCARD_DATA_WIDTH_1_BIT:
-		SETR_32(SD_OPTION,
-			((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT15));
-		break;
-	case HAL_MEMCARD_DATA_WIDTH_4_BIT:
-		SETR_32(SD_OPTION, (GETR_32(SD_OPTION) & ~(BIT15 | BIT13)));
-		break;
-	case HAL_MEMCARD_DATA_WIDTH_8_BIT:
-		SETR_32(SD_OPTION,
-			((GETR_32(SD_OPTION) & ~(BIT15 | BIT13)) | BIT13));
-		break;
-	default:
-		goto EXIT;
-	}
-
-	/* CMD13 */
-	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		goto EXIT;
-	}
-
-	/* CMD8 (EXT_CSD) */
-	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
-			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
-			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
-			    HAL_MEMCARD_NOT_DMA);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		goto EXIT;
-	}
-
-	return EMMC_SUCCESS;
-
-EXIT:
-
-	emmc_write_error_info(EMMC_FUNCNO_BUS_WIDTH, result);
-	ERROR("BL2: emmc bus_width error end\n");
-	return result;
-}
-
-EMMC_ERROR_CODE emmc_select_partition(EMMC_PARTITION_ID id)
-{
-	EMMC_ERROR_CODE result;
-	uint32_t arg;
-	uint32_t partition_config;
-
-	/* state check */
-	if (mmc_drv_obj.mount != TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* id = PARTITION_ACCESS(Bit[2:0]) */
-	if ((id & ~PARTITION_ID_MASK) != 0) {
-		emmc_write_error_info(EMMC_FUNCNO_NONE, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* EXT_CSD[179] value */
-	partition_config =
-	    (uint32_t) mmc_drv_obj.ext_csd_data[EMMC_EXT_CSD_PARTITION_CONFIG];
-	if ((partition_config & PARTITION_ID_MASK) == id) {
-		result = EMMC_SUCCESS;
-	} else {
-
-		partition_config =
-		    (uint32_t) ((partition_config & ~PARTITION_ID_MASK) | id);
-		arg = EMMC_SWITCH_PARTITION_CONFIG | (partition_config << 8);
-
-		result = emmc_set_ext_csd(arg);
-	}
-
-	return result;
-}
-
-static void set_sd_clk(uint32_t clkDiv)
-{
-	uint32_t dataL;
-
-	dataL = (GETR_32(SD_CLK_CTRL) & (~SD_CLK_CTRL_CLKDIV_MASK));
-
-	switch (clkDiv) {
-	case 1:
-		dataL |= 0x000000FFU;
-		break;		/* 1/1   */
-	case 2:
-		dataL |= 0x00000000U;
-		break;		/* 1/2   */
-	case 4:
-		dataL |= 0x00000001U;
-		break;		/* 1/4   */
-	case 8:
-		dataL |= 0x00000002U;
-		break;		/* 1/8   */
-	case 16:
-		dataL |= 0x00000004U;
-		break;		/* 1/16  */
-	case 32:
-		dataL |= 0x00000008U;
-		break;		/* 1/32  */
-	case 64:
-		dataL |= 0x00000010U;
-		break;		/* 1/64  */
-	case 128:
-		dataL |= 0x00000020U;
-		break;		/* 1/128 */
-	case 256:
-		dataL |= 0x00000040U;
-		break;		/* 1/256 */
-	case 512:
-		dataL |= 0x00000080U;
-		break;		/* 1/512 */
-	}
-
-	SETR_32(SD_CLK_CTRL, dataL);
-	mmc_drv_obj.current_freq = (uint32_t) clkDiv;
-}
-
-static void emmc_get_partition_access(void)
-{
-	uint32_t reg;
-	EMMC_ERROR_CODE result;
-
-	reg = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
-	if ((reg == PRR_PRODUCT_H3_CUT20) || (reg == PRR_PRODUCT_M3_CUT11)) {
-		SETR_32(SD_OPTION, 0x000060EEU);	/* 8 bits width */
-		/* CMD8 (EXT_CSD) */
-		emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000U,
-				    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
-				    EMMC_MAX_EXT_CSD_LENGTH,
-				    HAL_MEMCARD_READ, HAL_MEMCARD_NOT_DMA);
-		mmc_drv_obj.get_partition_access_flag = TRUE;
-		result =
-		    emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-		mmc_drv_obj.get_partition_access_flag = FALSE;
-		if (result == EMMC_SUCCESS) {
-			mmc_drv_obj.partition_access =
-			    (EMMC_PARTITION_ID) (mmc_drv_obj.ext_csd_data[179]
-						 & PARTITION_ID_MASK);
-		} else if (result == EMMC_ERR_CMD_TIMEOUT) {
-			mmc_drv_obj.partition_access = PARTITION_ID_BOOT_1;
-		} else {
-			emmc_write_error_info(EMMC_FUNCNO_GET_PERTITION_ACCESS,
-					      result);
-			panic();
-		}
-		SETR_32(SD_OPTION, 0x0000C0EEU);	/* Initialize */
-	}
-}
-
-static uint32_t emmc_calc_tran_speed(uint32_t *freq)
-{
-	const uint32_t unit[8] = { 10000, 100000, 1000000, 10000000,
-				0, 0, 0, 0 };   /**< frequency unit (1/10) */
-	const uint32_t mult[16] = { 0, 10, 12, 13, 15, 20, 26, 30, 35, 40, 45,
-				52, 55, 60, 70, 80 };
-
-	uint32_t maxFreq;
-	uint32_t result;
-	uint32_t tran_speed = EMMC_CSD_TRAN_SPEED();
-
-	/* tran_speed = 0x32
-	 * unit[tran_speed&0x7] = uint[0x2] = 1000000
-	 * mult[(tran_speed&0x78)>>3] = mult[0x30>>3] = mult[6] = 26
-	 * 1000000 * 26 = 26000000 (26MHz)
-	 */
-
-	result = 1;
-	maxFreq =
-	    unit[tran_speed & EMMC_TRANSPEED_FREQ_UNIT_MASK] *
-	    mult[(tran_speed & EMMC_TRANSPEED_MULT_MASK) >>
-		 EMMC_TRANSPEED_MULT_SHIFT];
-
-	if (maxFreq == 0) {
-		result = 0;
-	} else if (MMC_FREQ_52MHZ <= maxFreq)
-		*freq = MMC_52MHZ;
-	else if (MMC_FREQ_26MHZ <= maxFreq)
-		*freq = MMC_26MHZ;
-	else if (MMC_FREQ_20MHZ <= maxFreq)
-		*freq = MMC_20MHZ;
-	else
-		*freq = MMC_400KHZ;
-
-	return result;
-}
-
-static uint32_t emmc_set_timeout_register_value(uint32_t freq)
-{
-	uint32_t timeoutCnt;	/* SD_OPTION   - Timeout Counter  */
-
-	switch (freq) {
-	case 1U:
-		timeoutCnt = 0xE0U;
-		break;		/* SDCLK * 2^27 */
-	case 2U:
-		timeoutCnt = 0xE0U;
-		break;		/* SDCLK * 2^27 */
-	case 4U:
-		timeoutCnt = 0xD0U;
-		break;		/* SDCLK * 2^26 */
-	case 8U:
-		timeoutCnt = 0xC0U;
-		break;		/* SDCLK * 2^25 */
-	case 16U:
-		timeoutCnt = 0xB0U;
-		break;		/* SDCLK * 2^24 */
-	case 32U:
-		timeoutCnt = 0xA0U;
-		break;		/* SDCLK * 2^23 */
-	case 64U:
-		timeoutCnt = 0x90U;
-		break;		/* SDCLK * 2^22 */
-	case 128U:
-		timeoutCnt = 0x80U;
-		break;		/* SDCLK * 2^21 */
-	case 256U:
-		timeoutCnt = 0x70U;
-		break;		/* SDCLK * 2^20 */
-	case 512U:
-		timeoutCnt = 0x70U;
-		break;		/* SDCLK * 2^20 */
-	default:
-		timeoutCnt = 0xE0U;
-		break;		/* SDCLK * 2^27 */
-	}
-
-	return timeoutCnt;
-}
-
-EMMC_ERROR_CODE emmc_set_ext_csd(uint32_t arg)
-{
-	EMMC_ERROR_CODE result;
-
-	/* CMD6 */
-	emmc_make_nontrans_cmd(CMD6_SWITCH, arg);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-
-	/* CMD13 */
-	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-
-	/* CMD8 (EXT_CSD) */
-	emmc_make_trans_cmd(CMD8_SEND_EXT_CSD, 0x00000000,
-			    (uint32_t *) (&mmc_drv_obj.ext_csd_data[0]),
-			    EMMC_MAX_EXT_CSD_LENGTH, HAL_MEMCARD_READ,
-			    HAL_MEMCARD_NOT_DMA);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-	return EMMC_SUCCESS;
-}
-
-EMMC_ERROR_CODE emmc_set_request_mmc_clock(uint32_t *freq)
-{
-	/* parameter check */
-	if (freq == NULL) {
-		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* state check */
-	if ((mmc_drv_obj.initialize != TRUE)
-	    || (mmc_drv_obj.card_power_enable != TRUE)) {
-		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* clock is already running in the desired frequency. */
-	if ((mmc_drv_obj.clock_enable == TRUE)
-	    && (mmc_drv_obj.current_freq == *freq)) {
-		return EMMC_SUCCESS;
-	}
-
-	/* busy check */
-	if ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0) {
-		emmc_write_error_info(EMMC_FUNCNO_SET_CLOCK,
-				      EMMC_ERR_CARD_BUSY);
-		return EMMC_ERR;
-	}
-
-	set_sd_clk(*freq);
-	mmc_drv_obj.clock_enable = FALSE;
-
-	return emmc_clock_ctrl(TRUE);	/* clock on */
-}
-
-EMMC_ERROR_CODE rcar_emmc_mount(void)
-{
-	EMMC_ERROR_CODE result;
-
-	/* state check */
-	if ((mmc_drv_obj.initialize != TRUE)
-	    || (mmc_drv_obj.card_power_enable != TRUE)
-	    || ((GETR_32(SD_INFO2) & SD_INFO2_CBSY) != 0)
-	    ) {
-		emmc_write_error_info(EMMC_FUNCNO_MOUNT, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* initialize card (IDLE state --> Transfer state) */
-	result = emmc_card_init();
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_CARD_INIT);
-		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
-			/* nothing to do. */
-		}
-		return result;
-	}
-
-	/* Switching high speed mode */
-	result = emmc_high_speed();
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_HIGH_SPEED);
-		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
-			/* nothing to do. */
-		}
-		return result;
-	}
-
-	/* Changing the data bus width */
-	result = emmc_bus_width(8);
-	if (result != EMMC_SUCCESS) {
-		emmc_write_error_info_func_no(EMMC_FUNCNO_BUS_WIDTH);
-		if (emmc_clock_ctrl(FALSE) != EMMC_SUCCESS) {
-			/* nothing to do. */
-		}
-		return result;
-	}
-
-	/* mount complete */
-	mmc_drv_obj.mount = TRUE;
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_read.c b/drivers/renesas/rcar/emmc/emmc_read.c
deleted file mode 100644
index 390d0ca..0000000
--- a/drivers/renesas/rcar/emmc/emmc_read.c
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch_helpers.h>
-
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_registers.h"
-#include "emmc_def.h"
-
-#define MIN_EMMC(a, b)        (((a) < (b)) ? (a) : (b))
-#define EMMC_RW_SECTOR_COUNT_MAX        0x0000ffffU
-
-static EMMC_ERROR_CODE emmc_multiple_block_read (uint32_t *buff_address_virtual,
-		uint32_t sector_number, uint32_t count,
-		HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode)
-{
-	EMMC_ERROR_CODE result;
-
-	/* parameter check */
-	if ((count > EMMC_RW_SECTOR_COUNT_MAX)
-	    || (count == 0)
-	    || ((transfer_mode != HAL_MEMCARD_DMA)
-		&& (transfer_mode != HAL_MEMCARD_NOT_DMA))
-	    ) {
-		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* CMD23 */
-	emmc_make_nontrans_cmd(CMD23_SET_BLOCK_COUNT, count);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-	SETR_32(SD_SECCNT, count);
-	SETR_32(SD_STOP, 0x00000100);
-	SETR_32(CC_EXT_MODE, (CC_EXT_MODE_CLEAR | CC_EXT_MODE_DMASDRW_ENABLE));	/* SD_BUF Read/Write DMA Transfer enable */
-
-	/* CMD18 */
-	emmc_make_trans_cmd(CMD18_READ_MULTIPLE_BLOCK, sector_number,
-			    buff_address_virtual,
-			    count << EMMC_SECTOR_SIZE_SHIFT, HAL_MEMCARD_READ,
-			    transfer_mode);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;	/* CMD18 error code */
-	}
-
-	/* CMD13 */
-	emmc_make_nontrans_cmd(CMD13_SEND_STATUS, EMMC_RCA << 16);
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-#if RCAR_BL2_DCACHE == 1
-	if (transfer_mode == HAL_MEMCARD_NOT_DMA) {
-		flush_dcache_range((uint64_t) buff_address_virtual,
-				   ((size_t) count << EMMC_SECTOR_SIZE_SHIFT));
-	}
-#endif /* RCAR_BL2_DCACHE == 1 */
-
-	/* ready status check */
-	if ((mmc_drv_obj.r1_card_status & EMMC_R1_READY) == 0) {
-		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR,
-				      EMMC_ERR_CARD_BUSY);
-		return EMMC_ERR_CARD_BUSY;
-	}
-
-	/* state check */
-	if (mmc_drv_obj.current_state != EMMC_R1_STATE_TRAN) {
-		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR,
-				      EMMC_ERR_CARD_STATE);
-		return EMMC_ERR_CARD_STATE;
-	}
-
-	return EMMC_SUCCESS;
-}
-
-EMMC_ERROR_CODE emmc_read_sector(uint32_t *buff_address_virtual,
-				 uint32_t sector_number,
-				 uint32_t count, uint32_t feature_flags)
-{
-	uint32_t trans_count;
-	uint32_t remain;
-	EMMC_ERROR_CODE result;
-	HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode;
-
-	/* parameter check */
-	if (count == 0) {
-		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_PARAM);
-		return EMMC_ERR_PARAM;
-	}
-
-	/* state check */
-	if (mmc_drv_obj.mount != TRUE) {
-		emmc_write_error_info(EMMC_FUNCNO_READ_SECTOR, EMMC_ERR_STATE);
-		return EMMC_ERR_STATE;
-	}
-
-	/* DMA? */
-	if ((feature_flags & LOADIMAGE_FLAGS_DMA_ENABLE) != 0) {
-		transfer_mode = HAL_MEMCARD_DMA;
-	} else {
-		transfer_mode = HAL_MEMCARD_NOT_DMA;
-	}
-
-	remain = count;
-	while (remain != 0) {
-		trans_count = MIN_EMMC(remain, EMMC_RW_SECTOR_COUNT_MAX);
-		result =
-		    emmc_multiple_block_read(buff_address_virtual,
-					     sector_number, trans_count,
-					     transfer_mode);
-		if (result != EMMC_SUCCESS) {
-			return result;
-		}
-
-		buff_address_virtual += (EMMC_BLOCK_LENGTH_DW * trans_count);
-		sector_number += trans_count;
-		remain -= trans_count;
-	}
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/emmc/emmc_registers.h b/drivers/renesas/rcar/emmc/emmc_registers.h
deleted file mode 100644
index 55ff33d..0000000
--- a/drivers/renesas/rcar/emmc/emmc_registers.h
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/**
- * @file  emmc_registers.h
- * @brief emmc boot driver is expecting this header file. HS-MMC module header file.
- *
- */
-
-#ifndef EMMC_REGISTERS_H
-#define EMMC_REGISTERS_H
-
-/* ************************ HEADER (INCLUDE) SECTION *********************** */
-
-/* ***************** MACROS, CONSTANTS, COMPILATION FLAGS ****************** */
-
-/* MMC channel select */
-#define MMC_CH0		(0U)	/* SDHI2/MMC0 */
-#define MMC_CH1		(1U)	/* SDHI3/MMC1 */
-
-#if RCAR_LSI == RCAR_E3
-#define USE_MMC_CH	(MMC_CH1)	/* R-Car E3 */
-#else /* RCAR_LSI == RCAR_E3 */
-#define USE_MMC_CH	(MMC_CH0)	/* R-Car H3/M3/M3N */
-#endif /* RCAR_LSI == RCAR_E3 */
-
-#define		BIT0	(0x00000001U)
-#define		BIT1	(0x00000002U)
-#define		BIT2	(0x00000004U)
-#define		BIT3	(0x00000008U)
-#define		BIT4	(0x00000010U)
-#define		BIT5	(0x00000020U)
-#define		BIT6	(0x00000040U)
-#define		BIT7	(0x00000080U)
-#define		BIT8	(0x00000100U)
-#define		BIT9	(0x00000200U)
-#define		BIT10	(0x00000400U)
-#define		BIT11	(0x00000800U)
-#define		BIT12	(0x00001000U)
-#define		BIT13	(0x00002000U)
-#define		BIT14	(0x00004000U)
-#define		BIT15	(0x00008000U)
-#define		BIT16	(0x00010000U)
-#define		BIT17	(0x00020000U)
-#define		BIT18	(0x00040000U)
-#define		BIT19	(0x00080000U)
-#define		BIT20	(0x00100000U)
-#define		BIT21	(0x00200000U)
-#define		BIT22	(0x00400000U)
-#define		BIT23	(0x00800000U)
-#define		BIT24	(0x01000000U)
-#define		BIT25	(0x02000000U)
-#define		BIT26	(0x04000000U)
-#define		BIT27	(0x08000000U)
-#define		BIT28	(0x10000000U)
-#define		BIT29	(0x20000000U)
-#define		BIT30	(0x40000000U)
-#define		BIT31	(0x80000000U)
-
-/** @brief Clock Pulse Generator (CPG) registers
- */
-#define	CPG_BASE		(0xE6150000U)
-
-#define	CPG_MSTPSR3		(CPG_BASE+0x0048U)	/* Module stop status register 3 */
-
-#define	CPG_SMSTPCR3		(CPG_BASE+0x013CU)	/* System module stop control register 3 */
-
-#define	CPG_SD2CKCR		(CPG_BASE+0x0268U)	/* SDHI2 clock frequency control register */
-#define CPG_SD3CKCR		(CPG_BASE+0x026CU)	/* SDHI3 clock frequency control register */
-
-#define	CPG_CPGWPR		(CPG_BASE+0x0900U)	/* CPG Write Protect Register */
-
-#if USE_MMC_CH == MMC_CH0
-#define	CPG_SDxCKCR		(CPG_SD2CKCR)	/* SDHI2/MMC0 */
-#else /* USE_MMC_CH == MMC_CH0 */
-#define	CPG_SDxCKCR		(CPG_SD3CKCR)	/* SDHI3/MMC1 */
-#endif /* USE_MMC_CH == MMC_CH0 */
-
-/** Boot Status register
- */
-#define  MFISBTSTSR			(0xE6260604U)
-
-#define  MFISBTSTSR_BOOT_PARTITION	(0x00000010U)
-
-/** brief eMMC registers
- */
-#define	MMC0_SD_BASE		(0xEE140000U)
-#define MMC1_SD_BASE		(0xEE160000U)
-
-#if USE_MMC_CH == MMC_CH0
-#define	MMC_SD_BASE		(MMC0_SD_BASE)
-#else /* USE_MMC_CH == MMC_CH0 */
-#define	MMC_SD_BASE		(MMC1_SD_BASE)
-#endif /* USE_MMC_CH == MMC_CH0 */
-
-#define SD_CMD			(MMC_SD_BASE + 0x0000U)
-#define SD_PORTSEL		(MMC_SD_BASE + 0x0008U)
-#define SD_ARG			(MMC_SD_BASE + 0x0010U)
-#define SD_ARG1			(MMC_SD_BASE + 0x0018U)
-#define SD_STOP			(MMC_SD_BASE + 0x0020U)
-#define SD_SECCNT		(MMC_SD_BASE + 0x0028U)
-#define SD_RSP10		(MMC_SD_BASE + 0x0030U)
-#define SD_RSP1			(MMC_SD_BASE + 0x0038U)
-#define SD_RSP32		(MMC_SD_BASE + 0x0040U)
-#define SD_RSP3			(MMC_SD_BASE + 0x0048U)
-#define SD_RSP54		(MMC_SD_BASE + 0x0050U)
-#define SD_RSP5			(MMC_SD_BASE + 0x0058U)
-#define SD_RSP76		(MMC_SD_BASE + 0x0060U)
-#define SD_RSP7			(MMC_SD_BASE + 0x0068U)
-#define SD_INFO1		(MMC_SD_BASE + 0x0070U)
-#define SD_INFO2		(MMC_SD_BASE + 0x0078U)
-#define SD_INFO1_MASK		(MMC_SD_BASE + 0x0080U)
-#define SD_INFO2_MASK		(MMC_SD_BASE + 0x0088U)
-#define SD_CLK_CTRL		(MMC_SD_BASE + 0x0090U)
-#define SD_SIZE			(MMC_SD_BASE + 0x0098U)
-#define SD_OPTION		(MMC_SD_BASE + 0x00A0U)
-#define SD_ERR_STS1		(MMC_SD_BASE + 0x00B0U)
-#define SD_ERR_STS2		(MMC_SD_BASE + 0x00B8U)
-#define SD_BUF0			(MMC_SD_BASE + 0x00C0U)
-#define SDIO_MODE		(MMC_SD_BASE + 0x00D0U)
-#define SDIO_INFO1		(MMC_SD_BASE + 0x00D8U)
-#define SDIO_INFO1_MASK		(MMC_SD_BASE + 0x00E0U)
-#define CC_EXT_MODE		(MMC_SD_BASE + 0x0360U)
-#define SOFT_RST		(MMC_SD_BASE + 0x0380U)
-#define VERSION			(MMC_SD_BASE + 0x0388U)
-#define HOST_MODE		(MMC_SD_BASE + 0x0390U)
-#define DM_CM_DTRAN_MODE	(MMC_SD_BASE + 0x0820U)
-#define DM_CM_DTRAN_CTRL	(MMC_SD_BASE + 0x0828U)
-#define DM_CM_RST		(MMC_SD_BASE + 0x0830U)
-#define DM_CM_INFO1		(MMC_SD_BASE + 0x0840U)
-#define DM_CM_INFO1_MASK	(MMC_SD_BASE + 0x0848U)
-#define DM_CM_INFO2		(MMC_SD_BASE + 0x0850U)
-#define DM_CM_INFO2_MASK	(MMC_SD_BASE + 0x0858U)
-#define DM_DTRAN_ADDR		(MMC_SD_BASE + 0x0880U)
-
-/** @brief SD_INFO1 Registers
- */
-#define SD_INFO1_HPIRES				0x00010000UL	/* Response Reception Completion        */
-#define SD_INFO1_INFO10				0x00000400UL	/* Indicates the SDDAT3 state           */
-#define SD_INFO1_INFO9				0x00000200UL	/* SDDAT3 Card Insertion                        */
-#define SD_INFO1_INFO8				0x00000100UL	/* SDDAT3 Card Removal                          */
-#define SD_INFO1_INFO7				0x00000080UL	/* Write Protect                                        */
-#define SD_INFO1_INFO5				0x00000020UL	/* Indicates the ISDCD state            */
-#define SD_INFO1_INFO4				0x00000010UL	/* ISDCD Card Insertion                         */
-#define SD_INFO1_INFO3				0x00000008UL	/* ISDCD Card Removal                           */
-#define SD_INFO1_INFO2				0x00000004UL	/* Access end                                           */
-#define SD_INFO1_INFO0				0x00000001UL	/* Response end                                         */
-
-/** @brief SD_INFO2 Registers
- */
-#define SD_INFO2_ILA				0x00008000UL	/* Illegal Access Error                 */
-#define SD_INFO2_CBSY				0x00004000UL	/* Command Type Register Busy   */
-#define SD_INFO2_SCLKDIVEN			0x00002000UL
-#define SD_INFO2_BWE				0x00000200UL	/* SD_BUF Write Enable                  */
-#define SD_INFO2_BRE				0x00000100UL	/* SD_BUF Read Enable                   */
-#define SD_INFO2_DAT0				0x00000080UL	/* SDDAT0                                               */
-#define SD_INFO2_ERR6				0x00000040UL	/* Response Timeout                             */
-#define SD_INFO2_ERR5				0x00000020UL	/* SD_BUF Illegal Read Access   */
-#define SD_INFO2_ERR4				0x00000010UL	/* SD_BUF Illegal Write Access  */
-#define SD_INFO2_ERR3				0x00000008UL	/* Data Timeout                                 */
-#define SD_INFO2_ERR2				0x00000004UL	/* END Error                                    */
-#define SD_INFO2_ERR1				0x00000002UL	/* CRC Error                                    */
-#define SD_INFO2_ERR0				0x00000001UL	/* CMD Error                                    */
-#define SD_INFO2_ALL_ERR			0x0000807FUL
-#define SD_INFO2_CLEAR				0x00000800UL	/* BIT11 The write value should always be 1. HWM_0003 */
-
-/** @brief SOFT_RST
- */
-#define SOFT_RST_SDRST				0x00000001UL
-
-/** @brief SD_CLK_CTRL
- */
-#define SD_CLK_CTRL_SDCLKOFFEN		0x00000200UL
-#define SD_CLK_CTRL_SCLKEN			0x00000100UL
-#define SD_CLK_CTRL_CLKDIV_MASK     0x000000FFUL
-#define SD_CLOCK_ENABLE             0x00000100UL
-#define SD_CLOCK_DISABLE            0x00000000UL
-#define SD_CLK_WRITE_MASK           0x000003FFUL
-#define SD_CLK_CLKDIV_CLEAR_MASK    0xFFFFFF0FUL
-
-/** @brief SD_OPTION
- */
-#define SD_OPTION_TIMEOUT_CNT_MASK	0x000000F0UL
-
-/** @brief MMC Clock Frequency
- * 200MHz * 1/x = output clock
- */
-#define MMC_CLK_OFF			0UL	/* Clock output is disabled                                                             */
-#define MMC_400KHZ			512UL	/* 200MHz * 1/512 = 390 KHz                             */
-#define MMC_20MHZ			16UL	/* 200MHz * 1/16   = 12.5 MHz Normal speed mode         */
-#define MMC_26MHZ			8UL	/* 200MHz * 1/8   = 25 MHz High speed mode 26Mhz        */
-#define MMC_52MHZ			4UL	/* 200MHz * 1/4   = 50 MHz High speed mode 52Mhz        */
-#define MMC_100MHZ			2UL	/* 200MHz * 1/2   = 100 MHz                             */
-#define MMC_200MHZ			1UL	/* 200MHz * 1/1   = 200 MHz                             */
-
-#define MMC_FREQ_52MHZ		52000000UL
-#define MMC_FREQ_26MHZ		26000000UL
-#define MMC_FREQ_20MHZ		20000000UL
-
-/** @brief MMC Clock DIV
- */
-#define MMC_SD_CLK_START	0x00000100UL	/* CLOCK On             */
-#define MMC_SD_CLK_STOP		(~0x00000100UL)	/* CLOCK stop   */
-#define MMC_SD_CLK_DIV1		0x000000FFUL	/* 1/1          */
-#define MMC_SD_CLK_DIV2		0x00000000UL	/* 1/2          */
-#define MMC_SD_CLK_DIV4		0x00000001UL	/* 1/4          */
-#define MMC_SD_CLK_DIV8		0x00000002UL	/* 1/8          */
-#define MMC_SD_CLK_DIV16	0x00000004UL	/* 1/16         */
-#define MMC_SD_CLK_DIV32	0x00000008UL	/* 1/32         */
-#define MMC_SD_CLK_DIV64	0x00000010UL	/* 1/64         */
-#define MMC_SD_CLK_DIV128	0x00000020UL	/* 1/128        */
-#define MMC_SD_CLK_DIV256	0x00000040UL	/* 1/256        */
-#define MMC_SD_CLK_DIV512	0x00000080UL	/* 1/512        */
-
-/** @brief DM_CM_DTRAN_MODE
- */
-#define DM_CM_DTRAN_MODE_CH0		0x00000000UL	/* CH0(downstream)      */
-#define DM_CM_DTRAN_MODE_CH1		0x00010000UL	/* CH1(upstream)        */
-#define DM_CM_DTRAN_MODE_BIT_WIDTH	0x00000030UL
-
-/** @brief CC_EXT_MODE
- */
-#define CC_EXT_MODE_DMASDRW_ENABLE	0x00000002UL	/* SD_BUF Read/Write DMA Transfer */
-#define CC_EXT_MODE_CLEAR			0x00001010UL	/* BIT 12 & 4 always 1. */
-
-/** @brief DM_CM_INFO_MASK
- */
-#define DM_CM_INFO_MASK_CLEAR		0xFFFCFFFEUL
-#define DM_CM_INFO_CH0_ENABLE		0x00010001UL
-#define DM_CM_INFO_CH1_ENABLE		0x00020001UL
-
-/** @brief DM_DTRAN_ADDR
- */
-#define DM_DTRAN_ADDR_WRITE_MASK	0xFFFFFFF8UL
-
-/** @brief DM_CM_DTRAN_CTRL
- */
-#define DM_CM_DTRAN_CTRL_START		0x00000001UL
-
-/** @brief SYSC Registers
- */
-#if USE_MMC_CH == MMC_CH0
-#define CPG_MSTP_MMC		(BIT12)	/* SDHI2/MMC0 */
-#else /* USE_MMC_CH == MMC_CH0 */
-#define CPG_MSTP_MMC		(BIT11)	/* SDHI3/MMC1 */
-#endif /* USE_MMC_CH == MMC_CH0 */
-
-/* ********************** STRUCTURES, TYPE DEFINITIONS ********************* */
-
-/* ********************** DECLARATION OF EXTERNAL DATA ********************* */
-
-/* ************************** FUNCTION PROTOTYPES ************************** */
-
-/* ********************************* CODE ********************************** */
-
-#endif /* EMMC_REGISTERS_H */
-/* ******************************** END ************************************ */
diff --git a/drivers/renesas/rcar/emmc/emmc_std.h b/drivers/renesas/rcar/emmc/emmc_std.h
deleted file mode 100644
index 99cb6b9..0000000
--- a/drivers/renesas/rcar/emmc/emmc_std.h
+++ /dev/null
@@ -1,474 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/**
- * @file  emmc_std.h
- * @brief eMMC boot is expecting this header file
- *
- */
-
-#ifndef EMMC_STD_H
-#define EMMC_STD_H
-
-#include "emmc_hal.h"
-
-/* ************************ HEADER (INCLUDE) SECTION *********************** */
-
-/* ***************** MACROS, CONSTANTS, COMPILATION FLAGS ****************** */
-#ifndef FALSE
-#define FALSE	0U
-#endif
-#ifndef TRUE
-#define TRUE	1U
-#endif
-
-/** @brief 64bit registers
- **/
-#define SETR_64(r, v)                   (*(volatile uint64_t *)(r) = (v))
-#define GETR_64(r)                      (*(volatile uint64_t *)(r))
-
-/** @brief 32bit registers
- **/
-#define SETR_32(r, v)                   (*(volatile uint32_t *)(r) = (v))
-#define GETR_32(r)                      (*(volatile uint32_t *)(r))
-
-/** @brief 16bit registers
- */
-#define SETR_16(r, v)                   (*(volatile uint16_t *)(r) = (v))
-#define GETR_16(r)                      (*(volatile uint16_t *)(r))
-
-/** @brief 8bit registers
- */
-#define SETR_8(r, v)                    (*(volatile uint8_t *)(r) = (v))
-#define GETR_8(r)                       (*(volatile uint8_t *)(r))
-
-/** @brief CSD register Macros
- */
-#define EMMC_GET_CID(x, y) (emmc_bit_field(mmc_drv_obj.cid_data, (x), (y)))
-
-#define EMMC_CID_MID()			(EMMC_GET_CID(127, 120))
-#define EMMC_CID_CBX()			(EMMC_GET_CID(113, 112))
-#define EMMC_CID_OID()			(EMMC_GET_CID(111, 104))
-#define EMMC_CID_PNM1()			(EMMC_GET_CID(103, 88))
-#define EMMC_CID_PNM2()			(EMMC_GET_CID(87, 56))
-#define EMMC_CID_PRV()			(EMMC_GET_CID(55, 48))
-#define EMMC_CID_PSN()			(EMMC_GET_CID(47, 16))
-#define EMMC_CID_MDT()			(EMMC_GET_CID(15, 8))
-#define EMMC_CID_CRC()			(EMMC_GET_CID(7, 1))
-
-/** @brief CSD register Macros
- */
-#define EMMC_GET_CSD(x, y) (emmc_bit_field(mmc_drv_obj.csd_data, (x), (y)))
-
-#define EMMC_CSD_CSD_STRUCTURE()        (EMMC_GET_CSD(127, 126))
-#define EMMC_CSD_SPEC_VARS()            (EMMC_GET_CSD(125, 122))
-#define EMMC_CSD_TAAC()                 (EMMC_GET_CSD(119, 112))
-#define EMMC_CSD_NSAC()                 (EMMC_GET_CSD(111, 104))
-#define EMMC_CSD_TRAN_SPEED()           (EMMC_GET_CSD(103, 96))
-#define EMMC_CSD_CCC()                  (EMMC_GET_CSD(95, 84))
-#define EMMC_CSD_READ_BL_LEN()          (EMMC_GET_CSD(83, 80))
-#define EMMC_CSD_READ_BL_PARTIAL()      (EMMC_GET_CSD(79, 79))
-#define EMMC_CSD_WRITE_BLK_MISALIGN()   (EMMC_GET_CSD(78, 78))
-#define EMMC_CSD_READ_BLK_MISALIGN()    (EMMC_GET_CSD(77, 77))
-#define EMMC_CSD_DSR_IMP()              (EMMC_GET_CSD(76, 76))
-#define EMMC_CSD_C_SIZE()               (EMMC_GET_CSD(73, 62))
-#define EMMC_CSD_VDD_R_CURR_MIN()       (EMMC_GET_CSD(61, 59))
-#define EMMC_CSD_VDD_R_CURR_MAX()       (EMMC_GET_CSD(58, 56))
-#define EMMC_CSD_VDD_W_CURR_MIN()       (EMMC_GET_CSD(55, 53))
-#define EMMC_CSD_VDD_W_CURR_MAX()       (EMMC_GET_CSD(52, 50))
-#define EMMC_CSD_C_SIZE_MULT()          (EMMC_GET_CSD(49, 47))
-#define EMMC_CSD_ERASE_GRP_SIZE()       (EMMC_GET_CSD(46, 42))
-#define EMMC_CSD_ERASE_GRP_MULT()       (EMMC_GET_CSD(41, 37))
-#define EMMC_CSD_WP_GRP_SIZE()          (EMMC_GET_CSD(36, 32))
-#define EMMC_CSD_WP_GRP_ENABLE()        (EMMC_GET_CSD(31, 31))
-#define EMMC_CSD_DEFALT_ECC()           (EMMC_GET_CSD(30, 29))
-#define EMMC_CSD_R2W_FACTOR()           (EMMC_GET_CSD(28, 26))
-#define EMMC_CSD_WRITE_BL_LEN()         (EMMC_GET_CSD(25, 22))
-#define EMMC_CSD_WRITE_BL_PARTIAL()     (EMMC_GET_CSD(21, 21))
-#define EMMC_CSD_CONTENT_PROT_APP()     (EMMC_GET_CSD(16, 16))
-#define EMMC_CSD_FILE_FORMAT_GRP()      (EMMC_GET_CSD(15, 15))
-#define EMMC_CSD_COPY()                 (EMMC_GET_CSD(14, 14))
-#define EMMC_CSD_PERM_WRITE_PROTECT()   (EMMC_GET_CSD(13, 13))
-#define EMMC_CSD_TMP_WRITE_PROTECT()    (EMMC_GET_CSD(12, 12))
-#define EMMC_CSD_FILE_FORMAT()          (EMMC_GET_CSD(11, 10))
-#define EMMC_CSD_ECC()                  (EMMC_GET_CSD(9, 8))
-#define EMMC_CSD_CRC()                  (EMMC_GET_CSD(7, 1))
-
-/** @brief for sector access
- */
-#define EMMC_4B_BOUNDARY_CHECK_MASK         0x00000003
-#define EMMC_SECTOR_SIZE_SHIFT              9U	/* 512 = 2^9 */
-#define EMMC_SECTOR_SIZE                    512
-#define EMMC_BLOCK_LENGTH                   512
-#define EMMC_BLOCK_LENGTH_DW                128
-#define EMMC_BUF_SIZE_SHIFT                 3U	/* 8byte = 2^3 */
-
-/** @brief eMMC specification clock
- */
-#define EMMC_CLOCK_SPEC_400K                400000UL	 /**< initialize clock 400KHz */
-#define EMMC_CLOCK_SPEC_20M                 20000000UL	 /**< normal speed 20MHz */
-#define EMMC_CLOCK_SPEC_26M                 26000000UL	 /**< high speed 26MHz */
-#define EMMC_CLOCK_SPEC_52M                 52000000UL	 /**< high speed 52MHz */
-#define EMMC_CLOCK_SPEC_100M                100000000UL	 /**< high speed 100MHz */
-
-/** @brief EMMC driver error code. (extended HAL_MEMCARD_RETURN)
- */
-typedef enum {
-	EMMC_ERR = 0,				/**< unknown error */
-	EMMC_SUCCESS,				/**< OK */
-	EMMC_ERR_FROM_DMAC,			/**< DMAC allocation error */
-	EMMC_ERR_FROM_DMAC_TRANSFER,		/**< DMAC transfer error */
-	EMMC_ERR_CARD_STATUS_BIT,		/**< card status error. Non-masked error bit was set in the card status */
-	EMMC_ERR_CMD_TIMEOUT,			/**< command timeout error */
-	EMMC_ERR_DATA_TIMEOUT,			/**< data timeout error */
-	EMMC_ERR_CMD_CRC,			/**< command CRC error */
-	EMMC_ERR_DATA_CRC,			/**< data CRC error */
-	EMMC_ERR_PARAM,				/**< parameter error */
-	EMMC_ERR_RESPONSE,			/**< response error */
-	EMMC_ERR_RESPONSE_BUSY,			/**< response busy error */
-	EMMC_ERR_TRANSFER,			/**< data transfer error */
-	EMMC_ERR_READ_SECTOR,			/**< read sector error */
-	EMMC_ERR_WRITE_SECTOR,			/**< write sector error */
-	EMMC_ERR_STATE,				/**< state error */
-	EMMC_ERR_TIMEOUT,			/**< timeout error */
-	EMMC_ERR_ILLEGAL_CARD,			/**< illegal card */
-	EMMC_ERR_CARD_BUSY,			/**< Busy state */
-	EMMC_ERR_CARD_STATE,			/**< card state error */
-	EMMC_ERR_SET_TRACE,			/**< trace information error */
-	EMMC_ERR_FROM_TIMER,			/**< Timer error */
-	EMMC_ERR_FORCE_TERMINATE,		/**< Force terminate */
-	EMMC_ERR_CARD_POWER,			/**< card power fail */
-	EMMC_ERR_ERASE_SECTOR,			/**< erase sector error */
-	EMMC_ERR_INFO2				    /**< exec cmd error info2 */
-} EMMC_ERROR_CODE;
-
-/** @brief Function number */
-#define EMMC_FUNCNO_NONE						0U
-#define EMMC_FUNCNO_DRIVER_INIT						1U
-#define EMMC_FUNCNO_CARD_POWER_ON					2U
-#define EMMC_FUNCNO_MOUNT						3U
-#define EMMC_FUNCNO_CARD_INIT						4U
-#define EMMC_FUNCNO_HIGH_SPEED						5U
-#define EMMC_FUNCNO_BUS_WIDTH						6U
-#define EMMC_FUNCNO_MULTI_BOOT_SELECT_PARTITION				7U
-#define EMMC_FUNCNO_MULTI_BOOT_READ_SECTOR				8U
-#define EMMC_FUNCNO_TRANS_DATA_READ_SECTOR				9U
-#define EMMC_FUNCNO_UBOOT_IMAGE_SELECT_PARTITION			10U
-#define EMMC_FUNCNO_UBOOT_IMAGE_READ_SECTOR				11U
-#define EMMC_FUNCNO_SET_CLOCK						12U
-#define EMMC_FUNCNO_EXEC_CMD						13U
-#define EMMC_FUNCNO_READ_SECTOR						14U
-#define EMMC_FUNCNO_WRITE_SECTOR					15U
-#define EMMC_FUNCNO_ERASE_SECTOR					16U
-#define EMMC_FUNCNO_GET_PERTITION_ACCESS				17U
-/** @brief Response
- */
-/** R1 */
-#define EMMC_R1_ERROR_MASK                      0xFDBFE080U	/* Type 'E' bit and bit14(must be 0). ignore bit22 */
-#define EMMC_R1_ERROR_MASK_WITHOUT_CRC          (0xFD3FE080U)	/* Ignore bit23 (Not check CRC error) */
-#define EMMC_R1_STATE_MASK                      0x00001E00U	/* [12:9] */
-#define EMMC_R1_READY                           0x00000100U	/* bit8 */
-#define EMMC_R1_STATE_SHIFT                     9
-
-/** R4 */
-#define EMMC_R4_RCA_MASK                        0xFFFF0000UL
-#define EMMC_R4_STATUS                          0x00008000UL
-
-/** CSD */
-#define EMMC_TRANSPEED_FREQ_UNIT_MASK           0x07	/* bit[2:0] */
-#define EMMC_TRANSPEED_FREQ_UNIT_SHIFT          0
-#define EMMC_TRANSPEED_MULT_MASK                0x78	/* bit[6:3] */
-#define EMMC_TRANSPEED_MULT_SHIFT               3
-
-/** OCR */
-#define EMMC_HOST_OCR_VALUE                     0x40FF8080
-#define EMMC_OCR_STATUS_BIT                     0x80000000L	/* Card power up status bit */
-#define EMMC_OCR_ACCESS_MODE_MASK               0x60000000L	/* bit[30:29] */
-#define EMMC_OCR_ACCESS_MODE_SECT               0x40000000L
-#define EMMC_OCR_ACCESS_MODE_BYTE               0x00000000L
-
-/** EXT_CSD */
-#define EMMC_EXT_CSD_S_CMD_SET                      504
-#define EMMC_EXT_CSD_INI_TIMEOUT_AP                 241
-#define EMMC_EXT_CSD_PWR_CL_DDR_52_360              239
-#define EMMC_EXT_CSD_PWR_CL_DDR_52_195              238
-#define EMMC_EXT_CSD_MIN_PERF_DDR_W_8_52            235
-#define EMMC_EXT_CSD_MIN_PERF_DDR_R_8_52            234
-#define EMMC_EXT_CSD_TRIM_MULT                      232
-#define EMMC_EXT_CSD_SEC_FEATURE_SUPPORT            231
-#define EMMC_EXT_CSD_SEC_ERASE_MULT                 229
-#define EMMC_EXT_CSD_BOOT_INFO                      228
-#define EMMC_EXT_CSD_BOOT_SIZE_MULTI                226
-#define EMMC_EXT_CSD_ACC_SIZE                       225
-#define EMMC_EXT_CSD_HC_ERASE_GRP_SIZE              224
-#define EMMC_EXT_CSD_ERASE_TIMEOUT_MULT             223
-#define EMMC_EXT_CSD_PEL_WR_SEC_C                   222
-#define EMMC_EXT_CSD_HC_WP_GRP_SIZE                 221
-#define EMMC_EXT_CSD_S_C_VCC                        220
-#define EMMC_EXT_CSD_S_C_VCCQ                       219
-#define EMMC_EXT_CSD_S_A_TIMEOUT                    217
-#define EMMC_EXT_CSD_SEC_COUNT                      215
-#define EMMC_EXT_CSD_MIN_PERF_W_8_52                210
-#define EMMC_EXT_CSD_MIN_PERF_R_8_52                209
-#define EMMC_EXT_CSD_MIN_PERF_W_8_26_4_52           208
-#define EMMC_EXT_CSD_MIN_PERF_R_8_26_4_52           207
-#define EMMC_EXT_CSD_MIN_PERF_W_4_26                206
-#define EMMC_EXT_CSD_MIN_PERF_R_4_26                205
-#define EMMC_EXT_CSD_PWR_CL_26_360                  203
-#define EMMC_EXT_CSD_PWR_CL_52_360                  202
-#define EMMC_EXT_CSD_PWR_CL_26_195                  201
-#define EMMC_EXT_CSD_PWR_CL_52_195                  200
-#define EMMC_EXT_CSD_CARD_TYPE                      196
-#define EMMC_EXT_CSD_CSD_STRUCTURE                  194
-#define EMMC_EXT_CSD_EXT_CSD_REV                    192
-#define EMMC_EXT_CSD_CMD_SET                        191
-#define EMMC_EXT_CSD_CMD_SET_REV                    189
-#define EMMC_EXT_CSD_POWER_CLASS                    187
-#define EMMC_EXT_CSD_HS_TIMING                      185
-#define EMMC_EXT_CSD_BUS_WIDTH                      183
-#define EMMC_EXT_CSD_ERASED_MEM_CONT                181
-#define EMMC_EXT_CSD_PARTITION_CONFIG               179
-#define EMMC_EXT_CSD_BOOT_CONFIG_PROT               178
-#define EMMC_EXT_CSD_BOOT_BUS_WIDTH                 177
-#define EMMC_EXT_CSD_ERASE_GROUP_DEF                175
-#define EMMC_EXT_CSD_BOOT_WP                        173
-#define EMMC_EXT_CSD_USER_WP                        171
-#define EMMC_EXT_CSD_FW_CONFIG                      169
-#define EMMC_EXT_CSD_RPMB_SIZE_MULT                 168
-#define EMMC_EXT_CSD_RST_n_FUNCTION                 162
-#define EMMC_EXT_CSD_PARTITIONING_SUPPORT           160
-#define EMMC_EXT_CSD_MAX_ENH_SIZE_MULT              159
-#define EMMC_EXT_CSD_PARTITIONS_ATTRIBUTE           156
-#define EMMC_EXT_CSD_PARTITION_SETTING_COMPLETED    155
-#define EMMC_EXT_CSD_GP_SIZE_MULT                   154
-#define EMMC_EXT_CSD_ENH_SIZE_MULT                  142
-#define EMMC_EXT_CSD_ENH_START_ADDR                 139
-#define EMMC_EXT_CSD_SEC_BAD_BLK_MGMNT              134
-
-#define EMMC_EXT_CSD_CARD_TYPE_26MHZ                0x01
-#define EMMC_EXT_CSD_CARD_TYPE_52MHZ                0x02
-#define EMMC_EXT_CSD_CARD_TYPE_DDR_52MHZ_12V        0x04
-#define EMMC_EXT_CSD_CARD_TYPE_DDR_52MHZ_18V        0x08
-#define EMMC_EXT_CSD_CARD_TYPE_52MHZ_MASK           0x0e
-
-/** SWITCH (CMD6) argument */
-#define	EXTCSD_ACCESS_BYTE	(BIT25|BIT24)
-#define	EXTCSD_SET_BITS		BIT24
-
-#define	HS_TIMING_ADD		(185<<16)	/* H'b9 */
-#define	HS_TIMING_1			(1<<8)
-#define	HS_TIMING_HS200		(2<<8)
-#define	HS_TIMING_HS400		(3<<8)
-
-#define	BUS_WIDTH_ADD		(183<<16)	/* H'b7 */
-#define	BUS_WIDTH_1			(0<<8)
-#define	BUS_WIDTH_4			(1<<8)
-#define	BUS_WIDTH_8			(2<<8)
-#define	BUS_WIDTH_4DDR		(5<<8)
-#define	BUS_WIDTH_8DDR		(6<<8)
-
-#define EMMC_SWITCH_HS_TIMING           (EXTCSD_ACCESS_BYTE|HS_TIMING_ADD|HS_TIMING_1)		/**< H'03b90100 */
-#define	EMMC_SWITCH_HS_TIMING_OFF	    (EXTCSD_ACCESS_BYTE|HS_TIMING_ADD)					/**< H'03b90000 */
-
-#define EMMC_SWITCH_BUS_WIDTH_1         (EXTCSD_ACCESS_BYTE|BUS_WIDTH_ADD|BUS_WIDTH_1)		/**< H'03b70000 */
-#define EMMC_SWITCH_BUS_WIDTH_4         (EXTCSD_ACCESS_BYTE|BUS_WIDTH_ADD|BUS_WIDTH_4)		/**< H'03b70100 */
-#define EMMC_SWITCH_BUS_WIDTH_8         (EXTCSD_ACCESS_BYTE|BUS_WIDTH_ADD|BUS_WIDTH_8)		/**< H'03b70200 */
-#define	EMMC_SWITCH_BUS_WIDTH_4DDR      (EXTCSD_ACCESS_BYTE|BUS_WIDTH_ADD|BUS_WIDTH_4DDR)	/**< H'03b70500 */
-#define	EMMC_SWITCH_BUS_WIDTH_8DDR      (EXTCSD_ACCESS_BYTE|BUS_WIDTH_ADD|BUS_WIDTH_8DDR)	/**< H'03b70600 */
-#define EMMC_SWITCH_PARTITION_CONFIG    0x03B30000UL	/**< Partition config = 0x00 */
-
-#define TIMING_HIGH_SPEED					1UL
-#define EMMC_BOOT_PARTITION_EN_MASK	0x38U
-#define EMMC_BOOT_PARTITION_EN_SHIFT	3U
-
-/** Bus width */
-#define EMMC_BUSWIDTH_1BIT              CE_CMD_SET_DATW_1BIT
-#define EMMC_BUSWIDTH_4BIT              CE_CMD_SET_DATW_4BIT
-#define EMMC_BUSWIDTH_8BIT              CE_CMD_SET_DATW_8BIT
-
-/** for st_mmc_base */
-#define EMMC_MAX_RESPONSE_LENGTH        17
-#define EMMC_MAX_CID_LENGTH             16
-#define EMMC_MAX_CSD_LENGTH             16
-#define EMMC_MAX_EXT_CSD_LENGTH         512U
-#define EMMC_RES_REG_ALIGNED            4U
-#define EMMC_BUF_REG_ALIGNED            8U
-
-/** @brief for TAAC mask
- */
-#define TAAC_TIME_UNIT_MASK         (0x07)
-#define TAAC_MULTIPLIER_FACTOR_MASK (0x0F)
-
-/* ********************** STRUCTURES, TYPE DEFINITIONS ********************* */
-
-/** @brief Partition id
- */
-typedef enum {
-	PARTITION_ID_USER = 0x0,    /**< User Area */
-	PARTITION_ID_BOOT_1 = 0x1,  /**< boot partition 1 */
-	PARTITION_ID_BOOT_2 = 0x2,  /**< boot partition 2 */
-	PARTITION_ID_RPMB = 0x3,    /**< Replay Protected Memory Block */
-	PARTITION_ID_GP_1 = 0x4,    /**< General Purpose partition 1 */
-	PARTITION_ID_GP_2 = 0x5,    /**< General Purpose partition 2 */
-	PARTITION_ID_GP_3 = 0x6,    /**< General Purpose partition 3 */
-	PARTITION_ID_GP_4 = 0x7,    /**< General Purpose partition 4 */
-	PARTITION_ID_MASK = 0x7	    /**< [2:0] */
-} EMMC_PARTITION_ID;
-
-/** @brief card state in R1 response [12:9]
- */
-typedef enum {
-	EMMC_R1_STATE_IDLE = 0,
-	EMMC_R1_STATE_READY,
-	EMMC_R1_STATE_IDENT,
-	EMMC_R1_STATE_STBY,
-	EMMC_R1_STATE_TRAN,
-	EMMC_R1_STATE_DATA,
-	EMMC_R1_STATE_RCV,
-	EMMC_R1_STATE_PRG,
-	EMMC_R1_STATE_DIS,
-	EMMC_R1_STATE_BTST,
-	EMMC_R1_STATE_SLEP
-} EMMC_R1_STATE;
-
-typedef enum {
-	ESTATE_BEGIN = 0,
-	ESTATE_ISSUE_CMD,
-	ESTATE_NON_RESP_CMD,
-	ESTATE_RCV_RESP,
-	ESTATE_RCV_RESPONSE_BUSY,
-	ESTATE_CHECK_RESPONSE_COMPLETE,
-	ESTATE_DATA_TRANSFER,
-	ESTATE_DATA_TRANSFER_COMPLETE,
-	ESTATE_ACCESS_END,
-	ESTATE_TRANSFER_ERROR,
-	ESTATE_ERROR,
-	ESTATE_END
-} EMMC_INT_STATE;
-
-/** @brief eMMC boot driver error information
- */
-typedef struct {
-	uint16_t num;		  /**< error no */
-	uint16_t code;		  /**< error code */
-	volatile uint32_t info1;  /**< SD_INFO1 register value. (hardware dependence) */
-	volatile uint32_t info2;  /**< SD_INFO2 register value. (hardware dependence) */
-	volatile uint32_t status1;/**< SD_ERR_STS1 register value. (hardware dependence) */
-	volatile uint32_t status2;/**< SD_ERR_STS2 register value. (hardware dependence) */
-	volatile uint32_t dm_info1;/**< DM_CM_INFO1 register value. (hardware dependence) */
-	volatile uint32_t dm_info2;/**< DM_CM_INFO2 register value. (hardware dependence) */
-} st_error_info;
-
-/** @brief Command information
- */
-typedef struct {
-	HAL_MEMCARD_COMMAND cmd;	/**< Command information */
-	uint32_t arg;			  /**< argument */
-	HAL_MEMCARD_OPERATION dir;	/**< direction */
-	uint32_t hw;			  /**< H/W dependence. SD_CMD register value. */
-} st_command_info;
-
-/** @brief MMC driver base
- */
-typedef struct {
-	st_error_info error_info;	/**< error information */
-	st_command_info cmd_info;	/**< command information */
-
-	/* for data transfer */
-	uint32_t *buff_address_virtual;	   /**< Dest or Src buff */
-	uint32_t *buff_address_physical;   /**< Dest or Src buff */
-	HAL_MEMCARD_DATA_WIDTH bus_width;
-					/**< bus width */
-	uint32_t trans_size;		  /**< transfer size for this command */
-	uint32_t remain_size;		  /**< remain size for this command */
-	uint32_t response_length;	  /**< response length for this command */
-	uint32_t sector_size;		   /**< sector_size */
-
-	/* clock */
-	uint32_t base_clock;		  /**< MMC host controller clock */
-	uint32_t max_freq;		  /**< Max frequency (Card Spec)[Hz]. It changes dynamically by CSD and EXT_CSD. */
-	uint32_t request_freq;		  /**< request freq [Hz] (400K, 26MHz, 52MHz, etc) */
-	uint32_t current_freq;		  /**< current MMC clock[Hz] (the closest frequency supported by HW) */
-
-	/* state flag */
-	HAL_MEMCARD_PRESENCE_STATUS card_present;
-						/**< presence status of the memory card */
-	uint32_t card_power_enable;		  /**< True : Power ON */
-	uint32_t clock_enable;			  /**< True : Clock ON */
-	uint32_t initialize;			  /**< True : initialize complete. */
-	uint32_t access_mode;			  /**< True : sector access, FALSE : byte access */
-	uint32_t mount;				  /**< True : mount complete. */
-	uint32_t selected;			  /**< True : selected card. */
-	HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode;
-						    /**< 0: DMA, 1:PIO */
-	uint32_t image_num;			  /**< loaded ISSW image No. ISSW have copy image. */
-	EMMC_R1_STATE current_state;		/**< card state */
-	volatile uint32_t during_cmd_processing;  /**< True : during command processing */
-	volatile uint32_t during_transfer;	  /**< True : during transfer */
-	volatile uint32_t during_dma_transfer;	  /**< True : during transfer (DMA)*/
-	volatile uint32_t dma_error_flag;	  /**< True : occurred DMAC error */
-	volatile uint32_t force_terminate;	  /**< force terminate flag */
-	volatile uint32_t state_machine_blocking; /**< state machine blocking flag : True or False */
-	volatile uint32_t get_partition_access_flag;
-						  /**< True : get partition access processing */
-
-	EMMC_PARTITION_ID boot_partition_en;	/**< Boot partition */
-	EMMC_PARTITION_ID partition_access;	/**< Current access partition */
-
-	/* timeout */
-	uint32_t hs_timing;			/**< high speed */
-
-	/* timeout */
-	uint32_t data_timeout;			  /**< read and write data timeout.*/
-
-	/* retry */
-	uint32_t retries_after_fail;  /**< how many times to try after fail, for instance sending command */
-
-	/* interrupt */
-	volatile uint32_t int_event1; /**< interrupt SD_INFO1 Event */
-	volatile uint32_t int_event2;	  /**< interrupt SD_INFO2 Event */
-	volatile uint32_t dm_event1;  /**< interrupt DM_CM_INFO1 Event */
-	volatile uint32_t dm_event2;	  /**< interrupt DM_CM_INFO2 Event */
-
-	/* response */
-	uint32_t *response;	      /**< pointer to buffer for executing command. */
-	uint32_t r1_card_status;      /**< R1 response data */
-	uint32_t r3_ocr;	      /**< R3 response data */
-	uint32_t r4_resp;	      /**< R4 response data */
-	uint32_t r5_resp;	      /**< R5 response data */
-
-	uint32_t low_clock_mode_enable;
-				      /**< True : clock mode is low. (MMC clock = Max26MHz) */
-	uint32_t reserved2;
-	uint32_t reserved3;
-	uint32_t reserved4;
-
-	/* CSD registers (4byte align) */
-	uint8_t csd_data[EMMC_MAX_CSD_LENGTH]		      /**< CSD */
-	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
-	/* CID registers (4byte align) */
-	uint8_t cid_data[EMMC_MAX_CID_LENGTH]		      /**< CID */
-	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
-	/* EXT CSD registers (8byte align) */
-	uint8_t ext_csd_data[EMMC_MAX_EXT_CSD_LENGTH]	      /**< EXT_CSD */
-	    __attribute__ ((aligned(EMMC_BUF_REG_ALIGNED)));
-	/* Response registers (4byte align) */
-	uint8_t response_data[EMMC_MAX_RESPONSE_LENGTH]	      /**< other response */
-	    __attribute__ ((aligned(EMMC_RES_REG_ALIGNED)));
-} st_mmc_base;
-
-typedef int (*func) (void);
-
-/* ********************** DECLARATION OF EXTERNAL DATA ********************* */
-
-/* ************************** FUNCTION PROTOTYPES ************************** */
-uint32_t emmc_get_csd_time(void);
-
-#define MMC_DEBUG
-/* ********************************* CODE ********************************** */
-
-/* ******************************** END ************************************ */
-#endif /* EMMC_STD_H */
diff --git a/drivers/renesas/rcar/emmc/emmc_utility.c b/drivers/renesas/rcar/emmc/emmc_utility.c
deleted file mode 100644
index 39d9ede..0000000
--- a/drivers/renesas/rcar/emmc/emmc_utility.c
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_registers.h"
-#include "emmc_def.h"
-
-static const uint32_t cmd_reg_hw[EMMC_CMD_MAX + 1] = {
-	0x00000000,		/* CMD0 */
-	0x00000701,		/* CMD1 */
-	0x00000002,		/* CMD2 */
-	0x00000003,		/* CMD3 */
-	0x00000004,		/* CMD4 */
-	0x00000505,		/* CMD5 */
-	0x00000406,		/* CMD6 */
-	0x00000007,		/* CMD7 */
-	0x00001C08,		/* CMD8 */
-	0x00000009,		/* CMD9 */
-	0x0000000A,		/* CMD10 */
-	0x00000000,		/* reserved */
-	0x0000000C,		/* CMD12 */
-	0x0000000D,		/* CMD13 */
-	0x00001C0E,		/* CMD14 */
-	0x0000000F,		/* CMD15 */
-	0x00000010,		/* CMD16 */
-	0x00000011,		/* CMD17 */
-	0x00007C12,		/* CMD18 */
-	0x00000C13,		/* CMD19 */
-	0x00000000,
-	0x00001C15,		/* CMD21 */
-	0x00000000,
-	0x00000017,		/* CMD23 */
-	0x00000018,		/* CMD24 */
-	0x00006C19,		/* CMD25 */
-	0x00000C1A,		/* CMD26 */
-	0x0000001B,		/* CMD27 */
-	0x0000001C,		/* CMD28 */
-	0x0000001D,		/* CMD29 */
-	0x0000001E,		/* CMD30 */
-	0x00001C1F,		/* CMD31 */
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000423,		/* CMD35 */
-	0x00000424,		/* CMD36 */
-	0x00000000,
-	0x00000026,		/* CMD38 */
-	0x00000427,		/* CMD39 */
-	0x00000428,		/* CMD40(send cmd) */
-	0x00000000,
-	0x0000002A,		/* CMD42 */
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000C31,
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00007C35,
-	0x00006C36,
-	0x00000037,		/* CMD55 */
-	0x00000038,		/* CMD56(Read) */
-	0x00000000,
-	0x00000000,
-	0x00000000,
-	0x00000000
-};
-
-uint32_t emmc_bit_field(uint8_t *data, uint32_t top, uint32_t bottom)
-{
-	uint32_t value;
-
-	uint32_t index_top = (uint32_t) (15 - (top >> 3));
-	uint32_t index_bottom = (uint32_t) (15 - (bottom >> 3));
-
-	if (index_top == index_bottom) {
-		value = data[index_top];
-	} else if ((index_top + 1) == index_bottom) {
-		value =
-		    (uint32_t) ((data[index_top] << 8) | data[index_bottom]);
-	} else if ((index_top + 2) == index_bottom) {
-		value =
-		    (uint32_t) ((data[index_top] << 16) |
-				(data[index_top + 1] << 8) | data[index_top +
-								  2]);
-	} else {
-		value =
-		    (uint32_t) ((data[index_top] << 24) |
-				(data[index_top + 1] << 16) |
-				(data[index_top + 2] << 8) | data[index_top +
-								  3]);
-	}
-
-	value = ((value >> (bottom & 0x07)) & ((1 << (top - bottom + 1)) - 1));
-
-	return value;
-}
-
-void emmc_write_error_info(uint16_t func_no, EMMC_ERROR_CODE error_code)
-{
-
-	mmc_drv_obj.error_info.num = func_no;
-	mmc_drv_obj.error_info.code = (uint16_t) error_code;
-
-	ERROR("BL2: emmc err:func_no=0x%x code=0x%x\n", func_no, error_code);
-}
-
-void emmc_write_error_info_func_no(uint16_t func_no)
-{
-
-	mmc_drv_obj.error_info.num = func_no;
-
-	ERROR("BL2: emmc err:func_no=0x%x\n", func_no);
-}
-
-void emmc_make_nontrans_cmd(HAL_MEMCARD_COMMAND cmd, uint32_t arg)
-{
-	/* command information */
-	mmc_drv_obj.cmd_info.cmd = cmd;
-	mmc_drv_obj.cmd_info.arg = arg;
-	mmc_drv_obj.cmd_info.dir = HAL_MEMCARD_READ;
-	mmc_drv_obj.cmd_info.hw =
-	    cmd_reg_hw[cmd & HAL_MEMCARD_COMMAND_INDEX_MASK];
-
-	/* clear data transfer information */
-	mmc_drv_obj.trans_size = 0;
-	mmc_drv_obj.remain_size = 0;
-	mmc_drv_obj.buff_address_virtual = NULL;
-	mmc_drv_obj.buff_address_physical = NULL;
-
-	/* response information */
-	mmc_drv_obj.response_length = 6;
-
-	switch (mmc_drv_obj.cmd_info.cmd & HAL_MEMCARD_RESPONSE_TYPE_MASK) {
-	case HAL_MEMCARD_RESPONSE_NONE:
-		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
-		mmc_drv_obj.response_length = 0;
-		break;
-	case HAL_MEMCARD_RESPONSE_R1:
-		mmc_drv_obj.response = &mmc_drv_obj.r1_card_status;
-		break;
-	case HAL_MEMCARD_RESPONSE_R1b:
-		mmc_drv_obj.cmd_info.hw |= BIT10;	/* bit10 = R1 busy bit */
-		mmc_drv_obj.response = &mmc_drv_obj.r1_card_status;
-		break;
-	case HAL_MEMCARD_RESPONSE_R2:
-		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
-		mmc_drv_obj.response_length = 17;
-		break;
-	case HAL_MEMCARD_RESPONSE_R3:
-		mmc_drv_obj.response = &mmc_drv_obj.r3_ocr;
-		break;
-	case HAL_MEMCARD_RESPONSE_R4:
-		mmc_drv_obj.response = &mmc_drv_obj.r4_resp;
-		break;
-	case HAL_MEMCARD_RESPONSE_R5:
-		mmc_drv_obj.response = &mmc_drv_obj.r5_resp;
-		break;
-	default:
-		mmc_drv_obj.response = (uint32_t *) mmc_drv_obj.response_data;
-		break;
-	}
-}
-
-void emmc_make_trans_cmd(HAL_MEMCARD_COMMAND cmd, uint32_t arg,
-			 uint32_t *buff_address_virtual,
-			 uint32_t len,
-			 HAL_MEMCARD_OPERATION dir,
-			 HAL_MEMCARD_DATA_TRANSFER_MODE transfer_mode)
-{
-	emmc_make_nontrans_cmd(cmd, arg);	/* update common information */
-
-	/* for data transfer command */
-	mmc_drv_obj.cmd_info.dir = dir;
-	mmc_drv_obj.buff_address_virtual = buff_address_virtual;
-	mmc_drv_obj.buff_address_physical = buff_address_virtual;
-	mmc_drv_obj.trans_size = len;
-	mmc_drv_obj.remain_size = len;
-	mmc_drv_obj.transfer_mode = transfer_mode;
-}
-
-EMMC_ERROR_CODE emmc_send_idle_cmd(uint32_t arg)
-{
-	EMMC_ERROR_CODE result;
-	uint32_t freq;
-
-	/* initialize state */
-	mmc_drv_obj.mount = FALSE;
-	mmc_drv_obj.selected = FALSE;
-	mmc_drv_obj.during_transfer = FALSE;
-	mmc_drv_obj.during_cmd_processing = FALSE;
-	mmc_drv_obj.during_dma_transfer = FALSE;
-	mmc_drv_obj.dma_error_flag = FALSE;
-	mmc_drv_obj.force_terminate = FALSE;
-	mmc_drv_obj.state_machine_blocking = FALSE;
-
-	mmc_drv_obj.bus_width = HAL_MEMCARD_DATA_WIDTH_1_BIT;
-	mmc_drv_obj.max_freq = MMC_20MHZ;	/* 20MHz */
-	mmc_drv_obj.current_state = EMMC_R1_STATE_IDLE;
-
-	/* CMD0 (MMC clock is current frequency. if Data transfer mode, 20MHz or higher.) */
-	emmc_make_nontrans_cmd(CMD0_GO_IDLE_STATE, arg);	/* CMD0 */
-	result = emmc_exec_cmd(EMMC_R1_ERROR_MASK, mmc_drv_obj.response);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-
-	/* change MMC clock(400KHz) */
-	freq = MMC_400KHZ;
-	result = emmc_set_request_mmc_clock(&freq);
-	if (result != EMMC_SUCCESS) {
-		return result;
-	}
-
-	return EMMC_SUCCESS;
-}
diff --git a/drivers/renesas/rcar/iic_dvfs/iic_dvfs.c b/drivers/renesas/rcar/iic_dvfs/iic_dvfs.c
deleted file mode 100644
index 28b56c1..0000000
--- a/drivers/renesas/rcar/iic_dvfs/iic_dvfs.c
+++ /dev/null
@@ -1,569 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <lib/mmio.h>
-
-#include "rcar_def.h"
-#include "cpg_registers.h"
-#include "iic_dvfs.h"
-#include "rcar_private.h"
-
-#define DVFS_RETRY_MAX				(2U)
-
-#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_0		(0x07)
-#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_1		(0x09)
-#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_2		(0x0B)
-#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_3		(0x0E)
-#define IIC_DVFS_SET_ICCL_EXTAL_TYPE_E		(0x15)
-
-#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_0		(0x01)
-#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_1		(0x02)
-#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_2		(0x03)
-#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_3		(0x05)
-#define IIC_DVFS_SET_ICCH_EXTAL_TYPE_E		(0x07)
-
-#define CPG_BIT_SMSTPCR9_DVFS			(0x04000000)
-
-#define IIC_DVFS_REG_BASE			(0xE60B0000)
-#define IIC_DVFS_REG_ICDR			(IIC_DVFS_REG_BASE + 0x0000)
-#define IIC_DVFS_REG_ICCR			(IIC_DVFS_REG_BASE + 0x0004)
-#define IIC_DVFS_REG_ICSR			(IIC_DVFS_REG_BASE + 0x0008)
-#define IIC_DVFS_REG_ICIC			(IIC_DVFS_REG_BASE + 0x000C)
-#define IIC_DVFS_REG_ICCL			(IIC_DVFS_REG_BASE + 0x0010)
-#define IIC_DVFS_REG_ICCH			(IIC_DVFS_REG_BASE + 0x0014)
-
-#define IIC_DVFS_BIT_ICSR_BUSY			(0x10)
-#define IIC_DVFS_BIT_ICSR_AL			(0x08)
-#define IIC_DVFS_BIT_ICSR_TACK			(0x04)
-#define IIC_DVFS_BIT_ICSR_WAIT			(0x02)
-#define IIC_DVFS_BIT_ICSR_DTE			(0x01)
-
-#define IIC_DVFS_BIT_ICCR_ENABLE		(0x80)
-#define IIC_DVFS_SET_ICCR_START			(0x94)
-#define IIC_DVFS_SET_ICCR_STOP			(0x90)
-#define	IIC_DVFS_SET_ICCR_RETRANSMISSION	(0x94)
-#define	IIC_DVFS_SET_ICCR_CHANGE		(0x81)
-#define	IIC_DVFS_SET_ICCR_STOP_READ		(0xC0)
-
-#define IIC_DVFS_BIT_ICIC_TACKE			(0x04)
-#define IIC_DVFS_BIT_ICIC_WAITE			(0x02)
-#define IIC_DVFS_BIT_ICIC_DTEE			(0x01)
-
-#define	DVFS_READ_MODE				(0x01)
-#define	DVFS_WRITE_MODE				(0x00)
-
-#define IIC_DVFS_SET_DUMMY			(0x52)
-#define IIC_DVFS_SET_BUSY_LOOP			(500000000U)
-
-typedef enum {
-	DVFS_START = 0,
-	DVFS_STOP,
-	DVFS_RETRANSMIT,
-	DVFS_READ,
-	DVFS_STOP_READ,
-	DVFS_SET_SLAVE_READ,
-	DVFS_SET_SLAVE,
-	DVFS_WRITE_ADDR,
-	DVFS_WRITE_DATA,
-	DVFS_CHANGE_SEND_TO_RECIEVE,
-	DVFS_DONE,
-} DVFS_STATE_T;
-
-#define DVFS_PROCESS			(1)
-#define DVFS_COMPLETE			(0)
-#define DVFS_ERROR			(-1)
-
-#if IMAGE_BL31
-#define IIC_DVFS_FUNC(__name, ...)					\
-static int32_t 	__attribute__ ((section (".system_ram")))		\
-dvfs_ ##__name(__VA_ARGS__)
-
-#define RCAR_DVFS_API(__name, ...)					\
-int32_t __attribute__ ((section (".system_ram"))) 			\
-rcar_iic_dvfs_ ##__name(__VA_ARGS__)
-
-#else
-#define IIC_DVFS_FUNC(__name, ...) 					\
-static int32_t dvfs_ ##__name(__VA_ARGS__)
-
-#define RCAR_DVFS_API(__name, ...)					\
-int32_t rcar_iic_dvfs_ ##__name(__VA_ARGS__)
-#endif
-
-IIC_DVFS_FUNC(check_error, DVFS_STATE_T *state, uint32_t *err, uint8_t mode)
-{
-	uint8_t icsr_al = 0, icsr_tack = 0;
-	uint8_t reg, stop;
-	uint32_t i = 0;
-
-	stop = mode == DVFS_READ_MODE ? IIC_DVFS_SET_ICCR_STOP_READ :
-	    IIC_DVFS_SET_ICCR_STOP;
-
-	reg = mmio_read_8(IIC_DVFS_REG_ICSR);
-	icsr_al = (reg & IIC_DVFS_BIT_ICSR_AL) == IIC_DVFS_BIT_ICSR_AL;
-	icsr_tack = (reg & IIC_DVFS_BIT_ICSR_TACK) == IIC_DVFS_BIT_ICSR_TACK;
-
-	if (icsr_al == 0 && icsr_tack == 0)
-		return DVFS_PROCESS;
-
-	if (icsr_al) {
-		reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_AL;
-		mmio_write_8(IIC_DVFS_REG_ICSR, reg);
-
-		if (*state == DVFS_SET_SLAVE)
-			mmio_write_8(IIC_DVFS_REG_ICDR, IIC_DVFS_SET_DUMMY);
-
-		do {
-			reg = mmio_read_8(IIC_DVFS_REG_ICSR) &
-			    IIC_DVFS_BIT_ICSR_WAIT;
-		} while (reg == 0);
-
-		mmio_write_8(IIC_DVFS_REG_ICCR, stop);
-
-		reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-		mmio_write_8(IIC_DVFS_REG_ICSR, reg);
-
-		i = 0;
-		do {
-			reg = mmio_read_8(IIC_DVFS_REG_ICSR) &
-			    IIC_DVFS_BIT_ICSR_BUSY;
-			if (reg == 0)
-				break;
-
-			if (i++ > IIC_DVFS_SET_BUSY_LOOP)
-				panic();
-
-		} while (1);
-
-		mmio_write_8(IIC_DVFS_REG_ICCR, 0x00U);
-
-		(*err)++;
-		if (*err > DVFS_RETRY_MAX)
-			return DVFS_ERROR;
-
-		*state = DVFS_START;
-
-		return DVFS_PROCESS;
-
-	}
-
-	/* icsr_tack */
-	mmio_write_8(IIC_DVFS_REG_ICCR, stop);
-
-	reg = mmio_read_8(IIC_DVFS_REG_ICIC);
-	reg &= ~(IIC_DVFS_BIT_ICIC_WAITE | IIC_DVFS_BIT_ICIC_DTEE);
-	mmio_write_8(IIC_DVFS_REG_ICIC, reg);
-
-	reg = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_TACK;
-	mmio_write_8(IIC_DVFS_REG_ICSR, reg);
-
-	i = 0;
-	while ((mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_BUSY) != 0) {
-		if (i++ > IIC_DVFS_SET_BUSY_LOOP)
-			panic();
-	}
-
-	mmio_write_8(IIC_DVFS_REG_ICCR, 0);
-	(*err)++;
-
-	if (*err > DVFS_RETRY_MAX)
-		return DVFS_ERROR;
-
-	*state = DVFS_START;
-
-	return DVFS_PROCESS;
-}
-
-IIC_DVFS_FUNC(start, DVFS_STATE_T * state)
-{
-	uint8_t iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_E;
-	uint8_t icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_E;
-	int32_t result = DVFS_PROCESS;
-	uint32_t reg, lsi_product;
-	uint8_t mode;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICCR) | IIC_DVFS_BIT_ICCR_ENABLE;
-	mmio_write_8(IIC_DVFS_REG_ICCR, mode);
-
-	lsi_product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
-	if (lsi_product == PRR_PRODUCT_E3)
-		goto start;
-
-	reg = mmio_read_32(RCAR_MODEMR) & CHECK_MD13_MD14;
-	switch (reg) {
-	case MD14_MD13_TYPE_0:
-		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_0;
-		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_0;
-		break;
-	case MD14_MD13_TYPE_1:
-		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_1;
-		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_1;
-		break;
-	case MD14_MD13_TYPE_2:
-		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_2;
-		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_2;
-		break;
-	default:
-		iccl = IIC_DVFS_SET_ICCL_EXTAL_TYPE_3;
-		icch = IIC_DVFS_SET_ICCH_EXTAL_TYPE_3;
-		break;
-	}
-start:
-	mmio_write_8(IIC_DVFS_REG_ICCL, iccl);
-	mmio_write_8(IIC_DVFS_REG_ICCH, icch);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC)
-	    | IIC_DVFS_BIT_ICIC_TACKE
-	    | IIC_DVFS_BIT_ICIC_WAITE | IIC_DVFS_BIT_ICIC_DTEE;
-
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_START);
-
-	*state = DVFS_SET_SLAVE;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(set_slave, DVFS_STATE_T * state, uint32_t *err, uint8_t slave)
-{
-	uint8_t mode;
-	int32_t result;
-	uint8_t address;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
-	if (mode != IIC_DVFS_BIT_ICSR_DTE)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-
-	address = slave << 1;
-	mmio_write_8(IIC_DVFS_REG_ICDR, address);
-
-	*state = DVFS_WRITE_ADDR;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(write_addr, DVFS_STATE_T *state, uint32_t *err, uint8_t reg_addr)
-{
-	uint8_t mode;
-	int32_t result;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICDR, reg_addr);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	*state = DVFS_WRITE_DATA;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(write_data, DVFS_STATE_T *state, uint32_t *err, uint8_t reg_data)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICDR, reg_data);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	*state = DVFS_STOP;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(stop, DVFS_STATE_T *state, uint32_t *err)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_STOP);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	*state = DVFS_DONE;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(done, void)
-{
-	uint32_t i;
-
-	for (i = 0; i < IIC_DVFS_SET_BUSY_LOOP; i++) {
-		if (mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_BUSY)
-			continue;
-		goto done;
-	}
-
-	panic();
-done:
-	mmio_write_8(IIC_DVFS_REG_ICCR, 0);
-
-	return DVFS_COMPLETE;
-}
-
-IIC_DVFS_FUNC(write_reg_addr_read, DVFS_STATE_T *state, uint32_t *err,
-	uint8_t reg_addr)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICDR, reg_addr);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	*state = DVFS_RETRANSMIT;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(retransmit, DVFS_STATE_T *state, uint32_t *err)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_RETRANSMISSION);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC) | IIC_DVFS_BIT_ICIC_DTEE;
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-
-	*state = DVFS_SET_SLAVE_READ;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(set_slave_read, DVFS_STATE_T *state, uint32_t *err,
-		uint8_t slave)
-{
-	uint8_t address;
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
-	if (mode != IIC_DVFS_BIT_ICSR_DTE)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-
-	address = ((uint8_t) (slave << 1) + DVFS_READ_MODE);
-	mmio_write_8(IIC_DVFS_REG_ICDR, address);
-
-	*state = DVFS_CHANGE_SEND_TO_RECIEVE;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(change_send_to_recieve, DVFS_STATE_T *state, uint32_t *err)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_WRITE_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_CHANGE);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	*state = DVFS_STOP_READ;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(stop_read, DVFS_STATE_T *state, uint32_t *err)
-{
-	int32_t result;
-	uint8_t mode;
-
-	result = dvfs_check_error(state, err, DVFS_READ_MODE);
-	if (result == DVFS_ERROR)
-		return result;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_WAIT;
-	if (mode != IIC_DVFS_BIT_ICSR_WAIT)
-		return result;
-
-	mmio_write_8(IIC_DVFS_REG_ICCR, IIC_DVFS_SET_ICCR_STOP_READ);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & ~IIC_DVFS_BIT_ICSR_WAIT;
-	mmio_write_8(IIC_DVFS_REG_ICSR, mode);
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC) | IIC_DVFS_BIT_ICIC_DTEE;
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-
-	*state = DVFS_READ;
-
-	return result;
-}
-
-IIC_DVFS_FUNC(read, DVFS_STATE_T *state, uint8_t *reg_data)
-{
-	uint8_t mode;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICSR) & IIC_DVFS_BIT_ICSR_DTE;
-	if (mode != IIC_DVFS_BIT_ICSR_DTE)
-		return DVFS_PROCESS;
-
-	mode = mmio_read_8(IIC_DVFS_REG_ICIC) & ~IIC_DVFS_BIT_ICIC_DTEE;
-	mmio_write_8(IIC_DVFS_REG_ICIC, mode);
-
-	*reg_data = mmio_read_8(IIC_DVFS_REG_ICDR);
-	*state = DVFS_DONE;
-
-	return DVFS_PROCESS;
-}
-
-RCAR_DVFS_API(send, uint8_t slave, uint8_t reg_addr, uint8_t reg_data)
-{
-	DVFS_STATE_T state = DVFS_START;
-	int32_t result = DVFS_PROCESS;
-	uint32_t err = 0;
-
-	mstpcr_write(SCMSTPCR9, CPG_MSTPSR9, CPG_BIT_SMSTPCR9_DVFS);
-	mmio_write_8(IIC_DVFS_REG_ICCR, 0);
-again:
-	switch (state) {
-	case DVFS_START:
-		result = dvfs_start(&state);
-		break;
-	case DVFS_SET_SLAVE:
-		result = dvfs_set_slave(&state, &err, slave);
-		break;
-	case DVFS_WRITE_ADDR:
-		result = dvfs_write_addr(&state, &err, reg_addr);
-		break;
-	case DVFS_WRITE_DATA:
-		result = dvfs_write_data(&state, &err, reg_data);
-		break;
-	case DVFS_STOP:
-		result = dvfs_stop(&state, &err);
-		break;
-	case DVFS_DONE:
-		result = dvfs_done();
-		break;
-	default:
-		panic();
-		break;
-	}
-
-	if (result == DVFS_PROCESS)
-		goto again;
-
-	return result;
-}
-
-RCAR_DVFS_API(receive, uint8_t slave, uint8_t reg, uint8_t *data)
-{
-	DVFS_STATE_T state = DVFS_START;
-	int32_t result = DVFS_PROCESS;
-	uint32_t err = 0;
-
-	mstpcr_write(SCMSTPCR9, CPG_MSTPSR9, CPG_BIT_SMSTPCR9_DVFS);
-	mmio_write_8(IIC_DVFS_REG_ICCR, 0);
-again:
-	switch (state) {
-	case DVFS_START:
-		result = dvfs_start(&state);
-		break;
-	case DVFS_SET_SLAVE:
-		result = dvfs_set_slave(&state, &err, slave);
-		break;
-	case DVFS_WRITE_ADDR:
-		result = dvfs_write_reg_addr_read(&state, &err, reg);
-		break;
-	case DVFS_RETRANSMIT:
-		result = dvfs_retransmit(&state, &err);
-		break;
-	case DVFS_SET_SLAVE_READ:
-		result = dvfs_set_slave_read(&state, &err, slave);
-		break;
-	case DVFS_CHANGE_SEND_TO_RECIEVE:
-		result = dvfs_change_send_to_recieve(&state, &err);
-		break;
-	case DVFS_STOP_READ:
-		result = dvfs_stop_read(&state, &err);
-		break;
-	case DVFS_READ:
-		result = dvfs_read(&state, data);
-		break;
-	case DVFS_DONE:
-		result = dvfs_done();
-		break;
-	default:
-		panic();
-		break;
-	}
-
-	if (result == DVFS_PROCESS)
-		goto again;
-
-	return result;
-}
diff --git a/drivers/renesas/rcar/iic_dvfs/iic_dvfs.h b/drivers/renesas/rcar/iic_dvfs/iic_dvfs.h
deleted file mode 100644
index 2dec58f..0000000
--- a/drivers/renesas/rcar/iic_dvfs/iic_dvfs.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef IIC_DVFS_H
-#define IIC_DVFS_H
-
-/* PMIC slave */
-#define PMIC			(0x30)
-#define	BKUP_MODE_CNT		(0x20)
-#define	DVFS_SET_VID		(0x54)
-#define	REG_KEEP10		(0x79)
-
-/* EEPROM slave */
-#define EEPROM			(0x50)
-#define	BOARD_ID		(0x70)
-
-int32_t rcar_iic_dvfs_receive(uint8_t slave, uint8_t reg, uint8_t *data);
-int32_t rcar_iic_dvfs_send(uint8_t slave, uint8_t regr, uint8_t data);
-
-#endif /* IIC_DVFS_H */
diff --git a/drivers/renesas/rcar/io/io_emmcdrv.c b/drivers/renesas/rcar/io/io_emmcdrv.c
deleted file mode 100644
index 84240d2..0000000
--- a/drivers/renesas/rcar/io/io_emmcdrv.c
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <string.h>
-
-#include <common/debug.h>
-#include <drivers/io/io_driver.h>
-#include <drivers/io/io_storage.h>
-
-#include "io_common.h"
-#include "io_emmcdrv.h"
-#include "io_private.h"
-#include "emmc_config.h"
-#include "emmc_hal.h"
-#include "emmc_std.h"
-#include "emmc_def.h"
-
-static int32_t emmcdrv_dev_open(const uintptr_t spec __attribute__ ((unused)),
-				io_dev_info_t **dev_info);
-static int32_t emmcdrv_dev_close(io_dev_info_t *dev_info);
-
-typedef struct {
-	uint32_t in_use;
-	uintptr_t base;
-	signed long long file_pos;
-	EMMC_PARTITION_ID partition;
-} file_state_t;
-
-static file_state_t current_file = { 0 };
-
-static EMMC_PARTITION_ID emmcdrv_bootpartition = PARTITION_ID_USER;
-
-static io_type_t device_type_emmcdrv(void)
-{
-	return IO_TYPE_MEMMAP;
-}
-
-static int32_t emmcdrv_block_seek(io_entity_t *entity, int32_t mode,
-				  signed long long offset)
-{
-	if (mode != IO_SEEK_SET)
-		return IO_FAIL;
-
-	((file_state_t *) entity->info)->file_pos = offset;
-
-	return IO_SUCCESS;
-}
-
-static int32_t emmcdrv_block_read(io_entity_t *entity, uintptr_t buffer,
-				  size_t length, size_t *length_read)
-{
-	file_state_t *fp = (file_state_t *) entity->info;
-	uint32_t sector_add, sector_num, emmc_dma = 0;
-	int32_t result = IO_SUCCESS;
-
-	sector_add = current_file.file_pos >> EMMC_SECTOR_SIZE_SHIFT;
-	sector_num = (length + EMMC_SECTOR_SIZE - 1U) >> EMMC_SECTOR_SIZE_SHIFT;
-
-	NOTICE("BL2: Load dst=0x%lx src=(p:%d)0x%llx(%d) len=0x%lx(%d)\n",
-	       buffer,
-	       current_file.partition, current_file.file_pos,
-	       sector_add, length, sector_num);
-
-	if ((buffer + length - 1U) <= (uintptr_t)UINT32_MAX)
-		emmc_dma = LOADIMAGE_FLAGS_DMA_ENABLE;
-
-	if (emmc_read_sector((uint32_t *) buffer, sector_add, sector_num,
-			     emmc_dma) != EMMC_SUCCESS)
-		result = IO_FAIL;
-
-	*length_read = length;
-	fp->file_pos += (signed long long)length;
-
-	return result;
-}
-
-static int32_t emmcdrv_block_open(io_dev_info_t *dev_info,
-				  const uintptr_t spec, io_entity_t *entity)
-{
-	const io_drv_spec_t *block_spec = (io_drv_spec_t *) spec;
-
-	if (current_file.in_use != 0U) {
-		WARN("mmc_block: Only one open spec at a time\n");
-		return IO_RESOURCES_EXHAUSTED;
-	}
-
-	current_file.file_pos = 0;
-	current_file.in_use = 1;
-
-	if (emmcdrv_bootpartition == PARTITION_ID_USER) {
-		emmcdrv_bootpartition = mmc_drv_obj.boot_partition_en;
-		if ((PARTITION_ID_BOOT_1 == emmcdrv_bootpartition) ||
-		    (PARTITION_ID_BOOT_2 == emmcdrv_bootpartition)) {
-			current_file.partition = emmcdrv_bootpartition;
-
-			NOTICE("BL2: eMMC boot from partition %d\n",
-			       emmcdrv_bootpartition);
-			goto done;
-		}
-		return IO_FAIL;
-	}
-
-	if ((PARTITION_ID_USER == block_spec->partition) ||
-	    (PARTITION_ID_BOOT_1 == block_spec->partition) ||
-	    (PARTITION_ID_BOOT_2 == block_spec->partition))
-		current_file.partition = block_spec->partition;
-	else
-		current_file.partition = emmcdrv_bootpartition;
-
-done:
-	if (emmc_select_partition(current_file.partition) != EMMC_SUCCESS)
-		return IO_FAIL;
-
-	entity->info = (uintptr_t) &current_file;
-
-	return IO_SUCCESS;
-}
-
-static int32_t emmcdrv_block_close(io_entity_t *entity)
-{
-	memset((void *)&current_file, 0, sizeof(current_file));
-	entity->info = 0U;
-
-	return IO_SUCCESS;
-}
-
-static const io_dev_funcs_t emmcdrv_dev_funcs = {
-	.type = &device_type_emmcdrv,
-	.open = &emmcdrv_block_open,
-	.seek = &emmcdrv_block_seek,
-	.size = NULL,
-	.read = &emmcdrv_block_read,
-	.write = NULL,
-	.close = &emmcdrv_block_close,
-	.dev_init = NULL,
-	.dev_close = &emmcdrv_dev_close
-};
-
-static const io_dev_info_t emmcdrv_dev_info = {
-	.funcs = &emmcdrv_dev_funcs,
-	.info = (uintptr_t) 0
-};
-
-static const io_dev_connector_t emmcdrv_dev_connector = {
-	&emmcdrv_dev_open,
-};
-
-static int32_t emmcdrv_dev_open(const uintptr_t spec __attribute__ ((unused)),
-				io_dev_info_t **dev_info)
-{
-	*dev_info = (io_dev_info_t *) &emmcdrv_dev_info;
-
-	return IO_SUCCESS;
-}
-
-static int32_t emmcdrv_dev_close(io_dev_info_t *dev_info)
-{
-	return IO_SUCCESS;
-}
-
-int32_t rcar_register_io_dev_emmcdrv(const io_dev_connector_t **dev_con)
-{
-	int32_t rc;
-
-	rc = io_register_device(&emmcdrv_dev_info);
-	if (rc == IO_SUCCESS)
-		*dev_con = &emmcdrv_dev_connector;
-
-	return rc;
-}
diff --git a/drivers/renesas/rcar/io/io_memdrv.c b/drivers/renesas/rcar/io/io_memdrv.c
deleted file mode 100644
index 7e8c1d3..0000000
--- a/drivers/renesas/rcar/io/io_memdrv.c
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <string.h>
-
-#include <common/debug.h>
-#include <drivers/io/io_driver.h>
-#include <drivers/io/io_storage.h>
-
-#include "io_common.h"
-#include "io_private.h"
-#include "io_memdrv.h"
-#include "rcar_def.h"
-
-extern void rcar_dma_exec(uintptr_t dst, uint32_t src, uint32_t len);
-
-static int32_t memdrv_dev_open(const uintptr_t dev __attribute__ ((unused)),
-			       io_dev_info_t **dev_info);
-static int32_t memdrv_dev_close(io_dev_info_t *dev_info);
-
-/* As we need to be able to keep state for seek, only one file can be open
- * at a time. Make this a structure and point to the entity->info. When we
- * can malloc memory we can change this to support more open files.
- */
-typedef struct {
-	uint32_t in_use;
-	uintptr_t base;
-	signed long long file_pos;
-} file_state_t;
-
-static file_state_t current_file = { 0 };
-
-static io_type_t device_type_memdrv(void)
-{
-	return IO_TYPE_MEMMAP;
-}
-
-static int32_t memdrv_block_open(io_dev_info_t *dev_info, const uintptr_t spec,
-				 io_entity_t *entity)
-{
-	const io_drv_spec_t *block_spec = (io_drv_spec_t *) spec;
-
-	/* Since we need to track open state for seek() we only allow one open
-	 * spec at a time. When we have dynamic memory we can malloc and set
-	 * entity->info.
-	 */
-	if (current_file.in_use != 0U)
-		return IO_RESOURCES_EXHAUSTED;
-
-	/* File cursor offset for seek and incremental reads etc. */
-	current_file.base = block_spec->offset;
-	current_file.file_pos = 0;
-	current_file.in_use = 1;
-
-	entity->info = (uintptr_t) &current_file;
-
-	return IO_SUCCESS;
-}
-
-static int32_t memdrv_block_seek(io_entity_t *entity, int32_t mode,
-				 signed long long offset)
-{
-	if (mode != IO_SEEK_SET)
-		return IO_FAIL;
-
-	((file_state_t *) entity->info)->file_pos = offset;
-
-	return IO_SUCCESS;
-}
-
-static int32_t memdrv_block_read(io_entity_t *entity, uintptr_t buffer,
-				 size_t length, size_t *cnt)
-{
-	file_state_t *fp;
-
-	fp = (file_state_t *) entity->info;
-
-	NOTICE("BL2: dst=0x%lx src=0x%llx len=%ld(0x%lx)\n",
-	       buffer, (unsigned long long)fp->base +
-	       (unsigned long long)fp->file_pos, length, length);
-
-	if (FLASH_MEMORY_SIZE < (fp->file_pos + (signed long long)length)) {
-		ERROR("BL2: check load image (source address)\n");
-		return IO_FAIL;
-	}
-
-	rcar_dma_exec(buffer, fp->base + (uintptr_t)fp->file_pos, length);
-	fp->file_pos += (signed long long)length;
-	*cnt = length;
-
-	return IO_SUCCESS;
-}
-
-static int32_t memdrv_block_close(io_entity_t *entity)
-{
-	entity->info = 0U;
-
-	memset((void *)&current_file, 0, sizeof(current_file));
-
-	return IO_SUCCESS;
-}
-
-static const io_dev_funcs_t memdrv_dev_funcs = {
-	.type = &device_type_memdrv,
-	.open = &memdrv_block_open,
-	.seek = &memdrv_block_seek,
-	.size = NULL,
-	.read = &memdrv_block_read,
-	.write = NULL,
-	.close = &memdrv_block_close,
-	.dev_init = NULL,
-	.dev_close = &memdrv_dev_close,
-};
-
-static const io_dev_info_t memdrv_dev_info = {
-	.funcs = &memdrv_dev_funcs,
-	.info = 0,
-};
-
-static const io_dev_connector_t memdrv_dev_connector = {
-	.dev_open = &memdrv_dev_open
-};
-
-static int32_t memdrv_dev_open(const uintptr_t dev __attribute__ ((unused)),
-			       io_dev_info_t **dev_info)
-{
-	*dev_info = (io_dev_info_t *) &memdrv_dev_info;
-
-	return IO_SUCCESS;
-}
-
-static int32_t memdrv_dev_close(io_dev_info_t *dev_info)
-{
-	return IO_SUCCESS;
-}
-
-int32_t rcar_register_io_dev_memdrv(const io_dev_connector_t **dev_con)
-{
-	int32_t result;
-
-	result = io_register_device(&memdrv_dev_info);
-	if (result == IO_SUCCESS)
-		*dev_con = &memdrv_dev_connector;
-
-	return result;
-}
diff --git a/drivers/renesas/rcar/io/io_rcar.c b/drivers/renesas/rcar/io/io_rcar.c
deleted file mode 100644
index b82c510..0000000
--- a/drivers/renesas/rcar/io/io_rcar.c
+++ /dev/null
@@ -1,641 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <errno.h>
-#include <stdint.h>
-#include <string.h>
-
-#include <platform_def.h>
-
-#include <arch_helpers.h>
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/auth/auth_mod.h>
-#include <drivers/io/io_driver.h>
-#include <drivers/io/io_storage.h>
-#include <lib/mmio.h>
-#include <plat/common/platform.h>
-#include <tools_share/firmware_image_package.h>
-#include <tools_share/uuid.h>
-
-#include "io_rcar.h"
-#include "io_common.h"
-#include "io_private.h"
-
-extern int32_t plat_get_drv_source(uint32_t id, uintptr_t *dev,
-				   uintptr_t *image_spec);
-
-static int32_t rcar_dev_open(const uintptr_t dev_spec __attribute__ ((unused)),
-			     io_dev_info_t **dev_info);
-static int32_t rcar_dev_close(io_dev_info_t *dev_info);
-
-typedef struct {
-	const int32_t name;
-	const uint32_t offset;
-	const uint32_t attr;
-} plat_rcar_name_offset_t;
-
-typedef struct {
-	/* Put position above the struct to allow {0} on static init.
-	 * It is a workaround for a known bug in GCC
-	 * http://gcc.gnu.org/bugzilla/show_bug.cgi?id=53119
-	 */
-	uint32_t position;
-	uint32_t no_load;
-	uintptr_t offset;
-	uint32_t size;
-	uintptr_t dst;
-	uintptr_t partition;	/* for eMMC */
-	/* RCAR_EMMC_PARTITION_BOOT_0 */
-	/* RCAR_EMMC_PARTITION_BOOT_1 */
-	/* RCAR_EMMC_PARTITION_USER   */
-} file_state_t;
-
-#define RCAR_GET_FLASH_ADR(a, b)	((uint32_t)((0x40000U * (a)) + (b)))
-#define RCAR_ATTR_SET_CALCADDR(a)	((a) & 0xF)
-#define RCAR_ATTR_SET_ISNOLOAD(a)	(((a) & 0x1) << 16U)
-#define RCAR_ATTR_SET_CERTOFF(a)	(((a) & 0xF) << 8U)
-#define RCAR_ATTR_SET_ALL(a, b, c)	((uint32_t)(RCAR_ATTR_SET_CALCADDR(a) |\
-					RCAR_ATTR_SET_ISNOLOAD(b) | 	\
-					RCAR_ATTR_SET_CERTOFF(c)))
-
-#define RCAR_ATTR_GET_CALCADDR(a)	((a) & 0xFU)
-#define RCAR_ATTR_GET_ISNOLOAD(a)	(((a) >> 16) & 0x1U)
-#define RCAR_ATTR_GET_CERTOFF(a)	((uint32_t)(((a) >> 8) & 0xFU))
-
-#define RCAR_MAX_BL3X_IMAGE		(8U)
-#define RCAR_SECTOR6_CERT_OFFSET	(0x400U)
-#define RCAR_SDRAM_certESS		(0x43F00000U)
-#define RCAR_CERT_SIZE			(0x800U)
-#define RCAR_CERT_INFO_SIZE_OFFSET	(0x264U)
-#define RCAR_CERT_INFO_DST_OFFSET	(0x154U)
-#define RCAR_CERT_INFO_SIZE_OFFSET1	(0x364U)
-#define RCAR_CERT_INFO_DST_OFFSET1	(0x1D4U)
-#define RCAR_CERT_INFO_SIZE_OFFSET2	(0x464U)
-#define RCAR_CERT_INFO_DST_OFFSET2	(0x254U)
-#define RCAR_CERT_LOAD			(1U)
-
-#define RCAR_FLASH_CERT_HEADER		RCAR_GET_FLASH_ADR(6U, 0U)
-#define RCAR_EMMC_CERT_HEADER		(0x00030000U)
-
-#define RCAR_COUNT_LOAD_BL33		(2U)
-#define RCAR_COUNT_LOAD_BL33X		(3U)
-
-static const plat_rcar_name_offset_t name_offset[] = {
-	{BL31_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(0, 0, 0)},
-
-	/* BL3-2 is optional in the platform */
-	{BL32_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(1, 0, 1)},
-	{BL33_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(2, 0, 2)},
-	{BL332_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(3, 0, 3)},
-	{BL333_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(4, 0, 4)},
-	{BL334_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(5, 0, 5)},
-	{BL335_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(6, 0, 6)},
-	{BL336_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(7, 0, 7)},
-	{BL337_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(8, 0, 8)},
-	{BL338_IMAGE_ID, 0U, RCAR_ATTR_SET_ALL(9, 0, 9)},
-};
-
-#if TRUSTED_BOARD_BOOT
-static const plat_rcar_name_offset_t cert_offset[] = {
-	/* Certificates */
-	{TRUSTED_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
-	{SOC_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
-	{TRUSTED_OS_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
-	{NON_TRUSTED_FW_KEY_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
-	{SOC_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 0)},
-	{TRUSTED_OS_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 1)},
-	{NON_TRUSTED_FW_CONTENT_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 2)},
-	{BL332_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 3)},
-	{BL333_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 4)},
-	{BL334_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 5)},
-	{BL335_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 6)},
-	{BL336_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 7)},
-	{BL337_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 8)},
-	{BL338_CERT_ID, 0U, RCAR_ATTR_SET_ALL(0, 1, 9)},
-};
-#endif /* TRUSTED_BOARD_BOOT */
-
-static file_state_t current_file = { 0 };
-
-static uintptr_t rcar_handle, rcar_spec;
-static uint64_t rcar_image_header[RCAR_MAX_BL3X_IMAGE + 2U] = { 0U };
-static uint64_t rcar_image_header_prttn[RCAR_MAX_BL3X_IMAGE + 2U] = { 0U };
-static uint64_t rcar_image_number = { 0U };
-static uint32_t rcar_cert_load = { 0U };
-
-static io_type_t device_type_rcar(void)
-{
-	return IO_TYPE_FIRMWARE_IMAGE_PACKAGE;
-}
-
-int32_t rcar_get_certificate(const int32_t name, uint32_t *cert)
-{
-#if TRUSTED_BOARD_BOOT
-	int32_t i;
-	for (i = 0; i < ARRAY_SIZE(cert_offset); i++) {
-		if (name != cert_offset[i].name)
-			continue;
-
-		*cert = RCAR_CERT_SIZE;
-		*cert *= RCAR_ATTR_GET_CERTOFF(cert_offset[i].attr);
-		*cert += RCAR_SDRAM_certESS;
-		return 0;
-	}
-#endif
-	return -EINVAL;
-}
-
-static int32_t file_to_offset(const int32_t name, uintptr_t *offset,
-			      uint32_t *cert, uint32_t *no_load,
-			      uintptr_t *partition)
-{
-	uint32_t addr;
-	int32_t i;
-
-	for (i = 0; i < ARRAY_SIZE(name_offset); i++) {
-		if (name != name_offset[i].name)
-			continue;
-
-		addr = RCAR_ATTR_GET_CALCADDR(name_offset[i].attr);
-		if (rcar_image_number + 2 < addr)
-			continue;
-
-		*offset = rcar_image_header[addr];
-		*cert = RCAR_CERT_SIZE;
-		*cert *= RCAR_ATTR_GET_CERTOFF(name_offset[i].attr);
-		*cert += RCAR_SDRAM_certESS;
-		*no_load = RCAR_ATTR_GET_ISNOLOAD(name_offset[i].attr);
-		*partition = rcar_image_header_prttn[addr];
-		return IO_SUCCESS;
-	}
-
-#if TRUSTED_BOARD_BOOT
-	for (i = 0; i < ARRAY_SIZE(cert_offset); i++) {
-		if (name != cert_offset[i].name)
-			continue;
-
-		*no_load = RCAR_ATTR_GET_ISNOLOAD(cert_offset[i].attr);
-		*partition = 0U;
-		*offset = 0U;
-		*cert = 0U;
-		return IO_SUCCESS;
-	}
-#endif
-	return -EINVAL;
-}
-
-#define RCAR_BOOT_KEY_CERT_NEW	(0xE6300F00U)
-#define	RCAR_CERT_MAGIC_NUM	(0xE291F358U)
-
-void rcar_read_certificate(uint64_t cert, uint32_t *len, uintptr_t *dst)
-{
-	uint32_t seed, val, info_1, info_2;
-	uintptr_t size, dsth, dstl;
-
-	cert &= 0xFFFFFFFFU;
-
-	seed = mmio_read_32(RCAR_BOOT_KEY_CERT_NEW);
-	val = mmio_read_32(RCAR_BOOT_KEY_CERT_NEW + 0xC);
-	info_1 = (val >> 18) & 0x3U;
-	val = mmio_read_32(cert + 0xC);
-	info_2 = (val >> 21) & 0x3;
-
-	if (seed == RCAR_CERT_MAGIC_NUM) {
-		if (info_1 != 1) {
-			ERROR("BL2: Cert is invalid.\n");
-			*dst = 0;
-			*len = 0;
-			return;
-		}
-
-		if (info_2 > 2) {
-			ERROR("BL2: Cert is invalid.\n");
-			*dst = 0;
-			*len = 0;
-			return;
-		}
-
-		switch (info_2) {
-		case 2:
-			size = cert + RCAR_CERT_INFO_SIZE_OFFSET2;
-			dstl = cert + RCAR_CERT_INFO_DST_OFFSET2;
-			break;
-		case 1:
-			size = cert + RCAR_CERT_INFO_SIZE_OFFSET1;
-			dstl = cert + RCAR_CERT_INFO_DST_OFFSET1;
-			break;
-		case 0:
-			size = cert + RCAR_CERT_INFO_SIZE_OFFSET;
-			dstl = cert + RCAR_CERT_INFO_DST_OFFSET;
-			break;
-		}
-
-		*len = mmio_read_32(size) * 4U;
-		dsth = dstl + 4U;
-		*dst = ((uintptr_t) mmio_read_32(dsth) << 32) +
-		    ((uintptr_t) mmio_read_32(dstl));
-		return;
-	}
-
-	size = cert + RCAR_CERT_INFO_SIZE_OFFSET;
-	*len = mmio_read_32(size) * 4U;
-	dstl = cert + RCAR_CERT_INFO_DST_OFFSET;
-	dsth = dstl + 4U;
-	*dst = ((uintptr_t) mmio_read_32(dsth) << 32) +
-	    ((uintptr_t) mmio_read_32(dstl));
-}
-
-static int32_t check_load_area(uintptr_t dst, uintptr_t len)
-{
-	uint32_t legacy = dst + len <= UINT32_MAX - 1 ? 1 : 0;
-	uintptr_t dram_start, dram_end;
-	uintptr_t prot_start, prot_end;
-	int32_t result = IO_SUCCESS;
-
-	dram_start = legacy ? DRAM1_BASE : DRAM_40BIT_BASE;
-
-	dram_end = legacy ? DRAM1_BASE + DRAM1_SIZE :
-	    DRAM_40BIT_BASE + DRAM_40BIT_SIZE;
-
-	prot_start = legacy ? DRAM_PROTECTED_BASE : DRAM_40BIT_PROTECTED_BASE;
-
-	prot_end = prot_start + DRAM_PROTECTED_SIZE;
-
-	if (dst < dram_start || dst > dram_end - len) {
-		ERROR("BL2: dst address is on the protected area.\n");
-		result = IO_FAIL;
-		goto done;
-	}
-
-	/* load image is within SDRAM protected area */
-	if (dst >= prot_start && dst < prot_end) {
-		ERROR("BL2: dst address is on the protected area.\n");
-		result = IO_FAIL;
-	}
-
-	if (dst < prot_start && dst > prot_start - len) {
-		ERROR("BL2: loaded data is on the protected area.\n");
-		result = IO_FAIL;
-	}
-done:
-	if (result == IO_FAIL)
-		ERROR("BL2: Out of range : dst=0x%lx len=0x%lx\n", dst, len);
-
-	return result;
-}
-
-static int32_t load_bl33x(void)
-{
-	static int32_t loaded = IO_NOT_SUPPORTED;
-	uintptr_t dst, partition, handle;
-	uint32_t noload, cert, len, i;
-	uintptr_t offset;
-	int32_t rc;
-	size_t cnt;
-	const int32_t img[] = {
-		BL33_IMAGE_ID,
-		BL332_IMAGE_ID,
-		BL333_IMAGE_ID,
-		BL334_IMAGE_ID,
-		BL335_IMAGE_ID,
-		BL336_IMAGE_ID,
-		BL337_IMAGE_ID,
-		BL338_IMAGE_ID
-	};
-
-	if (loaded != IO_NOT_SUPPORTED)
-		return loaded;
-
-	for (i = 1; i < rcar_image_number; i++) {
-		rc = file_to_offset(img[i], &offset, &cert, &noload,
-				    &partition);
-		if (rc != IO_SUCCESS) {
-			WARN("load_bl33x: failed to get offset\n");
-			loaded = IO_FAIL;
-			return loaded;
-		}
-
-		rcar_read_certificate((uint64_t) cert, &len, &dst);
-		((io_drv_spec_t *) rcar_spec)->partition = partition;
-
-		rc = io_open(rcar_handle, rcar_spec, &handle);
-		if (rc != IO_SUCCESS) {
-			WARN("Failed to open FIP (%i)\n", rc);
-			loaded = IO_FAIL;
-			return loaded;
-		}
-
-		rc = io_seek(handle, IO_SEEK_SET, offset);
-		if (rc != IO_SUCCESS) {
-			WARN("load_bl33x: failed to seek\n");
-			loaded = IO_FAIL;
-			return loaded;
-		}
-
-		rc = check_load_area(dst, len);
-		if (rc != IO_SUCCESS) {
-			WARN("load_bl33x: check load area\n");
-			loaded = IO_FAIL;
-			return loaded;
-		}
-
-		rc = io_read(handle, dst, len, &cnt);
-		if (rc != IO_SUCCESS) {
-			WARN("load_bl33x: failed to read\n");
-			loaded = IO_FAIL;
-			return loaded;
-		}
-#if TRUSTED_BOARD_BOOT
-		rc = auth_mod_verify_img(img[i], (void *)dst, len);
-		if (rc) {
-			memset((void *)dst, 0x00, len);
-			loaded = IO_FAIL;
-			return loaded;
-		}
-#endif
-		io_close(handle);
-	}
-
-	loaded = IO_SUCCESS;
-
-	return loaded;
-}
-
-static int32_t rcar_dev_init(io_dev_info_t *dev_info, const uintptr_t name)
-{
-	uint64_t header[64] __aligned(FLASH_TRANS_SIZE_UNIT) = {
-	0};
-	uintptr_t handle;
-	ssize_t offset;
-	uint32_t i;
-	int32_t rc;
-	size_t cnt;
-
-	/* Obtain a reference to the image by querying the platform layer */
-	rc = plat_get_drv_source(name, &rcar_handle, &rcar_spec);
-	if (rc != IO_SUCCESS) {
-		WARN("Failed to obtain reference to img %ld (%i)\n", name, rc);
-		return IO_FAIL;
-	}
-
-	if (RCAR_CERT_LOAD == rcar_cert_load)
-		return IO_SUCCESS;
-
-	rc = io_open(rcar_handle, rcar_spec, &handle);
-	if (rc != IO_SUCCESS) {
-		WARN("Failed to access img %ld (%i)\n", name, rc);
-		return IO_FAIL;
-	}
-
-	/* get start address list   */
-	/* [0] address num          */
-	/* [1] BL33-1 image address */
-	/* [2] BL33-2 image address */
-	/* [3] BL33-3 image address */
-	/* [4] BL33-4 image address */
-	/* [5] BL33-5 image address */
-	/* [6] BL33-6 image address */
-	/* [7] BL33-7 image address */
-	/* [8] BL33-8 image address */
-	offset = name == EMMC_DEV_ID ? RCAR_EMMC_CERT_HEADER :
-	    RCAR_FLASH_CERT_HEADER;
-	rc = io_seek(handle, IO_SEEK_SET, offset);
-	if (rc != IO_SUCCESS) {
-		WARN("Firmware Image Package header failed to seek\n");
-		goto error;
-	}
-#if RCAR_BL2_DCACHE == 1
-	inv_dcache_range((uint64_t) header, sizeof(header));
-#endif
-	rc = io_read(handle, (uintptr_t) &header, sizeof(header), &cnt);
-	if (rc != IO_SUCCESS) {
-		WARN("Firmware Image Package header failed to read\n");
-		goto error;
-	}
-
-	rcar_image_number = header[0];
-	for (i = 0; i < rcar_image_number + 2; i++) {
-		rcar_image_header[i] = header[i * 2 + 1];
-		rcar_image_header_prttn[i] = header[i * 2 + 2];
-	}
-
-	if (rcar_image_number == 0 || rcar_image_number > RCAR_MAX_BL3X_IMAGE) {
-		WARN("Firmware Image Package header check failed.\n");
-		goto error;
-	}
-
-	rc = io_seek(handle, IO_SEEK_SET, offset + RCAR_SECTOR6_CERT_OFFSET);
-	if (rc != IO_SUCCESS) {
-		WARN("Firmware Image Package header failed to seek cert\n");
-		goto error;
-	}
-#if RCAR_BL2_DCACHE == 1
-	inv_dcache_range(RCAR_SDRAM_certESS,
-			 RCAR_CERT_SIZE * (2 + rcar_image_number));
-#endif
-	rc = io_read(handle, RCAR_SDRAM_certESS,
-		     RCAR_CERT_SIZE * (2 + rcar_image_number), &cnt);
-	if (rc != IO_SUCCESS) {
-		WARN("cert file read error.\n");
-		goto error;
-	}
-
-	rcar_cert_load = RCAR_CERT_LOAD;
-error:
-
-	if (rc != IO_SUCCESS)
-		rc = IO_FAIL;
-
-	io_close(handle);
-
-	return rc;
-
-}
-
-static int32_t rcar_file_open(io_dev_info_t *info, const uintptr_t file_spec,
-			      io_entity_t *entity)
-{
-	const io_drv_spec_t *spec = (io_drv_spec_t *) file_spec;
-	uintptr_t partition, offset, dst;
-	uint32_t noload, cert, len;
-	int32_t rc;
-
-	/* Only one file open at a time. We need to  track state (ie, file
-	 * cursor position). Since the header lives at * offset zero, this entry
-	 * should never be zero in an active file.
-	 * Once the system supports dynamic memory allocation we will allow more
-	 * than one open file at a time. */
-	if (current_file.offset != 0U) {
-		WARN("rcar_file_open : Only one open file at a time.\n");
-		return IO_RESOURCES_EXHAUSTED;
-	}
-
-	rc = file_to_offset(spec->offset, &offset, &cert, &noload, &partition);
-	if (rc != IO_SUCCESS) {
-		WARN("Failed to open file name %ld (%i)\n", spec->offset, rc);
-		return IO_FAIL;
-	}
-
-	if (noload) {
-		current_file.offset = 1;
-		current_file.dst = 0;
-		current_file.size = 1;
-		current_file.position = 0;
-		current_file.no_load = noload;
-		current_file.partition = 0;
-		entity->info = (uintptr_t) &current_file;
-
-		return IO_SUCCESS;
-	}
-
-	rcar_read_certificate((uint64_t) cert, &len, &dst);
-
-	/*----------------*
-	 * Baylibre: HACK *
-	 *----------------*/
-	if (BL31_IMAGE_ID == spec->offset && len < RCAR_TRUSTED_SRAM_SIZE) {
-		WARN("r-car ignoring the BL31 size from certificate,"
-		     "using RCAR_TRUSTED_SRAM_SIZE instead\n");
-		len = RCAR_TRUSTED_SRAM_SIZE;
-	}
-
-	current_file.partition = partition;
-	current_file.no_load = noload;
-	current_file.offset = offset;
-	current_file.position = 0;
-	current_file.size = len;
-	current_file.dst = dst;
-	entity->info = (uintptr_t) &current_file;
-
-	return IO_SUCCESS;
-}
-
-static int32_t rcar_file_len(io_entity_t *entity, size_t *length)
-{
-	*length = ((file_state_t *) entity->info)->size;
-
-	NOTICE("%s: len: 0x%08lx\n", __func__, *length);
-
-	return IO_SUCCESS;
-}
-
-static int32_t rcar_file_read(io_entity_t *entity, uintptr_t buffer,
-			      size_t length, size_t *cnt)
-{
-	file_state_t *fp = (file_state_t *) entity->info;
-	ssize_t offset = fp->offset + fp->position;
-	uintptr_t handle;
-	int32_t rc;
-
-#ifdef SPD_NONE
-	static uint32_t load_bl33x_counter = 1;
-#else
-	static uint32_t load_bl33x_counter;
-#endif
-	if (current_file.no_load) {
-		*cnt = length;
-		return IO_SUCCESS;
-	}
-
-	((io_drv_spec_t *) rcar_spec)->partition = fp->partition;
-
-	rc = io_open(rcar_handle, rcar_spec, &handle);
-	if (rc != IO_SUCCESS) {
-		WARN("Failed to open FIP (%i)\n", rc);
-		return IO_FAIL;
-	}
-
-	rc = io_seek(handle, IO_SEEK_SET, offset);
-	if (rc != IO_SUCCESS) {
-		WARN("rcar_file_read: failed to seek\n");
-		goto error;
-	}
-
-	if (load_bl33x_counter == RCAR_COUNT_LOAD_BL33) {
-		rc = check_load_area(buffer, length);
-		if (rc != IO_SUCCESS) {
-			WARN("rcar_file_read: load area err\n");
-			goto error;
-		}
-	}
-
-	rc = io_read(handle, buffer, length, cnt);
-	if (rc != IO_SUCCESS) {
-		WARN("Failed to read payload (%i)\n", rc);
-		goto error;
-	}
-
-	fp->position += *cnt;
-	io_close(handle);
-
-	load_bl33x_counter += 1;
-	if (load_bl33x_counter == RCAR_COUNT_LOAD_BL33X)
-		return load_bl33x();
-
-	return IO_SUCCESS;
-error:
-	io_close(handle);
-	return IO_FAIL;
-}
-
-static int32_t rcar_file_close(io_entity_t *entity)
-{
-	if (current_file.offset)
-		memset(&current_file, 0, sizeof(current_file));
-
-	entity->info = 0U;
-
-	return IO_SUCCESS;
-}
-
-static const io_dev_funcs_t rcar_dev_funcs = {
-	.type = &device_type_rcar,
-	.open = &rcar_file_open,
-	.seek = NULL,
-	.size = &rcar_file_len,
-	.read = &rcar_file_read,
-	.write = NULL,
-	.close = &rcar_file_close,
-	.dev_init = &rcar_dev_init,
-	.dev_close = &rcar_dev_close,
-};
-
-static const io_dev_info_t rcar_dev_info = {
-	.funcs = &rcar_dev_funcs,
-	.info = (uintptr_t) 0
-};
-
-static const io_dev_connector_t rcar_dev_connector = {
-	.dev_open = &rcar_dev_open
-};
-
-static int32_t rcar_dev_open(const uintptr_t dev_spec __attribute__ ((unused)),
-			     io_dev_info_t **dev_info)
-{
-	*dev_info = (io_dev_info_t *) &rcar_dev_info;
-
-	return IO_SUCCESS;
-}
-
-static int32_t rcar_dev_close(io_dev_info_t *dev_info)
-{
-	rcar_handle = 0;
-	rcar_spec = 0;
-
-	return IO_SUCCESS;
-}
-
-int32_t rcar_register_io_dev(const io_dev_connector_t **dev_con)
-{
-	int32_t result;
-
-	result = io_register_device(&rcar_dev_info);
-	if (result == IO_SUCCESS)
-		*dev_con = &rcar_dev_connector;
-
-	return result;
-}
diff --git a/drivers/renesas/rcar/pwrc/pwrc.c b/drivers/renesas/rcar/pwrc/pwrc.c
deleted file mode 100644
index 2ce6b61..0000000
--- a/drivers/renesas/rcar/pwrc/pwrc.c
+++ /dev/null
@@ -1,866 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-#include <string.h>
-
-#include <arch.h>
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <lib/bakery_lock.h>
-#include <lib/mmio.h>
-#include <lib/xlat_tables/xlat_tables_v2.h>
-#include <plat/common/platform.h>
-
-#include "iic_dvfs.h"
-#include "rcar_def.h"
-#include "rcar_private.h"
-#include "micro_delay.h"
-#include "pwrc.h"
-
-/*
- * Someday there will be a generic power controller api. At the moment each
- * platform has its own pwrc so just exporting functions should be acceptable.
- */
-RCAR_INSTANTIATE_LOCK
-
-#define	WUP_IRQ_SHIFT				(0U)
-#define	WUP_FIQ_SHIFT				(8U)
-#define	WUP_CSD_SHIFT				(16U)
-#define	BIT_SOFTRESET				(1U<<15)
-#define	BIT_CA53_SCU				(1U<<21)
-#define	BIT_CA57_SCU				(1U<<12)
-#define	REQ_RESUME				(1U<<1)
-#define	REQ_OFF					(1U<<0)
-#define	STATUS_PWRUP				(1U<<4)
-#define	STATUS_PWRDOWN				(1U<<0)
-#define	STATE_CA57_CPU				(27U)
-#define	STATE_CA53_CPU				(22U)
-#define	MODE_L2_DOWN				(0x00000002U)
-#define	CPU_PWR_OFF				(0x00000003U)
-#define	RCAR_PSTR_MASK				(0x00000003U)
-#define	ST_ALL_STANDBY				(0x00003333U)
-/* Suspend to ram	*/
-#define	DBSC4_REG_BASE				(0xE6790000U)
-#define	DBSC4_REG_DBSYSCNT0			(DBSC4_REG_BASE + 0x0100U)
-#define	DBSC4_REG_DBACEN			(DBSC4_REG_BASE + 0x0200U)
-#define	DBSC4_REG_DBCMD				(DBSC4_REG_BASE + 0x0208U)
-#define	DBSC4_REG_DBRFEN			(DBSC4_REG_BASE + 0x0204U)
-#define	DBSC4_REG_DBWAIT			(DBSC4_REG_BASE + 0x0210U)
-#define	DBSC4_REG_DBCALCNF			(DBSC4_REG_BASE + 0x0424U)
-#define	DBSC4_REG_DBDFIPMSTRCNF			(DBSC4_REG_BASE + 0x0520U)
-#define	DBSC4_REG_DBPDLK0			(DBSC4_REG_BASE + 0x0620U)
-#define	DBSC4_REG_DBPDRGA0			(DBSC4_REG_BASE + 0x0624U)
-#define	DBSC4_REG_DBPDRGD0			(DBSC4_REG_BASE + 0x0628U)
-#define	DBSC4_REG_DBCAM0CTRL0			(DBSC4_REG_BASE + 0x0940U)
-#define	DBSC4_REG_DBCAM0STAT0			(DBSC4_REG_BASE + 0x0980U)
-#define	DBSC4_REG_DBCAM1STAT0			(DBSC4_REG_BASE + 0x0990U)
-#define	DBSC4_REG_DBCAM2STAT0			(DBSC4_REG_BASE + 0x09A0U)
-#define	DBSC4_REG_DBCAM3STAT0			(DBSC4_REG_BASE + 0x09B0U)
-#define	DBSC4_BIT_DBACEN_ACCEN			((uint32_t)(1U << 0))
-#define	DBSC4_BIT_DBRFEN_ARFEN			((uint32_t)(1U << 0))
-#define	DBSC4_BIT_DBCAMxSTAT0			(0x00000001U)
-#define	DBSC4_BIT_DBDFIPMSTRCNF_PMSTREN		(0x00000001U)
-#define	DBSC4_SET_DBCMD_OPC_PRE			(0x04000000U)
-#define	DBSC4_SET_DBCMD_OPC_SR			(0x0A000000U)
-#define	DBSC4_SET_DBCMD_OPC_PD			(0x08000000U)
-#define	DBSC4_SET_DBCMD_OPC_MRW			(0x0E000000U)
-#define	DBSC4_SET_DBCMD_CH_ALL			(0x00800000U)
-#define	DBSC4_SET_DBCMD_RANK_ALL		(0x00040000U)
-#define	DBSC4_SET_DBCMD_ARG_ALL			(0x00000010U)
-#define	DBSC4_SET_DBCMD_ARG_ENTER		(0x00000000U)
-#define	DBSC4_SET_DBCMD_ARG_MRW_ODTC		(0x00000B00U)
-#define	DBSC4_SET_DBSYSCNT0_WRITE_ENABLE	(0x00001234U)
-#define	DBSC4_SET_DBSYSCNT0_WRITE_DISABLE	(0x00000000U)
-#define	DBSC4_SET_DBPDLK0_PHY_ACCESS		(0x0000A55AU)
-#define	DBSC4_SET_DBPDRGA0_ACIOCR0		(0x0000001AU)
-#define	DBSC4_SET_DBPDRGD0_ACIOCR0		(0x33C03C11U)
-#define	DBSC4_SET_DBPDRGA0_DXCCR		(0x00000020U)
-#define	DBSC4_SET_DBPDRGD0_DXCCR		(0x00181006U)
-#define	DBSC4_SET_DBPDRGA0_PGCR1		(0x00000003U)
-#define	DBSC4_SET_DBPDRGD0_PGCR1		(0x0380C600U)
-#define	DBSC4_SET_DBPDRGA0_ACIOCR1		(0x0000001BU)
-#define	DBSC4_SET_DBPDRGD0_ACIOCR1		(0xAAAAAAAAU)
-#define	DBSC4_SET_DBPDRGA0_ACIOCR3		(0x0000001DU)
-#define	DBSC4_SET_DBPDRGD0_ACIOCR3		(0xAAAAAAAAU)
-#define	DBSC4_SET_DBPDRGA0_ACIOCR5		(0x0000001FU)
-#define	DBSC4_SET_DBPDRGD0_ACIOCR5		(0x000000AAU)
-#define	DBSC4_SET_DBPDRGA0_DX0GCR2		(0x000000A2U)
-#define	DBSC4_SET_DBPDRGD0_DX0GCR2		(0xAAAA0000U)
-#define	DBSC4_SET_DBPDRGA0_DX1GCR2		(0x000000C2U)
-#define	DBSC4_SET_DBPDRGD0_DX1GCR2		(0xAAAA0000U)
-#define	DBSC4_SET_DBPDRGA0_DX2GCR2		(0x000000E2U)
-#define	DBSC4_SET_DBPDRGD0_DX2GCR2		(0xAAAA0000U)
-#define	DBSC4_SET_DBPDRGA0_DX3GCR2		(0x00000102U)
-#define	DBSC4_SET_DBPDRGD0_DX3GCR2		(0xAAAA0000U)
-#define	DBSC4_SET_DBPDRGA0_ZQCR			(0x00000090U)
-#define	DBSC4_SET_DBPDRGD0_ZQCR_MD19_0		(0x04058904U)
-#define	DBSC4_SET_DBPDRGD0_ZQCR_MD19_1		(0x04058A04U)
-#define	DBSC4_SET_DBPDRGA0_DX0GCR0		(0x000000A0U)
-#define	DBSC4_SET_DBPDRGD0_DX0GCR0		(0x7C0002E5U)
-#define	DBSC4_SET_DBPDRGA0_DX1GCR0		(0x000000C0U)
-#define	DBSC4_SET_DBPDRGD0_DX1GCR0		(0x7C0002E5U)
-#define	DBSC4_SET_DBPDRGA0_DX2GCR0		(0x000000E0U)
-#define	DBSC4_SET_DBPDRGD0_DX2GCR0		(0x7C0002E5U)
-#define	DBSC4_SET_DBPDRGA0_DX3GCR0		(0x00000100U)
-#define	DBSC4_SET_DBPDRGD0_DX3GCR0		(0x7C0002E5U)
-#define	DBSC4_SET_DBPDRGA0_DX0GCR1		(0x000000A1U)
-#define	DBSC4_SET_DBPDRGD0_DX0GCR1		(0x55550000U)
-#define	DBSC4_SET_DBPDRGA0_DX1GCR1		(0x000000C1U)
-#define	DBSC4_SET_DBPDRGD0_DX1GCR1		(0x55550000U)
-#define	DBSC4_SET_DBPDRGA0_DX2GCR1		(0x000000E1U)
-#define	DBSC4_SET_DBPDRGD0_DX2GCR1		(0x55550000U)
-#define	DBSC4_SET_DBPDRGA0_DX3GCR1		(0x00000101U)
-#define	DBSC4_SET_DBPDRGD0_DX3GCR1		(0x55550000U)
-#define	DBSC4_SET_DBPDRGA0_DX0GCR3		(0x000000A3U)
-#define	DBSC4_SET_DBPDRGD0_DX0GCR3		(0x00008484U)
-#define	DBSC4_SET_DBPDRGA0_DX1GCR3		(0x000000C3U)
-#define	DBSC4_SET_DBPDRGD0_DX1GCR3		(0x00008484U)
-#define	DBSC4_SET_DBPDRGA0_DX2GCR3		(0x000000E3U)
-#define	DBSC4_SET_DBPDRGD0_DX2GCR3		(0x00008484U)
-#define	DBSC4_SET_DBPDRGA0_DX3GCR3		(0x00000103U)
-#define	DBSC4_SET_DBPDRGD0_DX3GCR3		(0x00008484U)
-#define	RST_BASE				(0xE6160000U)
-#define	RST_MODEMR				(RST_BASE + 0x0060U)
-#define	RST_MODEMR_BIT0				(0x00000001U)
-
-#define RCAR_CNTCR_OFF				(0x00U)
-#define RCAR_CNTCVL_OFF				(0x08U)
-#define RCAR_CNTCVU_OFF				(0x0CU)
-#define RCAR_CNTFID_OFF				(0x20U)
-
-#define RCAR_CNTCR_EN				((uint32_t)1U << 0U)
-#define RCAR_CNTCR_FCREQ(x)			((uint32_t)(x) << 8U)
-
-#if PMIC_ROHM_BD9571
-#define	BIT_BKUP_CTRL_OUT			((uint8_t)(1U << 4))
-#define	PMIC_BKUP_MODE_CNT			(0x20U)
-#define	PMIC_QLLM_CNT				(0x27U)
-#define	PMIC_RETRY_MAX				(100U)
-#endif
-#define	SCTLR_EL3_M_BIT				((uint32_t)1U << 0)
-#define	RCAR_CA53CPU_NUM_MAX			(4U)
-#define	RCAR_CA57CPU_NUM_MAX			(4U)
-#define IS_A53A57(c) 	((c) == RCAR_CLUSTER_A53A57)
-#define IS_CA57(c) 	((c) == RCAR_CLUSTER_CA57)
-#define IS_CA53(c) 	((c) == RCAR_CLUSTER_CA53)
-
-#ifndef __ASSEMBLER__
-IMPORT_SYM(unsigned long, __system_ram_start__, SYSTEM_RAM_START);
-IMPORT_SYM(unsigned long, __system_ram_end__, SYSTEM_RAM_END);
-IMPORT_SYM(unsigned long, __SRAM_COPY_START__, SRAM_COPY_START);
-#endif
-
-uint32_t rcar_pwrc_status(uint64_t mpidr)
-{
-	uint32_t ret = 0;
-	uint64_t cm, cpu;
-	uint32_t reg;
-	uint32_t c;
-
-	rcar_lock_get();
-
-	c = rcar_pwrc_get_cluster();
-	cm = mpidr & MPIDR_CLUSTER_MASK;
-
-	if (!IS_A53A57(c) && cm != 0) {
-		ret = RCAR_INVALID;
-		goto done;
-	}
-
-	reg = mmio_read_32(RCAR_PRR);
-	cpu = mpidr & MPIDR_CPU_MASK;
-
-	if (IS_CA53(c))
-		if (reg & (1 << (STATE_CA53_CPU + cpu)))
-			ret = RCAR_INVALID;
-	if (IS_CA57(c))
-		if (reg & (1 << (STATE_CA57_CPU + cpu)))
-			ret = RCAR_INVALID;
-done:
-	rcar_lock_release();
-
-	return ret;
-}
-
-static void scu_power_up(uint64_t mpidr)
-{
-	uintptr_t reg_pwrsr, reg_cpumcr, reg_pwron, reg_pwrer;
-	uint32_t c, sysc_reg_bit;
-
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	reg_cpumcr = IS_CA57(c) ? RCAR_CA57CPUCMCR : RCAR_CA53CPUCMCR;
-	sysc_reg_bit = IS_CA57(c) ? BIT_CA57_SCU : BIT_CA53_SCU;
-	reg_pwron = IS_CA57(c) ? RCAR_PWRONCR5 : RCAR_PWRONCR3;
-	reg_pwrer = IS_CA57(c) ? RCAR_PWRER5 : RCAR_PWRER3;
-	reg_pwrsr = IS_CA57(c) ? RCAR_PWRSR5 : RCAR_PWRSR3;
-
-	if ((mmio_read_32(reg_pwrsr) & STATUS_PWRDOWN) == 0)
-		return;
-
-	if (mmio_read_32(reg_cpumcr) != 0)
-		mmio_write_32(reg_cpumcr, 0);
-
-	mmio_setbits_32(RCAR_SYSCIER, sysc_reg_bit);
-	mmio_setbits_32(RCAR_SYSCIMR, sysc_reg_bit);
-
-	do {
-		while ((mmio_read_32(RCAR_SYSCSR) & REQ_RESUME) == 0)
-			;
-		mmio_write_32(reg_pwron, 1);
-	} while (mmio_read_32(reg_pwrer) & 1);
-
-	while ((mmio_read_32(RCAR_SYSCISR) & sysc_reg_bit) == 0)
-		;
-	mmio_write_32(RCAR_SYSCISR, sysc_reg_bit);
-	while ((mmio_read_32(reg_pwrsr) & STATUS_PWRUP) == 0)
-		;
-}
-
-void rcar_pwrc_cpuon(uint64_t mpidr)
-{
-	uint32_t res_data, on_data;
-	uintptr_t res_reg, on_reg;
-	uint32_t limit, c;
-	uint64_t cpu;
-
-	rcar_lock_get();
-
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	res_reg = IS_CA53(c) ? RCAR_CA53RESCNT : RCAR_CA57RESCNT;
-	on_reg = IS_CA53(c) ? RCAR_CA53WUPCR : RCAR_CA57WUPCR;
-	limit = IS_CA53(c) ? 0x5A5A0000 : 0xA5A50000;
-
-	res_data = mmio_read_32(res_reg) | limit;
-	scu_power_up(mpidr);
-	cpu = mpidr & MPIDR_CPU_MASK;
-	on_data = 1 << cpu;
-	mmio_write_32(RCAR_CPGWPR, ~on_data);
-	mmio_write_32(on_reg, on_data);
-	mmio_write_32(res_reg, res_data & (~(1 << (3 - cpu))));
-
-	rcar_lock_release();
-}
-
-void rcar_pwrc_cpuoff(uint64_t mpidr)
-{
-	uint32_t c;
-	uintptr_t reg;
-	uint64_t cpu;
-
-	rcar_lock_get();
-
-	cpu = mpidr & MPIDR_CPU_MASK;
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	reg = IS_CA53(c) ? RCAR_CA53CPU0CR : RCAR_CA57CPU0CR;
-
-	if (read_mpidr_el1() != mpidr)
-		panic();
-
-	mmio_write_32(RCAR_CPGWPR, ~CPU_PWR_OFF);
-	mmio_write_32(reg + cpu * 0x0010, CPU_PWR_OFF);
-
-	rcar_lock_release();
-}
-
-void rcar_pwrc_enable_interrupt_wakeup(uint64_t mpidr)
-{
-	uint32_t c, shift_irq, shift_fiq;
-	uintptr_t reg;
-	uint64_t cpu;
-
-	rcar_lock_get();
-
-	cpu = mpidr & MPIDR_CPU_MASK;
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	reg = IS_CA53(c) ? RCAR_WUPMSKCA53 : RCAR_WUPMSKCA57;
-
-	shift_irq = WUP_IRQ_SHIFT + cpu;
-	shift_fiq = WUP_FIQ_SHIFT + cpu;
-
-	mmio_write_32(reg, ~((uint32_t) 1 << shift_irq) &
-		      ~((uint32_t) 1 << shift_fiq));
-	rcar_lock_release();
-}
-
-void rcar_pwrc_disable_interrupt_wakeup(uint64_t mpidr)
-{
-	uint32_t c, shift_irq, shift_fiq;
-	uintptr_t reg;
-	uint64_t cpu;
-
-	rcar_lock_get();
-
-	cpu = mpidr & MPIDR_CPU_MASK;
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	reg = IS_CA53(c) ? RCAR_WUPMSKCA53 : RCAR_WUPMSKCA57;
-
-	shift_irq = WUP_IRQ_SHIFT + cpu;
-	shift_fiq = WUP_FIQ_SHIFT + cpu;
-
-	mmio_write_32(reg, ((uint32_t) 1 << shift_irq) |
-		      ((uint32_t) 1 << shift_fiq));
-	rcar_lock_release();
-}
-
-void rcar_pwrc_clusteroff(uint64_t mpidr)
-{
-	uint32_t c, product, cut, reg;
-	uintptr_t dst;
-
-	rcar_lock_get();
-
-	reg = mmio_read_32(RCAR_PRR);
-	product = reg & PRR_PRODUCT_MASK;
-	cut = reg & PRR_CUT_MASK;
-
-	c = rcar_pwrc_get_mpidr_cluster(mpidr);
-	dst = IS_CA53(c) ? RCAR_CA53CPUCMCR : RCAR_CA57CPUCMCR;
-
-	if (PRR_PRODUCT_M3 == product && cut < PRR_PRODUCT_30)
-		goto done;
-
-	if (PRR_PRODUCT_H3 == product && cut <= PRR_PRODUCT_20)
-		goto done;
-
-	/* all of the CPUs in the cluster is in the CoreStandby mode */
-	mmio_write_32(dst, MODE_L2_DOWN);
-done:
-	rcar_lock_release();
-}
-
-static uint64_t rcar_pwrc_saved_cntpct_el0;
-static uint32_t rcar_pwrc_saved_cntfid;
-
-#if RCAR_SYSTEM_SUSPEND
-static void rcar_pwrc_save_timer_state(void)
-{
-	rcar_pwrc_saved_cntpct_el0 = read_cntpct_el0();
-
-	rcar_pwrc_saved_cntfid =
-		mmio_read_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTFID_OFF));
-}
-#endif
-
-void rcar_pwrc_restore_timer_state(void)
-{
-	/* Stop timer before restoring counter value */
-	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCR_OFF), 0U);
-
-	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCVL_OFF),
-		(uint32_t)(rcar_pwrc_saved_cntpct_el0 & 0xFFFFFFFFU));
-	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCVU_OFF),
-		(uint32_t)(rcar_pwrc_saved_cntpct_el0 >> 32U));
-
-	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTFID_OFF),
-		rcar_pwrc_saved_cntfid);
-
-	/* Start generic timer back */
-	write_cntfrq_el0((u_register_t)plat_get_syscnt_freq2());
-
-	mmio_write_32((uintptr_t)(RCAR_CNTC_BASE + RCAR_CNTCR_OFF),
-		(RCAR_CNTCR_FCREQ(0U) | RCAR_CNTCR_EN));
-}
-
-#if !PMIC_ROHM_BD9571
-void rcar_pwrc_system_reset(void)
-{
-	mmio_write_32(RCAR_SRESCR, 0x5AA50000U | BIT_SOFTRESET);
-}
-#endif /* PMIC_ROHM_BD9571 */
-
-#define	RST_CA53_CPU0_BARH		(0xE6160080U)
-#define	RST_CA53_CPU0_BARL		(0xE6160084U)
-#define	RST_CA57_CPU0_BARH		(0xE61600C0U)
-#define	RST_CA57_CPU0_BARL		(0xE61600C4U)
-
-void rcar_pwrc_setup(void)
-{
-	uintptr_t rst_barh;
-	uintptr_t rst_barl;
-	uint32_t i, j;
-	uint64_t reset = (uint64_t) (&plat_secondary_reset) & 0xFFFFFFFF;
-
-	const uint32_t cluster[PLATFORM_CLUSTER_COUNT] = {
-		RCAR_CLUSTER_CA53,
-		RCAR_CLUSTER_CA57
-	};
-	const uintptr_t reg_barh[PLATFORM_CLUSTER_COUNT] = {
-		RST_CA53_CPU0_BARH,
-		RST_CA57_CPU0_BARH
-	};
-	const uintptr_t reg_barl[PLATFORM_CLUSTER_COUNT] = {
-		RST_CA53_CPU0_BARL,
-		RST_CA57_CPU0_BARL
-	};
-
-	for (i = 0; i < PLATFORM_CLUSTER_COUNT; i++) {
-		rst_barh = reg_barh[i];
-		rst_barl = reg_barl[i];
-		for (j = 0; j < rcar_pwrc_get_cpu_num(cluster[i]); j++) {
-			mmio_write_32(rst_barh, 0);
-			mmio_write_32(rst_barl, (uint32_t) reset);
-			rst_barh += 0x10;
-			rst_barl += 0x10;
-		}
-	}
-
-	rcar_lock_init();
-}
-
-#if RCAR_SYSTEM_SUSPEND
-#define DBCAM_FLUSH(__bit)		\
-do {					\
-	;				\
-} while (!(mmio_read_32(DBSC4_REG_DBCAM##__bit##STAT0) & DBSC4_BIT_DBCAMxSTAT0))
-
-
-static void __attribute__ ((section(".system_ram")))
-	rcar_pwrc_set_self_refresh(void)
-{
-	uint32_t reg = mmio_read_32(RCAR_PRR);
-	uint32_t cut, product;
-
-	product = reg & PRR_PRODUCT_MASK;
-	cut = reg & PRR_CUT_MASK;
-
-	if (product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30)
-		goto self_refresh;
-
-	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20)
-		goto self_refresh;
-
-	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_ENABLE);
-
-self_refresh:
-
-	/* DFI_PHYMSTR_ACK setting */
-	mmio_write_32(DBSC4_REG_DBDFIPMSTRCNF,
-			mmio_read_32(DBSC4_REG_DBDFIPMSTRCNF) &
-			(~DBSC4_BIT_DBDFIPMSTRCNF_PMSTREN));
-
-	/* Set the Self-Refresh mode */
-	mmio_write_32(DBSC4_REG_DBACEN, 0);
-
-	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20)
-		rcar_micro_delay(100);
-	else if (product == PRR_PRODUCT_H3) {
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
-		DBCAM_FLUSH(0);
-		DBCAM_FLUSH(1);
-		DBCAM_FLUSH(2);
-		DBCAM_FLUSH(3);
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
-	} else if (product == PRR_PRODUCT_M3) {
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
-		DBCAM_FLUSH(0);
-		DBCAM_FLUSH(1);
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
-	} else {
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 1);
-		DBCAM_FLUSH(0);
-		mmio_write_32(DBSC4_REG_DBCAM0CTRL0, 0);
-	}
-
-	/* Set the SDRAM calibration configuration register */
-	mmio_write_32(DBSC4_REG_DBCALCNF, 0);
-
-	reg = DBSC4_SET_DBCMD_OPC_PRE | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ALL;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	/* Self-Refresh entry command   */
-	reg = DBSC4_SET_DBCMD_OPC_SR | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	/* Mode Register Write command. (ODT disabled)  */
-	reg = DBSC4_SET_DBCMD_OPC_MRW | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_MRW_ODTC;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	/* Power Down entry command     */
-	reg = DBSC4_SET_DBCMD_OPC_PD | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	/* Set the auto-refresh enable register */
-	mmio_write_32(DBSC4_REG_DBRFEN, 0U);
-	rcar_micro_delay(1U);
-
-	if (product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30)
-		return;
-
-	if (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20)
-		return;
-
-	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_DISABLE);
-}
-
-static void __attribute__ ((section(".system_ram")))
-    rcar_pwrc_set_self_refresh_e3(void)
-{
-	uint32_t ddr_md;
-	uint32_t reg;
-
-	ddr_md = (mmio_read_32(RST_MODEMR) >> 19) & RST_MODEMR_BIT0;
-
-	/* Write enable */
-	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_ENABLE);
-	mmio_write_32(DBSC4_REG_DBACEN, 0);
-	DBCAM_FLUSH(0);
-
-	reg = DBSC4_SET_DBCMD_OPC_PRE | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ALL;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	reg = DBSC4_SET_DBCMD_OPC_SR | DBSC4_SET_DBCMD_CH_ALL |
-	    DBSC4_SET_DBCMD_RANK_ALL | DBSC4_SET_DBCMD_ARG_ENTER;
-	mmio_write_32(DBSC4_REG_DBCMD, reg);
-	while (mmio_read_32(DBSC4_REG_DBWAIT))
-		;
-
-	/* Set the auto-refresh enable register */
-	/* Set the ARFEN bit to 0 in the DBRFEN */
-	mmio_write_32(DBSC4_REG_DBRFEN, 0);
-
-	mmio_write_32(DBSC4_REG_DBPDLK0, DBSC4_SET_DBPDLK0_PHY_ACCESS);
-
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR0);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR0);
-
-	/* DDR_DXCCR */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DXCCR);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DXCCR);
-
-	/* DDR_PGCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_PGCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_PGCR1);
-
-	/* DDR_ACIOCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR1);
-
-	/* DDR_ACIOCR3 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR3);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR3);
-
-	/* DDR_ACIOCR5 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ACIOCR5);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_ACIOCR5);
-
-	/* DDR_DX0GCR2 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR2);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR2);
-
-	/* DDR_DX1GCR2 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR2);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR2);
-
-	/* DDR_DX2GCR2 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR2);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR2);
-
-	/* DDR_DX3GCR2 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR2);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR2);
-
-	/* DDR_ZQCR */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_ZQCR);
-
-	mmio_write_32(DBSC4_REG_DBPDRGD0, ddr_md == 0 ?
-		      DBSC4_SET_DBPDRGD0_ZQCR_MD19_0 :
-		      DBSC4_SET_DBPDRGD0_ZQCR_MD19_1);
-
-	/* DDR_DX0GCR0 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR0);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR0);
-
-	/* DDR_DX1GCR0 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR0);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR0);
-
-	/* DDR_DX2GCR0 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR0);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR0);
-
-	/* DDR_DX3GCR0 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR0);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR0);
-
-	/* DDR_DX0GCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR1);
-
-	/* DDR_DX1GCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR1);
-
-	/* DDR_DX2GCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR1);
-
-	/* DDR_DX3GCR1 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR1);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR1);
-
-	/* DDR_DX0GCR3 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX0GCR3);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX0GCR3);
-
-	/* DDR_DX1GCR3 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX1GCR3);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX1GCR3);
-
-	/* DDR_DX2GCR3 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX2GCR3);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX2GCR3);
-
-	/* DDR_DX3GCR3 */
-	mmio_write_32(DBSC4_REG_DBPDRGA0, DBSC4_SET_DBPDRGA0_DX3GCR3);
-	mmio_write_32(DBSC4_REG_DBPDRGD0, DBSC4_SET_DBPDRGD0_DX3GCR3);
-
-	/* Write disable */
-	mmio_write_32(DBSC4_REG_DBSYSCNT0, DBSC4_SET_DBSYSCNT0_WRITE_DISABLE);
-}
-
-void __attribute__ ((section(".system_ram"))) __attribute__ ((noinline))
-    rcar_pwrc_go_suspend_to_ram(void)
-{
-#if PMIC_ROHM_BD9571
-	int32_t rc = -1, qllm = -1;
-	uint8_t mode;
-	uint32_t i;
-#endif
-	uint32_t reg, product;
-
-	reg = mmio_read_32(RCAR_PRR);
-	product = reg & PRR_PRODUCT_MASK;
-
-	if (product != PRR_PRODUCT_E3)
-		rcar_pwrc_set_self_refresh();
-	else
-		rcar_pwrc_set_self_refresh_e3();
-
-#if PMIC_ROHM_BD9571
-	/* Set QLLM Cnt Disable */
-	for (i = 0; (i < PMIC_RETRY_MAX) && (qllm != 0); i++)
-		qllm = rcar_iic_dvfs_send(PMIC, PMIC_QLLM_CNT, 0);
-
-	/* Set trigger of power down to PMIV */
-	for (i = 0; (i < PMIC_RETRY_MAX) && (rc != 0) && (qllm == 0); i++) {
-		rc = rcar_iic_dvfs_receive(PMIC, PMIC_BKUP_MODE_CNT, &mode);
-		if (rc == 0) {
-			mode |= BIT_BKUP_CTRL_OUT;
-			rc = rcar_iic_dvfs_send(PMIC, PMIC_BKUP_MODE_CNT, mode);
-		}
-	}
-#endif
-	wfi();
-
-	while (1)
-		;
-}
-
-void rcar_pwrc_set_suspend_to_ram(void)
-{
-	uintptr_t jump = (uintptr_t) &rcar_pwrc_go_suspend_to_ram;
-	uintptr_t stack = (uintptr_t) (DEVICE_SRAM_STACK_BASE +
-				       DEVICE_SRAM_STACK_SIZE);
-	uint32_t sctlr;
-
-	rcar_pwrc_save_timer_state();
-
-	/* disable MMU */
-	sctlr = (uint32_t) read_sctlr_el3();
-	sctlr &= (uint32_t) ~SCTLR_EL3_M_BIT;
-	write_sctlr_el3((uint64_t) sctlr);
-
-	rcar_pwrc_switch_stack(jump, stack, NULL);
-}
-
-void rcar_pwrc_init_suspend_to_ram(void)
-{
-#if PMIC_ROHM_BD9571
-	uint8_t mode;
-
-	if (rcar_iic_dvfs_receive(PMIC, PMIC_BKUP_MODE_CNT, &mode))
-		panic();
-
-	mode &= (uint8_t) (~BIT_BKUP_CTRL_OUT);
-	if (rcar_iic_dvfs_send(PMIC, PMIC_BKUP_MODE_CNT, mode))
-		panic();
-#endif
-}
-
-void rcar_pwrc_suspend_to_ram(void)
-{
-#if RCAR_SYSTEM_RESET_KEEPON_DDR
-	int32_t error;
-
-	error = rcar_iic_dvfs_send(PMIC, REG_KEEP10, 0);
-	if (error) {
-		ERROR("Failed send KEEP10 init ret=%d \n", error);
-		return;
-	}
-#endif
-	rcar_pwrc_set_suspend_to_ram();
-}
-#endif
-
-void rcar_pwrc_code_copy_to_system_ram(void)
-{
-	int ret __attribute__ ((unused));	/* in assert */
-	uint32_t attr;
-	struct device_sram_t {
-		uintptr_t base;
-		size_t len;
-	} sram = {
-		.base = (uintptr_t) DEVICE_SRAM_BASE,
-		.len = DEVICE_SRAM_SIZE,
-	};
-	struct ddr_code_t {
-		void *base;
-		size_t len;
-	} code = {
-		.base = (void *) SRAM_COPY_START,
-		.len = SYSTEM_RAM_END - SYSTEM_RAM_START,
-	};
-
-	attr = MT_MEMORY | MT_RW | MT_SECURE | MT_EXECUTE_NEVER;
-	ret = xlat_change_mem_attributes(sram.base, sram.len, attr);
-	assert(ret == 0);
-
-	memcpy((void *)sram.base, code.base, code.len);
-	flush_dcache_range((uint64_t) sram.base, code.len);
-
-	/* Invalidate instruction cache */
-	plat_invalidate_icache();
-	dsb();
-	isb();
-
-	attr = MT_MEMORY | MT_RO | MT_SECURE | MT_EXECUTE;
-	ret = xlat_change_mem_attributes(sram.base, sram.len, attr);
-	assert(ret == 0);
-}
-
-uint32_t rcar_pwrc_get_cluster(void)
-{
-	uint32_t reg;
-
-	reg = mmio_read_32(RCAR_PRR);
-
-	if (reg & (1U << (STATE_CA53_CPU + RCAR_CA53CPU_NUM_MAX)))
-		return RCAR_CLUSTER_CA57;
-
-	if (reg & (1U << (STATE_CA57_CPU + RCAR_CA57CPU_NUM_MAX)))
-		return RCAR_CLUSTER_CA53;
-
-	return RCAR_CLUSTER_A53A57;
-}
-
-uint32_t rcar_pwrc_get_mpidr_cluster(uint64_t mpidr)
-{
-	uint32_t c = rcar_pwrc_get_cluster();
-
-	if (IS_A53A57(c)) {
-		if (mpidr & MPIDR_CLUSTER_MASK)
-			return RCAR_CLUSTER_CA53;
-
-		return RCAR_CLUSTER_CA57;
-	}
-
-	return c;
-}
-
-#if RCAR_LSI == RCAR_D3
-uint32_t rcar_pwrc_get_cpu_num(uint32_t c)
-{
-	return 1;
-}
-#else
-uint32_t rcar_pwrc_get_cpu_num(uint32_t c)
-{
-	uint32_t reg = mmio_read_32(RCAR_PRR);
-	uint32_t count = 0, i;
-
-	if (IS_A53A57(c) || IS_CA53(c)) {
-		if (reg & (1 << (STATE_CA53_CPU + RCAR_CA53CPU_NUM_MAX)))
-			goto count_ca57;
-
-		for (i = 0; i < RCAR_CA53CPU_NUM_MAX; i++) {
-			if (reg & (1 << (STATE_CA53_CPU + i)))
-				continue;
-			count++;
-		}
-	}
-
-count_ca57:
-	if (IS_A53A57(c) || IS_CA57(c)) {
-		if (reg & (1U << (STATE_CA57_CPU + RCAR_CA57CPU_NUM_MAX)))
-			goto done;
-
-		for (i = 0; i < RCAR_CA57CPU_NUM_MAX; i++) {
-			if (reg & (1 << (STATE_CA57_CPU + i)))
-				continue;
-			count++;
-		}
-	}
-
-done:
-	return count;
-}
-#endif
-
-int32_t rcar_pwrc_cpu_on_check(uint64_t mpidr)
-{
-	uint64_t i;
-	uint64_t j;
-	uint64_t cpu_count;
-	uintptr_t reg_PSTR;
-	uint32_t status;
-	uint64_t my_cpu;
-	int32_t rtn;
-	uint32_t my_cluster_type;
-
-	const uint32_t cluster_type[PLATFORM_CLUSTER_COUNT] = {
-			RCAR_CLUSTER_CA53,
-			RCAR_CLUSTER_CA57
-	};
-	const uintptr_t registerPSTR[PLATFORM_CLUSTER_COUNT] = {
-			RCAR_CA53PSTR,
-			RCAR_CA57PSTR
-	};
-
-	my_cluster_type = rcar_pwrc_get_cluster();
-
-	rtn = 0;
-	my_cpu = mpidr & ((uint64_t)(MPIDR_CPU_MASK));
-	for (i = 0U; i < ((uint64_t)(PLATFORM_CLUSTER_COUNT)); i++) {
-		cpu_count = rcar_pwrc_get_cpu_num(cluster_type[i]);
-		reg_PSTR = registerPSTR[i];
-		for (j = 0U; j < cpu_count; j++) {
-			if ((my_cluster_type != cluster_type[i]) || (my_cpu != j)) {
-				status = mmio_read_32(reg_PSTR) >> (j * 4U);
-				if ((status & 0x00000003U) == 0U) {
-					rtn--;
-				}
-			}
-		}
-	}
-	return (rtn);
-
-}
diff --git a/drivers/renesas/rcar/pwrc/pwrc.h b/drivers/renesas/rcar/pwrc/pwrc.h
deleted file mode 100644
index 2b81783..0000000
--- a/drivers/renesas/rcar/pwrc/pwrc.h
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PWRC_H
-#define PWRC_H
-
-#define PPOFFR_OFF		0x0
-#define PPONR_OFF		0x4
-#define PCOFFR_OFF		0x8
-#define PWKUPR_OFF		0xc
-#define PSYSR_OFF		0x10
-
-#define PWKUPR_WEN		(1ull << 31)
-
-#define PSYSR_AFF_L2		(1U << 31)
-#define PSYSR_AFF_L1		(1 << 30)
-#define PSYSR_AFF_L0		(1 << 29)
-#define PSYSR_WEN		(1 << 28)
-#define PSYSR_PC		(1 << 27)
-#define PSYSR_PP		(1 << 26)
-
-#define PSYSR_WK_SHIFT		(24)
-#define PSYSR_WK_MASK		(0x3)
-#define PSYSR_WK(x)		(((x) >> PSYSR_WK_SHIFT) & PSYSR_WK_MASK)
-
-#define WKUP_COLD		0x0
-#define WKUP_RESET		0x1
-#define WKUP_PPONR		0x2
-#define WKUP_GICREQ		0x3
-
-#define	RCAR_INVALID		(0xffffffffU)
-#define PSYSR_INVALID		0xffffffff
-
-#define	RCAR_CLUSTER_A53A57	(0U)
-#define	RCAR_CLUSTER_CA53	(1U)
-#define	RCAR_CLUSTER_CA57	(2U)
-
-#ifndef __ASSEMBLER__
-void rcar_pwrc_disable_interrupt_wakeup(uint64_t mpidr);
-void rcar_pwrc_enable_interrupt_wakeup(uint64_t mpidr);
-void rcar_pwrc_clusteroff(uint64_t mpidr);
-void rcar_pwrc_cpuoff(uint64_t mpidr);
-void rcar_pwrc_cpuon(uint64_t mpidr);
-int32_t rcar_pwrc_cpu_on_check(uint64_t mpidr);
-void rcar_pwrc_setup(void);
-
-uint32_t rcar_pwrc_get_cpu_wkr(uint64_t mpidr);
-uint32_t rcar_pwrc_status(uint64_t mpidr);
-uint32_t rcar_pwrc_get_cluster(void);
-uint32_t rcar_pwrc_get_mpidr_cluster(uint64_t mpidr);
-uint32_t rcar_pwrc_get_cpu_num(uint32_t cluster_type);
-void rcar_pwrc_restore_timer_state(void);
-void plat_secondary_reset(void);
-
-void rcar_pwrc_code_copy_to_system_ram(void);
-
-#if !PMIC_ROHM_BD9571
-void rcar_pwrc_system_reset(void);
-#endif
-
-#if RCAR_SYSTEM_SUSPEND
-void rcar_pwrc_go_suspend_to_ram(void);
-void rcar_pwrc_set_suspend_to_ram(void);
-void rcar_pwrc_init_suspend_to_ram(void);
-void rcar_pwrc_suspend_to_ram(void);
-#endif
-
-extern uint32_t rcar_pwrc_switch_stack(uintptr_t jump, uintptr_t stack,
-				       void *arg);
-#endif
-
-#endif /* PWRC_H */
diff --git a/drivers/renesas/rcar/scif/scif.S b/drivers/renesas/rcar/scif/scif.S
deleted file mode 100644
index ae26cc4..0000000
--- a/drivers/renesas/rcar/scif/scif.S
+++ /dev/null
@@ -1,329 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <console_macros.S>
-#include <drivers/renesas/rcar/console/console.h>
-
-#define	SCIF_INTERNAL_CLK	0
-#define	SCIF_EXTARNAL_CLK	1
-#define	SCIF_CLK		SCIF_INTERNAL_CLK
-
-/* product register */
-#define	PRR			(0xFFF00044)
-#define	PRR_PRODUCT_MASK	(0x00007F00)
-#define	PRR_CUT_MASK		(0x000000FF)
-#define	PRR_PRODUCT_H3_VER_10	(0x00004F00)
-#define	PRR_PRODUCT_E3		(0x00005700)
-#define	PRR_PRODUCT_D3		(0x00005800)
-
-/* module stop */
-#define	CPG_BASE		(0xE6150000)
-#define	CPG_SMSTPCR2		(0x0138)
-#define	CPG_SMSTPCR3		(0x013C)
-#define CPG_MSTPSR2		(0x0040)
-#define	CPG_MSTPSR3		(0x0048)
-#define	MSTP207			(1 << 7)
-#define	MSTP310			(1 << 10)
-#define	CPG_CPGWPR		(0x0900)
-
-/* scif */
-#define	SCIF0_BASE		(0xE6E60000)
-#define	SCIF2_BASE		(0xE6E88000)
-#define	SCIF_SCSMR		(0x00)
-#define	SCIF_SCBRR		(0x04)
-#define	SCIF_SCSCR		(0x08)
-#define	SCIF_SCFTDR		(0x0C)
-#define	SCIF_SCFSR		(0x10)
-#define	SCIF_SCFRDR		(0x14)
-#define	SCIF_SCFCR		(0x18)
-#define	SCIF_SCFDR		(0x1C)
-#define	SCIF_SCSPTR		(0x20)
-#define	SCIF_SCLSR		(0x24)
-#define	SCIF_DL			(0x30)
-#define	SCIF_CKS		(0x34)
-
-#if RCAR_LSI == RCAR_V3M
-#define SCIF_BASE		SCIF0_BASE
-#define CPG_SMSTPCR		CPG_SMSTPCR2
-#define CPG_MSTPSR		CPG_MSTPSR2
-#define MSTP			MSTP207
-#else
-#define SCIF_BASE		SCIF2_BASE
-#define CPG_SMSTPCR		CPG_SMSTPCR3
-#define CPG_MSTPSR		CPG_MSTPSR3
-#define MSTP			MSTP310
-#endif
-
-/* mode pin */
-#define	RST_MODEMR		(0xE6160060)
-#define	MODEMR_MD12		(0x00001000)
-
-#define	SCSMR_CA_MASK		(1 << 7)
-#define	SCSMR_CA_ASYNC		(0x0000)
-#define	SCSMR_CHR_MASK		(1 << 6)
-#define	SCSMR_CHR_8		(0x0000)
-#define	SCSMR_PE_MASK		(1 << 5)
-#define	SCSMR_PE_DIS		(0x0000)
-#define	SCSMR_STOP_MASK		(1 << 3)
-#define	SCSMR_STOP_1		(0x0000)
-#define	SCSMR_CKS_MASK		(3 << 0)
-#define	SCSMR_CKS_DIV1		(0x0000)
-#define	SCSMR_INIT_DATA		(SCSMR_CA_ASYNC +	\
-					 SCSMR_CHR_8 +		\
-					 SCSMR_PE_DIS +		\
-					 SCSMR_STOP_1 +		\
-					 SCSMR_CKS_DIV1)
-#define	SCBRR_115200BPS		(17)
-#define	SCBRR_115200BPSON	(16)
-#define	SCBRR_115200BPS_E3_SSCG	(15)
-#define	SCBRR_230400BPS		(8)
-
-#define	SCSCR_TE_MASK		(1 << 5)
-#define	SCSCR_TE_DIS		(0x0000)
-#define	SCSCR_TE_EN		(0x0020)
-#define	SCSCR_RE_MASK		(1 << 4)
-#define	SCSCR_RE_DIS		(0x0000)
-#define	SCSCR_RE_EN		(0x0010)
-#define	SCSCR_CKE_MASK		(3 << 0)
-#define	SCSCR_CKE_INT		(0x0000)
-#define 	SCSCR_CKE_BRG		(0x0002)
-#if SCIF_CLK == SCIF_EXTARNAL_CLK
-#define	SCSCR_CKE_INT_CLK	(SCSCR_CKE_BRG)
-#else
-#define	SCFSR_TEND_MASK		(1 << 6)
-#define	SCFSR_TEND_TRANS_END	(0x0040)
-#define	SCSCR_CKE_INT_CLK	(SCSCR_CKE_INT)
-#endif
-#define	SCFSR_INIT_DATA		(0x0000)
-#define	SCFCR_TTRG_MASK		(3 << 4)
-#define	SCFCR_TTRG_8		(0x0000)
-#define	SCFCR_TTRG_0		(0x0030)
-#define	SCFCR_TFRST_MASK	(1 << 2)
-#define	SCFCR_TFRST_DIS		(0x0000)
-#define	SCFCR_TFRST_EN		(0x0004)
-#define	SCFCR_RFRS_MASK		(1 << 1)
-#define	SCFCR_RFRS_DIS		(0x0000)
-#define	SCFCR_RFRS_EN		(0x0002)
-#define	SCFCR_INIT_DATA		(SCFCR_TTRG_8)
-#define	SCFDR_T_MASK		(0x1f << 8)
-#define	DL_INIT_DATA		(8)
-#define	CKS_CKS_DIV_MASK	(1 << 15)
-#define	CKS_CKS_DIV_CLK		(0x0000)
-#define	CKS_XIN_MASK		(1 << 14)
-#define	CKS_XIN_SCIF_CLK	(0x0000)
-#define	CKS_INIT_DATA		(CKS_CKS_DIV_CLK + CKS_XIN_SCIF_CLK)
-
-	.globl	console_rcar_register
-	.globl	console_rcar_init
-	.globl	console_rcar_putc
-	.globl	console_rcar_flush
-
-	/* -----------------------------------------------
-	 * int console_rcar_register(
-	 *      uintptr_t base, uint32_t clk, uint32_t baud,
-	 *      console_t *console)
-	 * Function to initialize and register a new rcar
-	 * console. Storage passed in for the console struct
-	 * *must* be persistent (i.e. not from the stack).
-	 * In: x0 - UART register base address
-	 *     w1 - UART clock in Hz
-	 *     w2 - Baud rate
-	 *     x3 - pointer to empty console_t struct
-	 * Out: return 1 on success, 0 on error
-	 * Clobber list : x0, x1, x2, x6, x7, x14
-	 * -----------------------------------------------
-	 */
-func console_rcar_register
-	mov	x7, x30
-	mov	x6, x3
-	cbz	x6, register_fail
-	str	x0, [x6, #CONSOLE_T_BASE]
-
-	bl	console_rcar_init
-
-	mov	x0, x6
-	mov	x30, x7
-	finish_console_register rcar, putc=1, getc=0, flush=1
-
-register_fail:
-	ret	x7
-endfunc console_rcar_register
-
-	/* -----------------------------------------------
-	 * int console_rcar_init(unsigned long base_addr,
-	 * unsigned int uart_clk, unsigned int baud_rate)
-	 * Function to initialize the console without a
-	 * C Runtime to print debug information. This
-	 * function will be accessed by console_rcar_register
-	 * and crash reporting.
-	 * In: x0 - console base address
-	 *     w1 - Uart clock in Hz
-	 *     w2 - Baud rate
-	 * Out: return 1 on success
-	 * Clobber list : x1, x2
-	 * -----------------------------------------------
-	 */
-func console_rcar_init
-	ldr	x0, =CPG_BASE
-	ldr	w1, [x0, #CPG_SMSTPCR]
-	and	w1, w1, #~MSTP
-	mvn	w2, w1
-	str	w2, [x0, #CPG_CPGWPR]
-	str	w1, [x0, #CPG_SMSTPCR]
-5:
-	ldr w1, [x0, #CPG_MSTPSR]
-	and w1, w1, #MSTP
-	cbnz w1, 5b
-
-	ldr	x0, =SCIF_BASE
-	/* Clear bits TE and RE in SCSCR to 0 */
-	mov	w1, #(SCSCR_TE_DIS + SCSCR_RE_DIS)
-	strh	w1, [x0, #SCIF_SCSCR]
-	/* Set bits TFRST and RFRST in SCFCR to 1 */
-	ldrh	w1, [x0, #SCIF_SCFCR]
-	orr	w1, w1, #(SCFCR_TFRST_EN + SCFCR_RFRS_EN)
-	strh	w1, [x0, #SCIF_SCFCR]
-	/* Read flags of ER, DR, BRK, and RDF in SCFSR and those of TO and ORER
-	   in SCLSR, then clear them to 0 */
-	mov	w1, #SCFSR_INIT_DATA
-	strh	w1, [x0, #SCIF_SCFSR]
-	mov	w1, #0
-	strh	w1, [x0, #SCIF_SCLSR]
-	/* Set bits CKE[1:0] in SCSCR */
-	ldrh	w1, [x0, #SCIF_SCSCR]
-	and	w1, w1, #~SCSCR_CKE_MASK
-	mov	w2, #SCSCR_CKE_INT_CLK
-	orr	w1, w1, w2
-	strh	w1, [x0, #SCIF_SCSCR]
-	/* Set data transfer format in SCSMR */
-	mov	w1, #SCSMR_INIT_DATA
-	strh	w1, [x0, #SCIF_SCSMR]
-	/* Set value in SCBRR */
-#if SCIF_CLK == SCIF_INTERNAL_CLK
-	ldr	x1, =PRR
-	ldr	w1, [x1]
-	and	w1, w1, #(PRR_PRODUCT_MASK | PRR_CUT_MASK)
-	mov	w2, #PRR_PRODUCT_H3_VER_10
-	cmp	w1, w2
-	beq	3f
-	and	w1, w1, #PRR_PRODUCT_MASK
-	mov	w2, #PRR_PRODUCT_D3
-	cmp	w1, w2
-	beq	4f
-	and	w1, w1, #PRR_PRODUCT_MASK
-	mov	w2, #PRR_PRODUCT_E3
-	cmp	w1, w2
-	bne	5f
-
-	ldr	x1, =RST_MODEMR
-	ldr	w1, [x1]
-	and	w1, w1, #MODEMR_MD12
-	mov	w2, #MODEMR_MD12
-	cmp	w1, w2
-	bne	5f
-
-	mov	w1, #SCBRR_115200BPS_E3_SSCG
-	b	2f
-5:
-	mov	w1, #SCBRR_115200BPS
-	b	2f
-4:
-	mov	w1, #SCBRR_115200BPSON
-	b	2f
-3:
-	mov	w1, #SCBRR_230400BPS
-2:
-	strb	w1, [x0, SCIF_SCBRR]
-#else
-	mov	w1, #DL_INIT_DATA
-	strh	w1, [x0, #SCIF_DL]
-	mov	w1, #CKS_INIT_DATA
-	strh	w1, [x0, #SCIF_CKS]
-#endif
-	/* 1-bit interval elapsed */
-	mov	w1, #100
-1:
-	subs	w1, w1, #1
-	cbnz	w1, 1b
-	/*
-	 * Set bits RTRG[1:0], TTRG[1:0], and MCE in SCFCR
-	 * Clear bits FRST and RFRST to 0
-	 */
-	mov	w1, #SCFCR_INIT_DATA
-	strh	w1, [x0, #SCIF_SCFCR]
-	/* Set bits TE and RE in SCSCR to 1 */
-	ldrh	w1, [x0, #SCIF_SCSCR]
-	orr	w1, w1, #(SCSCR_TE_EN + SCSCR_RE_EN)
-	strh	w1, [x0, #SCIF_SCSCR]
-	mov	x0, #1
-
-	ret
-endfunc console_rcar_init
-
-	/* --------------------------------------------------------
-	 * int console_rcar_putc(int c, unsigned int base_addr)
-	 * Function to output a character over the console. It
-	 * returns the character printed on success or -1 on error.
-	 * In : w0 - character to be printed
-	 *      x1 - pointer to console_t structure
-	 * Out : return -1 on error else return character.
-	 * Clobber list : x2
-	 * --------------------------------------------------------
-	 */
-func console_rcar_putc
-	ldr	x1, =SCIF_BASE
-	cmp	w0, #0xA
-	/* Prepend '\r' to '\n' */
-	bne	2f
-1:
-	/* Check if the transmit FIFO is full */
-	ldrh	w2, [x1, #SCIF_SCFDR]
-	ubfx	w2, w2, #8, #5
-	cmp	w2, #16
-	bcs	1b
-	mov	w2, #0x0D
-	strb	w2, [x1, #SCIF_SCFTDR]
-2:
-	/* Check if the transmit FIFO is full */
-	ldrh	w2, [x1, #SCIF_SCFDR]
-	ubfx	w2, w2, #8, #5
-	cmp	w2, #16
-	bcs	2b
-	strb	w0, [x1, #SCIF_SCFTDR]
-
-	/* Clear TEND flag */
-	ldrh	w2, [x1, #SCIF_SCFSR]
-	and	w2, w2, #~SCFSR_TEND_MASK
-	strh	w2, [x1, #SCIF_SCFSR]
-
-	ret
-endfunc console_rcar_putc
-
-	/* ---------------------------------------------
-	 * void console_rcar_flush(void)
-	 * Function to force a write of all buffered
-	 * data that hasn't been output. It returns void
-	 * Clobber list : x0, x1
-	 * ---------------------------------------------
-	 */
-func console_rcar_flush
-	ldr	x0, =SCIF_BASE
-1:
-	/* Check TEND flag */
-	ldrh	w1, [x0, #SCIF_SCFSR]
-	and	w1, w1, #SCFSR_TEND_MASK
-	cmp	w1, #SCFSR_TEND_TRANS_END
-	bne	1b
-
-	ldr	x0, =SCIF_BASE
-	ldrh	w1, [x0, #SCIF_SCSCR]
-	and	w1, w1, #~(SCSCR_TE_EN + SCSCR_RE_EN)
-	strh	w1, [x0, #SCIF_SCSCR]
-
-	ret
-endfunc console_rcar_flush
diff --git a/drivers/renesas/rcar/watchdog/swdt.c b/drivers/renesas/rcar/watchdog/swdt.c
deleted file mode 100644
index 111e651..0000000
--- a/drivers/renesas/rcar/watchdog/swdt.c
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <drivers/arm/gicv2.h>
-#include <lib/mmio.h>
-
-#include "rcar_def.h"
-
-extern void gicd_set_icenabler(uintptr_t base, unsigned int id);
-
-#define RST_BASE			(0xE6160000U)
-#define RST_WDTRSTCR			(RST_BASE + 0x0054U)
-#define SWDT_BASE			(0xE6030000U)
-#define SWDT_WTCNT			(SWDT_BASE + 0x0000U)
-#define SWDT_WTCSRA			(SWDT_BASE + 0x0004U)
-#define SWDT_WTCSRB			(SWDT_BASE + 0x0008U)
-#define SWDT_GICD_BASE			(0xF1010000U)
-#define SWDT_GICC_BASE			(0xF1020000U)
-#define SWDT_GICD_CTLR			(SWDT_GICD_BASE + 0x0000U)
-#define SWDT_GICD_IGROUPR		(SWDT_GICD_BASE + 0x0080U)
-#define SWDT_GICD_ISPRIORITYR		(SWDT_GICD_BASE + 0x0400U)
-#define SWDT_GICC_CTLR			(SWDT_GICC_BASE + 0x0000U)
-#define SWDT_GICC_PMR			(SWDT_GICC_BASE + 0x0004U)
-#define SWDT_GICD_ITARGETSR		(SWDT_GICD_BASE + 0x0800U)
-#define IGROUPR_NUM			(16U)
-#define ISPRIORITY_NUM			(128U)
-#define ITARGET_MASK			(0x03U)
-
-#define WDTRSTCR_UPPER_BYTE		(0xA55A0000U)
-#define WTCSRA_UPPER_BYTE		(0xA5A5A500U)
-#define WTCSRB_UPPER_BYTE		(0xA5A5A500U)
-#define WTCNT_UPPER_BYTE		(0x5A5A0000U)
-#define WTCNT_RESET_VALUE		(0xF488U)
-#define WTCSRA_BIT_CKS			(0x0007U)
-#define WTCSRB_BIT_CKS			(0x003FU)
-#define SWDT_RSTMSK			(1U << 1U)
-#define WTCSRA_WOVFE			(1U << 3U)
-#define WTCSRA_WRFLG			(1U << 5U)
-#define SWDT_ENABLE			(1U << 7U)
-
-#define WDTRSTCR_MASK_ALL		(0x0000FFFFU)
-#define WTCSRA_MASK_ALL			(0x000000FFU)
-#define WTCNT_INIT_DATA			(WTCNT_UPPER_BYTE + WTCNT_RESET_VALUE)
-#define WTCSRA_INIT_DATA		(WTCSRA_UPPER_BYTE + 0x0FU)
-#define WTCSRB_INIT_DATA		(WTCSRB_UPPER_BYTE + 0x21U)
-
-#if RCAR_LSI == RCAR_D3
-#define WTCNT_COUNT_8p13k		(0x10000U - 40760U)
-#else
-#define WTCNT_COUNT_8p13k		(0x10000U - 40687U)
-#endif
-#define WTCNT_COUNT_8p13k_H3VER10	(0x10000U - 20343U)
-#define WTCNT_COUNT_8p22k		(0x10000U - 41115U)
-#define WTCNT_COUNT_7p81k		(0x10000U - 39062U)
-#define WTCSRA_CKS_DIV16		(0x00000002U)
-
-static void swdt_disable(void)
-{
-	uint32_t rmsk;
-
-	rmsk = mmio_read_32(RST_WDTRSTCR) & WDTRSTCR_MASK_ALL;
-	rmsk |= SWDT_RSTMSK;
-	mmio_write_32(RST_WDTRSTCR, WDTRSTCR_UPPER_BYTE | rmsk);
-
-	mmio_write_32(SWDT_WTCNT, WTCNT_INIT_DATA);
-	mmio_write_32(SWDT_WTCSRA, WTCSRA_INIT_DATA);
-	mmio_write_32(SWDT_WTCSRB, WTCSRB_INIT_DATA);
-
-	/* Set the interrupt clear enable register */
-	gicd_set_icenabler(RCAR_GICD_BASE, ARM_IRQ_SEC_WDT);
-}
-
-void rcar_swdt_init(void)
-{
-	uint32_t rmsk, sr;
-#if (RCAR_LSI != RCAR_E3)
-	uint32_t reg, val, product_cut, chk_data;
-
-	reg = mmio_read_32(RCAR_PRR);
-	product_cut = reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
-
-	reg = mmio_read_32(RCAR_MODEMR);
-	chk_data = reg & CHECK_MD13_MD14;
-#endif
-	/* stop watchdog */
-	if (mmio_read_32(SWDT_WTCSRA) & SWDT_ENABLE)
-		mmio_write_32(SWDT_WTCSRA, WTCSRA_UPPER_BYTE);
-
-	mmio_write_32(SWDT_WTCSRA, WTCSRA_UPPER_BYTE |
-		      WTCSRA_WOVFE | WTCSRA_CKS_DIV16);
-
-#if (RCAR_LSI == RCAR_E3)
-	mmio_write_32(SWDT_WTCNT, WTCNT_UPPER_BYTE | WTCNT_COUNT_7p81k);
-#else
-	val = WTCNT_UPPER_BYTE;
-
-	switch (chk_data) {
-	case MD14_MD13_TYPE_0:
-	case MD14_MD13_TYPE_2:
-		val |= WTCNT_COUNT_8p13k;
-		break;
-	case MD14_MD13_TYPE_1:
-		val |= WTCNT_COUNT_8p22k;
-		break;
-	case MD14_MD13_TYPE_3:
-		val |= product_cut == (PRR_PRODUCT_H3 | PRR_PRODUCT_10) ?
-		    WTCNT_COUNT_8p13k_H3VER10 : WTCNT_COUNT_8p13k;
-		break;
-	default:
-		ERROR("MODEMR ERROR value = %x\n", chk_data);
-		panic();
-		break;
-	}
-
-	mmio_write_32(SWDT_WTCNT, val);
-#endif
-	rmsk = mmio_read_32(RST_WDTRSTCR) & WDTRSTCR_MASK_ALL;
-	rmsk |= SWDT_RSTMSK | WDTRSTCR_UPPER_BYTE;
-	mmio_write_32(RST_WDTRSTCR, rmsk);
-
-	while ((mmio_read_8(SWDT_WTCSRA) & WTCSRA_WRFLG) != 0U)
-		;
-
-	/* Start the System WatchDog Timer */
-	sr = mmio_read_32(SWDT_WTCSRA) & WTCSRA_MASK_ALL;
-	mmio_write_32(SWDT_WTCSRA, (WTCSRA_UPPER_BYTE | sr | SWDT_ENABLE));
-}
-
-void rcar_swdt_release(void)
-{
-	uintptr_t itarget = SWDT_GICD_ITARGETSR +
-	    (ARM_IRQ_SEC_WDT & ~ITARGET_MASK);
-	uint32_t i;
-
-	/* Disable FIQ interrupt */
-	write_daifset(DAIF_FIQ_BIT);
-	/* FIQ interrupts are not taken to EL3 */
-	write_scr_el3(read_scr_el3() & ~SCR_FIQ_BIT);
-
-	swdt_disable();
-	gicv2_cpuif_disable();
-
-	for (i = 0; i < IGROUPR_NUM; i++)
-		mmio_write_32(SWDT_GICD_IGROUPR + i * 4, 0U);
-
-	for (i = 0; i < ISPRIORITY_NUM; i++)
-		mmio_write_32(SWDT_GICD_ISPRIORITYR + i * 4, 0U);
-
-	mmio_write_32(itarget, 0U);
-	mmio_write_32(SWDT_GICD_CTLR, 0U);
-	mmio_write_32(SWDT_GICC_CTLR, 0U);
-	mmio_write_32(SWDT_GICC_PMR, 0U);
-}
-
-void rcar_swdt_exec(uint64_t p)
-{
-	gicv2_end_of_interrupt(ARM_IRQ_SEC_WDT);
-	rcar_swdt_release();
-	ERROR("\n");
-	ERROR("System WDT overflow, occured address is %p\n", (void *)p);
-	panic();
-}
diff --git a/drivers/renesas/rzg/board/board.c b/drivers/renesas/rzg/board/board.c
new file mode 100644
index 0000000..7636372
--- /dev/null
+++ b/drivers/renesas/rzg/board/board.c
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+
+#include "board.h"
+#include "rcar_def.h"
+
+#ifndef BOARD_DEFAULT
+#if (RCAR_LSI == RZ_G2H)
+#define BOARD_DEFAULT		(BOARD_HIHOPE_RZ_G2H << BOARD_CODE_SHIFT)
+#elif (RCAR_LSI == RZ_G2N)
+#define BOARD_DEFAULT		(BOARD_HIHOPE_RZ_G2N << BOARD_CODE_SHIFT)
+#elif (RCAR_LSI == RZ_G2E)
+#define BOARD_DEFAULT		(BOARD_EK874_RZ_G2E << BOARD_CODE_SHIFT)
+#else
+#define BOARD_DEFAULT		(BOARD_HIHOPE_RZ_G2M << BOARD_CODE_SHIFT)
+#endif /* RCAR_LSI == RZ_G2H */
+#endif /* BOARD_DEFAULT */
+
+#define BOARD_CODE_MASK		(0xF8U)
+#define BOARD_REV_MASK		(0x07U)
+#define BOARD_CODE_SHIFT	(0x03)
+#define BOARD_ID_UNKNOWN	(0xFFU)
+
+#define GPIO_INDT5	0xE605500C
+#define GP5_19_BIT	(0x01U << 19)
+#define GP5_21_BIT	(0x01U << 21)
+#define GP5_25_BIT	(0x01U << 25)
+
+#define HM_ID	{ 0x10U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
+#define HH_ID	HM_ID
+#define HN_ID	{ 0x20U, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU, 0xFFU }
+#define EK_ID	HM_ID
+
+const char *g_board_tbl[] = {
+	[BOARD_HIHOPE_RZ_G2M] = "HiHope RZ/G2M",
+	[BOARD_HIHOPE_RZ_G2H] = "HiHope RZ/G2H",
+	[BOARD_HIHOPE_RZ_G2N] = "HiHope RZ/G2N",
+	[BOARD_EK874_RZ_G2E] = "EK874 RZ/G2E",
+	[BOARD_UNKNOWN] = "unknown"
+};
+
+void rzg_get_board_type(uint32_t *type, uint32_t *rev)
+{
+	static uint8_t board_id = BOARD_ID_UNKNOWN;
+	const uint8_t board_tbl[][8] = {
+		[BOARD_HIHOPE_RZ_G2M] = HM_ID,
+		[BOARD_HIHOPE_RZ_G2H] = HH_ID,
+		[BOARD_HIHOPE_RZ_G2N] = HN_ID,
+		[BOARD_EK874_RZ_G2E] = EK_ID,
+	};
+	uint32_t reg;
+#if (RCAR_LSI != RZ_G2E)
+	uint32_t boardInfo;
+#endif /* RCAR_LSI == RZ_G2E */
+
+	if (board_id == BOARD_ID_UNKNOWN) {
+		board_id = BOARD_DEFAULT;
+	}
+
+	*type = ((uint32_t) board_id & BOARD_CODE_MASK) >> BOARD_CODE_SHIFT;
+
+	if (*type >= ARRAY_SIZE(board_tbl)) {
+		/* no revision information, set Rev0.0. */
+		*rev = 0;
+		return;
+	}
+
+	reg = mmio_read_32(RCAR_PRR);
+#if (RCAR_LSI == RZ_G2E)
+	if (reg & RCAR_MINOR_MASK) {
+		*rev = 0x30U;
+	} else {
+		*rev = board_tbl[*type][(uint8_t)(board_id & BOARD_REV_MASK)];
+	}
+#else
+	if ((reg & PRR_CUT_MASK) == RCAR_M3_CUT_VER11) {
+		*rev = board_tbl[*type][(uint8_t)(board_id & BOARD_REV_MASK)];
+	} else {
+		reg = mmio_read_32(GPIO_INDT5);
+		if (reg & GP5_25_BIT) {
+			*rev = board_tbl[*type][(uint8_t)(board_id & BOARD_REV_MASK)];
+		} else {
+			boardInfo = reg & (GP5_19_BIT | GP5_21_BIT);
+			*rev = (((boardInfo & GP5_19_BIT) >> 14) |
+				((boardInfo & GP5_21_BIT) >> 17)) + 0x30U;
+		}
+	}
+#endif /* RCAR_LSI == RZ_G2E */
+}
diff --git a/drivers/renesas/rzg/board/board.h b/drivers/renesas/rzg/board/board.h
new file mode 100644
index 0000000..1a76849
--- /dev/null
+++ b/drivers/renesas/rzg/board/board.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RZ_G2_BOARD_H
+#define RZ_G2_BOARD_H
+
+enum rzg2_board_id {
+	BOARD_HIHOPE_RZ_G2M = 0,
+	BOARD_HIHOPE_RZ_G2H,
+	BOARD_HIHOPE_RZ_G2N,
+	BOARD_EK874_RZ_G2E,
+	BOARD_UNKNOWN
+};
+
+#define BOARD_REV_UNKNOWN	(0xFFU)
+
+extern const char *g_board_tbl[];
+
+/************************************************************************
+ * Revisions are expressed in 8 bits.
+ *  The upper 4 bits are major version.
+ *  The lower 4 bits are minor version.
+ ************************************************************************/
+#define GET_BOARD_MAJOR(a)	((uint32_t)(a) >> 0x4)
+#define GET_BOARD_MINOR(a)	((uint32_t)(a) &  0xF)
+#define GET_BOARD_NAME(a)	(g_board_tbl[(a)])
+
+void rzg_get_board_type(uint32_t *type, uint32_t *rev);
+
+#endif /* RZ_G2_BOARD_H */
diff --git a/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c b/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c
new file mode 100644
index 0000000..663df50
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c
@@ -0,0 +1,700 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <lib/mmio.h>
+
+#include "pfc_init_g2e.h"
+#include "rcar_def.h"
+
+#include "../pfc_regs.h"
+
+/* PFC */
+#define GPSR0_SDA4		BIT(17)
+#define GPSR0_SCL4		BIT(16)
+#define GPSR0_D15		BIT(15)
+#define GPSR0_D14		BIT(14)
+#define GPSR0_D13		BIT(13)
+#define GPSR0_D12		BIT(12)
+#define GPSR0_D11		BIT(11)
+#define GPSR0_D10		BIT(10)
+#define GPSR0_D9		BIT(9)
+#define GPSR0_D8		BIT(8)
+#define GPSR0_D7		BIT(7)
+#define GPSR0_D6		BIT(6)
+#define GPSR0_D5		BIT(5)
+#define GPSR0_D4		BIT(4)
+#define GPSR0_D3		BIT(3)
+#define GPSR0_D2		BIT(2)
+#define GPSR0_D1		BIT(1)
+#define GPSR0_D0		BIT(0)
+#define GPSR1_WE0		BIT(22)
+#define GPSR1_CS0		BIT(21)
+#define GPSR1_CLKOUT		BIT(20)
+#define GPSR1_A19		BIT(19)
+#define GPSR1_A18		BIT(18)
+#define GPSR1_A17		BIT(17)
+#define GPSR1_A16		BIT(16)
+#define GPSR1_A15		BIT(15)
+#define GPSR1_A14		BIT(14)
+#define GPSR1_A13		BIT(13)
+#define GPSR1_A12		BIT(12)
+#define GPSR1_A11		BIT(11)
+#define GPSR1_A10		BIT(10)
+#define GPSR1_A9		BIT(9)
+#define GPSR1_A8		BIT(8)
+#define GPSR1_A7		BIT(7)
+#define GPSR1_A6		BIT(6)
+#define GPSR1_A5		BIT(5)
+#define GPSR1_A4		BIT(4)
+#define GPSR1_A3		BIT(3)
+#define GPSR1_A2		BIT(2)
+#define GPSR1_A1		BIT(1)
+#define GPSR1_A0		BIT(0)
+#define GPSR2_BIT27_REVERSED	BIT(27)
+#define GPSR2_BIT26_REVERSED	BIT(26)
+#define GPSR2_EX_WAIT0		BIT(25)
+#define GPSR2_RD_WR		BIT(24)
+#define GPSR2_RD		BIT(23)
+#define GPSR2_BS		BIT(22)
+#define GPSR2_AVB_PHY_INT	BIT(21)
+#define GPSR2_AVB_TXCREFCLK	BIT(20)
+#define GPSR2_AVB_RD3		BIT(19)
+#define GPSR2_AVB_RD2		BIT(18)
+#define GPSR2_AVB_RD1		BIT(17)
+#define GPSR2_AVB_RD0		BIT(16)
+#define GPSR2_AVB_RXC		BIT(15)
+#define GPSR2_AVB_RX_CTL	BIT(14)
+#define GPSR2_RPC_RESET		BIT(13)
+#define GPSR2_RPC_RPC_INT	BIT(12)
+#define GPSR2_QSPI1_SSL		BIT(11)
+#define GPSR2_QSPI1_IO3		BIT(10)
+#define GPSR2_QSPI1_IO2		BIT(9)
+#define GPSR2_QSPI1_MISO_IO1	BIT(8)
+#define GPSR2_QSPI1_MOSI_IO0	BIT(7)
+#define GPSR2_QSPI1_SPCLK	BIT(6)
+#define GPSR2_QSPI0_SSL		BIT(5)
+#define GPSR2_QSPI0_IO3		BIT(4)
+#define GPSR2_QSPI0_IO2		BIT(3)
+#define GPSR2_QSPI0_MISO_IO1	BIT(2)
+#define GPSR2_QSPI0_MOSI_IO0	BIT(1)
+#define GPSR2_QSPI0_SPCLK	BIT(0)
+#define GPSR3_SD1_WP		BIT(15)
+#define GPSR3_SD1_CD		BIT(14)
+#define GPSR3_SD0_WP		BIT(13)
+#define GPSR3_SD0_CD		BIT(12)
+#define GPSR3_SD1_DAT3		BIT(11)
+#define GPSR3_SD1_DAT2		BIT(10)
+#define GPSR3_SD1_DAT1		BIT(9)
+#define GPSR3_SD1_DAT0		BIT(8)
+#define GPSR3_SD1_CMD		BIT(7)
+#define GPSR3_SD1_CLK		BIT(6)
+#define GPSR3_SD0_DAT3		BIT(5)
+#define GPSR3_SD0_DAT2		BIT(4)
+#define GPSR3_SD0_DAT1		BIT(3)
+#define GPSR3_SD0_DAT0		BIT(2)
+#define GPSR3_SD0_CMD		BIT(1)
+#define GPSR3_SD0_CLK		BIT(0)
+#define GPSR4_SD3_DS		BIT(10)
+#define GPSR4_SD3_DAT7		BIT(9)
+#define GPSR4_SD3_DAT6		BIT(8)
+#define GPSR4_SD3_DAT5		BIT(7)
+#define GPSR4_SD3_DAT4		BIT(6)
+#define GPSR4_SD3_DAT3		BIT(5)
+#define GPSR4_SD3_DAT2		BIT(4)
+#define GPSR4_SD3_DAT1		BIT(3)
+#define GPSR4_SD3_DAT0		BIT(2)
+#define GPSR4_SD3_CMD		BIT(1)
+#define GPSR4_SD3_CLK		BIT(0)
+#define GPSR5_MLB_DAT		BIT(19)
+#define GPSR5_MLB_SIG		BIT(18)
+#define GPSR5_MLB_CLK		BIT(17)
+#define GPSR5_SSI_SDATA9	BIT(16)
+#define GPSR5_MSIOF0_SS2	BIT(15)
+#define GPSR5_MSIOF0_SS1	BIT(14)
+#define GPSR5_MSIOF0_SYNC	BIT(13)
+#define GPSR5_MSIOF0_TXD	BIT(12)
+#define GPSR5_MSIOF0_RXD	BIT(11)
+#define GPSR5_MSIOF0_SCK	BIT(10)
+#define GPSR5_RX2_A		BIT(9)
+#define GPSR5_TX2_A		BIT(8)
+#define GPSR5_SCK2_A		BIT(7)
+#define GPSR5_TX1		BIT(6)
+#define GPSR5_RX1		BIT(5)
+#define GPSR5_RTS0_A		BIT(4)
+#define GPSR5_CTS0_A		BIT(3)
+#define GPSR5_TX0_A		BIT(2)
+#define GPSR5_RX0_A		BIT(1)
+#define GPSR5_SCK0_A		BIT(0)
+#define GPSR6_USB30_PWEN	BIT(17)
+#define GPSR6_SSI_SDATA6	BIT(16)
+#define GPSR6_SSI_WS6		BIT(15)
+#define GPSR6_SSI_SCK6		BIT(14)
+#define GPSR6_SSI_SDATA5	BIT(13)
+#define GPSR6_SSI_WS5		BIT(12)
+#define GPSR6_SSI_SCK5		BIT(11)
+#define GPSR6_SSI_SDATA4	BIT(10)
+#define GPSR6_USB30_OVC		BIT(9)
+#define GPSR6_AUDIO_CLKA	BIT(8)
+#define GPSR6_SSI_SDATA3	BIT(7)
+#define GPSR6_SSI_WS349		BIT(6)
+#define GPSR6_SSI_SCK349	BIT(5)
+#define GPSR6_SSI_SDATA2	BIT(4)
+#define GPSR6_SSI_SDATA1	BIT(3)
+#define GPSR6_SSI_SDATA0	BIT(2)
+#define GPSR6_SSI_WS01239	BIT(1)
+#define GPSR6_SSI_SCK01239	BIT(0)
+
+#define IPSR_28_FUNC(x)		((uint32_t)(x) << 28U)
+#define IPSR_24_FUNC(x)		((uint32_t)(x) << 24U)
+#define IPSR_20_FUNC(x)		((uint32_t)(x) << 20U)
+#define IPSR_16_FUNC(x)		((uint32_t)(x) << 16U)
+#define IPSR_12_FUNC(x)		((uint32_t)(x) << 12U)
+#define IPSR_8_FUNC(x)		((uint32_t)(x) << 8U)
+#define IPSR_4_FUNC(x)		((uint32_t)(x) << 4U)
+#define IPSR_0_FUNC(x)		((uint32_t)(x) << 0U)
+
+#define POCCTRL0_MASK		(0x0007F000U)
+#define POC_SD3_DS_33V		BIT(29)
+#define POC_SD3_DAT7_33V	BIT(28)
+#define POC_SD3_DAT6_33V	BIT(27)
+#define POC_SD3_DAT5_33V	BIT(26)
+#define POC_SD3_DAT4_33V	BIT(25)
+#define POC_SD3_DAT3_33V	BIT(24)
+#define POC_SD3_DAT2_33V	BIT(23)
+#define POC_SD3_DAT1_33V	BIT(22)
+#define POC_SD3_DAT0_33V	BIT(21)
+#define POC_SD3_CMD_33V		BIT(20)
+#define POC_SD3_CLK_33V		BIT(19)
+#define POC_SD1_DAT3_33V	BIT(11)
+#define POC_SD1_DAT2_33V	BIT(10)
+#define POC_SD1_DAT1_33V	BIT(9)
+#define POC_SD1_DAT0_33V	BIT(8)
+#define POC_SD1_CMD_33V		BIT(7)
+#define POC_SD1_CLK_33V		BIT(6)
+#define POC_SD0_DAT3_33V	BIT(5)
+#define POC_SD0_DAT2_33V	BIT(4)
+#define POC_SD0_DAT1_33V	BIT(3)
+#define POC_SD0_DAT0_33V	BIT(2)
+#define POC_SD0_CMD_33V		BIT(1)
+#define POC_SD0_CLK_33V		BIT(0)
+
+#define POCCTRL2_MASK		(0xFFFFFFFEU)
+#define POC2_VREF_33V		BIT(0)
+
+#define MOD_SEL0_ADGB_A			((uint32_t)0U << 29U)
+#define MOD_SEL0_ADGB_B			((uint32_t)1U << 29U)
+#define MOD_SEL0_ADGB_C			((uint32_t)2U << 29U)
+#define MOD_SEL0_DRIF0_A		((uint32_t)0U << 28U)
+#define MOD_SEL0_DRIF0_B		((uint32_t)1U << 28U)
+#define MOD_SEL0_FM_A			((uint32_t)0U << 26U)
+#define MOD_SEL0_FM_B			((uint32_t)1U << 26U)
+#define MOD_SEL0_FM_C			((uint32_t)2U << 26U)
+#define MOD_SEL0_FSO_A			((uint32_t)0U << 25U)
+#define MOD_SEL0_FSO_B			((uint32_t)1U << 25U)
+#define MOD_SEL0_HSCIF0_A		((uint32_t)0U << 24U)
+#define MOD_SEL0_HSCIF0_B		((uint32_t)1U << 24U)
+#define MOD_SEL0_HSCIF1_A		((uint32_t)0U << 23U)
+#define MOD_SEL0_HSCIF1_B		((uint32_t)1U << 23U)
+#define MOD_SEL0_HSCIF2_A		((uint32_t)0U << 22U)
+#define MOD_SEL0_HSCIF2_B		((uint32_t)1U << 22U)
+#define MOD_SEL0_I2C1_A			((uint32_t)0U << 20U)
+#define MOD_SEL0_I2C1_B			((uint32_t)1U << 20U)
+#define MOD_SEL0_I2C1_C			((uint32_t)2U << 20U)
+#define MOD_SEL0_I2C1_D			((uint32_t)3U << 20U)
+#define MOD_SEL0_I2C2_A			((uint32_t)0U << 17U)
+#define MOD_SEL0_I2C2_B			((uint32_t)1U << 17U)
+#define MOD_SEL0_I2C2_C			((uint32_t)2U << 17U)
+#define MOD_SEL0_I2C2_D			((uint32_t)3U << 17U)
+#define MOD_SEL0_I2C2_E			((uint32_t)4U << 17U)
+#define MOD_SEL0_NDFC_A			((uint32_t)0U << 16U)
+#define MOD_SEL0_NDFC_B			((uint32_t)1U << 16U)
+#define MOD_SEL0_PWM0_A			((uint32_t)0U << 15U)
+#define MOD_SEL0_PWM0_B			((uint32_t)1U << 15U)
+#define MOD_SEL0_PWM1_A			((uint32_t)0U << 14U)
+#define MOD_SEL0_PWM1_B			((uint32_t)1U << 14U)
+#define MOD_SEL0_PWM2_A			((uint32_t)0U << 12U)
+#define MOD_SEL0_PWM2_B			((uint32_t)1U << 12U)
+#define MOD_SEL0_PWM2_C			((uint32_t)2U << 12U)
+#define MOD_SEL0_PWM3_A			((uint32_t)0U << 10U)
+#define MOD_SEL0_PWM3_B			((uint32_t)1U << 10U)
+#define MOD_SEL0_PWM3_C			((uint32_t)2U << 10U)
+#define MOD_SEL0_PWM4_A			((uint32_t)0U << 9U)
+#define MOD_SEL0_PWM4_B			((uint32_t)1U << 9U)
+#define MOD_SEL0_PWM5_A			((uint32_t)0U << 8U)
+#define MOD_SEL0_PWM5_B			((uint32_t)1U << 8U)
+#define MOD_SEL0_PWM6_A			((uint32_t)0U << 7U)
+#define MOD_SEL0_PWM6_B			((uint32_t)1U << 7U)
+#define MOD_SEL0_REMOCON_A		((uint32_t)0U << 5U)
+#define MOD_SEL0_REMOCON_B		((uint32_t)1U << 5U)
+#define MOD_SEL0_REMOCON_C		((uint32_t)2U << 5U)
+#define MOD_SEL0_SCIF_A			((uint32_t)0U << 4U)
+#define MOD_SEL0_SCIF_B			((uint32_t)1U << 4U)
+#define MOD_SEL0_SCIF0_A		((uint32_t)0U << 3U)
+#define MOD_SEL0_SCIF0_B		((uint32_t)1U << 3U)
+#define MOD_SEL0_SCIF2_A		((uint32_t)0U << 2U)
+#define MOD_SEL0_SCIF2_B		((uint32_t)1U << 2U)
+#define MOD_SEL0_SPEED_PULSE_IF_A	((uint32_t)0U << 0U)
+#define MOD_SEL0_SPEED_PULSE_IF_B	((uint32_t)1U << 0U)
+#define MOD_SEL0_SPEED_PULSE_IF_C	((uint32_t)2U << 0U)
+#define MOD_SEL1_SIMCARD_A		((uint32_t)0U << 31U)
+#define MOD_SEL1_SIMCARD_B		((uint32_t)1U << 31U)
+#define MOD_SEL1_SSI2_A			((uint32_t)0U << 30U)
+#define MOD_SEL1_SSI2_B			((uint32_t)1U << 30U)
+#define MOD_SEL1_TIMER_TMU_A		((uint32_t)0U << 29U)
+#define MOD_SEL1_TIMER_TMU_B		((uint32_t)1U << 29U)
+#define MOD_SEL1_USB20_CH0_A		((uint32_t)0U << 28U)
+#define MOD_SEL1_USB20_CH0_B		((uint32_t)1U << 28U)
+#define MOD_SEL1_DRIF2_A		((uint32_t)0U << 26U)
+#define MOD_SEL1_DRIF2_B		((uint32_t)1U << 26U)
+#define MOD_SEL1_DRIF3_A		((uint32_t)0U << 25U)
+#define MOD_SEL1_DRIF3_B		((uint32_t)1U << 25U)
+#define MOD_SEL1_HSCIF3_A		((uint32_t)0U << 22U)
+#define MOD_SEL1_HSCIF3_B		((uint32_t)1U << 22U)
+#define MOD_SEL1_HSCIF3_C		((uint32_t)2U << 22U)
+#define MOD_SEL1_HSCIF3_D		((uint32_t)3U << 22U)
+#define MOD_SEL1_HSCIF3_E		((uint32_t)4U << 22U)
+#define MOD_SEL1_HSCIF4_A		((uint32_t)0U << 19U)
+#define MOD_SEL1_HSCIF4_B		((uint32_t)1U << 19U)
+#define MOD_SEL1_HSCIF4_C		((uint32_t)2U << 19U)
+#define MOD_SEL1_HSCIF4_D		((uint32_t)3U << 19U)
+#define MOD_SEL1_HSCIF4_E		((uint32_t)4U << 19U)
+#define MOD_SEL1_I2C6_A			((uint32_t)0U << 18U)
+#define MOD_SEL1_I2C6_B			((uint32_t)1U << 18U)
+#define MOD_SEL1_I2C7_A			((uint32_t)0U << 17U)
+#define MOD_SEL1_I2C7_B			((uint32_t)1U << 17U)
+#define MOD_SEL1_MSIOF2_A		((uint32_t)0U << 16U)
+#define MOD_SEL1_MSIOF2_B		((uint32_t)1U << 16U)
+#define MOD_SEL1_MSIOF3_A		((uint32_t)0U << 15U)
+#define MOD_SEL1_MSIOF3_B		((uint32_t)1U << 15U)
+#define MOD_SEL1_SCIF3_A		((uint32_t)0U << 13U)
+#define MOD_SEL1_SCIF3_B		((uint32_t)1U << 13U)
+#define MOD_SEL1_SCIF3_C		((uint32_t)2U << 13U)
+#define MOD_SEL1_SCIF4_A		((uint32_t)0U << 11U)
+#define MOD_SEL1_SCIF4_B		((uint32_t)1U << 11U)
+#define MOD_SEL1_SCIF4_C		((uint32_t)2U << 11U)
+#define MOD_SEL1_SCIF5_A		((uint32_t)0U << 9U)
+#define MOD_SEL1_SCIF5_B		((uint32_t)1U << 9U)
+#define MOD_SEL1_SCIF5_C		((uint32_t)2U << 9U)
+#define MOD_SEL1_VIN4_A			((uint32_t)0U << 8U)
+#define MOD_SEL1_VIN4_B			((uint32_t)1U << 8U)
+#define MOD_SEL1_VIN5_A			((uint32_t)0U << 7U)
+#define MOD_SEL1_VIN5_B			((uint32_t)1U << 7U)
+#define MOD_SEL1_ADGC_A			((uint32_t)0U << 5U)
+#define MOD_SEL1_ADGC_B			((uint32_t)1U << 5U)
+#define MOD_SEL1_ADGC_C			((uint32_t)2U << 5U)
+#define MOD_SEL1_SSI9_A			((uint32_t)0U << 4U)
+#define MOD_SEL1_SSI9_B			((uint32_t)1U << 4U)
+
+static void pfc_reg_write(uint32_t addr, uint32_t data)
+{
+	mmio_write_32(PFC_PMMR, ~data);
+	mmio_write_32((uintptr_t)addr, data);
+}
+
+void pfc_init_g2e(void)
+{
+	uint32_t reg;
+
+	/* initialize module select */
+	pfc_reg_write(PFC_MOD_SEL0,
+		      MOD_SEL0_ADGB_A |
+		      MOD_SEL0_DRIF0_A |
+		      MOD_SEL0_FM_A |
+		      MOD_SEL0_FSO_A |
+		      MOD_SEL0_HSCIF0_A |
+		      MOD_SEL0_HSCIF1_A |
+		      MOD_SEL0_HSCIF2_A |
+		      MOD_SEL0_I2C1_A |
+		      MOD_SEL0_I2C2_A |
+		      MOD_SEL0_NDFC_A |
+		      MOD_SEL0_PWM0_A |
+		      MOD_SEL0_PWM1_A |
+		      MOD_SEL0_PWM2_A |
+		      MOD_SEL0_PWM3_A |
+		      MOD_SEL0_PWM4_A |
+		      MOD_SEL0_PWM5_A |
+		      MOD_SEL0_PWM6_A |
+		      MOD_SEL0_REMOCON_A |
+		      MOD_SEL0_SCIF_A |
+		      MOD_SEL0_SCIF0_A |
+		      MOD_SEL0_SCIF2_A |
+		      MOD_SEL0_SPEED_PULSE_IF_A);
+
+	pfc_reg_write(PFC_MOD_SEL1,
+		      MOD_SEL1_SIMCARD_A |
+		      MOD_SEL1_SSI2_A |
+		      MOD_SEL1_TIMER_TMU_A |
+		      MOD_SEL1_USB20_CH0_B |
+		      MOD_SEL1_DRIF2_A |
+		      MOD_SEL1_DRIF3_A |
+		      MOD_SEL1_HSCIF3_C |
+		      MOD_SEL1_HSCIF4_B |
+		      MOD_SEL1_I2C6_A |
+		      MOD_SEL1_I2C7_A |
+		      MOD_SEL1_MSIOF2_A |
+		      MOD_SEL1_MSIOF3_A |
+		      MOD_SEL1_SCIF3_A |
+		      MOD_SEL1_SCIF4_A |
+		      MOD_SEL1_SCIF5_A |
+		      MOD_SEL1_VIN4_A |
+		      MOD_SEL1_VIN5_A |
+		      MOD_SEL1_ADGC_A |
+		      MOD_SEL1_SSI9_A);
+
+	/* initialize peripheral function select */
+	pfc_reg_write(PFC_IPSR0,
+		      IPSR_28_FUNC(2) |	/* HRX4_B */
+		      IPSR_24_FUNC(2) |	/* HTX4_B */
+		      IPSR_20_FUNC(0) |	/* QSPI1_SPCLK */
+		      IPSR_16_FUNC(0) |	/* QSPI0_IO3 */
+		      IPSR_12_FUNC(0) |	/* QSPI0_IO2 */
+		      IPSR_8_FUNC(0) |	/* QSPI0_MISO/IO1 */
+		      IPSR_4_FUNC(0) |	/* QSPI0_MOSI/IO0 */
+		      IPSR_0_FUNC(0));	/* QSPI0_SPCLK */
+
+	pfc_reg_write(PFC_IPSR1,
+		      IPSR_28_FUNC(0) |	/* AVB_RD2 */
+		      IPSR_24_FUNC(0) |	/* AVB_RD1 */
+		      IPSR_20_FUNC(0) |	/* AVB_RD0 */
+		      IPSR_16_FUNC(0) |	/* RPC_RESET# */
+		      IPSR_12_FUNC(0) |	/* RPC_INT# */
+		      IPSR_8_FUNC(0) |	/* QSPI1_SSL */
+		      IPSR_4_FUNC(2) |	/* HRX3_C */
+		      IPSR_0_FUNC(2));	/* HTX3_C */
+
+	pfc_reg_write(PFC_IPSR2,
+		      IPSR_28_FUNC(1) |	/* IRQ0 */
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(2) |	/* AVB_LINK */
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |	/* AVB_MDC */
+		      IPSR_4_FUNC(0) |	/* AVB_MDIO */
+		      IPSR_0_FUNC(0));	/* AVB_TXCREFCLK */
+
+	pfc_reg_write(PFC_IPSR3,
+		      IPSR_28_FUNC(5) |	/* DU_HSYNC */
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(5) |	/* DU_DG4 */
+		      IPSR_8_FUNC(5) |	/* DU_DOTCLKOUT0 */
+		      IPSR_4_FUNC(5) |	/* DU_DISP */
+		      IPSR_0_FUNC(1));	/* IRQ1 */
+
+	pfc_reg_write(PFC_IPSR4,
+		      IPSR_28_FUNC(5) |	/* DU_DB5 */
+		      IPSR_24_FUNC(5) |	/* DU_DB4 */
+		      IPSR_20_FUNC(5) |	/* DU_DB3 */
+		      IPSR_16_FUNC(5) |	/* DU_DB2 */
+		      IPSR_12_FUNC(5) |	/* DU_DG6 */
+		      IPSR_8_FUNC(5) |	/* DU_VSYNC */
+		      IPSR_4_FUNC(5) |	/* DU_DG5 */
+		      IPSR_0_FUNC(5));	/* DU_DG7 */
+
+	pfc_reg_write(PFC_IPSR5,
+		      IPSR_28_FUNC(5) |	/* DU_DR3 */
+		      IPSR_24_FUNC(5) |	/* DU_DB7 */
+		      IPSR_20_FUNC(5) |	/* DU_DR2 */
+		      IPSR_16_FUNC(5) |	/* DU_DR1 */
+		      IPSR_12_FUNC(5) |	/* DU_DR0 */
+		      IPSR_8_FUNC(5) |	/* DU_DB1 */
+		      IPSR_4_FUNC(5) |	/* DU_DB0 */
+		      IPSR_0_FUNC(5));	/* DU_DB6 */
+
+	pfc_reg_write(PFC_IPSR6,
+		      IPSR_28_FUNC(5) |	/* DU_DG1 */
+		      IPSR_24_FUNC(5) |	/* DU_DG0 */
+		      IPSR_20_FUNC(5) |	/* DU_DR7 */
+		      IPSR_16_FUNC(1) |	/* CANFD1_RX */
+		      IPSR_12_FUNC(5) |	/* DU_DR6 */
+		      IPSR_8_FUNC(5) |	/* DU_DR5 */
+		      IPSR_4_FUNC(1) |	/* CANFD1_TX */
+		      IPSR_0_FUNC(5));	/* DU_DR4 */
+
+	pfc_reg_write(PFC_IPSR7,
+		      IPSR_28_FUNC(0) |	/* SD0_CLK */
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(5) |	/* DU_DOTCLKIN0 */
+		      IPSR_16_FUNC(5) |	/* DU_DG3 */
+		      IPSR_12_FUNC(1) |	/* CAN_CLK */
+		      IPSR_8_FUNC(1) |	/* CANFD0_RX */
+		      IPSR_4_FUNC(1) |	/* CANFD0_TX */
+		      IPSR_0_FUNC(5));	/* DU_DG2 */
+
+	pfc_reg_write(PFC_IPSR8,
+		      IPSR_28_FUNC(0) |	/* SD1_DAT0 */
+		      IPSR_24_FUNC(0) |	/* SD1_CMD */
+		      IPSR_20_FUNC(0) |	/* SD1_CLK */
+		      IPSR_16_FUNC(0) |	/* SD0_DAT3 */
+		      IPSR_12_FUNC(0) |	/* SD0_DAT2 */
+		      IPSR_8_FUNC(0) |	/* SD0_DAT1 */
+		      IPSR_4_FUNC(0) |	/* SD0_DAT0 */
+		      IPSR_0_FUNC(0));	/* SD0_CMD */
+
+	pfc_reg_write(PFC_IPSR9,
+		      IPSR_28_FUNC(0) |	/* SD3_DAT2 */
+		      IPSR_24_FUNC(0) |	/* SD3_DAT1 */
+		      IPSR_20_FUNC(0) |	/* SD3_DAT0 */
+		      IPSR_16_FUNC(0) |	/* SD3_CMD */
+		      IPSR_12_FUNC(0) |	/* SD3_CLK */
+		      IPSR_8_FUNC(0) |	/* SD1_DAT3 */
+		      IPSR_4_FUNC(0) |	/* SD1_DAT2 */
+		      IPSR_0_FUNC(0));	/* SD1_DAT1 */
+
+	pfc_reg_write(PFC_IPSR10,
+		      IPSR_24_FUNC(0) |	/* SD0_CD */
+		      IPSR_20_FUNC(0) |	/* SD3_DS */
+		      IPSR_16_FUNC(0) |	/* SD3_DAT7 */
+		      IPSR_12_FUNC(0) |	/* SD3_DAT6 */
+		      IPSR_8_FUNC(0) |	/* SD3_DAT5 */
+		      IPSR_4_FUNC(0) |	/* SD3_DAT4 */
+		      IPSR_0_FUNC(0));	/* SD3_DAT3 */
+
+	pfc_reg_write(PFC_IPSR11,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(8) |	/* USB0_ID */
+		      IPSR_20_FUNC(2) |	/* AUDIO_CLKOUT1_A */
+		      IPSR_16_FUNC(0) |	/* CTS0#_A */
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |	/* SD1_WP */
+		      IPSR_0_FUNC(0));	/* SD1_CD */
+
+	pfc_reg_write(PFC_IPSR12,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |	/* RX2_A */
+		      IPSR_8_FUNC(0) |	/* TX2_A */
+		      IPSR_4_FUNC(0) |	/* SCK2_A */
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR13,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(4) |	/* SDA1_B */
+		      IPSR_12_FUNC(4) |	/* SCL1_B */
+		      IPSR_8_FUNC(0) |	/* SSI_SDATA9 */
+		      IPSR_4_FUNC(1) |	/* HTX2_A */
+		      IPSR_0_FUNC(1));	/* HRX2_A */
+
+	pfc_reg_write(PFC_IPSR14,
+		      IPSR_28_FUNC(0) |	/* SSI_SCK5 */
+		      IPSR_24_FUNC(0) |	/* SSI_SDATA4 */
+		      IPSR_20_FUNC(0) |	/* SSI_SDATA3 */
+		      IPSR_16_FUNC(0) |	/* SSI_WS349 */
+		      IPSR_12_FUNC(0) |	/* SSI_SCK349 */
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |	/* SSI_SDATA1 */
+		      IPSR_0_FUNC(0));/* SSI_SDATA0 */
+
+	pfc_reg_write(PFC_IPSR15,
+		      IPSR_28_FUNC(0) |	/* USB30_OVC */
+		      IPSR_24_FUNC(0) |	/* USB30_PWEN */
+		      IPSR_20_FUNC(0) |	/* AUDIO_CLKA */
+		      IPSR_16_FUNC(1) |	/* HRTS2#_A */
+		      IPSR_12_FUNC(1) |	/* HCTS2#_A */
+		      IPSR_8_FUNC(3) |	/* TPU0TO1 */
+		      IPSR_4_FUNC(3) |	/* TPU0TO0 */
+		      IPSR_0_FUNC(0));	/* SSI_WS5 */
+
+	/* initialize GPIO/peripheral function select */
+	pfc_reg_write(PFC_GPSR0,
+		      GPSR0_SCL4 |
+		      GPSR0_D15 |
+		      GPSR0_D14 |
+		      GPSR0_D13 |
+		      GPSR0_D12 |
+		      GPSR0_D11 |
+		      GPSR0_D10 |
+		      GPSR0_D9 |
+		      GPSR0_D8 |
+		      GPSR0_D7 |
+		      GPSR0_D6 |
+		      GPSR0_D5 |
+		      GPSR0_D4 |
+		      GPSR0_D3 |
+		      GPSR0_D2 |
+		      GPSR0_D1 |
+		      GPSR0_D0);
+
+	pfc_reg_write(PFC_GPSR1,
+		      GPSR1_WE0 |
+		      GPSR1_CS0 |
+		      GPSR1_A19 |
+		      GPSR1_A18 |
+		      GPSR1_A17 |
+		      GPSR1_A16 |
+		      GPSR1_A15 |
+		      GPSR1_A14 |
+		      GPSR1_A13 |
+		      GPSR1_A12 |
+		      GPSR1_A11 |
+		      GPSR1_A10 |
+		      GPSR1_A9 |
+		      GPSR1_A8 |
+		      GPSR1_A4 |
+		      GPSR1_A3 |
+		      GPSR1_A2 |
+		      GPSR1_A1 |
+		      GPSR1_A0);
+
+	pfc_reg_write(PFC_GPSR2,
+		      GPSR2_BIT27_REVERSED |
+		      GPSR2_BIT26_REVERSED |
+		      GPSR2_AVB_PHY_INT |
+		      GPSR2_AVB_TXCREFCLK |
+		      GPSR2_AVB_RD3 |
+		      GPSR2_AVB_RD2 |
+		      GPSR2_AVB_RD1 |
+		      GPSR2_AVB_RD0 |
+		      GPSR2_AVB_RXC |
+		      GPSR2_AVB_RX_CTL |
+		      GPSR2_RPC_RESET |
+		      GPSR2_RPC_RPC_INT |
+		      GPSR2_QSPI1_IO3 |
+		      GPSR2_QSPI1_IO2 |
+		      GPSR2_QSPI1_MISO_IO1 |
+		      GPSR2_QSPI1_MOSI_IO0 |
+		      GPSR2_QSPI0_SSL |
+		      GPSR2_QSPI0_IO3 |
+		      GPSR2_QSPI0_IO2 |
+		      GPSR2_QSPI0_MISO_IO1 |
+		      GPSR2_QSPI0_MOSI_IO0 |
+		      GPSR2_QSPI0_SPCLK);
+
+	pfc_reg_write(PFC_GPSR3,
+		      GPSR3_SD0_CD |
+		      GPSR3_SD1_DAT3 |
+		      GPSR3_SD1_DAT2 |
+		      GPSR3_SD1_DAT1 |
+		      GPSR3_SD1_DAT0 |
+		      GPSR3_SD1_CMD |
+		      GPSR3_SD1_CLK |
+		      GPSR3_SD0_DAT3 |
+		      GPSR3_SD0_DAT2 |
+		      GPSR3_SD0_DAT1 |
+		      GPSR3_SD0_DAT0 |
+		      GPSR3_SD0_CMD |
+		      GPSR3_SD0_CLK);
+
+	pfc_reg_write(PFC_GPSR4,
+		      GPSR4_SD3_DAT3 |
+		      GPSR4_SD3_DAT2 |
+		      GPSR4_SD3_DAT1 |
+		      GPSR4_SD3_DAT0 |
+		      GPSR4_SD3_CMD |
+		      GPSR4_SD3_CLK);
+
+	pfc_reg_write(PFC_GPSR5,
+		      GPSR5_MLB_SIG |
+		      GPSR5_MLB_CLK |
+		      GPSR5_SSI_SDATA9 |
+		      GPSR5_MSIOF0_SS2 |
+		      GPSR5_MSIOF0_SS1 |
+		      GPSR5_MSIOF0_SYNC |
+		      GPSR5_MSIOF0_TXD |
+		      GPSR5_MSIOF0_RXD |
+		      GPSR5_MSIOF0_SCK |
+		      GPSR5_RX2_A |
+		      GPSR5_TX2_A |
+		      GPSR5_RTS0_A |
+		      GPSR5_SCK0_A);
+
+	pfc_reg_write(PFC_GPSR6,
+		      GPSR6_USB30_PWEN |
+		      GPSR6_SSI_SDATA6 |
+		      GPSR6_SSI_WS6 |
+		      GPSR6_SSI_SCK6 |
+		      GPSR6_SSI_SDATA5 |
+		      GPSR6_SSI_SCK5 |
+		      GPSR6_SSI_SDATA4 |
+		      GPSR6_USB30_OVC |
+		      GPSR6_AUDIO_CLKA |
+		      GPSR6_SSI_SDATA3 |
+		      GPSR6_SSI_WS349 |
+		      GPSR6_SSI_SCK349 |
+		      GPSR6_SSI_SDATA0 |
+		      GPSR6_SSI_WS01239 |
+		      GPSR6_SSI_SCK01239);
+
+	/* initialize POC control */
+	reg = mmio_read_32(PFC_POCCTRL0);
+	reg = (reg & POCCTRL0_MASK) |
+	      POC_SD1_DAT3_33V |
+	      POC_SD1_DAT2_33V |
+	      POC_SD1_DAT1_33V |
+	      POC_SD1_DAT0_33V |
+	      POC_SD1_CMD_33V |
+	      POC_SD1_CLK_33V |
+	      POC_SD0_DAT3_33V |
+	      POC_SD0_DAT2_33V |
+	      POC_SD0_DAT1_33V |
+	      POC_SD0_DAT0_33V |
+	      POC_SD0_CMD_33V |
+	      POC_SD0_CLK_33V;
+	pfc_reg_write(PFC_POCCTRL0, reg);
+
+	reg = mmio_read_32(PFC_POCCTRL2);
+	reg = ((reg & POCCTRL2_MASK) & ~POC2_VREF_33V);
+	pfc_reg_write(PFC_POCCTRL2, reg);
+
+	/* initialize LSI pin pull-up/down control */
+	pfc_reg_write(PFC_PUD0, 0x00080000U);
+	pfc_reg_write(PFC_PUD1, 0xCE398464U);
+	pfc_reg_write(PFC_PUD2, 0xA4C380F4U);
+	pfc_reg_write(PFC_PUD3, 0x0000079FU);
+	pfc_reg_write(PFC_PUD4, 0xFFF0FFFFU);
+	pfc_reg_write(PFC_PUD5, 0x40000000U);
+
+	/* initialize LSI pin pull-enable register */
+	pfc_reg_write(PFC_PUEN0, 0x00000000U);
+	pfc_reg_write(PFC_PUEN1, 0x00300000U);
+	pfc_reg_write(PFC_PUEN2, 0x00400074U);
+	pfc_reg_write(PFC_PUEN3, 0x00000000U);
+	pfc_reg_write(PFC_PUEN4, 0x07900600U);
+	pfc_reg_write(PFC_PUEN5, 0x00000000U);
+
+	/* initialize positive/negative logic select */
+	mmio_write_32(GPIO_POSNEG0, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG1, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG2, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG3, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG4, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG5, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG6, 0x00000000U);
+
+	/* initialize general IO/interrupt switching */
+	mmio_write_32(GPIO_IOINTSEL0, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL1, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL2, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL3, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL4, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL5, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL6, 0x00000000U);
+
+	/* initialize general output register */
+	mmio_write_32(GPIO_OUTDT0, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT1, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT2, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT3, 0x00006000U);
+	mmio_write_32(GPIO_OUTDT5, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT6, 0x00000000U);
+
+	/* initialize general input/output switching */
+	mmio_write_32(GPIO_INOUTSEL0, 0x00020000U);
+	mmio_write_32(GPIO_INOUTSEL1, 0x00100000U);
+	mmio_write_32(GPIO_INOUTSEL2, 0x03000000U);
+	mmio_write_32(GPIO_INOUTSEL3, 0x0000E000U);
+	mmio_write_32(GPIO_INOUTSEL4, 0x00000440U);
+	mmio_write_32(GPIO_INOUTSEL5, 0x00080000U);
+	mmio_write_32(GPIO_INOUTSEL6, 0x00000010U);
+}
diff --git a/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.h b/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.h
new file mode 100644
index 0000000..677591a
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PFC_INIT_G2E_H
+#define PFC_INIT_G2E_H
+
+void pfc_init_g2e(void);
+
+#endif /* PFC_INIT_G2E_H */
diff --git a/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c b/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c
new file mode 100644
index 0000000..90a1c99
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c
@@ -0,0 +1,1310 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <lib/mmio.h>
+
+#include "pfc_init_g2h.h"
+#include "rcar_def.h"
+#include "../pfc_regs.h"
+
+#define GPSR0_D15			BIT(15)
+#define GPSR0_D14			BIT(14)
+#define GPSR0_D13			BIT(13)
+#define GPSR0_D12			BIT(12)
+#define GPSR0_D11			BIT(11)
+#define GPSR0_D10			BIT(10)
+#define GPSR0_D9			BIT(9)
+#define GPSR0_D8			BIT(8)
+#define GPSR0_D7			BIT(7)
+#define GPSR0_D6			BIT(6)
+#define GPSR0_D5			BIT(5)
+#define GPSR0_D4			BIT(4)
+#define GPSR0_D3			BIT(3)
+#define GPSR0_D2			BIT(2)
+#define GPSR0_D1			BIT(1)
+#define GPSR0_D0			BIT(0)
+#define GPSR1_CLKOUT			BIT(28)
+#define GPSR1_EX_WAIT0_A		BIT(27)
+#define GPSR1_WE1			BIT(26)
+#define GPSR1_WE0			BIT(25)
+#define GPSR1_RD_WR			BIT(24)
+#define GPSR1_RD			BIT(23)
+#define GPSR1_BS			BIT(22)
+#define GPSR1_CS1_A26			BIT(21)
+#define GPSR1_CS0			BIT(20)
+#define GPSR1_A19			BIT(19)
+#define GPSR1_A18			BIT(18)
+#define GPSR1_A17			BIT(17)
+#define GPSR1_A16			BIT(16)
+#define GPSR1_A15			BIT(15)
+#define GPSR1_A14			BIT(14)
+#define GPSR1_A13			BIT(13)
+#define GPSR1_A12			BIT(12)
+#define GPSR1_A11			BIT(11)
+#define GPSR1_A10			BIT(10)
+#define GPSR1_A9			BIT(9)
+#define GPSR1_A8			BIT(8)
+#define GPSR1_A7			BIT(7)
+#define GPSR1_A6			BIT(6)
+#define GPSR1_A5			BIT(5)
+#define GPSR1_A4			BIT(4)
+#define GPSR1_A3			BIT(3)
+#define GPSR1_A2			BIT(2)
+#define GPSR1_A1			BIT(1)
+#define GPSR1_A0			BIT(0)
+#define GPSR2_AVB_AVTP_CAPTURE_A	BIT(14)
+#define GPSR2_AVB_AVTP_MATCH_A		BIT(13)
+#define GPSR2_AVB_LINK			BIT(12)
+#define GPSR2_AVB_PHY_INT		BIT(11)
+#define GPSR2_AVB_MAGIC			BIT(10)
+#define GPSR2_AVB_MDC			BIT(9)
+#define GPSR2_PWM2_A			BIT(8)
+#define GPSR2_PWM1_A			BIT(7)
+#define GPSR2_PWM0			BIT(6)
+#define GPSR2_IRQ5			BIT(5)
+#define GPSR2_IRQ4			BIT(4)
+#define GPSR2_IRQ3			BIT(3)
+#define GPSR2_IRQ2			BIT(2)
+#define GPSR2_IRQ1			BIT(1)
+#define GPSR2_IRQ0			BIT(0)
+#define GPSR3_SD1_WP			BIT(15)
+#define GPSR3_SD1_CD			BIT(14)
+#define GPSR3_SD0_WP			BIT(13)
+#define GPSR3_SD0_CD			BIT(12)
+#define GPSR3_SD1_DAT3			BIT(11)
+#define GPSR3_SD1_DAT2			BIT(10)
+#define GPSR3_SD1_DAT1			BIT(9)
+#define GPSR3_SD1_DAT0			BIT(8)
+#define GPSR3_SD1_CMD			BIT(7)
+#define GPSR3_SD1_CLK			BIT(6)
+#define GPSR3_SD0_DAT3			BIT(5)
+#define GPSR3_SD0_DAT2			BIT(4)
+#define GPSR3_SD0_DAT1			BIT(3)
+#define GPSR3_SD0_DAT0			BIT(2)
+#define GPSR3_SD0_CMD			BIT(1)
+#define GPSR3_SD0_CLK			BIT(0)
+#define GPSR4_SD3_DS			BIT(17)
+#define GPSR4_SD3_DAT7			BIT(16)
+#define GPSR4_SD3_DAT6			BIT(15)
+#define GPSR4_SD3_DAT5			BIT(14)
+#define GPSR4_SD3_DAT4			BIT(13)
+#define GPSR4_SD3_DAT3			BIT(12)
+#define GPSR4_SD3_DAT2			BIT(11)
+#define GPSR4_SD3_DAT1			BIT(10)
+#define GPSR4_SD3_DAT0			BIT(9)
+#define GPSR4_SD3_CMD			BIT(8)
+#define GPSR4_SD3_CLK			BIT(7)
+#define GPSR4_SD2_DS			BIT(6)
+#define GPSR4_SD2_DAT3			BIT(5)
+#define GPSR4_SD2_DAT2			BIT(4)
+#define GPSR4_SD2_DAT1			BIT(3)
+#define GPSR4_SD2_DAT0			BIT(2)
+#define GPSR4_SD2_CMD			BIT(1)
+#define GPSR4_SD2_CLK			BIT(0)
+#define GPSR5_MLB_DAT			BIT(25)
+#define GPSR5_MLB_SIG			BIT(24)
+#define GPSR5_MLB_CLK			BIT(23)
+#define GPSR5_MSIOF0_RXD		BIT(22)
+#define GPSR5_MSIOF0_SS2		BIT(21)
+#define GPSR5_MSIOF0_TXD		BIT(20)
+#define GPSR5_MSIOF0_SS1		BIT(19)
+#define GPSR5_MSIOF0_SYNC		BIT(18)
+#define GPSR5_MSIOF0_SCK		BIT(17)
+#define GPSR5_HRTS0			BIT(16)
+#define GPSR5_HCTS0			BIT(15)
+#define GPSR5_HTX0			BIT(14)
+#define GPSR5_HRX0			BIT(13)
+#define GPSR5_HSCK0			BIT(12)
+#define GPSR5_RX2_A			BIT(11)
+#define GPSR5_TX2_A			BIT(10)
+#define GPSR5_SCK2			BIT(9)
+#define GPSR5_RTS1			BIT(8)
+#define GPSR5_CTS1			BIT(7)
+#define GPSR5_TX1_A			BIT(6)
+#define GPSR5_RX1_A			BIT(5)
+#define GPSR5_RTS0			BIT(4)
+#define GPSR5_CTS0			BIT(3)
+#define GPSR5_TX0			BIT(2)
+#define GPSR5_RX0			BIT(1)
+#define GPSR5_SCK0			BIT(0)
+#define GPSR6_USB31_OVC			BIT(31)
+#define GPSR6_USB31_PWEN		BIT(30)
+#define GPSR6_USB30_OVC			BIT(29)
+#define GPSR6_USB30_PWEN		BIT(28)
+#define GPSR6_USB1_OVC			BIT(27)
+#define GPSR6_USB1_PWEN			BIT(26)
+#define GPSR6_USB0_OVC			BIT(25)
+#define GPSR6_USB0_PWEN			BIT(24)
+#define GPSR6_AUDIO_CLKB_B		BIT(23)
+#define GPSR6_AUDIO_CLKA_A		BIT(22)
+#define GPSR6_SSI_SDATA9_A		BIT(21)
+#define GPSR6_SSI_SDATA8		BIT(20)
+#define GPSR6_SSI_SDATA7		BIT(19)
+#define GPSR6_SSI_WS78			BIT(18)
+#define GPSR6_SSI_SCK78			BIT(17)
+#define GPSR6_SSI_SDATA6		BIT(16)
+#define GPSR6_SSI_WS6			BIT(15)
+#define GPSR6_SSI_SCK6			BIT(14)
+#define GPSR6_SSI_SDATA5		BIT(13)
+#define GPSR6_SSI_WS5			BIT(12)
+#define GPSR6_SSI_SCK5			BIT(11)
+#define GPSR6_SSI_SDATA4		BIT(10)
+#define GPSR6_SSI_WS4			BIT(9)
+#define GPSR6_SSI_SCK4			BIT(8)
+#define GPSR6_SSI_SDATA3		BIT(7)
+#define GPSR6_SSI_WS34			BIT(6)
+#define GPSR6_SSI_SCK34			BIT(5)
+#define GPSR6_SSI_SDATA2_A		BIT(4)
+#define GPSR6_SSI_SDATA1_A		BIT(3)
+#define GPSR6_SSI_SDATA0		BIT(2)
+#define GPSR6_SSI_WS0129		BIT(1)
+#define GPSR6_SSI_SCK0129		BIT(0)
+#define GPSR7_AVS2			BIT(1)
+#define GPSR7_AVS1			BIT(0)
+
+#define IPSR_28_FUNC(x)			((uint32_t)(x) << 28U)
+#define IPSR_24_FUNC(x)			((uint32_t)(x) << 24U)
+#define IPSR_20_FUNC(x)			((uint32_t)(x) << 20U)
+#define IPSR_16_FUNC(x)			((uint32_t)(x) << 16U)
+#define IPSR_12_FUNC(x)			((uint32_t)(x) << 12U)
+#define IPSR_8_FUNC(x)			((uint32_t)(x) << 8U)
+#define IPSR_4_FUNC(x)			((uint32_t)(x) << 4U)
+#define IPSR_0_FUNC(x)			((uint32_t)(x) << 0U)
+
+#define POC_SD3_DS_33V			BIT(29)
+#define POC_SD3_DAT7_33V		BIT(28)
+#define POC_SD3_DAT6_33V		BIT(27)
+#define POC_SD3_DAT5_33V		BIT(26)
+#define POC_SD3_DAT4_33V		BIT(25)
+#define POC_SD3_DAT3_33V		BIT(24)
+#define POC_SD3_DAT2_33V		BIT(23)
+#define POC_SD3_DAT1_33V		BIT(22)
+#define POC_SD3_DAT0_33V		BIT(21)
+#define POC_SD3_CMD_33V			BIT(20)
+#define POC_SD3_CLK_33V			BIT(19)
+#define POC_SD2_DS_33V			BIT(18)
+#define POC_SD2_DAT3_33V		BIT(17)
+#define POC_SD2_DAT2_33V		BIT(16)
+#define POC_SD2_DAT1_33V		BIT(15)
+#define POC_SD2_DAT0_33V		BIT(14)
+#define POC_SD2_CMD_33V			BIT(13)
+#define POC_SD2_CLK_33V			BIT(12)
+#define POC_SD1_DAT3_33V		BIT(11)
+#define POC_SD1_DAT2_33V		BIT(10)
+#define POC_SD1_DAT1_33V		BIT(9)
+#define POC_SD1_DAT0_33V		BIT(8)
+#define POC_SD1_CMD_33V			BIT(7)
+#define POC_SD1_CLK_33V			BIT(6)
+#define POC_SD0_DAT3_33V		BIT(5)
+#define POC_SD0_DAT2_33V		BIT(4)
+#define POC_SD0_DAT1_33V		BIT(3)
+#define POC_SD0_DAT0_33V		BIT(2)
+#define POC_SD0_CMD_33V			BIT(1)
+#define POC_SD0_CLK_33V			BIT(0)
+
+#define DRVCTRL0_MASK			(0xCCCCCCCCU)
+#define DRVCTRL1_MASK			(0xCCCCCCC8U)
+#define DRVCTRL2_MASK			(0x88888888U)
+#define DRVCTRL3_MASK			(0x88888888U)
+#define DRVCTRL4_MASK			(0x88888888U)
+#define DRVCTRL5_MASK			(0x88888888U)
+#define DRVCTRL6_MASK			(0x88888888U)
+#define DRVCTRL7_MASK			(0x88888888U)
+#define DRVCTRL8_MASK			(0x88888888U)
+#define DRVCTRL9_MASK			(0x88888888U)
+#define DRVCTRL10_MASK			(0x88888888U)
+#define DRVCTRL11_MASK			(0x888888CCU)
+#define DRVCTRL12_MASK			(0xCCCFFFCFU)
+#define DRVCTRL13_MASK			(0xCC888888U)
+#define DRVCTRL14_MASK			(0x88888888U)
+#define DRVCTRL15_MASK			(0x88888888U)
+#define DRVCTRL16_MASK			(0x88888888U)
+#define DRVCTRL17_MASK			(0x88888888U)
+#define DRVCTRL18_MASK			(0x88888888U)
+#define DRVCTRL19_MASK			(0x88888888U)
+#define DRVCTRL20_MASK			(0x88888888U)
+#define DRVCTRL21_MASK			(0x88888888U)
+#define DRVCTRL22_MASK			(0x88888888U)
+#define DRVCTRL23_MASK			(0x88888888U)
+#define DRVCTRL24_MASK			(0x8888888FU)
+
+#define DRVCTRL0_QSPI0_SPCLK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL0_QSPI0_MOSI_IO0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL0_QSPI0_MISO_IO1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL0_QSPI0_IO2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL0_QSPI0_IO3(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL0_QSPI0_SSL(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL0_QSPI1_SPCLK(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL0_QSPI1_MOSI_IO0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL1_QSPI1_MISO_IO1(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL1_QSPI1_IO2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL1_QSPI1_IO3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL1_QSPI1_SS(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL1_RPC_INT(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL1_RPC_WP(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL1_RPC_RESET(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL1_AVB_RX_CTL(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL2_AVB_RXC(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL2_AVB_RD0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL2_AVB_RD1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL2_AVB_RD2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL2_AVB_RD3(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL2_AVB_TX_CTL(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL2_AVB_TXC(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL2_AVB_TD0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL3_AVB_TD1(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL3_AVB_TD2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL3_AVB_TD3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL3_AVB_TXCREFCLK(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL3_AVB_MDIO(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL3_AVB_MDC(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL3_AVB_MAGIC(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL3_AVB_PHY_INT(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL4_AVB_LINK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL4_AVB_AVTP_MATCH(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL4_AVB_AVTP_CAPTURE(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL4_IRQ0(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL4_IRQ1(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL4_IRQ2(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL4_IRQ3(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL4_IRQ4(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL5_IRQ5(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL5_PWM0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL5_PWM1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL5_PWM2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL5_A0(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL5_A1(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL5_A2(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL5_A3(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL6_A4(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL6_A5(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL6_A6(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL6_A7(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL6_A8(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL6_A9(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL6_A10(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL6_A11(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL7_A12(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL7_A13(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL7_A14(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL7_A15(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL7_A16(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL7_A17(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL7_A18(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL7_A19(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL8_CLKOUT(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL8_CS0(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL8_CS1_A2(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL8_BS(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL8_RD(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL8_RD_W(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL8_WE0(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL8_WE1(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL9_EX_WAIT0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL9_PRESETOU(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL9_D0(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL9_D1(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL9_D2(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL9_D3(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL9_D4(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL9_D5(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL10_D6(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL10_D7(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL10_D8(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL10_D9(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL10_D10(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL10_D11(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL10_D12(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL10_D13(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL11_D14(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL11_D15(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL11_AVS1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL11_AVS2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL11_GP7_02(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL11_GP7_03(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL11_DU_DOTCLKIN0(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL11_DU_DOTCLKIN1(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL12_DU_DOTCLKIN2(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL12_DU_DOTCLKIN3(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL12_DU_FSCLKST(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL12_DU_TMS(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL13_TDO(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL13_ASEBRK(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL13_SD0_CLK(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL13_SD0_CMD(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL13_SD0_DAT0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL13_SD0_DAT1(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL13_SD0_DAT2(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL13_SD0_DAT3(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL14_SD1_CLK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL14_SD1_CMD(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL14_SD1_DAT0(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL14_SD1_DAT1(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL14_SD1_DAT2(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL14_SD1_DAT3(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL14_SD2_CLK(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL14_SD2_CMD(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL15_SD2_DAT0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL15_SD2_DAT1(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL15_SD2_DAT2(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL15_SD2_DAT3(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL15_SD2_DS(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL15_SD3_CLK(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL15_SD3_CMD(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL15_SD3_DAT0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL16_SD3_DAT1(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL16_SD3_DAT2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL16_SD3_DAT3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL16_SD3_DAT4(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL16_SD3_DAT5(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL16_SD3_DAT6(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL16_SD3_DAT7(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL16_SD3_DS(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL17_SD0_CD(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL17_SD0_WP(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL17_SD1_CD(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL17_SD1_WP(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL17_SCK0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL17_RX0(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL17_TX0(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL17_CTS0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL18_RTS0_TANS(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL18_RX1(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL18_TX1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL18_CTS1(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL18_RTS1_TANS(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL18_SCK2(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL18_TX2(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL18_RX2(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL19_HSCK0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL19_HRX0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL19_HTX0(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL19_HCTS0(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL19_HRTS0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL19_MSIOF0_SCK(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL19_MSIOF0_SYNC(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL19_MSIOF0_SS1(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL20_MSIOF0_TXD(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL20_MSIOF0_SS2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL20_MSIOF0_RXD(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL20_MLB_CLK(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL20_MLB_SIG(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL20_MLB_DAT(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL20_MLB_REF(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL20_SSI_SCK0129(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL21_SSI_WS0129(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL21_SSI_SDATA0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL21_SSI_SDATA1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL21_SSI_SDATA2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL21_SSI_SCK34(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL21_SSI_WS34(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL21_SSI_SDATA3(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL21_SSI_SCK4(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL22_SSI_WS4(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL22_SSI_SDATA4(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL22_SSI_SCK5(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL22_SSI_WS5(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL22_SSI_SDATA5(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL22_SSI_SCK6(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL22_SSI_WS6(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL22_SSI_SDATA6(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL23_SSI_SCK78(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL23_SSI_WS78(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL23_SSI_SDATA7(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL23_SSI_SDATA8(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL23_SSI_SDATA9(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL23_AUDIO_CLKA(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL23_AUDIO_CLKB(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL23_USB0_PWEN(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL24_USB0_OVC(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL24_USB1_PWEN(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL24_USB1_OVC(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL24_USB30_PWEN(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL24_USB30_OVC(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL24_USB31_PWEN(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL24_USB31_OVC(x)		((uint32_t)(x) << 4U)
+
+#define MOD_SEL0_MSIOF3_A		((uint32_t)0U << 29U)
+#define MOD_SEL0_MSIOF3_B		((uint32_t)1U << 29U)
+#define MOD_SEL0_MSIOF3_C		((uint32_t)2U << 29U)
+#define MOD_SEL0_MSIOF3_D		((uint32_t)3U << 29U)
+#define MOD_SEL0_MSIOF3_E		((uint32_t)4U << 29U)
+#define MOD_SEL0_MSIOF2_A		((uint32_t)0U << 27U)
+#define MOD_SEL0_MSIOF2_B		((uint32_t)1U << 27U)
+#define MOD_SEL0_MSIOF2_C		((uint32_t)2U << 27U)
+#define MOD_SEL0_MSIOF2_D		((uint32_t)3U << 27U)
+#define MOD_SEL0_MSIOF1_A		((uint32_t)0U << 24U)
+#define MOD_SEL0_MSIOF1_B		((uint32_t)1U << 24U)
+#define MOD_SEL0_MSIOF1_C		((uint32_t)2U << 24U)
+#define MOD_SEL0_MSIOF1_D		((uint32_t)3U << 24U)
+#define MOD_SEL0_MSIOF1_E		((uint32_t)4U << 24U)
+#define MOD_SEL0_MSIOF1_F		((uint32_t)5U << 24U)
+#define MOD_SEL0_MSIOF1_G		((uint32_t)6U << 24U)
+#define MOD_SEL0_LBSC_A			((uint32_t)0U << 23U)
+#define MOD_SEL0_LBSC_B			((uint32_t)1U << 23U)
+#define MOD_SEL0_IEBUS_A		((uint32_t)0U << 22U)
+#define MOD_SEL0_IEBUS_B		((uint32_t)1U << 22U)
+#define MOD_SEL0_I2C2_A			((uint32_t)0U << 21U)
+#define MOD_SEL0_I2C2_B			((uint32_t)1U << 21U)
+#define MOD_SEL0_I2C1_A			((uint32_t)0U << 20U)
+#define MOD_SEL0_I2C1_B			((uint32_t)1U << 20U)
+#define MOD_SEL0_HSCIF4_A		((uint32_t)0U << 19U)
+#define MOD_SEL0_HSCIF4_B		((uint32_t)1U << 19U)
+#define MOD_SEL0_HSCIF3_A		((uint32_t)0U << 17U)
+#define MOD_SEL0_HSCIF3_B		((uint32_t)1U << 17U)
+#define MOD_SEL0_HSCIF3_C		((uint32_t)2U << 17U)
+#define MOD_SEL0_HSCIF3_D		((uint32_t)3U << 17U)
+#define MOD_SEL0_HSCIF1_A		((uint32_t)0U << 16U)
+#define MOD_SEL0_HSCIF1_B		((uint32_t)1U << 16U)
+#define MOD_SEL0_FSO_A			((uint32_t)0U << 15U)
+#define MOD_SEL0_FSO_B			((uint32_t)1U << 15U)
+#define MOD_SEL0_HSCIF2_A		((uint32_t)0U << 13U)
+#define MOD_SEL0_HSCIF2_B		((uint32_t)1U << 13U)
+#define MOD_SEL0_HSCIF2_C		((uint32_t)2U << 13U)
+#define MOD_SEL0_ETHERAVB_A		((uint32_t)0U << 12U)
+#define MOD_SEL0_ETHERAVB_B		((uint32_t)1U << 12U)
+#define MOD_SEL0_DRIF3_A		((uint32_t)0U << 11U)
+#define MOD_SEL0_DRIF3_B		((uint32_t)1U << 11U)
+#define MOD_SEL0_DRIF2_A		((uint32_t)0U << 10U)
+#define MOD_SEL0_DRIF2_B		((uint32_t)1U << 10U)
+#define MOD_SEL0_DRIF1_A		((uint32_t)0U << 8U)
+#define MOD_SEL0_DRIF1_B		((uint32_t)1U << 8U)
+#define MOD_SEL0_DRIF1_C		((uint32_t)2U << 8U)
+#define MOD_SEL0_DRIF0_A		((uint32_t)0U << 6U)
+#define MOD_SEL0_DRIF0_B		((uint32_t)1U << 6U)
+#define MOD_SEL0_DRIF0_C		((uint32_t)2U << 6U)
+#define MOD_SEL0_CANFD0_A		((uint32_t)0U << 5U)
+#define MOD_SEL0_CANFD0_B		((uint32_t)1U << 5U)
+#define MOD_SEL0_ADG_A_A		((uint32_t)0U << 3U)
+#define MOD_SEL0_ADG_A_B		((uint32_t)1U << 3U)
+#define MOD_SEL0_ADG_A_C		((uint32_t)2U << 3U)
+#define MOD_SEL1_TSIF1_A		((uint32_t)0U << 30U)
+#define MOD_SEL1_TSIF1_B		((uint32_t)1U << 30U)
+#define MOD_SEL1_TSIF1_C		((uint32_t)2U << 30U)
+#define MOD_SEL1_TSIF1_D		((uint32_t)3U << 30U)
+#define MOD_SEL1_TSIF0_A		((uint32_t)0U << 27U)
+#define MOD_SEL1_TSIF0_B		((uint32_t)1U << 27U)
+#define MOD_SEL1_TSIF0_C		((uint32_t)2U << 27U)
+#define MOD_SEL1_TSIF0_D		((uint32_t)3U << 27U)
+#define MOD_SEL1_TSIF0_E		((uint32_t)4U << 27U)
+#define MOD_SEL1_TIMER_TMU_A		((uint32_t)0U << 26U)
+#define MOD_SEL1_TIMER_TMU_B		((uint32_t)1U << 26U)
+#define MOD_SEL1_SSP1_1_A		((uint32_t)0U << 24U)
+#define MOD_SEL1_SSP1_1_B		((uint32_t)1U << 24U)
+#define MOD_SEL1_SSP1_1_C		((uint32_t)2U << 24U)
+#define MOD_SEL1_SSP1_1_D		((uint32_t)3U << 24U)
+#define MOD_SEL1_SSP1_0_A		((uint32_t)0U << 21U)
+#define MOD_SEL1_SSP1_0_B		((uint32_t)1U << 21U)
+#define MOD_SEL1_SSP1_0_C		((uint32_t)2U << 21U)
+#define MOD_SEL1_SSP1_0_D		((uint32_t)3U << 21U)
+#define MOD_SEL1_SSP1_0_E		((uint32_t)4U << 21U)
+#define MOD_SEL1_SSI_A			((uint32_t)0U << 20U)
+#define MOD_SEL1_SSI_B			((uint32_t)1U << 20U)
+#define MOD_SEL1_SPEED_PULSE_IF_A	((uint32_t)0U << 19U)
+#define MOD_SEL1_SPEED_PULSE_IF_B	((uint32_t)1U << 19U)
+#define MOD_SEL1_SIMCARD_A		((uint32_t)0U << 17U)
+#define MOD_SEL1_SIMCARD_B		((uint32_t)1U << 17U)
+#define MOD_SEL1_SIMCARD_C		((uint32_t)2U << 17U)
+#define MOD_SEL1_SIMCARD_D		((uint32_t)3U << 17U)
+#define MOD_SEL1_SDHI2_A		((uint32_t)0U << 16U)
+#define MOD_SEL1_SDHI2_B		((uint32_t)1U << 16U)
+#define MOD_SEL1_SCIF4_A		((uint32_t)0U << 14U)
+#define MOD_SEL1_SCIF4_B		((uint32_t)1U << 14U)
+#define MOD_SEL1_SCIF4_C		((uint32_t)2U << 14U)
+#define MOD_SEL1_SCIF3_A		((uint32_t)0U << 13U)
+#define MOD_SEL1_SCIF3_B		((uint32_t)1U << 13U)
+#define MOD_SEL1_SCIF2_A		((uint32_t)0U << 12U)
+#define MOD_SEL1_SCIF2_B		((uint32_t)1U << 12U)
+#define MOD_SEL1_SCIF1_A		((uint32_t)0U << 11U)
+#define MOD_SEL1_SCIF1_B		((uint32_t)1U << 11U)
+#define MOD_SEL1_SCIF_A			((uint32_t)0U << 10U)
+#define MOD_SEL1_SCIF_B			((uint32_t)1U << 10U)
+#define MOD_SEL1_REMOCON_A		((uint32_t)0U << 9U)
+#define MOD_SEL1_REMOCON_B		((uint32_t)1U << 9U)
+#define MOD_SEL1_RCAN0_A		((uint32_t)0U << 6U)
+#define MOD_SEL1_RCAN0_B		((uint32_t)1U << 6U)
+#define MOD_SEL1_PWM6_A			((uint32_t)0U << 5U)
+#define MOD_SEL1_PWM6_B			((uint32_t)1U << 5U)
+#define MOD_SEL1_PWM5_A			((uint32_t)0U << 4U)
+#define MOD_SEL1_PWM5_B			((uint32_t)1U << 4U)
+#define MOD_SEL1_PWM4_A			((uint32_t)0U << 3U)
+#define MOD_SEL1_PWM4_B			((uint32_t)1U << 3U)
+#define MOD_SEL1_PWM3_A			((uint32_t)0U << 2U)
+#define MOD_SEL1_PWM3_B			((uint32_t)1U << 2U)
+#define MOD_SEL1_PWM2_A			((uint32_t)0U << 1U)
+#define MOD_SEL1_PWM2_B			((uint32_t)1U << 1U)
+#define MOD_SEL1_PWM1_A			((uint32_t)0U << 0U)
+#define MOD_SEL1_PWM1_B			((uint32_t)1U << 0U)
+#define MOD_SEL2_I2C_5_A		((uint32_t)0U << 31U)
+#define MOD_SEL2_I2C_5_B		((uint32_t)1U << 31U)
+#define MOD_SEL2_I2C_3_A		((uint32_t)0U << 30U)
+#define MOD_SEL2_I2C_3_B		((uint32_t)1U << 30U)
+#define MOD_SEL2_I2C_0_A		((uint32_t)0U << 29U)
+#define MOD_SEL2_I2C_0_B		((uint32_t)1U << 29U)
+#define MOD_SEL2_FM_A			((uint32_t)0U << 27U)
+#define MOD_SEL2_FM_B			((uint32_t)1U << 27U)
+#define MOD_SEL2_FM_C			((uint32_t)2U << 27U)
+#define MOD_SEL2_FM_D			((uint32_t)3U << 27U)
+#define MOD_SEL2_SCIF5_A		((uint32_t)0U << 26U)
+#define MOD_SEL2_SCIF5_B		((uint32_t)1U << 26U)
+#define MOD_SEL2_I2C6_A			((uint32_t)0U << 23U)
+#define MOD_SEL2_I2C6_B			((uint32_t)1U << 23U)
+#define MOD_SEL2_I2C6_C			((uint32_t)2U << 23U)
+#define MOD_SEL2_NDF_A			((uint32_t)0U << 22U)
+#define MOD_SEL2_NDF_B			((uint32_t)1U << 22U)
+#define MOD_SEL2_SSI2_A			((uint32_t)0U << 21U)
+#define MOD_SEL2_SSI2_B			((uint32_t)1U << 21U)
+#define MOD_SEL2_SSI9_A			((uint32_t)0U << 20U)
+#define MOD_SEL2_SSI9_B			((uint32_t)1U << 20U)
+#define MOD_SEL2_TIMER_TMU2_A		((uint32_t)0U << 19U)
+#define MOD_SEL2_TIMER_TMU2_B		((uint32_t)1U << 19U)
+#define MOD_SEL2_ADG_B_A		((uint32_t)0U << 18U)
+#define MOD_SEL2_ADG_B_B		((uint32_t)1U << 18U)
+#define MOD_SEL2_ADG_C_A		((uint32_t)0U << 17U)
+#define MOD_SEL2_ADG_C_B		((uint32_t)1U << 17U)
+#define MOD_SEL2_VIN4_A			((uint32_t)0U << 0U)
+#define MOD_SEL2_VIN4_B			((uint32_t)1U << 0U)
+
+static void pfc_reg_write(uint32_t addr, uint32_t data)
+{
+	mmio_write_32(PFC_PMMR, ~data);
+	mmio_write_32((uintptr_t)addr, data);
+}
+
+void pfc_init_g2h(void)
+{
+	uint32_t reg;
+
+	/* initialize module select */
+	pfc_reg_write(PFC_MOD_SEL0,
+		      MOD_SEL0_MSIOF3_A |
+		      MOD_SEL0_MSIOF2_A |
+		      MOD_SEL0_MSIOF1_A |
+		      MOD_SEL0_LBSC_A |
+		      MOD_SEL0_IEBUS_A |
+		      MOD_SEL0_I2C2_A |
+		      MOD_SEL0_I2C1_A |
+		      MOD_SEL0_HSCIF4_A |
+		      MOD_SEL0_HSCIF3_A |
+		      MOD_SEL0_HSCIF1_A |
+		      MOD_SEL0_FSO_A |
+		      MOD_SEL0_HSCIF2_A |
+		      MOD_SEL0_ETHERAVB_A |
+		      MOD_SEL0_DRIF3_A |
+		      MOD_SEL0_DRIF2_A |
+		      MOD_SEL0_DRIF1_A |
+		      MOD_SEL0_DRIF0_A |
+		      MOD_SEL0_CANFD0_A |
+		      MOD_SEL0_ADG_A_A);
+
+	pfc_reg_write(PFC_MOD_SEL1,
+		      MOD_SEL1_TSIF1_A |
+		      MOD_SEL1_TSIF0_A |
+		      MOD_SEL1_TIMER_TMU_A |
+		      MOD_SEL1_SSP1_1_A |
+		      MOD_SEL1_SSP1_0_A |
+		      MOD_SEL1_SSI_A |
+		      MOD_SEL1_SPEED_PULSE_IF_A |
+		      MOD_SEL1_SIMCARD_A |
+		      MOD_SEL1_SDHI2_A |
+		      MOD_SEL1_SCIF4_A |
+		      MOD_SEL1_SCIF3_A |
+		      MOD_SEL1_SCIF2_A |
+		      MOD_SEL1_SCIF1_A |
+		      MOD_SEL1_SCIF_A |
+		      MOD_SEL1_REMOCON_A |
+		      MOD_SEL1_RCAN0_A |
+		      MOD_SEL1_PWM6_A |
+		      MOD_SEL1_PWM5_A |
+		      MOD_SEL1_PWM4_A |
+		      MOD_SEL1_PWM3_A |
+		      MOD_SEL1_PWM2_A |
+		      MOD_SEL1_PWM1_A);
+
+	pfc_reg_write(PFC_MOD_SEL2,
+		      MOD_SEL2_I2C_5_B |
+		      MOD_SEL2_I2C_3_B |
+		      MOD_SEL2_I2C_0_B |
+		      MOD_SEL2_FM_A |
+		      MOD_SEL2_SCIF5_A |
+		      MOD_SEL2_I2C6_A |
+		      MOD_SEL2_NDF_A |
+		      MOD_SEL2_SSI2_A |
+		      MOD_SEL2_SSI9_A |
+		      MOD_SEL2_TIMER_TMU2_A |
+		      MOD_SEL2_ADG_B_A |
+		      MOD_SEL2_ADG_C_A |
+		      MOD_SEL2_VIN4_A);
+
+	/* initialize peripheral function select */
+	pfc_reg_write(PFC_IPSR0,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR1,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(3) |
+		      IPSR_8_FUNC(3) |
+		      IPSR_4_FUNC(3) |
+		      IPSR_0_FUNC(3));
+
+	pfc_reg_write(PFC_IPSR2,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR3,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR4,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR5,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR6,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR7,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR8,
+		      IPSR_28_FUNC(1) |
+		      IPSR_24_FUNC(1) |
+		      IPSR_20_FUNC(1) |
+		      IPSR_16_FUNC(1) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR9,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR10,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR11,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(4) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR12,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(4) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR13,
+		      IPSR_28_FUNC(8) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(3) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR14,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(3) |
+		      IPSR_0_FUNC(8));
+
+	pfc_reg_write(PFC_IPSR15,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR16,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR17,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(1) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR18,
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	/* initialize GPIO/peripheral function select */
+	pfc_reg_write(PFC_GPSR0,
+		      GPSR0_D15 |
+		      GPSR0_D14 |
+		      GPSR0_D13 |
+		      GPSR0_D12 |
+		      GPSR0_D11 |
+		      GPSR0_D10 |
+		      GPSR0_D9 |
+		      GPSR0_D8 |
+		      GPSR0_D7 |
+		      GPSR0_D6 |
+		      GPSR0_D5 |
+		      GPSR0_D4 |
+		      GPSR0_D3 |
+		      GPSR0_D2 |
+		      GPSR0_D0);
+
+	pfc_reg_write(PFC_GPSR1,
+		      GPSR1_CLKOUT |
+		      GPSR1_EX_WAIT0_A |
+		      GPSR1_WE1 |
+		      GPSR1_RD |
+		      GPSR1_RD_WR |
+		      GPSR1_CS0 |
+		      GPSR1_A19 |
+		      GPSR1_A18 |
+		      GPSR1_A17 |
+		      GPSR1_A16 |
+		      GPSR1_A15 |
+		      GPSR1_A14 |
+		      GPSR1_A13 |
+		      GPSR1_A12 |
+		      GPSR1_A7 |
+		      GPSR1_A6 |
+		      GPSR1_A5 |
+		      GPSR1_A4 |
+		      GPSR1_A3 |
+		      GPSR1_A2 |
+		      GPSR1_A1 |
+		      GPSR1_A0);
+
+	pfc_reg_write(PFC_GPSR2,
+		      GPSR2_AVB_AVTP_CAPTURE_A |
+		      GPSR2_AVB_AVTP_MATCH_A |
+		      GPSR2_AVB_LINK |
+		      GPSR2_AVB_PHY_INT |
+		      GPSR2_AVB_MDC |
+		      GPSR2_PWM2_A |
+		      GPSR2_PWM1_A |
+		      GPSR2_IRQ4 |
+		      GPSR2_IRQ3 |
+		      GPSR2_IRQ2 |
+		      GPSR2_IRQ1 |
+		      GPSR2_IRQ0);
+
+	pfc_reg_write(PFC_GPSR3,
+		      GPSR3_SD0_CD |
+		      GPSR3_SD1_DAT3 |
+		      GPSR3_SD1_DAT2 |
+		      GPSR3_SD1_DAT1 |
+		      GPSR3_SD1_DAT0 |
+		      GPSR3_SD0_DAT3 |
+		      GPSR3_SD0_DAT2 |
+		      GPSR3_SD0_DAT1 |
+		      GPSR3_SD0_DAT0 |
+		      GPSR3_SD0_CMD |
+		      GPSR3_SD0_CLK);
+
+	pfc_reg_write(PFC_GPSR4,
+		      GPSR4_SD3_DS |
+		      GPSR4_SD3_DAT7 |
+		      GPSR4_SD3_DAT6 |
+		      GPSR4_SD3_DAT5 |
+		      GPSR4_SD3_DAT4 |
+		      GPSR4_SD3_DAT3 |
+		      GPSR4_SD3_DAT2 |
+		      GPSR4_SD3_DAT1 |
+		      GPSR4_SD3_DAT0 |
+		      GPSR4_SD3_CMD |
+		      GPSR4_SD3_CLK |
+		      GPSR4_SD2_DAT3 |
+		      GPSR4_SD2_DAT2 |
+		      GPSR4_SD2_DAT1 |
+		      GPSR4_SD2_DAT0 |
+		      GPSR4_SD2_CMD |
+		      GPSR4_SD2_CLK);
+
+	pfc_reg_write(PFC_GPSR5,
+		      GPSR5_MSIOF0_RXD |
+		      GPSR5_MSIOF0_TXD |
+		      GPSR5_MSIOF0_SYNC |
+		      GPSR5_MSIOF0_SCK |
+		      GPSR5_RX2_A |
+		      GPSR5_TX2_A |
+		      GPSR5_RTS1 |
+		      GPSR5_CTS1 |
+		      GPSR5_TX1_A |
+		      GPSR5_RX1_A |
+		      GPSR5_RTS0 |
+		      GPSR5_SCK0);
+
+	pfc_reg_write(PFC_GPSR6,
+		      GPSR6_AUDIO_CLKB_B |
+		      GPSR6_AUDIO_CLKA_A |
+		      GPSR6_SSI_WS6 |
+		      GPSR6_SSI_SCK6 |
+		      GPSR6_SSI_SDATA4 |
+		      GPSR6_SSI_WS4 |
+		      GPSR6_SSI_SCK4 |
+		      GPSR6_SSI_SDATA1_A |
+		      GPSR6_SSI_SDATA0 |
+		      GPSR6_SSI_WS0129 |
+		      GPSR6_SSI_SCK0129);
+
+	pfc_reg_write(PFC_GPSR7,
+		      GPSR7_AVS2 |
+		      GPSR7_AVS1);
+
+	/* initialize POC control register */
+	pfc_reg_write(PFC_POCCTRL0,
+		      POC_SD0_DAT3_33V |
+		      POC_SD0_DAT2_33V |
+		      POC_SD0_DAT1_33V |
+		      POC_SD0_DAT0_33V |
+		      POC_SD0_CMD_33V |
+		      POC_SD0_CLK_33V);
+
+	/* initialize DRV control register */
+	reg = mmio_read_32(PFC_DRVCTRL0);
+	reg = (reg & DRVCTRL0_MASK) |
+	      DRVCTRL0_QSPI0_SPCLK(3) |
+	      DRVCTRL0_QSPI0_MOSI_IO0(3) |
+	      DRVCTRL0_QSPI0_MISO_IO1(3) |
+	      DRVCTRL0_QSPI0_IO2(3) |
+	      DRVCTRL0_QSPI0_IO3(3) |
+	      DRVCTRL0_QSPI0_SSL(3) |
+	      DRVCTRL0_QSPI1_SPCLK(3) |
+	      DRVCTRL0_QSPI1_MOSI_IO0(3);
+	pfc_reg_write(PFC_DRVCTRL0, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL1);
+	reg = (reg & DRVCTRL1_MASK) |
+	      DRVCTRL1_QSPI1_MISO_IO1(3) |
+	      DRVCTRL1_QSPI1_IO2(3) |
+	      DRVCTRL1_QSPI1_IO3(3) |
+	      DRVCTRL1_QSPI1_SS(3) |
+	      DRVCTRL1_RPC_INT(3) |
+	      DRVCTRL1_RPC_WP(3) |
+	      DRVCTRL1_RPC_RESET(3) |
+	      DRVCTRL1_AVB_RX_CTL(7);
+	pfc_reg_write(PFC_DRVCTRL1, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL2);
+	reg = (reg & DRVCTRL2_MASK) |
+	      DRVCTRL2_AVB_RXC(7) |
+	      DRVCTRL2_AVB_RD0(7) |
+	      DRVCTRL2_AVB_RD1(7) |
+	      DRVCTRL2_AVB_RD2(7) |
+	      DRVCTRL2_AVB_RD3(7) |
+	      DRVCTRL2_AVB_TX_CTL(3) |
+	      DRVCTRL2_AVB_TXC(3) |
+	      DRVCTRL2_AVB_TD0(3);
+	pfc_reg_write(PFC_DRVCTRL2, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL3);
+	reg = (reg & DRVCTRL3_MASK) |
+	      DRVCTRL3_AVB_TD1(3) |
+	      DRVCTRL3_AVB_TD2(3) |
+	      DRVCTRL3_AVB_TD3(3) |
+	      DRVCTRL3_AVB_TXCREFCLK(7) |
+	      DRVCTRL3_AVB_MDIO(7) |
+	      DRVCTRL3_AVB_MDC(7) |
+	      DRVCTRL3_AVB_MAGIC(7) |
+	      DRVCTRL3_AVB_PHY_INT(7);
+	pfc_reg_write(PFC_DRVCTRL3, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL4);
+	reg = (reg & DRVCTRL4_MASK) |
+	      DRVCTRL4_AVB_LINK(7) |
+	      DRVCTRL4_AVB_AVTP_MATCH(7) |
+	      DRVCTRL4_AVB_AVTP_CAPTURE(7) |
+	      DRVCTRL4_IRQ0(7) |
+	      DRVCTRL4_IRQ1(7) |
+	      DRVCTRL4_IRQ2(7) |
+	      DRVCTRL4_IRQ3(7) |
+	      DRVCTRL4_IRQ4(7);
+	pfc_reg_write(PFC_DRVCTRL4, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL5);
+	reg = (reg & DRVCTRL5_MASK) |
+	      DRVCTRL5_IRQ5(7) |
+	      DRVCTRL5_PWM0(7) |
+	      DRVCTRL5_PWM1(7) |
+	      DRVCTRL5_PWM2(7) |
+	      DRVCTRL5_A0(3) |
+	      DRVCTRL5_A1(3) |
+	      DRVCTRL5_A2(3) |
+	      DRVCTRL5_A3(3);
+	pfc_reg_write(PFC_DRVCTRL5, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL6);
+	reg = (reg & DRVCTRL6_MASK) |
+	      DRVCTRL6_A4(3) |
+	      DRVCTRL6_A5(3) |
+	      DRVCTRL6_A6(3) |
+	      DRVCTRL6_A7(3) |
+	      DRVCTRL6_A8(7) |
+	      DRVCTRL6_A9(7) |
+	      DRVCTRL6_A10(7) |
+	      DRVCTRL6_A11(7);
+	pfc_reg_write(PFC_DRVCTRL6, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL7);
+	reg = (reg & DRVCTRL7_MASK) |
+	      DRVCTRL7_A12(3) |
+	      DRVCTRL7_A13(3) |
+	      DRVCTRL7_A14(3) |
+	      DRVCTRL7_A15(3) |
+	      DRVCTRL7_A16(3) |
+	      DRVCTRL7_A17(3) |
+	      DRVCTRL7_A18(3) |
+	      DRVCTRL7_A19(3);
+	pfc_reg_write(PFC_DRVCTRL7, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL8);
+	reg = (reg & DRVCTRL8_MASK) |
+	      DRVCTRL8_CLKOUT(7) |
+	      DRVCTRL8_CS0(7) |
+	      DRVCTRL8_CS1_A2(7) |
+	      DRVCTRL8_BS(7) |
+	      DRVCTRL8_RD(7) |
+	      DRVCTRL8_RD_W(7) |
+	      DRVCTRL8_WE0(7) |
+	      DRVCTRL8_WE1(7);
+	pfc_reg_write(PFC_DRVCTRL8, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL9);
+	reg = (reg & DRVCTRL9_MASK) |
+	      DRVCTRL9_EX_WAIT0(7) |
+	      DRVCTRL9_PRESETOU(7) |
+	      DRVCTRL9_D0(7) |
+	      DRVCTRL9_D1(7) |
+	      DRVCTRL9_D2(7) |
+	      DRVCTRL9_D3(7) |
+	      DRVCTRL9_D4(7) |
+	      DRVCTRL9_D5(7);
+	pfc_reg_write(PFC_DRVCTRL9, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL10);
+	reg = (reg & DRVCTRL10_MASK) |
+	      DRVCTRL10_D6(7) |
+	      DRVCTRL10_D7(7) |
+	      DRVCTRL10_D8(3) |
+	      DRVCTRL10_D9(3) |
+	      DRVCTRL10_D10(3) |
+	      DRVCTRL10_D11(3) |
+	      DRVCTRL10_D12(3) |
+	      DRVCTRL10_D13(3);
+	pfc_reg_write(PFC_DRVCTRL10, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL11);
+	reg = (reg & DRVCTRL11_MASK) |
+	      DRVCTRL11_D14(3) |
+	      DRVCTRL11_D15(3) |
+	      DRVCTRL11_AVS1(7) |
+	      DRVCTRL11_AVS2(7) |
+	      DRVCTRL11_GP7_02(7) |
+	      DRVCTRL11_GP7_03(7) |
+	      DRVCTRL11_DU_DOTCLKIN0(3) |
+	      DRVCTRL11_DU_DOTCLKIN1(3);
+	pfc_reg_write(PFC_DRVCTRL11, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL12);
+	reg = (reg & DRVCTRL12_MASK) |
+	      DRVCTRL12_DU_DOTCLKIN2(3) |
+	      DRVCTRL12_DU_DOTCLKIN3(3) |
+	      DRVCTRL12_DU_FSCLKST(3) |
+	      DRVCTRL12_DU_TMS(3);
+	pfc_reg_write(PFC_DRVCTRL12, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL13);
+	reg = (reg & DRVCTRL13_MASK) |
+	      DRVCTRL13_TDO(3) |
+	      DRVCTRL13_ASEBRK(3) |
+	      DRVCTRL13_SD0_CLK(7) |
+	      DRVCTRL13_SD0_CMD(7) |
+	      DRVCTRL13_SD0_DAT0(7) |
+	      DRVCTRL13_SD0_DAT1(7) |
+	      DRVCTRL13_SD0_DAT2(7) |
+	      DRVCTRL13_SD0_DAT3(7);
+	pfc_reg_write(PFC_DRVCTRL13, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL14);
+	reg = (reg & DRVCTRL14_MASK) |
+	      DRVCTRL14_SD1_CLK(7) |
+	      DRVCTRL14_SD1_CMD(7) |
+	      DRVCTRL14_SD1_DAT0(5) |
+	      DRVCTRL14_SD1_DAT1(5) |
+	      DRVCTRL14_SD1_DAT2(5) |
+	      DRVCTRL14_SD1_DAT3(5) |
+	      DRVCTRL14_SD2_CLK(5) |
+	      DRVCTRL14_SD2_CMD(5);
+	pfc_reg_write(PFC_DRVCTRL14, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL15);
+	reg = (reg & DRVCTRL15_MASK) |
+	      DRVCTRL15_SD2_DAT0(5) |
+	      DRVCTRL15_SD2_DAT1(5) |
+	      DRVCTRL15_SD2_DAT2(5) |
+	      DRVCTRL15_SD2_DAT3(5) |
+	      DRVCTRL15_SD2_DS(5) |
+	      DRVCTRL15_SD3_CLK(7) |
+	      DRVCTRL15_SD3_CMD(7) |
+	      DRVCTRL15_SD3_DAT0(7);
+	pfc_reg_write(PFC_DRVCTRL15, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL16);
+	reg = (reg & DRVCTRL16_MASK) |
+	      DRVCTRL16_SD3_DAT1(7) |
+	      DRVCTRL16_SD3_DAT2(7) |
+	      DRVCTRL16_SD3_DAT3(7) |
+	      DRVCTRL16_SD3_DAT4(7) |
+	      DRVCTRL16_SD3_DAT5(7) |
+	      DRVCTRL16_SD3_DAT6(7) |
+	      DRVCTRL16_SD3_DAT7(7) |
+	      DRVCTRL16_SD3_DS(7);
+	pfc_reg_write(PFC_DRVCTRL16, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL17);
+	reg = (reg & DRVCTRL17_MASK) |
+	      DRVCTRL17_SD0_CD(7) |
+	      DRVCTRL17_SD0_WP(7) |
+	      DRVCTRL17_SD1_CD(7) |
+	      DRVCTRL17_SD1_WP(7) |
+	      DRVCTRL17_SCK0(7) |
+	      DRVCTRL17_RX0(7) |
+	      DRVCTRL17_TX0(7) |
+	      DRVCTRL17_CTS0(7);
+	pfc_reg_write(PFC_DRVCTRL17, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL18);
+	reg = (reg & DRVCTRL18_MASK) |
+	      DRVCTRL18_RTS0_TANS(7) |
+	      DRVCTRL18_RX1(7) |
+	      DRVCTRL18_TX1(7) |
+	      DRVCTRL18_CTS1(7) |
+	      DRVCTRL18_RTS1_TANS(7) |
+	      DRVCTRL18_SCK2(7) |
+	      DRVCTRL18_TX2(7) |
+	      DRVCTRL18_RX2(7);
+	pfc_reg_write(PFC_DRVCTRL18, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL19);
+	reg = (reg & DRVCTRL19_MASK) |
+	      DRVCTRL19_HSCK0(7) |
+	      DRVCTRL19_HRX0(7) |
+	      DRVCTRL19_HTX0(7) |
+	      DRVCTRL19_HCTS0(7) |
+	      DRVCTRL19_HRTS0(7) |
+	      DRVCTRL19_MSIOF0_SCK(7) |
+	      DRVCTRL19_MSIOF0_SYNC(7) |
+	      DRVCTRL19_MSIOF0_SS1(7);
+	pfc_reg_write(PFC_DRVCTRL19, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL20);
+	reg = (reg & DRVCTRL20_MASK) |
+	      DRVCTRL20_MSIOF0_TXD(7) |
+	      DRVCTRL20_MSIOF0_SS2(7) |
+	      DRVCTRL20_MSIOF0_RXD(7) |
+	      DRVCTRL20_MLB_CLK(7) |
+	      DRVCTRL20_MLB_SIG(7) |
+	      DRVCTRL20_MLB_DAT(7) |
+	      DRVCTRL20_MLB_REF(7) |
+	      DRVCTRL20_SSI_SCK0129(7);
+	pfc_reg_write(PFC_DRVCTRL20, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL21);
+	reg = (reg & DRVCTRL21_MASK) |
+	      DRVCTRL21_SSI_WS0129(7) |
+	      DRVCTRL21_SSI_SDATA0(7) |
+	      DRVCTRL21_SSI_SDATA1(7) |
+	      DRVCTRL21_SSI_SDATA2(7) |
+	      DRVCTRL21_SSI_SCK34(7) |
+	      DRVCTRL21_SSI_WS34(7) |
+	      DRVCTRL21_SSI_SDATA3(7) |
+	      DRVCTRL21_SSI_SCK4(7);
+	pfc_reg_write(PFC_DRVCTRL21, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL22);
+	reg = (reg & DRVCTRL22_MASK) |
+	      DRVCTRL22_SSI_WS4(7) |
+	      DRVCTRL22_SSI_SDATA4(7) |
+	      DRVCTRL22_SSI_SCK5(7) |
+	      DRVCTRL22_SSI_WS5(7) |
+	      DRVCTRL22_SSI_SDATA5(7) |
+	      DRVCTRL22_SSI_SCK6(7) |
+	      DRVCTRL22_SSI_WS6(7) |
+	      DRVCTRL22_SSI_SDATA6(7);
+	pfc_reg_write(PFC_DRVCTRL22, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL23);
+	reg = (reg & DRVCTRL23_MASK) |
+	      DRVCTRL23_SSI_SCK78(7) |
+	      DRVCTRL23_SSI_WS78(7) |
+	      DRVCTRL23_SSI_SDATA7(7) |
+	      DRVCTRL23_SSI_SDATA8(7) |
+	      DRVCTRL23_SSI_SDATA9(7) |
+	      DRVCTRL23_AUDIO_CLKA(7) |
+	      DRVCTRL23_AUDIO_CLKB(7) |
+	      DRVCTRL23_USB0_PWEN(7);
+	pfc_reg_write(PFC_DRVCTRL23, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL24);
+	reg = (reg & DRVCTRL24_MASK) |
+	      DRVCTRL24_USB0_OVC(7) |
+	      DRVCTRL24_USB1_PWEN(7) |
+	      DRVCTRL24_USB1_OVC(7) |
+	      DRVCTRL24_USB30_PWEN(7) |
+	      DRVCTRL24_USB30_OVC(7) |
+	      DRVCTRL24_USB31_PWEN(7) |
+	      DRVCTRL24_USB31_OVC(7);
+	pfc_reg_write(PFC_DRVCTRL24, reg);
+
+	/* initialize LSI pin pull-up/down control */
+	pfc_reg_write(PFC_PUD0, 0x00005FBFU);
+	pfc_reg_write(PFC_PUD1, 0x00300EFEU);
+	pfc_reg_write(PFC_PUD2, 0x330001E6U);
+	pfc_reg_write(PFC_PUD3, 0x000002E0U);
+	pfc_reg_write(PFC_PUD4, 0xFFFFFF00U);
+	pfc_reg_write(PFC_PUD5, 0x7F5FFF87U);
+	pfc_reg_write(PFC_PUD6, 0x00000055U);
+
+	/* initialize LSI pin pull-enable register */
+	pfc_reg_write(PFC_PUEN0, 0x00000FFFU);
+	pfc_reg_write(PFC_PUEN1, 0x00100234U);
+	pfc_reg_write(PFC_PUEN2, 0x000004C4U);
+	pfc_reg_write(PFC_PUEN3, 0x00000200U);
+	pfc_reg_write(PFC_PUEN4, 0x3E000000U);
+	pfc_reg_write(PFC_PUEN5, 0x1F000805U);
+	pfc_reg_write(PFC_PUEN6, 0x00000006U);
+
+	/* initialize positive/negative logic select */
+	mmio_write_32(GPIO_POSNEG0, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG1, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG2, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG3, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG4, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG5, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG6, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG7, 0x00000000U);
+
+	/* initialize general IO/interrupt switching */
+	mmio_write_32(GPIO_IOINTSEL0, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL1, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL2, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL3, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL4, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL5, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL6, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL7, 0x00000000U);
+
+	/* initialize general output register */
+	mmio_write_32(GPIO_OUTDT0, 0x00000001U);
+	mmio_write_32(GPIO_OUTDT1, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT2, 0x00000400U);
+	mmio_write_32(GPIO_OUTDT3, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT4, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT5, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT6, 0x00003800U);
+	mmio_write_32(GPIO_OUTDT7, 0x00000003U);
+
+	/* initialize general input/output switching */
+	mmio_write_32(GPIO_INOUTSEL0, 0x00000001U);
+	mmio_write_32(GPIO_INOUTSEL1, 0x00100B00U);
+	mmio_write_32(GPIO_INOUTSEL2, 0x00000418U);
+	mmio_write_32(GPIO_INOUTSEL3, 0x00002000U);
+	mmio_write_32(GPIO_INOUTSEL4, 0x00000040U);
+	mmio_write_32(GPIO_INOUTSEL5, 0x00000208U);
+	mmio_write_32(GPIO_INOUTSEL6, 0x00013F00U);
+	mmio_write_32(GPIO_INOUTSEL7, 0x00000003U);
+}
diff --git a/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.h b/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.h
new file mode 100644
index 0000000..5efce45
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PFC_INIT_G2H_H
+#define PFC_INIT_G2H_H
+
+void pfc_init_g2h(void);
+
+#endif /* PFC_INIT_G2H_H */
diff --git a/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c b/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c
new file mode 100644
index 0000000..f76b83f
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c
@@ -0,0 +1,1300 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>		/* for uint32_t */
+
+#include <lib/mmio.h>
+
+#include "pfc_init_g2m.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+#include "pfc_regs.h"
+
+#define GPSR0_D15		BIT(15)
+#define GPSR0_D14		BIT(14)
+#define GPSR0_D13		BIT(13)
+#define GPSR0_D12		BIT(12)
+#define GPSR0_D11		BIT(11)
+#define GPSR0_D10		BIT(10)
+#define GPSR0_D9		BIT(9)
+#define GPSR0_D8		BIT(8)
+#define GPSR0_D7		BIT(7)
+#define GPSR0_D6		BIT(6)
+#define GPSR0_D5		BIT(5)
+#define GPSR0_D4		BIT(4)
+#define GPSR0_D3		BIT(3)
+#define GPSR0_D2		BIT(2)
+#define GPSR0_D1		BIT(1)
+#define GPSR0_D0		BIT(0)
+#define GPSR1_CLKOUT		BIT(28)
+#define GPSR1_EX_WAIT0_A	BIT(27)
+#define GPSR1_WE1		BIT(26)
+#define GPSR1_WE0		BIT(25)
+#define GPSR1_RD_WR		BIT(24)
+#define GPSR1_RD		BIT(23)
+#define GPSR1_BS		BIT(22)
+#define GPSR1_CS1_A26		BIT(21)
+#define GPSR1_CS0		BIT(20)
+#define GPSR1_A19		BIT(19)
+#define GPSR1_A18		BIT(18)
+#define GPSR1_A17		BIT(17)
+#define GPSR1_A16		BIT(16)
+#define GPSR1_A15		BIT(15)
+#define GPSR1_A14		BIT(14)
+#define GPSR1_A13		BIT(13)
+#define GPSR1_A12		BIT(12)
+#define GPSR1_A11		BIT(11)
+#define GPSR1_A10		BIT(10)
+#define GPSR1_A9		BIT(9)
+#define GPSR1_A8		BIT(8)
+#define GPSR1_A7		BIT(7)
+#define GPSR1_A6		BIT(6)
+#define GPSR1_A5		BIT(5)
+#define GPSR1_A4		BIT(4)
+#define GPSR1_A3		BIT(3)
+#define GPSR1_A2		BIT(2)
+#define GPSR1_A1		BIT(1)
+#define GPSR1_A0		BIT(0)
+#define GPSR2_AVB_AVTP_CAPTURE_A	BIT(14)
+#define GPSR2_AVB_AVTP_MATCH_A	BIT(13)
+#define GPSR2_AVB_LINK		BIT(12)
+#define GPSR2_AVB_PHY_INT	BIT(11)
+#define GPSR2_AVB_MAGIC		BIT(10)
+#define GPSR2_AVB_MDC		BIT(9)
+#define GPSR2_PWM2_A		BIT(8)
+#define GPSR2_PWM1_A		BIT(7)
+#define GPSR2_PWM0		BIT(6)
+#define GPSR2_IRQ5		BIT(5)
+#define GPSR2_IRQ4		BIT(4)
+#define GPSR2_IRQ3		BIT(3)
+#define GPSR2_IRQ2		BIT(2)
+#define GPSR2_IRQ1		BIT(1)
+#define GPSR2_IRQ0		BIT(0)
+#define GPSR3_SD1_WP		BIT(15)
+#define GPSR3_SD1_CD		BIT(14)
+#define GPSR3_SD0_WP		BIT(13)
+#define GPSR3_SD0_CD		BIT(12)
+#define GPSR3_SD1_DAT3		BIT(11)
+#define GPSR3_SD1_DAT2		BIT(10)
+#define GPSR3_SD1_DAT1		BIT(9)
+#define GPSR3_SD1_DAT0		BIT(8)
+#define GPSR3_SD1_CMD		BIT(7)
+#define GPSR3_SD1_CLK		BIT(6)
+#define GPSR3_SD0_DAT3		BIT(5)
+#define GPSR3_SD0_DAT2		BIT(4)
+#define GPSR3_SD0_DAT1		BIT(3)
+#define GPSR3_SD0_DAT0		BIT(2)
+#define GPSR3_SD0_CMD		BIT(1)
+#define GPSR3_SD0_CLK		BIT(0)
+#define GPSR4_SD3_DS		BIT(17)
+#define GPSR4_SD3_DAT7		BIT(16)
+#define GPSR4_SD3_DAT6		BIT(15)
+#define GPSR4_SD3_DAT5		BIT(14)
+#define GPSR4_SD3_DAT4		BIT(13)
+#define GPSR4_SD3_DAT3		BIT(12)
+#define GPSR4_SD3_DAT2		BIT(11)
+#define GPSR4_SD3_DAT1		BIT(10)
+#define GPSR4_SD3_DAT0		BIT(9)
+#define GPSR4_SD3_CMD		BIT(8)
+#define GPSR4_SD3_CLK		BIT(7)
+#define GPSR4_SD2_DS		BIT(6)
+#define GPSR4_SD2_DAT3		BIT(5)
+#define GPSR4_SD2_DAT2		BIT(4)
+#define GPSR4_SD2_DAT1		BIT(3)
+#define GPSR4_SD2_DAT0		BIT(2)
+#define GPSR4_SD2_CMD		BIT(1)
+#define GPSR4_SD2_CLK		BIT(0)
+#define GPSR5_MLB_DAT		BIT(25)
+#define GPSR5_MLB_SIG		BIT(24)
+#define GPSR5_MLB_CLK		BIT(23)
+#define GPSR5_MSIOF0_RXD	BIT(22)
+#define GPSR5_MSIOF0_SS2	BIT(21)
+#define GPSR5_MSIOF0_TXD	BIT(20)
+#define GPSR5_MSIOF0_SS1	BIT(19)
+#define GPSR5_MSIOF0_SYNC	BIT(18)
+#define GPSR5_MSIOF0_SCK	BIT(17)
+#define GPSR5_HRTS0		BIT(16)
+#define GPSR5_HCTS0		BIT(15)
+#define GPSR5_HTX0		BIT(14)
+#define GPSR5_HRX0		BIT(13)
+#define GPSR5_HSCK0		BIT(12)
+#define GPSR5_RX2_A		BIT(11)
+#define GPSR5_TX2_A		BIT(10)
+#define GPSR5_SCK2		BIT(9)
+#define GPSR5_RTS1		BIT(8)
+#define GPSR5_CTS1		BIT(7)
+#define GPSR5_TX1_A		BIT(6)
+#define GPSR5_RX1_A		BIT(5)
+#define GPSR5_RTS0		BIT(4)
+#define GPSR5_CTS0		BIT(3)
+#define GPSR5_TX0		BIT(2)
+#define GPSR5_RX0		BIT(1)
+#define GPSR5_SCK0		BIT(0)
+#define GPSR6_USB31_OVC		BIT(31)
+#define GPSR6_USB31_PWEN	BIT(30)
+#define GPSR6_USB30_OVC		BIT(29)
+#define GPSR6_USB30_PWEN	BIT(28)
+#define GPSR6_USB1_OVC		BIT(27)
+#define GPSR6_USB1_PWEN		BIT(26)
+#define GPSR6_USB0_OVC		BIT(25)
+#define GPSR6_USB0_PWEN		BIT(24)
+#define GPSR6_AUDIO_CLKB_B	BIT(23)
+#define GPSR6_AUDIO_CLKA_A	BIT(22)
+#define GPSR6_SSI_SDATA9_A	BIT(21)
+#define GPSR6_SSI_SDATA8	BIT(20)
+#define GPSR6_SSI_SDATA7	BIT(19)
+#define GPSR6_SSI_WS78		BIT(18)
+#define GPSR6_SSI_SCK78		BIT(17)
+#define GPSR6_SSI_SDATA6	BIT(16)
+#define GPSR6_SSI_WS6		BIT(15)
+#define GPSR6_SSI_SCK6		BIT(14)
+#define GPSR6_SSI_SDATA5	BIT(13)
+#define GPSR6_SSI_WS5		BIT(12)
+#define GPSR6_SSI_SCK5		BIT(11)
+#define GPSR6_SSI_SDATA4	BIT(10)
+#define GPSR6_SSI_WS4		BIT(9)
+#define GPSR6_SSI_SCK4		BIT(8)
+#define GPSR6_SSI_SDATA3	BIT(7)
+#define GPSR6_SSI_WS34		BIT(6)
+#define GPSR6_SSI_SCK34		BIT(5)
+#define GPSR6_SSI_SDATA2_A	BIT(4)
+#define GPSR6_SSI_SDATA1_A	BIT(3)
+#define GPSR6_SSI_SDATA0	BIT(2)
+#define GPSR6_SSI_WS0129	BIT(1)
+#define GPSR6_SSI_SCK0129	BIT(0)
+#define GPSR7_AVS2		BIT(1)
+#define GPSR7_AVS1		BIT(0)
+
+#define IPSR_28_FUNC(x)		((uint32_t)(x) << 28U)
+#define IPSR_24_FUNC(x)		((uint32_t)(x) << 24U)
+#define IPSR_20_FUNC(x)		((uint32_t)(x) << 20U)
+#define IPSR_16_FUNC(x)		((uint32_t)(x) << 16U)
+#define IPSR_12_FUNC(x)		((uint32_t)(x) << 12U)
+#define IPSR_8_FUNC(x)		((uint32_t)(x) << 8U)
+#define IPSR_4_FUNC(x)		((uint32_t)(x) << 4U)
+#define IPSR_0_FUNC(x)		((uint32_t)(x) << 0U)
+
+#define POC_SD3_DS_33V		BIT(29)
+#define POC_SD3_DAT7_33V	BIT(28)
+#define POC_SD3_DAT6_33V	BIT(27)
+#define POC_SD3_DAT5_33V	BIT(26)
+#define POC_SD3_DAT4_33V	BIT(25)
+#define POC_SD3_DAT3_33V	BIT(24)
+#define POC_SD3_DAT2_33V	BIT(23)
+#define POC_SD3_DAT1_33V	BIT(22)
+#define POC_SD3_DAT0_33V	BIT(21)
+#define POC_SD3_CMD_33V		BIT(20)
+#define POC_SD3_CLK_33V		BIT(19)
+#define POC_SD2_DS_33V		BIT(18)
+#define POC_SD2_DAT3_33V	BIT(17)
+#define POC_SD2_DAT2_33V	BIT(16)
+#define POC_SD2_DAT1_33V	BIT(15)
+#define POC_SD2_DAT0_33V	BIT(14)
+#define POC_SD2_CMD_33V		BIT(13)
+#define POC_SD2_CLK_33V		BIT(12)
+#define POC_SD1_DAT3_33V	BIT(11)
+#define POC_SD1_DAT2_33V	BIT(10)
+#define POC_SD1_DAT1_33V	BIT(9)
+#define POC_SD1_DAT0_33V	BIT(8)
+#define POC_SD1_CMD_33V		BIT(7)
+#define POC_SD1_CLK_33V		BIT(6)
+#define POC_SD0_DAT3_33V	BIT(5)
+#define POC_SD0_DAT2_33V	BIT(4)
+#define POC_SD0_DAT1_33V	BIT(3)
+#define POC_SD0_DAT0_33V	BIT(2)
+#define POC_SD0_CMD_33V		BIT(1)
+#define POC_SD0_CLK_33V		BIT(0)
+
+#define DRVCTRL0_MASK		(0xCCCCCCCCU)
+#define DRVCTRL1_MASK		(0xCCCCCCC8U)
+#define DRVCTRL2_MASK		(0x88888888U)
+#define DRVCTRL3_MASK		(0x88888888U)
+#define DRVCTRL4_MASK		(0x88888888U)
+#define DRVCTRL5_MASK		(0x88888888U)
+#define DRVCTRL6_MASK		(0x88888888U)
+#define DRVCTRL7_MASK		(0x88888888U)
+#define DRVCTRL8_MASK		(0x88888888U)
+#define DRVCTRL9_MASK		(0x88888888U)
+#define DRVCTRL10_MASK		(0x88888888U)
+#define DRVCTRL11_MASK		(0x888888CCU)
+#define DRVCTRL12_MASK		(0xCCCFFFCFU)
+#define DRVCTRL13_MASK		(0xCC888888U)
+#define DRVCTRL14_MASK		(0x88888888U)
+#define DRVCTRL15_MASK		(0x88888888U)
+#define DRVCTRL16_MASK		(0x88888888U)
+#define DRVCTRL17_MASK		(0x88888888U)
+#define DRVCTRL18_MASK		(0x88888888U)
+#define DRVCTRL19_MASK		(0x88888888U)
+#define DRVCTRL20_MASK		(0x88888888U)
+#define DRVCTRL21_MASK		(0x88888888U)
+#define DRVCTRL22_MASK		(0x88888888U)
+#define DRVCTRL23_MASK		(0x88888888U)
+#define DRVCTRL24_MASK		(0x8888888FU)
+
+#define DRVCTRL0_QSPI0_SPCLK(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL0_QSPI0_MOSI_IO0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL0_QSPI0_MISO_IO1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL0_QSPI0_IO2(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL0_QSPI0_IO3(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL0_QSPI0_SSL(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL0_QSPI1_SPCLK(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL0_QSPI1_MOSI_IO0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL1_QSPI1_MISO_IO1(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL1_QSPI1_IO2(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL1_QSPI1_IO3(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL1_QSPI1_SS(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL1_RPC_INT(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL1_RPC_WP(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL1_RPC_RESET(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL1_AVB_RX_CTL(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL2_AVB_RXC(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL2_AVB_RD0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL2_AVB_RD1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL2_AVB_RD2(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL2_AVB_RD3(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL2_AVB_TX_CTL(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL2_AVB_TXC(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL2_AVB_TD0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL3_AVB_TD1(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL3_AVB_TD2(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL3_AVB_TD3(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL3_AVB_TXCREFCLK(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL3_AVB_MDIO(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL3_AVB_MDC(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL3_AVB_MAGIC(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL3_AVB_PHY_INT(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL4_AVB_LINK(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL4_AVB_AVTP_MATCH(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL4_AVB_AVTP_CAPTURE(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL4_IRQ0(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL4_IRQ1(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL4_IRQ2(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL4_IRQ3(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL4_IRQ4(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL5_IRQ5(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL5_PWM0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL5_PWM1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL5_PWM2(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL5_A0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL5_A1(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL5_A2(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL5_A3(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL6_A4(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL6_A5(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL6_A6(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL6_A7(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL6_A8(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL6_A9(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL6_A10(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL6_A11(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL7_A12(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL7_A13(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL7_A14(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL7_A15(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL7_A16(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL7_A17(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL7_A18(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL7_A19(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL8_CLKOUT(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL8_CS0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL8_CS1_A2(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL8_BS(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL8_RD(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL8_RD_W(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL8_WE0(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL8_WE1(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL9_EX_WAIT0(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL9_PRESETOU(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL9_D0(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL9_D1(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL9_D2(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL9_D3(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL9_D4(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL9_D5(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL10_D6(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL10_D7(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL10_D8(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL10_D9(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL10_D10(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL10_D11(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL10_D12(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL10_D13(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL11_D14(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL11_D15(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL11_AVS1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL11_AVS2(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL11_GP7_02(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL11_GP7_03(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL11_DU_DOTCLKIN0(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL11_DU_DOTCLKIN1(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL12_DU_DOTCLKIN2(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL12_DU_DOTCLKIN3(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL12_DU_FSCLKST(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL12_DU_TMS(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL13_TDO(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL13_ASEBRK(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL13_SD0_CLK(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL13_SD0_CMD(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL13_SD0_DAT0(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL13_SD0_DAT1(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL13_SD0_DAT2(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL13_SD0_DAT3(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL14_SD1_CLK(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL14_SD1_CMD(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL14_SD1_DAT0(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL14_SD1_DAT1(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL14_SD1_DAT2(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL14_SD1_DAT3(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL14_SD2_CLK(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL14_SD2_CMD(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL15_SD2_DAT0(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL15_SD2_DAT1(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL15_SD2_DAT2(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL15_SD2_DAT3(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL15_SD2_DS(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL15_SD3_CLK(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL15_SD3_CMD(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL15_SD3_DAT0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL16_SD3_DAT1(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL16_SD3_DAT2(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL16_SD3_DAT3(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL16_SD3_DAT4(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL16_SD3_DAT5(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL16_SD3_DAT6(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL16_SD3_DAT7(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL16_SD3_DS(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL17_SD0_CD(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL17_SD0_WP(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL17_SD1_CD(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL17_SD1_WP(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL17_SCK0(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL17_RX0(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL17_TX0(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL17_CTS0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL18_RTS0_TANS(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL18_RX1(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL18_TX1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL18_CTS1(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL18_RTS1_TANS(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL18_SCK2(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL18_TX2(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL18_RX2(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL19_HSCK0(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL19_HRX0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL19_HTX0(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL19_HCTS0(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL19_HRTS0(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL19_MSIOF0_SCK(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL19_MSIOF0_SYNC(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL19_MSIOF0_SS1(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL20_MSIOF0_TXD(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL20_MSIOF0_SS2(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL20_MSIOF0_RXD(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL20_MLB_CLK(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL20_MLB_SIG(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL20_MLB_DAT(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL20_MLB_REF(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL20_SSI_SCK0129(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL21_SSI_WS0129(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL21_SSI_SDATA0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL21_SSI_SDATA1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL21_SSI_SDATA2(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL21_SSI_SCK34(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL21_SSI_WS34(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL21_SSI_SDATA3(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL21_SSI_SCK4(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL22_SSI_WS4(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL22_SSI_SDATA4(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL22_SSI_SCK5(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL22_SSI_WS5(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL22_SSI_SDATA5(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL22_SSI_SCK6(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL22_SSI_WS6(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL22_SSI_SDATA6(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL23_SSI_SCK78(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL23_SSI_WS78(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL23_SSI_SDATA7(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL23_SSI_SDATA8(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL23_SSI_SDATA9(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL23_AUDIO_CLKA(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL23_AUDIO_CLKB(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL23_USB0_PWEN(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL24_USB0_OVC(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL24_USB1_PWEN(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL24_USB1_OVC(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL24_USB30_PWEN(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL24_USB30_OVC(x)	((uint32_t)(x) << 12U)
+#define DRVCTRL24_USB31_PWEN(x)	((uint32_t)(x) << 8U)
+#define DRVCTRL24_USB31_OVC(x)	((uint32_t)(x) << 4U)
+
+#define MOD_SEL0_MSIOF3_A	((uint32_t)0U << 29U)
+#define MOD_SEL0_MSIOF3_B	((uint32_t)1U << 29U)
+#define MOD_SEL0_MSIOF3_C	((uint32_t)2U << 29U)
+#define MOD_SEL0_MSIOF3_D	((uint32_t)3U << 29U)
+#define MOD_SEL0_MSIOF3_E	((uint32_t)4U << 29U)
+#define MOD_SEL0_MSIOF2_A	((uint32_t)0U << 27U)
+#define MOD_SEL0_MSIOF2_B	((uint32_t)1U << 27U)
+#define MOD_SEL0_MSIOF2_C	((uint32_t)2U << 27U)
+#define MOD_SEL0_MSIOF2_D	((uint32_t)3U << 27U)
+#define MOD_SEL0_MSIOF1_A	((uint32_t)0U << 24U)
+#define MOD_SEL0_MSIOF1_B	((uint32_t)1U << 24U)
+#define MOD_SEL0_MSIOF1_C	((uint32_t)2U << 24U)
+#define MOD_SEL0_MSIOF1_D	((uint32_t)3U << 24U)
+#define MOD_SEL0_MSIOF1_E	((uint32_t)4U << 24U)
+#define MOD_SEL0_MSIOF1_F	((uint32_t)5U << 24U)
+#define MOD_SEL0_MSIOF1_G	((uint32_t)6U << 24U)
+#define MOD_SEL0_LBSC_A		((uint32_t)0U << 23U)
+#define MOD_SEL0_LBSC_B		((uint32_t)1U << 23U)
+#define MOD_SEL0_IEBUS_A	((uint32_t)0U << 22U)
+#define MOD_SEL0_IEBUS_B	((uint32_t)1U << 22U)
+#define MOD_SEL0_I2C2_A		((uint32_t)0U << 21U)
+#define MOD_SEL0_I2C2_B		((uint32_t)1U << 21U)
+#define MOD_SEL0_I2C1_A		((uint32_t)0U << 20U)
+#define MOD_SEL0_I2C1_B		((uint32_t)1U << 20U)
+#define MOD_SEL0_HSCIF4_A	((uint32_t)0U << 19U)
+#define MOD_SEL0_HSCIF4_B	((uint32_t)1U << 19U)
+#define MOD_SEL0_HSCIF3_A	((uint32_t)0U << 17U)
+#define MOD_SEL0_HSCIF3_B	((uint32_t)1U << 17U)
+#define MOD_SEL0_HSCIF3_C	((uint32_t)2U << 17U)
+#define MOD_SEL0_HSCIF3_D	((uint32_t)3U << 17U)
+#define MOD_SEL0_HSCIF1_A	((uint32_t)0U << 16U)
+#define MOD_SEL0_HSCIF1_B	((uint32_t)1U << 16U)
+#define MOD_SEL0_FSO_A		((uint32_t)0U << 15U)
+#define MOD_SEL0_FSO_B		((uint32_t)1U << 15U)
+#define MOD_SEL0_HSCIF2_A	((uint32_t)0U << 13U)
+#define MOD_SEL0_HSCIF2_B	((uint32_t)1U << 13U)
+#define MOD_SEL0_HSCIF2_C	((uint32_t)2U << 13U)
+#define MOD_SEL0_ETHERAVB_A	((uint32_t)0U << 12U)
+#define MOD_SEL0_ETHERAVB_B	((uint32_t)1U << 12U)
+#define MOD_SEL0_DRIF3_A	((uint32_t)0U << 11U)
+#define MOD_SEL0_DRIF3_B	((uint32_t)1U << 11U)
+#define MOD_SEL0_DRIF2_A	((uint32_t)0U << 10U)
+#define MOD_SEL0_DRIF2_B	((uint32_t)1U << 10U)
+#define MOD_SEL0_DRIF1_A	((uint32_t)0U << 8U)
+#define MOD_SEL0_DRIF1_B	((uint32_t)1U << 8U)
+#define MOD_SEL0_DRIF1_C	((uint32_t)2U << 8U)
+#define MOD_SEL0_DRIF0_A	((uint32_t)0U << 6U)
+#define MOD_SEL0_DRIF0_B	((uint32_t)1U << 6U)
+#define MOD_SEL0_DRIF0_C	((uint32_t)2U << 6U)
+#define MOD_SEL0_CANFD0_A	((uint32_t)0U << 5U)
+#define MOD_SEL0_CANFD0_B	((uint32_t)1U << 5U)
+#define MOD_SEL0_ADG_A_A	((uint32_t)0U << 3U)
+#define MOD_SEL0_ADG_A_B	((uint32_t)1U << 3U)
+#define MOD_SEL0_ADG_A_C	((uint32_t)2U << 3U)
+#define MOD_SEL1_TSIF1_A	((uint32_t)0U << 30U)
+#define MOD_SEL1_TSIF1_B	((uint32_t)1U << 30U)
+#define MOD_SEL1_TSIF1_C	((uint32_t)2U << 30U)
+#define MOD_SEL1_TSIF1_D	((uint32_t)3U << 30U)
+#define MOD_SEL1_TSIF0_A	((uint32_t)0U << 27U)
+#define MOD_SEL1_TSIF0_B	((uint32_t)1U << 27U)
+#define MOD_SEL1_TSIF0_C	((uint32_t)2U << 27U)
+#define MOD_SEL1_TSIF0_D	((uint32_t)3U << 27U)
+#define MOD_SEL1_TSIF0_E	((uint32_t)4U << 27U)
+#define MOD_SEL1_TIMER_TMU_A	((uint32_t)0U << 26U)
+#define MOD_SEL1_TIMER_TMU_B	((uint32_t)1U << 26U)
+#define MOD_SEL1_SSP1_1_A	((uint32_t)0U << 24U)
+#define MOD_SEL1_SSP1_1_B	((uint32_t)1U << 24U)
+#define MOD_SEL1_SSP1_1_C	((uint32_t)2U << 24U)
+#define MOD_SEL1_SSP1_1_D	((uint32_t)3U << 24U)
+#define MOD_SEL1_SSP1_0_A	((uint32_t)0U << 21U)
+#define MOD_SEL1_SSP1_0_B	((uint32_t)1U << 21U)
+#define MOD_SEL1_SSP1_0_C	((uint32_t)2U << 21U)
+#define MOD_SEL1_SSP1_0_D	((uint32_t)3U << 21U)
+#define MOD_SEL1_SSP1_0_E	((uint32_t)4U << 21U)
+#define MOD_SEL1_SSI_A		((uint32_t)0U << 20U)
+#define MOD_SEL1_SSI_B		((uint32_t)1U << 20U)
+#define MOD_SEL1_SPEED_PULSE_IF_A	((uint32_t)0U << 19U)
+#define MOD_SEL1_SPEED_PULSE_IF_B	((uint32_t)1U << 19U)
+#define MOD_SEL1_SIMCARD_A	((uint32_t)0U << 17U)
+#define MOD_SEL1_SIMCARD_B	((uint32_t)1U << 17U)
+#define MOD_SEL1_SIMCARD_C	((uint32_t)2U << 17U)
+#define MOD_SEL1_SIMCARD_D	((uint32_t)3U << 17U)
+#define MOD_SEL1_SDHI2_A	((uint32_t)0U << 16U)
+#define MOD_SEL1_SDHI2_B	((uint32_t)1U << 16U)
+#define MOD_SEL1_SCIF4_A	((uint32_t)0U << 14U)
+#define MOD_SEL1_SCIF4_B	((uint32_t)1U << 14U)
+#define MOD_SEL1_SCIF4_C	((uint32_t)2U << 14U)
+#define MOD_SEL1_SCIF3_A	((uint32_t)0U << 13U)
+#define MOD_SEL1_SCIF3_B	((uint32_t)1U << 13U)
+#define MOD_SEL1_SCIF2_A	((uint32_t)0U << 12U)
+#define MOD_SEL1_SCIF2_B	((uint32_t)1U << 12U)
+#define MOD_SEL1_SCIF1_A	((uint32_t)0U << 11U)
+#define MOD_SEL1_SCIF1_B	((uint32_t)1U << 11U)
+#define MOD_SEL1_SCIF_A		((uint32_t)0U << 10U)
+#define MOD_SEL1_SCIF_B		((uint32_t)1U << 10U)
+#define MOD_SEL1_REMOCON_A	((uint32_t)0U << 9U)
+#define MOD_SEL1_REMOCON_B	((uint32_t)1U << 9U)
+#define MOD_SEL1_RCAN0_A	((uint32_t)0U << 6U)
+#define MOD_SEL1_RCAN0_B	((uint32_t)1U << 6U)
+#define MOD_SEL1_PWM6_A		((uint32_t)0U << 5U)
+#define MOD_SEL1_PWM6_B		((uint32_t)1U << 5U)
+#define MOD_SEL1_PWM5_A		((uint32_t)0U << 4U)
+#define MOD_SEL1_PWM5_B		((uint32_t)1U << 4U)
+#define MOD_SEL1_PWM4_A		((uint32_t)0U << 3U)
+#define MOD_SEL1_PWM4_B		((uint32_t)1U << 3U)
+#define MOD_SEL1_PWM3_A		((uint32_t)0U << 2U)
+#define MOD_SEL1_PWM3_B		((uint32_t)1U << 2U)
+#define MOD_SEL1_PWM2_A		((uint32_t)0U << 1U)
+#define MOD_SEL1_PWM2_B		((uint32_t)1U << 1U)
+#define MOD_SEL1_PWM1_A		((uint32_t)0U << 0U)
+#define MOD_SEL1_PWM1_B		((uint32_t)1U << 0U)
+#define MOD_SEL2_I2C_5_A	((uint32_t)0U << 31U)
+#define MOD_SEL2_I2C_5_B	((uint32_t)1U << 31U)
+#define MOD_SEL2_I2C_3_A	((uint32_t)0U << 30U)
+#define MOD_SEL2_I2C_3_B	((uint32_t)1U << 30U)
+#define MOD_SEL2_I2C_0_A	((uint32_t)0U << 29U)
+#define MOD_SEL2_I2C_0_B	((uint32_t)1U << 29U)
+#define MOD_SEL2_FM_A		((uint32_t)0U << 27U)
+#define MOD_SEL2_FM_B		((uint32_t)1U << 27U)
+#define MOD_SEL2_FM_C		((uint32_t)2U << 27U)
+#define MOD_SEL2_FM_D		((uint32_t)3U << 27U)
+#define MOD_SEL2_SCIF5_A	((uint32_t)0U << 26U)
+#define MOD_SEL2_SCIF5_B	((uint32_t)1U << 26U)
+#define MOD_SEL2_I2C6_A		((uint32_t)0U << 23U)
+#define MOD_SEL2_I2C6_B		((uint32_t)1U << 23U)
+#define MOD_SEL2_I2C6_C		((uint32_t)2U << 23U)
+#define MOD_SEL2_NDF_A		((uint32_t)0U << 22U)
+#define MOD_SEL2_NDF_B		((uint32_t)1U << 22U)
+#define MOD_SEL2_SSI2_A		((uint32_t)0U << 21U)
+#define MOD_SEL2_SSI2_B		((uint32_t)1U << 21U)
+#define MOD_SEL2_SSI9_A		((uint32_t)0U << 20U)
+#define MOD_SEL2_SSI9_B		((uint32_t)1U << 20U)
+#define MOD_SEL2_TIMER_TMU2_A	((uint32_t)0U << 19U)
+#define MOD_SEL2_TIMER_TMU2_B	((uint32_t)1U << 19U)
+#define MOD_SEL2_ADG_B_A	((uint32_t)0U << 18U)
+#define MOD_SEL2_ADG_B_B	((uint32_t)1U << 18U)
+#define MOD_SEL2_ADG_C_A	((uint32_t)0U << 17U)
+#define MOD_SEL2_ADG_C_B	((uint32_t)1U << 17U)
+#define MOD_SEL2_VIN4_A		((uint32_t)0U << 0U)
+#define MOD_SEL2_VIN4_B		((uint32_t)1U << 0U)
+
+/* SCIF3 Registers for Dummy write */
+#define SCIF3_BASE		(0xE6C50000U)
+#define SCIF3_SCFCR		(SCIF3_BASE + 0x0018U)
+#define SCIF3_SCFDR		(SCIF3_BASE + 0x001CU)
+#define SCFCR_DATA		(0x0000U)
+
+/* Realtime module stop control */
+#define CPG_BASE		(0xE6150000U)
+#define CPG_SCMSTPCR0		(CPG_BASE + 0x0B20U)
+#define CPG_MSTPSR0		(CPG_BASE + 0x0030U)
+#define SCMSTPCR0_RTDMAC	(0x00200000U)
+
+/* RT-DMAC Registers */
+#define RTDMAC_CH		(0U)	/* choose 0 to 15 */
+
+#define RTDMAC_BASE		(0xFFC10000U)
+#define RTDMAC_RDMOR		(RTDMAC_BASE + 0x0060U)
+#define RTDMAC_RDMCHCLR		(RTDMAC_BASE + 0x0080U)
+#define RTDMAC_RDMSAR(x)	(RTDMAC_BASE + 0x8000U + (0x80U * (x)))
+#define RTDMAC_RDMDAR(x)	(RTDMAC_BASE + 0x8004U + (0x80U * (x)))
+#define RTDMAC_RDMTCR(x)	(RTDMAC_BASE + 0x8008U + (0x80U * (x)))
+#define RTDMAC_RDMCHCR(x)	(RTDMAC_BASE + 0x800CU + (0x80U * (x)))
+#define RTDMAC_RDMCHCRB(x)	(RTDMAC_BASE + 0x801CU + (0x80U * (x)))
+#define RTDMAC_RDMDPBASE(x)	(RTDMAC_BASE + 0x8050U + (0x80U * (x)))
+#define RTDMAC_DESC_BASE	(RTDMAC_BASE + 0xA000U)
+#define RTDMAC_DESC_RDMSAR	(RTDMAC_DESC_BASE + 0x0000U)
+#define RTDMAC_DESC_RDMDAR	(RTDMAC_DESC_BASE + 0x0004U)
+#define RTDMAC_DESC_RDMTCR	(RTDMAC_DESC_BASE + 0x0008U)
+
+#define RDMOR_DME		(0x0001U)	/* DMA Master Enable */
+#define RDMCHCR_DPM_INFINITE	(0x30000000U)	/* Infinite repeat mode */
+#define RDMCHCR_RPT_TCR		(0x02000000U)	/* enable to update TCR */
+#define RDMCHCR_TS_2		(0x00000008U)	/* Word(2byte) units transfer */
+#define RDMCHCR_RS_AUTO		(0x00000400U)	/* Auto request */
+#define RDMCHCR_DE		(0x00000001U)	/* DMA Enable */
+#define RDMCHCRB_DRST		(0x00008000U)	/* Descriptor reset */
+#define RDMCHCRB_SLM_256	(0x00000080U)	/* once in 256 clock cycle */
+#define RDMDPBASE_SEL_EXT	(0x00000001U)	/* External memory use */
+
+static void start_rtdma0_descriptor(void)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(RCAR_PRR);
+	reg &= (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+	if (reg == (PRR_PRODUCT_M3_CUT10)) {
+		/* Enable clock supply to RTDMAC. */
+		mstpcr_write(CPG_SCMSTPCR0, CPG_MSTPSR0, SCMSTPCR0_RTDMAC);
+
+		/* Initialize ch0, Reset Descriptor */
+		mmio_write_32(RTDMAC_RDMCHCLR, BIT(RTDMAC_CH));
+		mmio_write_32(RTDMAC_RDMCHCRB(RTDMAC_CH), RDMCHCRB_DRST);
+
+		/* Enable DMA */
+		mmio_write_16(RTDMAC_RDMOR, RDMOR_DME);
+
+		/* Set first transfer */
+		mmio_write_32(RTDMAC_RDMSAR(RTDMAC_CH), RCAR_PRR);
+		mmio_write_32(RTDMAC_RDMDAR(RTDMAC_CH), SCIF3_SCFDR);
+		mmio_write_32(RTDMAC_RDMTCR(RTDMAC_CH), 0x00000001U);
+
+		/* Set descriptor */
+		mmio_write_32(RTDMAC_DESC_RDMSAR, 0x00000000U);
+		mmio_write_32(RTDMAC_DESC_RDMDAR, 0x00000000U);
+		mmio_write_32(RTDMAC_DESC_RDMTCR, 0x00200000U);
+		mmio_write_32(RTDMAC_RDMCHCRB(RTDMAC_CH), RDMCHCRB_SLM_256);
+		mmio_write_32(RTDMAC_RDMDPBASE(RTDMAC_CH), RTDMAC_DESC_BASE
+			      | RDMDPBASE_SEL_EXT);
+
+		/* Set transfer parameter, Start transfer */
+		mmio_write_32(RTDMAC_RDMCHCR(RTDMAC_CH), RDMCHCR_DPM_INFINITE
+			      | RDMCHCR_RPT_TCR
+			      | RDMCHCR_TS_2
+			      | RDMCHCR_RS_AUTO
+			      | RDMCHCR_DE);
+	}
+}
+
+static void pfc_reg_write(uint32_t addr, uint32_t data)
+{
+	uint32_t prr;
+
+	prr = mmio_read_32(RCAR_PRR);
+	prr &= (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+
+	mmio_write_32(PFC_PMMR, ~data);
+	if (prr == (PRR_PRODUCT_M3_CUT10)) {
+		mmio_write_16(SCIF3_SCFCR, SCFCR_DATA);	/* Dummy write */
+	}
+	mmio_write_32((uintptr_t)addr, data);
+	if (prr == (PRR_PRODUCT_M3_CUT10)) {
+		mmio_write_16(SCIF3_SCFCR, SCFCR_DATA);	/* Dummy write */
+	}
+}
+
+void pfc_init_g2m(void)
+{
+	uint32_t reg;
+
+	/*
+	 * PFC write access problem seen on older SoC's. Added a workaround
+	 * in RT-DMAC for fixing the same.
+	 */
+	start_rtdma0_descriptor();
+
+	/* initialize module select */
+	pfc_reg_write(PFC_MOD_SEL0, MOD_SEL0_MSIOF3_A
+		      | MOD_SEL0_MSIOF2_A
+		      | MOD_SEL0_MSIOF1_A
+		      | MOD_SEL0_LBSC_A
+		      | MOD_SEL0_IEBUS_A
+		      | MOD_SEL0_I2C2_A
+		      | MOD_SEL0_I2C1_A
+		      | MOD_SEL0_HSCIF4_A
+		      | MOD_SEL0_HSCIF3_A
+		      | MOD_SEL0_HSCIF1_A
+		      | MOD_SEL0_FSO_A
+		      | MOD_SEL0_HSCIF2_A
+		      | MOD_SEL0_ETHERAVB_A
+		      | MOD_SEL0_DRIF3_A
+		      | MOD_SEL0_DRIF2_A
+		      | MOD_SEL0_DRIF1_A
+		      | MOD_SEL0_DRIF0_A
+		      | MOD_SEL0_CANFD0_A
+		      | MOD_SEL0_ADG_A_A);
+	pfc_reg_write(PFC_MOD_SEL1, MOD_SEL1_TSIF1_A
+		      | MOD_SEL1_TSIF0_A
+		      | MOD_SEL1_TIMER_TMU_A
+		      | MOD_SEL1_SSP1_1_A
+		      | MOD_SEL1_SSP1_0_A
+		      | MOD_SEL1_SSI_A
+		      | MOD_SEL1_SPEED_PULSE_IF_A
+		      | MOD_SEL1_SIMCARD_A
+		      | MOD_SEL1_SDHI2_A
+		      | MOD_SEL1_SCIF4_A
+		      | MOD_SEL1_SCIF3_A
+		      | MOD_SEL1_SCIF2_A
+		      | MOD_SEL1_SCIF1_A
+		      | MOD_SEL1_SCIF_A
+		      | MOD_SEL1_REMOCON_A
+		      | MOD_SEL1_RCAN0_A
+		      | MOD_SEL1_PWM6_A
+		      | MOD_SEL1_PWM5_A
+		      | MOD_SEL1_PWM4_A
+		      | MOD_SEL1_PWM3_A
+		      | MOD_SEL1_PWM2_A
+		      | MOD_SEL1_PWM1_A);
+	pfc_reg_write(PFC_MOD_SEL2, MOD_SEL2_I2C_5_B
+		      | MOD_SEL2_I2C_3_B
+		      | MOD_SEL2_I2C_0_B
+		      | MOD_SEL2_FM_A
+		      | MOD_SEL2_SCIF5_A
+		      | MOD_SEL2_I2C6_A
+		      | MOD_SEL2_NDF_A
+		      | MOD_SEL2_SSI2_A
+		      | MOD_SEL2_SSI9_A
+		      | MOD_SEL2_TIMER_TMU2_A
+		      | MOD_SEL2_ADG_B_A
+		      | MOD_SEL2_ADG_C_A
+		      | MOD_SEL2_VIN4_A);
+
+	/* initialize peripheral function select */
+	pfc_reg_write(PFC_IPSR0, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR1, IPSR_28_FUNC(6)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(3)
+		      | IPSR_8_FUNC(3)
+		      | IPSR_4_FUNC(3)
+		      | IPSR_0_FUNC(3));
+	pfc_reg_write(PFC_IPSR2, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(6)
+		      | IPSR_20_FUNC(6)
+		      | IPSR_16_FUNC(6)
+		      | IPSR_12_FUNC(6)
+		      | IPSR_8_FUNC(6)
+		      | IPSR_4_FUNC(6)
+		      | IPSR_0_FUNC(6));
+	pfc_reg_write(PFC_IPSR3, IPSR_28_FUNC(6)
+		      | IPSR_24_FUNC(6)
+		      | IPSR_20_FUNC(6)
+		      | IPSR_16_FUNC(6)
+		      | IPSR_12_FUNC(6)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR4, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(6)
+		      | IPSR_4_FUNC(6)
+		      | IPSR_0_FUNC(6));
+	pfc_reg_write(PFC_IPSR5, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(6)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR6, IPSR_28_FUNC(6)
+		      | IPSR_24_FUNC(6)
+		      | IPSR_20_FUNC(6)
+		      | IPSR_16_FUNC(6)
+		      | IPSR_12_FUNC(6)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR7, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(6)
+		      | IPSR_4_FUNC(6)
+		      | IPSR_0_FUNC(6));
+	pfc_reg_write(PFC_IPSR8, IPSR_28_FUNC(1)
+		      | IPSR_24_FUNC(1)
+		      | IPSR_20_FUNC(1)
+		      | IPSR_16_FUNC(1)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR9, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR10, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR11, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(4)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR12, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(4)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR13, IPSR_28_FUNC(8)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(3)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR14, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(3)
+		      | IPSR_0_FUNC(8));
+	pfc_reg_write(PFC_IPSR15, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR16, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR17, IPSR_28_FUNC(0)
+		      | IPSR_24_FUNC(0)
+		      | IPSR_20_FUNC(0)
+		      | IPSR_16_FUNC(0)
+		      | IPSR_12_FUNC(0)
+		      | IPSR_8_FUNC(0)
+		      | IPSR_4_FUNC(1)
+		      | IPSR_0_FUNC(0));
+	pfc_reg_write(PFC_IPSR18, IPSR_4_FUNC(0)
+		      | IPSR_0_FUNC(0));
+
+	/* initialize GPIO/perihperal function select */
+	pfc_reg_write(PFC_GPSR0, GPSR0_D15
+		      | GPSR0_D14
+		      | GPSR0_D13
+		      | GPSR0_D12
+		      | GPSR0_D11
+		      | GPSR0_D10
+		      | GPSR0_D9
+		      | GPSR0_D8
+		      | GPSR0_D7
+		      | GPSR0_D6
+		      | GPSR0_D5
+		      | GPSR0_D4
+		      | GPSR0_D3
+		      | GPSR0_D2
+		      | GPSR0_D0);
+	pfc_reg_write(PFC_GPSR1, GPSR1_CLKOUT
+		      | GPSR1_EX_WAIT0_A
+		      | GPSR1_WE1
+		      | GPSR1_RD
+		      | GPSR1_RD_WR
+		      | GPSR1_CS0
+		      | GPSR1_A19
+		      | GPSR1_A18
+		      | GPSR1_A17
+		      | GPSR1_A16
+		      | GPSR1_A15
+		      | GPSR1_A14
+		      | GPSR1_A13
+		      | GPSR1_A12
+		      | GPSR1_A7
+		      | GPSR1_A6
+		      | GPSR1_A5
+		      | GPSR1_A4
+		      | GPSR1_A3
+		      | GPSR1_A2
+		      | GPSR1_A1
+		      | GPSR1_A0);
+	pfc_reg_write(PFC_GPSR2, GPSR2_AVB_AVTP_CAPTURE_A
+		      | GPSR2_AVB_AVTP_MATCH_A
+		      | GPSR2_AVB_LINK
+		      | GPSR2_AVB_PHY_INT
+		      | GPSR2_AVB_MDC
+		      | GPSR2_PWM2_A
+		      | GPSR2_PWM1_A
+		      | GPSR2_IRQ4
+		      | GPSR2_IRQ3
+		      | GPSR2_IRQ2
+		      | GPSR2_IRQ1
+		      | GPSR2_IRQ0);
+	pfc_reg_write(PFC_GPSR3, GPSR3_SD0_CD
+		      | GPSR3_SD1_DAT3
+		      | GPSR3_SD1_DAT2
+		      | GPSR3_SD1_DAT1
+		      | GPSR3_SD1_DAT0
+		      | GPSR3_SD0_DAT3
+		      | GPSR3_SD0_DAT2
+		      | GPSR3_SD0_DAT1
+		      | GPSR3_SD0_DAT0
+		      | GPSR3_SD0_CMD
+		      | GPSR3_SD0_CLK);
+	pfc_reg_write(PFC_GPSR4, GPSR4_SD3_DS
+		      | GPSR4_SD3_DAT7
+		      | GPSR4_SD3_DAT6
+		      | GPSR4_SD3_DAT5
+		      | GPSR4_SD3_DAT4
+		      | GPSR4_SD3_DAT3
+		      | GPSR4_SD3_DAT2
+		      | GPSR4_SD3_DAT1
+		      | GPSR4_SD3_DAT0
+		      | GPSR4_SD3_CMD
+		      | GPSR4_SD3_CLK
+		      | GPSR4_SD2_DAT3
+		      | GPSR4_SD2_DAT2
+		      | GPSR4_SD2_DAT1
+		      | GPSR4_SD2_DAT0
+		      | GPSR4_SD2_CMD
+		      | GPSR4_SD2_CLK);
+	pfc_reg_write(PFC_GPSR5, GPSR5_MSIOF0_RXD
+		      | GPSR5_MSIOF0_TXD
+		      | GPSR5_MSIOF0_SYNC
+		      | GPSR5_MSIOF0_SCK
+		      | GPSR5_RX2_A
+		      | GPSR5_TX2_A
+		      | GPSR5_RTS1
+		      | GPSR5_CTS1
+		      | GPSR5_TX1_A
+		      | GPSR5_RX1_A
+		      | GPSR5_RTS0
+		      | GPSR5_SCK0);
+	pfc_reg_write(PFC_GPSR6, GPSR6_AUDIO_CLKB_B
+		      | GPSR6_AUDIO_CLKA_A
+		      | GPSR6_SSI_WS6
+		      | GPSR6_SSI_SCK6
+		      | GPSR6_SSI_SDATA4
+		      | GPSR6_SSI_WS4
+		      | GPSR6_SSI_SCK4
+		      | GPSR6_SSI_SDATA1_A
+		      | GPSR6_SSI_SDATA0
+		      | GPSR6_SSI_WS0129
+		      | GPSR6_SSI_SCK0129);
+	pfc_reg_write(PFC_GPSR7, GPSR7_AVS2
+		      | GPSR7_AVS1);
+
+	/* initialize POC control register */
+	pfc_reg_write(PFC_POCCTRL0, POC_SD0_DAT3_33V
+		      | POC_SD0_DAT2_33V
+		      | POC_SD0_DAT1_33V
+		      | POC_SD0_DAT0_33V
+		      | POC_SD0_CMD_33V
+		      | POC_SD0_CLK_33V);
+
+	/* initialize DRV control register */
+	reg = mmio_read_32(PFC_DRVCTRL0);
+	reg = ((reg & DRVCTRL0_MASK) | DRVCTRL0_QSPI0_SPCLK(3)
+		      | DRVCTRL0_QSPI0_MOSI_IO0(3)
+		      | DRVCTRL0_QSPI0_MISO_IO1(3)
+		      | DRVCTRL0_QSPI0_IO2(3)
+		      | DRVCTRL0_QSPI0_IO3(3)
+		      | DRVCTRL0_QSPI0_SSL(3)
+		      | DRVCTRL0_QSPI1_SPCLK(3)
+		      | DRVCTRL0_QSPI1_MOSI_IO0(3));
+	pfc_reg_write(PFC_DRVCTRL0, reg);
+	reg = mmio_read_32(PFC_DRVCTRL1);
+	reg = ((reg & DRVCTRL1_MASK) | DRVCTRL1_QSPI1_MISO_IO1(3)
+		      | DRVCTRL1_QSPI1_IO2(3)
+		      | DRVCTRL1_QSPI1_IO3(3)
+		      | DRVCTRL1_QSPI1_SS(3)
+		      | DRVCTRL1_RPC_INT(3)
+		      | DRVCTRL1_RPC_WP(3)
+		      | DRVCTRL1_RPC_RESET(3)
+		      | DRVCTRL1_AVB_RX_CTL(7));
+	pfc_reg_write(PFC_DRVCTRL1, reg);
+	reg = mmio_read_32(PFC_DRVCTRL2);
+	reg = ((reg & DRVCTRL2_MASK) | DRVCTRL2_AVB_RXC(7)
+		      | DRVCTRL2_AVB_RD0(7)
+		      | DRVCTRL2_AVB_RD1(7)
+		      | DRVCTRL2_AVB_RD2(7)
+		      | DRVCTRL2_AVB_RD3(7)
+		      | DRVCTRL2_AVB_TX_CTL(3)
+		      | DRVCTRL2_AVB_TXC(3)
+		      | DRVCTRL2_AVB_TD0(3));
+	pfc_reg_write(PFC_DRVCTRL2, reg);
+	reg = mmio_read_32(PFC_DRVCTRL3);
+	reg = ((reg & DRVCTRL3_MASK) | DRVCTRL3_AVB_TD1(3)
+		      | DRVCTRL3_AVB_TD2(3)
+		      | DRVCTRL3_AVB_TD3(3)
+		      | DRVCTRL3_AVB_TXCREFCLK(7)
+		      | DRVCTRL3_AVB_MDIO(7)
+		      | DRVCTRL3_AVB_MDC(7)
+		      | DRVCTRL3_AVB_MAGIC(7)
+		      | DRVCTRL3_AVB_PHY_INT(7));
+	pfc_reg_write(PFC_DRVCTRL3, reg);
+	reg = mmio_read_32(PFC_DRVCTRL4);
+	reg = ((reg & DRVCTRL4_MASK) | DRVCTRL4_AVB_LINK(7)
+		      | DRVCTRL4_AVB_AVTP_MATCH(7)
+		      | DRVCTRL4_AVB_AVTP_CAPTURE(7)
+		      | DRVCTRL4_IRQ0(7)
+		      | DRVCTRL4_IRQ1(7)
+		      | DRVCTRL4_IRQ2(7)
+		      | DRVCTRL4_IRQ3(7)
+		      | DRVCTRL4_IRQ4(7));
+	pfc_reg_write(PFC_DRVCTRL4, reg);
+	reg = mmio_read_32(PFC_DRVCTRL5);
+	reg = ((reg & DRVCTRL5_MASK) | DRVCTRL5_IRQ5(7)
+		      | DRVCTRL5_PWM0(7)
+		      | DRVCTRL5_PWM1(7)
+		      | DRVCTRL5_PWM2(7)
+		      | DRVCTRL5_A0(3)
+		      | DRVCTRL5_A1(3)
+		      | DRVCTRL5_A2(3)
+		      | DRVCTRL5_A3(3));
+	pfc_reg_write(PFC_DRVCTRL5, reg);
+	reg = mmio_read_32(PFC_DRVCTRL6);
+	reg = ((reg & DRVCTRL6_MASK) | DRVCTRL6_A4(3)
+		      | DRVCTRL6_A5(3)
+		      | DRVCTRL6_A6(3)
+		      | DRVCTRL6_A7(3)
+		      | DRVCTRL6_A8(7)
+		      | DRVCTRL6_A9(7)
+		      | DRVCTRL6_A10(7)
+		      | DRVCTRL6_A11(7));
+	pfc_reg_write(PFC_DRVCTRL6, reg);
+	reg = mmio_read_32(PFC_DRVCTRL7);
+	reg = ((reg & DRVCTRL7_MASK) | DRVCTRL7_A12(3)
+		      | DRVCTRL7_A13(3)
+		      | DRVCTRL7_A14(3)
+		      | DRVCTRL7_A15(3)
+		      | DRVCTRL7_A16(3)
+		      | DRVCTRL7_A17(3)
+		      | DRVCTRL7_A18(3)
+		      | DRVCTRL7_A19(3));
+	pfc_reg_write(PFC_DRVCTRL7, reg);
+	reg = mmio_read_32(PFC_DRVCTRL8);
+	reg = ((reg & DRVCTRL8_MASK) | DRVCTRL8_CLKOUT(7)
+		      | DRVCTRL8_CS0(7)
+		      | DRVCTRL8_CS1_A2(7)
+		      | DRVCTRL8_BS(7)
+		      | DRVCTRL8_RD(7)
+		      | DRVCTRL8_RD_W(7)
+		      | DRVCTRL8_WE0(7)
+		      | DRVCTRL8_WE1(7));
+	pfc_reg_write(PFC_DRVCTRL8, reg);
+	reg = mmio_read_32(PFC_DRVCTRL9);
+	reg = ((reg & DRVCTRL9_MASK) | DRVCTRL9_EX_WAIT0(7)
+		      | DRVCTRL9_PRESETOU(7)
+		      | DRVCTRL9_D0(7)
+		      | DRVCTRL9_D1(7)
+		      | DRVCTRL9_D2(7)
+		      | DRVCTRL9_D3(7)
+		      | DRVCTRL9_D4(7)
+		      | DRVCTRL9_D5(7));
+	pfc_reg_write(PFC_DRVCTRL9, reg);
+	reg = mmio_read_32(PFC_DRVCTRL10);
+	reg = ((reg & DRVCTRL10_MASK) | DRVCTRL10_D6(7)
+		       | DRVCTRL10_D7(7)
+		       | DRVCTRL10_D8(3)
+		       | DRVCTRL10_D9(3)
+		       | DRVCTRL10_D10(3)
+		       | DRVCTRL10_D11(3)
+		       | DRVCTRL10_D12(3)
+		       | DRVCTRL10_D13(3));
+	pfc_reg_write(PFC_DRVCTRL10, reg);
+	reg = mmio_read_32(PFC_DRVCTRL11);
+	reg = ((reg & DRVCTRL11_MASK) | DRVCTRL11_D14(3)
+		       | DRVCTRL11_D15(3)
+		       | DRVCTRL11_AVS1(7)
+		       | DRVCTRL11_AVS2(7)
+		       | DRVCTRL11_GP7_02(7)
+		       | DRVCTRL11_GP7_03(7)
+		       | DRVCTRL11_DU_DOTCLKIN0(3)
+		       | DRVCTRL11_DU_DOTCLKIN1(3));
+	pfc_reg_write(PFC_DRVCTRL11, reg);
+	reg = mmio_read_32(PFC_DRVCTRL12);
+	reg = ((reg & DRVCTRL12_MASK) | DRVCTRL12_DU_DOTCLKIN2(3)
+		       | DRVCTRL12_DU_DOTCLKIN3(3)
+		       | DRVCTRL12_DU_FSCLKST(3)
+		       | DRVCTRL12_DU_TMS(3));
+	pfc_reg_write(PFC_DRVCTRL12, reg);
+	reg = mmio_read_32(PFC_DRVCTRL13);
+	reg = ((reg & DRVCTRL13_MASK) | DRVCTRL13_TDO(3)
+		       | DRVCTRL13_ASEBRK(3)
+		       | DRVCTRL13_SD0_CLK(7)
+		       | DRVCTRL13_SD0_CMD(7)
+		       | DRVCTRL13_SD0_DAT0(7)
+		       | DRVCTRL13_SD0_DAT1(7)
+		       | DRVCTRL13_SD0_DAT2(7)
+		       | DRVCTRL13_SD0_DAT3(7));
+	pfc_reg_write(PFC_DRVCTRL13, reg);
+	reg = mmio_read_32(PFC_DRVCTRL14);
+	reg = ((reg & DRVCTRL14_MASK) | DRVCTRL14_SD1_CLK(7)
+		       | DRVCTRL14_SD1_CMD(7)
+		       | DRVCTRL14_SD1_DAT0(5)
+		       | DRVCTRL14_SD1_DAT1(5)
+		       | DRVCTRL14_SD1_DAT2(5)
+		       | DRVCTRL14_SD1_DAT3(5)
+		       | DRVCTRL14_SD2_CLK(5)
+		       | DRVCTRL14_SD2_CMD(5));
+	pfc_reg_write(PFC_DRVCTRL14, reg);
+	reg = mmio_read_32(PFC_DRVCTRL15);
+	reg = ((reg & DRVCTRL15_MASK) | DRVCTRL15_SD2_DAT0(5)
+		       | DRVCTRL15_SD2_DAT1(5)
+		       | DRVCTRL15_SD2_DAT2(5)
+		       | DRVCTRL15_SD2_DAT3(5)
+		       | DRVCTRL15_SD2_DS(5)
+		       | DRVCTRL15_SD3_CLK(7)
+		       | DRVCTRL15_SD3_CMD(7)
+		       | DRVCTRL15_SD3_DAT0(7));
+	pfc_reg_write(PFC_DRVCTRL15, reg);
+	reg = mmio_read_32(PFC_DRVCTRL16);
+	reg = ((reg & DRVCTRL16_MASK) | DRVCTRL16_SD3_DAT1(7)
+		       | DRVCTRL16_SD3_DAT2(7)
+		       | DRVCTRL16_SD3_DAT3(7)
+		       | DRVCTRL16_SD3_DAT4(7)
+		       | DRVCTRL16_SD3_DAT5(7)
+		       | DRVCTRL16_SD3_DAT6(7)
+		       | DRVCTRL16_SD3_DAT7(7)
+		       | DRVCTRL16_SD3_DS(7));
+	pfc_reg_write(PFC_DRVCTRL16, reg);
+	reg = mmio_read_32(PFC_DRVCTRL17);
+	reg = ((reg & DRVCTRL17_MASK) | DRVCTRL17_SD0_CD(7)
+		       | DRVCTRL17_SD0_WP(7)
+		       | DRVCTRL17_SD1_CD(7)
+		       | DRVCTRL17_SD1_WP(7)
+		       | DRVCTRL17_SCK0(7)
+		       | DRVCTRL17_RX0(7)
+		       | DRVCTRL17_TX0(7)
+		       | DRVCTRL17_CTS0(7));
+	pfc_reg_write(PFC_DRVCTRL17, reg);
+	reg = mmio_read_32(PFC_DRVCTRL18);
+	reg = ((reg & DRVCTRL18_MASK) | DRVCTRL18_RTS0_TANS(7)
+		       | DRVCTRL18_RX1(7)
+		       | DRVCTRL18_TX1(7)
+		       | DRVCTRL18_CTS1(7)
+		       | DRVCTRL18_RTS1_TANS(7)
+		       | DRVCTRL18_SCK2(7)
+		       | DRVCTRL18_TX2(7)
+		       | DRVCTRL18_RX2(7));
+	pfc_reg_write(PFC_DRVCTRL18, reg);
+	reg = mmio_read_32(PFC_DRVCTRL19);
+	reg = ((reg & DRVCTRL19_MASK) | DRVCTRL19_HSCK0(7)
+		       | DRVCTRL19_HRX0(7)
+		       | DRVCTRL19_HTX0(7)
+		       | DRVCTRL19_HCTS0(7)
+		       | DRVCTRL19_HRTS0(7)
+		       | DRVCTRL19_MSIOF0_SCK(7)
+		       | DRVCTRL19_MSIOF0_SYNC(7)
+		       | DRVCTRL19_MSIOF0_SS1(7));
+	pfc_reg_write(PFC_DRVCTRL19, reg);
+	reg = mmio_read_32(PFC_DRVCTRL20);
+	reg = ((reg & DRVCTRL20_MASK) | DRVCTRL20_MSIOF0_TXD(7)
+		       | DRVCTRL20_MSIOF0_SS2(7)
+		       | DRVCTRL20_MSIOF0_RXD(7)
+		       | DRVCTRL20_MLB_CLK(7)
+		       | DRVCTRL20_MLB_SIG(7)
+		       | DRVCTRL20_MLB_DAT(7)
+		       | DRVCTRL20_MLB_REF(7)
+		       | DRVCTRL20_SSI_SCK0129(7));
+	pfc_reg_write(PFC_DRVCTRL20, reg);
+	reg = mmio_read_32(PFC_DRVCTRL21);
+	reg = ((reg & DRVCTRL21_MASK) | DRVCTRL21_SSI_WS0129(7)
+		       | DRVCTRL21_SSI_SDATA0(7)
+		       | DRVCTRL21_SSI_SDATA1(7)
+		       | DRVCTRL21_SSI_SDATA2(7)
+		       | DRVCTRL21_SSI_SCK34(7)
+		       | DRVCTRL21_SSI_WS34(7)
+		       | DRVCTRL21_SSI_SDATA3(7)
+		       | DRVCTRL21_SSI_SCK4(7));
+	pfc_reg_write(PFC_DRVCTRL21, reg);
+	reg = mmio_read_32(PFC_DRVCTRL22);
+	reg = ((reg & DRVCTRL22_MASK) | DRVCTRL22_SSI_WS4(7)
+		       | DRVCTRL22_SSI_SDATA4(7)
+		       | DRVCTRL22_SSI_SCK5(7)
+		       | DRVCTRL22_SSI_WS5(7)
+		       | DRVCTRL22_SSI_SDATA5(7)
+		       | DRVCTRL22_SSI_SCK6(7)
+		       | DRVCTRL22_SSI_WS6(7)
+		       | DRVCTRL22_SSI_SDATA6(7));
+	pfc_reg_write(PFC_DRVCTRL22, reg);
+	reg = mmio_read_32(PFC_DRVCTRL23);
+	reg = ((reg & DRVCTRL23_MASK) | DRVCTRL23_SSI_SCK78(7)
+		       | DRVCTRL23_SSI_WS78(7)
+		       | DRVCTRL23_SSI_SDATA7(7)
+		       | DRVCTRL23_SSI_SDATA8(7)
+		       | DRVCTRL23_SSI_SDATA9(7)
+		       | DRVCTRL23_AUDIO_CLKA(7)
+		       | DRVCTRL23_AUDIO_CLKB(7)
+		       | DRVCTRL23_USB0_PWEN(7));
+	pfc_reg_write(PFC_DRVCTRL23, reg);
+	reg = mmio_read_32(PFC_DRVCTRL24);
+	reg = ((reg & DRVCTRL24_MASK) | DRVCTRL24_USB0_OVC(7)
+		       | DRVCTRL24_USB1_PWEN(7)
+		       | DRVCTRL24_USB1_OVC(7)
+		       | DRVCTRL24_USB30_PWEN(7)
+		       | DRVCTRL24_USB30_OVC(7)
+		       | DRVCTRL24_USB31_PWEN(7)
+		       | DRVCTRL24_USB31_OVC(7));
+	pfc_reg_write(PFC_DRVCTRL24, reg);
+
+	/* initialize LSI pin pull-up/down control */
+	pfc_reg_write(PFC_PUD0, 0x00005FBFU);
+	pfc_reg_write(PFC_PUD1, 0x00300EFEU);
+	pfc_reg_write(PFC_PUD2, 0x330001E6U);
+	pfc_reg_write(PFC_PUD3, 0x000002E0U);
+	pfc_reg_write(PFC_PUD4, 0xFFFFFF00U);
+	pfc_reg_write(PFC_PUD5, 0x7F5FFF87U);
+	pfc_reg_write(PFC_PUD6, 0x00000055U);
+
+	/* initialize LSI pin pull-enable register */
+	pfc_reg_write(PFC_PUEN0, 0x00000FFFU);
+	pfc_reg_write(PFC_PUEN1, 0x00100234U);
+	pfc_reg_write(PFC_PUEN2, 0x000004C4U);
+	pfc_reg_write(PFC_PUEN3, 0x00000200U);
+	pfc_reg_write(PFC_PUEN4, 0x3E000000U);
+	pfc_reg_write(PFC_PUEN5, 0x1F000805U);
+	pfc_reg_write(PFC_PUEN6, 0x00000006U);
+
+	/* initialize positive/negative logic select */
+	mmio_write_32(GPIO_POSNEG0, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG1, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG2, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG3, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG4, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG5, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG6, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG7, 0x00000000U);
+
+	/* initialize general IO/interrupt switching */
+	mmio_write_32(GPIO_IOINTSEL0, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL1, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL2, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL3, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL4, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL5, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL6, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL7, 0x00000000U);
+
+	/* initialize general output register */
+	mmio_write_32(GPIO_OUTDT0, 0x00000001U);
+	mmio_write_32(GPIO_OUTDT1, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT2, 0x00000400U);
+	mmio_write_32(GPIO_OUTDT3, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT4, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT5, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT6, 0x00003800U);
+	mmio_write_32(GPIO_OUTDT7, 0x00000003U);
+
+	/* initialize general input/output switching */
+	mmio_write_32(GPIO_INOUTSEL0, 0x00000001U);
+	mmio_write_32(GPIO_INOUTSEL1, 0x00100B00U);
+	mmio_write_32(GPIO_INOUTSEL2, 0x00000418U);
+	mmio_write_32(GPIO_INOUTSEL3, 0x00002000U);
+	mmio_write_32(GPIO_INOUTSEL4, 0x00000040U);
+	mmio_write_32(GPIO_INOUTSEL5, 0x00000208U);
+	mmio_write_32(GPIO_INOUTSEL6, 0x00013F00U);
+	mmio_write_32(GPIO_INOUTSEL7, 0x00000003U);
+
+}
diff --git a/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.h b/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.h
new file mode 100644
index 0000000..3315cd6
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PFC_INIT_G2M_H
+#define PFC_INIT_G2M_H
+
+void pfc_init_g2m(void);
+
+#endif /* PFC_INIT_G2M_H */
diff --git a/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c b/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c
new file mode 100644
index 0000000..c951e0a
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c
@@ -0,0 +1,1306 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <lib/mmio.h>
+
+#include "pfc_init_g2n.h"
+#include "rcar_def.h"
+#include "../pfc_regs.h"
+
+#define GPSR0_D15			BIT(15)
+#define GPSR0_D14			BIT(14)
+#define GPSR0_D13			BIT(13)
+#define GPSR0_D12			BIT(12)
+#define GPSR0_D11			BIT(11)
+#define GPSR0_D10			BIT(10)
+#define GPSR0_D9			BIT(9)
+#define GPSR0_D8			BIT(8)
+#define GPSR0_D7			BIT(7)
+#define GPSR0_D6			BIT(6)
+#define GPSR0_D5			BIT(5)
+#define GPSR0_D4			BIT(4)
+#define GPSR0_D3			BIT(3)
+#define GPSR0_D2			BIT(2)
+#define GPSR0_D1			BIT(1)
+#define GPSR0_D0			BIT(0)
+#define GPSR1_CLKOUT			BIT(28)
+#define GPSR1_EX_WAIT0_A		BIT(27)
+#define GPSR1_WE1			BIT(26)
+#define GPSR1_WE0			BIT(25)
+#define GPSR1_RD_WR			BIT(24)
+#define GPSR1_RD			BIT(23)
+#define GPSR1_BS			BIT(22)
+#define GPSR1_CS1_A26			BIT(21)
+#define GPSR1_CS0			BIT(20)
+#define GPSR1_A19			BIT(19)
+#define GPSR1_A18			BIT(18)
+#define GPSR1_A17			BIT(17)
+#define GPSR1_A16			BIT(16)
+#define GPSR1_A15			BIT(15)
+#define GPSR1_A14			BIT(14)
+#define GPSR1_A13			BIT(13)
+#define GPSR1_A12			BIT(12)
+#define GPSR1_A11			BIT(11)
+#define GPSR1_A10			BIT(10)
+#define GPSR1_A9			BIT(9)
+#define GPSR1_A8			BIT(8)
+#define GPSR1_A7			BIT(7)
+#define GPSR1_A6			BIT(6)
+#define GPSR1_A5			BIT(5)
+#define GPSR1_A4			BIT(4)
+#define GPSR1_A3			BIT(3)
+#define GPSR1_A2			BIT(2)
+#define GPSR1_A1			BIT(1)
+#define GPSR1_A0			BIT(0)
+#define GPSR2_AVB_AVTP_CAPTURE_A	BIT(14)
+#define GPSR2_AVB_AVTP_MATCH_A		BIT(13)
+#define GPSR2_AVB_LINK			BIT(12)
+#define GPSR2_AVB_PHY_INT		BIT(11)
+#define GPSR2_AVB_MAGIC			BIT(10)
+#define GPSR2_AVB_MDC			BIT(9)
+#define GPSR2_PWM2_A			BIT(8)
+#define GPSR2_PWM1_A			BIT(7)
+#define GPSR2_PWM0			BIT(6)
+#define GPSR2_IRQ5			BIT(5)
+#define GPSR2_IRQ4			BIT(4)
+#define GPSR2_IRQ3			BIT(3)
+#define GPSR2_IRQ2			BIT(2)
+#define GPSR2_IRQ1			BIT(1)
+#define GPSR2_IRQ0			BIT(0)
+#define GPSR3_SD1_WP			BIT(15)
+#define GPSR3_SD1_CD			BIT(14)
+#define GPSR3_SD0_WP			BIT(13)
+#define GPSR3_SD0_CD			BIT(12)
+#define GPSR3_SD1_DAT3			BIT(11)
+#define GPSR3_SD1_DAT2			BIT(10)
+#define GPSR3_SD1_DAT1			BIT(9)
+#define GPSR3_SD1_DAT0			BIT(8)
+#define GPSR3_SD1_CMD			BIT(7)
+#define GPSR3_SD1_CLK			BIT(6)
+#define GPSR3_SD0_DAT3			BIT(5)
+#define GPSR3_SD0_DAT2			BIT(4)
+#define GPSR3_SD0_DAT1			BIT(3)
+#define GPSR3_SD0_DAT0			BIT(2)
+#define GPSR3_SD0_CMD			BIT(1)
+#define GPSR3_SD0_CLK			BIT(0)
+#define GPSR4_SD3_DS			BIT(17)
+#define GPSR4_SD3_DAT7			BIT(16)
+#define GPSR4_SD3_DAT6			BIT(15)
+#define GPSR4_SD3_DAT5			BIT(14)
+#define GPSR4_SD3_DAT4			BIT(13)
+#define GPSR4_SD3_DAT3			BIT(12)
+#define GPSR4_SD3_DAT2			BIT(11)
+#define GPSR4_SD3_DAT1			BIT(10)
+#define GPSR4_SD3_DAT0			BIT(9)
+#define GPSR4_SD3_CMD			BIT(8)
+#define GPSR4_SD3_CLK			BIT(7)
+#define GPSR4_SD2_DS			BIT(6)
+#define GPSR4_SD2_DAT3			BIT(5)
+#define GPSR4_SD2_DAT2			BIT(4)
+#define GPSR4_SD2_DAT1			BIT(3)
+#define GPSR4_SD2_DAT0			BIT(2)
+#define GPSR4_SD2_CMD			BIT(1)
+#define GPSR4_SD2_CLK			BIT(0)
+#define GPSR5_MLB_DAT			BIT(25)
+#define GPSR5_MLB_SIG			BIT(24)
+#define GPSR5_MLB_CLK			BIT(23)
+#define GPSR5_MSIOF0_RXD		BIT(22)
+#define GPSR5_MSIOF0_SS2		BIT(21)
+#define GPSR5_MSIOF0_TXD		BIT(20)
+#define GPSR5_MSIOF0_SS1		BIT(19)
+#define GPSR5_MSIOF0_SYNC		BIT(18)
+#define GPSR5_MSIOF0_SCK		BIT(17)
+#define GPSR5_HRTS0			BIT(16)
+#define GPSR5_HCTS0			BIT(15)
+#define GPSR5_HTX0			BIT(14)
+#define GPSR5_HRX0			BIT(13)
+#define GPSR5_HSCK0			BIT(12)
+#define GPSR5_RX2_A			BIT(11)
+#define GPSR5_TX2_A			BIT(10)
+#define GPSR5_SCK2			BIT(9)
+#define GPSR5_RTS1			BIT(8)
+#define GPSR5_CTS1			BIT(7)
+#define GPSR5_TX1_A			BIT(6)
+#define GPSR5_RX1_A			BIT(5)
+#define GPSR5_RTS0			BIT(4)
+#define GPSR5_CTS0			BIT(3)
+#define GPSR5_TX0			BIT(2)
+#define GPSR5_RX0			BIT(1)
+#define GPSR5_SCK0			BIT(0)
+#define GPSR6_USB31_OVC			BIT(31)
+#define GPSR6_USB31_PWEN		BIT(30)
+#define GPSR6_USB30_OVC			BIT(29)
+#define GPSR6_USB30_PWEN		BIT(28)
+#define GPSR6_USB1_OVC			BIT(27)
+#define GPSR6_USB1_PWEN			BIT(26)
+#define GPSR6_USB0_OVC			BIT(25)
+#define GPSR6_USB0_PWEN			BIT(24)
+#define GPSR6_AUDIO_CLKB_B		BIT(23)
+#define GPSR6_AUDIO_CLKA_A		BIT(22)
+#define GPSR6_SSI_SDATA9_A		BIT(21)
+#define GPSR6_SSI_SDATA8		BIT(20)
+#define GPSR6_SSI_SDATA7		BIT(19)
+#define GPSR6_SSI_WS78			BIT(18)
+#define GPSR6_SSI_SCK78			BIT(17)
+#define GPSR6_SSI_SDATA6		BIT(16)
+#define GPSR6_SSI_WS6			BIT(15)
+#define GPSR6_SSI_SCK6			BIT(14)
+#define GPSR6_SSI_SDATA5		BIT(13)
+#define GPSR6_SSI_WS5			BIT(12)
+#define GPSR6_SSI_SCK5			BIT(11)
+#define GPSR6_SSI_SDATA4		BIT(10)
+#define GPSR6_SSI_WS4			BIT(9)
+#define GPSR6_SSI_SCK4			BIT(8)
+#define GPSR6_SSI_SDATA3		BIT(7)
+#define GPSR6_SSI_WS34			BIT(6)
+#define GPSR6_SSI_SCK34			BIT(5)
+#define GPSR6_SSI_SDATA2_A		BIT(4)
+#define GPSR6_SSI_SDATA1_A		BIT(3)
+#define GPSR6_SSI_SDATA0		BIT(2)
+#define GPSR6_SSI_WS0129		BIT(1)
+#define GPSR6_SSI_SCK0129		BIT(0)
+#define GPSR7_AVS2			BIT(1)
+#define GPSR7_AVS1			BIT(0)
+
+#define IPSR_28_FUNC(x)		((uint32_t)(x) << 28U)
+#define IPSR_24_FUNC(x)		((uint32_t)(x) << 24U)
+#define IPSR_20_FUNC(x)		((uint32_t)(x) << 20U)
+#define IPSR_16_FUNC(x)		((uint32_t)(x) << 16U)
+#define IPSR_12_FUNC(x)		((uint32_t)(x) << 12U)
+#define IPSR_8_FUNC(x)		((uint32_t)(x) << 8U)
+#define IPSR_4_FUNC(x)		((uint32_t)(x) << 4U)
+#define IPSR_0_FUNC(x)		((uint32_t)(x) << 0U)
+
+#define POC_SD3_DS_33V		BIT(29)
+#define POC_SD3_DAT7_33V	BIT(28)
+#define POC_SD3_DAT6_33V	BIT(27)
+#define POC_SD3_DAT5_33V	BIT(26)
+#define POC_SD3_DAT4_33V	BIT(25)
+#define POC_SD3_DAT3_33V	BIT(24)
+#define POC_SD3_DAT2_33V	BIT(23)
+#define POC_SD3_DAT1_33V	BIT(22)
+#define POC_SD3_DAT0_33V	BIT(21)
+#define POC_SD3_CMD_33V		BIT(20)
+#define POC_SD3_CLK_33V		BIT(19)
+#define POC_SD2_DS_33V		BIT(18)
+#define POC_SD2_DAT3_33V	BIT(17)
+#define POC_SD2_DAT2_33V	BIT(16)
+#define POC_SD2_DAT1_33V	BIT(15)
+#define POC_SD2_DAT0_33V	BIT(14)
+#define POC_SD2_CMD_33V		BIT(13)
+#define POC_SD2_CLK_33V		BIT(12)
+#define POC_SD1_DAT3_33V	BIT(11)
+#define POC_SD1_DAT2_33V	BIT(10)
+#define POC_SD1_DAT1_33V	BIT(9)
+#define POC_SD1_DAT0_33V	BIT(8)
+#define POC_SD1_CMD_33V		BIT(7)
+#define POC_SD1_CLK_33V		BIT(6)
+#define POC_SD0_DAT3_33V	BIT(5)
+#define POC_SD0_DAT2_33V	BIT(4)
+#define POC_SD0_DAT1_33V	BIT(3)
+#define POC_SD0_DAT0_33V	BIT(2)
+#define POC_SD0_CMD_33V		BIT(1)
+#define POC_SD0_CLK_33V		BIT(0)
+
+#define DRVCTRL0_MASK		(0xCCCCCCCCU)
+#define DRVCTRL1_MASK		(0xCCCCCCC8U)
+#define DRVCTRL2_MASK		(0x88888888U)
+#define DRVCTRL3_MASK		(0x88888888U)
+#define DRVCTRL4_MASK		(0x88888888U)
+#define DRVCTRL5_MASK		(0x88888888U)
+#define DRVCTRL6_MASK		(0x88888888U)
+#define DRVCTRL7_MASK		(0x88888888U)
+#define DRVCTRL8_MASK		(0x88888888U)
+#define DRVCTRL9_MASK		(0x88888888U)
+#define DRVCTRL10_MASK		(0x88888888U)
+#define DRVCTRL11_MASK		(0x888888CCU)
+#define DRVCTRL12_MASK		(0xCCCFFFCFU)
+#define DRVCTRL13_MASK		(0xCC888888U)
+#define DRVCTRL14_MASK		(0x88888888U)
+#define DRVCTRL15_MASK		(0x88888888U)
+#define DRVCTRL16_MASK		(0x88888888U)
+#define DRVCTRL17_MASK		(0x88888888U)
+#define DRVCTRL18_MASK		(0x88888888U)
+#define DRVCTRL19_MASK		(0x88888888U)
+#define DRVCTRL20_MASK		(0x88888888U)
+#define DRVCTRL21_MASK		(0x88888888U)
+#define DRVCTRL22_MASK		(0x88888888U)
+#define DRVCTRL23_MASK		(0x88888888U)
+#define DRVCTRL24_MASK		(0x8888888FU)
+
+#define DRVCTRL0_QSPI0_SPCLK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL0_QSPI0_MOSI_IO0(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL0_QSPI0_MISO_IO1(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL0_QSPI0_IO2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL0_QSPI0_IO3(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL0_QSPI0_SSL(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL0_QSPI1_SPCLK(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL0_QSPI1_MOSI_IO0(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL1_QSPI1_MISO_IO1(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL1_QSPI1_IO2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL1_QSPI1_IO3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL1_QSPI1_SS(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL1_RPC_INT(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL1_RPC_WP(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL1_RPC_RESET(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL1_AVB_RX_CTL(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL2_AVB_RXC(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL2_AVB_RD0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL2_AVB_RD1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL2_AVB_RD2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL2_AVB_RD3(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL2_AVB_TX_CTL(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL2_AVB_TXC(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL2_AVB_TD0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL3_AVB_TD1(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL3_AVB_TD2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL3_AVB_TD3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL3_AVB_TXCREFCLK(x)	((uint32_t)(x) << 16U)
+#define DRVCTRL3_AVB_MDIO(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL3_AVB_MDC(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL3_AVB_MAGIC(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL3_AVB_PHY_INT(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL4_AVB_LINK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL4_AVB_AVTP_MATCH(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL4_AVB_AVTP_CAPTURE(x)	((uint32_t)(x) << 20U)
+#define DRVCTRL4_IRQ0(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL4_IRQ1(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL4_IRQ2(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL4_IRQ3(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL4_IRQ4(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL5_IRQ5(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL5_PWM0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL5_PWM1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL5_PWM2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL5_A0(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL5_A1(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL5_A2(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL5_A3(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL6_A4(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL6_A5(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL6_A6(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL6_A7(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL6_A8(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL6_A9(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL6_A10(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL6_A11(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL7_A12(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL7_A13(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL7_A14(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL7_A15(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL7_A16(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL7_A17(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL7_A18(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL7_A19(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL8_CLKOUT(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL8_CS0(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL8_CS1_A2(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL8_BS(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL8_RD(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL8_RD_W(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL8_WE0(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL8_WE1(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL9_EX_WAIT0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL9_PRESETOU(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL9_D0(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL9_D1(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL9_D2(x)			((uint32_t)(x) << 12U)
+#define DRVCTRL9_D3(x)			((uint32_t)(x) << 8U)
+#define DRVCTRL9_D4(x)			((uint32_t)(x) << 4U)
+#define DRVCTRL9_D5(x)			((uint32_t)(x) << 0U)
+#define DRVCTRL10_D6(x)			((uint32_t)(x) << 28U)
+#define DRVCTRL10_D7(x)			((uint32_t)(x) << 24U)
+#define DRVCTRL10_D8(x)			((uint32_t)(x) << 20U)
+#define DRVCTRL10_D9(x)			((uint32_t)(x) << 16U)
+#define DRVCTRL10_D10(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL10_D11(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL10_D12(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL10_D13(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL11_D14(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL11_D15(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL11_AVS1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL11_AVS2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL11_GP7_02(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL11_GP7_03(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL11_DU_DOTCLKIN0(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL11_DU_DOTCLKIN1(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL12_DU_DOTCLKIN2(x)	((uint32_t)(x) << 28U)
+#define DRVCTRL12_DU_DOTCLKIN3(x)	((uint32_t)(x) << 24U)
+#define DRVCTRL12_DU_FSCLKST(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL12_DU_TMS(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL13_TDO(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL13_ASEBRK(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL13_SD0_CLK(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL13_SD0_CMD(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL13_SD0_DAT0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL13_SD0_DAT1(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL13_SD0_DAT2(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL13_SD0_DAT3(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL14_SD1_CLK(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL14_SD1_CMD(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL14_SD1_DAT0(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL14_SD1_DAT1(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL14_SD1_DAT2(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL14_SD1_DAT3(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL14_SD2_CLK(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL14_SD2_CMD(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL15_SD2_DAT0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL15_SD2_DAT1(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL15_SD2_DAT2(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL15_SD2_DAT3(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL15_SD2_DS(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL15_SD3_CLK(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL15_SD3_CMD(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL15_SD3_DAT0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL16_SD3_DAT1(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL16_SD3_DAT2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL16_SD3_DAT3(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL16_SD3_DAT4(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL16_SD3_DAT5(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL16_SD3_DAT6(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL16_SD3_DAT7(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL16_SD3_DS(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL17_SD0_CD(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL17_SD0_WP(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL17_SD1_CD(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL17_SD1_WP(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL17_SCK0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL17_RX0(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL17_TX0(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL17_CTS0(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL18_RTS0_TANS(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL18_RX1(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL18_TX1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL18_CTS1(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL18_RTS1_TANS(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL18_SCK2(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL18_TX2(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL18_RX2(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL19_HSCK0(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL19_HRX0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL19_HTX0(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL19_HCTS0(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL19_HRTS0(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL19_MSIOF0_SCK(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL19_MSIOF0_SYNC(x)	((uint32_t)(x) << 4U)
+#define DRVCTRL19_MSIOF0_SS1(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL20_MSIOF0_TXD(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL20_MSIOF0_SS2(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL20_MSIOF0_RXD(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL20_MLB_CLK(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL20_MLB_SIG(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL20_MLB_DAT(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL20_MLB_REF(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL20_SSI_SCK0129(x)	((uint32_t)(x) << 0U)
+#define DRVCTRL21_SSI_WS0129(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL21_SSI_SDATA0(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL21_SSI_SDATA1(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL21_SSI_SDATA2(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL21_SSI_SCK34(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL21_SSI_WS34(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL21_SSI_SDATA3(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL21_SSI_SCK4(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL22_SSI_WS4(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL22_SSI_SDATA4(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL22_SSI_SCK5(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL22_SSI_WS5(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL22_SSI_SDATA5(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL22_SSI_SCK6(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL22_SSI_WS6(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL22_SSI_SDATA6(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL23_SSI_SCK78(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL23_SSI_WS78(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL23_SSI_SDATA7(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL23_SSI_SDATA8(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL23_SSI_SDATA9(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL23_AUDIO_CLKA(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL23_AUDIO_CLKB(x)		((uint32_t)(x) << 4U)
+#define DRVCTRL23_USB0_PWEN(x)		((uint32_t)(x) << 0U)
+#define DRVCTRL24_USB0_OVC(x)		((uint32_t)(x) << 28U)
+#define DRVCTRL24_USB1_PWEN(x)		((uint32_t)(x) << 24U)
+#define DRVCTRL24_USB1_OVC(x)		((uint32_t)(x) << 20U)
+#define DRVCTRL24_USB30_PWEN(x)		((uint32_t)(x) << 16U)
+#define DRVCTRL24_USB30_OVC(x)		((uint32_t)(x) << 12U)
+#define DRVCTRL24_USB31_PWEN(x)		((uint32_t)(x) << 8U)
+#define DRVCTRL24_USB31_OVC(x)		((uint32_t)(x) << 4U)
+
+#define MOD_SEL0_MSIOF3_A		((uint32_t)0U << 29U)
+#define MOD_SEL0_MSIOF3_B		((uint32_t)1U << 29U)
+#define MOD_SEL0_MSIOF3_C		((uint32_t)2U << 29U)
+#define MOD_SEL0_MSIOF3_D		((uint32_t)3U << 29U)
+#define MOD_SEL0_MSIOF3_E		((uint32_t)4U << 29U)
+#define MOD_SEL0_MSIOF2_A		((uint32_t)0U << 27U)
+#define MOD_SEL0_MSIOF2_B		((uint32_t)1U << 27U)
+#define MOD_SEL0_MSIOF2_C		((uint32_t)2U << 27U)
+#define MOD_SEL0_MSIOF2_D		((uint32_t)3U << 27U)
+#define MOD_SEL0_MSIOF1_A		((uint32_t)0U << 24U)
+#define MOD_SEL0_MSIOF1_B		((uint32_t)1U << 24U)
+#define MOD_SEL0_MSIOF1_C		((uint32_t)2U << 24U)
+#define MOD_SEL0_MSIOF1_D		((uint32_t)3U << 24U)
+#define MOD_SEL0_MSIOF1_E		((uint32_t)4U << 24U)
+#define MOD_SEL0_MSIOF1_F		((uint32_t)5U << 24U)
+#define MOD_SEL0_MSIOF1_G		((uint32_t)6U << 24U)
+#define MOD_SEL0_LBSC_A			((uint32_t)0U << 23U)
+#define MOD_SEL0_LBSC_B			((uint32_t)1U << 23U)
+#define MOD_SEL0_IEBUS_A		((uint32_t)0U << 22U)
+#define MOD_SEL0_IEBUS_B		((uint32_t)1U << 22U)
+#define MOD_SEL0_I2C2_A			((uint32_t)0U << 21U)
+#define MOD_SEL0_I2C2_B			((uint32_t)1U << 21U)
+#define MOD_SEL0_I2C1_A			((uint32_t)0U << 20U)
+#define MOD_SEL0_I2C1_B			((uint32_t)1U << 20U)
+#define MOD_SEL0_HSCIF4_A		((uint32_t)0U << 19U)
+#define MOD_SEL0_HSCIF4_B		((uint32_t)1U << 19U)
+#define MOD_SEL0_HSCIF3_A		((uint32_t)0U << 17U)
+#define MOD_SEL0_HSCIF3_B		((uint32_t)1U << 17U)
+#define MOD_SEL0_HSCIF3_C		((uint32_t)2U << 17U)
+#define MOD_SEL0_HSCIF3_D		((uint32_t)3U << 17U)
+#define MOD_SEL0_HSCIF1_A		((uint32_t)0U << 16U)
+#define MOD_SEL0_HSCIF1_B		((uint32_t)1U << 16U)
+#define MOD_SEL0_FSO_A			((uint32_t)0U << 15U)
+#define MOD_SEL0_FSO_B			((uint32_t)1U << 15U)
+#define MOD_SEL0_HSCIF2_A		((uint32_t)0U << 13U)
+#define MOD_SEL0_HSCIF2_B		((uint32_t)1U << 13U)
+#define MOD_SEL0_HSCIF2_C		((uint32_t)2U << 13U)
+#define MOD_SEL0_ETHERAVB_A		((uint32_t)0U << 12U)
+#define MOD_SEL0_ETHERAVB_B		((uint32_t)1U << 12U)
+#define MOD_SEL0_DRIF3_A		((uint32_t)0U << 11U)
+#define MOD_SEL0_DRIF3_B		((uint32_t)1U << 11U)
+#define MOD_SEL0_DRIF2_A		((uint32_t)0U << 10U)
+#define MOD_SEL0_DRIF2_B		((uint32_t)1U << 10U)
+#define MOD_SEL0_DRIF1_A		((uint32_t)0U << 8U)
+#define MOD_SEL0_DRIF1_B		((uint32_t)1U << 8U)
+#define MOD_SEL0_DRIF1_C		((uint32_t)2U << 8U)
+#define MOD_SEL0_DRIF0_A		((uint32_t)0U << 6U)
+#define MOD_SEL0_DRIF0_B		((uint32_t)1U << 6U)
+#define MOD_SEL0_DRIF0_C		((uint32_t)2U << 6U)
+#define MOD_SEL0_CANFD0_A		((uint32_t)0U << 5U)
+#define MOD_SEL0_CANFD0_B		((uint32_t)1U << 5U)
+#define MOD_SEL0_ADG_A_A		((uint32_t)0U << 3U)
+#define MOD_SEL0_ADG_A_B		((uint32_t)1U << 3U)
+#define MOD_SEL0_ADG_A_C		((uint32_t)2U << 3U)
+#define MOD_SEL1_TSIF1_A		((uint32_t)0U << 30U)
+#define MOD_SEL1_TSIF1_B		((uint32_t)1U << 30U)
+#define MOD_SEL1_TSIF1_C		((uint32_t)2U << 30U)
+#define MOD_SEL1_TSIF1_D		((uint32_t)3U << 30U)
+#define MOD_SEL1_TSIF0_A		((uint32_t)0U << 27U)
+#define MOD_SEL1_TSIF0_B		((uint32_t)1U << 27U)
+#define MOD_SEL1_TSIF0_C		((uint32_t)2U << 27U)
+#define MOD_SEL1_TSIF0_D		((uint32_t)3U << 27U)
+#define MOD_SEL1_TSIF0_E		((uint32_t)4U << 27U)
+#define MOD_SEL1_TIMER_TMU_A		((uint32_t)0U << 26U)
+#define MOD_SEL1_TIMER_TMU_B		((uint32_t)1U << 26U)
+#define MOD_SEL1_SSP1_1_A		((uint32_t)0U << 24U)
+#define MOD_SEL1_SSP1_1_B		((uint32_t)1U << 24U)
+#define MOD_SEL1_SSP1_1_C		((uint32_t)2U << 24U)
+#define MOD_SEL1_SSP1_1_D		((uint32_t)3U << 24U)
+#define MOD_SEL1_SSP1_0_A		((uint32_t)0U << 21U)
+#define MOD_SEL1_SSP1_0_B		((uint32_t)1U << 21U)
+#define MOD_SEL1_SSP1_0_C		((uint32_t)2U << 21U)
+#define MOD_SEL1_SSP1_0_D		((uint32_t)3U << 21U)
+#define MOD_SEL1_SSP1_0_E		((uint32_t)4U << 21U)
+#define MOD_SEL1_SSI_A			((uint32_t)0U << 20U)
+#define MOD_SEL1_SSI_B			((uint32_t)1U << 20U)
+#define MOD_SEL1_SPEED_PULSE_IF_A	((uint32_t)0U << 19U)
+#define MOD_SEL1_SPEED_PULSE_IF_B	((uint32_t)1U << 19U)
+#define MOD_SEL1_SIMCARD_A		((uint32_t)0U << 17U)
+#define MOD_SEL1_SIMCARD_B		((uint32_t)1U << 17U)
+#define MOD_SEL1_SIMCARD_C		((uint32_t)2U << 17U)
+#define MOD_SEL1_SIMCARD_D		((uint32_t)3U << 17U)
+#define MOD_SEL1_SDHI2_A		((uint32_t)0U << 16U)
+#define MOD_SEL1_SDHI2_B		((uint32_t)1U << 16U)
+#define MOD_SEL1_SCIF4_A		((uint32_t)0U << 14U)
+#define MOD_SEL1_SCIF4_B		((uint32_t)1U << 14U)
+#define MOD_SEL1_SCIF4_C		((uint32_t)2U << 14U)
+#define MOD_SEL1_SCIF3_A		((uint32_t)0U << 13U)
+#define MOD_SEL1_SCIF3_B		((uint32_t)1U << 13U)
+#define MOD_SEL1_SCIF2_A		((uint32_t)0U << 12U)
+#define MOD_SEL1_SCIF2_B		((uint32_t)1U << 12U)
+#define MOD_SEL1_SCIF1_A		((uint32_t)0U << 11U)
+#define MOD_SEL1_SCIF1_B		((uint32_t)1U << 11U)
+#define MOD_SEL1_SCIF_A			((uint32_t)0U << 10U)
+#define MOD_SEL1_SCIF_B			((uint32_t)1U << 10U)
+#define MOD_SEL1_REMOCON_A		((uint32_t)0U << 9U)
+#define MOD_SEL1_REMOCON_B		((uint32_t)1U << 9U)
+#define MOD_SEL1_RCAN0_A		((uint32_t)0U << 6U)
+#define MOD_SEL1_RCAN0_B		((uint32_t)1U << 6U)
+#define MOD_SEL1_PWM6_A			((uint32_t)0U << 5U)
+#define MOD_SEL1_PWM6_B			((uint32_t)1U << 5U)
+#define MOD_SEL1_PWM5_A			((uint32_t)0U << 4U)
+#define MOD_SEL1_PWM5_B			((uint32_t)1U << 4U)
+#define MOD_SEL1_PWM4_A			((uint32_t)0U << 3U)
+#define MOD_SEL1_PWM4_B			((uint32_t)1U << 3U)
+#define MOD_SEL1_PWM3_A			((uint32_t)0U << 2U)
+#define MOD_SEL1_PWM3_B			((uint32_t)1U << 2U)
+#define MOD_SEL1_PWM2_A			((uint32_t)0U << 1U)
+#define MOD_SEL1_PWM2_B			((uint32_t)1U << 1U)
+#define MOD_SEL1_PWM1_A			((uint32_t)0U << 0U)
+#define MOD_SEL1_PWM1_B			((uint32_t)1U << 0U)
+#define MOD_SEL2_I2C_5_A		((uint32_t)0U << 31U)
+#define MOD_SEL2_I2C_5_B		((uint32_t)1U << 31U)
+#define MOD_SEL2_I2C_3_A		((uint32_t)0U << 30U)
+#define MOD_SEL2_I2C_3_B		((uint32_t)1U << 30U)
+#define MOD_SEL2_I2C_0_A		((uint32_t)0U << 29U)
+#define MOD_SEL2_I2C_0_B		((uint32_t)1U << 29U)
+#define MOD_SEL2_FM_A			((uint32_t)0U << 27U)
+#define MOD_SEL2_FM_B			((uint32_t)1U << 27U)
+#define MOD_SEL2_FM_C			((uint32_t)2U << 27U)
+#define MOD_SEL2_FM_D			((uint32_t)3U << 27U)
+#define MOD_SEL2_SCIF5_A		((uint32_t)0U << 26U)
+#define MOD_SEL2_SCIF5_B		((uint32_t)1U << 26U)
+#define MOD_SEL2_I2C6_A			((uint32_t)0U << 23U)
+#define MOD_SEL2_I2C6_B			((uint32_t)1U << 23U)
+#define MOD_SEL2_I2C6_C			((uint32_t)2U << 23U)
+#define MOD_SEL2_NDF_A			((uint32_t)0U << 22U)
+#define MOD_SEL2_NDF_B			((uint32_t)1U << 22U)
+#define MOD_SEL2_SSI2_A			((uint32_t)0U << 21U)
+#define MOD_SEL2_SSI2_B			((uint32_t)1U << 21U)
+#define MOD_SEL2_SSI9_A			((uint32_t)0U << 20U)
+#define MOD_SEL2_SSI9_B			((uint32_t)1U << 20U)
+#define MOD_SEL2_TIMER_TMU2_A		((uint32_t)0U << 19U)
+#define MOD_SEL2_TIMER_TMU2_B		((uint32_t)1U << 19U)
+#define MOD_SEL2_ADG_B_A		((uint32_t)0U << 18U)
+#define MOD_SEL2_ADG_B_B		((uint32_t)1U << 18U)
+#define MOD_SEL2_ADG_C_A		((uint32_t)0U << 17U)
+#define MOD_SEL2_ADG_C_B		((uint32_t)1U << 17U)
+#define MOD_SEL2_VIN4_A			((uint32_t)0U << 0U)
+#define MOD_SEL2_VIN4_B			((uint32_t)1U << 0U)
+
+static void pfc_reg_write(uint32_t addr, uint32_t data)
+{
+	mmio_write_32(PFC_PMMR, ~data);
+	mmio_write_32((uintptr_t)addr, data);
+}
+
+void pfc_init_g2n(void)
+{
+	uint32_t reg;
+
+	/* initialize module select */
+	pfc_reg_write(PFC_MOD_SEL0,
+		      MOD_SEL0_MSIOF3_A |
+		      MOD_SEL0_MSIOF2_A |
+		      MOD_SEL0_MSIOF1_A |
+		      MOD_SEL0_LBSC_A |
+		      MOD_SEL0_IEBUS_A |
+		      MOD_SEL0_I2C2_A |
+		      MOD_SEL0_I2C1_A |
+		      MOD_SEL0_HSCIF4_A |
+		      MOD_SEL0_HSCIF3_A |
+		      MOD_SEL0_HSCIF1_A |
+		      MOD_SEL0_FSO_A |
+		      MOD_SEL0_HSCIF2_A |
+		      MOD_SEL0_ETHERAVB_A |
+		      MOD_SEL0_DRIF3_A |
+		      MOD_SEL0_DRIF2_A |
+		      MOD_SEL0_DRIF1_A |
+		      MOD_SEL0_DRIF0_A |
+		      MOD_SEL0_CANFD0_A |
+		      MOD_SEL0_ADG_A_A);
+
+	pfc_reg_write(PFC_MOD_SEL1,
+		      MOD_SEL1_TSIF1_A |
+		      MOD_SEL1_TSIF0_A |
+		      MOD_SEL1_TIMER_TMU_A |
+		      MOD_SEL1_SSP1_1_A |
+		      MOD_SEL1_SSP1_0_A |
+		      MOD_SEL1_SSI_A |
+		      MOD_SEL1_SPEED_PULSE_IF_A |
+		      MOD_SEL1_SIMCARD_A |
+		      MOD_SEL1_SDHI2_A |
+		      MOD_SEL1_SCIF4_A |
+		      MOD_SEL1_SCIF3_A |
+		      MOD_SEL1_SCIF2_A |
+		      MOD_SEL1_SCIF1_A |
+		      MOD_SEL1_SCIF_A |
+		      MOD_SEL1_REMOCON_A |
+		      MOD_SEL1_RCAN0_A |
+		      MOD_SEL1_PWM6_A |
+		      MOD_SEL1_PWM5_A |
+		      MOD_SEL1_PWM4_A |
+		      MOD_SEL1_PWM3_A |
+		      MOD_SEL1_PWM2_A |
+		      MOD_SEL1_PWM1_A);
+
+	pfc_reg_write(PFC_MOD_SEL2,
+		      MOD_SEL2_I2C_5_B |
+		      MOD_SEL2_I2C_3_B |
+		      MOD_SEL2_I2C_0_B |
+		      MOD_SEL2_FM_A |
+		      MOD_SEL2_SCIF5_A |
+		      MOD_SEL2_I2C6_A |
+		      MOD_SEL2_NDF_A |
+		      MOD_SEL2_SSI2_A |
+		      MOD_SEL2_SSI9_A |
+		      MOD_SEL2_TIMER_TMU2_A |
+		      MOD_SEL2_ADG_B_A |
+		      MOD_SEL2_ADG_C_A |
+		      MOD_SEL2_VIN4_A);
+
+	/* initialize peripheral function select */
+	pfc_reg_write(PFC_IPSR0,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR1,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(3) |
+		      IPSR_8_FUNC(3) |
+		      IPSR_4_FUNC(3) |
+		      IPSR_0_FUNC(3));
+
+	pfc_reg_write(PFC_IPSR2,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR3,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR4,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR5,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR6,
+		      IPSR_28_FUNC(6) |
+		      IPSR_24_FUNC(6) |
+		      IPSR_20_FUNC(6) |
+		      IPSR_16_FUNC(6) |
+		      IPSR_12_FUNC(6) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR7,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(6) |
+		      IPSR_4_FUNC(6) |
+		      IPSR_0_FUNC(6));
+
+	pfc_reg_write(PFC_IPSR8,
+		      IPSR_28_FUNC(1) |
+		      IPSR_24_FUNC(1) |
+		      IPSR_20_FUNC(1) |
+		      IPSR_16_FUNC(1) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR9,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR10,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR11,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(4) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR12,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(4) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR13,
+		      IPSR_28_FUNC(8) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(3) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR14,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(3) |
+		      IPSR_0_FUNC(8));
+
+	pfc_reg_write(PFC_IPSR15,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR16,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(0) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR17,
+		      IPSR_28_FUNC(0) |
+		      IPSR_24_FUNC(0) |
+		      IPSR_20_FUNC(0) |
+		      IPSR_16_FUNC(0) |
+		      IPSR_12_FUNC(0) |
+		      IPSR_8_FUNC(0) |
+		      IPSR_4_FUNC(1) |
+		      IPSR_0_FUNC(0));
+
+	pfc_reg_write(PFC_IPSR18, IPSR_4_FUNC(0) | IPSR_0_FUNC(0));
+
+	/* initialize GPIO/peripheral function select */
+	pfc_reg_write(PFC_GPSR0,
+		      GPSR0_D15 |
+		      GPSR0_D14 |
+		      GPSR0_D13 |
+		      GPSR0_D12 |
+		      GPSR0_D11 |
+		      GPSR0_D10 |
+		      GPSR0_D9 |
+		      GPSR0_D8 |
+		      GPSR0_D7 |
+		      GPSR0_D6 |
+		      GPSR0_D5 |
+		      GPSR0_D4 |
+		      GPSR0_D3 |
+		      GPSR0_D2 |
+		      GPSR0_D0);
+
+	pfc_reg_write(PFC_GPSR1,
+		      GPSR1_CLKOUT |
+		      GPSR1_EX_WAIT0_A |
+		      GPSR1_WE1 |
+		      GPSR1_RD |
+		      GPSR1_RD_WR |
+		      GPSR1_CS0 |
+		      GPSR1_A19 |
+		      GPSR1_A18 |
+		      GPSR1_A17 |
+		      GPSR1_A16 |
+		      GPSR1_A15 |
+		      GPSR1_A14 |
+		      GPSR1_A13 |
+		      GPSR1_A12 |
+		      GPSR1_A7 |
+		      GPSR1_A6 |
+		      GPSR1_A5 |
+		      GPSR1_A4 |
+		      GPSR1_A3 |
+		      GPSR1_A2 |
+		      GPSR1_A1 |
+		      GPSR1_A0);
+
+	pfc_reg_write(PFC_GPSR2,
+		      GPSR2_AVB_AVTP_CAPTURE_A |
+		      GPSR2_AVB_AVTP_MATCH_A |
+		      GPSR2_AVB_LINK |
+		      GPSR2_AVB_PHY_INT |
+		      GPSR2_AVB_MDC |
+		      GPSR2_PWM2_A |
+		      GPSR2_PWM1_A |
+		      GPSR2_IRQ4 |
+		      GPSR2_IRQ3 |
+		      GPSR2_IRQ2 |
+		      GPSR2_IRQ1 |
+		      GPSR2_IRQ0);
+
+	pfc_reg_write(PFC_GPSR3,
+		      GPSR3_SD0_CD |
+		      GPSR3_SD1_DAT3 |
+		      GPSR3_SD1_DAT2 |
+		      GPSR3_SD1_DAT1 |
+		      GPSR3_SD1_DAT0 |
+		      GPSR3_SD0_DAT3 |
+		      GPSR3_SD0_DAT2 |
+		      GPSR3_SD0_DAT1 |
+		      GPSR3_SD0_DAT0 |
+		      GPSR3_SD0_CMD |
+		      GPSR3_SD0_CLK);
+
+	pfc_reg_write(PFC_GPSR4,
+		      GPSR4_SD3_DS |
+		      GPSR4_SD3_DAT7 |
+		      GPSR4_SD3_DAT6 |
+		      GPSR4_SD3_DAT5 |
+		      GPSR4_SD3_DAT4 |
+		      GPSR4_SD3_DAT3 |
+		      GPSR4_SD3_DAT2 |
+		      GPSR4_SD3_DAT1 |
+		      GPSR4_SD3_DAT0 |
+		      GPSR4_SD3_CMD |
+		      GPSR4_SD3_CLK |
+		      GPSR4_SD2_DAT3 |
+		      GPSR4_SD2_DAT2 |
+		      GPSR4_SD2_DAT1 |
+		      GPSR4_SD2_DAT0 |
+		      GPSR4_SD2_CMD |
+		      GPSR4_SD2_CLK);
+
+	pfc_reg_write(PFC_GPSR5,
+		      GPSR5_MSIOF0_RXD |
+		      GPSR5_MSIOF0_TXD |
+		      GPSR5_MSIOF0_SYNC |
+		      GPSR5_MSIOF0_SCK |
+		      GPSR5_RX2_A |
+		      GPSR5_TX2_A |
+		      GPSR5_RTS1 |
+		      GPSR5_CTS1 |
+		      GPSR5_TX1_A |
+		      GPSR5_RX1_A |
+		      GPSR5_RTS0 |
+		      GPSR5_SCK0);
+
+	pfc_reg_write(PFC_GPSR6,
+		      GPSR6_AUDIO_CLKB_B |
+		      GPSR6_AUDIO_CLKA_A |
+		      GPSR6_SSI_WS6 |
+		      GPSR6_SSI_SCK6 |
+		      GPSR6_SSI_SDATA4 |
+		      GPSR6_SSI_WS4 |
+		      GPSR6_SSI_SCK4 |
+		      GPSR6_SSI_SDATA1_A |
+		      GPSR6_SSI_SDATA0 |
+		      GPSR6_SSI_WS0129 |
+		      GPSR6_SSI_SCK0129);
+
+	pfc_reg_write(PFC_GPSR7, GPSR7_AVS2 | GPSR7_AVS1);
+
+	/* initialize POC control register */
+	pfc_reg_write(PFC_POCCTRL0,
+		      POC_SD0_DAT3_33V |
+		      POC_SD0_DAT2_33V |
+		      POC_SD0_DAT1_33V |
+		      POC_SD0_DAT0_33V |
+		      POC_SD0_CMD_33V |
+		      POC_SD0_CLK_33V);
+
+	/* initialize DRV control register */
+	reg = mmio_read_32(PFC_DRVCTRL0);
+	reg = (reg & DRVCTRL0_MASK) |
+	      DRVCTRL0_QSPI0_SPCLK(3) |
+	      DRVCTRL0_QSPI0_MOSI_IO0(3) |
+	      DRVCTRL0_QSPI0_MISO_IO1(3) |
+	      DRVCTRL0_QSPI0_IO2(3) |
+	      DRVCTRL0_QSPI0_IO3(3) |
+	      DRVCTRL0_QSPI0_SSL(3) |
+	      DRVCTRL0_QSPI1_SPCLK(3) |
+	      DRVCTRL0_QSPI1_MOSI_IO0(3);
+	pfc_reg_write(PFC_DRVCTRL0, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL1);
+	reg = (reg & DRVCTRL1_MASK) |
+	      DRVCTRL1_QSPI1_MISO_IO1(3) |
+	      DRVCTRL1_QSPI1_IO2(3) |
+	      DRVCTRL1_QSPI1_IO3(3) |
+	      DRVCTRL1_QSPI1_SS(3) |
+	      DRVCTRL1_RPC_INT(3) |
+	      DRVCTRL1_RPC_WP(3) |
+	      DRVCTRL1_RPC_RESET(3) |
+	      DRVCTRL1_AVB_RX_CTL(7);
+	pfc_reg_write(PFC_DRVCTRL1, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL2);
+	reg = (reg & DRVCTRL2_MASK) |
+	      DRVCTRL2_AVB_RXC(7) |
+	      DRVCTRL2_AVB_RD0(7) |
+	      DRVCTRL2_AVB_RD1(7) |
+	      DRVCTRL2_AVB_RD2(7) |
+	      DRVCTRL2_AVB_RD3(7) |
+	      DRVCTRL2_AVB_TX_CTL(3) |
+	      DRVCTRL2_AVB_TXC(3) |
+	      DRVCTRL2_AVB_TD0(3);
+	pfc_reg_write(PFC_DRVCTRL2, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL3);
+	reg = (reg & DRVCTRL3_MASK) |
+	      DRVCTRL3_AVB_TD1(3) |
+	      DRVCTRL3_AVB_TD2(3) |
+	      DRVCTRL3_AVB_TD3(3) |
+	      DRVCTRL3_AVB_TXCREFCLK(7) |
+	      DRVCTRL3_AVB_MDIO(7) |
+	      DRVCTRL3_AVB_MDC(7) |
+	      DRVCTRL3_AVB_MAGIC(7) |
+	      DRVCTRL3_AVB_PHY_INT(7);
+	pfc_reg_write(PFC_DRVCTRL3, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL4);
+	reg = (reg & DRVCTRL4_MASK) |
+	      DRVCTRL4_AVB_LINK(7) |
+	      DRVCTRL4_AVB_AVTP_MATCH(7) |
+	      DRVCTRL4_AVB_AVTP_CAPTURE(7) |
+	      DRVCTRL4_IRQ0(7) |
+	      DRVCTRL4_IRQ1(7) |
+	      DRVCTRL4_IRQ2(7) |
+	      DRVCTRL4_IRQ3(7) |
+	      DRVCTRL4_IRQ4(7);
+	pfc_reg_write(PFC_DRVCTRL4, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL5);
+	reg = (reg & DRVCTRL5_MASK) |
+	      DRVCTRL5_IRQ5(7) |
+	      DRVCTRL5_PWM0(7) |
+	      DRVCTRL5_PWM1(7) |
+	      DRVCTRL5_PWM2(7) |
+	      DRVCTRL5_A0(3) |
+	      DRVCTRL5_A1(3) |
+	      DRVCTRL5_A2(3) |
+	      DRVCTRL5_A3(3);
+	pfc_reg_write(PFC_DRVCTRL5, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL6);
+	reg = (reg & DRVCTRL6_MASK) |
+	      DRVCTRL6_A4(3) |
+	      DRVCTRL6_A5(3) |
+	      DRVCTRL6_A6(3) |
+	      DRVCTRL6_A7(3) |
+	      DRVCTRL6_A8(7) |
+	      DRVCTRL6_A9(7) |
+	      DRVCTRL6_A10(7) |
+	      DRVCTRL6_A11(7);
+	pfc_reg_write(PFC_DRVCTRL6, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL7);
+	reg = (reg & DRVCTRL7_MASK) |
+	      DRVCTRL7_A12(3) |
+	      DRVCTRL7_A13(3) |
+	      DRVCTRL7_A14(3) |
+	      DRVCTRL7_A15(3) |
+	      DRVCTRL7_A16(3) |
+	      DRVCTRL7_A17(3) |
+	      DRVCTRL7_A18(3) |
+	      DRVCTRL7_A19(3);
+	pfc_reg_write(PFC_DRVCTRL7, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL8);
+	reg = (reg & DRVCTRL8_MASK) |
+	      DRVCTRL8_CLKOUT(7) |
+	      DRVCTRL8_CS0(7) |
+	      DRVCTRL8_CS1_A2(7) |
+	      DRVCTRL8_BS(7) |
+	      DRVCTRL8_RD(7) |
+	      DRVCTRL8_RD_W(7) |
+	      DRVCTRL8_WE0(7) |
+	      DRVCTRL8_WE1(7);
+	pfc_reg_write(PFC_DRVCTRL8, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL9);
+	reg = (reg & DRVCTRL9_MASK) |
+	      DRVCTRL9_EX_WAIT0(7) |
+	      DRVCTRL9_PRESETOU(7) |
+	      DRVCTRL9_D0(7) |
+	      DRVCTRL9_D1(7) |
+	      DRVCTRL9_D2(7) |
+	      DRVCTRL9_D3(7) |
+	      DRVCTRL9_D4(7) |
+	      DRVCTRL9_D5(7);
+	pfc_reg_write(PFC_DRVCTRL9, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL10);
+	reg = (reg & DRVCTRL10_MASK) |
+	      DRVCTRL10_D6(7) |
+	      DRVCTRL10_D7(7) |
+	      DRVCTRL10_D8(3) |
+	      DRVCTRL10_D9(3) |
+	      DRVCTRL10_D10(3) |
+	      DRVCTRL10_D11(3) |
+	      DRVCTRL10_D12(3) |
+	      DRVCTRL10_D13(3);
+	pfc_reg_write(PFC_DRVCTRL10, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL11);
+	reg = (reg & DRVCTRL11_MASK) |
+	      DRVCTRL11_D14(3) |
+	      DRVCTRL11_D15(3) |
+	      DRVCTRL11_AVS1(7) |
+	      DRVCTRL11_AVS2(7) |
+	      DRVCTRL11_GP7_02(7) |
+	      DRVCTRL11_GP7_03(7) |
+	      DRVCTRL11_DU_DOTCLKIN0(3) |
+	      DRVCTRL11_DU_DOTCLKIN1(3);
+	pfc_reg_write(PFC_DRVCTRL11, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL12);
+	reg = (reg & DRVCTRL12_MASK) |
+	      DRVCTRL12_DU_DOTCLKIN2(3) |
+	      DRVCTRL12_DU_DOTCLKIN3(3) |
+	      DRVCTRL12_DU_FSCLKST(3) |
+	      DRVCTRL12_DU_TMS(3);
+	pfc_reg_write(PFC_DRVCTRL12, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL13);
+	reg = (reg & DRVCTRL13_MASK) |
+	      DRVCTRL13_TDO(3) |
+	      DRVCTRL13_ASEBRK(3) |
+	      DRVCTRL13_SD0_CLK(7) |
+	      DRVCTRL13_SD0_CMD(7) |
+	      DRVCTRL13_SD0_DAT0(7) |
+	      DRVCTRL13_SD0_DAT1(7) |
+	      DRVCTRL13_SD0_DAT2(7) |
+	      DRVCTRL13_SD0_DAT3(7);
+	pfc_reg_write(PFC_DRVCTRL13, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL14);
+	reg = (reg & DRVCTRL14_MASK) |
+	      DRVCTRL14_SD1_CLK(7) |
+	      DRVCTRL14_SD1_CMD(7) |
+	      DRVCTRL14_SD1_DAT0(5) |
+	      DRVCTRL14_SD1_DAT1(5) |
+	      DRVCTRL14_SD1_DAT2(5) |
+	      DRVCTRL14_SD1_DAT3(5) |
+	      DRVCTRL14_SD2_CLK(5) |
+	      DRVCTRL14_SD2_CMD(5);
+	pfc_reg_write(PFC_DRVCTRL14, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL15);
+	reg = (reg & DRVCTRL15_MASK) |
+	      DRVCTRL15_SD2_DAT0(5) |
+	      DRVCTRL15_SD2_DAT1(5) |
+	      DRVCTRL15_SD2_DAT2(5) |
+	      DRVCTRL15_SD2_DAT3(5) |
+	      DRVCTRL15_SD2_DS(5) |
+	      DRVCTRL15_SD3_CLK(7) |
+	      DRVCTRL15_SD3_CMD(7) |
+	      DRVCTRL15_SD3_DAT0(7);
+	pfc_reg_write(PFC_DRVCTRL15, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL16);
+	reg = (reg & DRVCTRL16_MASK) |
+	      DRVCTRL16_SD3_DAT1(7) |
+	      DRVCTRL16_SD3_DAT2(7) |
+	      DRVCTRL16_SD3_DAT3(7) |
+	      DRVCTRL16_SD3_DAT4(7) |
+	      DRVCTRL16_SD3_DAT5(7) |
+	      DRVCTRL16_SD3_DAT6(7) |
+	      DRVCTRL16_SD3_DAT7(7) |
+	      DRVCTRL16_SD3_DS(7);
+	pfc_reg_write(PFC_DRVCTRL16, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL17);
+	reg = (reg & DRVCTRL17_MASK) |
+	      DRVCTRL17_SD0_CD(7) |
+	      DRVCTRL17_SD0_WP(7) |
+	      DRVCTRL17_SD1_CD(7) |
+	      DRVCTRL17_SD1_WP(7) |
+	      DRVCTRL17_SCK0(7) |
+	      DRVCTRL17_RX0(7) |
+	      DRVCTRL17_TX0(7) |
+	      DRVCTRL17_CTS0(7);
+	pfc_reg_write(PFC_DRVCTRL17, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL18);
+	reg = (reg & DRVCTRL18_MASK) |
+	      DRVCTRL18_RTS0_TANS(7) |
+	      DRVCTRL18_RX1(7) |
+	      DRVCTRL18_TX1(7) |
+	      DRVCTRL18_CTS1(7) |
+	      DRVCTRL18_RTS1_TANS(7) |
+	      DRVCTRL18_SCK2(7) |
+	      DRVCTRL18_TX2(7) |
+	      DRVCTRL18_RX2(7);
+	pfc_reg_write(PFC_DRVCTRL18, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL19);
+	reg = (reg & DRVCTRL19_MASK) |
+	      DRVCTRL19_HSCK0(7) |
+	      DRVCTRL19_HRX0(7) |
+	      DRVCTRL19_HTX0(7) |
+	      DRVCTRL19_HCTS0(7) |
+	      DRVCTRL19_HRTS0(7) |
+	      DRVCTRL19_MSIOF0_SCK(7) |
+	      DRVCTRL19_MSIOF0_SYNC(7) |
+	      DRVCTRL19_MSIOF0_SS1(7);
+	pfc_reg_write(PFC_DRVCTRL19, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL20);
+	reg = (reg & DRVCTRL20_MASK) |
+	      DRVCTRL20_MSIOF0_TXD(7) |
+	      DRVCTRL20_MSIOF0_SS2(7) |
+	      DRVCTRL20_MSIOF0_RXD(7) |
+	      DRVCTRL20_MLB_CLK(7) |
+	      DRVCTRL20_MLB_SIG(7) |
+	      DRVCTRL20_MLB_DAT(7) |
+	      DRVCTRL20_MLB_REF(7) |
+	      DRVCTRL20_SSI_SCK0129(7);
+	pfc_reg_write(PFC_DRVCTRL20, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL21);
+	reg = (reg & DRVCTRL21_MASK) |
+	      DRVCTRL21_SSI_WS0129(7) |
+	      DRVCTRL21_SSI_SDATA0(7) |
+	      DRVCTRL21_SSI_SDATA1(7) |
+	      DRVCTRL21_SSI_SDATA2(7) |
+	      DRVCTRL21_SSI_SCK34(7) |
+	      DRVCTRL21_SSI_WS34(7) |
+	      DRVCTRL21_SSI_SDATA3(7) |
+	      DRVCTRL21_SSI_SCK4(7);
+	pfc_reg_write(PFC_DRVCTRL21, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL22);
+	reg = (reg & DRVCTRL22_MASK) |
+	      DRVCTRL22_SSI_WS4(7) |
+	      DRVCTRL22_SSI_SDATA4(7) |
+	      DRVCTRL22_SSI_SCK5(7) |
+	      DRVCTRL22_SSI_WS5(7) |
+	      DRVCTRL22_SSI_SDATA5(7) |
+	      DRVCTRL22_SSI_SCK6(7) |
+	      DRVCTRL22_SSI_WS6(7) |
+	      DRVCTRL22_SSI_SDATA6(7);
+	pfc_reg_write(PFC_DRVCTRL22, reg);
+
+	reg = mmio_read_32(PFC_DRVCTRL23);
+	reg = (reg & DRVCTRL23_MASK) |
+	      DRVCTRL23_SSI_SCK78(7) |
+	      DRVCTRL23_SSI_WS78(7) |
+	      DRVCTRL23_SSI_SDATA7(7) |
+	      DRVCTRL23_SSI_SDATA8(7) |
+	      DRVCTRL23_SSI_SDATA9(7) |
+	      DRVCTRL23_AUDIO_CLKA(7) |
+	      DRVCTRL23_AUDIO_CLKB(7) |
+	      DRVCTRL23_USB0_PWEN(7);
+
+	pfc_reg_write(PFC_DRVCTRL23, reg);
+	reg = mmio_read_32(PFC_DRVCTRL24);
+	reg = (reg & DRVCTRL24_MASK) |
+	      DRVCTRL24_USB0_OVC(7) |
+	      DRVCTRL24_USB1_PWEN(7) |
+	      DRVCTRL24_USB1_OVC(7) |
+	      DRVCTRL24_USB30_PWEN(7) |
+	      DRVCTRL24_USB30_OVC(7) |
+	      DRVCTRL24_USB31_PWEN(7) |
+	      DRVCTRL24_USB31_OVC(7);
+	pfc_reg_write(PFC_DRVCTRL24, reg);
+
+	/* initialize LSI pin pull-up/down control */
+	pfc_reg_write(PFC_PUD0, 0x00005FBFU);
+	pfc_reg_write(PFC_PUD1, 0x00300EFEU);
+	pfc_reg_write(PFC_PUD2, 0x330001E6U);
+	pfc_reg_write(PFC_PUD3, 0x000002E0U);
+	pfc_reg_write(PFC_PUD4, 0xFFFFFF00U);
+	pfc_reg_write(PFC_PUD5, 0x7F5FFF87U);
+	pfc_reg_write(PFC_PUD6, 0x00000055U);
+
+	/* initialize LSI pin pull-enable register */
+	pfc_reg_write(PFC_PUEN0, 0x00000FFFU);
+	pfc_reg_write(PFC_PUEN1, 0x00100234U);
+	pfc_reg_write(PFC_PUEN2, 0x000004C4U);
+	pfc_reg_write(PFC_PUEN3, 0x00000200U);
+	pfc_reg_write(PFC_PUEN4, 0x3E000000U);
+	pfc_reg_write(PFC_PUEN5, 0x1F000805U);
+	pfc_reg_write(PFC_PUEN6, 0x00000006U);
+
+	/* initialize positive/negative logic select */
+	mmio_write_32(GPIO_POSNEG0, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG1, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG2, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG3, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG4, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG5, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG6, 0x00000000U);
+	mmio_write_32(GPIO_POSNEG7, 0x00000000U);
+
+	/* initialize general IO/interrupt switching */
+	mmio_write_32(GPIO_IOINTSEL0, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL1, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL2, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL3, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL4, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL5, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL6, 0x00000000U);
+	mmio_write_32(GPIO_IOINTSEL7, 0x00000000U);
+
+	/* initialize general output register */
+	mmio_write_32(GPIO_OUTDT0, 0x00000001U);
+	mmio_write_32(GPIO_OUTDT1, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT2, 0x00000400U);
+	mmio_write_32(GPIO_OUTDT3, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT4, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT5, 0x00000000U);
+	mmio_write_32(GPIO_OUTDT6, 0x00003800U);
+	mmio_write_32(GPIO_OUTDT7, 0x00000003U);
+
+	/* initialize general input/output switching */
+	mmio_write_32(GPIO_INOUTSEL0, 0x00000001U);
+	mmio_write_32(GPIO_INOUTSEL1, 0x00100B00U);
+	mmio_write_32(GPIO_INOUTSEL2, 0x00000418U);
+	mmio_write_32(GPIO_INOUTSEL3, 0x00002000U);
+	mmio_write_32(GPIO_INOUTSEL4, 0x00000040U);
+	mmio_write_32(GPIO_INOUTSEL5, 0x00000208U);
+	mmio_write_32(GPIO_INOUTSEL6, 0x00013F00U);
+	mmio_write_32(GPIO_INOUTSEL7, 0x00000003U);
+}
diff --git a/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.h b/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.h
new file mode 100644
index 0000000..f0616b6
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PFC_INIT_G2N_H
+#define PFC_INIT_G2N_H
+
+void pfc_init_g2n(void);
+
+#endif /* PFC_INIT_G2N_H */
diff --git a/drivers/renesas/rzg/pfc/pfc.mk b/drivers/renesas/rzg/pfc/pfc.mk
new file mode 100644
index 0000000..15d0e8d
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/pfc.mk
@@ -0,0 +1,41 @@
+#
+# Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${RCAR_LSI},${RCAR_AUTO})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c
+
+else ifdef RCAR_LSI_CUT_COMPAT
+  ifeq (${RCAR_LSI},${RZ_G2M})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2H})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2N})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2E})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c
+  endif
+else
+  ifeq (${RCAR_LSI},${RZ_G2M})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2M/pfc_init_g2m.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2H})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2H/pfc_init_g2h.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2N})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2N/pfc_init_g2n.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2E})
+    BL2_SOURCES += drivers/renesas/rzg/pfc/G2E/pfc_init_g2e.c
+  endif
+endif
+
+BL2_SOURCES += drivers/renesas/rzg/pfc/pfc_init.c
diff --git a/drivers/renesas/rzg/pfc/pfc_init.c b/drivers/renesas/rzg/pfc/pfc_init.c
new file mode 100644
index 0000000..762450c
--- /dev/null
+++ b/drivers/renesas/rzg/pfc/pfc_init.c
@@ -0,0 +1,129 @@
+/*
+ * Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#if RCAR_LSI == RCAR_AUTO
+#include "G2E/pfc_init_g2e.h"
+#include "G2H/pfc_init_g2h.h"
+#include "G2M/pfc_init_g2m.h"
+#include "G2N/pfc_init_g2n.h"
+#endif /* RCAR_LSI == RCAR_AUTO */
+#if (RCAR_LSI == RZ_G2E)
+#include "G2E/pfc_init_g2e.h"
+#endif /* RCAR_LSI == RZ_G2N */
+#if (RCAR_LSI == RZ_G2H)
+#include "G2H/pfc_init_g2h.h"
+#endif /* RCAR_LSI == RZ_G2H */
+#if (RCAR_LSI == RZ_G2M)
+#include "G2M/pfc_init_g2m.h"
+#endif /* RCAR_LSI == RZ_G2M */
+#if (RCAR_LSI == RZ_G2N)
+#include "G2N/pfc_init_g2n.h"
+#endif /* RCAR_LSI == RZ_G2N */
+#include "rcar_def.h"
+
+#define PRR_PRODUCT_ERR(reg)				\
+	do {						\
+		ERROR("LSI Product ID(PRR=0x%x) PFC init not supported.\n", \
+			reg);				\
+		panic();				\
+	} while (0)
+
+#define PRR_CUT_ERR(reg)				\
+	do {						\
+		ERROR("LSI Cut ID(PRR=0x%x) PFC init not supported.\n", \
+			reg);				\
+		panic();\
+	} while (0)
+
+void rzg_pfc_init(void)
+{
+	uint32_t reg;
+
+	reg = mmio_read_32(RCAR_PRR);
+#if RCAR_LSI == RCAR_AUTO
+	switch (reg & PRR_PRODUCT_MASK) {
+	case PRR_PRODUCT_M3:
+		pfc_init_g2m();
+		break;
+	case PRR_PRODUCT_H3:
+		pfc_init_g2h();
+		break;
+	case PRR_PRODUCT_M3N:
+		pfc_init_g2n();
+		break;
+	case PRR_PRODUCT_E3:
+		pfc_init_g2e();
+		break;
+	default:
+		PRR_PRODUCT_ERR(reg);
+		break;
+	}
+
+#elif RCAR_LSI_CUT_COMPAT /* RCAR_LSI == RCAR_AUTO */
+	switch (reg & PRR_PRODUCT_MASK) {
+	case PRR_PRODUCT_M3:
+#if RCAR_LSI != RZ_G2M
+		PRR_PRODUCT_ERR(reg);
+#else /* RCAR_LSI != RZ_G2M */
+		pfc_init_g2m();
+#endif /* RCAR_LSI != RZ_G2M */
+		break;
+	case PRR_PRODUCT_H3:
+#if (RCAR_LSI != RZ_G2H)
+		PRR_PRODUCT_ERR(reg);
+#else /* RCAR_LSI != RZ_G2H */
+		pfc_init_g2h();
+#endif /* RCAR_LSI != RZ_G2H */
+		break;
+	case PRR_PRODUCT_M3N:
+#if RCAR_LSI != RZ_G2N
+		PRR_PRODUCT_ERR(reg);
+#else
+		pfc_init_g2n();
+#endif /* RCAR_LSI != RZ_G2N */
+		break;
+	case PRR_PRODUCT_E3:
+#if RCAR_LSI != RZ_G2E
+		PRR_PRODUCT_ERR(reg);
+#else
+		pfc_init_g2e();
+#endif
+		break;
+	default:
+		PRR_PRODUCT_ERR(reg);
+		break;
+	}
+
+#else /* RCAR_LSI == RCAR_AUTO */
+#if (RCAR_LSI == RZ_G2M)
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_M3) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	pfc_init_m3();
+#elif (RCAR_LSI == RZ_G2H)
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_H3) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	pfc_init_g2h();
+#elif (RCAR_LSI == RZ_G2N)	/* G2N */
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_M3N) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	pfc_init_g2n();
+#elif (RCAR_LSI == RZ_G2E)
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_E3) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	pfc_init_g2e();
+#else /* RCAR_LSI == RZ_G2M */
+#error "Don't have PFC initialize routine(unknown)."
+#endif /* RCAR_LSI == RZ_G2M */
+#endif /* RCAR_LSI == RCAR_AUTO */
+}
diff --git a/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c
new file mode 100644
index 0000000..14ccc21
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c
@@ -0,0 +1,140 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "qos_init_g2e_v10.h"
+#include "../qos_common.h"
+#include "../qos_reg.h"
+
+#define RCAR_QOS_VERSION	"rev.0.05"
+
+#define REF_ARS_ARBSTOPCYCLE_G2E	(((SL_INIT_SSLOTCLK_G2E) - 5U) << 16U)
+
+#if RCAR_QOS_TYPE == RCAR_QOS_TYPE_DEFAULT
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2e_v10_mstat390.h"
+#else
+#include "qos_init_g2e_v10_mstat780.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#endif /* RCAR_QOS_TYPE == RCAR_QOS_TYPE_DEFAULT */
+
+static const struct rcar_gen3_dbsc_qos_settings g2e_qos[] = {
+	/* BUFCAM settings */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBSCHCNT0, 0x000F0037U },
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS Settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000100U },
+	{ DBSC_DBSCHQOS91, 0x000000F0U },
+	{ DBSC_DBSCHQOS92, 0x000000A0U },
+	{ DBSC_DBSCHQOS93, 0x00000040U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2e_v10(void)
+{
+	rzg_qos_dbsc_setting(g2e_qos, ARRAY_SIZE(g2e_qos), true);
+
+	/* DRAM Split Address mapping */
+#if RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH
+#if RCAR_LSI == RCAR_RZ_G2E
+#error "Don't set DRAM Split 4ch(G2E)"
+#else
+	ERROR("DRAM Split 4ch not supported.(G2E)");
+	panic();
+#endif
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH)
+#if RCAR_LSI == RCAR_RZ_G2E
+#error "Don't set DRAM Split 2ch(G2E)"
+#else
+	ERROR("DRAM Split 2ch not supported.(G2E)");
+	panic();
+#endif
+#else
+	NOTICE("BL2: DRAM Split is OFF\n");
+#endif
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+	NOTICE("BL2: DRAM refresh interval 3.9 usec\n");
+#else
+	NOTICE("BL2: DRAM refresh interval 7.8 usec\n");
+#endif
+
+	mmio_write_32(QOSCTRL_RAS, 0x00000020U);
+	mmio_write_64(QOSCTRL_DANN, 0x0404020002020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x00100804U);
+	mmio_write_32(QOSCTRL_FSS, 0x0000000AU);
+	mmio_write_32(QOSCTRL_INSFC, 0x06330001U);
+	mmio_write_32(QOSCTRL_EARLYR, 0x00000000U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x00010003U);
+
+	mmio_write_32(QOSCTRL_SL_INIT, SL_INIT_REFFSSLOT |
+		      SL_INIT_SLOTSSLOT | SL_INIT_SSLOTCLK_G2E);
+	mmio_write_32(QOSCTRL_REF_ARS, REF_ARS_ARBSTOPCYCLE_G2E);
+
+	/* QOSBW SRAM setting */
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+
+	/* RT bus Leaf setting */
+	mmio_write_32(RT_ACT0, 0x00000000U);
+	mmio_write_32(RT_ACT1, 0x00000000U);
+
+	/* CCI bus Leaf setting */
+	mmio_write_32(CPU_ACT0, 0x00000003U);
+	mmio_write_32(CPU_ACT1, 0x00000003U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else
+	NOTICE("BL2: QoS is None\n");
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif
+}
diff --git a/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.h b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.h
new file mode 100644
index 0000000..d27de1b
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2E_V10_H
+#define QOS_INIT_G2E_V10_H
+
+void qos_init_g2e_v10(void);
+
+#endif /* QOS_INIT_G2E_V10_H */
diff --git a/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat390.h b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat390.h
new file mode 100644
index 0000000..63b08c4
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat390.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2E_V10_MSTAT390_H
+#define QOS_INIT_G2E_V10_MSTAT390_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008620000FFFFUL,
+	/* 0x0038, */ 0x001008620000FFFFUL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x001415260000FFFFUL,
+	/* 0x0060, */ 0x001415260000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414930000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C08380000FFFFUL,
+	/* 0x00a8, */ 0x000C04110000FFFFUL,
+	/* 0x00b0, */ 0x000C04150000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C08380000FFFFUL,
+	/* 0x00c8, */ 0x000C04110000FFFFUL,
+	/* 0x00d0, */ 0x000C04150000FFFFUL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x000C084F0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x000C21E40000FFFFUL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x001008530000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00100C960000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x001008530000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0010042A0000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x00101D8D0000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x001008530000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x001410040000FFFFUL,
+	/* 0x0270, */ 0x001404020000FFFFUL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410040000FFFFUL,
+	/* 0x0298, */ 0x001404020000FFFFUL,
+	/* 0x02a0, */ 0x000C04090000FFFFUL,
+	/* 0x02a8, */ 0x000C04090000FFFFUL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04090000FFFFUL,
+	/* 0x02d8, */ 0x000C04090000FFFFUL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x000C04020000FFFFUL,
+	/* 0x0378, */ 0x000C04020000FFFFUL,
+	/* 0x0380, */ 0x000C04090000FFFFUL,
+	/* 0x0388, */ 0x000C04090000FFFFUL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001005F03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0021060005FFFC01UL,
+	/* 0x01c8, */ 0x0021060005FFFC01UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0011010005F79801UL,
+	/* 0x0220, */ 0x0011010005F79801UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011010005F79801UL,
+	/* 0x0238, */ 0x0011010005F79801UL,
+	/* 0x0240, */ 0x0012010005F79801UL,
+	/* 0x0248, */ 0x0011010005F79801UL,
+	/* 0x0250, */ 0x0012010005F79801UL,
+	/* 0x0258, */ 0x0011010005F79801UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011060005FFFC01UL,
+	/* 0x02f8, */ 0x0011060005FFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0012001005F03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0012060005FFFC01UL,
+	/* 0x0360, */ 0x0012060005FFFC01UL,
+	/* 0x0368, */ 0x0012001005F03401UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0012001005F03401UL,
+};
+#endif /* QOS_INIT_G2E_V10_MSTAT390_H */
diff --git a/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat780.h b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat780.h
new file mode 100644
index 0000000..3b888ea
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10_mstat780.h
@@ -0,0 +1,246 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2E_V10_MSTAT780_H
+#define QOS_INIT_G2E_V10_MSTAT780_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001010C40000FFFFUL,
+	/* 0x0038, */ 0x001010C40000FFFFUL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x00142A4B0000FFFFUL,
+	/* 0x0060, */ 0x00142A4B0000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001429260000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C10700000FFFFUL,
+	/* 0x00a8, */ 0x000C08210000FFFFUL,
+	/* 0x00b0, */ 0x000C082A0000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C10700000FFFFUL,
+	/* 0x00c8, */ 0x000C08210000FFFFUL,
+	/* 0x00d0, */ 0x000C082A0000FFFFUL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x00102CAF0000FFFFUL,
+	/* 0x00f8, */ 0x000C0C9D0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x00100CAF0000FFFFUL,
+	/* 0x0118, */ 0x000C43C80000FFFFUL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100CA50000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0010152C0000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x00100CA50000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008530000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001037190000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x00100CA50000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04040000FFFFUL,
+	/* 0x01f0, */ 0x000C08110000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04110000FFFFUL,
+	/* 0x0210, */ 0x000C08110000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C18530000FFFFUL,
+	/* 0x0268, */ 0x00141C070000FFFFUL,
+	/* 0x0270, */ 0x001404040000FFFFUL,
+	/* 0x0278, */ 0x000C0C210000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x00141C070000FFFFUL,
+	/* 0x0298, */ 0x001404040000FFFFUL,
+	/* 0x02a0, */ 0x000C04110000FFFFUL,
+	/* 0x02a8, */ 0x000C04110000FFFFUL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x000C04040000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04110000FFFFUL,
+	/* 0x02d8, */ 0x000C04110000FFFFUL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x000C04040000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x000C04040000FFFFUL,
+	/* 0x0378, */ 0x000C04040000FFFFUL,
+	/* 0x0380, */ 0x000C04110000FFFFUL,
+	/* 0x0388, */ 0x000C04110000FFFFUL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001002F03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0021060002FFFC01UL,
+	/* 0x01c8, */ 0x0021060002FFFC01UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0021010002F3CC01UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0021010002F3CC01UL,
+	/* 0x0218, */ 0x0011010002F3CC01UL,
+	/* 0x0220, */ 0x0011010002F3CC01UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011010002F3CC01UL,
+	/* 0x0238, */ 0x0011010002F3CC01UL,
+	/* 0x0240, */ 0x0012010002F3CC01UL,
+	/* 0x0248, */ 0x0011010002F3CC01UL,
+	/* 0x0250, */ 0x0012010002F3CC01UL,
+	/* 0x0258, */ 0x0011010002F3CC01UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011060002FFFC01UL,
+	/* 0x02f8, */ 0x0011060002FFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0012001002F03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0012060002FFFC01UL,
+	/* 0x0360, */ 0x0012060002FFFC01UL,
+	/* 0x0368, */ 0x0012001002F03401UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0012001002F03401UL,
+};
+
+#endif /* QOS_INIT_G2E_V10_MSTAT780_H */
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat195.h b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat195.h
new file mode 100644
index 0000000..7bb34aa
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat195.h
@@ -0,0 +1,236 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2H_MSTAT195_H
+#define QOS_INIT_G2H_MSTAT195_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000FFFFUL,
+	/* 0x0038, */ 0x001008070000FFFFUL,
+	/* 0x0040, */ 0x001410070000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404010000FFFFUL,
+	/* 0x0058, */ 0x0014100D0000FFFFUL,
+	/* 0x0060, */ 0x0014100D0000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404010000FFFFUL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001410070000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C04020000FFFFUL,
+	/* 0x00a8, */ 0x000C04010000FFFFUL,
+	/* 0x00b0, */ 0x000C04010000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C04020000FFFFUL,
+	/* 0x00c8, */ 0x000C04010000FFFFUL,
+	/* 0x00d0, */ 0x000C04010000FFFFUL,
+	/* 0x00d8, */ 0x001024090000FFFFUL,
+	/* 0x00e0, */ 0x00100C090000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001024090000FFFFUL,
+	/* 0x00f8, */ 0x000C100D0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x00100C090000FFFFUL,
+	/* 0x0118, */ 0x000C1C1B0000FFFFUL,
+	/* 0x0120, */ 0x000C1C1B0000FFFFUL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100C0B0000FFFFUL,
+	/* 0x0140, */ 0x00100C0B0000FFFFUL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0010100D0000FFFFUL,
+	/* 0x0158, */ 0x0010100D0000FFFFUL,
+	/* 0x0160, */ 0x00100C0B0000FFFFUL,
+	/* 0x0168, */ 0x00100C0B0000FFFFUL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008060000FFFFUL,
+	/* 0x0180, */ 0x001008060000FFFFUL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x00102C2C0000FFFFUL,
+	/* 0x0198, */ 0x00102C2C0000FFFFUL,
+	/* 0x01a0, */ 0x00100C0B0000FFFFUL,
+	/* 0x01a8, */ 0x00100C0B0000FFFFUL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04010000FFFFUL,
+	/* 0x01f0, */ 0x000C04010000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04010000FFFFUL,
+	/* 0x0210, */ 0x000C04010000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08020000FFFFUL,
+	/* 0x0268, */ 0x001408010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x000C04010000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x001408010000FFFFUL,
+	/* 0x02b8, */ 0x000C04010000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x001408010000FFFFUL,
+	/* 0x02e8, */ 0x000C04010000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x001200600BDFFC01UL,
+	/* 0x0008, */ 0x001200600BDFFC01UL,
+	/* 0x0010, */ 0x001200600BDFFC01UL,
+	/* 0x0018, */ 0x001200600BDFFC01UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x001200100BD0FC01UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002100600BDFFC01UL,
+	/* 0x01c8, */ 0x002100600BDFFC01UL,
+	/* 0x01d0, */ 0x002100600BDFFC01UL,
+	/* 0x01d8, */ 0x002100600BDFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x002100100BDF2401UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x002100100BDF2401UL,
+	/* 0x0218, */ 0x001100100BDF2401UL,
+	/* 0x0220, */ 0x001100100BDF2401UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x001100100BDF2401UL,
+	/* 0x0238, */ 0x001100100BDF2401UL,
+	/* 0x0240, */ 0x001200100BDF2401UL,
+	/* 0x0248, */ 0x001100100BDF2401UL,
+	/* 0x0250, */ 0x001200100BDF2401UL,
+	/* 0x0258, */ 0x001100100BDF2401UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x001100600BDFFC01UL,
+	/* 0x02f8, */ 0x001100600BDFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x001100600BDFFC01UL,
+	/* 0x0310, */ 0x001100600BDFFC01UL,
+	/* 0x0318, */ 0x001200100BD03401UL,
+	/* 0x0320, */ 0x001100600BDFFC01UL,
+	/* 0x0328, */ 0x001100600BDFFC01UL,
+	/* 0x0330, */ 0x001100600BDFFC01UL,
+	/* 0x0338, */ 0x001100600BDFFC01UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x001200100BD0FC01UL,
+};
+
+#endif /* QOS_INIT_G2H_MSTAT195_H */
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat390.h b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat390.h
new file mode 100644
index 0000000..9696a40
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_mstat390.h
@@ -0,0 +1,236 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2H_MSTAT390_H
+#define QOS_INIT_G2H_MSTAT390_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000FFFFUL,
+	/* 0x0038, */ 0x0010100D0000FFFFUL,
+	/* 0x0040, */ 0x00141C0E0000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001408010000FFFFUL,
+	/* 0x0058, */ 0x00141C190000FFFFUL,
+	/* 0x0060, */ 0x00141C190000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001408010000FFFFUL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x00141C0E0000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C08040000FFFFUL,
+	/* 0x00a8, */ 0x000C04020000FFFFUL,
+	/* 0x00b0, */ 0x000C04020000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C08040000FFFFUL,
+	/* 0x00c8, */ 0x000C04020000FFFFUL,
+	/* 0x00d0, */ 0x000C04020000FFFFUL,
+	/* 0x00d8, */ 0x001044110000FFFFUL,
+	/* 0x00e0, */ 0x001014110000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001044110000FFFFUL,
+	/* 0x00f8, */ 0x000C1C1A0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x001014110000FFFFUL,
+	/* 0x0118, */ 0x000C38360000FFFFUL,
+	/* 0x0120, */ 0x000C38360000FFFFUL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x001018150000FFFFUL,
+	/* 0x0140, */ 0x001018150000FFFFUL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00101C190000FFFFUL,
+	/* 0x0158, */ 0x00101C190000FFFFUL,
+	/* 0x0160, */ 0x001018150000FFFFUL,
+	/* 0x0168, */ 0x001018150000FFFFUL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x00100C0B0000FFFFUL,
+	/* 0x0180, */ 0x00100C0B0000FFFFUL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001058570000FFFFUL,
+	/* 0x0198, */ 0x001058570000FFFFUL,
+	/* 0x01a0, */ 0x001018150000FFFFUL,
+	/* 0x01a8, */ 0x001018150000FFFFUL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04010000FFFFUL,
+	/* 0x01f0, */ 0x000C04010000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04010000FFFFUL,
+	/* 0x0210, */ 0x000C04010000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFFFUL,
+	/* 0x0268, */ 0x001410010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x000C08020000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x00140C010000FFFFUL,
+	/* 0x02b8, */ 0x000C04010000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x00140C010000FFFFUL,
+	/* 0x02e8, */ 0x000C04010000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0012006005EFFC01UL,
+	/* 0x0008, */ 0x0012006005EFFC01UL,
+	/* 0x0010, */ 0x0012006005EFFC01UL,
+	/* 0x0018, */ 0x0012006005EFFC01UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001005E0FC01UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0021006005EFFC01UL,
+	/* 0x01c8, */ 0x0021006005EFFC01UL,
+	/* 0x01d0, */ 0x0021006005EFFC01UL,
+	/* 0x01d8, */ 0x0021006005EFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0021001005E79401UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0021001005E79401UL,
+	/* 0x0218, */ 0x0011001005E79401UL,
+	/* 0x0220, */ 0x0011001005E79401UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011001005E79401UL,
+	/* 0x0238, */ 0x0011001005E79401UL,
+	/* 0x0240, */ 0x0012001005E79401UL,
+	/* 0x0248, */ 0x0011001005E79401UL,
+	/* 0x0250, */ 0x0012001005E79401UL,
+	/* 0x0258, */ 0x0011001005E79401UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011006005EFFC01UL,
+	/* 0x02f8, */ 0x0011006005EFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0011006005EFFC01UL,
+	/* 0x0310, */ 0x0011006005EFFC01UL,
+	/* 0x0318, */ 0x0012001005E03401UL,
+	/* 0x0320, */ 0x0011006005EFFC01UL,
+	/* 0x0328, */ 0x0011006005EFFC01UL,
+	/* 0x0330, */ 0x0011006005EFFC01UL,
+	/* 0x0338, */ 0x0011006005EFFC01UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0012001005E0FC01UL,
+};
+
+#endif /* QOS_INIT_G2H_MSTAT390_H */
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt195.h b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt195.h
new file mode 100644
index 0000000..044f246
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt195.h
@@ -0,0 +1,236 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2H_QOSWT195_H
+#define QOS_INIT_G2H_QOSWT195_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000C010UL,
+	/* 0x0038, */ 0x001008070000C010UL,
+	/* 0x0040, */ 0x001410070000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0014100D0000C010UL,
+	/* 0x0060, */ 0x0014100D0000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001410070000FFF0UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08020000FFF0UL,
+	/* 0x0268, */ 0x001408010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C04010000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2H_QOSWT195_H */
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt390.h b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt390.h
new file mode 100644
index 0000000..2ae07ab
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_qoswt390.h
@@ -0,0 +1,236 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2H_QOSWT390_H
+#define QOS_INIT_G2H_QOSWT390_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000C010UL,
+	/* 0x0038, */ 0x0010100D0000C010UL,
+	/* 0x0040, */ 0x00141C0E0000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x00141C190000C010UL,
+	/* 0x0060, */ 0x00141C190000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x00141C0E0000FFF0UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFF0UL,
+	/* 0x0268, */ 0x001410010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C08020000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2H_QOSWT390_H */
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c
new file mode 100644
index 0000000..7f466c8
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c
@@ -0,0 +1,217 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "qos_init_g2h_v30.h"
+#include "../qos_common.h"
+#include "../qos_reg.h"
+
+#define RCAR_QOS_VERSION			"rev.0.07"
+
+#define QOSWT_TIME_BANK0			20000000U	/* unit:ns */
+#define QOSWT_WTEN_ENABLE			0x1U
+
+#define QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2H	(SL_INIT_SSLOTCLK_G2H - 0x5U)
+
+#define OSWT_WTREF_SLOT0_EN_REQ1_SLOT		3U
+#define OSWT_WTREF_SLOT0_EN_REQ2_SLOT		9U
+#define QOSWT_WTREF_SLOT0_EN			((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) | \
+						(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+#define QOSWT_WTREF_SLOT1_EN			((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) | \
+						(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+
+#define QOSWT_WTSET0_REQ_SSLOT0			5U
+#define WT_BASE_SUB_SLOT_NUM0			12U
+#define QOSWT_WTSET0_PERIOD0_G2H		((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2H) - 1U)
+#define QOSWT_WTSET0_SSLOT0			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET0_SLOTSLOT0			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+#define QOSWT_WTSET1_PERIOD1_G2H		(QOSWT_WTSET0_PERIOD0_G2H)
+#define QOSWT_WTSET1_SSLOT1			(QOSWT_WTSET0_SSLOT0)
+#define QOSWT_WTSET1_SLOTSLOT1			(QOSWT_WTSET0_SLOTSLOT0)
+
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2h_mstat195.h"
+#else
+#include "qos_init_g2h_mstat390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2h_qoswt195.h"
+#else
+#include "qos_init_g2h_qoswt390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+#endif /* RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT */
+
+static const struct rcar_gen3_dbsc_qos_settings g2h_v30_qos[] = {
+	/* BUFCAM settings */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBCAM0CNF3, 0x00000000U },
+	{ DBSC_DBSCHCNT0, 0x000F0037U },
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS Settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000100U },
+	{ DBSC_DBSCHQOS91, 0x000000F0U },
+	{ DBSC_DBSCHQOS92, 0x000000A0U },
+	{ DBSC_DBSCHQOS93, 0x00000040U },
+	{ DBSC_DBSCHQOS120, 0x00000040U },
+	{ DBSC_DBSCHQOS121, 0x00000030U },
+	{ DBSC_DBSCHQOS122, 0x00000020U },
+	{ DBSC_DBSCHQOS123, 0x00000010U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2h_v30(void)
+{
+	unsigned int split_area;
+
+	rzg_qos_dbsc_setting(g2h_v30_qos, ARRAY_SIZE(g2h_v30_qos), true);
+
+	/* use 1(2GB) for RCAR_DRAM_LPDDR4_MEMCONF for G2H */
+	split_area = 0x1CU;
+
+	/* DRAM split address mapping */
+#if (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH)
+#if RCAR_LSI == RZ_G2H
+#error "Don't set DRAM Split 4ch(G2H)"
+#else /* RCAR_LSI == RZ_G2H */
+	ERROR("DRAM split 4ch not supported.(G2H)");
+	panic();
+#endif /* RCAR_LSI == RZ_G2H */
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH) || \
+	(RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_AUTO)
+	NOTICE("BL2: DRAM Split is 2ch(DDR %x)\n", (int)qos_init_ddr_phyvalid);
+
+	mmio_write_32(AXI_ADSPLCR0, ADSPLCR0_AREA(split_area));
+	mmio_write_32(AXI_ADSPLCR1, ADSPLCR0_ADRMODE_DEFAULT |
+		    ADSPLCR0_SPLITSEL(0xFFU) | ADSPLCR0_AREA(split_area) |
+		    ADSPLCR0_SWP);
+	mmio_write_32(AXI_ADSPLCR2, 0x00001004U);
+	mmio_write_32(AXI_ADSPLCR3, 0x00000000U);
+#else /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+	mmio_write_32(AXI_ADSPLCR0, ADSPLCR0_AREA(split_area));
+	NOTICE("BL2: DRAM Split is OFF(DDR %x)\n", (int)qos_init_ddr_phyvalid);
+#endif /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+	NOTICE("BL2: DRAM refresh interval 1.95 usec\n");
+#else
+	NOTICE("BL2: DRAM refresh interval 3.9 usec\n");
+#endif
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	NOTICE("BL2: Periodic Write DQ Training\n");
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_RAS, 0x00000044U);
+	mmio_write_64(QOSCTRL_DANN, 0x0404020002020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x0020100AU);
+	mmio_write_32(QOSCTRL_FSS, 0x0000000AU);
+	mmio_write_32(QOSCTRL_INSFC, 0x06330001U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x00010003U);
+
+	/* GPU Boost Mode */
+	mmio_write_32(QOSCTRL_STATGEN0, 0x00000001U);
+
+	mmio_write_32(QOSCTRL_SL_INIT, SL_INIT_REFFSSLOT |
+		      SL_INIT_SLOTSSLOT | SL_INIT_SSLOTCLK_G2H);
+	mmio_write_32(QOSCTRL_REF_ARS, ((QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2H << 16)));
+
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	for (i = 0U; i < ARRAY_SIZE(qoswt_fix); i++) {
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK0 + i * 8U, qoswt_fix[i]);
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK1 + i * 8U, qoswt_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(qoswt_be); i++) {
+		mmio_write_64(QOSWT_BE_WTQOS_BANK0 + i * 8U, qoswt_be[i]);
+		mmio_write_64(QOSWT_BE_WTQOS_BANK1 + i * 8U, qoswt_be[i]);
+	}
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	/* AXI setting */
+	mmio_write_32(AXI_MMCR, 0x00010008U);
+	mmio_write_32(AXI_TR3CR, 0x00010000U);
+	mmio_write_32(AXI_TR4CR, 0x00010000U);
+
+	/* RT bus Leaf setting */
+	mmio_write_32(RT_ACT0, 0x00000000U);
+	mmio_write_32(RT_ACT1, 0x00000000U);
+
+	/* CCI bus Leaf setting */
+	mmio_write_32(CPU_ACT0, 0x00000003U);
+	mmio_write_32(CPU_ACT1, 0x00000003U);
+	mmio_write_32(CPU_ACT2, 0x00000003U);
+	mmio_write_32(CPU_ACT3, 0x00000003U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	/*  re-write training setting */
+	mmio_write_32(QOSWT_WTREF,
+		      ((QOSWT_WTREF_SLOT1_EN << 16) | QOSWT_WTREF_SLOT0_EN));
+	mmio_write_32(QOSWT_WTSET0,
+		      ((QOSWT_WTSET0_PERIOD0_G2H << 16) |
+		      (QOSWT_WTSET0_SSLOT0 << 8) | QOSWT_WTSET0_SLOTSLOT0));
+	mmio_write_32(QOSWT_WTSET1,
+		      ((QOSWT_WTSET1_PERIOD1_G2H << 16) |
+		      (QOSWT_WTSET1_SSLOT1 << 8) | QOSWT_WTSET1_SLOTSLOT1));
+
+	mmio_write_32(QOSWT_WTEN, QOSWT_WTEN_ENABLE);
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else
+	NOTICE("BL2: QoS is None\n");
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+}
diff --git a/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.h b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.h
new file mode 100644
index 0000000..acd9627
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2H_V30_H
+#define QOS_INIT_G2H_V30_H
+
+void qos_init_g2h_v30(void);
+
+#endif /* QOS_INIT_G2H_V30_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c
new file mode 100644
index 0000000..ceaad25
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "../qos_common.h"
+#include "qos_init_g2m_v10.h"
+#include "qos_init_g2m_v10_mstat.h"
+#include "qos_reg.h"
+
+#define RCAR_QOS_VERSION	"rev.0.19"
+
+static const struct rcar_gen3_dbsc_qos_settings g2m_v10_qos[] = {
+	/* BUFCAM settings */
+	/* DBSC_DBCAM0CNF0 not set */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBCAM0CNF3, 0x00000000U },
+	{ DBSC_DBSCHCNT0, 0x080F0037U },
+	/* DBSC_DBSCHCNT1 not set */
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS Settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000300U },
+	{ DBSC_DBSCHQOS91, 0x000002F0U },
+	{ DBSC_DBSCHQOS92, 0x00000200U },
+	{ DBSC_DBSCHQOS93, 0x00000100U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2m_v10(void)
+{
+	rzg_qos_dbsc_setting(g2m_v10_qos, ARRAY_SIZE(g2m_v10_qos), false);
+
+	/* DRAM split address mapping */
+#if RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH
+#if RCAR_LSI == RZ_G2M
+#error "Don't set DRAM Split 4ch(G2M)"
+#else /* RCAR_LSI == RZ_G2M */
+	ERROR("DRAM Split 4ch not supported.(G2M)");
+	panic();
+#endif /* RCAR_LSI == RZ_G2M */
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH) || \
+	(RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_AUTO)
+	NOTICE("BL2: DRAM Split is 2ch\n");
+	mmio_write_32(AXI_ADSPLCR0, 0x00000000U);
+	mmio_write_32(AXI_ADSPLCR1, ADSPLCR0_ADRMODE_DEFAULT |
+		      ADSPLCR0_SPLITSEL(0xFFU) | ADSPLCR0_AREA(0x1CU) |
+		      ADSPLCR0_SWP);
+	mmio_write_32(AXI_ADSPLCR2, 0x089A0000U);
+	mmio_write_32(AXI_ADSPLCR3, 0x00000000U);
+#else /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+	NOTICE("BL2: DRAM Split is OFF\n");
+#endif /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif
+
+	/* Resource Alloc setting */
+	mmio_write_32(QOSCTRL_RAS, 0x00000028U);
+	mmio_write_32(QOSCTRL_FIXTH, 0x000F0005U);
+	mmio_write_32(QOSCTRL_REGGD, 0x00000000U);
+	mmio_write_64(QOSCTRL_DANN, 0x0101010102020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x00100804U);
+	mmio_write_32(QOSCTRL_EC, 0x00000000U);
+	mmio_write_64(QOSCTRL_EMS, 0x0000000000000000UL);
+	mmio_write_32(QOSCTRL_FSS, 0x000003e8U);
+	mmio_write_32(QOSCTRL_INSFC, 0xC7840001U);
+	mmio_write_32(QOSCTRL_BERR, 0x00000000U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x00000000U);
+
+	/* QOSBW setting */
+	mmio_write_32(QOSCTRL_SL_INIT, SL_INIT_REFFSSLOT | SL_INIT_SLOTSSLOT |
+		      SL_INIT_SSLOTCLK);
+	mmio_write_32(QOSCTRL_REF_ARS, 0x00330000U);
+
+	/* QOSBW SRAM setting */
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+
+	/* 3DG bus Leaf setting */
+	mmio_write_32(0xFD820808U, 0x00001234U);
+	mmio_write_32(0xFD820800U, 0x00000006U);
+	mmio_write_32(0xFD821800U, 0x00000006U);
+	mmio_write_32(0xFD822800U, 0x00000006U);
+	mmio_write_32(0xFD823800U, 0x00000006U);
+	mmio_write_32(0xFD824800U, 0x00000006U);
+	mmio_write_32(0xFD825800U, 0x00000006U);
+	mmio_write_32(0xFD826800U, 0x00000006U);
+	mmio_write_32(0xFD827800U, 0x00000006U);
+
+	/* RT bus Leaf setting */
+	mmio_write_32(0xFFC50800U, 0x00000000U);
+	mmio_write_32(0xFFC51800U, 0x00000000U);
+
+	/* Resource Alloc start */
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+	/* QOSBW start */
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+	NOTICE("BL2: QoS is None\n");
+
+	/* Resource Alloc setting */
+	mmio_write_32(QOSCTRL_EC, 0x00000000U);
+	/* Resource Alloc start */
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+}
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.h
new file mode 100644
index 0000000..627974a
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V10_H
+#define QOS_INIT_G2M_V10_H
+
+void qos_init_g2m_v10(void);
+
+#endif /* QOS_INIT_G2M_V10_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10_mstat.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10_mstat.h
new file mode 100644
index 0000000..c37915c
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10_mstat.h
@@ -0,0 +1,232 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V10_MSTAT_H
+#define QOS_INIT_G2M_V10_MSTAT_H
+
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+static const uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004030000FFFFUL,
+	/* 0x0038, */ 0x001004030000FFFFUL,
+	/* 0x0040, */ 0x001414090000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001410010000FFFFUL,
+	/* 0x0058, */ 0x00140C090000FFFFUL,
+	/* 0x0060, */ 0x00140C090000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001410010000FFFFUL,
+	/* 0x0078, */ 0x001004020000FFFFUL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414090000FFFFUL,
+	/* 0x0090, */ 0x001408060000FFFFUL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00A0, */ 0x000C08020000FFFFUL,
+	/* 0x00A8, */ 0x000C04010000FFFFUL,
+	/* 0x00B0, */ 0x000C04010000FFFFUL,
+	/* 0x00B8, */ 0x0000000000000000UL,
+	/* 0x00C0, */ 0x000C08020000FFFFUL,
+	/* 0x00C8, */ 0x000C04010000FFFFUL,
+	/* 0x00D0, */ 0x000C04010000FFFFUL,
+	/* 0x00D8, */ 0x000C04030000FFFFUL,
+	/* 0x00E0, */ 0x000C100F0000FFFFUL,
+	/* 0x00E8, */ 0x0000000000000000UL,
+	/* 0x00F0, */ 0x001010080000FFFFUL,
+	/* 0x00F8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x001010080000FFFFUL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100C0A0000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00100C0A0000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x00100C0A0000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008050000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001028280000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01A0, */ 0x00100C0A0000FFFFUL,
+	/* 0x01A8, */ 0x0000000000000000UL,
+	/* 0x01B0, */ 0x0000000000000000UL,
+	/* 0x01B8, */ 0x0000000000000000UL,
+	/* 0x01C0, */ 0x0000000000000000UL,
+	/* 0x01C8, */ 0x0000000000000000UL,
+	/* 0x01D0, */ 0x0000000000000000UL,
+	/* 0x01D8, */ 0x0000000000000000UL,
+	/* 0x01E0, */ 0x0000000000000000UL,
+	/* 0x01E8, */ 0x0000000000000000UL,
+	/* 0x01F0, */ 0x0000000000000000UL,
+	/* 0x01F8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x001408010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02A0, */ 0x000C04010000FFFFUL,
+	/* 0x02A8, */ 0x000C04010000FFFFUL,
+	/* 0x02B0, */ 0x001404010000FFFFUL,
+	/* 0x02B8, */ 0x0000000000000000UL,
+	/* 0x02C0, */ 0x0000000000000000UL,
+	/* 0x02C8, */ 0x0000000000000000UL,
+	/* 0x02D0, */ 0x000C04010000FFFFUL,
+	/* 0x02D8, */ 0x000C04010000FFFFUL,
+	/* 0x02E0, */ 0x001404010000FFFFUL,
+	/* 0x02E8, */ 0x0000000000000000UL,
+	/* 0x02F0, */ 0x0000000000000000UL,
+	/* 0x02F8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static const uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x001200100C89C401UL,
+	/* 0x0008, */ 0x001200100C89C401UL,
+	/* 0x0010, */ 0x001200100C89C401UL,
+	/* 0x0018, */ 0x001200100C89C401UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x001100100C803401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00A0, */ 0x0000000000000000UL,
+	/* 0x00A8, */ 0x0000000000000000UL,
+	/* 0x00B0, */ 0x0000000000000000UL,
+	/* 0x00B8, */ 0x0000000000000000UL,
+	/* 0x00C0, */ 0x0000000000000000UL,
+	/* 0x00C8, */ 0x0000000000000000UL,
+	/* 0x00D0, */ 0x0000000000000000UL,
+	/* 0x00D8, */ 0x0000000000000000UL,
+	/* 0x00E0, */ 0x0000000000000000UL,
+	/* 0x00E8, */ 0x0000000000000000UL,
+	/* 0x00F0, */ 0x0000000000000000UL,
+	/* 0x00F8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01A0, */ 0x0000000000000000UL,
+	/* 0x01A8, */ 0x0000000000000000UL,
+	/* 0x01B0, */ 0x0000000000000000UL,
+	/* 0x01B8, */ 0x0000000000000000UL,
+	/* 0x01C0, */ 0x001100500C8FFC01UL,
+	/* 0x01C8, */ 0x001100500C8FFC01UL,
+	/* 0x01D0, */ 0x001100500C8FFC01UL,
+	/* 0x01D8, */ 0x001100500C8FFC01UL,
+	/* 0x01E0, */ 0x0000000000000000UL,
+	/* 0x01E8, */ 0x001200100C803401UL,
+	/* 0x01F0, */ 0x001100100C80FC01UL,
+	/* 0x01F8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x001200100C80FC01UL,
+	/* 0x0210, */ 0x001100100C80FC01UL,
+	/* 0x0218, */ 0x001100100C825801UL,
+	/* 0x0220, */ 0x001100100C825801UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x001100100C825801UL,
+	/* 0x0238, */ 0x001100100C825801UL,
+	/* 0x0240, */ 0x001200100C8BB801UL,
+	/* 0x0248, */ 0x001100100C8EA401UL,
+	/* 0x0250, */ 0x001200100C8BB801UL,
+	/* 0x0258, */ 0x001100100C8EA401UL,
+	/* 0x0260, */ 0x001100100C84E401UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x001100100C81F401UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02A0, */ 0x0000000000000000UL,
+	/* 0x02A8, */ 0x0000000000000000UL,
+	/* 0x02B0, */ 0x0000000000000000UL,
+	/* 0x02B8, */ 0x001100100C803401UL,
+	/* 0x02C0, */ 0x0000000000000000UL,
+	/* 0x02C8, */ 0x0000000000000000UL,
+	/* 0x02D0, */ 0x0000000000000000UL,
+	/* 0x02D8, */ 0x0000000000000000UL,
+	/* 0x02E0, */ 0x0000000000000000UL,
+	/* 0x02E8, */ 0x001100100C803401UL,
+	/* 0x02F0, */ 0x001100300C8FFC01UL,
+	/* 0x02F8, */ 0x001100500C8FFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x001100300C8FFC01UL,
+	/* 0x0310, */ 0x001100500C8FFC01UL,
+	/* 0x0318, */ 0x001200100C803401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+#endif /* RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT */
+
+#endif /* QOS_INIT_G2M_V10_MSTAT_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
new file mode 100644
index 0000000..db61858
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
@@ -0,0 +1,218 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "../qos_common.h"
+#include "qos_init_g2m_v11.h"
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2m_v11_mstat195.h"
+#else /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#include "qos_init_g2m_v11_mstat390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2m_v11_qoswt195.h"
+#else /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#include "qos_init_g2m_v11_qoswt390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+#endif /* RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT */
+#include "qos_reg.h"
+
+#define RCAR_QOS_VERSION			"rev.0.19"
+
+#define QOSWT_TIME_BANK0			20000000U	/* unit:ns */
+
+#define QOSWT_WTEN_ENABLE			0x1U
+
+#define QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2M_11	(SL_INIT_SSLOTCLK_G2M_11 - 0x5U)
+
+#define OSWT_WTREF_SLOT0_EN_REQ1_SLOT		3U
+#define OSWT_WTREF_SLOT0_EN_REQ2_SLOT		9U
+#define QOSWT_WTREF_SLOT0_EN				\
+	((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) |	\
+	(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+#define QOSWT_WTREF_SLOT1_EN				\
+	((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) |	\
+	(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+
+#define QOSWT_WTSET0_REQ_SSLOT0			5U
+#define WT_BASE_SUB_SLOT_NUM0			12U
+#define QOSWT_WTSET0_PERIOD0_G2M_11			\
+	((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2M_11) - 1U)
+#define QOSWT_WTSET0_SSLOT0			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET0_SLOTSLOT0			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+#define QOSWT_WTSET1_PERIOD1_G2M_11			\
+	((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2M_11) - 1U)
+#define QOSWT_WTSET1_SSLOT1			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET1_SLOTSLOT1			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+static const struct rcar_gen3_dbsc_qos_settings g2m_v11_qos[] = {
+	/* BUFCAM settings */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBCAM0CNF3, 0x00000000U },
+	{ DBSC_DBSCHCNT0, 0x000F0037U },
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000100U },
+	{ DBSC_DBSCHQOS91, 0x000000F0U },
+	{ DBSC_DBSCHQOS92, 0x000000A0U },
+	{ DBSC_DBSCHQOS93, 0x00000040U },
+	{ DBSC_DBSCHQOS120, 0x00000040U },
+	{ DBSC_DBSCHQOS121, 0x00000030U },
+	{ DBSC_DBSCHQOS122, 0x00000020U },
+	{ DBSC_DBSCHQOS123, 0x00000010U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2m_v11(void)
+{
+	uint32_t i;
+
+	rzg_qos_dbsc_setting(g2m_v11_qos, ARRAY_SIZE(g2m_v11_qos), false);
+
+	/* DRAM Split Address mapping */
+#if RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH
+#if RCAR_LSI == RZ_G2M
+#error "Don't set DRAM Split 4ch(G2M)"
+#else /* RCAR_LSI == RZ_G2M */
+	ERROR("DRAM Split 4ch not supported.(G2M)");
+	panic();
+#endif /* RCAR_LSI == RZ_G2M */
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH) || \
+	(RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_AUTO)
+	NOTICE("BL2: DRAM Split is 2ch\n");
+	mmio_write_32(AXI_ADSPLCR0, 0x00000000U);
+	mmio_write_32(AXI_ADSPLCR1, ADSPLCR0_ADRMODE_DEFAULT |
+		      ADSPLCR0_SPLITSEL(0xFFU) | ADSPLCR0_AREA(0x1CU) |
+		      ADSPLCR0_SWP);
+	mmio_write_32(AXI_ADSPLCR2, 0x00001004U);
+	mmio_write_32(AXI_ADSPLCR3, 0x00000000U);
+#else /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+	NOTICE("BL2: DRAM Split is OFF\n");
+#endif /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif /* RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT */
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+	NOTICE("BL2: DRAM refresh interval 1.95 usec\n");
+#else /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+	NOTICE("BL2: DRAM refresh interval 3.9 usec\n");
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	NOTICE("BL2: Periodic Write DQ Training\n");
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_RAS, 0x00000044U);
+	mmio_write_64(QOSCTRL_DANN, 0x0404020002020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x0020100AU);
+	mmio_write_32(QOSCTRL_INSFC, 0x06330001U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x02010003U); /* GPU Boost Mode ON */
+
+	mmio_write_32(QOSCTRL_SL_INIT,
+		    SL_INIT_REFFSSLOT | SL_INIT_SLOTSSLOT |
+		    SL_INIT_SSLOTCLK_G2M_11);
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	mmio_write_32(QOSCTRL_REF_ARS,
+		      QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2M_11 << 16);
+#else /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+	mmio_write_32(QOSCTRL_REF_ARS, 0x00330000U);
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	for (i = 0U; i < ARRAY_SIZE(qoswt_fix); i++) {
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK0 + i * 8U, qoswt_fix[i]);
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK1 + i * 8U, qoswt_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(qoswt_be); i++) {
+		mmio_write_64(QOSWT_BE_WTQOS_BANK0 + i * 8U, qoswt_be[i]);
+		mmio_write_64(QOSWT_BE_WTQOS_BANK1 + i * 8U, qoswt_be[i]);
+	}
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	/* 3DG bus Leaf setting */
+	mmio_write_32(GPU_ACT_GRD, 0x00001234U);
+	mmio_write_32(GPU_ACT0, 0x00000000U);
+	mmio_write_32(GPU_ACT1, 0x00000000U);
+	mmio_write_32(GPU_ACT2, 0x00000000U);
+	mmio_write_32(GPU_ACT3, 0x00000000U);
+
+	/* RT bus Leaf setting */
+	mmio_write_32(RT_ACT0, 0x00000000U);
+	mmio_write_32(RT_ACT1, 0x00000000U);
+
+	/* CCI bus Leaf setting */
+	mmio_write_32(CPU_ACT0, 0x00000003U);
+	mmio_write_32(CPU_ACT1, 0x00000003U);
+	mmio_write_32(CPU_ACT2, 0x00000003U);
+	mmio_write_32(CPU_ACT3, 0x00000003U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	/*  re-write training setting */
+	mmio_write_32(QOSWT_WTREF,
+		      (QOSWT_WTREF_SLOT1_EN << 16) | QOSWT_WTREF_SLOT0_EN);
+	mmio_write_32(QOSWT_WTSET0,
+		      (QOSWT_WTSET0_PERIOD0_G2M_11 << 16) |
+		      (QOSWT_WTSET0_SSLOT0 << 8) | QOSWT_WTSET0_SLOTSLOT0);
+	mmio_write_32(QOSWT_WTSET1,
+		      (QOSWT_WTSET1_PERIOD1_G2M_11 << 16) |
+		      (QOSWT_WTSET1_SSLOT1 << 8) | QOSWT_WTSET1_SLOTSLOT1);
+
+	mmio_write_32(QOSWT_WTEN, QOSWT_WTEN_ENABLE);
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+	NOTICE("BL2: QoS is None\n");
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+}
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.h
new file mode 100644
index 0000000..d042493
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V11_H
+#define QOS_INIT_G2M_V11_H
+
+void qos_init_g2m_v11(void);
+
+#endif /* QOS_INIT_G2M_V11_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat195.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat195.h
new file mode 100644
index 0000000..950abd6
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat195.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V11_MSTAT195_H
+#define QOS_INIT_G2M_V11_MSTAT195_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000FFFFUL,
+	/* 0x0038, */ 0x001004040000FFFFUL,
+	/* 0x0040, */ 0x001414090000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404010000FFFFUL,
+	/* 0x0058, */ 0x00140C0A0000FFFFUL,
+	/* 0x0060, */ 0x00140C0A0000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404010000FFFFUL,
+	/* 0x0078, */ 0x001004030000FFFFUL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414090000FFFFUL,
+	/* 0x0090, */ 0x001408070000FFFFUL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C04020000FFFFUL,
+	/* 0x00a8, */ 0x000C04010000FFFFUL,
+	/* 0x00b0, */ 0x000C04010000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C04020000FFFFUL,
+	/* 0x00c8, */ 0x000C04010000FFFFUL,
+	/* 0x00d0, */ 0x000C04010000FFFFUL,
+	/* 0x00d8, */ 0x000C08050000FFFFUL,
+	/* 0x00e0, */ 0x000C14120000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100C0B0000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0010100D0000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x00100C0B0000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008060000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x00102C2C0000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x00100C0B0000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x001408010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x001200100BD03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002100600BDFFC01UL,
+	/* 0x01c8, */ 0x002100600BDFFC01UL,
+	/* 0x01d0, */ 0x002100600BDFFC01UL,
+	/* 0x01d8, */ 0x002100600BDFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x001100200BDFFC01UL,
+	/* 0x0220, */ 0x001100200BDFFC01UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x001100200BDFFC01UL,
+	/* 0x0238, */ 0x001100200BDFFC01UL,
+	/* 0x0240, */ 0x001200200BDFFC01UL,
+	/* 0x0248, */ 0x001100200BDFFC01UL,
+	/* 0x0250, */ 0x001200200BDFFC01UL,
+	/* 0x0258, */ 0x001100200BDFFC01UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x001100400BDFFC01UL,
+	/* 0x02f8, */ 0x001100600BDFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x001100400BDFFC01UL,
+	/* 0x0310, */ 0x001100600BDFFC01UL,
+	/* 0x0318, */ 0x001200100BD03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V11_MSTAT195_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat390.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat390.h
new file mode 100644
index 0000000..5c6fd24
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_mstat390.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V11_MSTAT390_H
+#define QOS_INIT_G2M_V11_MSTAT390_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000FFFFUL,
+	/* 0x0038, */ 0x001008070000FFFFUL,
+	/* 0x0040, */ 0x001424120000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404010000FFFFUL,
+	/* 0x0058, */ 0x001414130000FFFFUL,
+	/* 0x0060, */ 0x001414130000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404010000FFFFUL,
+	/* 0x0078, */ 0x001008050000FFFFUL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001424120000FFFFUL,
+	/* 0x0090, */ 0x0014100D0000FFFFUL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C08040000FFFFUL,
+	/* 0x00a8, */ 0x000C04020000FFFFUL,
+	/* 0x00b0, */ 0x000C04020000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C08040000FFFFUL,
+	/* 0x00c8, */ 0x000C04020000FFFFUL,
+	/* 0x00d0, */ 0x000C04020000FFFFUL,
+	/* 0x00d8, */ 0x000C0C0A0000FFFFUL,
+	/* 0x00e0, */ 0x000C24230000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001044110000FFFFUL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x001014110000FFFFUL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x001018150000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00101C190000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x001018150000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x00100C0B0000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001058570000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x001018150000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04010000FFFFUL,
+	/* 0x01f0, */ 0x000C04010000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04010000FFFFUL,
+	/* 0x0210, */ 0x000C04010000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFFFUL,
+	/* 0x0268, */ 0x001410010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x000C08020000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x00140C010000FFFFUL,
+	/* 0x02b8, */ 0x000C04010000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x00140C010000FFFFUL,
+	/* 0x02e8, */ 0x000C04010000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0012003005EFFC01UL,
+	/* 0x0008, */ 0x0012003005EFFC01UL,
+	/* 0x0010, */ 0x0012003005EFFC01UL,
+	/* 0x0018, */ 0x0012003005EFFC01UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001005E03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002100B005EFFC01UL,
+	/* 0x01c8, */ 0x002100B005EFFC01UL,
+	/* 0x01d0, */ 0x002100B005EFFC01UL,
+	/* 0x01d8, */ 0x002100B005EFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0021003005EFFC01UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0021003005EFFC01UL,
+	/* 0x0218, */ 0x0011003005EFFC01UL,
+	/* 0x0220, */ 0x0011003005EFFC01UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011003005EFFC01UL,
+	/* 0x0238, */ 0x0011003005EFFC01UL,
+	/* 0x0240, */ 0x0012003005EFFC01UL,
+	/* 0x0248, */ 0x0011003005EFFC01UL,
+	/* 0x0250, */ 0x0012003005EFFC01UL,
+	/* 0x0258, */ 0x0011003005EFFC01UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011007005EFFC01UL,
+	/* 0x02f8, */ 0x001100B005EFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0011007005EFFC01UL,
+	/* 0x0310, */ 0x001100B005EFFC01UL,
+	/* 0x0318, */ 0x0012001005E03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V11_MSTAT390_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt195.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt195.h
new file mode 100644
index 0000000..f526a82
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt195.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V11_QOSWT195_H
+#define QOS_INIT_G2M_V11_QOSWT195_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000C010UL,
+	/* 0x0038, */ 0x001004040000C010UL,
+	/* 0x0040, */ 0x001414090000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x00140C0A0000C010UL,
+	/* 0x0060, */ 0x00140C0A0000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x001004030000C010UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414090000FFF0UL,
+	/* 0x0090, */ 0x001408070000C010UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08020000FFF0UL,
+	/* 0x0268, */ 0x001408010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C04010000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V11_QOSWT195_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt390.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt390.h
new file mode 100644
index 0000000..bfb80e3
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11_qoswt390.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V11_QOSWT390_H
+#define QOS_INIT_G2M_V11_QOSWT390_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000C010UL,
+	/* 0x0038, */ 0x001008070000C010UL,
+	/* 0x0040, */ 0x001424120000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x001414130000C010UL,
+	/* 0x0060, */ 0x001414130000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x001008050000C010UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001424120000FFF0UL,
+	/* 0x0090, */ 0x0014100D0000C010UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFF0UL,
+	/* 0x0268, */ 0x001410010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C08020000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V11_QOSWT390_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
new file mode 100644
index 0000000..321cd2b
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
@@ -0,0 +1,210 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "../qos_common.h"
+#include "qos_init_g2m_v30.h"
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2m_v30_mstat195.h"
+#else /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#include "qos_init_g2m_v30_mstat390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2m_v30_qoswt195.h"
+#else /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#include "qos_init_g2m_v30_qoswt390.h"
+#endif /* RCAR_REF_INT == RCAR_REF_DEFAULT */
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+#endif /* RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT */
+#include "qos_reg.h"
+
+#define RCAR_QOS_VERSION			"rev.0.04"
+
+#define QOSWT_TIME_BANK0			20000000U	/* unit:ns */
+
+#define QOSWT_WTEN_ENABLE			0x1U
+
+#define QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2M_30	(SL_INIT_SSLOTCLK_G2M_30 - 0x5U)
+
+#define OSWT_WTREF_SLOT0_EN_REQ1_SLOT		3U
+#define OSWT_WTREF_SLOT0_EN_REQ2_SLOT		9U
+#define QOSWT_WTREF_SLOT0_EN				\
+	((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) |	\
+	(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+#define QOSWT_WTREF_SLOT1_EN				\
+	((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) |	\
+	(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+
+#define QOSWT_WTSET0_REQ_SSLOT0			5U
+#define WT_BASE_SUB_SLOT_NUM0			12U
+#define QOSWT_WTSET0_PERIOD0_G2M_30			\
+	((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2M_30) - 1U)
+#define QOSWT_WTSET0_SSLOT0			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET0_SLOTSLOT0			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+#define QOSWT_WTSET1_PERIOD1_G2M_30			\
+	((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2M_30) - 1U)
+#define QOSWT_WTSET1_SSLOT1			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET1_SLOTSLOT1			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+static const struct rcar_gen3_dbsc_qos_settings g2m_v30_qos[] = {
+	/* BUFCAM settings */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBCAM0CNF3, 0x00000000U },
+	{ DBSC_DBSCHCNT0, 0x000F0037U },
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000100U },
+	{ DBSC_DBSCHQOS91, 0x000000F0U },
+	{ DBSC_DBSCHQOS92, 0x000000A0U },
+	{ DBSC_DBSCHQOS93, 0x00000040U },
+	{ DBSC_DBSCHQOS120, 0x00000040U },
+	{ DBSC_DBSCHQOS121, 0x00000030U },
+	{ DBSC_DBSCHQOS122, 0x00000020U },
+	{ DBSC_DBSCHQOS123, 0x00000010U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2m_v30(void)
+{
+	uint32_t i;
+
+	rzg_qos_dbsc_setting(g2m_v30_qos, ARRAY_SIZE(g2m_v30_qos), true);
+
+	/* DRAM Split Address mapping */
+#if RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH
+#if RCAR_LSI == RZ_G2M
+  #error "Don't set DRAM Split 4ch(G2M)"
+#else /* RCAR_LSI == RZ_G2M */
+	ERROR("DRAM Split 4ch not supported.(G2M)");
+	panic();
+#endif /* RCAR_LSI == RZ_G2M */
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH) || \
+	(RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_AUTO)
+	NOTICE("BL2: DRAM Split is 2ch\n");
+	mmio_write_32(AXI_ADSPLCR0, 0x00000000U);
+	mmio_write_32(AXI_ADSPLCR1, ADSPLCR0_ADRMODE_DEFAULT |
+		      ADSPLCR0_SPLITSEL(0xFFU) | ADSPLCR0_AREA(0x1DU) |
+		      ADSPLCR0_SWP);
+	mmio_write_32(AXI_ADSPLCR2, 0x00001004U);
+	mmio_write_32(AXI_ADSPLCR3, 0x00000000U);
+#else /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+	NOTICE("BL2: DRAM Split is OFF\n");
+#endif /* RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH */
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+	NOTICE("BL2: DRAM refresh interval 1.95 usec\n");
+#else /*  RCAR_REF_INT == RCAR_REF_DEFAULT */
+	NOTICE("BL2: DRAM refresh interval 3.9 usec\n");
+#endif /*  RCAR_REF_INT == RCAR_REF_DEFAULT */
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	NOTICE("BL2: Periodic Write DQ Training\n");
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_RAS, 0x00000044U);
+	mmio_write_64(QOSCTRL_DANN, 0x0404020002020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x0020100AU);
+	mmio_write_32(QOSCTRL_FSS, 0x0000000AU);
+	mmio_write_32(QOSCTRL_INSFC, 0x06330001U);
+	mmio_write_32(QOSCTRL_EARLYR, 0x00000001U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x02010003U); /* GPU Boost Mode ON */
+
+	/* GPU Boost Mode */
+	mmio_write_32(QOSCTRL_STATGEN0, 0x00000001U);
+
+	mmio_write_32(QOSCTRL_SL_INIT,
+		      SL_INIT_REFFSSLOT | SL_INIT_SLOTSSLOT |
+		      SL_INIT_SSLOTCLK_G2M_30);
+	mmio_write_32(QOSCTRL_REF_ARS,
+		      QOSCTRL_REF_ARS_ARBSTOPCYCLE_G2M_30 << 16);
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	for (i = 0U; i < ARRAY_SIZE(qoswt_fix); i++) {
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK0 + i * 8U, qoswt_fix[i]);
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK1 + i * 8U, qoswt_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(qoswt_be); i++) {
+		mmio_write_64(QOSWT_BE_WTQOS_BANK0 + i * 8U, qoswt_be[i]);
+		mmio_write_64(QOSWT_BE_WTQOS_BANK1 + i * 8U, qoswt_be[i]);
+	}
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	/* RT bus Leaf setting */
+	mmio_write_32(RT_ACT0, 0x00000000U);
+	mmio_write_32(RT_ACT1, 0x00000000U);
+
+	/* CCI bus Leaf setting */
+	mmio_write_32(CPU_ACT0, 0x00000003U);
+	mmio_write_32(CPU_ACT1, 0x00000003U);
+	mmio_write_32(CPU_ACT2, 0x00000003U);
+	mmio_write_32(CPU_ACT3, 0x00000003U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	/*  re-write training setting */
+	mmio_write_32(QOSWT_WTREF,
+		      (QOSWT_WTREF_SLOT1_EN << 16) | QOSWT_WTREF_SLOT0_EN);
+	mmio_write_32(QOSWT_WTSET0, (QOSWT_WTSET0_PERIOD0_G2M_30 << 16) |
+		      (QOSWT_WTSET0_SSLOT0 << 8) | QOSWT_WTSET0_SLOTSLOT0);
+	mmio_write_32(QOSWT_WTSET1, (QOSWT_WTSET1_PERIOD1_G2M_30 << 16) |
+		      (QOSWT_WTSET1_SSLOT1 << 8) | QOSWT_WTSET1_SLOTSLOT1);
+
+	mmio_write_32(QOSWT_WTEN,   QOSWT_WTEN_ENABLE);
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+	NOTICE("BL2: QoS is None\n");
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+}
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.h
new file mode 100644
index 0000000..f89eabf
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V30_H
+#define QOS_INIT_G2M_V30_H
+
+void qos_init_g2m_v30(void);
+
+#endif	/* QOS_INIT_G2M_V30_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat195.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat195.h
new file mode 100644
index 0000000..fd15788
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat195.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V30_MSTAT195_H
+#define QOS_INIT_G2M_V30_MSTAT195_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000FFFFUL,
+	/* 0x0038, */ 0x001004040000FFFFUL,
+	/* 0x0040, */ 0x001414090000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404010000FFFFUL,
+	/* 0x0058, */ 0x00140C0A0000FFFFUL,
+	/* 0x0060, */ 0x00140C0A0000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404010000FFFFUL,
+	/* 0x0078, */ 0x001004030000FFFFUL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414090000FFFFUL,
+	/* 0x0090, */ 0x001408070000FFFFUL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C04020000FFFFUL,
+	/* 0x00a8, */ 0x000C04010000FFFFUL,
+	/* 0x00b0, */ 0x000C04010000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C04020000FFFFUL,
+	/* 0x00c8, */ 0x000C04010000FFFFUL,
+	/* 0x00d0, */ 0x000C04010000FFFFUL,
+	/* 0x00d8, */ 0x000C08050000FFFFUL,
+	/* 0x00e0, */ 0x000C10100000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001024090000FFFFUL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x00100C090000FFFFUL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x000C10100000FFFFUL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100C0B0000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0010100D0000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x00100C0B0000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008060000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x00102C2C0000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x00100C0B0000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04010000FFFFUL,
+	/* 0x01f0, */ 0x000C04010000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04010000FFFFUL,
+	/* 0x0210, */ 0x000C04010000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08020000FFFFUL,
+	/* 0x0268, */ 0x001408010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x000C04010000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x001408010000FFFFUL,
+	/* 0x02b8, */ 0x000C04010000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x001408010000FFFFUL,
+	/* 0x02e8, */ 0x000C04010000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x001200200BDFFC01UL,
+	/* 0x0008, */ 0x001200200BDFFC01UL,
+	/* 0x0010, */ 0x001200200BDFFC01UL,
+	/* 0x0018, */ 0x001200200BDFFC01UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x001200100BD03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002100600BDFFC01UL,
+	/* 0x01c8, */ 0x002100600BDFFC01UL,
+	/* 0x01d0, */ 0x002100600BDFFC01UL,
+	/* 0x01d8, */ 0x002100600BDFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x002100200BDFFC01UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x002100200BDFFC01UL,
+	/* 0x0218, */ 0x001100200BDFFC01UL,
+	/* 0x0220, */ 0x001100200BDFFC01UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x001100200BDFFC01UL,
+	/* 0x0238, */ 0x001100200BDFFC01UL,
+	/* 0x0240, */ 0x001200200BDFFC01UL,
+	/* 0x0248, */ 0x001100200BDFFC01UL,
+	/* 0x0250, */ 0x001200200BDFFC01UL,
+	/* 0x0258, */ 0x001100200BDFFC01UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x001100400BDFFC01UL,
+	/* 0x02f8, */ 0x001100600BDFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x001100400BDFFC01UL,
+	/* 0x0310, */ 0x001100600BDFFC01UL,
+	/* 0x0318, */ 0x001200100BD03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif	/* QOS_INIT_G2M_V30_MSTAT195_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat390.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat390.h
new file mode 100644
index 0000000..aa2036d
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_mstat390.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V30_MSTAT390_H
+#define QOS_INIT_G2M_V30_MSTAT390_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000FFFFUL,
+	/* 0x0038, */ 0x001008070000FFFFUL,
+	/* 0x0040, */ 0x001424120000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404010000FFFFUL,
+	/* 0x0058, */ 0x001414130000FFFFUL,
+	/* 0x0060, */ 0x001414130000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404010000FFFFUL,
+	/* 0x0078, */ 0x001008050000FFFFUL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001424120000FFFFUL,
+	/* 0x0090, */ 0x0014100D0000FFFFUL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C08040000FFFFUL,
+	/* 0x00a8, */ 0x000C04020000FFFFUL,
+	/* 0x00b0, */ 0x000C04020000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C08040000FFFFUL,
+	/* 0x00c8, */ 0x000C04020000FFFFUL,
+	/* 0x00d0, */ 0x000C04020000FFFFUL,
+	/* 0x00d8, */ 0x000C0C0A0000FFFFUL,
+	/* 0x00e0, */ 0x000C201F0000FFFFUL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001044110000FFFFUL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x001014110000FFFFUL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x000C201F0000FFFFUL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x001018150000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00101C190000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x001018150000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x00100C0B0000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001058570000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x001018150000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x000C04010000FFFFUL,
+	/* 0x01d8, */ 0x000C04010000FFFFUL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04010000FFFFUL,
+	/* 0x01f0, */ 0x000C04010000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04010000FFFFUL,
+	/* 0x0210, */ 0x000C04010000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFFFUL,
+	/* 0x0268, */ 0x001410010000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x000C08020000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04010000FFFFUL,
+	/* 0x02a8, */ 0x000C04010000FFFFUL,
+	/* 0x02b0, */ 0x00140C010000FFFFUL,
+	/* 0x02b8, */ 0x000C04010000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04010000FFFFUL,
+	/* 0x02d8, */ 0x000C04010000FFFFUL,
+	/* 0x02e0, */ 0x00140C010000FFFFUL,
+	/* 0x02e8, */ 0x000C04010000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0012003005EFFC01UL,
+	/* 0x0008, */ 0x0012003005EFFC01UL,
+	/* 0x0010, */ 0x0012003005EFFC01UL,
+	/* 0x0018, */ 0x0012003005EFFC01UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001005E03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002100B005EFFC01UL,
+	/* 0x01c8, */ 0x002100B005EFFC01UL,
+	/* 0x01d0, */ 0x002100B005EFFC01UL,
+	/* 0x01d8, */ 0x002100B005EFFC01UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0021003005EFFC01UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0021003005EFFC01UL,
+	/* 0x0218, */ 0x0011003005EFFC01UL,
+	/* 0x0220, */ 0x0011003005EFFC01UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011003005EFFC01UL,
+	/* 0x0238, */ 0x0011003005EFFC01UL,
+	/* 0x0240, */ 0x0012003005EFFC01UL,
+	/* 0x0248, */ 0x0011003005EFFC01UL,
+	/* 0x0250, */ 0x0012003005EFFC01UL,
+	/* 0x0258, */ 0x0011003005EFFC01UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011007005EFFC01UL,
+	/* 0x02f8, */ 0x001100B005EFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0011007005EFFC01UL,
+	/* 0x0310, */ 0x001100B005EFFC01UL,
+	/* 0x0318, */ 0x0012001005E03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V30_MSTAT390_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt195.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt195.h
new file mode 100644
index 0000000..27c9c51
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt195.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V30_QOSWT195_H
+#define QOS_INIT_G2M_V30_QOSWT195_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004040000C010UL,
+	/* 0x0038, */ 0x001004040000C010UL,
+	/* 0x0040, */ 0x001414090000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x00140C0A0000C010UL,
+	/* 0x0060, */ 0x00140C0A0000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x001004030000C010UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001414090000FFF0UL,
+	/* 0x0090, */ 0x001408070000C010UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08020000FFF0UL,
+	/* 0x0268, */ 0x001408010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C04010000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V30_QOSWT195_H */
diff --git a/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt390.h b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt390.h
new file mode 100644
index 0000000..5d18212
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30_qoswt390.h
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2M_V30_QOSWT390_H
+#define QOS_INIT_G2M_V30_QOSWT390_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008070000C010UL,
+	/* 0x0038, */ 0x001008070000C010UL,
+	/* 0x0040, */ 0x001424120000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x001414130000C010UL,
+	/* 0x0060, */ 0x001414130000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x001008050000C010UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x001424120000FFF0UL,
+	/* 0x0090, */ 0x0014100D0000C010UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C030000FFF0UL,
+	/* 0x0268, */ 0x001410010000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C08020000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410010000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+};
+
+#endif /* QOS_INIT_G2M_V30_QOSWT390_H */
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
new file mode 100644
index 0000000..00b0948
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
@@ -0,0 +1,196 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "qos_init_g2n_v10.h"
+
+#include "../qos_common.h"
+#include "../qos_reg.h"
+
+#define RCAR_QOS_VERSION			"rev.0.09"
+
+#define REF_ARS_ARBSTOPCYCLE_G2N		(((SL_INIT_SSLOTCLK_G2N) - 5U) << 16U)
+
+#define QOSWT_TIME_BANK0			20000000U	/* unit:ns */
+
+#define	QOSWT_WTEN_ENABLE			0x1U
+
+#define OSWT_WTREF_SLOT0_EN_REQ1_SLOT		3U
+#define OSWT_WTREF_SLOT0_EN_REQ2_SLOT		9U
+#define QOSWT_WTREF_SLOT0_EN			((0x1U << OSWT_WTREF_SLOT0_EN_REQ1_SLOT) | \
+						(0x1U << OSWT_WTREF_SLOT0_EN_REQ2_SLOT))
+#define QOSWT_WTREF_SLOT1_EN			QOSWT_WTREF_SLOT0_EN
+
+#define QOSWT_WTSET0_REQ_SSLOT0			5U
+#define WT_BASE_SUB_SLOT_NUM0			12U
+#define QOSWT_WTSET0_PERIOD0_G2N		((QOSWT_TIME_BANK0 / QOSWT_WTSET0_CYCLE_G2N) - 1U)
+#define QOSWT_WTSET0_SSLOT0			(QOSWT_WTSET0_REQ_SSLOT0 - 1U)
+#define QOSWT_WTSET0_SLOTSLOT0			(WT_BASE_SUB_SLOT_NUM0 - 1U)
+
+#define QOSWT_WTSET1_PERIOD1_G2N		QOSWT_WTSET0_PERIOD0_G2N
+#define QOSWT_WTSET1_SSLOT1			QOSWT_WTSET0_SSLOT0
+#define QOSWT_WTSET1_SLOTSLOT1			QOSWT_WTSET0_SLOTSLOT0
+
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2n_v10_mstat195.h"
+#else
+#include "qos_init_g2n_v10_mstat390.h"
+#endif
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+#include "qos_init_g2n_v10_qoswt195.h"
+#else
+#include "qos_init_g2n_v10_qoswt390.h"
+#endif
+
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+#endif
+
+static const struct rcar_gen3_dbsc_qos_settings g2n_v10_qos[] = {
+	/* BUFCAM settings */
+	{ DBSC_DBCAM0CNF1, 0x00043218U },
+	{ DBSC_DBCAM0CNF2, 0x000000F4U },
+	{ DBSC_DBSCHCNT0, 0x000F0037U },
+	{ DBSC_DBSCHSZ0, 0x00000001U },
+	{ DBSC_DBSCHRW0, 0x22421111U },
+
+	/* DDR3 */
+	{ DBSC_SCFCTST2, 0x012F1123U },
+
+	/* QoS Settings */
+	{ DBSC_DBSCHQOS00, 0x00000F00U },
+	{ DBSC_DBSCHQOS01, 0x00000B00U },
+	{ DBSC_DBSCHQOS02, 0x00000000U },
+	{ DBSC_DBSCHQOS03, 0x00000000U },
+	{ DBSC_DBSCHQOS40, 0x00000300U },
+	{ DBSC_DBSCHQOS41, 0x000002F0U },
+	{ DBSC_DBSCHQOS42, 0x00000200U },
+	{ DBSC_DBSCHQOS43, 0x00000100U },
+	{ DBSC_DBSCHQOS90, 0x00000100U },
+	{ DBSC_DBSCHQOS91, 0x000000F0U },
+	{ DBSC_DBSCHQOS92, 0x000000A0U },
+	{ DBSC_DBSCHQOS93, 0x00000040U },
+	{ DBSC_DBSCHQOS130, 0x00000100U },
+	{ DBSC_DBSCHQOS131, 0x000000F0U },
+	{ DBSC_DBSCHQOS132, 0x000000A0U },
+	{ DBSC_DBSCHQOS133, 0x00000040U },
+	{ DBSC_DBSCHQOS140, 0x000000C0U },
+	{ DBSC_DBSCHQOS141, 0x000000B0U },
+	{ DBSC_DBSCHQOS142, 0x00000080U },
+	{ DBSC_DBSCHQOS143, 0x00000040U },
+	{ DBSC_DBSCHQOS150, 0x00000040U },
+	{ DBSC_DBSCHQOS151, 0x00000030U },
+	{ DBSC_DBSCHQOS152, 0x00000020U },
+	{ DBSC_DBSCHQOS153, 0x00000010U },
+};
+
+void qos_init_g2n_v10(void)
+{
+	rzg_qos_dbsc_setting(g2n_v10_qos, ARRAY_SIZE(g2n_v10_qos), true);
+
+	/* DRAM Split Address mapping */
+#if RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_4CH
+#if RCAR_LSI == RZ_G2N
+#error "Don't set DRAM Split 4ch(G2N)"
+#else
+	ERROR("DRAM Split 4ch not supported.(G2N)");
+	panic();
+#endif
+#elif (RCAR_DRAM_SPLIT == RCAR_DRAM_SPLIT_2CH)
+#if RCAR_LSI == RZ_G2N
+#error "Don't set DRAM Split 2ch(G2N)"
+#else
+	ERROR("DRAM Split 2ch not supported.(G2N)");
+	panic();
+#endif
+#else
+	NOTICE("BL2: DRAM Split is OFF\n");
+#endif
+
+#if !(RCAR_QOS_TYPE == RCAR_QOS_NONE)
+#if RCAR_QOS_TYPE  == RCAR_QOS_TYPE_DEFAULT
+	NOTICE("BL2: QoS is default setting(%s)\n", RCAR_QOS_VERSION);
+#endif
+
+#if RCAR_REF_INT == RCAR_REF_DEFAULT
+	NOTICE("BL2: DRAM refresh interval 1.95 usec\n");
+#else
+	NOTICE("BL2: DRAM refresh interval 3.9 usec\n");
+#endif
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	NOTICE("BL2: Periodic Write DQ Training\n");
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_RAS, 0x00000028U);
+	mmio_write_64(QOSCTRL_DANN, 0x0402000002020201UL);
+	mmio_write_32(QOSCTRL_DANT, 0x00100804U);
+	mmio_write_32(QOSCTRL_FSS, 0x0000000AU);
+	mmio_write_32(QOSCTRL_INSFC, 0x06330001U);
+	mmio_write_32(QOSCTRL_EARLYR, 0x00000001U);
+	mmio_write_32(QOSCTRL_RACNT0, 0x00010003U);
+
+	mmio_write_32(QOSCTRL_SL_INIT, SL_INIT_REFFSSLOT |
+		      SL_INIT_SLOTSSLOT | SL_INIT_SSLOTCLK_G2N);
+	mmio_write_32(QOSCTRL_REF_ARS, REF_ARS_ARBSTOPCYCLE_G2N);
+
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(mstat_fix); i++) {
+		mmio_write_64(QOSBW_FIX_QOS_BANK0 + i * 8U, mstat_fix[i]);
+		mmio_write_64(QOSBW_FIX_QOS_BANK1 + i * 8U, mstat_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(mstat_be); i++) {
+		mmio_write_64(QOSBW_BE_QOS_BANK0 + i * 8U, mstat_be[i]);
+		mmio_write_64(QOSBW_BE_QOS_BANK1 + i * 8U, mstat_be[i]);
+	}
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	for (i = 0U; i < ARRAY_SIZE(qoswt_fix); i++) {
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK0 + i * 8U, qoswt_fix[i]);
+		mmio_write_64(QOSWT_FIX_WTQOS_BANK1 + i * 8U, qoswt_fix[i]);
+	}
+	for (i = 0U; i < ARRAY_SIZE(qoswt_be); i++) {
+		mmio_write_64(QOSWT_BE_WTQOS_BANK0 + i * 8U, qoswt_be[i]);
+		mmio_write_64(QOSWT_BE_WTQOS_BANK1 + i * 8U, qoswt_be[i]);
+	}
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	/* RT bus Leaf setting */
+	mmio_write_32(RT_ACT0, 0x00000000U);
+	mmio_write_32(RT_ACT1, 0x00000000U);
+
+	/* CCI bus Leaf setting */
+	mmio_write_32(CPU_ACT0, 0x00000003U);
+	mmio_write_32(CPU_ACT1, 0x00000003U);
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+
+#if RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE
+	/*  re-write training setting */
+	mmio_write_32(QOSWT_WTREF, ((QOSWT_WTREF_SLOT1_EN << 16) | QOSWT_WTREF_SLOT0_EN));
+	mmio_write_32(QOSWT_WTSET0, ((QOSWT_WTSET0_PERIOD0_G2N << 16) |
+		      (QOSWT_WTSET0_SSLOT0 << 8) | QOSWT_WTSET0_SLOTSLOT0));
+	mmio_write_32(QOSWT_WTSET1, ((QOSWT_WTSET1_PERIOD1_G2N << 16) |
+		      (QOSWT_WTSET1_SSLOT1 << 8) | QOSWT_WTSET1_SLOTSLOT1));
+
+	mmio_write_32(QOSWT_WTEN, QOSWT_WTEN_ENABLE);
+#endif /* RCAR_REWT_TRAINING != RCAR_REWT_TRAINING_DISABLE */
+
+	mmio_write_32(QOSCTRL_STATQC, 0x00000001U);
+#else
+	NOTICE("BL2: QoS is None\n");
+
+	mmio_write_32(QOSCTRL_RAEN, 0x00000001U);
+#endif /* !(RCAR_QOS_TYPE == RCAR_QOS_NONE) */
+}
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.h b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.h
new file mode 100644
index 0000000..c7f02d9
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2N_V10_H
+#define QOS_INIT_G2N_V10_H
+
+void qos_init_g2n_v10(void);
+
+#endif /* QOS_INIT_G2N_V10_H */
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat195.h b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat195.h
new file mode 100644
index 0000000..6e304b0
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat195.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2N_MSTAT195_H
+#define QOS_INIT_G2N_MSTAT195_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004320000FFFFUL,
+	/* 0x0038, */ 0x001004320000FFFFUL,
+	/* 0x0040, */ 0x00140C5D0000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404040000FFFFUL,
+	/* 0x0058, */ 0x00140C940000FFFFUL,
+	/* 0x0060, */ 0x00140C940000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404040000FFFFUL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0014041F0000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C041D0000FFFFUL,
+	/* 0x00a8, */ 0x000C04090000FFFFUL,
+	/* 0x00b0, */ 0x000C040B0000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C041D0000FFFFUL,
+	/* 0x00c8, */ 0x000C04090000FFFFUL,
+	/* 0x00d0, */ 0x000C040B0000FFFFUL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x000C084F0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x000C21E60000FFFFUL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x00100CA50000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x001010C90000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x00100CA50000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x001008530000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x00101D9D0000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x00100CA50000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x001408020000FFFFUL,
+	/* 0x0270, */ 0x001404010000FFFFUL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408020000FFFFUL,
+	/* 0x0298, */ 0x001404010000FFFFUL,
+	/* 0x02a0, */ 0x000C04050000FFFFUL,
+	/* 0x02a8, */ 0x000C04050000FFFFUL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04050000FFFFUL,
+	/* 0x02d8, */ 0x000C04050000FFFFUL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x000C04050000FFFFUL,
+	/* 0x0388, */ 0x000C04050000FFFFUL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x001200100BD03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x002106000BDFFC01UL,
+	/* 0x01c8, */ 0x002106000BDFFC01UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x001101000BDF2401UL,
+	/* 0x0220, */ 0x001101000BDF2401UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x001101000BDF2401UL,
+	/* 0x0238, */ 0x001101000BDF2401UL,
+	/* 0x0240, */ 0x001201000BDF2401UL,
+	/* 0x0248, */ 0x001101000BDF2401UL,
+	/* 0x0250, */ 0x001201000BDF2401UL,
+	/* 0x0258, */ 0x001101000BDF2401UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x001106000BDFFC01UL,
+	/* 0x02f8, */ 0x001106000BDFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x001200100BD03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x001206000BDFFC01UL,
+	/* 0x0360, */ 0x001206000BDFFC01UL,
+	/* 0x0368, */ 0x001200100BD03401UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x001200100BD03401UL,
+};
+#endif /* QOS_INIT_G2N_MSTAT195_H */
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat390.h b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat390.h
new file mode 100644
index 0000000..4632413
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_mstat390.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2N_MSTAT390_H
+#define QOS_INIT_G2N_MSTAT390_H
+
+static uint64_t mstat_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008630000FFFFUL,
+	/* 0x0038, */ 0x001008630000FFFFUL,
+	/* 0x0040, */ 0x001418BA0000FFFFUL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x001404070000FFFFUL,
+	/* 0x0058, */ 0x001415270000FFFFUL,
+	/* 0x0060, */ 0x001415270000FFFFUL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x001404070000FFFFUL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0014083E0000FFFFUL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x000C08390000FFFFUL,
+	/* 0x00a8, */ 0x000C04110000FFFFUL,
+	/* 0x00b0, */ 0x000C04150000FFFFUL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x000C08390000FFFFUL,
+	/* 0x00c8, */ 0x000C04110000FFFFUL,
+	/* 0x00d0, */ 0x000C04150000FFFFUL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x001045080000FFFFUL,
+	/* 0x00f8, */ 0x000C0C9E0000FFFFUL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x001015080000FFFFUL,
+	/* 0x0118, */ 0x000C43CB0000FFFFUL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0010194A0000FFFFUL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x00101D910000FFFFUL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0010194A0000FFFFUL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x00100CA50000FFFFUL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x001037390000FFFFUL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0010194A0000FFFFUL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x000C04010000FFFFUL,
+	/* 0x01c8, */ 0x000C04010000FFFFUL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x000C04020000FFFFUL,
+	/* 0x01f0, */ 0x000C04090000FFFFUL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x000C04090000FFFFUL,
+	/* 0x0210, */ 0x000C04090000FFFFUL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C2A0000FFFFUL,
+	/* 0x0268, */ 0x001410040000FFFFUL,
+	/* 0x0270, */ 0x001404020000FFFFUL,
+	/* 0x0278, */ 0x000C08110000FFFFUL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410040000FFFFUL,
+	/* 0x0298, */ 0x001404020000FFFFUL,
+	/* 0x02a0, */ 0x000C04090000FFFFUL,
+	/* 0x02a8, */ 0x000C04090000FFFFUL,
+	/* 0x02b0, */ 0x00140C090000FFFFUL,
+	/* 0x02b8, */ 0x000C04020000FFFFUL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x000C04090000FFFFUL,
+	/* 0x02d8, */ 0x000C04090000FFFFUL,
+	/* 0x02e0, */ 0x00140C090000FFFFUL,
+	/* 0x02e8, */ 0x000C04020000FFFFUL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x000C04020000FFFFUL,
+	/* 0x0378, */ 0x000C04020000FFFFUL,
+	/* 0x0380, */ 0x000C04090000FFFFUL,
+	/* 0x0388, */ 0x000C04090000FFFFUL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t mstat_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0012001005E03401UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0021060005EFFC01UL,
+	/* 0x01c8, */ 0x0021060005EFFC01UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0021010005E79401UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0021010005E79401UL,
+	/* 0x0218, */ 0x0011010005E79401UL,
+	/* 0x0220, */ 0x0011010005E79401UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0011010005E79401UL,
+	/* 0x0238, */ 0x0011010005E79401UL,
+	/* 0x0240, */ 0x0012010005E79401UL,
+	/* 0x0248, */ 0x0011010005E79401UL,
+	/* 0x0250, */ 0x0012010005E79401UL,
+	/* 0x0258, */ 0x0011010005E79401UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0011060005EFFC01UL,
+	/* 0x02f8, */ 0x0011060005EFFC01UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0012001005E03401UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0012060005EFFC01UL,
+	/* 0x0360, */ 0x0012060005EFFC01UL,
+	/* 0x0368, */ 0x0012001005E03401UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0012001005E03401UL,
+};
+#endif /* QOS_INIT_G2N_MSTAT390_H */
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt195.h b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt195.h
new file mode 100644
index 0000000..eea1fce
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt195.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2N_QOSWT195_H
+#define QOS_INIT_G2N_QOSWT195_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001004320000C010UL,
+	/* 0x0038, */ 0x001004320000C010UL,
+	/* 0x0040, */ 0x00140C5D0000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x00140C940000C010UL,
+	/* 0x0060, */ 0x00140C940000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0014041F0000FFF0UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C08150000FFF0UL,
+	/* 0x0268, */ 0x001408020000FFF0UL,
+	/* 0x0270, */ 0x001404010000FFF0UL,
+	/* 0x0278, */ 0x000C04090000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001408020000FFF0UL,
+	/* 0x0298, */ 0x001404010000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+#endif /* QOS_INIT_G2N_QOSWT195_H */
diff --git a/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt390.h b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt390.h
new file mode 100644
index 0000000..7043303
--- /dev/null
+++ b/drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10_qoswt390.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_INIT_G2N_QOSWT390_H
+#define QOS_INIT_G2N_QOSWT390_H
+
+static uint64_t qoswt_fix[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x001008630000C010UL,
+	/* 0x0038, */ 0x001008630000C010UL,
+	/* 0x0040, */ 0x001418BA0000FFF0UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x001415270000C010UL,
+	/* 0x0060, */ 0x001415270000C010UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0014083E0000FFF0UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x000C0C2A0000FFF0UL,
+	/* 0x0268, */ 0x001410040000FFF0UL,
+	/* 0x0270, */ 0x001404020000FFF0UL,
+	/* 0x0278, */ 0x000C08110000FFF0UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x001410040000FFF0UL,
+	/* 0x0298, */ 0x001404020000FFF0UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+
+static uint64_t qoswt_be[] = {
+	/* 0x0000, */ 0x0000000000000000UL,
+	/* 0x0008, */ 0x0000000000000000UL,
+	/* 0x0010, */ 0x0000000000000000UL,
+	/* 0x0018, */ 0x0000000000000000UL,
+	/* 0x0020, */ 0x0000000000000000UL,
+	/* 0x0028, */ 0x0000000000000000UL,
+	/* 0x0030, */ 0x0000000000000000UL,
+	/* 0x0038, */ 0x0000000000000000UL,
+	/* 0x0040, */ 0x0000000000000000UL,
+	/* 0x0048, */ 0x0000000000000000UL,
+	/* 0x0050, */ 0x0000000000000000UL,
+	/* 0x0058, */ 0x0000000000000000UL,
+	/* 0x0060, */ 0x0000000000000000UL,
+	/* 0x0068, */ 0x0000000000000000UL,
+	/* 0x0070, */ 0x0000000000000000UL,
+	/* 0x0078, */ 0x0000000000000000UL,
+	/* 0x0080, */ 0x0000000000000000UL,
+	/* 0x0088, */ 0x0000000000000000UL,
+	/* 0x0090, */ 0x0000000000000000UL,
+	/* 0x0098, */ 0x0000000000000000UL,
+	/* 0x00a0, */ 0x0000000000000000UL,
+	/* 0x00a8, */ 0x0000000000000000UL,
+	/* 0x00b0, */ 0x0000000000000000UL,
+	/* 0x00b8, */ 0x0000000000000000UL,
+	/* 0x00c0, */ 0x0000000000000000UL,
+	/* 0x00c8, */ 0x0000000000000000UL,
+	/* 0x00d0, */ 0x0000000000000000UL,
+	/* 0x00d8, */ 0x0000000000000000UL,
+	/* 0x00e0, */ 0x0000000000000000UL,
+	/* 0x00e8, */ 0x0000000000000000UL,
+	/* 0x00f0, */ 0x0000000000000000UL,
+	/* 0x00f8, */ 0x0000000000000000UL,
+	/* 0x0100, */ 0x0000000000000000UL,
+	/* 0x0108, */ 0x0000000000000000UL,
+	/* 0x0110, */ 0x0000000000000000UL,
+	/* 0x0118, */ 0x0000000000000000UL,
+	/* 0x0120, */ 0x0000000000000000UL,
+	/* 0x0128, */ 0x0000000000000000UL,
+	/* 0x0130, */ 0x0000000000000000UL,
+	/* 0x0138, */ 0x0000000000000000UL,
+	/* 0x0140, */ 0x0000000000000000UL,
+	/* 0x0148, */ 0x0000000000000000UL,
+	/* 0x0150, */ 0x0000000000000000UL,
+	/* 0x0158, */ 0x0000000000000000UL,
+	/* 0x0160, */ 0x0000000000000000UL,
+	/* 0x0168, */ 0x0000000000000000UL,
+	/* 0x0170, */ 0x0000000000000000UL,
+	/* 0x0178, */ 0x0000000000000000UL,
+	/* 0x0180, */ 0x0000000000000000UL,
+	/* 0x0188, */ 0x0000000000000000UL,
+	/* 0x0190, */ 0x0000000000000000UL,
+	/* 0x0198, */ 0x0000000000000000UL,
+	/* 0x01a0, */ 0x0000000000000000UL,
+	/* 0x01a8, */ 0x0000000000000000UL,
+	/* 0x01b0, */ 0x0000000000000000UL,
+	/* 0x01b8, */ 0x0000000000000000UL,
+	/* 0x01c0, */ 0x0000000000000000UL,
+	/* 0x01c8, */ 0x0000000000000000UL,
+	/* 0x01d0, */ 0x0000000000000000UL,
+	/* 0x01d8, */ 0x0000000000000000UL,
+	/* 0x01e0, */ 0x0000000000000000UL,
+	/* 0x01e8, */ 0x0000000000000000UL,
+	/* 0x01f0, */ 0x0000000000000000UL,
+	/* 0x01f8, */ 0x0000000000000000UL,
+	/* 0x0200, */ 0x0000000000000000UL,
+	/* 0x0208, */ 0x0000000000000000UL,
+	/* 0x0210, */ 0x0000000000000000UL,
+	/* 0x0218, */ 0x0000000000000000UL,
+	/* 0x0220, */ 0x0000000000000000UL,
+	/* 0x0228, */ 0x0000000000000000UL,
+	/* 0x0230, */ 0x0000000000000000UL,
+	/* 0x0238, */ 0x0000000000000000UL,
+	/* 0x0240, */ 0x0000000000000000UL,
+	/* 0x0248, */ 0x0000000000000000UL,
+	/* 0x0250, */ 0x0000000000000000UL,
+	/* 0x0258, */ 0x0000000000000000UL,
+	/* 0x0260, */ 0x0000000000000000UL,
+	/* 0x0268, */ 0x0000000000000000UL,
+	/* 0x0270, */ 0x0000000000000000UL,
+	/* 0x0278, */ 0x0000000000000000UL,
+	/* 0x0280, */ 0x0000000000000000UL,
+	/* 0x0288, */ 0x0000000000000000UL,
+	/* 0x0290, */ 0x0000000000000000UL,
+	/* 0x0298, */ 0x0000000000000000UL,
+	/* 0x02a0, */ 0x0000000000000000UL,
+	/* 0x02a8, */ 0x0000000000000000UL,
+	/* 0x02b0, */ 0x0000000000000000UL,
+	/* 0x02b8, */ 0x0000000000000000UL,
+	/* 0x02c0, */ 0x0000000000000000UL,
+	/* 0x02c8, */ 0x0000000000000000UL,
+	/* 0x02d0, */ 0x0000000000000000UL,
+	/* 0x02d8, */ 0x0000000000000000UL,
+	/* 0x02e0, */ 0x0000000000000000UL,
+	/* 0x02e8, */ 0x0000000000000000UL,
+	/* 0x02f0, */ 0x0000000000000000UL,
+	/* 0x02f8, */ 0x0000000000000000UL,
+	/* 0x0300, */ 0x0000000000000000UL,
+	/* 0x0308, */ 0x0000000000000000UL,
+	/* 0x0310, */ 0x0000000000000000UL,
+	/* 0x0318, */ 0x0000000000000000UL,
+	/* 0x0320, */ 0x0000000000000000UL,
+	/* 0x0328, */ 0x0000000000000000UL,
+	/* 0x0330, */ 0x0000000000000000UL,
+	/* 0x0338, */ 0x0000000000000000UL,
+	/* 0x0340, */ 0x0000000000000000UL,
+	/* 0x0348, */ 0x0000000000000000UL,
+	/* 0x0350, */ 0x0000000000000000UL,
+	/* 0x0358, */ 0x0000000000000000UL,
+	/* 0x0360, */ 0x0000000000000000UL,
+	/* 0x0368, */ 0x0000000000000000UL,
+	/* 0x0370, */ 0x0000000000000000UL,
+	/* 0x0378, */ 0x0000000000000000UL,
+	/* 0x0380, */ 0x0000000000000000UL,
+	/* 0x0388, */ 0x0000000000000000UL,
+	/* 0x0390, */ 0x0000000000000000UL,
+};
+#endif /* QOS_INIT_G2N_QOSWT390_H */
diff --git a/drivers/renesas/rzg/qos/qos.mk b/drivers/renesas/rzg/qos/qos.mk
new file mode 100644
index 0000000..f05d126
--- /dev/null
+++ b/drivers/renesas/rzg/qos/qos.mk
@@ -0,0 +1,60 @@
+#
+# Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${RCAR_LSI},${RCAR_AUTO})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
+else ifeq (${RCAR_LSI_CUT_COMPAT},1)
+  ifeq (${RCAR_LSI},${RZ_G2M})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2H})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2N})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2E})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c
+  endif
+else
+  ifeq (${RCAR_LSI},${RZ_G2M})
+    ifeq (${LSI_CUT},10)
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v10.c
+    else ifeq (${LSI_CUT},11)
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
+    else ifeq (${LSI_CUT},13)
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v11.c
+    else ifeq (${LSI_CUT},30)
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
+    else
+#    LSI_CUT 30 or later
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2M/qos_init_g2m_v30.c
+    endif
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2H})
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2H/qos_init_g2h_v30.c
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2N})
+    ifeq (${LSI_CUT},10)
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
+    else
+#    LSI_CUT 10 or later
+     BL2_SOURCES += drivers/renesas/rzg/qos/G2N/qos_init_g2n_v10.c
+    endif
+  endif
+  ifeq (${RCAR_LSI},${RZ_G2E})
+    BL2_SOURCES += drivers/renesas/rzg/qos/G2E/qos_init_g2e_v10.c
+  endif
+endif
+
+BL2_SOURCES += drivers/renesas/rzg/qos/qos_init.c
diff --git a/drivers/renesas/rzg/qos/qos_common.h b/drivers/renesas/rzg/qos/qos_common.h
new file mode 100644
index 0000000..535bf4c
--- /dev/null
+++ b/drivers/renesas/rzg/qos/qos_common.h
@@ -0,0 +1,105 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QOS_COMMON_H
+#define QOS_COMMON_H
+
+#define RCAR_REF_DEFAULT		0U
+
+/* define used for get_refperiod. */
+/* REFPERIOD_CYCLE need smaller than QOSWT_WTSET0_CYCLEs */
+#if (RCAR_REF_INT == RCAR_REF_DEFAULT)	/* REF default */
+#define REFPERIOD_CYCLE		/* unit:ns */	\
+	((126U * BASE_SUB_SLOT_NUM * 1000U) / 400U)
+#else					/* REF option */
+#define REFPERIOD_CYCLE		/* unit:ns */	\
+	((252U * BASE_SUB_SLOT_NUM * 1000U) / 400U)
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M)
+/* define used for G2M */
+#if (RCAR_REF_INT == RCAR_REF_DEFAULT)	/* REF 1.95usec */
+#define SUB_SLOT_CYCLE_G2M_11		0x7EU	/* 126 */
+#define SUB_SLOT_CYCLE_G2M_30		0x7EU	/* 126 */
+#else /* REF 3.9usec */
+#define SUB_SLOT_CYCLE_G2M_11		0xFCU	/* 252 */
+#define SUB_SLOT_CYCLE_G2M_30		0xFCU	/* 252 */
+#endif /* (RCAR_REF_INT == RCAR_REF_DEFAULT) */
+
+#define SL_INIT_SSLOTCLK_G2M_11		(SUB_SLOT_CYCLE_G2M_11 - 1U)
+#define SL_INIT_SSLOTCLK_G2M_30		(SUB_SLOT_CYCLE_G2M_30 - 1U)
+#define QOSWT_WTSET0_CYCLE_G2M_11	/* unit:ns */	\
+	((SUB_SLOT_CYCLE_G2M_11 * BASE_SUB_SLOT_NUM * 1000U) / OPERATING_FREQ)
+#define QOSWT_WTSET0_CYCLE_G2M_30	/* unit:ns */	\
+	((SUB_SLOT_CYCLE_G2M_30 * BASE_SUB_SLOT_NUM * 1000U) / OPERATING_FREQ)
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2N)
+/* define used for G2N */
+#if (RCAR_REF_INT == RCAR_REF_DEFAULT)	/* REF 1.95usec */
+#define SUB_SLOT_CYCLE_G2N		0x7EU	/* 126 */
+#else /* REF 3.9usec */
+#define SUB_SLOT_CYCLE_G2N		0xFCU	/* 252 */
+#endif /* (RCAR_REF_INT == RCAR_REF_DEFAULT) */
+
+#define SL_INIT_SSLOTCLK_G2N		(SUB_SLOT_CYCLE_G2N - 1U)
+#define QOSWT_WTSET0_CYCLE_G2N		/* unit:ns */	\
+	((SUB_SLOT_CYCLE_G2N * BASE_SUB_SLOT_NUM * 1000U) / OPERATING_FREQ)
+#endif /* (RCAR_LSI == RZ_G2N) */
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2H)
+/* define used for G2H */
+#if (RCAR_REF_INT == RCAR_REF_DEFAULT)	/* REF 1.95usec */
+#define SUB_SLOT_CYCLE_G2H		0x7EU	/* 126 */
+#else /* REF 3.9usec */
+#define SUB_SLOT_CYCLE_G2H		0xFCU	/* 252 */
+#endif /* (RCAR_REF_INT == RCAR_REF_DEFAULT) */
+
+#define SL_INIT_SSLOTCLK_G2H		(SUB_SLOT_CYCLE_G2H - 1U)
+#define QOSWT_WTSET0_CYCLE_G2H		/* unit:ns */	\
+	((SUB_SLOT_CYCLE_G2H * BASE_SUB_SLOT_NUM * 1000U) / OPERATING_FREQ)
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2E)
+/* define used for G2E */
+#if (RCAR_REF_INT == RCAR_REF_DEFAULT)	/* REF 3.9usec */
+#define SUB_SLOT_CYCLE_G2E		0xAFU	/* 175 */
+#else /* REF 7.8usec */
+#define SUB_SLOT_CYCLE_G2E		0x15EU	/* 350 */
+#endif /* (RCAR_REF_INT == RCAR_REF_DEFAULT) */
+
+#define OPERATING_FREQ_G2E		266U	/* MHz */
+#define SL_INIT_SSLOTCLK_G2E		(SUB_SLOT_CYCLE_G2E - 1U)
+#endif
+
+#define OPERATING_FREQ			400U	/* MHz */
+#define BASE_SUB_SLOT_NUM		0x6U
+#define SUB_SLOT_CYCLE			0x7EU	/* 126 */
+
+#define QOSWT_WTSET0_CYCLE		/* unit:ns */	\
+	((SUB_SLOT_CYCLE * BASE_SUB_SLOT_NUM * 1000U) / OPERATING_FREQ)
+
+#define SL_INIT_REFFSSLOT		(0x3U << 24U)
+#define SL_INIT_SLOTSSLOT		((BASE_SUB_SLOT_NUM - 1U) << 16U)
+#define SL_INIT_SSLOTCLK		(SUB_SLOT_CYCLE - 1U)
+
+typedef struct {
+	uintptr_t addr;
+	uint64_t value;
+} mstat_slot_t;
+
+struct rcar_gen3_dbsc_qos_settings {
+	uint32_t	reg;
+	uint32_t	val;
+};
+
+extern uint32_t qos_init_ddr_ch;
+extern uint8_t qos_init_ddr_phyvalid;
+
+void rzg_qos_dbsc_setting(const struct rcar_gen3_dbsc_qos_settings *qos,
+			  unsigned int qos_size, bool dbsc_wren);
+
+#endif /* QOS_COMMON_H */
diff --git a/drivers/renesas/rzg/qos/qos_init.c b/drivers/renesas/rzg/qos/qos_init.c
new file mode 100644
index 0000000..e527a61
--- /dev/null
+++ b/drivers/renesas/rzg/qos/qos_init.c
@@ -0,0 +1,267 @@
+/*
+ * Copyright (c) 2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#if RCAR_LSI == RCAR_AUTO
+#include "G2E/qos_init_g2e_v10.h"
+#include "G2H/qos_init_g2h_v30.h"
+#include "G2M/qos_init_g2m_v10.h"
+#include "G2M/qos_init_g2m_v11.h"
+#include "G2M/qos_init_g2m_v30.h"
+#include "G2N/qos_init_g2n_v10.h"
+#endif /* RCAR_LSI == RCAR_AUTO */
+#if (RCAR_LSI == RZ_G2M)
+#include "G2M/qos_init_g2m_v10.h"
+#include "G2M/qos_init_g2m_v11.h"
+#include "G2M/qos_init_g2m_v30.h"
+#endif /* RCAR_LSI == RZ_G2M */
+#if RCAR_LSI == RZ_G2H
+#include "G2H/qos_init_g2h_v30.h"
+#endif /* RCAR_LSI == RZ_G2H */
+#if RCAR_LSI == RZ_G2N
+#include "G2N/qos_init_g2n_v10.h"
+#endif /* RCAR_LSI == RZ_G2N */
+#if RCAR_LSI == RZ_G2E
+#include "G2E/qos_init_g2e_v10.h"
+#endif /* RCAR_LSI == RZ_G2E */
+#include "qos_common.h"
+#include "qos_init.h"
+#include "qos_reg.h"
+#include "rcar_def.h"
+
+#if (RCAR_LSI != RZ_G2E)
+#define DRAM_CH_CNT	0x04U
+uint32_t qos_init_ddr_ch;
+uint8_t qos_init_ddr_phyvalid;
+#endif /* RCAR_LSI != RZ_G2E */
+
+#define PRR_PRODUCT_ERR(reg)				\
+	{						\
+		ERROR("LSI Product ID(PRR=0x%x) QoS "	\
+		"initialize not supported.\n", reg);	\
+		panic();				\
+	}
+
+#define PRR_CUT_ERR(reg)				\
+	{						\
+		ERROR("LSI Cut ID(PRR=0x%x) QoS "	\
+		"initialize not supported.\n", reg);	\
+		panic();				\
+	}
+
+void rzg_qos_init(void)
+{
+	uint32_t reg;
+#if (RCAR_LSI != RZ_G2E)
+	uint32_t i;
+
+	qos_init_ddr_ch = 0U;
+	qos_init_ddr_phyvalid = get_boardcnf_phyvalid();
+	for (i = 0U; i < DRAM_CH_CNT; i++) {
+		if ((qos_init_ddr_phyvalid & (1U << i))) {
+			qos_init_ddr_ch++;
+		}
+	}
+#endif /* RCAR_LSI != RZ_G2E */
+
+	reg = mmio_read_32(PRR);
+#if (RCAR_LSI == RCAR_AUTO) || RCAR_LSI_CUT_COMPAT
+	switch (reg & PRR_PRODUCT_MASK) {
+	case PRR_PRODUCT_M3:
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M)
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_10:
+			qos_init_g2m_v10();
+			break;
+		case PRR_PRODUCT_21: /* G2M Cut 13 */
+			qos_init_g2m_v11();
+			break;
+		case PRR_PRODUCT_30: /* G2M Cut 30 */
+		default:
+			qos_init_g2m_v30();
+			break;
+		}
+#else /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M) */
+		PRR_PRODUCT_ERR(reg);
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M) */
+		break;
+	case PRR_PRODUCT_H3:
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2H)
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_30:
+		default:
+			qos_init_g2h_v30();
+			break;
+		}
+#else
+		PRR_PRODUCT_ERR(reg);
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2H) */
+		break;
+	case PRR_PRODUCT_M3N:
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2N)
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_10:
+		default:
+			qos_init_g2n_v10();
+			break;
+		}
+#else
+		PRR_PRODUCT_ERR(reg);
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2N) */
+		break;
+	case PRR_PRODUCT_E3:
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2E)
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_10:
+		default:
+			qos_init_g2e_v10();
+			break;
+		}
+#else
+		PRR_PRODUCT_ERR(reg);
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2E) */
+		break;
+	default:
+		PRR_PRODUCT_ERR(reg);
+		break;
+	}
+#else /* RCAR_LSI == RCAR_AUTO || RCAR_LSI_CUT_COMPAT */
+#if (RCAR_LSI == RZ_G2M)
+#if RCAR_LSI_CUT == RCAR_CUT_10
+	/* G2M Cut 10 */
+	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_10)
+	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2m_v10();
+#elif RCAR_LSI_CUT == RCAR_CUT_11
+	/* G2M Cut 11 */
+	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_20)
+	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2m_v11();
+#elif RCAR_LSI_CUT == RCAR_CUT_13
+	/* G2M Cut 13 */
+	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_21)
+	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2m_v11();
+#else
+	/* G2M Cut 30 or later */
+	if ((PRR_PRODUCT_M3)
+	    != (reg & (PRR_PRODUCT_MASK))) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2m_v30();
+#endif /* RCAR_LSI_CUT == RCAR_CUT_10 */
+#elif (RCAR_LSI == RZ_G2H)
+	/* G2H Cut 30 or later */
+	if ((reg & PRR_PRODUCT_MASK) != PRR_PRODUCT_H3) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2h_v30();
+#elif (RCAR_LSI == RZ_G2N)
+	/* G2N Cut 10 or later */
+	if ((reg & (PRR_PRODUCT_MASK)) != PRR_PRODUCT_M3N) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2n_v10();
+#elif RCAR_LSI == RZ_G2E
+	/* G2E Cut 10 or later */
+	if ((reg & (PRR_PRODUCT_MASK)) != PRR_PRODUCT_E3) {
+		PRR_PRODUCT_ERR(reg);
+	}
+	qos_init_g2e_v10();
+#else /* (RCAR_LSI == RZ_G2M) */
+#error "Don't have QoS initialize routine(Unknown chip)."
+#endif /* (RCAR_LSI == RZ_G2M) */
+#endif /* RCAR_LSI == RCAR_AUTO || RCAR_LSI_CUT_COMPAT */
+}
+
+#if (RCAR_LSI != RZ_G2E)
+uint32_t get_refperiod(void)
+{
+	uint32_t refperiod = QOSWT_WTSET0_CYCLE;
+
+#if (RCAR_LSI == RCAR_AUTO) || RCAR_LSI_CUT_COMPAT
+	uint32_t reg;
+
+	reg = mmio_read_32(PRR);
+	switch (reg & PRR_PRODUCT_MASK) {
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M)
+	case PRR_PRODUCT_M3:
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_10:
+			break;
+		case PRR_PRODUCT_20: /* G2M Cut 11 */
+		case PRR_PRODUCT_21: /* G2M Cut 13 */
+		case PRR_PRODUCT_30: /* G2M Cut 30 */
+		default:
+			refperiod = REFPERIOD_CYCLE;
+			break;
+		}
+		break;
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2M) */
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2H)
+	case PRR_PRODUCT_H3:
+		switch (reg & PRR_CUT_MASK) {
+		case PRR_PRODUCT_30:
+		default:
+			refperiod = REFPERIOD_CYCLE;
+			break;
+		}
+		break;
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2H) */
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2N)
+	case PRR_PRODUCT_M3N:
+		refperiod = REFPERIOD_CYCLE;
+		break;
+#endif /* (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RZ_G2N) */
+	default:
+		break;
+	}
+#elif RCAR_LSI == RZ_G2M
+#if RCAR_LSI_CUT == RCAR_CUT_10
+	/* G2M Cut 10 */
+#else /* RCAR_LSI_CUT == RCAR_CUT_10 */
+	/* G2M Cut 11|13|30 or later */
+	refperiod = REFPERIOD_CYCLE;
+#endif /* RCAR_LSI_CUT == RCAR_CUT_10 */
+#elif RCAR_LSI == RZ_G2N
+	refperiod = REFPERIOD_CYCLE;
+#elif RCAR_LSI == RZ_G2H
+	/* G2H Cut 30 or later */
+	refperiod = REFPERIOD_CYCLE;
+#endif /* RCAR_LSI == RCAR_AUTO || RCAR_LSI_CUT_COMPAT */
+	return refperiod;
+}
+#endif /* RCAR_LSI != RZ_G2E */
+
+void rzg_qos_dbsc_setting(const struct rcar_gen3_dbsc_qos_settings *qos,
+			  unsigned int qos_size, bool dbsc_wren)
+{
+	unsigned int i;
+
+	/* Register write enable */
+	if (dbsc_wren) {
+		mmio_write_32(DBSC_DBSYSCNT0, 0x00001234U);
+	}
+
+	for (i = 0; i < qos_size; i++) {
+		mmio_write_32(qos[i].reg, qos[i].val);
+	}
+
+	/* Register write protect */
+	if (dbsc_wren) {
+		mmio_write_32(DBSC_DBSYSCNT0, 0x00000000U);
+	}
+}
diff --git a/drivers/renesas/rzg/qos/qos_init.h b/drivers/renesas/rzg/qos/qos_init.h
new file mode 100644
index 0000000..3d62744
--- /dev/null
+++ b/drivers/renesas/rzg/qos/qos_init.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RZG_QOS_INIT_H
+#define RZG_QOS_INIT_H
+
+void rzg_qos_init(void);
+uint8_t get_boardcnf_phyvalid(void);
+
+#endif /* RZG_QOS_INIT_H */
diff --git a/drivers/scmi-msg/base.c b/drivers/scmi-msg/base.c
new file mode 100644
index 0000000..2d72034
--- /dev/null
+++ b/drivers/scmi-msg/base.c
@@ -0,0 +1,198 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#include <assert.h>
+#include <string.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+#include <lib/utils.h>
+#include <lib/utils_def.h>
+
+#include "common.h"
+
+static bool message_id_is_supported(unsigned int message_id);
+
+static void report_version(struct scmi_msg *msg)
+{
+	struct scmi_protocol_version_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.version = SCMI_PROTOCOL_VERSION_BASE,
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_attributes(struct scmi_msg *msg)
+{
+	size_t protocol_count = plat_scmi_protocol_count();
+	struct scmi_protocol_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		/* Null agent count since agent discovery is not supported */
+		.attributes = SCMI_BASE_PROTOCOL_ATTRIBUTES(protocol_count, 0U),
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_message_attributes(struct scmi_msg *msg)
+{
+	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_protocol_message_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		/* For this protocol, attributes shall be zero */
+		.attributes = 0U,
+	};
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	if (!message_id_is_supported(in_args->message_id)) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void discover_vendor(struct scmi_msg *msg)
+{
+	const char *name = plat_scmi_vendor_name();
+	struct scmi_base_discover_vendor_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	COPY_NAME_IDENTIFIER(return_values.vendor_identifier, name);
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void discover_sub_vendor(struct scmi_msg *msg)
+{
+	const char *name = plat_scmi_sub_vendor_name();
+	struct scmi_base_discover_sub_vendor_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	COPY_NAME_IDENTIFIER(return_values.sub_vendor_identifier, name);
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void discover_implementation_version(struct scmi_msg *msg)
+{
+	struct scmi_protocol_version_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.version = SCMI_IMPL_VERSION,
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static unsigned int count_protocols_in_list(const uint8_t *protocol_list)
+{
+	unsigned int count = 0U;
+
+	if (protocol_list != NULL) {
+		while (protocol_list[count] != 0U) {
+			count++;
+		}
+	}
+
+	return count;
+}
+
+#define MAX_PROTOCOL_IN_LIST		8U
+
+static void discover_list_protocols(struct scmi_msg *msg)
+{
+	const struct scmi_base_discover_list_protocols_a2p *a2p = NULL;
+	struct scmi_base_discover_list_protocols_p2a p2a = {
+		.status = SCMI_SUCCESS,
+	};
+	uint8_t outargs[sizeof(p2a) + MAX_PROTOCOL_IN_LIST] = { 0U };
+	const uint8_t *list = NULL;
+	unsigned int count = 0U;
+
+	if (msg->in_size != sizeof(*a2p)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	assert(msg->out_size > sizeof(outargs));
+
+	a2p = (void *)msg->in;
+
+	list = plat_scmi_protocol_list(msg->agent_id);
+	count = count_protocols_in_list(list);
+	if (count > a2p->skip) {
+		count = MIN(count - a2p->skip, MAX_PROTOCOL_IN_LIST);
+	} else {
+		count = 0U;
+	}
+
+	p2a.num_protocols = count;
+
+	memcpy(outargs, &p2a, sizeof(p2a));
+	memcpy(outargs + sizeof(p2a), list + a2p->skip, count);
+
+	scmi_write_response(msg, outargs, sizeof(outargs));
+}
+
+static const scmi_msg_handler_t scmi_base_handler_table[] = {
+	[SCMI_PROTOCOL_VERSION] = report_version,
+	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
+	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
+	[SCMI_BASE_DISCOVER_VENDOR] = discover_vendor,
+	[SCMI_BASE_DISCOVER_SUB_VENDOR] = discover_sub_vendor,
+	[SCMI_BASE_DISCOVER_IMPLEMENTATION_VERSION] =
+					discover_implementation_version,
+	[SCMI_BASE_DISCOVER_LIST_PROTOCOLS] = discover_list_protocols,
+};
+
+static bool message_id_is_supported(unsigned int message_id)
+{
+	return (message_id < ARRAY_SIZE(scmi_base_handler_table)) &&
+	       (scmi_base_handler_table[message_id] != NULL);
+}
+
+scmi_msg_handler_t scmi_msg_get_base_handler(struct scmi_msg *msg)
+{
+	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
+
+	if (message_id >= ARRAY_SIZE(scmi_base_handler_table)) {
+		VERBOSE("Base handle not found %u\n", msg->message_id);
+		return NULL;
+	}
+
+	return scmi_base_handler_table[message_id];
+}
diff --git a/drivers/st/scmi-msg/base.h b/drivers/scmi-msg/base.h
similarity index 100%
rename from drivers/st/scmi-msg/base.h
rename to drivers/scmi-msg/base.h
diff --git a/drivers/scmi-msg/clock.c b/drivers/scmi-msg/clock.c
new file mode 100644
index 0000000..e96cede
--- /dev/null
+++ b/drivers/scmi-msg/clock.c
@@ -0,0 +1,381 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#include <cdefs.h>
+#include <string.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+#include <lib/utils_def.h>
+
+#include "common.h"
+
+#pragma weak plat_scmi_clock_count
+#pragma weak plat_scmi_clock_get_name
+#pragma weak plat_scmi_clock_rates_array
+#pragma weak plat_scmi_clock_rates_by_step
+#pragma weak plat_scmi_clock_get_rate
+#pragma weak plat_scmi_clock_set_rate
+#pragma weak plat_scmi_clock_get_state
+#pragma weak plat_scmi_clock_set_state
+
+static bool message_id_is_supported(unsigned int message_id);
+
+size_t plat_scmi_clock_count(unsigned int agent_id __unused)
+{
+	return 0U;
+}
+
+const char *plat_scmi_clock_get_name(unsigned int agent_id __unused,
+				     unsigned int scmi_id __unused)
+{
+	return NULL;
+}
+
+int32_t plat_scmi_clock_rates_array(unsigned int agent_id __unused,
+				    unsigned int scmi_id __unused,
+				    unsigned long *rates __unused,
+				    size_t *nb_elts __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+int32_t plat_scmi_clock_rates_by_step(unsigned int agent_id __unused,
+				      unsigned int scmi_id __unused,
+				      unsigned long *steps __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+unsigned long plat_scmi_clock_get_rate(unsigned int agent_id __unused,
+				       unsigned int scmi_id __unused)
+{
+	return 0U;
+}
+
+int32_t plat_scmi_clock_set_rate(unsigned int agent_id __unused,
+				 unsigned int scmi_id __unused,
+				 unsigned long rate __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+int32_t plat_scmi_clock_get_state(unsigned int agent_id __unused,
+				  unsigned int scmi_id __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+int32_t plat_scmi_clock_set_state(unsigned int agent_id __unused,
+				  unsigned int scmi_id __unused,
+				  bool enable_not_disable __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+static void report_version(struct scmi_msg *msg)
+{
+	struct scmi_protocol_version_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.version = SCMI_PROTOCOL_VERSION_CLOCK,
+	};
+
+	if (msg->in_size != 0) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_attributes(struct scmi_msg *msg)
+{
+	size_t agent_count = plat_scmi_clock_count(msg->agent_id);
+	struct scmi_protocol_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.attributes = SCMI_CLOCK_PROTOCOL_ATTRIBUTES(1U, agent_count),
+	};
+
+	if (msg->in_size != 0) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_message_attributes(struct scmi_msg *msg)
+{
+	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_protocol_message_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		/* For this protocol, attributes shall be zero */
+		.attributes = 0U,
+	};
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	if (!message_id_is_supported(in_args->message_id)) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_clock_attributes(struct scmi_msg *msg)
+{
+	const struct scmi_clock_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_clock_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+	const char *name = NULL;
+	unsigned int clock_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
+
+	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+
+	name = plat_scmi_clock_get_name(msg->agent_id, clock_id);
+	if (name == NULL) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	COPY_NAME_IDENTIFIER(return_values.clock_name, name);
+
+	return_values.attributes = plat_scmi_clock_get_state(msg->agent_id,
+							     clock_id);
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_clock_rate_get(struct scmi_msg *msg)
+{
+	const struct scmi_clock_rate_get_a2p *in_args = (void *)msg->in;
+	unsigned long rate = 0U;
+	struct scmi_clock_rate_get_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+	unsigned int clock_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
+
+	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	rate = plat_scmi_clock_get_rate(msg->agent_id, clock_id);
+
+	return_values.rate[0] = (uint32_t)rate;
+	return_values.rate[1] = (uint32_t)((uint64_t)rate >> 32);
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_clock_rate_set(struct scmi_msg *msg)
+{
+	const struct scmi_clock_rate_set_a2p *in_args = (void *)msg->in;
+	unsigned long rate = 0U;
+	int32_t status = 0;
+	unsigned int clock_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
+
+	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	rate = (unsigned long)(((uint64_t)in_args->rate[1] << 32) |
+			       in_args->rate[0]);
+
+	status = plat_scmi_clock_set_rate(msg->agent_id, clock_id, rate);
+
+	scmi_status_response(msg, status);
+}
+
+static void scmi_clock_config_set(struct scmi_msg *msg)
+{
+	const struct scmi_clock_config_set_a2p *in_args = (void *)msg->in;
+	int32_t status = SCMI_GENERIC_ERROR;
+	bool enable = false;
+	unsigned int clock_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
+
+	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	enable = in_args->attributes & SCMI_CLOCK_CONFIG_SET_ENABLE_MASK;
+
+	status = plat_scmi_clock_set_state(msg->agent_id, clock_id, enable);
+
+	scmi_status_response(msg, status);
+}
+
+#define RATES_ARRAY_SIZE_MAX	(SCMI_PLAYLOAD_MAX - \
+				 sizeof(struct scmi_clock_describe_rates_p2a))
+
+#define SCMI_RATES_BY_ARRAY(_nb_rates, _rem_rates) \
+	SCMI_CLOCK_DESCRIBE_RATES_NUM_RATES_FLAGS((_nb_rates), \
+						SCMI_CLOCK_RATE_FORMAT_LIST, \
+						(_rem_rates))
+#define SCMI_RATES_BY_STEP \
+	SCMI_CLOCK_DESCRIBE_RATES_NUM_RATES_FLAGS(3U, \
+						SCMI_CLOCK_RATE_FORMAT_RANGE, \
+						0U)
+
+#define RATE_DESC_SIZE		sizeof(struct scmi_clock_rate)
+
+static void write_rate_desc_array_in_buffer(char *dest, unsigned long *rates,
+					    size_t nb_elt)
+{
+	uint32_t *out = (uint32_t *)(uintptr_t)dest;
+	size_t n;
+
+	ASSERT_SYM_PTR_ALIGN(out);
+
+	for (n = 0U; n < nb_elt; n++) {
+		out[2 * n] = (uint32_t)rates[n];
+		out[2 * n + 1] = (uint32_t)((uint64_t)rates[n] >> 32);
+	}
+}
+
+static void scmi_clock_describe_rates(struct scmi_msg *msg)
+{
+	const struct scmi_clock_describe_rates_a2p *in_args = (void *)msg->in;
+	struct scmi_clock_describe_rates_p2a p2a = {
+		.status = SCMI_SUCCESS,
+	};
+	size_t nb_rates;
+	int32_t status;
+	unsigned int clock_id;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
+
+	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	/* Platform may support array rate description */
+	status = plat_scmi_clock_rates_array(msg->agent_id, clock_id, NULL,
+					     &nb_rates);
+	if (status == SCMI_SUCCESS) {
+		/* Currently 12 cells mex, so it's affordable for the stack */
+		unsigned long plat_rates[RATES_ARRAY_SIZE_MAX / RATE_DESC_SIZE];
+		size_t max_nb = RATES_ARRAY_SIZE_MAX / RATE_DESC_SIZE;
+		size_t ret_nb = MIN(nb_rates - in_args->rate_index, max_nb);
+		size_t rem_nb = nb_rates - in_args->rate_index - ret_nb;
+
+		status =  plat_scmi_clock_rates_array(msg->agent_id, clock_id,
+						      plat_rates, &ret_nb);
+		if (status == SCMI_SUCCESS) {
+			write_rate_desc_array_in_buffer(msg->out + sizeof(p2a),
+							plat_rates, ret_nb);
+
+			p2a.num_rates_flags = SCMI_RATES_BY_ARRAY(ret_nb,
+								  rem_nb);
+			p2a.status = SCMI_SUCCESS;
+
+			memcpy(msg->out, &p2a, sizeof(p2a));
+			msg->out_size_out = sizeof(p2a) +
+					    ret_nb * RATE_DESC_SIZE;
+		}
+	} else if (status == SCMI_NOT_SUPPORTED) {
+		unsigned long triplet[3] = { 0U, 0U, 0U };
+
+		/* Platform may support min§max/step triplet description */
+		status =  plat_scmi_clock_rates_by_step(msg->agent_id, clock_id,
+							triplet);
+		if (status == SCMI_SUCCESS) {
+			write_rate_desc_array_in_buffer(msg->out + sizeof(p2a),
+							triplet, 3U);
+
+			p2a.num_rates_flags = SCMI_RATES_BY_STEP;
+			p2a.status = SCMI_SUCCESS;
+
+			memcpy(msg->out, &p2a, sizeof(p2a));
+			msg->out_size_out = sizeof(p2a) + (3U * RATE_DESC_SIZE);
+		}
+	} else {
+		/* Fallthrough generic exit sequence below with error status */
+	}
+
+	if (status != SCMI_SUCCESS) {
+		scmi_status_response(msg, status);
+	} else {
+		/*
+		 * Message payload is already writen to msg->out, and
+		 * msg->out_size_out updated.
+		 */
+	}
+}
+
+static const scmi_msg_handler_t scmi_clock_handler_table[] = {
+	[SCMI_PROTOCOL_VERSION] = report_version,
+	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
+	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
+	[SCMI_CLOCK_ATTRIBUTES] = scmi_clock_attributes,
+	[SCMI_CLOCK_DESCRIBE_RATES] = scmi_clock_describe_rates,
+	[SCMI_CLOCK_RATE_SET] = scmi_clock_rate_set,
+	[SCMI_CLOCK_RATE_GET] = scmi_clock_rate_get,
+	[SCMI_CLOCK_CONFIG_SET] = scmi_clock_config_set,
+};
+
+static bool message_id_is_supported(size_t message_id)
+{
+	return (message_id < ARRAY_SIZE(scmi_clock_handler_table)) &&
+	       (scmi_clock_handler_table[message_id] != NULL);
+}
+
+scmi_msg_handler_t scmi_msg_get_clock_handler(struct scmi_msg *msg)
+{
+	const size_t array_size = ARRAY_SIZE(scmi_clock_handler_table);
+	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
+
+	if (message_id >= array_size) {
+		VERBOSE("Clock handle not found %u", msg->message_id);
+		return NULL;
+	}
+
+	return scmi_clock_handler_table[message_id];
+}
diff --git a/drivers/st/scmi-msg/clock.h b/drivers/scmi-msg/clock.h
similarity index 100%
rename from drivers/st/scmi-msg/clock.h
rename to drivers/scmi-msg/clock.h
diff --git a/drivers/scmi-msg/common.h b/drivers/scmi-msg/common.h
new file mode 100644
index 0000000..62f3087
--- /dev/null
+++ b/drivers/scmi-msg/common.h
@@ -0,0 +1,144 @@
+/* SPDX-License-Identifier: BSD-3-Clause */
+/*
+ * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#ifndef SCMI_MSG_COMMON_H
+#define SCMI_MSG_COMMON_H
+
+#include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <string.h>
+
+#include "base.h"
+#include "clock.h"
+#include "power_domain.h"
+#include "reset_domain.h"
+
+#define SCMI_VERSION			0x20000U
+#define SCMI_IMPL_VERSION		0U
+
+#define SCMI_PLAYLOAD_MAX		92U
+
+/*
+ * Copy name identifier in target buffer following the SCMI specification
+ * that state name identifier shall be a null terminated string.
+ */
+#define COPY_NAME_IDENTIFIER(_dst_array, _name)				\
+	do {								\
+		assert(strlen(_name) < sizeof(_dst_array));		\
+		strlcpy((_dst_array), (_name), sizeof(_dst_array));	\
+	} while (0)
+
+/* Common command identifiers shared by all procotols */
+enum scmi_common_message_id {
+	SCMI_PROTOCOL_VERSION = 0x000,
+	SCMI_PROTOCOL_ATTRIBUTES = 0x001,
+	SCMI_PROTOCOL_MESSAGE_ATTRIBUTES = 0x002
+};
+
+/* Common platform-to-agent (p2a) PROTOCOL_VERSION structure */
+struct scmi_protocol_version_p2a {
+	int32_t status;
+	uint32_t version;
+};
+
+/* Generic platform-to-agent (p2a) PROTOCOL_ATTRIBUTES structure */
+struct scmi_protocol_attributes_p2a {
+	int32_t status;
+	uint32_t attributes;
+};
+
+/* Generic agent-to-platform (a2p) PROTOCOL_MESSAGE_ATTRIBUTES structure */
+struct scmi_protocol_message_attributes_a2p {
+	uint32_t message_id;
+};
+
+/* Generic platform-to-agent (p2a) PROTOCOL_MESSAGE_ATTRIBUTES structure */
+struct scmi_protocol_message_attributes_p2a {
+	int32_t status;
+	uint32_t attributes;
+};
+
+/*
+ * struct scmi_msg - SCMI message context
+ *
+ * @agent_id: SCMI agent ID, safely set from secure world
+ * @protocol_id: SCMI protocol ID for the related message, set by caller agent
+ * @message_id: SCMI message ID for the related message, set by caller agent
+ * @in: Address of the incoming message payload copied in secure memory
+ * @in_size: Byte length of the incoming message payload, set by caller agent
+ * @out: Address of of the output message payload message in non-secure memory
+ * @out_size: Byte length of the provisionned output buffer
+ * @out_size_out: Byte length of the output message payload
+ */
+struct scmi_msg {
+	unsigned int agent_id;
+	unsigned int protocol_id;
+	unsigned int message_id;
+	char *in;
+	size_t in_size;
+	char *out;
+	size_t out_size;
+	size_t out_size_out;
+};
+
+/*
+ * Type scmi_msg_handler_t is used by procotol drivers to safely find
+ * the handler function for the incoming message ID.
+ */
+typedef void (*scmi_msg_handler_t)(struct scmi_msg *msg);
+
+/*
+ * scmi_msg_get_base_handler - Return a handler for a base message
+ * @msg - message to process
+ * Return a function handler for the message or NULL
+ */
+scmi_msg_handler_t scmi_msg_get_base_handler(struct scmi_msg *msg);
+
+/*
+ * scmi_msg_get_clock_handler - Return a handler for a clock message
+ * @msg - message to process
+ * Return a function handler for the message or NULL
+ */
+scmi_msg_handler_t scmi_msg_get_clock_handler(struct scmi_msg *msg);
+
+/*
+ * scmi_msg_get_rstd_handler - Return a handler for a reset domain message
+ * @msg - message to process
+ * Return a function handler for the message or NULL
+ */
+scmi_msg_handler_t scmi_msg_get_rstd_handler(struct scmi_msg *msg);
+
+/*
+ * scmi_msg_get_pd_handler - Return a handler for a power domain message
+ * @msg - message to process
+ * Return a function handler for the message or NULL
+ */
+scmi_msg_handler_t scmi_msg_get_pd_handler(struct scmi_msg *msg);
+
+/*
+ * Process Read, process and write response for input SCMI message
+ *
+ * @msg: SCMI message context
+ */
+void scmi_process_message(struct scmi_msg *msg);
+
+/*
+ * Write SCMI response payload to output message shared memory
+ *
+ * @msg: SCMI message context
+ * @payload: Output message payload
+ * @size: Byte size of output message payload
+ */
+void scmi_write_response(struct scmi_msg *msg, void *payload, size_t size);
+
+/*
+ * Write status only SCMI response payload to output message shared memory
+ *
+ * @msg: SCMI message context
+ * @status: SCMI status value returned to caller
+ */
+void scmi_status_response(struct scmi_msg *msg, int32_t status);
+#endif /* SCMI_MSG_COMMON_H */
diff --git a/drivers/scmi-msg/entry.c b/drivers/scmi-msg/entry.c
new file mode 100644
index 0000000..3537fbe
--- /dev/null
+++ b/drivers/scmi-msg/entry.c
@@ -0,0 +1,91 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+
+#include <assert.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+
+#include "common.h"
+
+#pragma weak scmi_msg_get_clock_handler
+#pragma weak scmi_msg_get_rstd_handler
+#pragma weak scmi_msg_get_pd_handler
+#pragma weak scmi_msg_get_voltage_handler
+
+scmi_msg_handler_t scmi_msg_get_clock_handler(struct scmi_msg *msg __unused)
+{
+	return NULL;
+}
+
+scmi_msg_handler_t scmi_msg_get_rstd_handler(struct scmi_msg *msg __unused)
+{
+	return NULL;
+}
+
+scmi_msg_handler_t scmi_msg_get_pd_handler(struct scmi_msg *msg __unused)
+{
+	return NULL;
+}
+
+scmi_msg_handler_t scmi_msg_get_voltage_handler(struct scmi_msg *msg __unused)
+{
+	return NULL;
+}
+
+void scmi_status_response(struct scmi_msg *msg, int32_t status)
+{
+	assert(msg->out && msg->out_size >= sizeof(int32_t));
+
+	memcpy(msg->out, &status, sizeof(int32_t));
+	msg->out_size_out = sizeof(int32_t);
+}
+
+void scmi_write_response(struct scmi_msg *msg, void *payload, size_t size)
+{
+	/*
+	 * Output payload shall be at least the size of the status
+	 * Output buffer shall be at least be the size of the status
+	 * Output paylaod shall fit in output buffer
+	 */
+	assert(payload && size >= sizeof(int32_t) && size <= msg->out_size &&
+	       msg->out && msg->out_size >= sizeof(int32_t));
+
+	memcpy(msg->out, payload, size);
+	msg->out_size_out = size;
+}
+
+void scmi_process_message(struct scmi_msg *msg)
+{
+	scmi_msg_handler_t handler = NULL;
+
+	switch (msg->protocol_id) {
+	case SCMI_PROTOCOL_ID_BASE:
+		handler = scmi_msg_get_base_handler(msg);
+		break;
+	case SCMI_PROTOCOL_ID_CLOCK:
+		handler = scmi_msg_get_clock_handler(msg);
+		break;
+	case SCMI_PROTOCOL_ID_RESET_DOMAIN:
+		handler = scmi_msg_get_rstd_handler(msg);
+		break;
+	case SCMI_PROTOCOL_ID_POWER_DOMAIN:
+		handler = scmi_msg_get_pd_handler(msg);
+		break;
+	default:
+		break;
+	}
+
+	if (handler) {
+		handler(msg);
+		return;
+	}
+
+	ERROR("Agent %u Protocol 0x%x Message 0x%x: not supported",
+	      msg->agent_id, msg->protocol_id, msg->message_id);
+
+	scmi_status_response(msg, SCMI_NOT_SUPPORTED);
+}
diff --git a/drivers/scmi-msg/power_domain.c b/drivers/scmi-msg/power_domain.c
new file mode 100644
index 0000000..c4e1289
--- /dev/null
+++ b/drivers/scmi-msg/power_domain.c
@@ -0,0 +1,239 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#include <cdefs.h>
+#include <string.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+#include <lib/utils_def.h>
+
+#include "common.h"
+
+#pragma weak plat_scmi_pd_count
+#pragma weak plat_scmi_pd_get_name
+#pragma weak plat_scmi_pd_get_state
+#pragma weak plat_scmi_pd_set_state
+#pragma weak plat_scmi_pd_statistics
+#pragma weak plat_scmi_pd_get_attributes
+
+static bool message_id_is_supported(size_t message_id);
+
+size_t plat_scmi_pd_count(unsigned int agent_id __unused)
+{
+	return 0U;
+}
+
+const char *plat_scmi_pd_get_name(unsigned int agent_id __unused,
+				  unsigned int pd_id __unused)
+{
+	return NULL;
+}
+
+unsigned int plat_scmi_pd_statistics(unsigned int agent_id __unused,
+				     unsigned long *pd_id __unused)
+{
+	return 0U;
+}
+
+unsigned int plat_scmi_pd_get_attributes(unsigned int agent_id __unused,
+					 unsigned int pd_id __unused)
+{
+	return 0U;
+}
+
+unsigned int plat_scmi_pd_get_state(unsigned int agent_id __unused,
+				    unsigned int pd_id __unused)
+{
+	return 0U;
+}
+
+int32_t plat_scmi_pd_set_state(unsigned int agent_id __unused,
+			       unsigned int flags __unused,
+			       unsigned int pd_id __unused,
+			       unsigned int state __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+static void report_version(struct scmi_msg *msg)
+{
+	struct scmi_protocol_version_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.version = SCMI_PROTOCOL_VERSION_PD,
+	};
+
+	if (msg->in_size != 0) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_attributes(struct scmi_msg *msg)
+{
+	unsigned long addr = 0UL;
+	unsigned int len;
+
+	struct scmi_protocol_attributes_p2a_pd return_values = {
+		.status = SCMI_SUCCESS,
+	};
+
+	if (msg->in_size != 0) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	return_values.attributes = plat_scmi_pd_count(msg->agent_id);
+	len = plat_scmi_pd_statistics(msg->agent_id, &addr);
+	if (len != 0U) {
+		return_values.statistics_addr_low = (unsigned int)addr;
+		return_values.statistics_addr_high = (uint32_t)(addr >> 32);
+		return_values.statistics_len = len;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_message_attributes(struct scmi_msg *msg)
+{
+	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_protocol_message_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		/* For this protocol, attributes shall be zero */
+		.attributes = 0U,
+	};
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	if (!message_id_is_supported(in_args->message_id)) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_pd_attributes(struct scmi_msg *msg)
+{
+	const struct scmi_pd_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_pd_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+	const char *name = NULL;
+	unsigned int pd_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	pd_id = SPECULATION_SAFE_VALUE(in_args->pd_id);
+
+	if (pd_id >= plat_scmi_pd_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	name = plat_scmi_pd_get_name(msg->agent_id, pd_id);
+	if (name == NULL) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	COPY_NAME_IDENTIFIER(return_values.pd_name, name);
+
+	return_values.attributes = plat_scmi_pd_get_attributes(msg->agent_id, pd_id);
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_pd_state_get(struct scmi_msg *msg)
+{
+	const struct scmi_pd_state_get_a2p *in_args = (void *)msg->in;
+	unsigned int state = 0U;
+	struct scmi_pd_state_get_p2a return_values = {
+		.status = SCMI_SUCCESS,
+	};
+	unsigned int pd_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	pd_id = SPECULATION_SAFE_VALUE(in_args->pd_id);
+
+	if (pd_id >= plat_scmi_pd_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	state = plat_scmi_pd_get_state(msg->agent_id, pd_id);
+
+	return_values.power_state = state;
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void scmi_pd_state_set(struct scmi_msg *msg)
+{
+	const struct scmi_pd_state_set_a2p *in_args = (void *)msg->in;
+	unsigned int flags = 0U;
+	int32_t status = 0;
+	unsigned int pd_id = 0U;
+	unsigned int state = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	pd_id = SPECULATION_SAFE_VALUE(in_args->pd_id);
+
+	if (pd_id >= plat_scmi_pd_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	flags = SPECULATION_SAFE_VALUE(in_args->flags);
+	state = SPECULATION_SAFE_VALUE(in_args->power_state);
+
+	status = plat_scmi_pd_set_state(msg->agent_id, flags, pd_id, state);
+
+	scmi_status_response(msg, status);
+}
+
+static const scmi_msg_handler_t scmi_pd_handler_table[] = {
+	[SCMI_PROTOCOL_VERSION] = report_version,
+	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
+	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
+	[SCMI_PD_ATTRIBUTES] = scmi_pd_attributes,
+	[SCMI_PD_STATE_SET] = scmi_pd_state_set,
+	[SCMI_PD_STATE_GET] = scmi_pd_state_get,
+};
+
+static bool message_id_is_supported(size_t message_id)
+{
+	return (message_id < ARRAY_SIZE(scmi_pd_handler_table)) &&
+	       (scmi_pd_handler_table[message_id] != NULL);
+}
+
+scmi_msg_handler_t scmi_msg_get_pd_handler(struct scmi_msg *msg)
+{
+	const size_t array_size = ARRAY_SIZE(scmi_pd_handler_table);
+	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
+
+	if (message_id >= array_size) {
+		VERBOSE("pd handle not found %u", msg->message_id);
+		return NULL;
+	}
+
+	return scmi_pd_handler_table[message_id];
+}
diff --git a/drivers/scmi-msg/power_domain.h b/drivers/scmi-msg/power_domain.h
new file mode 100644
index 0000000..48551fd
--- /dev/null
+++ b/drivers/scmi-msg/power_domain.h
@@ -0,0 +1,72 @@
+/* SPDX-License-Identifier: BSD-3-Clause */
+/*
+ * Copyright 2021 NXP
+ */
+
+#ifndef SCMI_MSG_PD_H
+#define SCMI_MSG_PD_H
+
+#include <stdint.h>
+
+#include <lib/utils_def.h>
+
+#define SCMI_PROTOCOL_VERSION_PD	0x21000U
+
+/*
+ * Identifiers of the SCMI POWER DOMAIN Protocol commands
+ */
+enum scmi_pd_command_id {
+	SCMI_PD_ATTRIBUTES = 0x003,
+	SCMI_PD_STATE_SET = 0x004,
+	SCMI_PD_STATE_GET = 0x005,
+};
+
+/* Protocol attributes */
+struct scmi_pd_attributes_a2p {
+	uint32_t pd_id;
+};
+
+struct scmi_protocol_attributes_p2a_pd {
+	int32_t status;
+	uint32_t attributes;
+	uint32_t statistics_addr_low;
+	uint32_t statistics_addr_high;
+	uint32_t statistics_len;
+};
+
+#define SCMI_PD_NAME_LENGTH_MAX	16U
+
+struct scmi_pd_attributes_p2a {
+	int32_t status;
+	uint32_t attributes;
+	char pd_name[SCMI_PD_NAME_LENGTH_MAX];
+};
+
+/*
+ * Power Domain State Get
+ */
+
+struct scmi_pd_state_get_a2p {
+	uint32_t pd_id;
+};
+
+struct scmi_pd_state_get_p2a {
+	int32_t status;
+	uint32_t power_state;
+};
+
+/*
+ * Power domain State Set
+ */
+
+struct scmi_pd_state_set_a2p {
+	uint32_t flags;
+	uint32_t pd_id;
+	uint32_t power_state;
+};
+
+struct scmi_pd_state_set_p2a {
+	int32_t status;
+};
+
+#endif /* SCMI_MSG_PD_H */
diff --git a/drivers/scmi-msg/reset_domain.c b/drivers/scmi-msg/reset_domain.c
new file mode 100644
index 0000000..76ac47e
--- /dev/null
+++ b/drivers/scmi-msg/reset_domain.c
@@ -0,0 +1,197 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#include <cdefs.h>
+#include <string.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+#include <lib/utils.h>
+#include <lib/utils_def.h>
+
+#include "common.h"
+
+static bool message_id_is_supported(unsigned int message_id);
+
+#pragma weak plat_scmi_rstd_count
+#pragma weak plat_scmi_rstd_get_name
+#pragma weak plat_scmi_rstd_autonomous
+#pragma weak plat_scmi_rstd_set_state
+
+size_t plat_scmi_rstd_count(unsigned int agent_id __unused)
+{
+	return 0U;
+}
+
+const char *plat_scmi_rstd_get_name(unsigned int agent_id __unused,
+				  unsigned int scmi_id __unused)
+{
+	return NULL;
+}
+
+int32_t plat_scmi_rstd_autonomous(unsigned int agent_id __unused,
+				unsigned int scmi_id __unused,
+				unsigned int state __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+int32_t plat_scmi_rstd_set_state(unsigned int agent_id __unused,
+			       unsigned int scmi_id __unused,
+			       bool assert_not_deassert __unused)
+{
+	return SCMI_NOT_SUPPORTED;
+}
+
+static void report_version(struct scmi_msg *msg)
+{
+	struct scmi_protocol_version_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.version = SCMI_PROTOCOL_VERSION_RESET_DOMAIN,
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_attributes(struct scmi_msg *msg)
+{
+	struct scmi_protocol_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		.attributes = plat_scmi_rstd_count(msg->agent_id),
+	};
+
+	if (msg->in_size != 0U) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void report_message_attributes(struct scmi_msg *msg)
+{
+	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_protocol_message_attributes_p2a return_values = {
+		.status = SCMI_SUCCESS,
+		/* For this protocol, attributes shall be zero */
+		.attributes = 0U,
+	};
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	if (!message_id_is_supported(in_args->message_id)) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void reset_domain_attributes(struct scmi_msg *msg)
+{
+	struct scmi_reset_domain_attributes_a2p *in_args = (void *)msg->in;
+	struct scmi_reset_domain_attributes_p2a return_values;
+	const char *name = NULL;
+	unsigned int domain_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	domain_id = SPECULATION_SAFE_VALUE(in_args->domain_id);
+
+	if (domain_id >= plat_scmi_rstd_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
+		return;
+	}
+
+	name = plat_scmi_rstd_get_name(msg->agent_id, domain_id);
+	if (name == NULL) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	zeromem(&return_values, sizeof(return_values));
+	COPY_NAME_IDENTIFIER(return_values.name, name);
+	return_values.status = SCMI_SUCCESS;
+	return_values.flags = 0U; /* Async and Notif are not supported */
+	return_values.latency = SCMI_RESET_DOMAIN_ATTR_UNK_LAT;
+
+	scmi_write_response(msg, &return_values, sizeof(return_values));
+}
+
+static void reset_request(struct scmi_msg *msg)
+{
+	struct scmi_reset_domain_request_a2p *in_args = (void *)msg->in;
+	struct scmi_reset_domain_request_p2a out_args = {
+		.status = SCMI_SUCCESS,
+	};
+	unsigned int domain_id = 0U;
+
+	if (msg->in_size != sizeof(*in_args)) {
+		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
+		return;
+	}
+
+	domain_id = SPECULATION_SAFE_VALUE(in_args->domain_id);
+
+	if (domain_id >= plat_scmi_rstd_count(msg->agent_id)) {
+		scmi_status_response(msg, SCMI_NOT_FOUND);
+		return;
+	}
+
+	if ((in_args->flags & SCMI_RESET_DOMAIN_AUTO) != 0U) {
+		out_args.status = plat_scmi_rstd_autonomous(msg->agent_id,
+							  domain_id,
+							  in_args->reset_state);
+	} else if ((in_args->flags & SCMI_RESET_DOMAIN_EXPLICIT) != 0U) {
+		out_args.status = plat_scmi_rstd_set_state(msg->agent_id,
+							 domain_id, true);
+	} else {
+		out_args.status = plat_scmi_rstd_set_state(msg->agent_id,
+							 domain_id, false);
+	}
+
+	if (out_args.status != SCMI_SUCCESS) {
+		scmi_status_response(msg, out_args.status);
+	} else {
+		scmi_write_response(msg, &out_args, sizeof(out_args));
+	}
+}
+
+static const scmi_msg_handler_t scmi_rstd_handler_table[] = {
+	[SCMI_PROTOCOL_VERSION] = report_version,
+	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
+	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
+	[SCMI_RESET_DOMAIN_ATTRIBUTES] = reset_domain_attributes,
+	[SCMI_RESET_DOMAIN_REQUEST] = reset_request,
+};
+
+static bool message_id_is_supported(unsigned int message_id)
+{
+	return (message_id < ARRAY_SIZE(scmi_rstd_handler_table)) &&
+	       (scmi_rstd_handler_table[message_id] != NULL);
+}
+
+scmi_msg_handler_t scmi_msg_get_rstd_handler(struct scmi_msg *msg)
+{
+	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
+
+	if (message_id >= ARRAY_SIZE(scmi_rstd_handler_table)) {
+		VERBOSE("Reset domain handle not found %u\n", msg->message_id);
+		return NULL;
+	}
+
+	return scmi_rstd_handler_table[message_id];
+}
diff --git a/drivers/st/scmi-msg/reset_domain.h b/drivers/scmi-msg/reset_domain.h
similarity index 100%
rename from drivers/st/scmi-msg/reset_domain.h
rename to drivers/scmi-msg/reset_domain.h
diff --git a/drivers/scmi-msg/smt.c b/drivers/scmi-msg/smt.c
new file mode 100644
index 0000000..9b079c7
--- /dev/null
+++ b/drivers/scmi-msg/smt.c
@@ -0,0 +1,206 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2020, Linaro Limited
+ */
+#include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
+#include <lib/cassert.h>
+#include <lib/mmio.h>
+#include <lib/spinlock.h>
+#include <lib/utils.h>
+#include <plat/common/platform.h>
+
+#include "common.h"
+
+/* Legacy SMT/SCMI messages are 128 bytes at most including SMT header */
+#define SCMI_PLAYLOAD_MAX		92U
+#define SCMI_PLAYLOAD_U32_MAX		(SCMI_PLAYLOAD_MAX / sizeof(uint32_t))
+
+/**
+ * struct smt_header - SMT formatted header for SMT base shared memory transfer
+ *
+ * @status: Bit flags, see SMT_STATUS_*
+ * @flags: Bit flags, see SMT_FLAG_*
+ * @length: Byte size of message payload (variable) + ::message_header (32bit)
+ * payload: SCMI message payload data
+ */
+struct smt_header {
+	uint32_t reserved0;
+	uint32_t status;
+	uint64_t reserved1;
+	uint32_t flags;
+	uint32_t length; /* message_header + payload */
+	uint32_t message_header;
+	uint32_t payload[];
+};
+
+CASSERT(SCMI_PLAYLOAD_MAX + sizeof(struct smt_header) <= SMT_BUF_SLOT_SIZE,
+	assert_scmi_message_max_length_fits_in_smt_buffer_slot);
+
+/* Flag set in smt_header::status when SMT does not contain pending message */
+#define SMT_STATUS_FREE			BIT_32(0)
+/* Flag set in smt_header::status when SMT reports an error */
+#define SMT_STATUS_ERROR		BIT_32(1)
+
+/* Flag set in smt_header::flags when SMT uses interrupts */
+#define SMT_FLAG_INTR_ENABLED		BIT_32(1)
+
+/* Bit fields packed in smt_header::message_header */
+#define SMT_MSG_ID_MASK			GENMASK_32(7, 0)
+#define SMT_HDR_MSG_ID(_hdr)		((_hdr) & SMT_MSG_ID_MASK)
+
+#define SMT_MSG_TYPE_MASK		GENMASK_32(9, 8)
+#define SMT_HDR_TYPE_ID(_hdr)		(((_hdr) & SMT_MSG_TYPE_MASK) >> 8)
+
+#define SMT_MSG_PROT_ID_MASK		GENMASK_32(17, 10)
+#define SMT_HDR_PROT_ID(_hdr)		(((_hdr) & SMT_MSG_PROT_ID_MASK) >> 10)
+
+/*
+ * Provision input message payload buffers for fastcall SMC context entries
+ * and for interrupt context execution entries.
+ */
+static uint32_t fast_smc_payload[PLATFORM_CORE_COUNT][SCMI_PLAYLOAD_U32_MAX];
+static uint32_t interrupt_payload[PLATFORM_CORE_COUNT][SCMI_PLAYLOAD_U32_MAX];
+
+/* SMP protection on channel access */
+static struct spinlock smt_channels_lock;
+
+/* If channel is not busy, set busy and return true, otherwise return false */
+static bool channel_set_busy(struct scmi_msg_channel *chan)
+{
+	bool channel_is_busy;
+
+	spin_lock(&smt_channels_lock);
+
+	channel_is_busy = chan->busy;
+
+	if (!channel_is_busy) {
+		chan->busy = true;
+	}
+
+	spin_unlock(&smt_channels_lock);
+
+	return !channel_is_busy;
+}
+
+static void channel_release_busy(struct scmi_msg_channel *chan)
+{
+	chan->busy = false;
+}
+
+static struct smt_header *channel_to_smt_hdr(struct scmi_msg_channel *chan)
+{
+	return (struct smt_header *)chan->shm_addr;
+}
+
+/*
+ * Creates a SCMI message instance in secure memory and pushes it in the SCMI
+ * message drivers. Message structure contains SCMI protocol meta-data and
+ * references to input payload in secure memory and output message buffer
+ * in shared memory.
+ */
+static void scmi_proccess_smt(unsigned int agent_id, uint32_t *payload_buf)
+{
+	struct scmi_msg_channel *chan;
+	struct smt_header *smt_hdr;
+	size_t in_payload_size;
+	uint32_t smt_status;
+	struct scmi_msg msg;
+	bool error = true;
+
+	chan = plat_scmi_get_channel(agent_id);
+	if (chan == NULL) {
+		return;
+	}
+
+	smt_hdr = channel_to_smt_hdr(chan);
+	assert(smt_hdr);
+
+	smt_status = __atomic_load_n(&smt_hdr->status, __ATOMIC_RELAXED);
+
+	if (!channel_set_busy(chan)) {
+		VERBOSE("SCMI channel %u busy", agent_id);
+		goto out;
+	}
+
+	in_payload_size = __atomic_load_n(&smt_hdr->length, __ATOMIC_RELAXED) -
+			  sizeof(smt_hdr->message_header);
+
+	if (in_payload_size > SCMI_PLAYLOAD_MAX) {
+		VERBOSE("SCMI payload too big %zu", in_payload_size);
+		goto out;
+	}
+
+	if ((smt_status & (SMT_STATUS_ERROR | SMT_STATUS_FREE)) != 0U) {
+		VERBOSE("SCMI channel bad status 0x%x",
+			smt_hdr->status & (SMT_STATUS_ERROR | SMT_STATUS_FREE));
+		goto out;
+	}
+
+	/* Fill message */
+	zeromem(&msg, sizeof(msg));
+	msg.in = (char *)payload_buf;
+	msg.in_size = in_payload_size;
+	msg.out = (char *)smt_hdr->payload;
+	msg.out_size = chan->shm_size - sizeof(*smt_hdr);
+
+	assert((msg.out != NULL) && (msg.out_size >= sizeof(int32_t)));
+
+	/* Here the payload is copied in secure memory */
+	memcpy(msg.in, smt_hdr->payload, in_payload_size);
+
+	msg.protocol_id = SMT_HDR_PROT_ID(smt_hdr->message_header);
+	msg.message_id = SMT_HDR_MSG_ID(smt_hdr->message_header);
+	msg.agent_id = agent_id;
+
+	scmi_process_message(&msg);
+
+	/* Update message length with the length of the response message */
+	smt_hdr->length = msg.out_size_out + sizeof(smt_hdr->message_header);
+
+	channel_release_busy(chan);
+	error = false;
+
+out:
+	if (error) {
+		VERBOSE("SCMI error");
+		smt_hdr->status |= SMT_STATUS_ERROR | SMT_STATUS_FREE;
+	} else {
+		smt_hdr->status |= SMT_STATUS_FREE;
+	}
+}
+
+void scmi_smt_fastcall_smc_entry(unsigned int agent_id)
+{
+	scmi_proccess_smt(agent_id,
+			  fast_smc_payload[plat_my_core_pos()]);
+}
+
+void scmi_smt_interrupt_entry(unsigned int agent_id)
+{
+	scmi_proccess_smt(agent_id,
+			  interrupt_payload[plat_my_core_pos()]);
+}
+
+/* Init a SMT header for a shared memory buffer: state it a free/no-error */
+void scmi_smt_init_agent_channel(struct scmi_msg_channel *chan)
+{
+	if (chan != NULL) {
+		struct smt_header *smt_header = channel_to_smt_hdr(chan);
+
+		if (smt_header != NULL) {
+			memset(smt_header, 0, sizeof(*smt_header));
+			smt_header->status = SMT_STATUS_FREE;
+
+			return;
+		}
+	}
+
+	panic();
+}
diff --git a/drivers/st/clk/stm32mp1_clk.c b/drivers/st/clk/stm32mp1_clk.c
index 564bd87..3ebc376 100644
--- a/drivers/st/clk/stm32mp1_clk.c
+++ b/drivers/st/clk/stm32mp1_clk.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (C) 2018-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
  */
@@ -56,6 +56,7 @@
 	_HSI_KER = NB_OSC,
 	_HSE_KER,
 	_HSE_KER_DIV2,
+	_HSE_RTC,
 	_CSI_KER,
 	_PLL1_P,
 	_PLL1_Q,
@@ -107,7 +108,7 @@
 	_USBPHY_SEL,
 	_USBO_SEL,
 	_MPU_SEL,
-	_PER_SEL,
+	_CKPER_SEL,
 	_RTC_SEL,
 	_PARENT_SEL_NB,
 	_UNKNOWN_SEL = 0xff,
@@ -125,6 +126,7 @@
 	[_HSI_KER] = CK_HSI,
 	[_HSE_KER] = CK_HSE,
 	[_HSE_KER_DIV2] = CK_HSE_DIV2,
+	[_HSE_RTC] = _UNKNOWN_ID,
 	[_CSI_KER] = CK_CSI,
 	[_PLL1_P] = PLL1_P,
 	[_PLL1_Q] = PLL1_Q,
@@ -465,12 +467,12 @@
 	_ACLK, _PLL3_R, _PLL4_P, _CK_PER
 };
 
-static const uint8_t ass_parents[] = {
-	_HSI, _HSE, _PLL2
+static const uint8_t axiss_parents[] = {
+	_HSI, _HSE, _PLL2_P
 };
 
-static const uint8_t mss_parents[] = {
-	_HSI, _HSE, _CSI, _PLL3
+static const uint8_t mcuss_parents[] = {
+	_HSI, _HSE, _CSI, _PLL3_P
 };
 
 static const uint8_t usbphy_parents[] = {
@@ -490,7 +492,7 @@
 };
 
 static const uint8_t rtc_parents[] = {
-	_UNKNOWN_ID, _LSE, _LSI, _HSE
+	_UNKNOWN_ID, _LSE, _LSI, _HSE_RTC
 };
 
 static const struct stm32mp1_clk_sel stm32mp1_clk_sel[_PARENT_SEL_NB] = {
@@ -502,7 +504,7 @@
 	_CLK_PARENT_SEL(UART1, RCC_UART1CKSELR, usart1_parents),
 	_CLK_PARENT_SEL(RNG1, RCC_RNG1CKSELR, rng1_parents),
 	_CLK_PARENT_SEL(MPU, RCC_MPCKSELR, mpu_parents),
-	_CLK_PARENT_SEL(PER, RCC_CPERCKSELR, per_parents),
+	_CLK_PARENT_SEL(CKPER, RCC_CPERCKSELR, per_parents),
 	_CLK_PARENT_SEL(RTC, RCC_BDCR, rtc_parents),
 	_CLK_PARENT_SEL(UART6, RCC_UART6CKSELR, uart6_parents),
 	_CLK_PARENT_SEL(UART24, RCC_UART24CKSELR, uart234578_parents),
@@ -512,8 +514,8 @@
 	_CLK_PARENT_SEL(SDMMC3, RCC_SDMMC3CKSELR, sdmmc3_parents),
 	_CLK_PARENT_SEL(QSPI, RCC_QSPICKSELR, qspi_parents),
 	_CLK_PARENT_SEL(FMC, RCC_FMCCKSELR, fmc_parents),
-	_CLK_PARENT_SEL(AXIS, RCC_ASSCKSELR, ass_parents),
-	_CLK_PARENT_SEL(MCUS, RCC_MSSCKSELR, mss_parents),
+	_CLK_PARENT_SEL(AXIS, RCC_ASSCKSELR, axiss_parents),
+	_CLK_PARENT_SEL(MCUS, RCC_MSSCKSELR, mcuss_parents),
 	_CLK_PARENT_SEL(USBPHY, RCC_USBCKSELR, usbphy_parents),
 	_CLK_PARENT_SEL(USBO, RCC_USBCKSELR, usbo_parents),
 };
@@ -587,6 +589,7 @@
 	[_HSI_KER] = "HSI_KER",
 	[_HSE_KER] = "HSE_KER",
 	[_HSE_KER_DIV2] = "HSE_KER_DIV2",
+	[_HSE_RTC] = "HSE_RTC",
 	[_CSI_KER] = "CSI_KER",
 	[_PLL1_P] = "PLL1_P",
 	[_PLL1_Q] = "PLL1_Q",
@@ -847,9 +850,7 @@
 
 			reg = mmio_read_32(rcc_base + RCC_MPCKDIVR);
 			clkdiv = reg & RCC_MPUDIV_MASK;
-			if (clkdiv != 0U) {
-				clock /= stm32mp1_mpu_div[clkdiv];
-			}
+			clock >>= stm32mp1_mpu_div[clkdiv];
 			break;
 		default:
 			break;
@@ -969,6 +970,10 @@
 	case _HSE_KER_DIV2:
 		clock = stm32mp1_clk_get_fixed(_HSE) >> 1;
 		break;
+	case _HSE_RTC:
+		clock = stm32mp1_clk_get_fixed(_HSE);
+		clock /= (mmio_read_32(rcc_base + RCC_RTCDIVR) & RCC_DIVR_DIV_MASK) + 1U;
+		break;
 	case _LSI:
 		clock = stm32mp1_clk_get_fixed(_LSI);
 		break;
@@ -1086,6 +1091,10 @@
 	case PLL3_P:
 	case PLL3_Q:
 	case PLL3_R:
+	case CK_AXI:
+	case CK_MPU:
+	case CK_MCU:
+	case RTC:
 		return true;
 	default:
 		return false;
@@ -1652,7 +1661,7 @@
 	    (clksrc != (uint32_t)CLK_RTC_DISABLED)) {
 		mmio_clrsetbits_32(address,
 				   RCC_BDCR_RTCSRC_MASK,
-				   clksrc << RCC_BDCR_RTCSRC_SHIFT);
+				   (clksrc & RCC_SELR_SRC_MASK) << RCC_BDCR_RTCSRC_SHIFT);
 
 		mmio_setbits_32(address, RCC_BDCR_RTCCKEN);
 	}
@@ -1737,7 +1746,7 @@
 	void *fdt;
 
 	if (fdt_get_address(&fdt) == 0) {
-		return false;
+		return -FDT_ERR_NOTFOUND;
 	}
 
 	/* Check status field to disable security */
@@ -2152,6 +2161,7 @@
 	case _HSE:
 	case _HSE_KER:
 	case _HSE_KER_DIV2:
+	case _HSE_RTC:
 	case _LSE:
 		break;
 
@@ -2210,6 +2220,7 @@
 		DDRC2, DDRC2LP,
 		DDRCAPB, DDRPHYCAPB, DDRPHYCAPBLP,
 		DDRPHYC, DDRPHYCLP,
+		RTCAPB,
 		TZC1, TZC2,
 		TZPC,
 		STGEN_K,
@@ -2218,10 +2229,6 @@
 	for (idx = 0U; idx < ARRAY_SIZE(secure_enable); idx++) {
 		stm32mp_clk_enable(secure_enable[idx]);
 	}
-
-	if (!stm32mp_is_single_core()) {
-		stm32mp1_clk_enable_secure(RTCAPB);
-	}
 }
 
 int stm32mp1_clk_probe(void)
diff --git a/drivers/st/clk/stm32mp_clkfunc.c b/drivers/st/clk/stm32mp_clkfunc.c
index 8333f6d..d57f120 100644
--- a/drivers/st/clk/stm32mp_clkfunc.c
+++ b/drivers/st/clk/stm32mp_clkfunc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -161,9 +161,15 @@
  * @param fdt: Device tree reference
  * @return: Node offset or a negative value on error
  */
-int fdt_get_rcc_node(void *fdt)
+static int fdt_get_rcc_node(void *fdt)
 {
-	return fdt_node_offset_by_compatible(fdt, -1, DT_RCC_CLK_COMPAT);
+	static int node;
+
+	if (node <= 0) {
+		node = fdt_node_offset_by_compatible(fdt, -1, DT_RCC_CLK_COMPAT);
+	}
+
+	return node;
 }
 
 /*
diff --git a/drivers/st/fmc/stm32_fmc2_nand.c b/drivers/st/fmc/stm32_fmc2_nand.c
index a58a243..453069b 100644
--- a/drivers/st/fmc/stm32_fmc2_nand.c
+++ b/drivers/st/fmc/stm32_fmc2_nand.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
  */
@@ -200,9 +200,6 @@
 	if ((twait < NAND_TCS_MIN) && (tset_mem < (NAND_TCS_MIN - twait))) {
 		tset_mem = NAND_TCS_MIN - twait;
 	}
-	if ((twait < NAND_TALS_MIN) && (tset_mem < (NAND_TALS_MIN - twait))) {
-		tset_mem = NAND_TALS_MIN - twait;
-	}
 	if ((twait > thiz) && ((twait - thiz) < NAND_TDS_MIN) &&
 	    (tset_mem < (NAND_TDS_MIN - (twait - thiz)))) {
 		tset_mem = NAND_TDS_MIN - (twait - thiz);
@@ -244,12 +241,6 @@
 	if ((twait < NAND_TCS_MIN) && (tset_att < (NAND_TCS_MIN - twait))) {
 		tset_att = NAND_TCS_MIN - twait;
 	}
-	if ((twait < NAND_TCLS_MIN) && (tset_att < (NAND_TCLS_MIN - twait))) {
-		tset_att = NAND_TCLS_MIN - twait;
-	}
-	if ((twait < NAND_TALS_MIN) && (tset_att < (NAND_TALS_MIN - twait))) {
-		tset_att = NAND_TALS_MIN - twait;
-	}
 	if ((thold_mem < NAND_TRHW_MIN) &&
 	    (tset_att < (NAND_TRHW_MIN - thold_mem))) {
 		tset_att = NAND_TRHW_MIN - thold_mem;
diff --git a/drivers/st/io/io_mmc.c b/drivers/st/io/io_mmc.c
index 0ed7154..2bf88e6 100644
--- a/drivers/st/io/io_mmc.c
+++ b/drivers/st/io/io_mmc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -29,6 +29,7 @@
 static io_type_t device_type_mmc(void);
 
 static signed long long seek_offset;
+static size_t (*_read_blocks)(int lba, uintptr_t buf, size_t size);
 
 static const io_dev_connector_t mmc_dev_connector = {
 	.dev_open = mmc_dev_open
@@ -60,9 +61,15 @@
 /* Open a connection to the mmc device */
 static int mmc_dev_open(const uintptr_t init_params, io_dev_info_t **dev_info)
 {
+	struct io_mmc_dev_spec *device_spec =
+		(struct io_mmc_dev_spec *)init_params;
+
 	assert(dev_info != NULL);
 	*dev_info = (io_dev_info_t *)&mmc_dev_info;
 
+	_read_blocks = !device_spec->use_boot_part ?
+		mmc_read_blocks : mmc_boot_part_read_blocks;
+
 	return 0;
 }
 
@@ -100,8 +107,8 @@
 	uint8_t retries;
 
 	for (retries = 0U; retries < 3U; retries++) {
-		*length_read = mmc_read_blocks(seek_offset / MMC_BLOCK_SIZE,
-					       buffer, length);
+		*length_read = _read_blocks(seek_offset / MMC_BLOCK_SIZE,
+					    buffer, length);
 
 		if (*length_read == length) {
 			return 0;
diff --git a/drivers/st/io/io_stm32image.c b/drivers/st/io/io_stm32image.c
index 3e377cd..9fa0c50 100644
--- a/drivers/st/io/io_stm32image.c
+++ b/drivers/st/io/io_stm32image.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -246,10 +246,11 @@
 static int stm32image_partition_read(io_entity_t *entity, uintptr_t buffer,
 				     size_t length, size_t *length_read)
 {
-	int result;
+	int result = -EINVAL;
 	uint8_t *local_buffer;
 	boot_api_image_header_t *header =
 		(boot_api_image_header_t *)first_lba_buffer;
+	size_t hdr_sz = sizeof(boot_api_image_header_t);
 
 	assert(entity != NULL);
 	assert(buffer != 0U);
@@ -286,16 +287,13 @@
 		}
 
 		/* Part of image already loaded with the header */
-		memcpy(local_buffer, (uint8_t *)first_lba_buffer +
-		       sizeof(boot_api_image_header_t),
-		       MAX_LBA_SIZE - sizeof(boot_api_image_header_t));
-		local_buffer += MAX_LBA_SIZE - sizeof(boot_api_image_header_t);
+		memcpy(local_buffer, (uint8_t *)first_lba_buffer + hdr_sz,
+		       MAX_LBA_SIZE - hdr_sz);
+		local_buffer += MAX_LBA_SIZE - hdr_sz;
 		offset = MAX_LBA_SIZE;
 
 		/* New image length to be read */
-		local_length = round_up(length -
-					((MAX_LBA_SIZE) -
-					 sizeof(boot_api_image_header_t)),
+		local_length = round_up(length - ((MAX_LBA_SIZE) - hdr_sz),
 					stm32image_dev.lba_size);
 
 		if ((header->load_address != 0U) &&
@@ -326,7 +324,7 @@
 				 local_length, length_read);
 
 		/* Adding part of size already read from header */
-		*length_read += MAX_LBA_SIZE - sizeof(boot_api_image_header_t);
+		*length_read += MAX_LBA_SIZE - hdr_sz;
 
 		if (result != 0) {
 			ERROR("%s: io_read (%i)\n", __func__, result);
@@ -348,6 +346,9 @@
 			return result;
 		}
 
+		inv_dcache_range(round_up((uintptr_t)(local_buffer + length - hdr_sz),
+					  CACHE_WRITEBACK_GRANULE), *length_read - length + hdr_sz);
+
 		io_close(backend_handle);
 	}
 
diff --git a/drivers/st/mmc/stm32_sdmmc2.c b/drivers/st/mmc/stm32_sdmmc2.c
index cff3a34..d3adeab 100644
--- a/drivers/st/mmc/stm32_sdmmc2.c
+++ b/drivers/st/mmc/stm32_sdmmc2.c
@@ -628,6 +628,7 @@
 	int sdmmc_node;
 	void *fdt = NULL;
 	const fdt32_t *cuint;
+	struct dt_node_info dt_info;
 
 	if (fdt_get_address(&fdt) == 0) {
 		return -FDT_ERR_NOTFOUND;
@@ -637,27 +638,14 @@
 		return -FDT_ERR_NOTFOUND;
 	}
 
-	sdmmc_node = fdt_node_offset_by_compatible(fdt, -1, DT_SDMMC2_COMPAT);
-
-	while (sdmmc_node != -FDT_ERR_NOTFOUND) {
-		cuint = fdt_getprop(fdt, sdmmc_node, "reg", NULL);
-		if (cuint == NULL) {
-			continue;
-		}
-
-		if (fdt32_to_cpu(*cuint) == sdmmc2_params.reg_base) {
-			break;
-		}
-
-		sdmmc_node = fdt_node_offset_by_compatible(fdt, sdmmc_node,
-							   DT_SDMMC2_COMPAT);
-	}
-
+	sdmmc_node = dt_match_instance_by_compatible(DT_SDMMC2_COMPAT,
+						     sdmmc2_params.reg_base);
 	if (sdmmc_node == -FDT_ERR_NOTFOUND) {
 		return -FDT_ERR_NOTFOUND;
 	}
 
-	if (fdt_get_status(sdmmc_node) == DT_DISABLED) {
+	dt_fill_device_info(&dt_info, sdmmc_node);
+	if (dt_info.status == DT_DISABLED) {
 		return -FDT_ERR_NOTFOUND;
 	}
 
@@ -665,21 +653,8 @@
 		return -FDT_ERR_BADVALUE;
 	}
 
-	cuint = fdt_getprop(fdt, sdmmc_node, "clocks", NULL);
-	if (cuint == NULL) {
-		return -FDT_ERR_NOTFOUND;
-	}
-
-	cuint++;
-	sdmmc2_params.clock_id = fdt32_to_cpu(*cuint);
-
-	cuint = fdt_getprop(fdt, sdmmc_node, "resets", NULL);
-	if (cuint == NULL) {
-		return -FDT_ERR_NOTFOUND;
-	}
-
-	cuint++;
-	sdmmc2_params.reset_id = fdt32_to_cpu(*cuint);
+	sdmmc2_params.clock_id = dt_info.clock;
+	sdmmc2_params.reset_id = dt_info.reset;
 
 	if ((fdt_getprop(fdt, sdmmc_node, "st,use-ckin", NULL)) != NULL) {
 		sdmmc2_params.pin_ckin = SDMMC_CLKCR_SELCLKRX_0;
diff --git a/drivers/st/pmic/stm32mp_pmic.c b/drivers/st/pmic/stm32mp_pmic.c
index b2bb482..be410a1 100644
--- a/drivers/st/pmic/stm32mp_pmic.c
+++ b/drivers/st/pmic/stm32mp_pmic.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -121,6 +121,9 @@
 	}
 
 	regulators_node = fdt_subnode_offset(fdt, pmic_node, "regulators");
+	if (regulators_node < 0) {
+		return -ENOENT;
+	}
 
 	fdt_for_each_subnode(regulator_node, fdt, regulators_node) {
 		const fdt32_t *cuint;
@@ -204,6 +207,7 @@
 	i2c->i2c_base_addr		= i2c_info.base;
 	i2c->dt_status			= i2c_info.status;
 	i2c->clock			= i2c_info.clock;
+	i2c->i2c_state			= I2C_STATE_RESET;
 	i2c_init.own_address1		= pmic_i2c_addr;
 	i2c_init.addressing_mode	= I2C_ADDRESSINGMODE_7BIT;
 	i2c_init.dual_address_mode	= I2C_DUALADDRESS_DISABLE;
diff --git a/drivers/st/pmic/stpmic1.c b/drivers/st/pmic/stpmic1.c
index 9999630..0a35df3 100644
--- a/drivers/st/pmic/stpmic1.c
+++ b/drivers/st/pmic/stpmic1.c
@@ -1,9 +1,10 @@
 /*
- * Copyright (c) 2016-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2016-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <errno.h>
 #include <string.h>
 
 #include <common/debug.h>
@@ -16,6 +17,7 @@
 	const uint16_t *voltage_table;
 	uint8_t voltage_table_size;
 	uint8_t control_reg;
+	uint8_t enable_mask;
 	uint8_t low_power_reg;
 	uint8_t pull_down_reg;
 	uint8_t pull_down;
@@ -426,6 +428,7 @@
 		.voltage_table	= buck1_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(buck1_voltage_table),
 		.control_reg	= BUCK1_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= BUCK1_PWRCTRL_REG,
 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
 		.pull_down	= BUCK1_PULL_DOWN_SHIFT,
@@ -437,6 +440,7 @@
 		.voltage_table	= buck2_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(buck2_voltage_table),
 		.control_reg	= BUCK2_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= BUCK2_PWRCTRL_REG,
 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
 		.pull_down	= BUCK2_PULL_DOWN_SHIFT,
@@ -448,6 +452,7 @@
 		.voltage_table	= buck3_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(buck3_voltage_table),
 		.control_reg	= BUCK3_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= BUCK3_PWRCTRL_REG,
 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
 		.pull_down	= BUCK3_PULL_DOWN_SHIFT,
@@ -459,6 +464,7 @@
 		.voltage_table	= buck4_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(buck4_voltage_table),
 		.control_reg	= BUCK4_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= BUCK4_PWRCTRL_REG,
 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
 		.pull_down	= BUCK4_PULL_DOWN_SHIFT,
@@ -470,6 +476,7 @@
 		.voltage_table	= ldo1_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo1_voltage_table),
 		.control_reg	= LDO1_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO1_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO1_MASK_RESET,
@@ -479,6 +486,7 @@
 		.voltage_table	= ldo2_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo2_voltage_table),
 		.control_reg	= LDO2_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO2_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO2_MASK_RESET,
@@ -488,6 +496,7 @@
 		.voltage_table	= ldo3_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo3_voltage_table),
 		.control_reg	= LDO3_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO3_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO3_MASK_RESET,
@@ -497,6 +506,7 @@
 		.voltage_table	= ldo4_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo4_voltage_table),
 		.control_reg	= LDO4_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO4_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO4_MASK_RESET,
@@ -506,6 +516,7 @@
 		.voltage_table	= ldo5_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo5_voltage_table),
 		.control_reg	= LDO5_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO5_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO5_MASK_RESET,
@@ -515,6 +526,7 @@
 		.voltage_table	= ldo6_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(ldo6_voltage_table),
 		.control_reg	= LDO6_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= LDO6_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= LDO6_MASK_RESET,
@@ -524,6 +536,7 @@
 		.voltage_table	= vref_ddr_voltage_table,
 		.voltage_table_size = ARRAY_SIZE(vref_ddr_voltage_table),
 		.control_reg	= VREF_DDR_CONTROL_REG,
+		.enable_mask	= LDO_BUCK_ENABLE_MASK,
 		.low_power_reg	= VREF_DDR_PWRCTRL_REG,
 		.mask_reset_reg	= MASK_RESET_LDO_REG,
 		.mask_reset	= VREF_DDR_MASK_RESET,
@@ -581,14 +594,16 @@
 {
 	const struct regul_struct *regul = get_regulator_data(name);
 
-	return stpmic1_register_update(regul->control_reg, BIT(0), BIT(0));
+	return stpmic1_register_update(regul->control_reg, regul->enable_mask,
+				       regul->enable_mask);
 }
 
 int stpmic1_regulator_disable(const char *name)
 {
 	const struct regul_struct *regul = get_regulator_data(name);
 
-	return stpmic1_register_update(regul->control_reg, 0, BIT(0));
+	return stpmic1_register_update(regul->control_reg, 0,
+				       regul->enable_mask);
 }
 
 uint8_t stpmic1_is_regulator_enabled(const char *name)
@@ -600,7 +615,7 @@
 		panic();
 	}
 
-	return (val & 0x1U);
+	return (val & regul->enable_mask);
 }
 
 int stpmic1_regulator_voltage_set(const char *name, uint16_t millivolts)
@@ -653,6 +668,7 @@
 	const struct regul_struct *regul = get_regulator_data(name);
 	uint8_t value;
 	uint8_t mask;
+	int status;
 
 	/* Voltage can be set for buck<N> or ldo<N> (except ldo4) regulators */
 	if (strncmp(name, "buck", 4) == 0) {
@@ -664,13 +680,16 @@
 		return 0;
 	}
 
-	if (stpmic1_register_read(regul->control_reg, &value))
-		return -1;
+	status = stpmic1_register_read(regul->control_reg, &value);
+	if (status < 0) {
+		return status;
+	}
 
 	value = (value & mask) >> LDO_BUCK_VOLTAGE_SHIFT;
 
-	if (value > regul->voltage_table_size)
-		return -1;
+	if (value > regul->voltage_table_size) {
+		return -ERANGE;
+	}
 
 	return (int)regul->voltage_table[value];
 }
@@ -706,7 +725,7 @@
 		}
 
 		if (readval != value) {
-			return -1;
+			return -EIO;
 		}
 	}
 #endif
@@ -751,12 +770,12 @@
 
 int stpmic1_get_version(unsigned long *version)
 {
-	int rc;
 	uint8_t read_val;
+	int status;
 
-	rc = stpmic1_register_read(VERSION_STATUS_REG, &read_val);
-	if (rc) {
-		return -1;
+	status = stpmic1_register_read(VERSION_STATUS_REG, &read_val);
+	if (status < 0) {
+		return status;
 	}
 
 	*version = (unsigned long)read_val;
diff --git a/drivers/st/scmi-msg/base.c b/drivers/st/scmi-msg/base.c
deleted file mode 100644
index e44bc52..0000000
--- a/drivers/st/scmi-msg/base.c
+++ /dev/null
@@ -1,198 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause
-/*
- * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-#include <assert.h>
-#include <string.h>
-
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
-#include <lib/utils.h>
-#include <lib/utils_def.h>
-
-#include "common.h"
-
-static bool message_id_is_supported(unsigned int message_id);
-
-static void report_version(struct scmi_msg *msg)
-{
-	struct scmi_protocol_version_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.version = SCMI_PROTOCOL_VERSION_BASE,
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_attributes(struct scmi_msg *msg)
-{
-	size_t protocol_count = plat_scmi_protocol_count();
-	struct scmi_protocol_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		/* Null agent count since agent discovery is not supported */
-		.attributes = SCMI_BASE_PROTOCOL_ATTRIBUTES(protocol_count, 0U),
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_message_attributes(struct scmi_msg *msg)
-{
-	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
-	struct scmi_protocol_message_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		/* For this protocol, attributes shall be zero */
-		.attributes = 0U,
-	};
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	if (!message_id_is_supported(in_args->message_id)) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void discover_vendor(struct scmi_msg *msg)
-{
-	const char *name = plat_scmi_vendor_name();
-	struct scmi_base_discover_vendor_p2a return_values = {
-		.status = SCMI_SUCCESS,
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	COPY_NAME_IDENTIFIER(return_values.vendor_identifier, name);
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void discover_sub_vendor(struct scmi_msg *msg)
-{
-	const char *name = plat_scmi_sub_vendor_name();
-	struct scmi_base_discover_sub_vendor_p2a return_values = {
-		.status = SCMI_SUCCESS,
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	COPY_NAME_IDENTIFIER(return_values.sub_vendor_identifier, name);
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void discover_implementation_version(struct scmi_msg *msg)
-{
-	struct scmi_protocol_version_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.version = SCMI_IMPL_VERSION,
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static unsigned int count_protocols_in_list(const uint8_t *protocol_list)
-{
-	unsigned int count = 0U;
-
-	if (protocol_list != NULL) {
-		while (protocol_list[count] != 0U) {
-			count++;
-		}
-	}
-
-	return count;
-}
-
-#define MAX_PROTOCOL_IN_LIST		8U
-
-static void discover_list_protocols(struct scmi_msg *msg)
-{
-	const struct scmi_base_discover_list_protocols_a2p *a2p = NULL;
-	struct scmi_base_discover_list_protocols_p2a p2a = {
-		.status = SCMI_SUCCESS,
-	};
-	uint8_t outargs[sizeof(p2a) + MAX_PROTOCOL_IN_LIST] = { 0U };
-	const uint8_t *list = NULL;
-	unsigned int count = 0U;
-
-	if (msg->in_size != sizeof(*a2p)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	assert(msg->out_size > sizeof(outargs));
-
-	a2p = (void *)msg->in;
-
-	list = plat_scmi_protocol_list(msg->agent_id);
-	count = count_protocols_in_list(list);
-	if (count > a2p->skip) {
-		count = MIN(count - a2p->skip, MAX_PROTOCOL_IN_LIST);
-	} else {
-		count = 0U;
-	}
-
-	p2a.num_protocols = count;
-
-	memcpy(outargs, &p2a, sizeof(p2a));
-	memcpy(outargs + sizeof(p2a), list + a2p->skip, count);
-
-	scmi_write_response(msg, outargs, sizeof(outargs));
-}
-
-static const scmi_msg_handler_t scmi_base_handler_table[] = {
-	[SCMI_PROTOCOL_VERSION] = report_version,
-	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
-	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
-	[SCMI_BASE_DISCOVER_VENDOR] = discover_vendor,
-	[SCMI_BASE_DISCOVER_SUB_VENDOR] = discover_sub_vendor,
-	[SCMI_BASE_DISCOVER_IMPLEMENTATION_VERSION] =
-					discover_implementation_version,
-	[SCMI_BASE_DISCOVER_LIST_PROTOCOLS] = discover_list_protocols,
-};
-
-static bool message_id_is_supported(unsigned int message_id)
-{
-	return (message_id < ARRAY_SIZE(scmi_base_handler_table)) &&
-	       (scmi_base_handler_table[message_id] != NULL);
-}
-
-scmi_msg_handler_t scmi_msg_get_base_handler(struct scmi_msg *msg)
-{
-	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
-
-	if (message_id >= ARRAY_SIZE(scmi_base_handler_table)) {
-		VERBOSE("Base handle not found %u\n", msg->message_id);
-		return NULL;
-	}
-
-	return scmi_base_handler_table[message_id];
-}
diff --git a/drivers/st/scmi-msg/clock.c b/drivers/st/scmi-msg/clock.c
deleted file mode 100644
index 319557c..0000000
--- a/drivers/st/scmi-msg/clock.c
+++ /dev/null
@@ -1,381 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause
-/*
- * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-#include <cdefs.h>
-#include <string.h>
-
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
-#include <lib/utils_def.h>
-
-#include "common.h"
-
-#pragma weak plat_scmi_clock_count
-#pragma weak plat_scmi_clock_get_name
-#pragma weak plat_scmi_clock_rates_array
-#pragma weak plat_scmi_clock_rates_by_step
-#pragma weak plat_scmi_clock_get_rate
-#pragma weak plat_scmi_clock_set_rate
-#pragma weak plat_scmi_clock_get_state
-#pragma weak plat_scmi_clock_set_state
-
-static bool message_id_is_supported(unsigned int message_id);
-
-size_t plat_scmi_clock_count(unsigned int agent_id __unused)
-{
-	return 0U;
-}
-
-const char *plat_scmi_clock_get_name(unsigned int agent_id __unused,
-				     unsigned int scmi_id __unused)
-{
-	return NULL;
-}
-
-int32_t plat_scmi_clock_rates_array(unsigned int agent_id __unused,
-				    unsigned int scmi_id __unused,
-				    unsigned long *rates __unused,
-				    size_t *nb_elts __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-int32_t plat_scmi_clock_rates_by_step(unsigned int agent_id __unused,
-				      unsigned int scmi_id __unused,
-				      unsigned long *steps __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-unsigned long plat_scmi_clock_get_rate(unsigned int agent_id __unused,
-				       unsigned int scmi_id __unused)
-{
-	return 0U;
-}
-
-int32_t plat_scmi_clock_set_rate(unsigned int agent_id __unused,
-				 unsigned int scmi_id __unused,
-				 unsigned long rate __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-int32_t plat_scmi_clock_get_state(unsigned int agent_id __unused,
-				  unsigned int scmi_id __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-int32_t plat_scmi_clock_set_state(unsigned int agent_id __unused,
-				  unsigned int scmi_id __unused,
-				  bool enable_not_disable __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-static void report_version(struct scmi_msg *msg)
-{
-	struct scmi_protocol_version_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.version = SCMI_PROTOCOL_VERSION_CLOCK,
-	};
-
-	if (msg->in_size != 0) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_attributes(struct scmi_msg *msg)
-{
-	size_t agent_count = plat_scmi_clock_count(msg->agent_id);
-	struct scmi_protocol_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.attributes = SCMI_CLOCK_PROTOCOL_ATTRIBUTES(1U, agent_count),
-	};
-
-	if (msg->in_size != 0) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_message_attributes(struct scmi_msg *msg)
-{
-	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
-	struct scmi_protocol_message_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		/* For this protocol, attributes shall be zero */
-		.attributes = 0U,
-	};
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	if (!message_id_is_supported(in_args->message_id)) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void scmi_clock_attributes(struct scmi_msg *msg)
-{
-	const struct scmi_clock_attributes_a2p *in_args = (void *)msg->in;
-	struct scmi_clock_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-	};
-	const char *name = NULL;
-	unsigned int clock_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
-
-	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-
-	name = plat_scmi_clock_get_name(msg->agent_id, clock_id);
-	if (name == NULL) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	COPY_NAME_IDENTIFIER(return_values.clock_name, name);
-
-	return_values.attributes = plat_scmi_clock_get_state(msg->agent_id,
-							     clock_id);
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void scmi_clock_rate_get(struct scmi_msg *msg)
-{
-	const struct scmi_clock_rate_get_a2p *in_args = (void *)msg->in;
-	unsigned long rate = 0U;
-	struct scmi_clock_rate_get_p2a return_values = {
-		.status = SCMI_SUCCESS,
-	};
-	unsigned int clock_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
-
-	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-	rate = plat_scmi_clock_get_rate(msg->agent_id, clock_id);
-
-	return_values.rate[0] = (uint32_t)rate;
-	return_values.rate[1] = (uint32_t)((uint64_t)rate >> 32);
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void scmi_clock_rate_set(struct scmi_msg *msg)
-{
-	const struct scmi_clock_rate_set_a2p *in_args = (void *)msg->in;
-	unsigned long rate = 0U;
-	int32_t status = 0;
-	unsigned int clock_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
-
-	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-	rate = (unsigned long)(((uint64_t)in_args->rate[1] << 32) |
-			       in_args->rate[0]);
-
-	status = plat_scmi_clock_set_rate(msg->agent_id, clock_id, rate);
-
-	scmi_status_response(msg, status);
-}
-
-static void scmi_clock_config_set(struct scmi_msg *msg)
-{
-	const struct scmi_clock_config_set_a2p *in_args = (void *)msg->in;
-	int32_t status = SCMI_GENERIC_ERROR;
-	bool enable = false;
-	unsigned int clock_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
-
-	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-	enable = in_args->attributes & SCMI_CLOCK_CONFIG_SET_ENABLE_MASK;
-
-	status = plat_scmi_clock_set_state(msg->agent_id, clock_id, enable);
-
-	scmi_status_response(msg, status);
-}
-
-#define RATES_ARRAY_SIZE_MAX	(SCMI_PLAYLOAD_MAX - \
-				 sizeof(struct scmi_clock_describe_rates_p2a))
-
-#define SCMI_RATES_BY_ARRAY(_nb_rates, _rem_rates) \
-	SCMI_CLOCK_DESCRIBE_RATES_NUM_RATES_FLAGS((_nb_rates), \
-						SCMI_CLOCK_RATE_FORMAT_LIST, \
-						(_rem_rates))
-#define SCMI_RATES_BY_STEP \
-	SCMI_CLOCK_DESCRIBE_RATES_NUM_RATES_FLAGS(3U, \
-						SCMI_CLOCK_RATE_FORMAT_RANGE, \
-						0U)
-
-#define RATE_DESC_SIZE		sizeof(struct scmi_clock_rate)
-
-static void write_rate_desc_array_in_buffer(char *dest, unsigned long *rates,
-					    size_t nb_elt)
-{
-	uint32_t *out = (uint32_t *)(uintptr_t)dest;
-	size_t n;
-
-	ASSERT_SYM_PTR_ALIGN(out);
-
-	for (n = 0U; n < nb_elt; n++) {
-		out[2 * n] = (uint32_t)rates[n];
-		out[2 * n + 1] = (uint32_t)((uint64_t)rates[n] >> 32);
-	}
-}
-
-static void scmi_clock_describe_rates(struct scmi_msg *msg)
-{
-	const struct scmi_clock_describe_rates_a2p *in_args = (void *)msg->in;
-	struct scmi_clock_describe_rates_p2a p2a = {
-		.status = SCMI_SUCCESS,
-	};
-	size_t nb_rates;
-	int32_t status;
-	unsigned int clock_id;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	clock_id = SPECULATION_SAFE_VALUE(in_args->clock_id);
-
-	if (clock_id >= plat_scmi_clock_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-	/* Platform may support array rate description */
-	status = plat_scmi_clock_rates_array(msg->agent_id, clock_id, NULL,
-					     &nb_rates);
-	if (status == SCMI_SUCCESS) {
-		/* Currently 12 cells mex, so it's affordable for the stack */
-		unsigned long plat_rates[RATES_ARRAY_SIZE_MAX / RATE_DESC_SIZE];
-		size_t max_nb = RATES_ARRAY_SIZE_MAX / RATE_DESC_SIZE;
-		size_t ret_nb = MIN(nb_rates - in_args->rate_index, max_nb);
-		size_t rem_nb = nb_rates - in_args->rate_index - ret_nb;
-
-		status =  plat_scmi_clock_rates_array(msg->agent_id, clock_id,
-						      plat_rates, &ret_nb);
-		if (status == SCMI_SUCCESS) {
-			write_rate_desc_array_in_buffer(msg->out + sizeof(p2a),
-							plat_rates, ret_nb);
-
-			p2a.num_rates_flags = SCMI_RATES_BY_ARRAY(ret_nb,
-								  rem_nb);
-			p2a.status = SCMI_SUCCESS;
-
-			memcpy(msg->out, &p2a, sizeof(p2a));
-			msg->out_size_out = sizeof(p2a) +
-					    ret_nb * RATE_DESC_SIZE;
-		}
-	} else if (status == SCMI_NOT_SUPPORTED) {
-		unsigned long triplet[3] = { 0U, 0U, 0U };
-
-		/* Platform may support min§max/step triplet description */
-		status =  plat_scmi_clock_rates_by_step(msg->agent_id, clock_id,
-							triplet);
-		if (status == SCMI_SUCCESS) {
-			write_rate_desc_array_in_buffer(msg->out + sizeof(p2a),
-							triplet, 3U);
-
-			p2a.num_rates_flags = SCMI_RATES_BY_STEP;
-			p2a.status = SCMI_SUCCESS;
-
-			memcpy(msg->out, &p2a, sizeof(p2a));
-			msg->out_size_out = sizeof(p2a) + (3U * RATE_DESC_SIZE);
-		}
-	} else {
-		/* Fallthrough generic exit sequence below with error status */
-	}
-
-	if (status != SCMI_SUCCESS) {
-		scmi_status_response(msg, status);
-	} else {
-		/*
-		 * Message payload is already writen to msg->out, and
-		 * msg->out_size_out updated.
-		 */
-	}
-}
-
-static const scmi_msg_handler_t scmi_clock_handler_table[] = {
-	[SCMI_PROTOCOL_VERSION] = report_version,
-	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
-	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
-	[SCMI_CLOCK_ATTRIBUTES] = scmi_clock_attributes,
-	[SCMI_CLOCK_DESCRIBE_RATES] = scmi_clock_describe_rates,
-	[SCMI_CLOCK_RATE_SET] = scmi_clock_rate_set,
-	[SCMI_CLOCK_RATE_GET] = scmi_clock_rate_get,
-	[SCMI_CLOCK_CONFIG_SET] = scmi_clock_config_set,
-};
-
-static bool message_id_is_supported(size_t message_id)
-{
-	return (message_id < ARRAY_SIZE(scmi_clock_handler_table)) &&
-	       (scmi_clock_handler_table[message_id] != NULL);
-}
-
-scmi_msg_handler_t scmi_msg_get_clock_handler(struct scmi_msg *msg)
-{
-	const size_t array_size = ARRAY_SIZE(scmi_clock_handler_table);
-	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
-
-	if (message_id >= array_size) {
-		VERBOSE("Clock handle not found %u", msg->message_id);
-		return NULL;
-	}
-
-	return scmi_clock_handler_table[message_id];
-}
diff --git a/drivers/st/scmi-msg/common.h b/drivers/st/scmi-msg/common.h
deleted file mode 100644
index ef5953b..0000000
--- a/drivers/st/scmi-msg/common.h
+++ /dev/null
@@ -1,136 +0,0 @@
-/* SPDX-License-Identifier: BSD-3-Clause */
-/*
- * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-#ifndef SCMI_MSG_COMMON_H
-#define SCMI_MSG_COMMON_H
-
-#include <assert.h>
-#include <stdbool.h>
-#include <stdint.h>
-#include <string.h>
-
-#include "base.h"
-#include "clock.h"
-#include "reset_domain.h"
-
-#define SCMI_VERSION			0x20000U
-#define SCMI_IMPL_VERSION		0U
-
-#define SCMI_PLAYLOAD_MAX		92U
-
-/*
- * Copy name identifier in target buffer following the SCMI specification
- * that state name identifier shall be a null terminated string.
- */
-#define COPY_NAME_IDENTIFIER(_dst_array, _name)				\
-	do {								\
-		assert(strlen(_name) < sizeof(_dst_array));		\
-		strlcpy((_dst_array), (_name), sizeof(_dst_array));	\
-	} while (0)
-
-/* Common command identifiers shared by all procotols */
-enum scmi_common_message_id {
-	SCMI_PROTOCOL_VERSION = 0x000,
-	SCMI_PROTOCOL_ATTRIBUTES = 0x001,
-	SCMI_PROTOCOL_MESSAGE_ATTRIBUTES = 0x002
-};
-
-/* Common platform-to-agent (p2a) PROTOCOL_VERSION structure */
-struct scmi_protocol_version_p2a {
-	int32_t status;
-	uint32_t version;
-};
-
-/* Generic platform-to-agent (p2a) PROTOCOL_ATTRIBUTES structure */
-struct scmi_protocol_attributes_p2a {
-	int32_t status;
-	uint32_t attributes;
-};
-
-/* Generic agent-to-platform (a2p) PROTOCOL_MESSAGE_ATTRIBUTES structure */
-struct scmi_protocol_message_attributes_a2p {
-	uint32_t message_id;
-};
-
-/* Generic platform-to-agent (p2a) PROTOCOL_MESSAGE_ATTRIBUTES structure */
-struct scmi_protocol_message_attributes_p2a {
-	int32_t status;
-	uint32_t attributes;
-};
-
-/*
- * struct scmi_msg - SCMI message context
- *
- * @agent_id: SCMI agent ID, safely set from secure world
- * @protocol_id: SCMI protocol ID for the related message, set by caller agent
- * @message_id: SCMI message ID for the related message, set by caller agent
- * @in: Address of the incoming message payload copied in secure memory
- * @in_size: Byte length of the incoming message payload, set by caller agent
- * @out: Address of of the output message payload message in non-secure memory
- * @out_size: Byte length of the provisionned output buffer
- * @out_size_out: Byte length of the output message payload
- */
-struct scmi_msg {
-	unsigned int agent_id;
-	unsigned int protocol_id;
-	unsigned int message_id;
-	char *in;
-	size_t in_size;
-	char *out;
-	size_t out_size;
-	size_t out_size_out;
-};
-
-/*
- * Type scmi_msg_handler_t is used by procotol drivers to safely find
- * the handler function for the incoming message ID.
- */
-typedef void (*scmi_msg_handler_t)(struct scmi_msg *msg);
-
-/*
- * scmi_msg_get_base_handler - Return a handler for a base message
- * @msg - message to process
- * Return a function handler for the message or NULL
- */
-scmi_msg_handler_t scmi_msg_get_base_handler(struct scmi_msg *msg);
-
-/*
- * scmi_msg_get_clock_handler - Return a handler for a clock message
- * @msg - message to process
- * Return a function handler for the message or NULL
- */
-scmi_msg_handler_t scmi_msg_get_clock_handler(struct scmi_msg *msg);
-
-/*
- * scmi_msg_get_rstd_handler - Return a handler for a reset domain message
- * @msg - message to process
- * Return a function handler for the message or NULL
- */
-scmi_msg_handler_t scmi_msg_get_rstd_handler(struct scmi_msg *msg);
-
-/*
- * Process Read, process and write response for input SCMI message
- *
- * @msg: SCMI message context
- */
-void scmi_process_message(struct scmi_msg *msg);
-
-/*
- * Write SCMI response payload to output message shared memory
- *
- * @msg: SCMI message context
- * @payload: Output message payload
- * @size: Byte size of output message payload
- */
-void scmi_write_response(struct scmi_msg *msg, void *payload, size_t size);
-
-/*
- * Write status only SCMI response payload to output message shared memory
- *
- * @msg: SCMI message context
- * @status: SCMI status value returned to caller
- */
-void scmi_status_response(struct scmi_msg *msg, int32_t status);
-#endif /* SCMI_MSG_COMMON_H */
diff --git a/drivers/st/scmi-msg/entry.c b/drivers/st/scmi-msg/entry.c
deleted file mode 100644
index eefcb31..0000000
--- a/drivers/st/scmi-msg/entry.c
+++ /dev/null
@@ -1,63 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause
-/*
- * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-
-#include <assert.h>
-
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
-
-#include "common.h"
-
-void scmi_status_response(struct scmi_msg *msg, int32_t status)
-{
-	assert(msg->out && msg->out_size >= sizeof(int32_t));
-
-	memcpy(msg->out, &status, sizeof(int32_t));
-	msg->out_size_out = sizeof(int32_t);
-}
-
-void scmi_write_response(struct scmi_msg *msg, void *payload, size_t size)
-{
-	/*
-	 * Output payload shall be at least the size of the status
-	 * Output buffer shall be at least be the size of the status
-	 * Output paylaod shall fit in output buffer
-	 */
-	assert(payload && size >= sizeof(int32_t) && size <= msg->out_size &&
-	       msg->out && msg->out_size >= sizeof(int32_t));
-
-	memcpy(msg->out, payload, size);
-	msg->out_size_out = size;
-}
-
-void scmi_process_message(struct scmi_msg *msg)
-{
-	scmi_msg_handler_t handler = NULL;
-
-	switch (msg->protocol_id) {
-	case SCMI_PROTOCOL_ID_BASE:
-		handler = scmi_msg_get_base_handler(msg);
-		break;
-	case SCMI_PROTOCOL_ID_CLOCK:
-		handler = scmi_msg_get_clock_handler(msg);
-		break;
-	case SCMI_PROTOCOL_ID_RESET_DOMAIN:
-		handler = scmi_msg_get_rstd_handler(msg);
-		break;
-	default:
-		break;
-	}
-
-	if (handler) {
-		handler(msg);
-		return;
-	}
-
-	ERROR("Agent %u Protocol 0x%x Message 0x%x: not supported",
-	      msg->agent_id, msg->protocol_id, msg->message_id);
-
-	scmi_status_response(msg, SCMI_NOT_SUPPORTED);
-}
diff --git a/drivers/st/scmi-msg/reset_domain.c b/drivers/st/scmi-msg/reset_domain.c
deleted file mode 100644
index b477302..0000000
--- a/drivers/st/scmi-msg/reset_domain.c
+++ /dev/null
@@ -1,197 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause
-/*
- * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-#include <cdefs.h>
-#include <string.h>
-
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
-#include <lib/utils.h>
-#include <lib/utils_def.h>
-
-#include "common.h"
-
-static bool message_id_is_supported(unsigned int message_id);
-
-#pragma weak plat_scmi_rstd_count
-#pragma weak plat_scmi_rstd_get_name
-#pragma weak plat_scmi_rstd_autonomous
-#pragma weak plat_scmi_rstd_set_state
-
-size_t plat_scmi_rstd_count(unsigned int agent_id __unused)
-{
-	return 0U;
-}
-
-const char *plat_scmi_rstd_get_name(unsigned int agent_id __unused,
-				  unsigned int scmi_id __unused)
-{
-	return NULL;
-}
-
-int32_t plat_scmi_rstd_autonomous(unsigned int agent_id __unused,
-				unsigned int scmi_id __unused,
-				unsigned int state __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-int32_t plat_scmi_rstd_set_state(unsigned int agent_id __unused,
-			       unsigned int scmi_id __unused,
-			       bool assert_not_deassert __unused)
-{
-	return SCMI_NOT_SUPPORTED;
-}
-
-static void report_version(struct scmi_msg *msg)
-{
-	struct scmi_protocol_version_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.version = SCMI_PROTOCOL_VERSION_RESET_DOMAIN,
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_attributes(struct scmi_msg *msg)
-{
-	struct scmi_protocol_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		.attributes = plat_scmi_rstd_count(msg->agent_id),
-	};
-
-	if (msg->in_size != 0U) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void report_message_attributes(struct scmi_msg *msg)
-{
-	struct scmi_protocol_message_attributes_a2p *in_args = (void *)msg->in;
-	struct scmi_protocol_message_attributes_p2a return_values = {
-		.status = SCMI_SUCCESS,
-		/* For this protocol, attributes shall be zero */
-		.attributes = 0U,
-	};
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	if (!message_id_is_supported(in_args->message_id)) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void reset_domain_attributes(struct scmi_msg *msg)
-{
-	struct scmi_reset_domain_attributes_a2p *in_args = (void *)msg->in;
-	struct scmi_reset_domain_attributes_p2a return_values;
-	const char *name = NULL;
-	unsigned int domain_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	domain_id = SPECULATION_SAFE_VALUE(in_args->domain_id);
-
-	if (domain_id >= plat_scmi_rstd_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_INVALID_PARAMETERS);
-		return;
-	}
-
-	name = plat_scmi_rstd_get_name(msg->agent_id, domain_id);
-	if (name == NULL) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	zeromem(&return_values, sizeof(return_values));
-	COPY_NAME_IDENTIFIER(return_values.name, name);
-	return_values.status = SCMI_SUCCESS;
-	return_values.flags = 0U; /* Async and Notif are not supported */
-	return_values.latency = SCMI_RESET_DOMAIN_ATTR_UNK_LAT;
-
-	scmi_write_response(msg, &return_values, sizeof(return_values));
-}
-
-static void reset_request(struct scmi_msg *msg)
-{
-	struct scmi_reset_domain_request_a2p *in_args = (void *)msg->in;
-	struct scmi_reset_domain_request_p2a out_args = {
-		.status = SCMI_SUCCESS,
-	};
-	unsigned int domain_id = 0U;
-
-	if (msg->in_size != sizeof(*in_args)) {
-		scmi_status_response(msg, SCMI_PROTOCOL_ERROR);
-		return;
-	}
-
-	domain_id = SPECULATION_SAFE_VALUE(in_args->domain_id);
-
-	if (domain_id >= plat_scmi_rstd_count(msg->agent_id)) {
-		scmi_status_response(msg, SCMI_NOT_FOUND);
-		return;
-	}
-
-	if ((in_args->flags & SCMI_RESET_DOMAIN_AUTO) != 0U) {
-		out_args.status = plat_scmi_rstd_autonomous(msg->agent_id,
-							  domain_id,
-							  in_args->reset_state);
-	} else if ((in_args->flags & SCMI_RESET_DOMAIN_EXPLICIT) != 0U) {
-		out_args.status = plat_scmi_rstd_set_state(msg->agent_id,
-							 domain_id, true);
-	} else {
-		out_args.status = plat_scmi_rstd_set_state(msg->agent_id,
-							 domain_id, false);
-	}
-
-	if (out_args.status != SCMI_SUCCESS) {
-		scmi_status_response(msg, out_args.status);
-	} else {
-		scmi_write_response(msg, &out_args, sizeof(out_args));
-	}
-}
-
-static const scmi_msg_handler_t scmi_rstd_handler_table[] = {
-	[SCMI_PROTOCOL_VERSION] = report_version,
-	[SCMI_PROTOCOL_ATTRIBUTES] = report_attributes,
-	[SCMI_PROTOCOL_MESSAGE_ATTRIBUTES] = report_message_attributes,
-	[SCMI_RESET_DOMAIN_ATTRIBUTES] = reset_domain_attributes,
-	[SCMI_RESET_DOMAIN_REQUEST] = reset_request,
-};
-
-static bool message_id_is_supported(unsigned int message_id)
-{
-	return (message_id < ARRAY_SIZE(scmi_rstd_handler_table)) &&
-	       (scmi_rstd_handler_table[message_id] != NULL);
-}
-
-scmi_msg_handler_t scmi_msg_get_rstd_handler(struct scmi_msg *msg)
-{
-	unsigned int message_id = SPECULATION_SAFE_VALUE(msg->message_id);
-
-	if (message_id >= ARRAY_SIZE(scmi_rstd_handler_table)) {
-		VERBOSE("Reset domain handle not found %u\n", msg->message_id);
-		return NULL;
-	}
-
-	return scmi_rstd_handler_table[message_id];
-}
diff --git a/drivers/st/scmi-msg/smt.c b/drivers/st/scmi-msg/smt.c
deleted file mode 100644
index 2d5cd73..0000000
--- a/drivers/st/scmi-msg/smt.c
+++ /dev/null
@@ -1,206 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause
-/*
- * Copyright (c) 2015-2019, Arm Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Linaro Limited
- */
-#include <assert.h>
-#include <stdbool.h>
-#include <stdint.h>
-#include <string.h>
-
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
-#include <lib/cassert.h>
-#include <lib/mmio.h>
-#include <lib/spinlock.h>
-#include <lib/utils.h>
-#include <plat/common/platform.h>
-
-#include "common.h"
-
-/* Legacy SMT/SCMI messages are 128 bytes at most including SMT header */
-#define SCMI_PLAYLOAD_MAX		92U
-#define SCMI_PLAYLOAD_U32_MAX		(SCMI_PLAYLOAD_MAX / sizeof(uint32_t))
-
-/**
- * struct smt_header - SMT formatted header for SMT base shared memory transfer
- *
- * @status: Bit flags, see SMT_STATUS_*
- * @flags: Bit flags, see SMT_FLAG_*
- * @length: Byte size of message payload (variable) + ::message_header (32bit)
- * payload: SCMI message payload data
- */
-struct smt_header {
-	uint32_t reserved0;
-	uint32_t status;
-	uint64_t reserved1;
-	uint32_t flags;
-	uint32_t length; /* message_header + payload */
-	uint32_t message_header;
-	uint32_t payload[];
-};
-
-CASSERT(SCMI_PLAYLOAD_MAX + sizeof(struct smt_header) <= SMT_BUF_SLOT_SIZE,
-	assert_scmi_message_max_length_fits_in_smt_buffer_slot);
-
-/* Flag set in smt_header::status when SMT does not contain pending message */
-#define SMT_STATUS_FREE			BIT(0)
-/* Flag set in smt_header::status when SMT reports an error */
-#define SMT_STATUS_ERROR		BIT(1)
-
-/* Flag set in smt_header::flags when SMT uses interrupts */
-#define SMT_FLAG_INTR_ENABLED		BIT(1)
-
-/* Bit fields packed in smt_header::message_header */
-#define SMT_MSG_ID_MASK			GENMASK_32(7, 0)
-#define SMT_HDR_MSG_ID(_hdr)		((_hdr) & SMT_MSG_ID_MASK)
-
-#define SMT_MSG_TYPE_MASK		GENMASK_32(9, 8)
-#define SMT_HDR_TYPE_ID(_hdr)		(((_hdr) & SMT_MSG_TYPE_MASK) >> 8)
-
-#define SMT_MSG_PROT_ID_MASK		GENMASK_32(17, 10)
-#define SMT_HDR_PROT_ID(_hdr)		(((_hdr) & SMT_MSG_PROT_ID_MASK) >> 10)
-
-/*
- * Provision input message payload buffers for fastcall SMC context entries
- * and for interrupt context execution entries.
- */
-static uint32_t fast_smc_payload[PLATFORM_CORE_COUNT][SCMI_PLAYLOAD_U32_MAX];
-static uint32_t interrupt_payload[PLATFORM_CORE_COUNT][SCMI_PLAYLOAD_U32_MAX];
-
-/* SMP protection on channel access */
-static struct spinlock smt_channels_lock;
-
-/* If channel is not busy, set busy and return true, otherwise return false */
-static bool channel_set_busy(struct scmi_msg_channel *chan)
-{
-	bool channel_is_busy;
-
-	spin_lock(&smt_channels_lock);
-
-	channel_is_busy = chan->busy;
-
-	if (!channel_is_busy) {
-		chan->busy = true;
-	}
-
-	spin_unlock(&smt_channels_lock);
-
-	return !channel_is_busy;
-}
-
-static void channel_release_busy(struct scmi_msg_channel *chan)
-{
-	chan->busy = false;
-}
-
-static struct smt_header *channel_to_smt_hdr(struct scmi_msg_channel *chan)
-{
-	return (struct smt_header *)chan->shm_addr;
-}
-
-/*
- * Creates a SCMI message instance in secure memory and pushes it in the SCMI
- * message drivers. Message structure contains SCMI protocol meta-data and
- * references to input payload in secure memory and output message buffer
- * in shared memory.
- */
-static void scmi_proccess_smt(unsigned int agent_id, uint32_t *payload_buf)
-{
-	struct scmi_msg_channel *chan;
-	struct smt_header *smt_hdr;
-	size_t in_payload_size;
-	uint32_t smt_status;
-	struct scmi_msg msg;
-	bool error = true;
-
-	chan = plat_scmi_get_channel(agent_id);
-	if (chan == NULL) {
-		return;
-	}
-
-	smt_hdr = channel_to_smt_hdr(chan);
-	assert(smt_hdr);
-
-	smt_status = __atomic_load_n(&smt_hdr->status, __ATOMIC_RELAXED);
-
-	if (!channel_set_busy(chan)) {
-		VERBOSE("SCMI channel %u busy", agent_id);
-		goto out;
-	}
-
-	in_payload_size = __atomic_load_n(&smt_hdr->length, __ATOMIC_RELAXED) -
-			  sizeof(smt_hdr->message_header);
-
-	if (in_payload_size > SCMI_PLAYLOAD_MAX) {
-		VERBOSE("SCMI payload too big %u", in_payload_size);
-		goto out;
-	}
-
-	if ((smt_status & (SMT_STATUS_ERROR | SMT_STATUS_FREE)) != 0U) {
-		VERBOSE("SCMI channel bad status 0x%x",
-			smt_hdr->status & (SMT_STATUS_ERROR | SMT_STATUS_FREE));
-		goto out;
-	}
-
-	/* Fill message */
-	zeromem(&msg, sizeof(msg));
-	msg.in = (char *)payload_buf;
-	msg.in_size = in_payload_size;
-	msg.out = (char *)smt_hdr->payload;
-	msg.out_size = chan->shm_size - sizeof(*smt_hdr);
-
-	assert((msg.out != NULL) && (msg.out_size >= sizeof(int32_t)));
-
-	/* Here the payload is copied in secure memory */
-	memcpy(msg.in, smt_hdr->payload, in_payload_size);
-
-	msg.protocol_id = SMT_HDR_PROT_ID(smt_hdr->message_header);
-	msg.message_id = SMT_HDR_MSG_ID(smt_hdr->message_header);
-	msg.agent_id = agent_id;
-
-	scmi_process_message(&msg);
-
-	/* Update message length with the length of the response message */
-	smt_hdr->length = msg.out_size_out + sizeof(smt_hdr->message_header);
-
-	channel_release_busy(chan);
-	error = false;
-
-out:
-	if (error) {
-		VERBOSE("SCMI error");
-		smt_hdr->status |= SMT_STATUS_ERROR | SMT_STATUS_FREE;
-	} else {
-		smt_hdr->status |= SMT_STATUS_FREE;
-	}
-}
-
-void scmi_smt_fastcall_smc_entry(unsigned int agent_id)
-{
-	scmi_proccess_smt(agent_id,
-			  fast_smc_payload[plat_my_core_pos()]);
-}
-
-void scmi_smt_interrupt_entry(unsigned int agent_id)
-{
-	scmi_proccess_smt(agent_id,
-			  interrupt_payload[plat_my_core_pos()]);
-}
-
-/* Init a SMT header for a shared memory buffer: state it a free/no-error */
-void scmi_smt_init_agent_channel(struct scmi_msg_channel *chan)
-{
-	if (chan != NULL) {
-		struct smt_header *smt_header = channel_to_smt_hdr(chan);
-
-		if (smt_header != NULL) {
-			memset(smt_header, 0, sizeof(*smt_header));
-			smt_header->status = SMT_STATUS_FREE;
-
-			return;
-		}
-	}
-
-	panic();
-}
diff --git a/drivers/st/spi/stm32_qspi.c b/drivers/st/spi/stm32_qspi.c
index d67f831..4b1a029 100644
--- a/drivers/st/spi/stm32_qspi.c
+++ b/drivers/st/spi/stm32_qspi.c
@@ -4,6 +4,7 @@
  * SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
  */
 
+#include <inttypes.h>
 #include <libfdt.h>
 
 #include <platform_def.h>
@@ -244,7 +245,7 @@
 	uint8_t mode = QSPI_CCR_IND_WRITE;
 	int ret;
 
-	VERBOSE("%s: cmd:%x mode:%d.%d.%d.%d addr:%llx len:%x\n",
+	VERBOSE("%s: cmd:%x mode:%d.%d.%d.%d addr:%" PRIx64 " len:%x\n",
 		__func__, op->cmd.opcode, op->cmd.buswidth, op->addr.buswidth,
 		op->dummy.buswidth, op->data.buswidth,
 		op->addr.val, op->data.nbytes);
diff --git a/drivers/st/uart/aarch32/stm32_console.S b/drivers/st/uart/aarch32/stm32_console.S
index 686b18b..2b8879a 100644
--- a/drivers/st/uart/aarch32/stm32_console.S
+++ b/drivers/st/uart/aarch32/stm32_console.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -45,7 +45,12 @@
 	/* Check the input base address */
 	cmp	r0, #0
 	beq	core_init_fail
-#if defined(IMAGE_BL2)
+#if !defined(IMAGE_BL2)
+	/* Skip UART initialization if it is already enabled */
+	ldr	r3, [r0, #USART_CR1]
+	ands	r3, r3, #USART_CR1_UE
+	bne	1f
+#endif /* IMAGE_BL2 */
 	/* Check baud rate and uart clock for sanity */
 	cmp	r1, #0
 	beq	core_init_fail
@@ -78,7 +83,7 @@
 	ldr	r3, [r0, #USART_ISR]
 	tst	r3, #USART_ISR_TEACK
 	beq	teack_loop
-#endif /* IMAGE_BL2 */
+1:
 	mov	r0, #1
 	bx	lr
 core_init_fail:
diff --git a/drivers/st/usb/stm32mp1_usb.c b/drivers/st/usb/stm32mp1_usb.c
new file mode 100644
index 0000000..9a49690
--- /dev/null
+++ b/drivers/st/usb/stm32mp1_usb.c
@@ -0,0 +1,1091 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <drivers/st/stm32mp1_usb.h>
+#include <lib/mmio.h>
+
+#include <platform_def.h>
+
+#define USB_OTG_MODE_DEVICE			0U
+#define USB_OTG_MODE_HOST			1U
+#define USB_OTG_MODE_DRD			2U
+
+#define EP_TYPE_CTRL				0U
+#define EP_TYPE_ISOC				1U
+#define EP_TYPE_BULK				2U
+#define EP_TYPE_INTR				3U
+
+#define USBD_FIFO_FLUSH_TIMEOUT_US		1000U
+#define EP0_FIFO_SIZE				64U
+
+/* OTG registers offsets */
+#define OTG_GOTGINT				0x004U
+#define OTG_GAHBCFG				0x008U
+#define OTG_GUSBCFG				0x00CU
+#define OTG_GRSTCTL				0x010U
+#define OTG_GINTSTS				0x014U
+#define OTG_GINTMSK				0x018U
+#define OTG_GRXSTSP				0x020U
+#define OTG_GLPMCFG				0x054U
+#define OTG_DCFG				0x800U
+#define OTG_DCTL				0x804U
+#define OTG_DSTS				0x808U
+#define OTG_DIEPMSK				0x810U
+#define OTG_DOEPMSK				0x814U
+#define OTG_DAINT				0x818U
+#define OTG_DAINTMSK				0x81CU
+#define OTG_DIEPEMPMSK				0x834U
+
+/* Definitions for OTG_DIEPx registers */
+#define OTG_DIEP_BASE				0x900U
+#define OTG_DIEP_SIZE				0x20U
+#define OTG_DIEPCTL				0x00U
+#define OTG_DIEPINT				0x08U
+#define OTG_DIEPTSIZ				0x10U
+#define OTG_DIEPDMA				0x14U
+#define OTG_DTXFSTS				0x18U
+#define OTG_DIEP_MAX_NB				9U
+
+/* Definitions for OTG_DOEPx registers */
+#define OTG_DOEP_BASE				0xB00U
+#define OTG_DOEP_SIZE				0x20U
+#define OTG_DOEPCTL				0x00U
+#define OTG_DOEPINT				0x08U
+#define OTG_DOEPTSIZ				0x10U
+#define OTG_DOEPDMA				0x14U
+#define OTG_D0EP_MAX_NB				9U
+
+/* Definitions for OTG_DAINT registers */
+#define OTG_DAINT_OUT_MASK			GENMASK(31, 16)
+#define OTG_DAINT_OUT_SHIFT			16U
+#define OTG_DAINT_IN_MASK			GENMASK(15, 0)
+#define OTG_DAINT_IN_SHIFT			0U
+
+#define OTG_DAINT_EP0_IN			BIT(16)
+#define OTG_DAINT_EP0_OUT			BIT(0)
+
+/* Definitions for FIFOs */
+#define OTG_FIFO_BASE				0x1000U
+#define OTG_FIFO_SIZE				0x1000U
+
+/* Bit definitions for OTG_GOTGINT register */
+#define OTG_GOTGINT_SEDET			BIT(2)
+
+/* Bit definitions for OTG_GAHBCFG register */
+#define OTG_GAHBCFG_GINT			BIT(0)
+
+/* Bit definitions for OTG_GUSBCFG register */
+#define OTG_GUSBCFG_TRDT			GENMASK(13, 10)
+#define OTG_GUSBCFG_TRDT_SHIFT			10U
+
+#define USBD_HS_TRDT_VALUE			9U
+
+/* Bit definitions for OTG_GRSTCTL register */
+#define OTG_GRSTCTL_RXFFLSH			BIT(4)
+#define OTG_GRSTCTL_TXFFLSH			BIT(5)
+#define OTG_GRSTCTL_TXFNUM_SHIFT		6U
+
+/* Bit definitions for OTG_GINTSTS register */
+#define OTG_GINTSTS_CMOD			BIT(0)
+#define OTG_GINTSTS_MMIS			BIT(1)
+#define OTG_GINTSTS_OTGINT			BIT(2)
+#define OTG_GINTSTS_SOF				BIT(3)
+#define OTG_GINTSTS_RXFLVL			BIT(4)
+#define OTG_GINTSTS_USBSUSP			BIT(11)
+#define OTG_GINTSTS_USBRST			BIT(12)
+#define OTG_GINTSTS_ENUMDNE			BIT(13)
+#define OTG_GINTSTS_IEPINT			BIT(18)
+#define OTG_GINTSTS_OEPINT			BIT(19)
+#define OTG_GINTSTS_IISOIXFR			BIT(20)
+#define OTG_GINTSTS_IPXFR_INCOMPISOOUT		BIT(21)
+#define OTG_GINTSTS_LPMINT			BIT(27)
+#define OTG_GINTSTS_SRQINT			BIT(30)
+#define OTG_GINTSTS_WKUPINT			BIT(31)
+
+/* Bit definitions for OTG_GRXSTSP register */
+#define OTG_GRXSTSP_EPNUM			GENMASK(3, 0)
+#define OTG_GRXSTSP_BCNT			GENMASK(14, 4)
+#define OTG_GRXSTSP_BCNT_SHIFT			4U
+#define OTG_GRXSTSP_PKTSTS			GENMASK(20, 17)
+#define OTG_GRXSTSP_PKTSTS_SHIFT		17U
+
+#define STS_GOUT_NAK				1U
+#define STS_DATA_UPDT				2U
+#define STS_XFER_COMP				3U
+#define STS_SETUP_COMP				4U
+#define STS_SETUP_UPDT				6U
+
+/* Bit definitions for OTG_GLPMCFG register */
+#define OTG_GLPMCFG_BESL			GENMASK(5, 2)
+
+/* Bit definitions for OTG_DCFG register */
+#define OTG_DCFG_DAD				GENMASK(10, 4)
+#define OTG_DCFG_DAD_SHIFT			4U
+
+/* Bit definitions for OTG_DCTL register */
+#define OTG_DCTL_RWUSIG				BIT(0)
+#define OTG_DCTL_SDIS				BIT(1)
+#define OTG_DCTL_CGINAK				BIT(8)
+
+/* Bit definitions for OTG_DSTS register */
+#define OTG_DSTS_SUSPSTS			BIT(0)
+#define OTG_DSTS_ENUMSPD_MASK			GENMASK(2, 1)
+#define OTG_DSTS_FNSOF0				BIT(8)
+
+#define OTG_DSTS_ENUMSPD(val)			((val) << 1)
+#define OTG_DSTS_ENUMSPD_HS_PHY_30MHZ_OR_60MHZ	OTG_DSTS_ENUMSPD(0U)
+#define OTG_DSTS_ENUMSPD_FS_PHY_30MHZ_OR_60MHZ	OTG_DSTS_ENUMSPD(1U)
+#define OTG_DSTS_ENUMSPD_LS_PHY_6MHZ		OTG_DSTS_ENUMSPD(2U)
+#define OTG_DSTS_ENUMSPD_FS_PHY_48MHZ		OTG_DSTS_ENUMSPD(3U)
+
+/* Bit definitions for OTG_DIEPMSK register */
+#define OTG_DIEPMSK_XFRCM			BIT(0)
+#define OTG_DIEPMSK_EPDM			BIT(1)
+#define OTG_DIEPMSK_TOM				BIT(3)
+
+/* Bit definitions for OTG_DOEPMSK register */
+#define OTG_DOEPMSK_XFRCM			BIT(0)
+#define OTG_DOEPMSK_EPDM			BIT(1)
+#define OTG_DOEPMSK_STUPM			BIT(3)
+
+/* Bit definitions for OTG_DIEPCTLx registers */
+#define OTG_DIEPCTL_MPSIZ			GENMASK(10, 0)
+#define OTG_DIEPCTL_STALL			BIT(21)
+#define OTG_DIEPCTL_CNAK			BIT(26)
+#define OTG_DIEPCTL_SD0PID_SEVNFRM		BIT(28)
+#define OTG_DIEPCTL_SODDFRM			BIT(29)
+#define OTG_DIEPCTL_EPDIS			BIT(30)
+#define OTG_DIEPCTL_EPENA			BIT(31)
+
+/* Bit definitions for OTG_DIEPINTx registers */
+#define OTG_DIEPINT_XFRC			BIT(0)
+#define OTG_DIEPINT_EPDISD			BIT(1)
+#define OTG_DIEPINT_TOC				BIT(3)
+#define OTG_DIEPINT_ITTXFE			BIT(4)
+#define OTG_DIEPINT_INEPNE			BIT(6)
+#define OTG_DIEPINT_TXFE			BIT(7)
+#define OTG_DIEPINT_TXFE_SHIFT			7U
+
+#define OTG_DIEPINT_MASK			(BIT(13) | BIT(11) | GENMASK(9, 0))
+
+/* Bit definitions for OTG_DIEPTSIZx registers */
+#define OTG_DIEPTSIZ_XFRSIZ			GENMASK(18, 0)
+#define OTG_DIEPTSIZ_PKTCNT			GENMASK(28, 19)
+#define OTG_DIEPTSIZ_PKTCNT_SHIFT		19U
+#define OTG_DIEPTSIZ_MCNT_MASK			GENMASK(30, 29)
+#define OTG_DIEPTSIZ_MCNT_DATA0			BIT(29)
+
+#define OTG_DIEPTSIZ_PKTCNT_1			BIT(19)
+
+/* Bit definitions for OTG_DTXFSTSx registers */
+#define OTG_DTXFSTS_INEPTFSAV			GENMASK(15, 0)
+
+/* Bit definitions for OTG_DOEPCTLx registers */
+#define OTG_DOEPCTL_STALL			BIT(21)
+#define OTG_DOEPCTL_CNAK			BIT(26)
+#define OTG_DOEPCTL_SD0PID_SEVNFRM		BIT(28) /* other than endpoint 0 */
+#define OTG_DOEPCTL_SD1PID_SODDFRM		BIT(29) /* other than endpoint 0 */
+#define OTG_DOEPCTL_EPDIS			BIT(30)
+#define OTG_DOEPCTL_EPENA			BIT(31)
+
+/* Bit definitions for OTG_DOEPTSIZx registers */
+#define OTG_DOEPTSIZ_XFRSIZ			GENMASK(18, 0)
+#define OTG_DOEPTSIZ_PKTCNT			GENMASK(28, 19)
+#define OTG_DOEPTSIZ_RXDPID_STUPCNT		GENMASK(30, 29)
+
+/* Bit definitions for OTG_DOEPINTx registers */
+#define OTG_DOEPINT_XFRC			BIT(0)
+#define OTG_DOEPINT_STUP			BIT(3)
+#define OTG_DOEPINT_OTEPDIS			BIT(4)
+
+#define OTG_DOEPINT_MASK			(GENMASK(15, 12) | GENMASK(9, 8) | GENMASK(6, 0))
+
+#define EP_NB					15U
+#define EP_ALL					0x10U
+
+/*
+ * Flush TX FIFO.
+ * handle: PCD handle.
+ * num: FIFO number.
+ *	   This parameter can be a value from 1 to 15 or EP_ALL.
+ *	   EP_ALL= 0x10 means Flush all TX FIFOs
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_flush_tx_fifo(void *handle, uint32_t num)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint64_t timeout = timeout_init_us(USBD_FIFO_FLUSH_TIMEOUT_US);
+
+	mmio_write_32(usb_base_addr + OTG_GRSTCTL,
+		      OTG_GRSTCTL_TXFFLSH | (uint32_t)(num << OTG_GRSTCTL_TXFNUM_SHIFT));
+
+	while ((mmio_read_32(usb_base_addr + OTG_GRSTCTL) &
+		OTG_GRSTCTL_TXFFLSH) == OTG_GRSTCTL_TXFFLSH) {
+		if (timeout_elapsed(timeout)) {
+			return USBD_TIMEOUT;
+		}
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Flush RX FIFO.
+ * handle: PCD handle.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_flush_rx_fifo(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint64_t timeout = timeout_init_us(USBD_FIFO_FLUSH_TIMEOUT_US);
+
+	mmio_write_32(usb_base_addr + OTG_GRSTCTL, OTG_GRSTCTL_RXFFLSH);
+
+	while ((mmio_read_32(usb_base_addr + OTG_GRSTCTL) &
+		 OTG_GRSTCTL_RXFFLSH) == OTG_GRSTCTL_RXFFLSH) {
+		if (timeout_elapsed(timeout)) {
+			return USBD_TIMEOUT;
+		}
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Return the global USB interrupt status.
+ * handle: PCD handle.
+ * return: Interrupt register value.
+ */
+static uint32_t usb_dwc2_read_int(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	return mmio_read_32(usb_base_addr + OTG_GINTSTS) &
+	       mmio_read_32(usb_base_addr + OTG_GINTMSK);
+}
+
+/*
+ * Return the USB device OUT endpoints interrupt.
+ * handle: PCD handle.
+ * return: Device OUT endpoint interrupts.
+ */
+static uint32_t usb_dwc2_all_out_ep_int(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	return ((mmio_read_32(usb_base_addr + OTG_DAINT) &
+		 mmio_read_32(usb_base_addr + OTG_DAINTMSK)) &
+		OTG_DAINT_OUT_MASK) >> OTG_DAINT_OUT_SHIFT;
+}
+
+/*
+ * Return the USB device IN endpoints interrupt.
+ * handle: PCD handle.
+ * return: Device IN endpoint interrupts.
+ */
+static uint32_t usb_dwc2_all_in_ep_int(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	return ((mmio_read_32(usb_base_addr + OTG_DAINT) &
+		 mmio_read_32(usb_base_addr + OTG_DAINTMSK)) &
+		OTG_DAINT_IN_MASK) >> OTG_DAINT_IN_SHIFT;
+}
+
+/*
+ * Return Device OUT EP interrupt register.
+ * handle: PCD handle.
+ * epnum: Endpoint number.
+ *         This parameter can be a value from 0 to 15.
+ * return: Device OUT EP Interrupt register.
+ */
+static uint32_t usb_dwc2_out_ep_int(void *handle, uint8_t epnum)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	return mmio_read_32(usb_base_addr + OTG_DOEP_BASE +
+			    (epnum * OTG_DOEP_SIZE) + OTG_DOEPINT) &
+	       mmio_read_32(usb_base_addr + OTG_DOEPMSK);
+}
+
+/*
+ * Return Device IN EP interrupt register.
+ * handle: PCD handle.
+ * epnum: Endpoint number.
+ *         This parameter can be a value from 0 to 15.
+ * return: Device IN EP Interrupt register.
+ */
+static uint32_t usb_dwc2_in_ep_int(void *handle, uint8_t epnum)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t msk;
+	uint32_t emp;
+
+	msk = mmio_read_32(usb_base_addr + OTG_DIEPMSK);
+	emp = mmio_read_32(usb_base_addr + OTG_DIEPEMPMSK);
+	msk |= ((emp >> epnum) << OTG_DIEPINT_TXFE_SHIFT) & OTG_DIEPINT_TXFE;
+
+	return mmio_read_32(usb_base_addr + OTG_DIEP_BASE +
+			    (epnum * OTG_DIEP_SIZE) + OTG_DIEPINT) & msk;
+}
+
+/*
+ * Return USB core mode.
+ * handle: PCD handle.
+ * return: Core mode.
+ *         This parameter can be 0 (host) or 1 (device).
+ */
+static uint32_t usb_dwc2_get_mode(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	return mmio_read_32(usb_base_addr + OTG_GINTSTS) & OTG_GINTSTS_CMOD;
+}
+
+/*
+ * Activate EP0 for detup transactions.
+ * handle: PCD handle.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_activate_setup(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uintptr_t reg_offset = usb_base_addr + OTG_DIEP_BASE;
+
+	/* Set the MPS of the IN EP based on the enumeration speed */
+	mmio_clrbits_32(reg_offset + OTG_DIEPCTL, OTG_DIEPCTL_MPSIZ);
+
+	if ((mmio_read_32(usb_base_addr + OTG_DSTS) & OTG_DSTS_ENUMSPD_MASK) ==
+	    OTG_DSTS_ENUMSPD_LS_PHY_6MHZ) {
+		mmio_setbits_32(reg_offset + OTG_DIEPCTL, 3U);
+	}
+
+	mmio_setbits_32(usb_base_addr + OTG_DCTL, OTG_DCTL_CGINAK);
+
+	return USBD_OK;
+}
+
+/*
+ * Prepare the EP0 to start the first control setup.
+ * handle: Selected device.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_ep0_out_start(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uintptr_t reg_offset = usb_base_addr + OTG_DIEP_BASE + OTG_DIEPTSIZ;
+	uint32_t reg_value = 0U;
+
+	/* PKTCNT = 1 and XFRSIZ = 24 bytes for endpoint 0 */
+	reg_value |= OTG_DIEPTSIZ_PKTCNT_1;
+	reg_value |= (EP0_FIFO_SIZE & OTG_DIEPTSIZ_XFRSIZ);
+	reg_value |= OTG_DOEPTSIZ_RXDPID_STUPCNT;
+
+	mmio_write_32(reg_offset, reg_value);
+
+	return USBD_OK;
+}
+
+/*
+ * Write a packet into the TX FIFO associated with the EP/channel.
+ * handle: Selected device.
+ * src: Pointer to source buffer.
+ * ch_ep_num: Endpoint or host channel number.
+ * len: Number of bytes to write.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_write_packet(void *handle, uint8_t *src,
+					  uint8_t ch_ep_num, uint16_t len)
+{
+	uint32_t reg_offset;
+	uint32_t count32b = (len + 3U) / 4U;
+	uint32_t i;
+
+	reg_offset = (uintptr_t)handle + OTG_FIFO_BASE +
+		     (ch_ep_num * OTG_FIFO_SIZE);
+
+	for (i = 0U; i < count32b; i++) {
+		uint32_t src_copy = 0U;
+		uint32_t j;
+
+		/* Data written to FIFO need to be 4 bytes aligned */
+		for (j = 0U; j < 4U; j++) {
+			src_copy += (*(src + j)) << (8U * j);
+		}
+
+		mmio_write_32(reg_offset, src_copy);
+		src += 4U;
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Read a packet from the RX FIFO associated with the EP/channel.
+ * handle: Selected device.
+ * dst: Destination pointer.
+ * len: Number of bytes to read.
+ * return: Pointer to destination buffer.
+ */
+static void *usb_dwc2_read_packet(void *handle, uint8_t *dest, uint16_t len)
+{
+	uint32_t reg_offset;
+	uint32_t count32b = (len + 3U) / 4U;
+	uint32_t i;
+
+	VERBOSE("read packet length %i to 0x%lx\n", len, (uintptr_t)dest);
+
+	reg_offset = (uintptr_t)handle + OTG_FIFO_BASE;
+
+	for (i = 0U; i < count32b; i++) {
+		*(uint32_t *)dest = mmio_read_32(reg_offset);
+		dest += 4U;
+		dsb();
+	}
+
+	return (void *)dest;
+}
+
+/*
+ * Setup and start a transfer over an EP.
+ * handle: Selected device
+ * ep: Pointer to endpoint structure.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_ep_start_xfer(void *handle, struct usbd_ep *ep)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t reg_offset;
+	uint32_t reg_value;
+	uint32_t clear_value;
+
+	if (ep->is_in) {
+		reg_offset = usb_base_addr + OTG_DIEP_BASE + (ep->num * OTG_DIEP_SIZE);
+		clear_value = OTG_DIEPTSIZ_PKTCNT | OTG_DIEPTSIZ_XFRSIZ;
+		if (ep->xfer_len == 0U) {
+			reg_value = OTG_DIEPTSIZ_PKTCNT_1;
+		} else {
+			/*
+			 * Program the transfer size and packet count
+			 * as follows:
+			 * xfersize = N * maxpacket + short_packet
+			 * pktcnt = N + (short_packet exist ? 1 : 0)
+			 */
+			reg_value = (OTG_DIEPTSIZ_PKTCNT &
+				     (((ep->xfer_len + ep->maxpacket - 1U) /
+				       ep->maxpacket) << OTG_DIEPTSIZ_PKTCNT_SHIFT))
+				    | ep->xfer_len;
+
+			if (ep->type == EP_TYPE_ISOC) {
+				clear_value |= OTG_DIEPTSIZ_MCNT_MASK;
+				reg_value |= OTG_DIEPTSIZ_MCNT_DATA0;
+			}
+		}
+
+		mmio_clrsetbits_32(reg_offset + OTG_DIEPTSIZ, clear_value, reg_value);
+
+		if ((ep->type != EP_TYPE_ISOC) && (ep->xfer_len > 0U)) {
+			/* Enable the TX FIFO empty interrupt for this EP */
+			mmio_setbits_32(usb_base_addr + OTG_DIEPEMPMSK, BIT(ep->num));
+		}
+
+		/* EP enable, IN data in FIFO */
+		reg_value = OTG_DIEPCTL_CNAK | OTG_DIEPCTL_EPENA;
+
+		if (ep->type == EP_TYPE_ISOC) {
+			if ((mmio_read_32(usb_base_addr + OTG_DSTS) & OTG_DSTS_FNSOF0) == 0U) {
+				reg_value |= OTG_DIEPCTL_SODDFRM;
+			} else {
+				reg_value |= OTG_DIEPCTL_SD0PID_SEVNFRM;
+			}
+		}
+
+		mmio_setbits_32(reg_offset + OTG_DIEPCTL, reg_value);
+
+		if (ep->type == EP_TYPE_ISOC) {
+			usb_dwc2_write_packet(handle, ep->xfer_buff, ep->num, ep->xfer_len);
+		}
+	} else {
+		reg_offset = usb_base_addr + OTG_DOEP_BASE + (ep->num * OTG_DOEP_SIZE);
+		/*
+		 * Program the transfer size and packet count as follows:
+		 * pktcnt = N
+		 * xfersize = N * maxpacket
+		 */
+		if (ep->xfer_len == 0U) {
+			reg_value = ep->maxpacket | OTG_DIEPTSIZ_PKTCNT_1;
+		} else {
+			uint16_t pktcnt = (ep->xfer_len + ep->maxpacket - 1U) / ep->maxpacket;
+
+			reg_value = (pktcnt << OTG_DIEPTSIZ_PKTCNT_SHIFT) |
+				    (ep->maxpacket * pktcnt);
+		}
+
+		mmio_clrsetbits_32(reg_offset + OTG_DOEPTSIZ,
+				   OTG_DOEPTSIZ_XFRSIZ & OTG_DOEPTSIZ_PKTCNT,
+				   reg_value);
+
+		/* EP enable */
+		reg_value = OTG_DOEPCTL_CNAK | OTG_DOEPCTL_EPENA;
+
+		if (ep->type == EP_TYPE_ISOC) {
+			if ((mmio_read_32(usb_base_addr + OTG_DSTS) & OTG_DSTS_FNSOF0) == 0U) {
+				reg_value |= OTG_DOEPCTL_SD1PID_SODDFRM;
+			} else {
+				reg_value |= OTG_DOEPCTL_SD0PID_SEVNFRM;
+			}
+		}
+
+		mmio_setbits_32(reg_offset + OTG_DOEPCTL, reg_value);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Setup and start a transfer over the EP0.
+ * handle: Selected device.
+ * ep: Pointer to endpoint structure.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_ep0_start_xfer(void *handle, struct usbd_ep *ep)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t reg_offset;
+	uint32_t reg_value;
+
+	if (ep->is_in) {
+		reg_offset = usb_base_addr + OTG_DIEP_BASE +
+			     (ep->num * OTG_DIEP_SIZE);
+
+		if (ep->xfer_len == 0U) {
+			reg_value = OTG_DIEPTSIZ_PKTCNT_1;
+		} else {
+			/*
+			 * Program the transfer size and packet count
+			 * as follows:
+			 * xfersize = N * maxpacket + short_packet
+			 * pktcnt = N + (short_packet exist ? 1 : 0)
+			 */
+
+			if (ep->xfer_len > ep->maxpacket) {
+				ep->xfer_len = ep->maxpacket;
+			}
+
+			reg_value = OTG_DIEPTSIZ_PKTCNT_1 | ep->xfer_len;
+		}
+
+		mmio_clrsetbits_32(reg_offset + OTG_DIEPTSIZ,
+				   OTG_DIEPTSIZ_XFRSIZ | OTG_DIEPTSIZ_PKTCNT,
+				   reg_value);
+
+		/* Enable the TX FIFO empty interrupt for this EP */
+		if (ep->xfer_len > 0U) {
+			mmio_setbits_32(usb_base_addr +	OTG_DIEPEMPMSK,
+					BIT(ep->num));
+		}
+
+		/* EP enable, IN data in FIFO */
+		mmio_setbits_32(reg_offset + OTG_DIEPCTL,
+				OTG_DIEPCTL_CNAK | OTG_DIEPCTL_EPENA);
+	} else {
+		reg_offset = usb_base_addr + OTG_DOEP_BASE +
+			     (ep->num * OTG_DOEP_SIZE);
+
+		/*
+		 * Program the transfer size and packet count as follows:
+		 * pktcnt = N
+		 * xfersize = N * maxpacket
+		 */
+		if (ep->xfer_len > 0U) {
+			ep->xfer_len = ep->maxpacket;
+		}
+
+		reg_value = OTG_DIEPTSIZ_PKTCNT_1 | ep->maxpacket;
+
+		mmio_clrsetbits_32(reg_offset + OTG_DIEPTSIZ,
+				   OTG_DIEPTSIZ_XFRSIZ | OTG_DIEPTSIZ_PKTCNT,
+				   reg_value);
+
+		/* EP enable */
+		mmio_setbits_32(reg_offset + OTG_DOEPCTL,
+				OTG_DOEPCTL_CNAK | OTG_DOEPCTL_EPENA);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Set a stall condition over an EP.
+ * handle: Selected device.
+ * ep: Pointer to endpoint structure.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_ep_set_stall(void *handle, struct usbd_ep *ep)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t reg_offset;
+	uint32_t reg_value;
+
+	if (ep->is_in) {
+		reg_offset = usb_base_addr + OTG_DIEP_BASE +
+			     (ep->num * OTG_DIEP_SIZE);
+		reg_value = mmio_read_32(reg_offset + OTG_DIEPCTL);
+
+		if ((reg_value & OTG_DIEPCTL_EPENA) == 0U) {
+			reg_value &= ~OTG_DIEPCTL_EPDIS;
+		}
+
+		reg_value |= OTG_DIEPCTL_STALL;
+
+		mmio_write_32(reg_offset + OTG_DIEPCTL, reg_value);
+	} else {
+		reg_offset = usb_base_addr + OTG_DOEP_BASE +
+			     (ep->num * OTG_DOEP_SIZE);
+		reg_value = mmio_read_32(reg_offset + OTG_DOEPCTL);
+
+		if ((reg_value & OTG_DOEPCTL_EPENA) == 0U) {
+			reg_value &= ~OTG_DOEPCTL_EPDIS;
+		}
+
+		reg_value |= OTG_DOEPCTL_STALL;
+
+		mmio_write_32(reg_offset + OTG_DOEPCTL, reg_value);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Stop the USB device mode.
+ * handle: Selected device.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_stop_device(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t i;
+
+	/* Disable Int */
+	mmio_clrbits_32(usb_base_addr + OTG_GAHBCFG, OTG_GAHBCFG_GINT);
+
+	/* Clear pending interrupts */
+	for (i = 0U; i < EP_NB; i++) {
+		mmio_write_32(usb_base_addr + OTG_DIEP_BASE + (i * OTG_DIEP_SIZE) + OTG_DIEPINT,
+			      OTG_DIEPINT_MASK);
+		mmio_write_32(usb_base_addr + OTG_DOEP_BASE + (i * OTG_DOEP_SIZE) + OTG_DOEPINT,
+			      OTG_DOEPINT_MASK);
+	}
+
+	mmio_write_32(usb_base_addr + OTG_DAINT, OTG_DAINT_IN_MASK | OTG_DAINT_OUT_MASK);
+
+	/* Clear interrupt masks */
+	mmio_write_32(usb_base_addr + OTG_DIEPMSK, 0U);
+	mmio_write_32(usb_base_addr + OTG_DOEPMSK, 0U);
+	mmio_write_32(usb_base_addr + OTG_DAINTMSK, 0U);
+
+	/* Flush the FIFO */
+	usb_dwc2_flush_rx_fifo(handle);
+	usb_dwc2_flush_tx_fifo(handle, EP_ALL);
+
+	/* Disconnect the USB device by disabling the pull-up/pull-down */
+	mmio_setbits_32((uintptr_t)handle + OTG_DCTL, OTG_DCTL_SDIS);
+
+	return USBD_OK;
+}
+
+/*
+ * Stop the USB device mode.
+ * handle: Selected device.
+ * address: New device address to be assigned.
+ *         This parameter can be a value from 0 to 255.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_set_address(void *handle, uint8_t address)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	mmio_clrsetbits_32(usb_base_addr + OTG_DCFG,
+			   OTG_DCFG_DAD,
+			   address << OTG_DCFG_DAD_SHIFT);
+
+	return USBD_OK;
+}
+
+/*
+ * Check FIFO for the next packet to be loaded.
+ * handle: Selected device.
+ * epnum : Endpoint number.
+ * xfer_len: Block length.
+ * xfer_count: Number of blocks.
+ * maxpacket: Max packet length.
+ * xfer_buff: Buffer pointer.
+ * return: USB status.
+ */
+static enum usb_status usb_dwc2_write_empty_tx_fifo(void *handle,
+						    uint32_t epnum,
+						    uint32_t xfer_len,
+						    uint32_t *xfer_count,
+						    uint32_t maxpacket,
+						    uint8_t **xfer_buff)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t reg_offset;
+	int32_t len;
+	uint32_t len32b;
+	enum usb_status ret;
+
+	len = xfer_len - *xfer_count;
+
+	if ((len > 0) && ((uint32_t)len > maxpacket)) {
+		len = maxpacket;
+	}
+
+	len32b = (len + 3U) / 4U;
+
+	reg_offset = usb_base_addr + OTG_DIEP_BASE + (epnum * OTG_DIEP_SIZE);
+
+	while (((mmio_read_32(reg_offset + OTG_DTXFSTS) &
+		OTG_DTXFSTS_INEPTFSAV) > len32b) &&
+	       (*xfer_count < xfer_len) && (xfer_len != 0U)) {
+		/* Write the FIFO */
+		len = xfer_len - *xfer_count;
+
+		if ((len > 0) && ((uint32_t)len > maxpacket)) {
+			len = maxpacket;
+		}
+
+		len32b = (len + 3U) / 4U;
+
+		ret = usb_dwc2_write_packet(handle, *xfer_buff, epnum, len);
+		if (ret != USBD_OK) {
+			return ret;
+		}
+
+		*xfer_buff  += len;
+		*xfer_count += len;
+	}
+
+	if (len <= 0) {
+		mmio_clrbits_32(usb_base_addr + OTG_DIEPEMPMSK, BIT(epnum));
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * Handle PCD interrupt request.
+ * handle: PCD handle.
+ * param: Pointer to information updated by the IT handling.
+ * return: Action to do after IT handling.
+ */
+static enum usb_action usb_dwc2_it_handler(void *handle, uint32_t *param)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+	uint32_t ep_intr;
+	uint32_t epint;
+	uint32_t epnum;
+	uint32_t temp;
+	enum usb_status ret;
+
+	if (usb_dwc2_get_mode(handle) != USB_OTG_MODE_DEVICE) {
+		return USB_NOTHING;
+	}
+
+	/* Avoid spurious interrupt */
+	if (usb_dwc2_read_int(handle) == 0U) {
+		return USB_NOTHING;
+	}
+
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_MMIS) != 0U) {
+		/* Incorrect mode, acknowledge the interrupt */
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_MMIS);
+	}
+
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_OEPINT) != 0U) {
+		uint32_t reg_offset;
+
+		/* Read in the device interrupt bits */
+		ep_intr = usb_dwc2_all_out_ep_int(handle);
+		epnum = 0U;
+		while ((ep_intr & BIT(0)) != BIT(0)) {
+			epnum++;
+			ep_intr >>= 1;
+		}
+
+		reg_offset = usb_base_addr + OTG_DOEP_BASE + (epnum * OTG_DOEP_SIZE) + OTG_DOEPINT;
+
+		epint = usb_dwc2_out_ep_int(handle, epnum);
+
+		if ((epint & OTG_DOEPINT_XFRC) == OTG_DOEPINT_XFRC) {
+			mmio_write_32(reg_offset, OTG_DOEPINT_XFRC);
+			*param = epnum;
+
+			return USB_DATA_OUT;
+		}
+
+		if ((epint & OTG_DOEPINT_STUP) == OTG_DOEPINT_STUP) {
+			/* Inform  that a setup packet is available */
+			mmio_write_32(reg_offset, OTG_DOEPINT_STUP);
+
+			return USB_SETUP;
+		}
+
+		if ((epint & OTG_DOEPINT_OTEPDIS) == OTG_DOEPINT_OTEPDIS) {
+			mmio_write_32(reg_offset, OTG_DOEPINT_OTEPDIS);
+		}
+	}
+
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_IEPINT) != 0U) {
+		uint32_t reg_offset;
+
+		/* Read in the device interrupt bits */
+		ep_intr = usb_dwc2_all_in_ep_int(handle);
+		epnum = 0U;
+		while ((ep_intr & BIT(0)) != BIT(0)) {
+			epnum++;
+			ep_intr >>= 1;
+		}
+
+		reg_offset = usb_base_addr + OTG_DIEP_BASE + (epnum * OTG_DIEP_SIZE) + OTG_DIEPINT;
+
+		epint = usb_dwc2_in_ep_int(handle, epnum);
+
+		if ((epint & OTG_DIEPINT_XFRC) == OTG_DIEPINT_XFRC) {
+			mmio_clrbits_32(usb_base_addr + OTG_DIEPEMPMSK, BIT(epnum));
+			mmio_write_32(reg_offset, OTG_DIEPINT_XFRC);
+			*param = epnum;
+
+			return USB_DATA_IN;
+		}
+
+		if ((epint & OTG_DIEPINT_TOC) == OTG_DIEPINT_TOC) {
+			mmio_write_32(reg_offset, OTG_DIEPINT_TOC);
+		}
+
+		if ((epint & OTG_DIEPINT_ITTXFE) == OTG_DIEPINT_ITTXFE) {
+			mmio_write_32(reg_offset, OTG_DIEPINT_ITTXFE);
+		}
+
+		if ((epint & OTG_DIEPINT_INEPNE) == OTG_DIEPINT_INEPNE) {
+			mmio_write_32(reg_offset, OTG_DIEPINT_INEPNE);
+		}
+
+		if ((epint & OTG_DIEPINT_EPDISD) == OTG_DIEPINT_EPDISD) {
+			mmio_write_32(reg_offset, OTG_DIEPINT_EPDISD);
+		}
+
+		if ((epint & OTG_DIEPINT_TXFE) == OTG_DIEPINT_TXFE) {
+			*param = epnum;
+
+			return USB_WRITE_EMPTY;
+		}
+	}
+
+	/* Handle resume interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_WKUPINT) != 0U) {
+		INFO("handle USB : Resume\n");
+
+		/* Clear the remote wake-up signaling */
+		mmio_clrbits_32(usb_base_addr + OTG_DCTL, OTG_DCTL_RWUSIG);
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_WKUPINT);
+
+		return USB_RESUME;
+	}
+
+	/* Handle suspend interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_USBSUSP) != 0U) {
+		INFO("handle USB : Suspend int\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_USBSUSP);
+
+		if ((mmio_read_32(usb_base_addr + OTG_DSTS) &
+		     OTG_DSTS_SUSPSTS) == OTG_DSTS_SUSPSTS) {
+			return USB_SUSPEND;
+		}
+	}
+
+	/* Handle LPM interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_LPMINT) != 0U) {
+		INFO("handle USB : LPM int enter in suspend\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_LPMINT);
+		*param = (mmio_read_32(usb_base_addr + OTG_GLPMCFG) &
+			  OTG_GLPMCFG_BESL) >> 2;
+
+		return USB_LPM;
+	}
+
+	/* Handle reset interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_USBRST) != 0U) {
+		INFO("handle USB : Reset\n");
+
+		mmio_clrbits_32(usb_base_addr + OTG_DCTL, OTG_DCTL_RWUSIG);
+
+		usb_dwc2_flush_tx_fifo(handle, 0U);
+
+		mmio_write_32(usb_base_addr + OTG_DAINT, OTG_DAINT_IN_MASK | OTG_DAINT_OUT_MASK);
+		mmio_setbits_32(usb_base_addr + OTG_DAINTMSK, OTG_DAINT_EP0_IN | OTG_DAINT_EP0_OUT);
+
+		mmio_setbits_32(usb_base_addr + OTG_DOEPMSK, OTG_DOEPMSK_STUPM |
+							     OTG_DOEPMSK_XFRCM |
+							     OTG_DOEPMSK_EPDM);
+		mmio_setbits_32(usb_base_addr + OTG_DIEPMSK, OTG_DIEPMSK_TOM |
+							     OTG_DIEPMSK_XFRCM |
+							     OTG_DIEPMSK_EPDM);
+
+		/* Set default address to 0 */
+		mmio_clrbits_32(usb_base_addr + OTG_DCFG, OTG_DCFG_DAD);
+
+		/* Setup EP0 to receive SETUP packets */
+		ret = usb_dwc2_ep0_out_start(handle);
+		if (ret != USBD_OK) {
+			return ret;
+		}
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_USBRST);
+
+		return USB_RESET;
+	}
+
+	/* Handle enumeration done interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_ENUMDNE) != 0U) {
+		ret = usb_dwc2_activate_setup(handle);
+		if (ret != USBD_OK) {
+			return ret;
+		}
+
+		mmio_clrbits_32(usb_base_addr + OTG_GUSBCFG, OTG_GUSBCFG_TRDT);
+
+		mmio_setbits_32(usb_base_addr + OTG_GUSBCFG,
+				(USBD_HS_TRDT_VALUE << OTG_GUSBCFG_TRDT_SHIFT) & OTG_GUSBCFG_TRDT);
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_ENUMDNE);
+
+		return USB_ENUM_DONE;
+	}
+
+	/* Handle RXQLevel interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_RXFLVL) != 0U) {
+		mmio_clrbits_32(usb_base_addr + OTG_GINTMSK,
+				OTG_GINTSTS_RXFLVL);
+
+		temp = mmio_read_32(usb_base_addr + OTG_GRXSTSP);
+
+		*param = temp & OTG_GRXSTSP_EPNUM;
+		*param |= (temp & OTG_GRXSTSP_BCNT) << (USBD_OUT_COUNT_SHIFT -
+							OTG_GRXSTSP_BCNT_SHIFT);
+
+		if (((temp & OTG_GRXSTSP_PKTSTS) >> OTG_GRXSTSP_PKTSTS_SHIFT) == STS_DATA_UPDT) {
+			if ((temp & OTG_GRXSTSP_BCNT) != 0U) {
+				mmio_setbits_32(usb_base_addr + OTG_GINTMSK, OTG_GINTSTS_RXFLVL);
+
+				return USB_READ_DATA_PACKET;
+			}
+		} else if (((temp & OTG_GRXSTSP_PKTSTS) >> OTG_GRXSTSP_PKTSTS_SHIFT) ==
+			    STS_SETUP_UPDT) {
+			mmio_setbits_32(usb_base_addr + OTG_GINTMSK, OTG_GINTSTS_RXFLVL);
+
+			return USB_READ_SETUP_PACKET;
+		}
+
+		mmio_setbits_32(usb_base_addr + OTG_GINTMSK, OTG_GINTSTS_RXFLVL);
+	}
+
+	/* Handle SOF interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_SOF) != 0U) {
+		INFO("handle USB : SOF\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_SOF);
+
+		return USB_SOF;
+	}
+
+	/* Handle incomplete ISO IN interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_IISOIXFR) != 0U) {
+		INFO("handle USB : ISO IN\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS,
+			      OTG_GINTSTS_IISOIXFR);
+	}
+
+	/* Handle incomplete ISO OUT interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_IPXFR_INCOMPISOOUT) !=
+	    0U) {
+		INFO("handle USB : ISO OUT\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS,
+			      OTG_GINTSTS_IPXFR_INCOMPISOOUT);
+	}
+
+	/* Handle connection event interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_SRQINT) != 0U) {
+		INFO("handle USB : Connect\n");
+
+		mmio_write_32(usb_base_addr + OTG_GINTSTS, OTG_GINTSTS_SRQINT);
+	}
+
+	/* Handle disconnection event interrupt */
+	if ((usb_dwc2_read_int(handle) & OTG_GINTSTS_OTGINT) != 0U) {
+		INFO("handle USB : Disconnect\n");
+
+		temp = mmio_read_32(usb_base_addr + OTG_GOTGINT);
+
+		if ((temp & OTG_GOTGINT_SEDET) == OTG_GOTGINT_SEDET) {
+			return USB_DISCONNECT;
+		}
+	}
+
+	return USB_NOTHING;
+}
+
+/*
+ * Start the usb device mode
+ * usb_core_handle: USB core driver handle.
+ * return  USB status.
+ */
+static enum usb_status usb_dwc2_start_device(void *handle)
+{
+	uintptr_t usb_base_addr = (uintptr_t)handle;
+
+	mmio_clrbits_32(usb_base_addr + OTG_DCTL, OTG_DCTL_SDIS);
+	mmio_setbits_32(usb_base_addr + OTG_GAHBCFG, OTG_GAHBCFG_GINT);
+
+	return USBD_OK;
+}
+
+static const struct usb_driver usb_dwc2driver = {
+	.ep0_out_start = usb_dwc2_ep0_out_start,
+	.ep_start_xfer = usb_dwc2_ep_start_xfer,
+	.ep0_start_xfer = usb_dwc2_ep0_start_xfer,
+	.write_packet = usb_dwc2_write_packet,
+	.read_packet = usb_dwc2_read_packet,
+	.ep_set_stall = usb_dwc2_ep_set_stall,
+	.start_device = usb_dwc2_start_device,
+	.stop_device = usb_dwc2_stop_device,
+	.set_address = usb_dwc2_set_address,
+	.write_empty_tx_fifo = usb_dwc2_write_empty_tx_fifo,
+	.it_handler = usb_dwc2_it_handler
+};
+
+/*
+ * Initialize USB DWC2 driver.
+ * usb_core_handle: USB core driver handle.
+ * pcd_handle: PCD handle.
+ * base_register: USB global register base address.
+ */
+void stm32mp1_usb_init_driver(struct usb_handle *usb_core_handle,
+			      struct pcd_handle *pcd_handle,
+			      void *base_register)
+{
+	register_usb_driver(usb_core_handle, pcd_handle, &usb_dwc2driver,
+			    base_register);
+}
diff --git a/drivers/ufs/ufs.c b/drivers/ufs/ufs.c
index 6dbf372..ae42e32 100644
--- a/drivers/ufs/ufs.c
+++ b/drivers/ufs/ufs.c
@@ -34,6 +34,9 @@
 {
 	unsigned int data;
 
+	if (base == 0 || cmd == NULL)
+		return -EINVAL;
+
 	data = mmio_read_32(base + HCS);
 	if ((data & HCS_UCRDY) == 0)
 		return -EBUSY;
@@ -54,9 +57,13 @@
 {
 	uintptr_t base;
 	unsigned int data;
-	int retries;
+	int result, retries;
+	uic_cmd_t cmd;
 
-	assert((ufs_params.reg_base != 0) && (val != NULL));
+	assert(ufs_params.reg_base != 0);
+
+	if (val == NULL)
+		return -EINVAL;
 
 	base = ufs_params.reg_base;
 	for (retries = 0; retries < 100; retries++) {
@@ -68,19 +75,20 @@
 	if (retries >= 100)
 		return -EBUSY;
 
-	mmio_write_32(base + IS, ~0);
-	mmio_write_32(base + UCMDARG1, (attr << 16) | GEN_SELECTOR_IDX(idx));
-	mmio_write_32(base + UCMDARG2, 0);
-	mmio_write_32(base + UCMDARG3, 0);
-	mmio_write_32(base + UICCMD, DME_GET);
-	do {
+	cmd.arg1 = (attr << 16) | GEN_SELECTOR_IDX(idx);
+	cmd.arg2 = 0;
+	cmd.arg3 = 0;
+	cmd.op = DME_GET;
+	for (retries = 0; retries < UFS_UIC_COMMAND_RETRIES; ++retries) {
+		result = ufshc_send_uic_cmd(base, &cmd);
+		if (result == 0)
+			break;
 		data = mmio_read_32(base + IS);
 		if (data & UFS_INT_UE)
 			return -EINVAL;
-	} while ((data & UFS_INT_UCCS) == 0);
-	mmio_write_32(base + IS, UFS_INT_UCCS);
-	data = mmio_read_32(base + UCMDARG2) & CONFIG_RESULT_CODE_MASK;
-	assert(data == 0);
+	}
+	if (retries >= UFS_UIC_COMMAND_RETRIES)
+		return -EIO;
 
 	*val = mmio_read_32(base + UCMDARG3);
 	return 0;
@@ -90,58 +98,101 @@
 {
 	uintptr_t base;
 	unsigned int data;
+	int result, retries;
+	uic_cmd_t cmd;
 
 	assert((ufs_params.reg_base != 0));
 
 	base = ufs_params.reg_base;
-	data = mmio_read_32(base + HCS);
-	if ((data & HCS_UCRDY) == 0)
-		return -EBUSY;
-	mmio_write_32(base + IS, ~0);
-	mmio_write_32(base + UCMDARG1, (attr << 16) | GEN_SELECTOR_IDX(idx));
-	mmio_write_32(base + UCMDARG2, 0);
-	mmio_write_32(base + UCMDARG3, val);
-	mmio_write_32(base + UICCMD, DME_SET);
-	do {
+	cmd.arg1 = (attr << 16) | GEN_SELECTOR_IDX(idx);
+	cmd.arg2 = 0;
+	cmd.arg3 = val;
+	cmd.op = DME_SET;
+
+	for (retries = 0; retries < UFS_UIC_COMMAND_RETRIES; ++retries) {
+		result = ufshc_send_uic_cmd(base, &cmd);
+		if (result == 0)
+			break;
 		data = mmio_read_32(base + IS);
 		if (data & UFS_INT_UE)
 			return -EINVAL;
-	} while ((data & UFS_INT_UCCS) == 0);
-	mmio_write_32(base + IS, UFS_INT_UCCS);
-	data = mmio_read_32(base + UCMDARG2) & CONFIG_RESULT_CODE_MASK;
-	assert(data == 0);
+	}
+	if (retries >= UFS_UIC_COMMAND_RETRIES)
+		return -EIO;
+
 	return 0;
 }
 
-static void ufshc_reset(uintptr_t base)
+static int ufshc_hce_enable(uintptr_t base)
 {
 	unsigned int data;
+	int retries;
 
 	/* Enable Host Controller */
 	mmio_write_32(base + HCE, HCE_ENABLE);
+
 	/* Wait until basic initialization sequence completed */
-	do {
+	for (retries = 0; retries < HCE_ENABLE_INNER_RETRIES; ++retries) {
 		data = mmio_read_32(base + HCE);
-	} while ((data & HCE_ENABLE) == 0);
+		if (data & HCE_ENABLE) {
+			break;
+		}
+		udelay(HCE_ENABLE_TIMEOUT_US);
+	}
+	if (retries >= HCE_ENABLE_INNER_RETRIES) {
+		return -ETIMEDOUT;
+	}
+
+	return 0;
+}
+
+static int ufshc_reset(uintptr_t base)
+{
+	unsigned int data;
+	int retries, result;
+
+	for (retries = 0; retries < HCE_ENABLE_OUTER_RETRIES; ++retries) {
+		result = ufshc_hce_enable(base);
+		if (result == 0) {
+			break;
+		}
+	}
+	if (retries >= HCE_ENABLE_OUTER_RETRIES) {
+		return -EIO;
+	}
 
 	/* Enable Interrupts */
 	data = UFS_INT_UCCS | UFS_INT_ULSS | UFS_INT_UE | UFS_INT_UTPES |
 	       UFS_INT_DFES | UFS_INT_HCFES | UFS_INT_SBFES;
 	mmio_write_32(base + IE, data);
+
+	return 0;
+}
+
+static int ufshc_dme_link_startup(uintptr_t base)
+{
+	uic_cmd_t cmd;
+
+	memset(&cmd, 0, sizeof(cmd));
+	cmd.op = DME_LINKSTARTUP;
+	return ufshc_send_uic_cmd(base, &cmd);
 }
 
 static int ufshc_link_startup(uintptr_t base)
 {
-	uic_cmd_t cmd;
 	int data, result;
 	int retries;
 
-	for (retries = 10; retries > 0; retries--) {
-		memset(&cmd, 0, sizeof(cmd));
-		cmd.op = DME_LINKSTARTUP;
-		result = ufshc_send_uic_cmd(base, &cmd);
-		if (result != 0)
+	for (retries = DME_LINKSTARTUP_RETRIES; retries > 0; retries--) {
+		result = ufshc_dme_link_startup(base);
+		if (result != 0) {
+			/* Reset controller before trying again */
+			result = ufshc_reset(base);
+			if (result != 0) {
+				return result;
+			}
 			continue;
+		}
 		while ((mmio_read_32(base + HCS) & HCS_DP) == 0)
 			;
 		data = mmio_read_32(base + IS);
@@ -772,7 +823,8 @@
 		assert((ops != NULL) && (ops->phy_init != NULL) &&
 		       (ops->phy_set_pwr_mode != NULL));
 
-		ufshc_reset(ufs_params.reg_base);
+		result = ufshc_reset(ufs_params.reg_base);
+		assert(result == 0);
 		ops->phy_init(&ufs_params);
 		result = ufshc_link_startup(ufs_params.reg_base);
 		assert(result == 0);
diff --git a/drivers/usb/usb_device.c b/drivers/usb/usb_device.c
new file mode 100644
index 0000000..031e678
--- /dev/null
+++ b/drivers/usb/usb_device.c
@@ -0,0 +1,845 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <drivers/usb_device.h>
+
+/* Define for EP address */
+#define EP_DIR_MASK		BIT(7)
+#define EP_DIR_IN		BIT(7)
+#define EP_NUM_MASK		GENMASK(3, 0)
+
+#define EP0_IN			(0U | EP_DIR_IN)
+#define EP0_OUT			0U
+
+/* USB address between 1 through 127 = 0x7F mask */
+#define ADDRESS_MASK		GENMASK(6, 0)
+
+/*
+ * Set a STALL condition over an endpoint
+ * pdev: USB handle
+ * ep_addr: endpoint address
+ * return : status
+ */
+static enum usb_status usb_core_set_stall(struct usb_handle *pdev, uint8_t ep_addr)
+{
+	struct usbd_ep *ep;
+	struct pcd_handle *hpcd = (struct pcd_handle *)pdev->data;
+	uint8_t num;
+
+	num = ep_addr & EP_NUM_MASK;
+	if (num >= USBD_EP_NB) {
+		return USBD_FAIL;
+	}
+	if ((EP_DIR_MASK & ep_addr) == EP_DIR_IN) {
+		ep = &hpcd->in_ep[num];
+		ep->is_in = true;
+	} else {
+		ep = &hpcd->out_ep[num];
+		ep->is_in = false;
+	}
+	ep->num = num;
+
+	pdev->driver->ep_set_stall(hpcd->instance, ep);
+	if (num == 0U) {
+		pdev->driver->ep0_out_start(hpcd->instance);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_get_desc
+ *         Handle Get Descriptor requests
+ * pdev : device instance
+ * req : usb request
+ */
+static void usb_core_get_desc(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	uint16_t len;
+	uint8_t *pbuf;
+	uint8_t desc_type = HIBYTE(req->value);
+	uint8_t desc_idx = LOBYTE(req->value);
+
+	switch (desc_type) {
+	case USB_DESC_TYPE_DEVICE:
+		pbuf = pdev->desc->get_device_desc(&len);
+		break;
+
+	case USB_DESC_TYPE_CONFIGURATION:
+		pbuf = pdev->desc->get_config_desc(&len);
+		break;
+
+	case USB_DESC_TYPE_STRING:
+		switch (desc_idx) {
+		case USBD_IDX_LANGID_STR:
+			pbuf = pdev->desc->get_lang_id_desc(&len);
+			break;
+
+		case USBD_IDX_MFC_STR:
+			pbuf = pdev->desc->get_manufacturer_desc(&len);
+			break;
+
+		case USBD_IDX_PRODUCT_STR:
+			pbuf = pdev->desc->get_product_desc(&len);
+			break;
+
+		case USBD_IDX_SERIAL_STR:
+			pbuf = pdev->desc->get_serial_desc(&len);
+			break;
+
+		case USBD_IDX_CONFIG_STR:
+			pbuf = pdev->desc->get_configuration_desc(&len);
+			break;
+
+		case USBD_IDX_INTERFACE_STR:
+			pbuf = pdev->desc->get_interface_desc(&len);
+			break;
+
+		/* For all USER string */
+		case USBD_IDX_USER0_STR:
+		default:
+			pbuf = pdev->desc->get_usr_desc(desc_idx - USBD_IDX_USER0_STR, &len);
+			break;
+		}
+		break;
+
+	case USB_DESC_TYPE_DEVICE_QUALIFIER:
+		pbuf = pdev->desc->get_device_qualifier_desc(&len);
+		break;
+
+	case USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION:
+		if (pdev->desc->get_other_speed_config_desc == NULL) {
+			usb_core_ctl_error(pdev);
+			return;
+		}
+		pbuf = pdev->desc->get_other_speed_config_desc(&len);
+		break;
+
+	default:
+		ERROR("Unknown request %i\n", desc_type);
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	if ((len != 0U) && (req->length != 0U)) {
+		len = MIN(len, req->length);
+
+		/* Start the transfer */
+		usb_core_transmit_ep0(pdev, pbuf, len);
+	}
+}
+
+/*
+ * usb_core_set_config
+ *         Handle Set device configuration request
+ * pdev : device instance
+ * req : usb request
+ */
+static void usb_core_set_config(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	static uint8_t cfgidx;
+
+	cfgidx = LOBYTE(req->value);
+
+	if (cfgidx > USBD_MAX_NUM_CONFIGURATION) {
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	switch (pdev->dev_state) {
+	case USBD_STATE_ADDRESSED:
+		if (cfgidx != 0U) {
+			pdev->dev_config = cfgidx;
+			pdev->dev_state = USBD_STATE_CONFIGURED;
+			if (!pdev->class) {
+				usb_core_ctl_error(pdev);
+				return;
+			}
+			/* Set configuration and Start the Class */
+			if (pdev->class->init(pdev, cfgidx) != 0U) {
+				usb_core_ctl_error(pdev);
+				return;
+			}
+		}
+		break;
+
+	case USBD_STATE_CONFIGURED:
+		if (cfgidx == 0U) {
+			pdev->dev_state = USBD_STATE_ADDRESSED;
+			pdev->dev_config = cfgidx;
+			pdev->class->de_init(pdev, cfgidx);
+		} else if (cfgidx != pdev->dev_config) {
+			if (pdev->class == NULL) {
+				usb_core_ctl_error(pdev);
+				return;
+			}
+			/* Clear old configuration */
+			pdev->class->de_init(pdev, pdev->dev_config);
+			/* Set new configuration */
+			pdev->dev_config = cfgidx;
+			/* Set configuration and start the USB class */
+			if (pdev->class->init(pdev, cfgidx) != 0U) {
+				usb_core_ctl_error(pdev);
+				return;
+			}
+		}
+		break;
+
+	default:
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	/* Send status */
+	usb_core_transmit_ep0(pdev, NULL, 0U);
+}
+
+/*
+ * usb_core_get_status
+ *         Handle Get Status request
+ * pdev : device instance
+ * req : usb request
+ */
+static void usb_core_get_status(struct usb_handle *pdev,
+				struct usb_setup_req *req)
+{
+	if ((pdev->dev_state != USBD_STATE_ADDRESSED) &&
+	    (pdev->dev_state != USBD_STATE_CONFIGURED)) {
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	pdev->dev_config_status = USB_CONFIG_SELF_POWERED;
+
+	if (pdev->dev_remote_wakeup != 0U) {
+		pdev->dev_config_status |= USB_CONFIG_REMOTE_WAKEUP;
+	}
+
+	/* Start the transfer */
+	usb_core_transmit_ep0(pdev, (uint8_t *)&pdev->dev_config_status, 2U);
+}
+
+/*
+ * usb_core_set_address
+ *         Set device address
+ * pdev : device instance
+ * req : usb request
+ */
+static void usb_core_set_address(struct usb_handle *pdev,
+				 struct usb_setup_req *req)
+{
+	uint8_t dev_addr;
+
+	if ((req->index != 0U) || (req->length != 0U)) {
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	dev_addr = req->value & ADDRESS_MASK;
+	if (pdev->dev_state != USBD_STATE_DEFAULT) {
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	pdev->dev_address = dev_addr;
+	pdev->driver->set_address(((struct pcd_handle *)(pdev->data))->instance, dev_addr);
+
+	/* Send status */
+	usb_core_transmit_ep0(pdev, NULL, 0U);
+
+	if (dev_addr != 0U) {
+		pdev->dev_state  = USBD_STATE_ADDRESSED;
+	} else {
+		pdev->dev_state  = USBD_STATE_DEFAULT;
+	}
+}
+
+/*
+ * usb_core_dev_req
+ *         Handle standard usb device requests
+ * pdev : device instance
+ * req : usb request
+ * return : status
+ */
+static enum usb_status usb_core_dev_req(struct usb_handle *pdev,
+					struct usb_setup_req *req)
+{
+	VERBOSE("receive request %i\n", req->b_request);
+	switch (req->b_request) {
+	case USB_REQ_GET_DESCRIPTOR:
+		usb_core_get_desc(pdev, req);
+		break;
+
+	case USB_REQ_SET_CONFIGURATION:
+		usb_core_set_config(pdev, req);
+		break;
+
+	case USB_REQ_GET_STATUS:
+		usb_core_get_status(pdev, req);
+		break;
+
+	case USB_REQ_SET_ADDRESS:
+		usb_core_set_address(pdev, req);
+		break;
+
+	case USB_REQ_GET_CONFIGURATION:
+	case USB_REQ_SET_FEATURE:
+	case USB_REQ_CLEAR_FEATURE:
+	default:
+		ERROR("NOT SUPPORTED %i\n", req->b_request);
+		usb_core_ctl_error(pdev);
+		break;
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_itf_req
+ *         Handle standard usb interface requests
+ * pdev : device instance
+ * req : usb request
+ * return : status
+ */
+static enum usb_status usb_core_itf_req(struct usb_handle *pdev,
+					struct usb_setup_req *req)
+{
+	if (pdev->dev_state != USBD_STATE_CONFIGURED) {
+		usb_core_ctl_error(pdev);
+		return USBD_OK;
+	}
+
+	if (LOBYTE(req->index) <= USBD_MAX_NUM_INTERFACES) {
+		pdev->class->setup(pdev, req);
+
+		if (req->length == 0U) {
+			usb_core_transmit_ep0(pdev, NULL, 0U);
+		}
+	} else {
+		usb_core_ctl_error(pdev);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_setup_stage
+ *         Handle the setup stage
+ * pdev: device instance
+ * psetup : setup buffer
+ * return : status
+ */
+static enum usb_status usb_core_setup_stage(struct usb_handle *pdev,
+					    uint8_t *psetup)
+{
+	struct usb_setup_req *req = &pdev->request;
+
+	/* Copy setup buffer into req structure */
+	req->bm_request = psetup[0];
+	req->b_request = psetup[1];
+	req->value = psetup[2] + (psetup[3] << 8);
+	req->index = psetup[4] + (psetup[5] << 8);
+	req->length = psetup[6] + (psetup[7] << 8);
+
+	pdev->ep0_state = USBD_EP0_SETUP;
+	pdev->ep0_data_len = pdev->request.length;
+
+	switch (pdev->request.bm_request & USB_REQ_RECIPIENT_MASK) {
+	case USB_REQ_RECIPIENT_DEVICE:
+		usb_core_dev_req(pdev, &pdev->request);
+		break;
+
+	case USB_REQ_RECIPIENT_INTERFACE:
+		usb_core_itf_req(pdev, &pdev->request);
+		break;
+
+	case USB_REQ_RECIPIENT_ENDPOINT:
+	default:
+		ERROR("receive unsupported request %i",
+		      pdev->request.bm_request & USB_REQ_RECIPIENT_MASK);
+		usb_core_set_stall(pdev, pdev->request.bm_request & USB_REQ_DIRECTION);
+		return USBD_FAIL;
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_data_out
+ *         Handle data OUT stage
+ * pdev: device instance
+ * epnum: endpoint index
+ * pdata: buffer to sent
+ * return : status
+ */
+static enum usb_status usb_core_data_out(struct usb_handle *pdev, uint8_t epnum,
+					 uint8_t *pdata)
+{
+	struct usb_endpoint *pep;
+
+	if (epnum == 0U) {
+		pep = &pdev->ep_out[0];
+		if (pdev->ep0_state == USBD_EP0_DATA_OUT) {
+			if (pep->rem_length > pep->maxpacket) {
+				pep->rem_length -= pep->maxpacket;
+
+				usb_core_receive(pdev, 0U, pdata,
+						 MIN(pep->rem_length,
+						     pep->maxpacket));
+			} else {
+				if (pdev->class->ep0_rx_ready &&
+				    (pdev->dev_state == USBD_STATE_CONFIGURED)) {
+					pdev->class->ep0_rx_ready(pdev);
+				}
+
+				usb_core_transmit_ep0(pdev, NULL, 0U);
+			}
+		}
+	} else if (pdev->class->data_out != NULL &&
+		   (pdev->dev_state == USBD_STATE_CONFIGURED)) {
+		pdev->class->data_out(pdev, epnum);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_data_in
+ *         Handle data in stage
+ * pdev: device instance
+ * epnum: endpoint index
+ * pdata: buffer to fill
+ * return : status
+ */
+static enum usb_status usb_core_data_in(struct usb_handle *pdev, uint8_t epnum,
+					uint8_t *pdata)
+{
+	if (epnum == 0U) {
+		struct usb_endpoint *pep = &pdev->ep_in[0];
+
+		if (pdev->ep0_state == USBD_EP0_DATA_IN) {
+			if (pep->rem_length > pep->maxpacket) {
+				pep->rem_length -= pep->maxpacket;
+
+				usb_core_transmit(pdev, 0U, pdata,
+						  pep->rem_length);
+
+				/* Prepare EP for premature end of transfer */
+				usb_core_receive(pdev, 0U, NULL, 0U);
+			} else {
+				/* Last packet is MPS multiple, send ZLP packet */
+				if ((pep->total_length % pep->maxpacket == 0U) &&
+				    (pep->total_length >= pep->maxpacket) &&
+				    (pep->total_length < pdev->ep0_data_len)) {
+					usb_core_transmit(pdev, 0U, NULL, 0U);
+
+					pdev->ep0_data_len = 0U;
+
+					/* Prepare endpoint for premature end of transfer */
+					usb_core_receive(pdev, 0U, NULL, 0U);
+				} else {
+					if (pdev->class->ep0_tx_sent != NULL &&
+					    (pdev->dev_state ==
+					     USBD_STATE_CONFIGURED)) {
+						pdev->class->ep0_tx_sent(pdev);
+					}
+					/* Start the transfer */
+					usb_core_receive_ep0(pdev, NULL, 0U);
+				}
+			}
+		}
+	} else if ((pdev->class->data_in != NULL) &&
+		  (pdev->dev_state == USBD_STATE_CONFIGURED)) {
+		pdev->class->data_in(pdev, epnum);
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_suspend
+ *         Handle suspend event
+ * pdev : device instance
+ * return : status
+ */
+static enum usb_status usb_core_suspend(struct usb_handle  *pdev)
+{
+	INFO("USB Suspend mode\n");
+	pdev->dev_old_state =  pdev->dev_state;
+	pdev->dev_state  = USBD_STATE_SUSPENDED;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_resume
+ *         Handle resume event
+ * pdev : device instance
+ * return : status
+ */
+static enum usb_status usb_core_resume(struct usb_handle *pdev)
+{
+	INFO("USB Resume\n");
+	pdev->dev_state = pdev->dev_old_state;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_sof
+ *         Handle SOF event
+ * pdev : device instance
+ * return : status
+ */
+static enum usb_status usb_core_sof(struct usb_handle *pdev)
+{
+	if (pdev->dev_state == USBD_STATE_CONFIGURED) {
+		if (pdev->class->sof != NULL) {
+			pdev->class->sof(pdev);
+		}
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_disconnect
+ *         Handle device disconnection event
+ * pdev : device instance
+ * return : status
+ */
+static enum usb_status usb_core_disconnect(struct usb_handle *pdev)
+{
+	/* Free class resources */
+	pdev->dev_state = USBD_STATE_DEFAULT;
+	pdev->class->de_init(pdev, pdev->dev_config);
+
+	return USBD_OK;
+}
+
+enum usb_status usb_core_handle_it(struct usb_handle *pdev)
+{
+	uint32_t param = 0U;
+	uint32_t len = 0U;
+	struct usbd_ep *ep;
+
+	switch (pdev->driver->it_handler(pdev->data->instance, &param)) {
+	case USB_DATA_OUT:
+		usb_core_data_out(pdev, param,
+				  pdev->data->out_ep[param].xfer_buff);
+		break;
+
+	case USB_DATA_IN:
+		usb_core_data_in(pdev, param,
+				 pdev->data->in_ep[param].xfer_buff);
+		break;
+
+	case USB_SETUP:
+		usb_core_setup_stage(pdev, (uint8_t *)pdev->data->setup);
+		break;
+
+	case USB_ENUM_DONE:
+		break;
+
+	case USB_READ_DATA_PACKET:
+		ep = &pdev->data->out_ep[param &  USBD_OUT_EPNUM_MASK];
+		len = (param &  USBD_OUT_COUNT_MASK) >> USBD_OUT_COUNT_SHIFT;
+		pdev->driver->read_packet(pdev->data->instance,
+					  ep->xfer_buff, len);
+		ep->xfer_buff += len;
+		ep->xfer_count += len;
+		break;
+
+	case USB_READ_SETUP_PACKET:
+		ep = &pdev->data->out_ep[param &  USBD_OUT_EPNUM_MASK];
+		len = (param &  USBD_OUT_COUNT_MASK) >> 0x10;
+		pdev->driver->read_packet(pdev->data->instance,
+					  (uint8_t *)pdev->data->setup, 8);
+		ep->xfer_count += len;
+		break;
+
+	case USB_RESET:
+		pdev->dev_state = USBD_STATE_DEFAULT;
+		break;
+
+	case USB_RESUME:
+		if (pdev->data->lpm_state == LPM_L1) {
+			pdev->data->lpm_state = LPM_L0;
+		} else {
+			usb_core_resume(pdev);
+		}
+		break;
+
+	case USB_SUSPEND:
+		usb_core_suspend(pdev);
+		break;
+
+	case USB_LPM:
+		if (pdev->data->lpm_state == LPM_L0) {
+			pdev->data->lpm_state = LPM_L1;
+		} else {
+			usb_core_suspend(pdev);
+		}
+		break;
+
+	case USB_SOF:
+		usb_core_sof(pdev);
+		break;
+
+	case USB_DISCONNECT:
+		usb_core_disconnect(pdev);
+		break;
+
+	case USB_WRITE_EMPTY:
+		pdev->driver->write_empty_tx_fifo(pdev->data->instance, param,
+				     pdev->data->in_ep[param].xfer_len,
+				     (uint32_t *)&pdev->data->in_ep[param].xfer_count,
+				     pdev->data->in_ep[param].maxpacket,
+				     &pdev->data->in_ep[param].xfer_buff);
+		break;
+
+	case USB_NOTHING:
+	default:
+		break;
+	}
+
+	return USBD_OK;
+}
+
+static void usb_core_start_xfer(struct usb_handle *pdev,
+				void *handle,
+				struct usbd_ep *ep)
+{
+	if (ep->num == 0U) {
+		pdev->driver->ep0_start_xfer(handle, ep);
+	} else {
+		pdev->driver->ep_start_xfer(handle, ep);
+	}
+}
+
+/*
+ * usb_core_receive
+ *          Receive an amount of data
+ * pdev: USB handle
+ * ep_addr: endpoint address
+ * buf: pointer to the reception buffer
+ * len: amount of data to be received
+ * return : status
+ */
+enum usb_status usb_core_receive(struct usb_handle *pdev, uint8_t ep_addr,
+				 uint8_t *buf, uint32_t len)
+{
+	struct usbd_ep *ep;
+	struct pcd_handle *hpcd = (struct pcd_handle *)pdev->data;
+	uint8_t num;
+
+	num = ep_addr & EP_NUM_MASK;
+	if (num >= USBD_EP_NB) {
+		return USBD_FAIL;
+	}
+	ep = &hpcd->out_ep[num];
+
+	/* Setup and start the Xfer */
+	ep->xfer_buff = buf;
+	ep->xfer_len = len;
+	ep->xfer_count = 0U;
+	ep->is_in = false;
+	ep->num = num;
+
+	usb_core_start_xfer(pdev, hpcd->instance, ep);
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_transmit
+ *          Send an amount of data
+ * pdev: USB handle
+ * ep_addr: endpoint address
+ * buf: pointer to the transmission buffer
+ * len: amount of data to be sent
+ * return : status
+ */
+enum usb_status usb_core_transmit(struct usb_handle *pdev, uint8_t ep_addr,
+				  uint8_t *buf, uint32_t len)
+{
+	struct usbd_ep *ep;
+	struct pcd_handle *hpcd = (struct pcd_handle *)pdev->data;
+	uint8_t num;
+
+	num = ep_addr & EP_NUM_MASK;
+	if (num >= USBD_EP_NB) {
+		return USBD_FAIL;
+	}
+	ep = &hpcd->in_ep[num];
+
+	/* Setup and start the Xfer */
+	ep->xfer_buff = buf;
+	ep->xfer_len = len;
+	ep->xfer_count = 0U;
+	ep->is_in = true;
+	ep->num = num;
+
+	usb_core_start_xfer(pdev, hpcd->instance, ep);
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_receive_ep0
+ *          Receive an amount of data on ep0
+ * pdev: USB handle
+ * buf: pointer to the reception buffer
+ * len: amount of data to be received
+ * return : status
+ */
+enum usb_status usb_core_receive_ep0(struct usb_handle *pdev, uint8_t *buf,
+				     uint32_t len)
+{
+	/* Prepare the reception of the buffer over EP0 */
+	if (len != 0U) {
+		pdev->ep0_state = USBD_EP0_DATA_OUT;
+	} else {
+		pdev->ep0_state = USBD_EP0_STATUS_OUT;
+	}
+
+	pdev->ep_out[0].total_length = len;
+	pdev->ep_out[0].rem_length = len;
+
+	/* Start the transfer */
+	return usb_core_receive(pdev, 0U, buf, len);
+}
+
+/*
+ * usb_core_transmit_ep0
+ *          Send an amount of data on ep0
+ * pdev: USB handle
+ * buf: pointer to the transmission buffer
+ * len: amount of data to be sent
+ * return : status
+ */
+enum usb_status usb_core_transmit_ep0(struct usb_handle *pdev, uint8_t *buf,
+				      uint32_t len)
+{
+	/* Set EP0 State */
+	if (len != 0U) {
+		pdev->ep0_state = USBD_EP0_DATA_IN;
+	} else {
+		pdev->ep0_state = USBD_EP0_STATUS_IN;
+	}
+
+	pdev->ep_in[0].total_length = len;
+	pdev->ep_in[0].rem_length = len;
+
+	/* Start the transfer */
+	return usb_core_transmit(pdev, 0U, buf, len);
+}
+
+/*
+ * usb_core_ctl_error
+ *         Handle USB low level error
+ * pdev: device instance
+ * req: usb request
+ * return : None
+ */
+
+void usb_core_ctl_error(struct usb_handle *pdev)
+{
+	ERROR("%s : Send an ERROR\n", __func__);
+	usb_core_set_stall(pdev, EP0_IN);
+	usb_core_set_stall(pdev, EP0_OUT);
+}
+
+/*
+ * usb_core_start
+ *         Start the USB device core.
+ * pdev: Device Handle
+ * return : USBD Status
+ */
+enum usb_status usb_core_start(struct usb_handle *pdev)
+{
+	/* Start the low level driver */
+	pdev->driver->start_device(pdev->data->instance);
+
+	return USBD_OK;
+}
+
+/*
+ * usb_core_stop
+ *         Stop the USB device core.
+ * pdev: Device Handle
+ * return : USBD Status
+ */
+enum usb_status usb_core_stop(struct usb_handle *pdev)
+{
+	/* Free class resources */
+	pdev->class->de_init(pdev, pdev->dev_config);
+
+	/* Stop the low level driver */
+	pdev->driver->stop_device(pdev->data->instance);
+
+	return USBD_OK;
+}
+
+/*
+ * register_usb_driver
+ *         Stop the USB device core.
+ * pdev: Device Handle
+ * pcd_handle: PCD handle
+ * driver: USB driver
+ * driver_handle: USB driver handle
+ * return : USBD Status
+ */
+enum usb_status register_usb_driver(struct usb_handle *pdev,
+				    struct pcd_handle *pcd_handle,
+				    const struct usb_driver *driver,
+				    void *driver_handle)
+{
+	uint8_t i;
+
+	assert(pdev != NULL);
+	assert(pcd_handle != NULL);
+	assert(driver != NULL);
+	assert(driver_handle != NULL);
+
+	/* Free class resources */
+	pdev->driver = driver;
+	pdev->data = pcd_handle;
+	pdev->data->instance = driver_handle;
+	pdev->dev_state = USBD_STATE_DEFAULT;
+	pdev->ep0_state = USBD_EP0_IDLE;
+
+	/* Copy endpoint information */
+	for (i = 0U; i < USBD_EP_NB; i++) {
+		pdev->ep_in[i].maxpacket = pdev->data->in_ep[i].maxpacket;
+		pdev->ep_out[i].maxpacket = pdev->data->out_ep[i].maxpacket;
+	}
+
+	return USBD_OK;
+}
+
+/*
+ * register_platform
+ *         Register the USB device core.
+ * pdev: Device Handle
+ * plat_call_back: callback
+ * return : USBD Status
+ */
+enum usb_status register_platform(struct usb_handle *pdev,
+			       const struct usb_desc *plat_call_back)
+{
+	assert(pdev != NULL);
+	assert(plat_call_back != NULL);
+
+	/* Save platform info in class resources */
+	pdev->desc = plat_call_back;
+
+	return USBD_OK;
+}
diff --git a/fdts/arm_fpga.dts b/fdts/arm_fpga.dts
index 6a966fd..c0efd09 100644
--- a/fdts/arm_fpga.dts
+++ b/fdts/arm_fpga.dts
@@ -28,7 +28,7 @@
 		bootargs = "console=ttyAMA0,38400n8 earlycon";
 		/* Allow to upload a generous 100MB initrd payload. */
 		linux,initrd-start = <0x0 0x84000000>;
-		linux,initrd-end = <0x0 0x85400000>;
+		linux,initrd-end = <0x0 0x8a400000>;
 	};
 
 	/* /cpus node will be added by BL31 at runtime. */
@@ -40,7 +40,6 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		clock-frequency = <10000000>;
 		interrupts = <GIC_PPI 13 IRQ_TYPE_LEVEL_LOW>,
 			     <GIC_PPI 14 IRQ_TYPE_LEVEL_LOW>,
 			     <GIC_PPI 11 IRQ_TYPE_LEVEL_LOW>,
@@ -82,7 +81,7 @@
 	dbg_uart: serial@7ff80000 {
 		compatible = "arm,pl011", "arm,primecell";
 		reg = <0x0 0x7ff80000 0x0 0x00001000>;
-		interrupts = <GIC_SPI 115 IRQ_TYPE_LEVEL_HIGH>;
+		interrupts = <GIC_SPI 415 IRQ_TYPE_LEVEL_HIGH>;
 		clocks = <&uartclk>, <&bus_refclk>;
 		clock-names = "uartclk", "apb_pclk";
 	};
@@ -98,5 +97,12 @@
 	/* The GICR size will be adjusted at runtime to match the cores. */
 		      <0x0 0x30040000 0x0 0x00020000>;	/* GICR for one core */
 		interrupts = <GIC_PPI 9 IRQ_TYPE_LEVEL_HIGH>;
+
+		its: msi-controller@30040000 {
+			compatible = "arm,gic-v3-its";
+			reg = <0x0 0x30040000 0x0 0x40000>;
+			#msi-cells = <1>;
+			msi-controller;
+		};
 	};
 };
diff --git a/fdts/fvp-base-gicv2-psci-aarch32.dts b/fdts/fvp-base-gicv2-psci-aarch32.dts
index 591ec58..3a921f4 100644
--- a/fdts/fvp-base-gicv2-psci-aarch32.dts
+++ b/fdts/fvp-base-gicv2-psci-aarch32.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,6 +11,7 @@
 #define	AFF
 #define	REG_32
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
 #include "fvp-defs.dtsi"
 
 /memreserve/ 0x80000000 0x00010000;
@@ -100,10 +101,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/fvp-base-gicv2-psci.dts b/fdts/fvp-base-gicv2-psci.dts
index 4b3942e..e99719e 100644
--- a/fdts/fvp-base-gicv2-psci.dts
+++ b/fdts/fvp-base-gicv2-psci.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,6 +10,7 @@
 
 #define	AFF
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
 #include "fvp-defs.dtsi"
 
 /memreserve/ 0x80000000 0x00010000;
@@ -99,10 +100,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/fvp-base-gicv3-psci-aarch32-common.dtsi b/fdts/fvp-base-gicv3-psci-aarch32-common.dtsi
index 1a1bd12..85988e9 100644
--- a/fdts/fvp-base-gicv3-psci-aarch32-common.dtsi
+++ b/fdts/fvp-base-gicv3-psci-aarch32-common.dtsi
@@ -1,9 +1,11 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
 /memreserve/ 0x80000000 0x00010000;
 
 / {
@@ -100,10 +102,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/fvp-base-gicv3-psci-common.dtsi b/fdts/fvp-base-gicv3-psci-common.dtsi
index 192f574..3cb613f 100644
--- a/fdts/fvp-base-gicv3-psci-common.dtsi
+++ b/fdts/fvp-base-gicv3-psci-common.dtsi
@@ -1,9 +1,10 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
 #include <services/sdei_flags.h>
 
 #define LEVEL	0
@@ -23,7 +24,11 @@
 	#address-cells = <2>;
 	#size-cells = <2>;
 
-	chosen { };
+#if (ENABLE_RME == 1)
+	chosen { bootargs = "mem=1G console=ttyAMA0 earlycon=pl011,0x1c090000 root=/dev/vda ip=on";};
+#else
+	chosen {};
+#endif
 
 	aliases {
 		serial0 = &v2m_serial0;
@@ -134,8 +139,13 @@
 
 	memory@80000000 {
 		device_type = "memory";
+#if (ENABLE_RME == 1)
+		reg = <0x00000000 0x80000000 0 0x7C000000>,
+		      <0x00000008 0x80000000 0 0x80000000>;
+#else
 		reg = <0x00000000 0x80000000 0 0x7F000000>,
 		      <0x00000008 0x80000000 0 0x80000000>;
+#endif
 	};
 
 	gic: interrupt-controller@2f000000 {
@@ -161,10 +171,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/fvp-foundation-gicv2-psci.dts b/fdts/fvp-foundation-gicv2-psci.dts
index 95a800e..5a82c46 100644
--- a/fdts/fvp-foundation-gicv2-psci.dts
+++ b/fdts/fvp-foundation-gicv2-psci.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,6 +11,7 @@
 #define	AFF
 #define	CLUSTER_COUNT	1
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
 #include "fvp-defs.dtsi"
 
 /memreserve/ 0x80000000 0x00010000;
@@ -100,10 +101,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/fvp-foundation-gicv3-psci.dts b/fdts/fvp-foundation-gicv3-psci.dts
index c295dc1..e1249d4 100644
--- a/fdts/fvp-foundation-gicv3-psci.dts
+++ b/fdts/fvp-foundation-gicv3-psci.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,6 +11,7 @@
 #define	AFF
 #define	CLUSTER_COUNT	1
 
+#include <dt-bindings/interrupt-controller/arm-gic.h>
 #include "fvp-defs.dtsi"
 
 /memreserve/ 0x80000000 0x00010000;
@@ -109,10 +110,14 @@
 
 	timer {
 		compatible = "arm,armv8-timer";
-		interrupts = <1 13 0xff01>,
-			     <1 14 0xff01>,
-			     <1 11 0xff01>,
-			     <1 10 0xff01>;
+		interrupts = <GIC_PPI 13
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 14
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 11
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>,
+			     <GIC_PPI 10
+				(GIC_CPU_MASK_RAW(0xff) | IRQ_TYPE_LEVEL_LOW)>;
 		clock-frequency = <100000000>;
 	};
 
diff --git a/fdts/juno-ethosn.dtsi b/fdts/juno-ethosn.dtsi
new file mode 100644
index 0000000..e2f3355
--- /dev/null
+++ b/fdts/juno-ethosn.dtsi
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/*
+ * For examples of multi-core and multi-device NPU, refer to the examples given in the
+ * Arm Ethos-N NPU driver stack.
+ * https://github.com/ARM-software/ethos-n-driver-stack
+ */
+
+/ {
+	#address-cells = <2>;
+	#size-cells = <2>;
+
+	ethosn0: ethosn@6f300000 {
+		compatible = "ethosn";
+		reg = <0 0x6f300000 0 0x00100000>;
+		status = "okay";
+
+		core0 {
+			compatible = "ethosn-core";
+			status = "okay";
+		};
+	};
+};
diff --git a/fdts/juno.dts b/fdts/juno.dts
new file mode 100644
index 0000000..56fe167
--- /dev/null
+++ b/fdts/juno.dts
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/dts-v1/;
+
+/ {
+
+};
+
+#if ARM_ETHOSN_NPU_DRIVER
+	#include "juno-ethosn.dtsi"
+#endif
diff --git a/fdts/morello-fvp.dts b/fdts/morello-fvp.dts
index 2218b2a..55c87bf 100644
--- a/fdts/morello-fvp.dts
+++ b/fdts/morello-fvp.dts
@@ -10,7 +10,7 @@
 / {
 
 	chosen {
-		stdout-path = "soc_uart0:115200n8";
+		stdout-path = "serial0:115200n8";
 	};
 
 	reserved-memory {
@@ -27,33 +27,52 @@
 	cpus {
 		#address-cells = <2>;
 		#size-cells = <0>;
-		cpu0@0 {
+
+		cpu-map {
+			cluster0 {
+				core0 {
+					cpu = <&CPU0>;
+				};
+				core1 {
+					cpu = <&CPU1>;
+				};
+			};
+			cluster1 {
+				core0 {
+					cpu = <&CPU2>;
+				};
+				core1 {
+					cpu = <&CPU3>;
+				};
+			};
+		};
+		CPU0: cpu0@0 {
 			compatible = "arm,armv8";
 			reg = <0x0 0x0>;
 			device_type = "cpu";
 			enable-method = "psci";
 			clocks = <&scmi_dvfs 0>;
 		};
-		cpu1@100 {
+		CPU1: cpu1@100 {
 			compatible = "arm,armv8";
 			reg = <0x0 0x100>;
 			device_type = "cpu";
 			enable-method = "psci";
 			clocks = <&scmi_dvfs 0>;
 		};
-		cpu2@10000 {
+		CPU2: cpu2@10000 {
 			compatible = "arm,armv8";
 			reg = <0x0 0x10000>;
 			device_type = "cpu";
 			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
+			clocks = <&scmi_dvfs 1>;
 		};
-		cpu3@10100 {
+		CPU3: cpu3@10100 {
 			compatible = "arm,armv8";
 			reg = <0x0 0x10100>;
 			device_type = "cpu";
 			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
+			clocks = <&scmi_dvfs 1>;
 		};
 	};
 
@@ -80,12 +99,24 @@
 		interrupts = <GIC_SPI 96 IRQ_TYPE_LEVEL_HIGH>;
 	};
 
+	virtio_net@1c180000 {
+		compatible = "virtio,mmio";
+		reg = <0x0 0x1c180000 0x0 0x200>;
+		interrupts = <GIC_SPI 102 IRQ_TYPE_LEVEL_HIGH>;
+	};
+
 	virtio_rng@1c190000 {
-		compatible = "virtio,mmio","virtio-rng";
+		compatible = "virtio,mmio";
 		reg = <0x0 0x1c190000 0x0 0x200>;
 		interrupts = <GIC_SPI 101 IRQ_TYPE_LEVEL_HIGH>;
 	};
 
+	virtio_p9@1c1a0000 {
+		compatible = "virtio,mmio";
+		reg = <0x0 0x1c1a0000 0x0 0x200>;
+		interrupts = <GIC_SPI 103 IRQ_TYPE_LEVEL_HIGH>;
+	};
+
 	ethernet@1d100000 {
 		compatible = "smsc,lan91c111";
 		reg = <0x0 0x1d100000 0x0 0x10000>;
diff --git a/fdts/n1sdp-single-chip.dts b/fdts/n1sdp-single-chip.dts
index bd48273..3c091ac 100644
--- a/fdts/n1sdp-single-chip.dts
+++ b/fdts/n1sdp-single-chip.dts
@@ -16,7 +16,7 @@
 	};
 
 	chosen {
-		stdout-path = "soc_uart0:115200n8";
+		stdout-path = "serial0:115200n8";
 	};
 
 	/* This configuration assumes that standard setup with two DIMM modules.
diff --git a/fdts/optee_sp_manifest.dts b/fdts/optee_sp_manifest.dts
deleted file mode 100644
index 02a5ef3..0000000
--- a/fdts/optee_sp_manifest.dts
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- *
- * This file is a Partition Manifest (PM) for a minimal Secure Partition (SP)
- * that has additional optional properties defined.
- *
- */
-
-/dts-v1/;
-
-/ {
-	compatible = "arm,ffa-manifest-1.0";
-
-	/* Properties */
-	description = "op-tee";
-	ffa-version = <0x00010000>; /* 31:16 - Major, 15:0 - Minor */
-	uuid = <0x486178e0 0xe7f811e3 0xbc5e0002 0xa5d5c51b>;
-	id = <1>;
-	execution-ctx-count = <8>;
-	exception-level = <2>; /* S-EL1 */
-	execution-state = <0>; /* AARCH64 */
-	load-address = <0x6280000>;
-	entrypoint-offset = <0x1000>;
-	xlat-granule = <0>; /* 4KiB */
-	boot-order = <0>;
-	messaging-method = <0>; /* Direct messaging only */
-	run-time-model = <1>; /* Run to completion */
-
-	/* Boot protocol */
-	gp-register-num = <0x0>;
-};
diff --git a/fdts/stm32mp15-bl2.dtsi b/fdts/stm32mp15-bl2.dtsi
new file mode 100644
index 0000000..074414b
--- /dev/null
+++ b/fdts/stm32mp15-bl2.dtsi
@@ -0,0 +1,91 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (C) STMicroelectronics 2020-2021 - All Rights Reserved
+ */
+
+/ {
+#if !STM32MP_EMMC && !STM32MP_SDMMC
+	aliases {
+		/delete-property/ mmc0;
+	};
+#endif
+
+	cpus {
+		/delete-node/ cpu@1;
+	};
+
+	/delete-node/ psci;
+
+	soc {
+		/delete-node/ timer@40006000;
+		/delete-node/ timer@44006000;
+#if !STM32MP_USB_PROGRAMMER
+		/delete-node/ usb-otg@49000000;
+#endif
+		/delete-node/ pwr_mcu@50001014;
+		/delete-node/ cryp@54001000;
+		/delete-node/ rng@54003000;
+#if !STM32MP_RAW_NAND
+		/delete-node/ memory-controller@58002000;
+#endif
+#if !STM32MP_SPI_NAND && !STM32MP_SPI_NOR
+		/delete-node/ spi@58003000;
+#endif
+#if !STM32MP_EMMC && !STM32MP_SDMMC
+		/delete-node/ mmc@58005000;
+		/delete-node/ mmc@58007000;
+#endif
+#if !STM32MP_USB_PROGRAMMER
+		/delete-node/ usbphyc@5a006000;
+#endif
+		/delete-node/ spi@5c001000;
+		/delete-node/ rtc@5c004000;
+		/delete-node/ etzpc@5c007000;
+		/delete-node/ stgen@5c008000;
+		/delete-node/ i2c@5c009000;
+		/delete-node/ tamp@5c00a000;
+
+		pin-controller@50002000 {
+#if !STM32MP_RAW_NAND
+			/delete-node/ fmc-0;
+#endif
+#if !STM32MP_SPI_NAND && !STM32MP_SPI_NOR
+			/delete-node/ qspi-clk-0;
+			/delete-node/ qspi-bk1-0;
+			/delete-node/ qspi-bk2-0;
+#endif
+#if !STM32MP_EMMC && !STM32MP_SDMMC
+			/delete-node/ sdmmc1-b4-0;
+			/delete-node/ sdmmc1-dir-0;
+			/delete-node/ sdmmc2-b4-0;
+			/delete-node/ sdmmc2-b4-1;
+			/delete-node/ sdmmc2-d47-0;
+#endif
+#if !STM32MP_USB_PROGRAMMER
+			/delete-node/ usbotg_hs-0;
+			/delete-node/ usbotg-fs-dp-dm-0;
+#endif
+		};
+	};
+
+#if !STM32MP_USE_STM32IMAGE
+	/*
+	 * UUID's here are UUID RFC 4122 compliant meaning fieds are stored in
+	 * network order (big endian)
+	 */
+
+	st-io_policies {
+		fip-handles {
+			compatible = "st,io-fip-handle";
+			fw_cfg_uuid = "5807e16a-8459-47be-8ed5-648e8dddab0e";
+			bl32_uuid = "05d0e189-53dc-1347-8d2b-500a4b7a3e38";
+			bl32_extra1_uuid = "0b70c29b-2a5a-7840-9f65-0a5682738288";
+			bl32_extra2_uuid = "8ea87bb1-cfa2-3f4d-85fd-e7bba50220d9";
+			bl33_uuid = "d6d0eea7-fcea-d54b-9782-9934f234b6e4";
+			hw_cfg_uuid = "08b8f1d9-c9cf-9349-a962-6fbc6b7265cc";
+			tos_fw_cfg_uuid = "26257c1a-dbc6-7f47-8d96-c4c4b0248021";
+			nt_fw_cfg_uuid = "28da9815-93e8-7e44-ac66-1aaf801550f9";
+		};
+	};
+#endif /* !STM32MP_USE_STM32IMAGE */
+};
diff --git a/fdts/stm32mp15-bl32.dtsi b/fdts/stm32mp15-bl32.dtsi
new file mode 100644
index 0000000..ca4bb3e
--- /dev/null
+++ b/fdts/stm32mp15-bl32.dtsi
@@ -0,0 +1,46 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (C) STMicroelectronics 2020-2021 - All Rights Reserved
+ */
+
+/ {
+	aliases {
+		/delete-property/ mmc0;
+		/delete-property/ mmc1;
+	};
+
+	cpus {
+		/delete-node/ cpu@1;
+	};
+
+	/delete-node/ psci;
+
+	soc {
+		/delete-node/ usb-otg@49000000;
+		/delete-node/ hash@54002000;
+		/delete-node/ memory-controller@58002000;
+		/delete-node/ spi@58003000;
+		/delete-node/ mmc@58005000;
+		/delete-node/ mmc@58007000;
+		/delete-node/ usbphyc@5a006000;
+		/delete-node/ spi@5c001000;
+		/delete-node/ stgen@5c008000;
+		/delete-node/ i2c@5c009000;
+
+		pin-controller@50002000 {
+			/delete-node/ fmc-0;
+			/delete-node/ qspi-clk-0;
+			/delete-node/ qspi-bk1-0;
+			/delete-node/ qspi-bk2-0;
+			/delete-node/ sdmmc1-b4-0;
+			/delete-node/ sdmmc1-dir-0;
+			/delete-node/ sdmmc2-b4-0;
+			/delete-node/ sdmmc2-b4-1;
+			/delete-node/ sdmmc2-d47-0;
+			/delete-node/ sdmmc2-d47-1;
+			/delete-node/ sdmmc2-d47-3;
+			/delete-node/ usbotg_hs-0;
+			/delete-node/ usbotg-fs-dp-dm-0;
+		};
+	};
+};
diff --git a/fdts/stm32mp15-ddr.dtsi b/fdts/stm32mp15-ddr.dtsi
index 4825691..e5efd92 100644
--- a/fdts/stm32mp15-ddr.dtsi
+++ b/fdts/stm32mp15-ddr.dtsi
@@ -1,153 +1,127 @@
 // SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
 /*
- * Copyright (C) 2018, STMicroelectronics - All Rights Reserved
+ * Copyright (C) 2018-2021, STMicroelectronics - All Rights Reserved
  */
 
-/ {
-	soc {
-		ddr: ddr@5a003000{
+&ddr {
+	st,mem-name = DDR_MEM_NAME;
+	st,mem-speed = <DDR_MEM_SPEED>;
+	st,mem-size = <DDR_MEM_SIZE>;
 
-			compatible = "st,stm32mp1-ddr";
+	st,ctl-reg = <
+		DDR_MSTR
+		DDR_MRCTRL0
+		DDR_MRCTRL1
+		DDR_DERATEEN
+		DDR_DERATEINT
+		DDR_PWRCTL
+		DDR_PWRTMG
+		DDR_HWLPCTL
+		DDR_RFSHCTL0
+		DDR_RFSHCTL3
+		DDR_CRCPARCTL0
+		DDR_ZQCTL0
+		DDR_DFITMG0
+		DDR_DFITMG1
+		DDR_DFILPCFG0
+		DDR_DFIUPD0
+		DDR_DFIUPD1
+		DDR_DFIUPD2
+		DDR_DFIPHYMSTR
+		DDR_ODTMAP
+		DDR_DBG0
+		DDR_DBG1
+		DDR_DBGCMD
+		DDR_POISONCFG
+		DDR_PCCFG
+	>;
 
-			reg = <0x5A003000 0x550
-			       0x5A004000 0x234>;
+	st,ctl-timing = <
+		DDR_RFSHTMG
+		DDR_DRAMTMG0
+		DDR_DRAMTMG1
+		DDR_DRAMTMG2
+		DDR_DRAMTMG3
+		DDR_DRAMTMG4
+		DDR_DRAMTMG5
+		DDR_DRAMTMG6
+		DDR_DRAMTMG7
+		DDR_DRAMTMG8
+		DDR_DRAMTMG14
+		DDR_ODTCFG
+	>;
 
-			clocks = <&rcc AXIDCG>,
-				 <&rcc DDRC1>,
-				 <&rcc DDRC2>,
-				 <&rcc DDRPHYC>,
-				 <&rcc DDRCAPB>,
-				 <&rcc DDRPHYCAPB>;
+	st,ctl-map = <
+		DDR_ADDRMAP1
+		DDR_ADDRMAP2
+		DDR_ADDRMAP3
+		DDR_ADDRMAP4
+		DDR_ADDRMAP5
+		DDR_ADDRMAP6
+		DDR_ADDRMAP9
+		DDR_ADDRMAP10
+		DDR_ADDRMAP11
+	>;
 
-			clock-names = "axidcg",
-				      "ddrc1",
-				      "ddrc2",
-				      "ddrphyc",
-				      "ddrcapb",
-				      "ddrphycapb";
+	st,ctl-perf = <
+		DDR_SCHED
+		DDR_SCHED1
+		DDR_PERFHPR1
+		DDR_PERFLPR1
+		DDR_PERFWR1
+		DDR_PCFGR_0
+		DDR_PCFGW_0
+		DDR_PCFGQOS0_0
+		DDR_PCFGQOS1_0
+		DDR_PCFGWQOS0_0
+		DDR_PCFGWQOS1_0
+		DDR_PCFGR_1
+		DDR_PCFGW_1
+		DDR_PCFGQOS0_1
+		DDR_PCFGQOS1_1
+		DDR_PCFGWQOS0_1
+		DDR_PCFGWQOS1_1
+	>;
 
-			st,mem-name = DDR_MEM_NAME;
-			st,mem-speed = <DDR_MEM_SPEED>;
-			st,mem-size = <DDR_MEM_SIZE>;
+	st,phy-reg = <
+		DDR_PGCR
+		DDR_ACIOCR
+		DDR_DXCCR
+		DDR_DSGCR
+		DDR_DCR
+		DDR_ODTCR
+		DDR_ZQ0CR1
+		DDR_DX0GCR
+		DDR_DX1GCR
+		DDR_DX2GCR
+		DDR_DX3GCR
+	>;
 
-			st,ctl-reg = <
-				DDR_MSTR
-				DDR_MRCTRL0
-				DDR_MRCTRL1
-				DDR_DERATEEN
-				DDR_DERATEINT
-				DDR_PWRCTL
-				DDR_PWRTMG
-				DDR_HWLPCTL
-				DDR_RFSHCTL0
-				DDR_RFSHCTL3
-				DDR_CRCPARCTL0
-				DDR_ZQCTL0
-				DDR_DFITMG0
-				DDR_DFITMG1
-				DDR_DFILPCFG0
-				DDR_DFIUPD0
-				DDR_DFIUPD1
-				DDR_DFIUPD2
-				DDR_DFIPHYMSTR
-				DDR_ODTMAP
-				DDR_DBG0
-				DDR_DBG1
-				DDR_DBGCMD
-				DDR_POISONCFG
-				DDR_PCCFG
-			>;
+	st,phy-timing = <
+		DDR_PTR0
+		DDR_PTR1
+		DDR_PTR2
+		DDR_DTPR0
+		DDR_DTPR1
+		DDR_DTPR2
+		DDR_MR0
+		DDR_MR1
+		DDR_MR2
+		DDR_MR3
+	>;
 
-			st,ctl-timing = <
-				DDR_RFSHTMG
-				DDR_DRAMTMG0
-				DDR_DRAMTMG1
-				DDR_DRAMTMG2
-				DDR_DRAMTMG3
-				DDR_DRAMTMG4
-				DDR_DRAMTMG5
-				DDR_DRAMTMG6
-				DDR_DRAMTMG7
-				DDR_DRAMTMG8
-				DDR_DRAMTMG14
-				DDR_ODTCFG
-			>;
-
-			st,ctl-map = <
-				DDR_ADDRMAP1
-				DDR_ADDRMAP2
-				DDR_ADDRMAP3
-				DDR_ADDRMAP4
-				DDR_ADDRMAP5
-				DDR_ADDRMAP6
-				DDR_ADDRMAP9
-				DDR_ADDRMAP10
-				DDR_ADDRMAP11
-			>;
-
-			st,ctl-perf = <
-				DDR_SCHED
-				DDR_SCHED1
-				DDR_PERFHPR1
-				DDR_PERFLPR1
-				DDR_PERFWR1
-				DDR_PCFGR_0
-				DDR_PCFGW_0
-				DDR_PCFGQOS0_0
-				DDR_PCFGQOS1_0
-				DDR_PCFGWQOS0_0
-				DDR_PCFGWQOS1_0
-				DDR_PCFGR_1
-				DDR_PCFGW_1
-				DDR_PCFGQOS0_1
-				DDR_PCFGQOS1_1
-				DDR_PCFGWQOS0_1
-				DDR_PCFGWQOS1_1
-			>;
-
-			st,phy-reg = <
-				DDR_PGCR
-				DDR_ACIOCR
-				DDR_DXCCR
-				DDR_DSGCR
-				DDR_DCR
-				DDR_ODTCR
-				DDR_ZQ0CR1
-				DDR_DX0GCR
-				DDR_DX1GCR
-				DDR_DX2GCR
-				DDR_DX3GCR
-			>;
-
-			st,phy-timing = <
-				DDR_PTR0
-				DDR_PTR1
-				DDR_PTR2
-				DDR_DTPR0
-				DDR_DTPR1
-				DDR_DTPR2
-				DDR_MR0
-				DDR_MR1
-				DDR_MR2
-				DDR_MR3
-			>;
-
-			st,phy-cal = <
-				DDR_DX0DLLCR
-				DDR_DX0DQTR
-				DDR_DX0DQSTR
-				DDR_DX1DLLCR
-				DDR_DX1DQTR
-				DDR_DX1DQSTR
-				DDR_DX2DLLCR
-				DDR_DX2DQTR
-				DDR_DX2DQSTR
-				DDR_DX3DLLCR
-				DDR_DX3DQTR
-				DDR_DX3DQSTR
-			>;
-
-			status = "okay";
-		};
-	};
+	st,phy-cal = <
+		DDR_DX0DLLCR
+		DDR_DX0DQTR
+		DDR_DX0DQSTR
+		DDR_DX1DLLCR
+		DDR_DX1DQTR
+		DDR_DX1DQSTR
+		DDR_DX2DLLCR
+		DDR_DX2DQTR
+		DDR_DX2DQSTR
+		DDR_DX3DLLCR
+		DDR_DX3DQTR
+		DDR_DX3DQSTR
+	>;
 };
diff --git a/fdts/stm32mp15-ddr3-1x4Gb-1066-binG.dtsi b/fdts/stm32mp15-ddr3-1x4Gb-1066-binG.dtsi
index c0fc1f7..c6d6434 100644
--- a/fdts/stm32mp15-ddr3-1x4Gb-1066-binG.dtsi
+++ b/fdts/stm32mp15-ddr3-1x4Gb-1066-binG.dtsi
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
 /*
- * Copyright (C) 2018, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2018-2021, STMicroelectronics - All Rights Reserved
  */
 
 /*
@@ -15,7 +15,7 @@
  * Save Date: 2020.02.20, save Time: 18:45:20
  */
 
-#define DDR_MEM_NAME	"DDR3-DDR3L 16bits 533000Khz"
+#define DDR_MEM_NAME	"DDR3-DDR3L 16bits 533000kHz"
 #define DDR_MEM_SPEED	533000
 #define DDR_MEM_SIZE	0x20000000
 
diff --git a/fdts/stm32mp15-ddr3-2x4Gb-1066-binG.dtsi b/fdts/stm32mp15-ddr3-2x4Gb-1066-binG.dtsi
index fc226d2..9614ab4 100644
--- a/fdts/stm32mp15-ddr3-2x4Gb-1066-binG.dtsi
+++ b/fdts/stm32mp15-ddr3-2x4Gb-1066-binG.dtsi
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
 /*
- * Copyright (C) 2018, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2018-2021, STMicroelectronics - All Rights Reserved
  */
 
 /*
@@ -15,7 +15,7 @@
  * Save Date: 2020.02.20, save Time: 18:49:33
  */
 
-#define DDR_MEM_NAME	"DDR3-DDR3L 32bits 533000Khz"
+#define DDR_MEM_NAME	"DDR3-DDR3L 32bits 533000kHz"
 #define DDR_MEM_SPEED	533000
 #define DDR_MEM_SIZE	0x40000000
 
diff --git a/fdts/stm32mp15-fw-config.dtsi b/fdts/stm32mp15-fw-config.dtsi
new file mode 100644
index 0000000..8aece28
--- /dev/null
+++ b/fdts/stm32mp15-fw-config.dtsi
@@ -0,0 +1,80 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ */
+
+#include <common/tbbr/tbbr_img_def.h>
+#include <dt-bindings/soc/stm32mp15-tzc400.h>
+
+#include <platform_def.h>
+
+#ifndef DDR_SIZE
+#error "DDR_SIZE is not defined"
+#endif
+
+#define DDR_NS_BASE	STM32MP_DDR_BASE
+#ifdef AARCH32_SP_OPTEE
+/* OP-TEE reserved shared memory: located at DDR top */
+#define DDR_SHARE_SIZE	STM32MP_DDR_SHMEM_SIZE
+#define DDR_SHARE_BASE	(STM32MP_DDR_BASE + (DDR_SIZE - DDR_SHARE_SIZE))
+/* OP-TEE secure memory: located right below OP-TEE reserved shared memory */
+#define DDR_SEC_SIZE	STM32MP_DDR_S_SIZE
+#define DDR_SEC_BASE	(DDR_SHARE_BASE - DDR_SEC_SIZE)
+#define DDR_NS_SIZE	(DDR_SEC_BASE - DDR_NS_BASE)
+#else /* !AARCH32_SP_OPTEE */
+#define DDR_NS_SIZE	DDR_SIZE
+#endif /* AARCH32_SP_OPTEE */
+
+/dts-v1/;
+
+/ {
+	dtb-registry {
+		compatible = "fconf,dyn_cfg-dtb_registry";
+
+		hw-config {
+			load-address = <0x0 STM32MP_HW_CONFIG_BASE>;
+			max-size = <STM32MP_HW_CONFIG_MAX_SIZE>;
+			id = <HW_CONFIG_ID>;
+		};
+
+		nt_fw {
+			load-address = <0x0 STM32MP_BL33_BASE>;
+			max-size = <STM32MP_BL33_MAX_SIZE>;
+			id = <BL33_IMAGE_ID>;
+		};
+
+#ifdef AARCH32_SP_OPTEE
+		tos_fw {
+			load-address = <0x0 STM32MP_OPTEE_BASE>;
+			max-size = <STM32MP_OPTEE_SIZE>;
+			id = <BL32_IMAGE_ID>;
+		};
+#else
+		tos_fw {
+			load-address = <0x0 STM32MP_BL32_BASE>;
+			max-size = <STM32MP_BL32_SIZE>;
+			id = <BL32_IMAGE_ID>;
+		};
+
+		tos_fw-config {
+			load-address = <0x0 STM32MP_BL32_DTB_BASE>;
+			max-size = <STM32MP_BL32_DTB_SIZE>;
+			id = <TOS_FW_CONFIG_ID>;
+		};
+#endif
+	};
+
+	st-mem-firewall {
+		compatible = "st,mem-firewall";
+#ifdef AARCH32_SP_OPTEE
+		memory-ranges = <
+			DDR_NS_BASE DDR_NS_SIZE TZC_REGION_S_NONE TZC_REGION_NSEC_ALL_ACCESS_RDWR
+			DDR_SEC_BASE DDR_SEC_SIZE TZC_REGION_S_RDWR 0
+			DDR_SHARE_BASE DDR_SHARE_SIZE TZC_REGION_S_NONE
+			TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_A7_ID)>;
+#else
+		memory-ranges = <
+			DDR_NS_BASE DDR_NS_SIZE TZC_REGION_S_NONE TZC_REGION_NSEC_ALL_ACCESS_RDWR>;
+#endif
+	};
+};
diff --git a/fdts/stm32mp15-pinctrl.dtsi b/fdts/stm32mp15-pinctrl.dtsi
index d3d1744..d74dc2b 100644
--- a/fdts/stm32mp15-pinctrl.dtsi
+++ b/fdts/stm32mp15-pinctrl.dtsi
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2017 - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  * Author: Ludovic Barre <ludovic.barre@st.com> for STMicroelectronics.
  */
 #include <dt-bindings/pinctrl/stm32-pinfunc.h>
@@ -31,6 +31,16 @@
 		};
 	};
 
+	i2c2_pins_a: i2c2-0 {
+		pins {
+			pinmux = <STM32_PINMUX('H', 4, AF4)>, /* I2C2_SCL */
+				 <STM32_PINMUX('H', 5, AF4)>; /* I2C2_SDA */
+			bias-disable;
+			drive-open-drain;
+			slew-rate = <0>;
+		};
+	};
+
 	qspi_clk_pins_a: qspi-clk-0 {
 		pins {
 			pinmux = <STM32_PINMUX('F', 10, AF9)>; /* QSPI_CLK */
@@ -76,12 +86,6 @@
 		};
 	};
 
-	rtc_out2_rmp_pins_a: rtc-out2-rmp-pins-0 {
-		pins {
-			pinmux = <STM32_PINMUX('I', 8, ANALOG)>; /* RTC_OUT2_RMP */
-		};
-	};
-
 	sdmmc1_b4_pins_a: sdmmc1-b4-0 {
 		pins1 {
 			pinmux = <STM32_PINMUX('C', 8, AF12)>, /* SDMMC1_D0 */
@@ -166,6 +170,27 @@
 		};
 	};
 
+	sdmmc2_d47_pins_b: sdmmc2-d47-1 {
+		pins {
+			pinmux = <STM32_PINMUX('A', 8, AF9)>,  /* SDMMC2_D4 */
+				 <STM32_PINMUX('A', 9, AF10)>, /* SDMMC2_D5 */
+				 <STM32_PINMUX('C', 6, AF10)>, /* SDMMC2_D6 */
+				 <STM32_PINMUX('C', 7, AF10)>; /* SDMMC2_D7 */
+			slew-rate = <1>;
+			drive-push-pull;
+			bias-disable;
+		};
+	};
+
+	sdmmc2_d47_pins_d: sdmmc2-d47-3 {
+		pins {
+			pinmux = <STM32_PINMUX('A', 8, AF9)>, /* SDMMC2_D4 */
+				 <STM32_PINMUX('A', 9, AF10)>, /* SDMMC2_D5 */
+				 <STM32_PINMUX('E', 5, AF9)>, /* SDMMC2_D6 */
+				 <STM32_PINMUX('C', 7, AF10)>; /* SDMMC2_D7 */
+		};
+	};
+
 	uart4_pins_a: uart4-0 {
 		pins1 {
 			pinmux = <STM32_PINMUX('G', 11, AF6)>; /* UART4_TX */
@@ -194,34 +219,90 @@
 
 	uart7_pins_a: uart7-0 {
 		pins1 {
-			pinmux = <STM32_PINMUX('E', 8, AF7)>; /* UART4_TX */
+			pinmux = <STM32_PINMUX('E', 8, AF7)>; /* UART7_TX */
 			bias-disable;
 			drive-push-pull;
 			slew-rate = <0>;
 		};
 		pins2 {
-			pinmux = <STM32_PINMUX('E', 7, AF7)>, /* UART4_RX */
-				 <STM32_PINMUX('E', 10, AF7)>, /* UART4_CTS */
-				 <STM32_PINMUX('E', 9, AF7)>; /* UART4_RTS */
+			pinmux = <STM32_PINMUX('E', 7, AF7)>, /* UART7_RX */
+				 <STM32_PINMUX('E', 10, AF7)>, /* UART7_CTS */
+				 <STM32_PINMUX('E', 9, AF7)>; /* UART7_RTS */
 			bias-disable;
 		};
 	};
 
 	uart7_pins_b: uart7-1 {
 		pins1 {
-			pinmux = <STM32_PINMUX('E', 8, AF7)>; /* USART7_TX */
+			pinmux = <STM32_PINMUX('F', 7, AF7)>; /* UART7_TX */
 			bias-disable;
 			drive-push-pull;
 			slew-rate = <0>;
 		};
 		pins2 {
-			pinmux = <STM32_PINMUX('E', 7, AF7)>; /* USART7_RX */
+			pinmux = <STM32_PINMUX('F', 6, AF7)>; /* UART7_RX */
+			bias-disable;
+		};
+	};
+
+	uart7_pins_c: uart7-2 {
+		pins1 {
+			pinmux = <STM32_PINMUX('E', 8, AF7)>; /* UART7_TX */
+			bias-disable;
+			drive-push-pull;
+			slew-rate = <0>;
+		};
+		pins2 {
+			pinmux = <STM32_PINMUX('E', 7, AF7)>; /* UART7_RX */
+			bias-disable;
+		};
+	};
+
+	uart8_pins_a: uart8-0 {
+		pins1 {
+			pinmux = <STM32_PINMUX('E', 1, AF8)>; /* UART8_TX */
+			bias-disable;
+			drive-push-pull;
+			slew-rate = <0>;
+		};
+		pins2 {
+			pinmux = <STM32_PINMUX('E', 0, AF8)>; /* UART8_RX */
 			bias-disable;
 		};
 	};
 
 	usart2_pins_a: usart2-0 {
 		pins1 {
+			pinmux = <STM32_PINMUX('F', 5, AF7)>, /* USART2_TX */
+				 <STM32_PINMUX('D', 4, AF7)>; /* USART2_RTS */
+			bias-disable;
+			drive-push-pull;
+			slew-rate = <0>;
+		};
+		pins2 {
+			pinmux = <STM32_PINMUX('D', 6, AF7)>, /* USART2_RX */
+				 <STM32_PINMUX('D', 3, AF7)>; /* USART2_CTS_NSS */
+			bias-disable;
+		};
+	};
+
+	usart2_pins_b: usart2-1 {
+		pins1 {
+			pinmux = <STM32_PINMUX('F', 5, AF7)>, /* USART2_TX */
+				 <STM32_PINMUX('A', 1, AF7)>; /* USART2_RTS */
+			bias-disable;
+			drive-push-pull;
+			slew-rate = <0>;
+		};
+		pins2 {
+			pinmux = <STM32_PINMUX('F', 4, AF7)>, /* USART2_RX */
+				 <STM32_PINMUX('E', 15, AF7)>; /* USART2_CTS_NSS */
+			bias-disable;
+		};
+	};
+
+	usart2_pins_c: usart2-2 {
+		pins1 {
 			pinmux = <STM32_PINMUX('D', 5, AF7)>, /* USART2_TX */
 				 <STM32_PINMUX('D', 4, AF7)>; /* USART2_RTS */
 			bias-disable;
@@ -237,15 +318,13 @@
 
 	usart3_pins_a: usart3-0 {
 		pins1 {
-			pinmux = <STM32_PINMUX('B', 10, AF7)>, /* USART3_TX */
-				 <STM32_PINMUX('G', 8, AF8)>; /* USART3_RTS */
+			pinmux = <STM32_PINMUX('B', 10, AF7)>; /* USART3_TX */
 			bias-disable;
 			drive-push-pull;
 			slew-rate = <0>;
 		};
 		pins2 {
-			pinmux = <STM32_PINMUX('B', 12, AF8)>, /* USART3_RX */
-				 <STM32_PINMUX('I', 10, AF8)>; /* USART3_CTS_NSS */
+			pinmux = <STM32_PINMUX('B', 12, AF8)>; /* USART3_RX */
 			bias-disable;
 		};
 	};
@@ -260,12 +339,27 @@
 		};
 		pins2 {
 			pinmux = <STM32_PINMUX('B', 12, AF8)>, /* USART3_RX */
+				 <STM32_PINMUX('I', 10, AF8)>; /* USART3_CTS_NSS */
+			bias-disable;
+		};
+	};
+
+	usart3_pins_c: usart3-2 {
+		pins1 {
+			pinmux = <STM32_PINMUX('B', 10, AF7)>, /* USART3_TX */
+				 <STM32_PINMUX('G', 8, AF8)>; /* USART3_RTS */
+			bias-disable;
+			drive-push-pull;
+			slew-rate = <0>;
+		};
+		pins2 {
+			pinmux = <STM32_PINMUX('B', 12, AF8)>, /* USART3_RX */
 				 <STM32_PINMUX('B', 13, AF7)>; /* USART3_CTS_NSS */
 			bias-disable;
 		};
 	};
 
-	usbotg_hs_pins_a: usbotg_hs-0 {
+	usbotg_hs_pins_a: usbotg-hs-0 {
 		pins {
 			pinmux = <STM32_PINMUX('A', 10, ANALOG)>; /* OTG_ID */
 		};
diff --git a/fdts/stm32mp151.dtsi b/fdts/stm32mp151.dtsi
index 8f175a6..ca93f0c 100644
--- a/fdts/stm32mp151.dtsi
+++ b/fdts/stm32mp151.dtsi
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2017 - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  * Author: Ludovic Barre <ludovic.barre@st.com> for STMicroelectronics.
  */
 #include <dt-bindings/interrupt-controller/arm-gic.h>
@@ -121,6 +121,21 @@
 			status = "disabled";
 		};
 
+		i2c2: i2c@40013000 {
+			compatible = "st,stm32mp15-i2c";
+			reg = <0x40013000 0x400>;
+			interrupt-names = "event", "error";
+			interrupts = <&exti 22 IRQ_TYPE_LEVEL_HIGH>,
+				     <&intc GIC_SPI 34 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&rcc I2C2_K>;
+			resets = <&rcc I2C2_R>;
+			#address-cells = <1>;
+			#size-cells = <0>;
+			st,syscfg-fmp = <&syscfg 0x4 0x2>;
+			wakeup-source;
+			status = "disabled";
+		};
+
 		uart7: serial@40018000 {
 			compatible = "st,stm32h7-uart";
 			reg = <0x40018000 0x400>;
@@ -159,7 +174,7 @@
 		};
 
 		usbotg_hs: usb-otg@49000000 {
-			compatible = "st,stm32mp1-hsotg", "snps,dwc2";
+			compatible = "st,stm32mp15-hsotg", "snps,dwc2";
 			reg = <0x49000000 0x10000>;
 			clocks = <&rcc USBO_K>;
 			clock-names = "otg";
@@ -304,7 +319,7 @@
 			status = "disabled";
 		};
 
-		sdmmc1: sdmmc@58005000 {
+		sdmmc1: mmc@58005000 {
 			compatible = "st,stm32-sdmmc2", "arm,pl18x", "arm,primecell";
 			arm,primecell-periphid = <0x00253180>;
 			reg = <0x58005000 0x1000>, <0x58006000 0x1000>;
@@ -319,7 +334,7 @@
 			status = "disabled";
 		};
 
-		sdmmc2: sdmmc@58007000 {
+		sdmmc2: mmc@58007000 {
 			compatible = "st,stm32-sdmmc2", "arm,pl18x", "arm,primecell";
 			arm,primecell-periphid = <0x00253180>;
 			reg = <0x58007000 0x1000>, <0x58008000 0x1000>;
@@ -343,6 +358,24 @@
 			status = "disabled";
 		};
 
+		ddr: ddr@5a003000{
+			compatible = "st,stm32mp1-ddr";
+			reg = <0x5A003000 0x550 0x5A004000 0x234>;
+			clocks = <&rcc AXIDCG>,
+				 <&rcc DDRC1>,
+				 <&rcc DDRC2>,
+				 <&rcc DDRPHYC>,
+				 <&rcc DDRCAPB>,
+				 <&rcc DDRPHYCAPB>;
+			clock-names = "axidcg",
+				      "ddrc1",
+				      "ddrc2",
+				      "ddrphyc",
+				      "ddrcapb",
+				      "ddrphycapb";
+			status = "okay";
+		};
+
 		usbphyc: usbphyc@5a006000 {
 			#address-cells = <1>;
 			#size-cells = <0>;
@@ -419,7 +452,7 @@
 			status = "disabled";
 		};
 
-		bsec: nvmem@5c005000 {
+		bsec: efuse@5c005000 {
 			compatible = "st,stm32mp15-bsec";
 			reg = <0x5c005000 0x400>;
 			#address-cells = <1>;
diff --git a/fdts/stm32mp157a-avenger96-fw-config.dts b/fdts/stm32mp157a-avenger96-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157a-avenger96-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157a-dk1-fw-config.dts b/fdts/stm32mp157a-dk1-fw-config.dts
new file mode 100644
index 0000000..83116d1
--- /dev/null
+++ b/fdts/stm32mp157a-dk1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157a-ed1-fw-config.dts b/fdts/stm32mp157a-ed1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157a-ed1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157a-ev1-fw-config.dts b/fdts/stm32mp157a-ev1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157a-ev1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-dk2-fw-config.dts b/fdts/stm32mp157c-dk2-fw-config.dts
new file mode 100644
index 0000000..83116d1
--- /dev/null
+++ b/fdts/stm32mp157c-dk2-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-ed1-fw-config.dts b/fdts/stm32mp157c-ed1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157c-ed1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-ed1.dts b/fdts/stm32mp157c-ed1.dts
index a6b98b7..11e0a61 100644
--- a/fdts/stm32mp157c-ed1.dts
+++ b/fdts/stm32mp157c-ed1.dts
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2017-2019 - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  * Author: Ludovic Barre <ludovic.barre@st.com> for STMicroelectronics.
  */
 /dts-v1/;
@@ -20,7 +20,6 @@
 		stdout-path = "serial0:115200n8";
 	};
 
-
 	memory@c0000000 {
 		device_type = "memory";
 		reg = <0xC0000000 0x40000000>;
@@ -52,7 +51,7 @@
 };
 
 &cryp1 {
-	status="okay";
+	status = "okay";
 };
 
 &hash1 {
@@ -233,7 +232,7 @@
 		CLK_CKPER_HSE
 		CLK_FMC_ACLK
 		CLK_QSPI_ACLK
-		CLK_ETH_DISABLED
+		CLK_ETH_PLL4P
 		CLK_SDMMC12_PLL4P
 		CLK_DSI_DSIPLL
 		CLK_STGEN_HSE
@@ -269,25 +268,33 @@
 
 	/* VCO = 1300.0 MHz => P = 650 (CPU) */
 	pll1: st,pll@0 {
-		cfg = < 2 80 0 0 0 PQR(1,0,0) >;
-		frac = < 0x800 >;
+		compatible = "st,stm32mp1-pll";
+		reg = <0>;
+		cfg = <2 80 0 0 0 PQR(1,0,0)>;
+		frac = <0x800>;
 	};
 
 	/* VCO = 1066.0 MHz => P = 266 (AXI), Q = 533 (GPU), R = 533 (DDR) */
 	pll2: st,pll@1 {
-		cfg = < 2 65 1 0 0 PQR(1,1,1) >;
-		frac = < 0x1400 >;
+		compatible = "st,stm32mp1-pll";
+		reg = <1>;
+		cfg = <2 65 1 0 0 PQR(1,1,1)>;
+		frac = <0x1400>;
 	};
 
 	/* VCO = 417.8 MHz => P = 209, Q = 24, R = 11 */
 	pll3: st,pll@2 {
-		cfg = < 1 33 1 16 36 PQR(1,1,1) >;
-		frac = < 0x1a04 >;
+		compatible = "st,stm32mp1-pll";
+		reg = <2>;
+		cfg = <1 33 1 16 36 PQR(1,1,1)>;
+		frac = <0x1a04>;
 	};
 
 	/* VCO = 594.0 MHz => P = 99, Q = 74, R = 74 */
 	pll4: st,pll@3 {
-		cfg = < 3 98 5 7 7 PQR(1,1,1) >;
+		compatible = "st,stm32mp1-pll";
+		reg = <3>;
+		cfg = <3 98 5 7 7 PQR(1,1,1)>;
 	};
 };
 
diff --git a/fdts/stm32mp157c-ev1-fw-config.dts b/fdts/stm32mp157c-ev1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157c-ev1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-ev1.dts b/fdts/stm32mp157c-ev1.dts
index c5d12e3..02840a2 100644
--- a/fdts/stm32mp157c-ev1.dts
+++ b/fdts/stm32mp157c-ev1.dts
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2017-2019 - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  * Author: Ludovic Barre <ludovic.barre@st.com> for STMicroelectronics.
  */
 /dts-v1/;
@@ -57,6 +57,7 @@
 
 &usart3 {
 	pinctrl-names = "default";
-	pinctrl-0 = <&usart3_pins_a>;
+	pinctrl-0 = <&usart3_pins_b>;
+	uart-has-rtscts;
 	status = "disabled";
 };
diff --git a/fdts/stm32mp157c-lxa-mc1-fw-config.dts b/fdts/stm32mp157c-lxa-mc1-fw-config.dts
new file mode 100644
index 0000000..9ee09e9
--- /dev/null
+++ b/fdts/stm32mp157c-lxa-mc1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-lxa-mc1.dts b/fdts/stm32mp157c-lxa-mc1.dts
new file mode 100644
index 0000000..6f67712
--- /dev/null
+++ b/fdts/stm32mp157c-lxa-mc1.dts
@@ -0,0 +1,93 @@
+/* SPDX-License-Identifier: (GPL-2.0-or-later OR BSD-3-Clause) */
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ * Copyright (C) 2020 Ahmad Fatoum, Pengutronix
+ */
+
+/dts-v1/;
+
+#include "stm32mp157.dtsi"
+#include "stm32mp15xc.dtsi"
+#include "stm32mp15-ddr3-1x4Gb-1066-binG.dtsi"
+#include "stm32mp15xx-osd32.dtsi"
+#include "stm32mp15xxac-pinctrl.dtsi"
+
+/ {
+	model = "Linux Automation MC-1 board";
+	compatible = "lxa,stm32mp157c-mc1", "oct,stm32mp15xx-osd32", "st,stm32mp157";
+
+	aliases {
+		mmc0 = &sdmmc1;
+		mmc1 = &sdmmc2;
+		serial0 = &uart4;
+	};
+
+	chosen {
+		stdout-path = &uart4;
+	};
+
+	led-act {
+		compatible = "gpio-leds";
+
+		led-green {
+			label = "mc1:green:act";
+			gpios = <&gpioa 13 1>;
+			linux,default-trigger = "heartbeat";
+		};
+	};
+
+	reg_3v3: regulator_3v3 {
+		compatible = "regulator-fixed";
+		regulator-name = "3V3";
+		regulator-min-microvolt = <3300000>;
+		regulator-max-microvolt = <3300000>;
+		regulator-always-on;
+		vin-supply = <&v3v3>;
+	};
+};
+
+&sdmmc1 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&sdmmc1_b4_pins_a>;
+	bus-width = <4>;
+	cd-gpios = <&gpioh 3 1>;
+	disable-wp;
+	no-1-8-v;
+	st,neg-edge;
+	vmmc-supply = <&reg_3v3>;
+	status = "okay";
+};
+
+&sdmmc1_b4_pins_a {
+	/*
+	 * board lacks external pull-ups on SDMMC lines. Class 10 SD refuses to
+	 * work, thus enable internal pull-ups.
+	 */
+	pins1 {
+		/delete-property/ bias-disable;
+		bias-pull-up;
+	};
+	pins2 {
+		/delete-property/ bias-disable;
+		bias-pull-up;
+	};
+};
+
+&sdmmc2 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&sdmmc2_b4_pins_a &sdmmc2_d47_pins_b>;
+	bus-width = <8>;
+	no-1-8-v;
+	no-sd;
+	no-sdio;
+	non-removable;
+	st,neg-edge;
+	vmmc-supply = <&reg_3v3>;
+	status = "okay";
+};
+
+&uart4 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&uart4_pins_a>;
+	status = "okay";
+};
diff --git a/fdts/stm32mp157c-odyssey-fw-config.dts b/fdts/stm32mp157c-odyssey-fw-config.dts
new file mode 100644
index 0000000..9ee09e9
--- /dev/null
+++ b/fdts/stm32mp157c-odyssey-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157c-odyssey-som.dtsi b/fdts/stm32mp157c-odyssey-som.dtsi
new file mode 100644
index 0000000..6bed339
--- /dev/null
+++ b/fdts/stm32mp157c-odyssey-som.dtsi
@@ -0,0 +1,325 @@
+/*
+ * Copyright (C) 2019, STMicroelectronics. All Rights Reserved.
+ * Copyright (C) 2021, Grzegorz Szymaszek.
+ *
+ * SPDX-License-Identifier: (GPL-2.0-or-later OR BSD-3-Clause)
+ */
+
+#include "stm32mp157.dtsi"
+#include "stm32mp15xc.dtsi"
+#include "stm32mp15-pinctrl.dtsi"
+#include "stm32mp15xxac-pinctrl.dtsi"
+#include <dt-bindings/clock/stm32mp1-clksrc.h>
+#include "stm32mp15-ddr3-1x4Gb-1066-binG.dtsi"
+
+/ {
+	memory@c0000000 {
+		device_type = "memory";
+		reg = <0xc0000000 0x20000000>;
+	};
+
+	vin: vin {
+		compatible = "regulator-fixed";
+		regulator-name = "vin";
+		regulator-min-microvolt = <5000000>;
+		regulator-max-microvolt = <5000000>;
+		regulator-always-on;
+	};
+};
+
+&bsec {
+	board_id: board_id@ec {
+		reg = <0xec 0x4>;
+		st,non-secure-otp;
+	};
+};
+
+&clk_hse {
+	st,digbypass;
+};
+
+&cpu0 {
+	cpu-supply = <&vddcore>;
+};
+
+&cpu1 {
+	cpu-supply = <&vddcore>;
+};
+
+&cryp1 {
+	status = "okay";
+};
+
+&hash1 {
+	status = "okay";
+};
+
+&i2c2 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&i2c2_pins_a>;
+	clock-frequency = <400000>;
+	i2c-scl-rising-time-ns = <185>;
+	i2c-scl-falling-time-ns = <20>;
+	status = "okay";
+
+	pmic: stpmic@33 {
+		compatible = "st,stpmic1";
+		reg = <0x33>;
+		interrupts-extended = <&exti_pwr 55 IRQ_TYPE_EDGE_FALLING>;
+		interrupt-controller;
+		#interrupt-cells = <2>;
+		status = "okay";
+
+		regulators {
+			compatible = "st,stpmic1-regulators";
+			buck1-supply = <&vin>;
+			buck2-supply = <&vin>;
+			buck3-supply = <&vin>;
+			buck4-supply = <&vin>;
+			ldo1-supply = <&v3v3>;
+			ldo2-supply = <&vin>;
+			ldo3-supply = <&vdd_ddr>;
+			ldo4-supply = <&vin>;
+			ldo5-supply = <&vin>;
+			ldo6-supply = <&v3v3>;
+			vref_ddr-supply = <&vin>;
+			boost-supply = <&vin>;
+			pwr_sw1-supply = <&bst_out>;
+			pwr_sw2-supply = <&bst_out>;
+
+			vddcore: buck1 {
+				regulator-name = "vddcore";
+				regulator-min-microvolt = <1200000>;
+				regulator-max-microvolt = <1350000>;
+				regulator-always-on;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			vdd_ddr: buck2 {
+				regulator-name = "vdd_ddr";
+				regulator-min-microvolt = <1350000>;
+				regulator-max-microvolt = <1350000>;
+				regulator-always-on;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			vdd: buck3 {
+				regulator-name = "vdd";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+				st,mask-reset;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			v3v3: buck4 {
+				regulator-name = "v3v3";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+				regulator-over-current-protection;
+				regulator-initial-mode = <0>;
+			};
+
+			v1v8_audio: ldo1 {
+				regulator-name = "v1v8_audio";
+				regulator-min-microvolt = <1800000>;
+				regulator-max-microvolt = <1800000>;
+				regulator-always-on;
+			};
+
+			v3v3_hdmi: ldo2 {
+				regulator-name = "v3v3_hdmi";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+			};
+
+			vtt_ddr: ldo3 {
+				regulator-name = "vtt_ddr";
+				regulator-min-microvolt = <500000>;
+				regulator-max-microvolt = <750000>;
+				regulator-always-on;
+				regulator-over-current-protection;
+			};
+
+			vdd_usb: ldo4 {
+				regulator-name = "vdd_usb";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+			};
+
+			vdda: ldo5 {
+				regulator-name = "vdda";
+				regulator-min-microvolt = <2900000>;
+				regulator-max-microvolt = <2900000>;
+				regulator-boot-on;
+			};
+
+			v1v2_hdmi: ldo6 {
+				regulator-name = "v1v2_hdmi";
+				regulator-min-microvolt = <1200000>;
+				regulator-max-microvolt = <1200000>;
+				regulator-always-on;
+			};
+
+			vref_ddr: vref_ddr {
+				regulator-name = "vref_ddr";
+				regulator-always-on;
+				regulator-over-current-protection;
+			};
+
+			bst_out: boost {
+				regulator-name = "bst_out";
+			};
+
+			vbus_otg: pwr_sw1 {
+				regulator-name = "vbus_otg";
+			};
+
+			vbus_sw: pwr_sw2 {
+				regulator-name = "vbus_sw";
+				regulator-active-discharge = <1>;
+			};
+		};
+
+		pmic_watchdog: watchdog {
+			compatible = "st,stpmic1-wdt";
+			status = "disabled";
+		};
+	};
+};
+
+&iwdg2 {
+	timeout-sec = <32>;
+	status = "okay";
+};
+
+&pwr_regulators {
+	vdd-supply = <&vdd>;
+	vdd_3v3_usbfs-supply = <&vdd_usb>;
+};
+
+&rcc {
+	secure-status = "disabled";
+	st,clksrc = <
+		CLK_MPU_PLL1P
+		CLK_AXI_PLL2P
+		CLK_MCU_PLL3P
+		CLK_PLL12_HSE
+		CLK_PLL3_HSE
+		CLK_PLL4_HSE
+		CLK_RTC_LSE
+		CLK_MCO1_DISABLED
+		CLK_MCO2_DISABLED
+	>;
+
+	st,clkdiv = <
+		1 /*MPU*/
+		0 /*AXI*/
+		0 /*MCU*/
+		1 /*APB1*/
+		1 /*APB2*/
+		1 /*APB3*/
+		1 /*APB4*/
+		2 /*APB5*/
+		23 /*RTC*/
+		0 /*MCO1*/
+		0 /*MCO2*/
+	>;
+
+	st,pkcs = <
+		CLK_CKPER_HSE
+		CLK_FMC_ACLK
+		CLK_QSPI_ACLK
+		CLK_ETH_PLL4P
+		CLK_SDMMC12_PLL4P
+		CLK_DSI_DSIPLL
+		CLK_STGEN_HSE
+		CLK_USBPHY_HSE
+		CLK_SPI2S1_PLL3Q
+		CLK_SPI2S23_PLL3Q
+		CLK_SPI45_HSI
+		CLK_SPI6_HSI
+		CLK_I2C46_HSI
+		CLK_SDMMC3_PLL4P
+		CLK_USBO_USBPHY
+		CLK_ADC_CKPER
+		CLK_CEC_LSE
+		CLK_I2C12_HSI
+		CLK_I2C35_HSI
+		CLK_UART1_HSI
+		CLK_UART24_HSI
+		CLK_UART35_HSI
+		CLK_UART6_HSI
+		CLK_UART78_HSI
+		CLK_SPDIF_PLL4P
+		CLK_FDCAN_PLL4R
+		CLK_SAI1_PLL3Q
+		CLK_SAI2_PLL3Q
+		CLK_SAI3_PLL3Q
+		CLK_SAI4_PLL3Q
+		CLK_RNG1_LSI
+		CLK_RNG2_LSI
+		CLK_LPTIM1_PCLK1
+		CLK_LPTIM23_PCLK3
+		CLK_LPTIM45_LSE
+	>;
+
+	/* VCO = 1300.0 MHz => P = 650 (CPU) */
+	pll1: st,pll@0 {
+		compatible = "st,stm32mp1-pll";
+		reg = <0>;
+		cfg = <2 80 0 0 0 PQR(1,0,0)>;
+		frac = <0x800>;
+	};
+
+	/* VCO = 1066.0 MHz => P = 266 (AXI), Q = 533 (GPU), R = 533 (DDR) */
+	pll2: st,pll@1 {
+		compatible = "st,stm32mp1-pll";
+		reg = <1>;
+		cfg = <2 65 1 0 0 PQR(1,1,1)>;
+		frac = <0x1400>;
+	};
+
+	/* VCO = 417.8 MHz => P = 209, Q = 24, R = 11 */
+	pll3: st,pll@2 {
+		compatible = "st,stm32mp1-pll";
+		reg = <2>;
+		cfg = <1 33 1 16 36 PQR(1,1,1)>;
+		frac = <0x1a04>;
+	};
+
+	/* VCO = 594.0 MHz => P = 99, Q = 74, R = 74 */
+	pll4: st,pll@3 {
+		compatible = "st,stm32mp1-pll";
+		reg = <3>;
+		cfg = <3 98 5 7 7 PQR(1,1,1)>;
+	};
+};
+
+&rng1 {
+	status = "okay";
+};
+
+&rtc {
+	status = "okay";
+};
+
+&sdmmc2 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&sdmmc2_b4_pins_a &sdmmc2_d47_pins_d>;
+	non-removable;
+	no-sd;
+	no-sdio;
+	st,neg-edge;
+	bus-width = <8>;
+	vmmc-supply = <&v3v3>;
+	vqmmc-supply = <&vdd>;
+	mmc-ddr-3_3v;
+	status = "okay";
+};
diff --git a/fdts/stm32mp157c-odyssey.dts b/fdts/stm32mp157c-odyssey.dts
new file mode 100644
index 0000000..03800f9
--- /dev/null
+++ b/fdts/stm32mp157c-odyssey.dts
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2019, STMicroelectronics. All Rights Reserved.
+ * Copyright (C) 2021, Grzegorz Szymaszek.
+ *
+ * SPDX-License-Identifier: (GPL-2.0-or-later OR BSD-3-Clause)
+ */
+
+/dts-v1/;
+
+#include "stm32mp157c-odyssey-som.dtsi"
+
+/ {
+	model = "Seeed Studio Odyssey-STM32MP157C Board";
+	compatible = "seeed,stm32mp157c-odyssey",
+		     "seeed,stm32mp157c-odyssey-som", "st,stm32mp157";
+
+	aliases {
+		serial0 = &uart4;
+	};
+
+	chosen {
+		stdout-path = "serial0:115200n8";
+	};
+};
+
+&sdmmc1 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&sdmmc1_b4_pins_a>;
+	disable-wp;
+	st,neg-edge;
+	bus-width = <4>;
+	vmmc-supply = <&v3v3>;
+	status = "okay";
+};
+
+&uart4 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&uart4_pins_a>;
+	status = "okay";
+};
diff --git a/fdts/stm32mp157d-dk1-fw-config.dts b/fdts/stm32mp157d-dk1-fw-config.dts
new file mode 100644
index 0000000..83116d1
--- /dev/null
+++ b/fdts/stm32mp157d-dk1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157d-ed1-fw-config.dts b/fdts/stm32mp157d-ed1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157d-ed1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157d-ev1-fw-config.dts b/fdts/stm32mp157d-ev1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157d-ev1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157f-dk2-fw-config.dts b/fdts/stm32mp157f-dk2-fw-config.dts
new file mode 100644
index 0000000..83116d1
--- /dev/null
+++ b/fdts/stm32mp157f-dk2-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x20000000 /* 512MB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157f-ed1-fw-config.dts b/fdts/stm32mp157f-ed1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157f-ed1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp157f-ev1-fw-config.dts b/fdts/stm32mp157f-ev1-fw-config.dts
new file mode 100644
index 0000000..2abbe50
--- /dev/null
+++ b/fdts/stm32mp157f-ev1-fw-config.dts
@@ -0,0 +1,7 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
+/*
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ */
+
+#define DDR_SIZE	0x40000000 /* 1GB */
+#include "stm32mp15-fw-config.dtsi"
diff --git a/fdts/stm32mp15xx-dkx.dtsi b/fdts/stm32mp15xx-dkx.dtsi
index 52b914b..9cc5368 100644
--- a/fdts/stm32mp15xx-dkx.dtsi
+++ b/fdts/stm32mp15xx-dkx.dtsi
@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2019 - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics.
  */
 
@@ -141,7 +141,6 @@
 				regulator-name = "vdd_usb";
 				regulator-min-microvolt = <3300000>;
 				regulator-max-microvolt = <3300000>;
-				regulator-always-on;
 			};
 
 			vdda: ldo5 {
@@ -223,7 +222,7 @@
 		CLK_CKPER_HSE
 		CLK_FMC_ACLK
 		CLK_QSPI_ACLK
-		CLK_ETH_DISABLED
+		CLK_ETH_PLL4P
 		CLK_SDMMC12_PLL4P
 		CLK_DSI_DSIPLL
 		CLK_STGEN_HSE
@@ -319,13 +318,13 @@
 
 &uart7 {
 	pinctrl-names = "default";
-	pinctrl-0 = <&uart7_pins_b>;
+	pinctrl-0 = <&uart7_pins_c>;
 	status = "disabled";
 };
 
 &usart3 {
 	pinctrl-names = "default";
-	pinctrl-0 = <&usart3_pins_b>;
+	pinctrl-0 = <&usart3_pins_c>;
 	uart-has-rtscts;
 	status = "disabled";
 };
diff --git a/fdts/stm32mp15xx-osd32.dtsi b/fdts/stm32mp15xx-osd32.dtsi
new file mode 100644
index 0000000..76a2561
--- /dev/null
+++ b/fdts/stm32mp15xx-osd32.dtsi
@@ -0,0 +1,281 @@
+/* SPDX-License-Identifier: (GPL-2.0-or-later OR BSD-3-Clause) */
+/*
+ * Copyright (C) 2020 STMicroelectronics - All Rights Reserved
+ * Copyright (C) 2020 Ahmad Fatoum, Pengutronix
+ */
+
+#include "stm32mp15-pinctrl.dtsi"
+
+&i2c4 {
+	pinctrl-names = "default";
+	pinctrl-0 = <&i2c4_pins_a>;
+	clock-frequency = <400000>;
+	i2c-scl-rising-time-ns = <185>;
+	i2c-scl-falling-time-ns = <20>;
+	status = "okay";
+
+	pmic: stpmic@33 {
+		compatible = "st,stpmic1";
+		reg = <0x33>;
+		interrupts-extended = <&gpioa 0 IRQ_TYPE_EDGE_FALLING>;
+		interrupt-controller;
+		#interrupt-cells = <2>;
+
+		regulators {
+			compatible = "st,stpmic1-regulators";
+
+			ldo1-supply = <&v3v3>;
+			ldo6-supply = <&v3v3>;
+			pwr_sw1-supply = <&bst_out>;
+
+			vddcore: buck1 {
+				regulator-name = "vddcore";
+				regulator-min-microvolt = <1200000>;
+				regulator-max-microvolt = <1350000>;
+				regulator-always-on;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			vdd_ddr: buck2 {
+				regulator-name = "vdd_ddr";
+				regulator-min-microvolt = <1350000>;
+				regulator-max-microvolt = <1350000>;
+				regulator-always-on;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			vdd: buck3 {
+				regulator-name = "vdd";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+				st,mask-reset;
+				regulator-initial-mode = <0>;
+				regulator-over-current-protection;
+			};
+
+			v3v3: buck4 {
+				regulator-name = "v3v3";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+				regulator-over-current-protection;
+				regulator-initial-mode = <0>;
+			};
+
+			v1v8_audio: ldo1 {
+				regulator-name = "v1v8_audio";
+				regulator-min-microvolt = <1800000>;
+				regulator-max-microvolt = <1800000>;
+				regulator-always-on;
+			};
+
+			v3v3_hdmi: ldo2 {
+				regulator-name = "v3v3_hdmi";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+				regulator-always-on;
+			};
+
+			vtt_ddr: ldo3 {
+				regulator-name = "vtt_ddr";
+				regulator-min-microvolt = <500000>;
+				regulator-max-microvolt = <750000>;
+				regulator-always-on;
+				regulator-over-current-protection;
+			};
+
+			vdd_usb: ldo4 {
+				regulator-name = "vdd_usb";
+				regulator-min-microvolt = <3300000>;
+				regulator-max-microvolt = <3300000>;
+			};
+
+			vdda: ldo5 {
+				regulator-name = "vdda";
+				regulator-min-microvolt = <2900000>;
+				regulator-max-microvolt = <2900000>;
+				regulator-boot-on;
+			};
+
+			v1v2_hdmi: ldo6 {
+				regulator-name = "v1v2_hdmi";
+				regulator-min-microvolt = <1200000>;
+				regulator-max-microvolt = <1200000>;
+				regulator-always-on;
+			};
+
+			vref_ddr: vref_ddr {
+				regulator-name = "vref_ddr";
+				regulator-always-on;
+				regulator-over-current-protection;
+			};
+
+			bst_out: boost {
+				regulator-name = "bst_out";
+			};
+
+			vbus_otg: pwr_sw1 {
+				regulator-name = "vbus_otg";
+				regulator-active-discharge;
+			};
+
+			vbus_sw: pwr_sw2 {
+				regulator-name = "vbus_sw";
+				regulator-active-discharge;
+			};
+		};
+
+		pmic_watchdog: watchdog {
+			compatible = "st,stpmic1-wdt";
+			status = "disabled";
+		};
+	};
+};
+
+&rng1 {
+	status = "okay";
+};
+
+/* ATF Specific */
+#include <dt-bindings/clock/stm32mp1-clksrc.h>
+
+/ {
+	aliases {
+		gpio0 = &gpioa;
+		gpio1 = &gpiob;
+		gpio2 = &gpioc;
+		gpio3 = &gpiod;
+		gpio4 = &gpioe;
+		gpio5 = &gpiof;
+		gpio6 = &gpiog;
+		gpio7 = &gpioh;
+		gpio8 = &gpioi;
+		gpio25 = &gpioz;
+		i2c3 = &i2c4;
+	};
+};
+
+&bsec {
+	board_id: board_id@ec {
+		reg = <0xec 0x4>;
+		st,non-secure-otp;
+	};
+};
+
+&clk_hse {
+	st,digbypass;
+};
+
+&cpu0{
+	cpu-supply = <&vddcore>;
+};
+
+&cpu1{
+	cpu-supply = <&vddcore>;
+};
+
+&hash1 {
+	status = "okay";
+};
+
+/* CLOCK init */
+&rcc {
+	secure-status = "disabled";
+	st,clksrc = <
+		CLK_MPU_PLL1P
+		CLK_AXI_PLL2P
+		CLK_MCU_PLL3P
+		CLK_PLL12_HSE
+		CLK_PLL3_HSE
+		CLK_PLL4_HSE
+		CLK_RTC_LSE
+		CLK_MCO1_DISABLED
+		CLK_MCO2_DISABLED
+	>;
+
+	st,clkdiv = <
+		1 /*MPU*/
+		0 /*AXI*/
+		0 /*MCU*/
+		1 /*APB1*/
+		1 /*APB2*/
+		1 /*APB3*/
+		1 /*APB4*/
+		2 /*APB5*/
+		23 /*RTC*/
+		0 /*MCO1*/
+		0 /*MCO2*/
+	>;
+
+	st,pkcs = <
+		CLK_CKPER_HSE
+		CLK_FMC_ACLK
+		CLK_QSPI_ACLK
+		CLK_ETH_PLL4P
+		CLK_SDMMC12_PLL4P
+		CLK_DSI_DSIPLL
+		CLK_STGEN_HSE
+		CLK_USBPHY_HSE
+		CLK_SPI2S1_PLL3Q
+		CLK_SPI2S23_PLL3Q
+		CLK_SPI45_HSI
+		CLK_SPI6_HSI
+		CLK_I2C46_HSI
+		CLK_SDMMC3_PLL4P
+		CLK_USBO_USBPHY
+		CLK_ADC_CKPER
+		CLK_CEC_LSE
+		CLK_I2C12_HSI
+		CLK_I2C35_HSI
+		CLK_UART1_HSI
+		CLK_UART24_HSI
+		CLK_UART35_HSI
+		CLK_UART6_HSI
+		CLK_UART78_HSI
+		CLK_SPDIF_PLL4P
+		CLK_FDCAN_PLL4R
+		CLK_SAI1_PLL3Q
+		CLK_SAI2_PLL3Q
+		CLK_SAI3_PLL3Q
+		CLK_SAI4_PLL3Q
+		CLK_RNG1_LSI
+		CLK_RNG2_LSI
+		CLK_LPTIM1_PCLK1
+		CLK_LPTIM23_PCLK3
+		CLK_LPTIM45_LSE
+	>;
+
+	/* VCO = 1300.0 MHz => P = 650 (CPU) */
+	pll1: st,pll@0 {
+		compatible = "st,stm32mp1-pll";
+		reg = <0>;
+		cfg = < 2 80 0 0 0 PQR(1,0,0) >;
+		frac = < 0x800 >;
+	};
+
+	/* VCO = 1066.0 MHz => P = 266 (AXI), Q = 533 (GPU), R = 533 (DDR) */
+	pll2: st,pll@1 {
+		compatible = "st,stm32mp1-pll";
+		reg = <1>;
+		cfg = <2 65 1 0 0 PQR(1,1,1)>;
+		frac = <0x1400>;
+	};
+
+	/* VCO = 417.8 MHz => P = 209, Q = 24, R = 11 */
+	pll3: st,pll@2 {
+		compatible = "st,stm32mp1-pll";
+		reg = <2>;
+		cfg = <1 33 1 16 36 PQR(1,1,1)>;
+		frac = <0x1a04>;
+	};
+
+	/* VCO = 594.0 MHz => P = 99, Q = 74, R = 74 */
+	pll4: st,pll@3 {
+		compatible = "st,stm32mp1-pll";
+		reg = <3>;
+		cfg = <3 98 5 7 7 PQR(1,1,1)>;
+	};
+};
diff --git a/fdts/stm32mp15xxaa-pinctrl.dtsi b/fdts/stm32mp15xxaa-pinctrl.dtsi
index 64e566b..f1d540a 100644
--- a/fdts/stm32mp15xxaa-pinctrl.dtsi
+++ b/fdts/stm32mp15xxaa-pinctrl.dtsi
@@ -1,7 +1,7 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2019 - All Rights Reserved
- * Author: Alexandre Torgue <alexandre.torgue@st.com>
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
+ * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics.
  */
 
 &pinctrl {
diff --git a/fdts/stm32mp15xxab-pinctrl.dtsi b/fdts/stm32mp15xxab-pinctrl.dtsi
index d29af89..b58c7e2 100644
--- a/fdts/stm32mp15xxab-pinctrl.dtsi
+++ b/fdts/stm32mp15xxab-pinctrl.dtsi
@@ -1,7 +1,7 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2019 - All Rights Reserved
- * Author: Alexandre Torgue <alexandre.torgue@st.com>
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
+ * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics.
  */
 
 &pinctrl {
diff --git a/fdts/stm32mp15xxac-pinctrl.dtsi b/fdts/stm32mp15xxac-pinctrl.dtsi
index 5d8199f..11e7e03 100644
--- a/fdts/stm32mp15xxac-pinctrl.dtsi
+++ b/fdts/stm32mp15xxac-pinctrl.dtsi
@@ -1,7 +1,7 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2019 - All Rights Reserved
- * Author: Alexandre Torgue <alexandre.torgue@st.com>
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
+ * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics.
  */
 
 &pinctrl {
diff --git a/fdts/stm32mp15xxad-pinctrl.dtsi b/fdts/stm32mp15xxad-pinctrl.dtsi
index 023f540..52806d6 100644
--- a/fdts/stm32mp15xxad-pinctrl.dtsi
+++ b/fdts/stm32mp15xxad-pinctrl.dtsi
@@ -1,7 +1,7 @@
 // SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
 /*
- * Copyright (C) STMicroelectronics 2019 - All Rights Reserved
- * Author: Alexandre Torgue <alexandre.torgue@st.com>
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
+ * Author: Alexandre Torgue <alexandre.torgue@st.com> for STMicroelectronics.
  */
 
 &pinctrl {
diff --git a/fdts/tc.dts b/fdts/tc.dts
new file mode 100644
index 0000000..13c9e16
--- /dev/null
+++ b/fdts/tc.dts
@@ -0,0 +1,479 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/dts-v1/;
+
+/ {
+	compatible = "arm,tc";
+	interrupt-parent = <&gic>;
+	#address-cells = <2>;
+	#size-cells = <2>;
+
+	aliases {
+		serial0 = &soc_uart0;
+	};
+
+	chosen {
+		bootargs = "console=ttyAMA0 debug user_debug=31 earlycon=pl011,0x7ff80000 loglevel=9 androidboot.hardware=total_compute androidboot.boot_devices=1c050000.mmci ip=dhcp androidboot.selinux=permissive allow_mismatched_32bit_el0";
+		stdout-path = "serial0:115200n8";
+	};
+
+	cpus {
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		cpu-map {
+			cluster0 {
+				core0 {
+					cpu = <&CPU0>;
+				};
+				core1 {
+					cpu = <&CPU1>;
+				};
+				core2 {
+					cpu = <&CPU2>;
+				};
+				core3 {
+					cpu = <&CPU3>;
+				};
+				core4 {
+					cpu = <&CPU4>;
+				};
+				core5 {
+					cpu = <&CPU5>;
+				};
+				core6 {
+					cpu = <&CPU6>;
+				};
+				core7 {
+					cpu = <&CPU7>;
+				};
+			};
+		};
+
+		/*
+		 * The timings below are just to demonstrate working cpuidle.
+		 * These values may be inaccurate.
+		 */
+		idle-states {
+			entry-method = "arm,psci";
+
+			CPU_SLEEP_0: cpu-sleep-0 {
+				compatible = "arm,idle-state";
+				arm,psci-suspend-param = <0x0010000>;
+				local-timer-stop;
+				entry-latency-us = <300>;
+				exit-latency-us = <1200>;
+				min-residency-us = <2000>;
+			};
+			CLUSTER_SLEEP_0: cluster-sleep-0 {
+				compatible = "arm,idle-state";
+				arm,psci-suspend-param = <0x1010000>;
+				local-timer-stop;
+				entry-latency-us = <400>;
+				exit-latency-us = <1200>;
+				min-residency-us = <2500>;
+			};
+		};
+
+		amus {
+			amu: amu-0 {
+				#address-cells = <1>;
+				#size-cells = <0>;
+
+				mpmm_gear0: counter@0 {
+					reg = <0>;
+
+					enable-at-el3;
+				};
+
+				mpmm_gear1: counter@1 {
+					reg = <1>;
+
+					enable-at-el3;
+				};
+
+				mpmm_gear2: counter@2 {
+					reg = <2>;
+
+					enable-at-el3;
+				};
+			};
+		};
+
+		CPU0:cpu@0 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 0>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <406>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU1:cpu@100 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x100>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 0>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <406>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU2:cpu@200 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x200>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 0>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <406>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU3:cpu@300 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x300>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 0>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <406>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU4:cpu@400 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x400>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 1>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <912>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU5:cpu@500 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x500>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 1>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <912>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU6:cpu@600 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x600>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 1>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <912>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+		CPU7:cpu@700 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x700>;
+			enable-method = "psci";
+			clocks = <&scmi_dvfs 2>;
+			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
+			capacity-dmips-mhz = <1024>;
+			amu = <&amu>;
+			supports-mpmm;
+		};
+
+	};
+
+	reserved-memory {
+		#address-cells = <2>;
+		#size-cells = <2>;
+		ranges;
+
+		optee@0xfce00000 {
+			reg = <0x00000000 0xfce00000 0 0x00200000>;
+			no-map;
+		};
+	};
+
+	psci {
+		compatible = "arm,psci-1.0", "arm,psci-0.2";
+		method = "smc";
+	};
+
+	sram: sram@6000000 {
+		compatible = "mmio-sram";
+		reg = <0x0 0x06000000 0x0 0x8000>;
+
+		#address-cells = <1>;
+		#size-cells = <1>;
+		ranges = <0 0x0 0x06000000 0x8000>;
+
+		cpu_scp_scmi_mem: scp-shmem@0 {
+			compatible = "arm,scmi-shmem";
+			reg = <0x0 0x80>;
+		};
+	};
+
+	mbox_db_rx: mhu@45010000 {
+		compatible = "arm,mhuv2-rx","arm,primecell";
+		reg = <0x0 0x45010000 0x0 0x1000>;
+		clocks = <&soc_refclk100mhz>;
+		clock-names = "apb_pclk";
+		#mbox-cells = <2>;
+		interrupts = <0 317 4>;
+		interrupt-names = "mhu_rx";
+		mhu-protocol = "doorbell";
+		arm,mhuv2-protocols = <0 1>;
+	};
+
+	mbox_db_tx: mhu@45000000 {
+		compatible = "arm,mhuv2-tx","arm,primecell";
+		reg = <0x0 0x45000000 0x0 0x1000>;
+		clocks = <&soc_refclk100mhz>;
+		clock-names = "apb_pclk";
+		#mbox-cells = <2>;
+		interrupt-names = "mhu_tx";
+		mhu-protocol = "doorbell";
+		arm,mhuv2-protocols = <0 1>;
+	};
+
+	scmi {
+		compatible = "arm,scmi";
+		mbox-names = "tx", "rx";
+		mboxes = <&mbox_db_tx 0 0 &mbox_db_rx 0 0 >;
+		shmem = <&cpu_scp_scmi_mem &cpu_scp_scmi_mem>;
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		scmi_dvfs: protocol@13 {
+			reg = <0x13>;
+			#clock-cells = <1>;
+		};
+
+		scmi_clk: protocol@14 {
+			reg = <0x14>;
+			#clock-cells = <1>;
+		};
+	};
+
+	gic: interrupt-controller@2c010000 {
+		compatible = "arm,gic-600", "arm,gic-v3";
+		#address-cells = <2>;
+		#interrupt-cells = <3>;
+		#size-cells = <2>;
+		ranges;
+		interrupt-controller;
+		reg = <0x0 0x30000000 0 0x10000>, /* GICD */
+		      <0x0 0x30080000 0 0x200000>; /* GICR */
+		interrupts = <0x1 0x9 0x4>;
+	};
+
+	timer {
+		compatible = "arm,armv8-timer";
+		interrupts = <0x1 13 0x8>,
+			     <0x1 14 0x8>,
+			     <0x1 11 0x8>,
+			     <0x1 10 0x8>;
+	};
+
+	soc_refclk100mhz: refclk100mhz {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <100000000>;
+		clock-output-names = "apb_pclk";
+	};
+
+	soc_refclk60mhz: refclk60mhz {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <60000000>;
+		clock-output-names = "iofpga_clk";
+	};
+
+	soc_uartclk:  uartclk {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <50000000>;
+		clock-output-names = "uartclk";
+	};
+
+	soc_uart0: uart@7ff80000 {
+		compatible = "arm,pl011", "arm,primecell";
+		reg = <0x0 0x7ff80000 0x0 0x1000>;
+		interrupts = <0x0 116 0x4>;
+		clocks = <&soc_uartclk>, <&soc_refclk100mhz>;
+		clock-names = "uartclk", "apb_pclk";
+		status = "okay";
+	};
+
+	vencoder {
+		compatible = "drm,virtual-encoder";
+
+		port {
+			vencoder_in: endpoint {
+				remote-endpoint = <&dp_pl0_out0>;
+			};
+		};
+
+		display-timings {
+			panel-timing {
+				clock-frequency = <25175000>;
+				hactive = <640>;
+				vactive = <480>;
+				hfront-porch = <16>;
+				hback-porch = <48>;
+				hsync-len = <96>;
+				vfront-porch = <10>;
+				vback-porch = <33>;
+				vsync-len = <2>;
+			};
+		};
+
+	};
+
+	hdlcd: hdlcd@7ff60000 {
+		compatible = "arm,hdlcd";
+		reg = <0x0 0x7ff60000 0x0 0x1000>;
+		interrupts = <0x0 117 0x4>;
+		clocks = <&fake_hdlcd_clk>;
+		clock-names = "pxlclk";
+		status = "disabled";
+
+		port {
+			hdlcd_out: endpoint {
+				remote-endpoint = <&vencoder_in>;
+			};
+		};
+	};
+
+	fake_hdlcd_clk: fake-hdlcd-clk {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <25175000>;
+		clock-output-names = "pxlclk";
+	};
+
+	ethernet@18000000 {
+		compatible = "smsc,lan91c111";
+		reg = <0x0 0x18000000 0x0 0x10000>;
+		interrupts = <0 109 4>;
+	};
+
+	kmi@1c060000 {
+		compatible = "arm,pl050", "arm,primecell";
+		reg = <0x0 0x001c060000 0x0 0x1000>;
+		interrupts = <0 197 4>;
+		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
+		clock-names = "KMIREFCLK", "apb_pclk";
+	};
+
+	kmi@1c070000 {
+		compatible = "arm,pl050", "arm,primecell";
+		reg = <0x0 0x001c070000 0x0 0x1000>;
+		interrupts = <0 103 4>;
+		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
+		clock-names = "KMIREFCLK", "apb_pclk";
+	};
+
+	bp_clock24mhz: clock24mhz {
+		compatible = "fixed-clock";
+		#clock-cells = <0>;
+		clock-frequency = <24000000>;
+		clock-output-names = "bp:clock24mhz";
+	};
+
+	virtio_block@1c130000 {
+		compatible = "virtio,mmio";
+		reg = <0x0 0x1c130000 0x0 0x200>;
+		interrupts = <0 204 4>;
+	};
+
+	sysreg: sysreg@1c010000 {
+		compatible = "arm,vexpress-sysreg";
+		reg = <0x0 0x001c010000 0x0 0x1000>;
+		gpio-controller;
+		#gpio-cells = <2>;
+	};
+
+	fixed_3v3: v2m-3v3 {
+		compatible = "regulator-fixed";
+		regulator-name = "3V3";
+		regulator-min-microvolt = <3300000>;
+		regulator-max-microvolt = <3300000>;
+		regulator-always-on;
+	};
+
+	mmci@1c050000 {
+		compatible = "arm,pl180", "arm,primecell";
+		reg = <0x0 0x001c050000 0x0 0x1000>;
+		interrupts = <0 107 0x4>,
+			     <0 108 0x4>;
+		cd-gpios = <&sysreg 0 0>;
+		wp-gpios = <&sysreg 1 0>;
+		bus-width = <8>;
+		max-frequency = <12000000>;
+		vmmc-supply = <&fixed_3v3>;
+		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
+		clock-names = "mclk", "apb_pclk";
+	};
+
+	dp0: display@2cc00000 {
+		#address-cells = <1>;
+		#size-cells = <0>;
+		compatible = "arm,mali-d71";
+		reg = <0 0x2cc00000 0 0x20000>;
+		interrupts = <0 69 4>;
+		interrupt-names = "DPU";
+		clocks = <&scmi_clk 0>;
+		clock-names = "aclk";
+		pl0: pipeline@0 {
+			reg = <0>;
+			clocks = <&scmi_clk 1>;
+			clock-names = "pxclk";
+			pl_id = <0>;
+			ports {
+				#address-cells = <1>;
+				#size-cells = <0>;
+				port@0 {
+					reg = <0>;
+					dp_pl0_out0: endpoint {
+						remote-endpoint = <&vencoder_in>;
+					};
+				};
+			};
+		};
+
+		pl1: pipeline@1 {
+			reg = <1>;
+			clocks = <&scmi_clk 2>;
+			clock-names = "pxclk";
+			pl_id = <1>;
+			ports {
+				#address-cells = <1>;
+				#size-cells = <0>;
+				port@0 {
+					reg = <0>;
+				};
+			};
+		};
+	};
+
+};
diff --git a/fdts/tc0.dts b/fdts/tc0.dts
deleted file mode 100644
index 763c813..0000000
--- a/fdts/tc0.dts
+++ /dev/null
@@ -1,373 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/dts-v1/;
-
-/ {
-	compatible = "arm,tc0";
-	interrupt-parent = <&gic>;
-	#address-cells = <2>;
-	#size-cells = <2>;
-
-	aliases {
-		serial0 = &soc_uart0;
-	};
-
-	chosen {
-		stdout-path = "soc_uart0:115200n8";
-	};
-
-	cpus {
-		#address-cells = <1>;
-		#size-cells = <0>;
-
-		cpu-map {
-			cluster0 {
-				core0 {
-					cpu = <&CPU0>;
-				};
-				core1 {
-					cpu = <&CPU1>;
-				};
-				core2 {
-					cpu = <&CPU2>;
-				};
-				core3 {
-					cpu = <&CPU3>;
-				};
-			};
-		};
-
-		/*
-		 * The timings below are just to demonstrate working cpuidle.
-		 * These values may be inaccurate.
-		 */
-		idle-states {
-			entry-method = "arm,psci";
-
-			CPU_SLEEP_0: cpu-sleep-0 {
-				compatible = "arm,idle-state";
-				arm,psci-suspend-param = <0x0010000>;
-				local-timer-stop;
-				entry-latency-us = <300>;
-				exit-latency-us = <1200>;
-				min-residency-us = <2000>;
-			};
-			CLUSTER_SLEEP_0: cluster-sleep-0 {
-				compatible = "arm,idle-state";
-				arm,psci-suspend-param = <0x1010000>;
-				local-timer-stop;
-				entry-latency-us = <400>;
-				exit-latency-us = <1200>;
-				min-residency-us = <2500>;
-			};
-		};
-
-		CPU0:cpu@0 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x0>;
-			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
-			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
-		};
-
-		CPU1:cpu@100 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x100>;
-			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
-			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
-		};
-
-		CPU2:cpu@200 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x200>;
-			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
-			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
-		};
-
-		CPU3:cpu@300 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x300>;
-			enable-method = "psci";
-			clocks = <&scmi_dvfs 0>;
-			cpu-idle-states = <&CPU_SLEEP_0 &CLUSTER_SLEEP_0>;
-		};
-
-	};
-
-	memory@80000000 {
-		device_type = "memory";
-		reg = <0x0 0x80000000 0x0 0x7d000000>;
-	};
-
-	psci {
-		compatible = "arm,psci-1.0", "arm,psci-0.2", "arm,psci";
-		method = "smc";
-	};
-
-	sram: sram@6000000 {
-		compatible = "mmio-sram";
-		reg = <0x0 0x06000000 0x0 0x8000>;
-
-		#address-cells = <1>;
-		#size-cells = <1>;
-		ranges = <0 0x0 0x06000000 0x8000>;
-
-		cpu_scp_scmi_mem: scp-shmem@0 {
-			compatible = "arm,scmi-shmem";
-			reg = <0x0 0x80>;
-		};
-	};
-
-	mbox_db_rx: mhu@45010000 {
-		compatible = "arm,mhuv2","arm,primecell";
-		reg = <0x0 0x45010000 0x0 0x1000>;
-		clocks = <&soc_refclk100mhz>;
-		clock-names = "apb_pclk";
-		#mbox-cells = <1>;
-		interrupts = <0 317 4>;
-		interrupt-names = "mhu_rx";
-		mhu-protocol = "doorbell";
-	};
-
-	mbox_db_tx: mhu@45000000 {
-		compatible = "arm,mhuv2","arm,primecell";
-		reg = <0x0 0x45000000 0x0 0x1000>;
-		clocks = <&soc_refclk100mhz>;
-		clock-names = "apb_pclk";
-		#mbox-cells = <1>;
-		interrupt-names = "mhu_tx";
-		mhu-protocol = "doorbell";
-	};
-
-	scmi {
-		compatible = "arm,scmi";
-		method = "mailbox-doorbell";
-		mbox-names = "tx", "rx";
-		mboxes = <&mbox_db_tx 0 &mbox_db_rx 0>;
-		shmem = <&cpu_scp_scmi_mem &cpu_scp_scmi_mem>;
-		#address-cells = <1>;
-		#size-cells = <0>;
-
-		scmi_dvfs: protocol@13 {
-			reg = <0x13>;
-			#clock-cells = <1>;
-		};
-
-		scmi_clk: protocol@14 {
-			reg = <0x14>;
-			#clock-cells = <1>;
-		};
-	};
-
-	gic: interrupt-controller@2c010000 {
-		compatible = "arm,gic-600", "arm,gic-v3";
-		#address-cells = <2>;
-		#interrupt-cells = <3>;
-		#size-cells = <2>;
-		ranges;
-		interrupt-controller;
-		reg = <0x0 0x30000000 0 0x10000>, /* GICD */
-		      <0x0 0x30140000 0 0x200000>; /* GICR */
-		interrupts = <0x1 0x9 0x4>;
-	};
-
-	timer {
-		compatible = "arm,armv8-timer";
-		interrupts = <0x1 13 0x8>,
-			     <0x1 14 0x8>,
-			     <0x1 11 0x8>,
-			     <0x1 10 0x8>;
-	};
-
-	soc_refclk100mhz: refclk100mhz {
-		compatible = "fixed-clock";
-		#clock-cells = <0>;
-		clock-frequency = <100000000>;
-		clock-output-names = "apb_pclk";
-	};
-
-	soc_refclk60mhz: refclk60mhz {
-		compatible = "fixed-clock";
-		#clock-cells = <0>;
-		clock-frequency = <60000000>;
-		clock-output-names = "iofpga_clk";
-	};
-
-	soc_uartclk:  uartclk {
-		compatible = "fixed-clock";
-		#clock-cells = <0>;
-		clock-frequency = <50000000>;
-		clock-output-names = "uartclk";
-	};
-
-	soc_uart0: uart@7ff80000 {
-		compatible = "arm,pl011", "arm,primecell";
-		reg = <0x0 0x7ff80000 0x0 0x1000>;
-		interrupts = <0x0 116 0x4>;
-		clocks = <&soc_uartclk>, <&soc_refclk100mhz>;
-		clock-names = "uartclk", "apb_pclk";
-		status = "okay";
-	};
-
-	vencoder {
-		compatible = "drm,virtual-encoder";
-
-		port {
-			vencoder_in: endpoint {
-				remote-endpoint = <&dp_pl0_out0>;
-			};
-		};
-
-		display-timings {
-			panel-timing {
-				clock-frequency = <25175000>;
-				hactive = <640>;
-				vactive = <480>;
-				hfront-porch = <16>;
-				hback-porch = <48>;
-				hsync-len = <96>;
-				vfront-porch = <10>;
-				vback-porch = <33>;
-				vsync-len = <2>;
-			};
-		};
-
-	};
-
-	hdlcd: hdlcd@7ff60000 {
-		compatible = "arm,hdlcd";
-		reg = <0x0 0x7ff60000 0x0 0x1000>;
-		interrupts = <0x0 117 0x4>;
-		clocks = <&fake_hdlcd_clk>;
-		clock-names = "pxlclk";
-		status = "disabled";
-
-		port {
-			hdlcd_out: endpoint {
-				remote-endpoint = <&vencoder_in>;
-			};
-		};
-	};
-
-	fake_hdlcd_clk: fake-hdlcd-clk {
-		compatible = "fixed-clock";
-		#clock-cells = <0>;
-		clock-frequency = <25175000>;
-		clock-output-names = "pxlclk";
-	};
-
-	ethernet@18000000 {
-		compatible = "smsc,lan91c111";
-		reg = <0x0 0x18000000 0x0 0x10000>;
-		interrupts = <0 109 4>;
-	};
-
-	kmi@1c060000 {
-		compatible = "arm,pl050", "arm,primecell";
-		reg = <0x0 0x001c060000 0x0 0x1000>;
-		interrupts = <0 197 4>;
-		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
-		clock-names = "KMIREFCLK", "apb_pclk";
-	};
-
-	kmi@1c070000 {
-		compatible = "arm,pl050", "arm,primecell";
-		reg = <0x0 0x001c070000 0x0 0x1000>;
-		interrupts = <0 103 4>;
-		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
-		clock-names = "KMIREFCLK", "apb_pclk";
-	};
-
-	bp_clock24mhz: clock24mhz {
-		compatible = "fixed-clock";
-		#clock-cells = <0>;
-		clock-frequency = <24000000>;
-		clock-output-names = "bp:clock24mhz";
-	};
-
-	virtio_block@1c130000 {
-		compatible = "virtio,mmio";
-		reg = <0x0 0x1c130000 0x0 0x200>;
-		interrupts = <0 204 4>;
-	};
-
-	sysreg: sysreg@1c010000 {
-		compatible = "arm,vexpress-sysreg";
-		reg = <0x0 0x001c010000 0x0 0x1000>;
-		gpio-controller;
-		#gpio-cells = <2>;
-	};
-
-	fixed_3v3: v2m-3v3 {
-		compatible = "regulator-fixed";
-		regulator-name = "3V3";
-		regulator-min-microvolt = <3300000>;
-		regulator-max-microvolt = <3300000>;
-		regulator-always-on;
-	};
-
-	mmci@1c050000 {
-		compatible = "arm,pl180", "arm,primecell";
-		reg = <0x0 0x001c050000 0x0 0x1000>;
-		interrupts = <0 107 0x4>,
-			     <0 108 0x4>;
-		cd-gpios = <&sysreg 0 0>;
-		wp-gpios = <&sysreg 1 0>;
-		bus-width = <8>;
-		max-frequency = <12000000>;
-		vmmc-supply = <&fixed_3v3>;
-		clocks = <&bp_clock24mhz>, <&bp_clock24mhz>;
-		clock-names = "mclk", "apb_pclk";
-	};
-
-	dp0: display@2cc00000 {
-		#address-cells = <1>;
-		#size-cells = <0>;
-		compatible = "arm,mali-d71";
-		reg = <0 0x2cc00000 0 0x20000>;
-		interrupts = <0 69 4>;
-		interrupt-names = "DPU";
-		clocks = <&scmi_clk 0>;
-		clock-names = "aclk";
-		pl0: pipeline@0 {
-			reg = <0>;
-			clocks = <&scmi_clk 1>;
-			clock-names = "pxclk";
-			pl_id = <0>;
-			ports {
-				#address-cells = <1>;
-				#size-cells = <0>;
-				port@0 {
-					reg = <0>;
-					dp_pl0_out0: endpoint {
-						remote-endpoint = <&vencoder_in>;
-					};
-				};
-			};
-		};
-
-		pl1: pipeline@1 {
-			reg = <1>;
-			clocks = <&scmi_clk 2>;
-			clock-names = "pxclk";
-			pl_id = <1>;
-			ports {
-				#address-cells = <1>;
-				#size-cells = <0>;
-				port@0 {
-					reg = <0>;
-				};
-			};
-		};
-	};
-};
diff --git a/include/arch/aarch32/arch.h b/include/arch/aarch32/arch.h
index db8938f..a1bd942 100644
--- a/include/arch/aarch32/arch.h
+++ b/include/arch/aarch32/arch.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -102,6 +102,21 @@
 /* CSSELR definitions */
 #define LEVEL_SHIFT		U(1)
 
+/* ID_DFR0_EL1 definitions */
+#define ID_DFR0_COPTRC_SHIFT		U(12)
+#define ID_DFR0_COPTRC_MASK		U(0xf)
+#define ID_DFR0_COPTRC_SUPPORTED	U(1)
+#define ID_DFR0_COPTRC_LENGTH		U(4)
+#define ID_DFR0_TRACEFILT_SHIFT		U(28)
+#define ID_DFR0_TRACEFILT_MASK		U(0xf)
+#define ID_DFR0_TRACEFILT_SUPPORTED	U(1)
+#define ID_DFR0_TRACEFILT_LENGTH	U(4)
+
+/* ID_DFR1_EL1 definitions */
+#define ID_DFR1_MTPMU_SHIFT	U(0)
+#define ID_DFR1_MTPMU_MASK	U(0xf)
+#define ID_DFR1_MTPMU_SUPPORTED	U(1)
+
 /* ID_MMFR4 definitions */
 #define ID_MMFR4_CNP_SHIFT	U(12)
 #define ID_MMFR4_CNP_LENGTH	U(4)
@@ -111,6 +126,9 @@
 #define ID_PFR0_AMU_SHIFT	U(20)
 #define ID_PFR0_AMU_LENGTH	U(4)
 #define ID_PFR0_AMU_MASK	U(0xf)
+#define ID_PFR0_AMU_NOT_SUPPORTED	U(0x0)
+#define ID_PFR0_AMU_V1		U(0x1)
+#define ID_PFR0_AMU_V1P1	U(0x2)
 
 #define ID_PFR0_DIT_SHIFT	U(24)
 #define ID_PFR0_DIT_LENGTH	U(4)
@@ -126,6 +144,9 @@
 #define ID_PFR1_GENTIMER_MASK	U(0xf)
 #define ID_PFR1_GIC_SHIFT	U(28)
 #define ID_PFR1_GIC_MASK	U(0xf)
+#define ID_PFR1_SEC_SHIFT	U(4)
+#define ID_PFR1_SEC_MASK	U(0xf)
+#define ID_PFR1_ELx_ENABLED	U(1)
 
 /* SCTLR definitions */
 #define SCTLR_RES1_DEF		((U(1) << 23) | (U(1) << 22) | (U(1) << 4) | \
@@ -162,8 +183,10 @@
 #define SDCR_SPD_DISABLE	U(0x2)
 #define SDCR_SPD_ENABLE		U(0x3)
 #define SDCR_SCCD_BIT		(U(1) << 23)
+#define SDCR_TTRF_BIT		(U(1) << 19)
 #define SDCR_SPME_BIT		(U(1) << 17)
 #define SDCR_RESET_VAL		U(0x0)
+#define SDCR_MTPME_BIT		(U(1) << 28)
 
 /* HSCTLR definitions */
 #define HSCTLR_RES1	((U(1) << 29) | (U(1) << 28) | (U(1) << 23) | \
@@ -230,7 +253,8 @@
 /* HCPTR definitions */
 #define HCPTR_RES1		((U(1) << 13) | (U(1) << 12) | U(0x3ff))
 #define TCPAC_BIT		(U(1) << 31)
-#define TAM_BIT			(U(1) << 30)
+#define TAM_SHIFT		U(30)
+#define TAM_BIT			(U(1) << TAM_SHIFT)
 #define TTA_BIT			(U(1) << 20)
 #define TCP11_BIT		(U(1) << 11)
 #define TCP10_BIT		(U(1) << 10)
@@ -244,6 +268,7 @@
 #define VTTBR_BADDR_SHIFT	U(0)
 
 /* HDCR definitions */
+#define HDCR_MTPME_BIT		(U(1) << 28)
 #define HDCR_HLP_BIT		(U(1) << 26)
 #define HDCR_HPME_BIT		(U(1) << 7)
 #define HDCR_RESET_VAL		U(0x0)
@@ -503,6 +528,8 @@
 #define CTR		p15, 0, c0, c0, 1
 #define CNTFRQ		p15, 0, c14, c0, 0
 #define ID_MMFR4	p15, 0, c0, c2, 6
+#define ID_DFR0		p15, 0, c0, c1, 2
+#define ID_DFR1		p15, 0, c0, c3, 5
 #define ID_PFR0		p15, 0, c0, c1, 0
 #define ID_PFR1		p15, 0, c0, c1, 1
 #define MAIR0		p15, 0, c10, c2, 0
@@ -642,7 +669,7 @@
 #define PAR_ADDR_MASK	(BIT_64(40) - ULL(1)) /* 40-bits-wide page address */
 
 /*******************************************************************************
- * Definitions for system register interface to AMU for ARMv8.4 onwards
+ * Definitions for system register interface to AMU for FEAT_AMUv1
  ******************************************************************************/
 #define AMCR		p15, 0, c13, c2, 0
 #define AMCFGR		p15, 0, c13, c2, 1
@@ -701,6 +728,26 @@
 #define AMEVTYPER1E	p15, 0, c13, c15, 6
 #define AMEVTYPER1F	p15, 0, c13, c15, 7
 
+/* AMCNTENSET0 definitions */
+#define AMCNTENSET0_Pn_SHIFT	U(0)
+#define AMCNTENSET0_Pn_MASK	U(0xffff)
+
+/* AMCNTENSET1 definitions */
+#define AMCNTENSET1_Pn_SHIFT	U(0)
+#define AMCNTENSET1_Pn_MASK	U(0xffff)
+
+/* AMCNTENCLR0 definitions */
+#define AMCNTENCLR0_Pn_SHIFT	U(0)
+#define AMCNTENCLR0_Pn_MASK	U(0xffff)
+
+/* AMCNTENCLR1 definitions */
+#define AMCNTENCLR1_Pn_SHIFT	U(0)
+#define AMCNTENCLR1_Pn_MASK	U(0xffff)
+
+/* AMCR definitions */
+#define AMCR_CG1RZ_SHIFT	U(17)
+#define AMCR_CG1RZ_BIT		(ULL(1) << AMCR_CG1RZ_SHIFT)
+
 /* AMCFGR definitions */
 #define AMCFGR_NCG_SHIFT	U(28)
 #define AMCFGR_NCG_MASK		U(0xf)
@@ -708,6 +755,8 @@
 #define AMCFGR_N_MASK		U(0xff)
 
 /* AMCGCR definitions */
+#define AMCGCR_CG0NC_SHIFT	U(0)
+#define AMCGCR_CG0NC_MASK	U(0xff)
 #define AMCGCR_CG1NC_SHIFT	U(8)
 #define AMCGCR_CG1NC_MASK	U(0xff)
 
diff --git a/include/arch/aarch32/arch_helpers.h b/include/arch/aarch32/arch_helpers.h
index 82efb18..0330989 100644
--- a/include/arch/aarch32/arch_helpers.h
+++ b/include/arch/aarch32/arch_helpers.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -217,6 +217,7 @@
 DEFINE_COPROCR_READ_FUNC(mpidr, MPIDR)
 DEFINE_COPROCR_READ_FUNC(midr, MIDR)
 DEFINE_COPROCR_READ_FUNC(id_mmfr4, ID_MMFR4)
+DEFINE_COPROCR_READ_FUNC(id_dfr0, ID_DFR0)
 DEFINE_COPROCR_READ_FUNC(id_pfr0, ID_PFR0)
 DEFINE_COPROCR_READ_FUNC(id_pfr1, ID_PFR1)
 DEFINE_COPROCR_READ_FUNC(isr, ISR)
@@ -282,6 +283,7 @@
 DEFINE_COPROCR_RW_FUNCS_64(icc_sgi0r_el1, ICC_SGI0R_EL1_64)
 DEFINE_COPROCR_WRITE_FUNC_64(icc_sgi1r, ICC_SGI1R_EL1_64)
 
+DEFINE_COPROCR_RW_FUNCS(sdcr, SDCR)
 DEFINE_COPROCR_RW_FUNCS(hdcr, HDCR)
 DEFINE_COPROCR_RW_FUNCS(cnthp_ctl, CNTHP_CTL)
 DEFINE_COPROCR_READ_FUNC(pmcr, PMCR)
@@ -303,6 +305,7 @@
 /* Coproc registers for 32bit AMU support */
 DEFINE_COPROCR_READ_FUNC(amcfgr, AMCFGR)
 DEFINE_COPROCR_READ_FUNC(amcgcr, AMCGCR)
+DEFINE_COPROCR_RW_FUNCS(amcr, AMCR)
 
 DEFINE_COPROCR_RW_FUNCS(amcntenset0, AMCNTENSET0)
 DEFINE_COPROCR_RW_FUNCS(amcntenset1, AMCNTENSET1)
diff --git a/include/arch/aarch32/asm_macros.S b/include/arch/aarch32/asm_macros.S
index f75da0c..483f9fe 100644
--- a/include/arch/aarch32/asm_macros.S
+++ b/include/arch/aarch32/asm_macros.S
@@ -107,12 +107,12 @@
 
 #else
 	/*
-	 * Macro for mitigating against speculative execution beyond ERET.
-	 * If possible use Speculation Barrier instruction defined in ARMv8.5
+	 * Macro for mitigating against speculative execution beyond ERET. Uses the
+	 * speculation barrier instruction introduced by FEAT_SB, if it's enabled.
 	 */
 	.macro exception_return
 	eret
-#if ARM_ARCH_AT_LEAST(8, 5)
+#if ENABLE_FEAT_SB
 	sb
 #else
 	dsb	nsh
diff --git a/include/arch/aarch32/el3_common_macros.S b/include/arch/aarch32/el3_common_macros.S
index 4fd746d..ad2a039 100644
--- a/include/arch/aarch32/el3_common_macros.S
+++ b/include/arch/aarch32/el3_common_macros.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,6 +10,9 @@
 #include <arch.h>
 #include <asm_macros.S>
 #include <assert_macros.S>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+
+#define PAGE_START_MASK		~(PAGE_SIZE_MASK)
 
 	/*
 	 * Helper macro to initialise EL3 registers we care about.
@@ -60,11 +63,23 @@
 	 *  cp11 field is ignored, but is set to same value as cp10. The cp10
 	 *  field is set to allow access to Advanced SIMD and floating point
 	 *  features from both Security states.
+	 *
+	 * NSACR.NSTRCDIS: When system register trace implemented, Set to one
+	 *  so that NS System register accesses to all implemented trace
+	 *  registers are disabled.
+	 *  When system register trace is not implemented, this bit is RES0 and
+	 *  hence set to zero.
 	 * ---------------------------------------------------------------------
 	 */
 	ldcopr	r0, NSACR
 	and	r0, r0, #NSACR_IMP_DEF_MASK
 	orr	r0, r0, #(NSACR_RESET_VAL | NSACR_ENABLE_FP_ACCESS)
+	ldcopr	r1, ID_DFR0
+	ubfx	r1, r1, #ID_DFR0_COPTRC_SHIFT, #ID_DFR0_COPTRC_LENGTH
+	cmp	r1, #ID_DFR0_COPTRC_SUPPORTED
+	bne	1f
+	orr	r0, r0, #NSTRCDIS_BIT
+1:
 	stcopr	r0, NSACR
 	isb
 
@@ -116,9 +131,22 @@
 	 *  in Secure state. This bit is RES0 in versions of the architecture
 	 *  earlier than ARMv8.5, setting it to 1 doesn't have any effect on
 	 *  them.
+	 *
+	 * SDCR.TTRF: Set to one so that access to trace filter control
+	 *  registers in non-monitor mode generate Monitor trap exception,
+	 *  unless the access generates a higher priority exception when
+	 *  trace filter control(FEAT_TRF) is implemented.
+	 *  When FEAT_TRF is not implemented, this bit is RES0.
 	 * ---------------------------------------------------------------------
 	 */
-	ldr	r0, =(SDCR_RESET_VAL | SDCR_SPD(SDCR_SPD_DISABLE) | SDCR_SCCD_BIT)
+	ldr	r0, =((SDCR_RESET_VAL | SDCR_SPD(SDCR_SPD_DISABLE) | \
+		      SDCR_SCCD_BIT) & ~SDCR_TTRF_BIT)
+	ldcopr	r1, ID_DFR0
+	ubfx	r1, r1, #ID_DFR0_TRACEFILT_SHIFT, #ID_DFR0_TRACEFILT_LENGTH
+	cmp	r1, #ID_DFR0_TRACEFILT_SUPPORTED
+	bne	1f
+	orr	r0, r0, #SDCR_TTRF_BIT
+1:
 	stcopr	r0, SDCR
 
 	/* ---------------------------------------------------------------------
@@ -199,11 +227,18 @@
  *
  * _exception_vectors:
  *	Address of the exception vectors to program in the VBAR_EL3 register.
+ *
+ * _pie_fixup_size:
+ *	Size of memory region to fixup Global Descriptor Table (GDT).
+ *
+ *	A non-zero value is expected when firmware needs GDT to be fixed-up.
+ *
  * -----------------------------------------------------------------------------
  */
 	.macro el3_entrypoint_common					\
 		_init_sctlr, _warm_boot_mailbox, _secondary_cold_boot,	\
-		_init_memory, _init_c_runtime, _exception_vectors
+		_init_memory, _init_c_runtime, _exception_vectors,	\
+		_pie_fixup_size
 
 	/* Make sure we are in Secure Mode */
 #if ENABLE_ASSERTIONS
@@ -242,6 +277,10 @@
 	cps	#MODE32_mon
 	isb
 
+#if DISABLE_MTPMU
+	bl	mtpmu_disable
+#endif
+
 	.if \_warm_boot_mailbox
 		/* -------------------------------------------------------------
 		 * This code will be executed for both warm and cold resets.
@@ -255,6 +294,27 @@
 		bxne	r0
 	.endif /* _warm_boot_mailbox */
 
+	.if \_pie_fixup_size
+#if ENABLE_PIE
+		/*
+		 * ------------------------------------------------------------
+		 * If PIE is enabled fixup the Global descriptor Table only
+		 * once during primary core cold boot path.
+		 *
+		 * Compile time base address, required for fixup, is calculated
+		 * using "pie_fixup" label present within first page.
+		 * ------------------------------------------------------------
+		 */
+	pie_fixup:
+		ldr	r0, =pie_fixup
+		ldr	r1, =PAGE_START_MASK
+		and	r0, r0, r1
+		mov_imm	r1, \_pie_fixup_size
+		add	r1, r1, r0
+		bl	fixup_gdt_reloc
+#endif /* ENABLE_PIE */
+	.endif /* _pie_fixup_size */
+
 	/* ---------------------------------------------------------------------
 	 * Set the exception vectors (VBAR/MVBAR).
 	 * ---------------------------------------------------------------------
@@ -320,10 +380,21 @@
 		 * includes the data and NOBITS sections. This is done to
 		 * safeguard against possible corruption of this memory by
 		 * dirty cache lines in a system cache as a result of use by
-		 * an earlier boot loader stage.
+		 * an earlier boot loader stage. If PIE is enabled however,
+		 * RO sections including the GOT may be modified during
+		 * pie fixup. Therefore, to be on the safe side, invalidate
+		 * the entire image region if PIE is enabled.
 		 * -----------------------------------------------------------------
 		 */
+#if ENABLE_PIE
+#if SEPARATE_CODE_AND_RODATA
+		ldr	r0, =__TEXT_START__
+#else
+		ldr	r0, =__RO_START__
+#endif /* SEPARATE_CODE_AND_RODATA */
+#else
 		ldr	r0, =__RW_START__
+#endif /* ENABLE_PIE */
 		ldr	r1, =__RW_END__
 		sub	r1, r1, r0
 		bl	inv_dcache_range
@@ -335,12 +406,14 @@
 		 */
 		mov	r7, r12
 		ldr	r0, =__BSS_START__
-		ldr	r1, =__BSS_SIZE__
+		ldr	r1, =__BSS_END__
+		sub 	r1, r1, r0
 		bl	zeromem
 
 #if USE_COHERENT_MEM
 		ldr	r0, =__COHERENT_RAM_START__
-		ldr	r1, =__COHERENT_RAM_UNALIGNED_SIZE__
+		ldr	r1, =__COHERENT_RAM_END_UNALIGNED__
+		sub 	r1, r1, r0
 		bl	zeromem
 #endif
 
@@ -354,7 +427,8 @@
 		 */
 		ldr	r0, =__DATA_RAM_START__
 		ldr	r1, =__DATA_ROM_START__
-		ldr	r2, =__DATA_SIZE__
+		ldr	r2, =__DATA_RAM_END__
+		sub 	r2, r2, r0
 		bl	memcpy4
 #endif
 	.endif /* _init_c_runtime */
diff --git a/include/arch/aarch64/arch.h b/include/arch/aarch64/arch.h
index 33e1134..0fb4e74 100644
--- a/include/arch/aarch64/arch.h
+++ b/include/arch/aarch64/arch.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
@@ -161,12 +161,16 @@
 #define ID_AA64PFR0_EL3_SHIFT	U(12)
 #define ID_AA64PFR0_AMU_SHIFT	U(44)
 #define ID_AA64PFR0_AMU_MASK	ULL(0xf)
+#define ID_AA64PFR0_AMU_NOT_SUPPORTED	U(0x0)
+#define ID_AA64PFR0_AMU_V1	U(0x1)
+#define ID_AA64PFR0_AMU_V1P1	U(0x2)
 #define ID_AA64PFR0_ELX_MASK	ULL(0xf)
 #define ID_AA64PFR0_GIC_SHIFT	U(24)
 #define ID_AA64PFR0_GIC_WIDTH	U(4)
 #define ID_AA64PFR0_GIC_MASK	ULL(0xf)
 #define ID_AA64PFR0_SVE_SHIFT	U(32)
 #define ID_AA64PFR0_SVE_MASK	ULL(0xf)
+#define ID_AA64PFR0_SVE_LENGTH	U(4)
 #define ID_AA64PFR0_SEL2_SHIFT	U(36)
 #define ID_AA64PFR0_SEL2_MASK	ULL(0xf)
 #define ID_AA64PFR0_MPAM_SHIFT	U(40)
@@ -178,16 +182,45 @@
 #define ID_AA64PFR0_CSV2_SHIFT	U(56)
 #define ID_AA64PFR0_CSV2_MASK	ULL(0xf)
 #define ID_AA64PFR0_CSV2_LENGTH	U(4)
+#define ID_AA64PFR0_FEAT_RME_SHIFT		U(52)
+#define ID_AA64PFR0_FEAT_RME_MASK		ULL(0xf)
+#define ID_AA64PFR0_FEAT_RME_LENGTH		U(4)
+#define ID_AA64PFR0_FEAT_RME_NOT_SUPPORTED	U(0)
+#define ID_AA64PFR0_FEAT_RME_V1			U(1)
 
 /* Exception level handling */
 #define EL_IMPL_NONE		ULL(0)
 #define EL_IMPL_A64ONLY		ULL(1)
 #define EL_IMPL_A64_A32		ULL(2)
 
+/* ID_AA64DFR0_EL1.TraceVer definitions */
+#define ID_AA64DFR0_TRACEVER_SHIFT	U(4)
+#define ID_AA64DFR0_TRACEVER_MASK	ULL(0xf)
+#define ID_AA64DFR0_TRACEVER_SUPPORTED	ULL(1)
+#define ID_AA64DFR0_TRACEVER_LENGTH	U(4)
+#define ID_AA64DFR0_TRACEFILT_SHIFT	U(40)
+#define ID_AA64DFR0_TRACEFILT_MASK	U(0xf)
+#define ID_AA64DFR0_TRACEFILT_SUPPORTED	U(1)
+#define ID_AA64DFR0_TRACEFILT_LENGTH	U(4)
+
 /* ID_AA64DFR0_EL1.PMS definitions (for ARMv8.2+) */
 #define ID_AA64DFR0_PMS_SHIFT	U(32)
 #define ID_AA64DFR0_PMS_MASK	ULL(0xf)
 
+/* ID_AA64DFR0_EL1.TraceBuffer definitions */
+#define ID_AA64DFR0_TRACEBUFFER_SHIFT		U(44)
+#define ID_AA64DFR0_TRACEBUFFER_MASK		ULL(0xf)
+#define ID_AA64DFR0_TRACEBUFFER_SUPPORTED	ULL(1)
+
+/* ID_AA64DFR0_EL1.MTPMU definitions (for ARMv8.6+) */
+#define ID_AA64DFR0_MTPMU_SHIFT		U(48)
+#define ID_AA64DFR0_MTPMU_MASK		ULL(0xf)
+#define ID_AA64DFR0_MTPMU_SUPPORTED	ULL(1)
+
+/* ID_AA64ISAR0_EL1 definitions */
+#define ID_AA64ISAR0_RNDR_SHIFT	U(60)
+#define ID_AA64ISAR0_RNDR_MASK	ULL(0xf)
+
 /* ID_AA64ISAR1_EL1 definitions */
 #define ID_AA64ISAR1_EL1	S3_0_C0_C6_1
 #define ID_AA64ISAR1_GPI_SHIFT	U(28)
@@ -243,6 +276,21 @@
 #define ID_AA64MMFR1_EL1_TWED_SUPPORTED		ULL(0x1)
 #define ID_AA64MMFR1_EL1_TWED_NOT_SUPPORTED	ULL(0x0)
 
+#define ID_AA64MMFR1_EL1_PAN_SHIFT		U(20)
+#define ID_AA64MMFR1_EL1_PAN_MASK		ULL(0xf)
+#define ID_AA64MMFR1_EL1_PAN_NOT_SUPPORTED	ULL(0x0)
+#define ID_AA64MMFR1_EL1_PAN_SUPPORTED		ULL(0x1)
+#define ID_AA64MMFR1_EL1_PAN2_SUPPORTED		ULL(0x2)
+#define ID_AA64MMFR1_EL1_PAN3_SUPPORTED		ULL(0x3)
+
+#define ID_AA64MMFR1_EL1_VHE_SHIFT		U(8)
+#define ID_AA64MMFR1_EL1_VHE_MASK		ULL(0xf)
+
+#define ID_AA64MMFR1_EL1_HCX_SHIFT		U(40)
+#define ID_AA64MMFR1_EL1_HCX_MASK		ULL(0xf)
+#define ID_AA64MMFR1_EL1_HCX_SUPPORTED		ULL(0x1)
+#define ID_AA64MMFR1_EL1_HCX_NOT_SUPPORTED	ULL(0x0)
+
 /* ID_AA64MMFR2_EL1 definitions */
 #define ID_AA64MMFR2_EL1		S3_0_C0_C7_2
 
@@ -266,13 +314,24 @@
 #define ID_AA64PFR1_EL1_MTE_SHIFT	U(8)
 #define ID_AA64PFR1_EL1_MTE_MASK	ULL(0xf)
 
-#define MTE_UNIMPLEMENTED	ULL(0)
-#define MTE_IMPLEMENTED_EL0	ULL(1)	/* MTE is only implemented at EL0 */
-#define MTE_IMPLEMENTED_ELX	ULL(2)	/* MTE is implemented at all ELs */
+/* Memory Tagging Extension is not implemented */
+#define MTE_UNIMPLEMENTED	U(0)
+/* FEAT_MTE: MTE instructions accessible at EL0 are implemented */
+#define MTE_IMPLEMENTED_EL0	U(1)
+/* FEAT_MTE2: Full MTE is implemented */
+#define MTE_IMPLEMENTED_ELX	U(2)
+/*
+ * FEAT_MTE3: MTE is implemented with support for
+ * asymmetric Tag Check Fault handling
+ */
+#define MTE_IMPLEMENTED_ASY	U(3)
 
 #define ID_AA64PFR1_MPAM_FRAC_SHIFT	ULL(16)
 #define ID_AA64PFR1_MPAM_FRAC_MASK	ULL(0xf)
 
+#define ID_AA64PFR1_EL1_SME_SHIFT	U(24)
+#define ID_AA64PFR1_EL1_SME_MASK	ULL(0xf)
+
 /* ID_PFR1_EL1 definitions */
 #define ID_PFR1_VIRTEXT_SHIFT	U(12)
 #define ID_PFR1_VIRTEXT_MASK	U(0xf)
@@ -286,6 +345,7 @@
 
 #define SCTLR_EL1_RES1	((UL(1) << 29) | (UL(1) << 28) | (UL(1) << 23) | \
 			 (UL(1) << 22) | (UL(1) << 20) | (UL(1) << 11))
+
 #define SCTLR_AARCH32_EL1_RES1 \
 			((U(1) << 23) | (U(1) << 22) | (U(1) << 11) | \
 			 (U(1) << 4) | (U(1) << 3))
@@ -300,9 +360,12 @@
 #define SCTLR_SA_BIT		(ULL(1) << 3)
 #define SCTLR_SA0_BIT		(ULL(1) << 4)
 #define SCTLR_CP15BEN_BIT	(ULL(1) << 5)
+#define SCTLR_nAA_BIT		(ULL(1) << 6)
 #define SCTLR_ITD_BIT		(ULL(1) << 7)
 #define SCTLR_SED_BIT		(ULL(1) << 8)
 #define SCTLR_UMA_BIT		(ULL(1) << 9)
+#define SCTLR_EnRCTX_BIT	(ULL(1) << 10)
+#define SCTLR_EOS_BIT		(ULL(1) << 11)
 #define SCTLR_I_BIT		(ULL(1) << 12)
 #define SCTLR_EnDB_BIT		(ULL(1) << 13)
 #define SCTLR_DZE_BIT		(ULL(1) << 14)
@@ -310,21 +373,67 @@
 #define SCTLR_NTWI_BIT		(ULL(1) << 16)
 #define SCTLR_NTWE_BIT		(ULL(1) << 18)
 #define SCTLR_WXN_BIT		(ULL(1) << 19)
-#define SCTLR_UWXN_BIT		(ULL(1) << 20)
+#define SCTLR_TSCXT_BIT		(ULL(1) << 20)
 #define SCTLR_IESB_BIT		(ULL(1) << 21)
+#define SCTLR_EIS_BIT		(ULL(1) << 22)
+#define SCTLR_SPAN_BIT		(ULL(1) << 23)
 #define SCTLR_E0E_BIT		(ULL(1) << 24)
 #define SCTLR_EE_BIT		(ULL(1) << 25)
 #define SCTLR_UCI_BIT		(ULL(1) << 26)
 #define SCTLR_EnDA_BIT		(ULL(1) << 27)
+#define SCTLR_nTLSMD_BIT	(ULL(1) << 28)
+#define SCTLR_LSMAOE_BIT	(ULL(1) << 29)
 #define SCTLR_EnIB_BIT		(ULL(1) << 30)
 #define SCTLR_EnIA_BIT		(ULL(1) << 31)
 #define SCTLR_BT0_BIT		(ULL(1) << 35)
 #define SCTLR_BT1_BIT		(ULL(1) << 36)
 #define SCTLR_BT_BIT		(ULL(1) << 36)
-#define SCTLR_DSSBS_BIT		(ULL(1) << 44)
+#define SCTLR_ITFSB_BIT		(ULL(1) << 37)
+#define SCTLR_TCF0_SHIFT	U(38)
+#define SCTLR_TCF0_MASK		ULL(3)
+#define SCTLR_ENTP2_BIT		(ULL(1) << 60)
+
+/* Tag Check Faults in EL0 have no effect on the PE */
+#define	SCTLR_TCF0_NO_EFFECT	U(0)
+/* Tag Check Faults in EL0 cause a synchronous exception */
+#define	SCTLR_TCF0_SYNC		U(1)
+/* Tag Check Faults in EL0 are asynchronously accumulated */
+#define	SCTLR_TCF0_ASYNC	U(2)
+/*
+ * Tag Check Faults in EL0 cause a synchronous exception on reads,
+ * and are asynchronously accumulated on writes
+ */
+#define	SCTLR_TCF0_SYNCR_ASYNCW	U(3)
+
+#define SCTLR_TCF_SHIFT		U(40)
+#define SCTLR_TCF_MASK		ULL(3)
+
+/* Tag Check Faults in EL1 have no effect on the PE */
+#define	SCTLR_TCF_NO_EFFECT	U(0)
+/* Tag Check Faults in EL1 cause a synchronous exception */
+#define	SCTLR_TCF_SYNC		U(1)
+/* Tag Check Faults in EL1 are asynchronously accumulated */
+#define	SCTLR_TCF_ASYNC		U(2)
+/*
+ * Tag Check Faults in EL1 cause a synchronous exception on reads,
+ * and are asynchronously accumulated on writes
+ */
+#define	SCTLR_TCF_SYNCR_ASYNCW	U(3)
+
+#define SCTLR_ATA0_BIT		(ULL(1) << 42)
+#define SCTLR_ATA_BIT		(ULL(1) << 43)
+#define SCTLR_DSSBS_SHIFT	U(44)
+#define SCTLR_DSSBS_BIT		(ULL(1) << SCTLR_DSSBS_SHIFT)
+#define SCTLR_TWEDEn_BIT	(ULL(1) << 45)
+#define SCTLR_TWEDEL_SHIFT	U(46)
+#define SCTLR_TWEDEL_MASK	ULL(0xf)
+#define SCTLR_EnASR_BIT		(ULL(1) << 54)
+#define SCTLR_EnAS0_BIT		(ULL(1) << 55)
+#define SCTLR_EnALS_BIT		(ULL(1) << 56)
+#define SCTLR_EPAN_BIT		(ULL(1) << 57)
 #define SCTLR_RESET_VAL		SCTLR_EL3_RES1
 
-/* CPACR_El1 definitions */
+/* CPACR_EL1 definitions */
 #define CPACR_EL1_FPEN(x)	((x) << 20)
 #define CPACR_EL1_FP_TRAP_EL0	UL(0x1)
 #define CPACR_EL1_FP_TRAP_ALL	UL(0x2)
@@ -332,12 +441,20 @@
 
 /* SCR definitions */
 #define SCR_RES1_BITS		((U(1) << 4) | (U(1) << 5))
+#define SCR_NSE_SHIFT		U(62)
+#define SCR_NSE_BIT		(ULL(1) << SCR_NSE_SHIFT)
+#define SCR_GPF_BIT		(UL(1) << 48)
 #define SCR_TWEDEL_SHIFT	U(30)
 #define SCR_TWEDEL_MASK		ULL(0xf)
+#define SCR_HXEn_BIT		(UL(1) << 38)
+#define SCR_ENTP2_SHIFT		U(41)
+#define SCR_ENTP2_BIT		(UL(1) << SCR_ENTP2_SHIFT)
+#define SCR_AMVOFFEN_BIT	(UL(1) << 35)
 #define SCR_TWEDEn_BIT		(UL(1) << 29)
-#define SCR_ECVEN_BIT           (UL(1) << 28)
-#define SCR_FGTEN_BIT           (UL(1) << 27)
+#define SCR_ECVEN_BIT		(UL(1) << 28)
+#define SCR_FGTEN_BIT		(UL(1) << 27)
 #define SCR_ATA_BIT		(UL(1) << 26)
+#define SCR_EnSCXT_BIT		(UL(1) << 25)
 #define SCR_FIEN_BIT		(UL(1) << 21)
 #define SCR_EEL2_BIT		(UL(1) << 18)
 #define SCR_API_BIT		(UL(1) << 17)
@@ -354,11 +471,23 @@
 #define SCR_FIQ_BIT		(UL(1) << 2)
 #define SCR_IRQ_BIT		(UL(1) << 1)
 #define SCR_NS_BIT		(UL(1) << 0)
-#define SCR_VALID_BIT_MASK	U(0x2f8f)
+#define SCR_VALID_BIT_MASK	U(0x24000002F8F)
 #define SCR_RESET_VAL		SCR_RES1_BITS
 
 /* MDCR_EL3 definitions */
+#define MDCR_EnPMSN_BIT		(ULL(1) << 36)
+#define MDCR_MPMX_BIT		(ULL(1) << 35)
+#define MDCR_MCCD_BIT		(ULL(1) << 34)
+#define MDCR_NSTB(x)		((x) << 24)
+#define MDCR_NSTB_EL1		ULL(0x3)
+#define MDCR_NSTBE		(ULL(1) << 26)
+#define MDCR_MTPME_BIT		(ULL(1) << 28)
+#define MDCR_TDCC_BIT		(ULL(1) << 27)
 #define MDCR_SCCD_BIT		(ULL(1) << 23)
+#define MDCR_EPMAD_BIT		(ULL(1) << 21)
+#define MDCR_EDAD_BIT		(ULL(1) << 20)
+#define MDCR_TTRF_BIT		(ULL(1) << 19)
+#define MDCR_STE_BIT		(ULL(1) << 18)
 #define MDCR_SPME_BIT		(ULL(1) << 17)
 #define MDCR_SDD_BIT		(ULL(1) << 16)
 #define MDCR_SPD32(x)		((x) << 14)
@@ -373,7 +502,10 @@
 #define MDCR_EL3_RESET_VAL	ULL(0x0)
 
 /* MDCR_EL2 definitions */
+#define MDCR_EL2_MTPME		(U(1) << 28)
 #define MDCR_EL2_HLP		(U(1) << 26)
+#define MDCR_EL2_E2TB(x)	((x) << 24)
+#define MDCR_EL2_E2TB_EL1	U(0x3)
 #define MDCR_EL2_HCCD		(U(1) << 23)
 #define MDCR_EL2_TTRF		(U(1) << 19)
 #define MDCR_EL2_HPMD		(U(1) << 17)
@@ -405,12 +537,19 @@
 #define VTTBR_BADDR_SHIFT	U(0)
 
 /* HCR definitions */
+#define HCR_RESET_VAL		ULL(0x0)
+#define HCR_AMVOFFEN_SHIFT	U(51)
+#define HCR_AMVOFFEN_BIT	(ULL(1) << HCR_AMVOFFEN_SHIFT)
+#define HCR_TEA_BIT		(ULL(1) << 47)
 #define HCR_API_BIT		(ULL(1) << 41)
 #define HCR_APK_BIT		(ULL(1) << 40)
 #define HCR_E2H_BIT		(ULL(1) << 34)
+#define HCR_HCD_BIT		(ULL(1) << 29)
 #define HCR_TGE_BIT		(ULL(1) << 27)
 #define HCR_RW_SHIFT		U(31)
 #define HCR_RW_BIT		(ULL(1) << HCR_RW_SHIFT)
+#define HCR_TWE_BIT		(ULL(1) << 14)
+#define HCR_TWI_BIT		(ULL(1) << 13)
 #define HCR_AMO_BIT		(ULL(1) << 5)
 #define HCR_IMO_BIT		(ULL(1) << 4)
 #define HCR_FMO_BIT		(ULL(1) << 3)
@@ -438,21 +577,32 @@
 
 /* CPTR_EL3 definitions */
 #define TCPAC_BIT		(U(1) << 31)
-#define TAM_BIT			(U(1) << 30)
+#define TAM_SHIFT		U(30)
+#define TAM_BIT			(U(1) << TAM_SHIFT)
 #define TTA_BIT			(U(1) << 20)
+#define ESM_BIT			(U(1) << 12)
 #define TFP_BIT			(U(1) << 10)
 #define CPTR_EZ_BIT		(U(1) << 8)
-#define CPTR_EL3_RESET_VAL	U(0x0)
+#define CPTR_EL3_RESET_VAL	((TCPAC_BIT | TAM_BIT | TTA_BIT | TFP_BIT) & \
+				~(CPTR_EZ_BIT | ESM_BIT))
 
 /* CPTR_EL2 definitions */
 #define CPTR_EL2_RES1		((U(1) << 13) | (U(1) << 12) | (U(0x3ff)))
 #define CPTR_EL2_TCPAC_BIT	(U(1) << 31)
-#define CPTR_EL2_TAM_BIT	(U(1) << 30)
+#define CPTR_EL2_TAM_SHIFT	U(30)
+#define CPTR_EL2_TAM_BIT	(U(1) << CPTR_EL2_TAM_SHIFT)
+#define CPTR_EL2_SMEN_MASK	ULL(0x3)
+#define CPTR_EL2_SMEN_SHIFT	U(24)
 #define CPTR_EL2_TTA_BIT	(U(1) << 20)
+#define CPTR_EL2_TSM_BIT	(U(1) << 12)
 #define CPTR_EL2_TFP_BIT	(U(1) << 10)
 #define CPTR_EL2_TZ_BIT		(U(1) << 8)
 #define CPTR_EL2_RESET_VAL	CPTR_EL2_RES1
 
+/* VTCR_EL2 definitions */
+#define VTCR_RESET_VAL		U(0x0)
+#define VTCR_EL2_MSA		(U(1) << 31)
+
 /* CPSR/SPSR definitions */
 #define DAIF_FIQ_BIT		(U(1) << 0)
 #define DAIF_IRQ_BIT		(U(1) << 1)
@@ -478,12 +628,21 @@
 #define SPSR_M_MASK		U(0x1)
 #define SPSR_M_AARCH64		U(0x0)
 #define SPSR_M_AARCH32		U(0x1)
+#define SPSR_M_EL2H		U(0x9)
 
 #define SPSR_EL_SHIFT		U(2)
 #define SPSR_EL_WIDTH		U(2)
 
-#define SPSR_SSBS_BIT_AARCH64	BIT_64(12)
-#define SPSR_SSBS_BIT_AARCH32	BIT_64(23)
+#define SPSR_SSBS_SHIFT_AARCH64 U(12)
+#define SPSR_SSBS_BIT_AARCH64	(ULL(1) << SPSR_SSBS_SHIFT_AARCH64)
+#define SPSR_SSBS_SHIFT_AARCH32 U(23)
+#define SPSR_SSBS_BIT_AARCH32	(ULL(1) << SPSR_SSBS_SHIFT_AARCH32)
+
+#define SPSR_PAN_BIT		BIT_64(22)
+
+#define SPSR_DIT_BIT		BIT(24)
+
+#define SPSR_TCO_BIT_AARCH64	BIT_64(25)
 
 #define DISABLE_ALL_EXCEPTIONS \
 		(DAIF_FIQ_BIT | DAIF_IRQ_BIT | DAIF_ABT_BIT | DAIF_DBG_BIT)
@@ -647,13 +806,13 @@
 #define MAX_CACHE_LINE_SIZE	U(0x800) /* 2KB */
 
 /* Physical timer control register bit fields shifts and masks */
-#define CNTP_CTL_ENABLE_SHIFT   U(0)
-#define CNTP_CTL_IMASK_SHIFT    U(1)
-#define CNTP_CTL_ISTATUS_SHIFT  U(2)
+#define CNTP_CTL_ENABLE_SHIFT	U(0)
+#define CNTP_CTL_IMASK_SHIFT	U(1)
+#define CNTP_CTL_ISTATUS_SHIFT	U(2)
 
-#define CNTP_CTL_ENABLE_MASK    U(1)
-#define CNTP_CTL_IMASK_MASK     U(1)
-#define CNTP_CTL_ISTATUS_MASK   U(1)
+#define CNTP_CTL_ENABLE_MASK	U(1)
+#define CNTP_CTL_IMASK_MASK	U(1)
+#define CNTP_CTL_ISTATUS_MASK	U(1)
 
 /* Physical timer control macros */
 #define CNTP_CTL_ENABLE_BIT	(U(1) << CNTP_CTL_ENABLE_SHIFT)
@@ -770,6 +929,20 @@
 #define ZCR_EL2_LEN_MASK	U(0xf)
 
 /*******************************************************************************
+ * Definitions for system register interface to SME as needed in EL3
+ ******************************************************************************/
+#define ID_AA64SMFR0_EL1		S3_0_C0_C4_5
+#define SMCR_EL3			S3_6_C1_C2_6
+
+/* ID_AA64SMFR0_EL1 definitions */
+#define ID_AA64SMFR0_EL1_FA64_BIT	(UL(1) << 63)
+
+/* SMCR_ELx definitions */
+#define SMCR_ELX_LEN_SHIFT		U(0)
+#define SMCR_ELX_LEN_MASK		U(0x1ff)
+#define SMCR_ELX_FA64_BIT		(U(1) << 31)
+
+/*******************************************************************************
  * Definitions of MAIR encodings for device and normal memory
  ******************************************************************************/
 /*
@@ -839,7 +1012,7 @@
 #define MPAM3_EL3		S3_6_C10_C5_0
 
 /*******************************************************************************
- * Definitions for system register interface to AMU for ARMv8.4 onwards
+ * Definitions for system register interface to AMU for FEAT_AMUv1
  ******************************************************************************/
 #define AMCR_EL0		S3_3_C13_C2_0
 #define AMCFGR_EL0		S3_3_C13_C2_1
@@ -898,6 +1071,22 @@
 #define AMEVTYPER1E_EL0		S3_3_C13_C15_6
 #define AMEVTYPER1F_EL0		S3_3_C13_C15_7
 
+/* AMCNTENSET0_EL0 definitions */
+#define AMCNTENSET0_EL0_Pn_SHIFT	U(0)
+#define AMCNTENSET0_EL0_Pn_MASK		ULL(0xffff)
+
+/* AMCNTENSET1_EL0 definitions */
+#define AMCNTENSET1_EL0_Pn_SHIFT	U(0)
+#define AMCNTENSET1_EL0_Pn_MASK		ULL(0xffff)
+
+/* AMCNTENCLR0_EL0 definitions */
+#define AMCNTENCLR0_EL0_Pn_SHIFT	U(0)
+#define AMCNTENCLR0_EL0_Pn_MASK		ULL(0xffff)
+
+/* AMCNTENCLR1_EL0 definitions */
+#define AMCNTENCLR1_EL0_Pn_SHIFT	U(0)
+#define AMCNTENCLR1_EL0_Pn_MASK		ULL(0xffff)
+
 /* AMCFGR_EL0 definitions */
 #define AMCFGR_EL0_NCG_SHIFT	U(28)
 #define AMCFGR_EL0_NCG_MASK	U(0xf)
@@ -905,6 +1094,8 @@
 #define AMCFGR_EL0_N_MASK	U(0xff)
 
 /* AMCGCR_EL0 definitions */
+#define AMCGCR_EL0_CG0NC_SHIFT	U(0)
+#define AMCGCR_EL0_CG0NC_MASK	U(0xff)
 #define AMCGCR_EL0_CG1NC_SHIFT	U(8)
 #define AMCGCR_EL0_CG1NC_MASK	U(0xff)
 
@@ -918,6 +1109,57 @@
 #define MPAMIDR_HAS_HCR_BIT		(ULL(1) << 17)
 
 /*******************************************************************************
+ * Definitions for system register interface to AMU for FEAT_AMUv1p1
+ ******************************************************************************/
+
+/* Definition for register defining which virtual offsets are implemented. */
+#define AMCG1IDR_EL0		S3_3_C13_C2_6
+#define AMCG1IDR_CTR_MASK	ULL(0xffff)
+#define AMCG1IDR_CTR_SHIFT	U(0)
+#define AMCG1IDR_VOFF_MASK	ULL(0xffff)
+#define AMCG1IDR_VOFF_SHIFT	U(16)
+
+/* New bit added to AMCR_EL0 */
+#define AMCR_CG1RZ_SHIFT	U(17)
+#define AMCR_CG1RZ_BIT		(ULL(0x1) << AMCR_CG1RZ_SHIFT)
+
+/*
+ * Definitions for virtual offset registers for architected activity monitor
+ * event counters.
+ * AMEVCNTVOFF01_EL2 intentionally left undefined, as it does not exist.
+ */
+#define AMEVCNTVOFF00_EL2	S3_4_C13_C8_0
+#define AMEVCNTVOFF02_EL2	S3_4_C13_C8_2
+#define AMEVCNTVOFF03_EL2	S3_4_C13_C8_3
+
+/*
+ * Definitions for virtual offset registers for auxiliary activity monitor event
+ * counters.
+ */
+#define AMEVCNTVOFF10_EL2	S3_4_C13_C10_0
+#define AMEVCNTVOFF11_EL2	S3_4_C13_C10_1
+#define AMEVCNTVOFF12_EL2	S3_4_C13_C10_2
+#define AMEVCNTVOFF13_EL2	S3_4_C13_C10_3
+#define AMEVCNTVOFF14_EL2	S3_4_C13_C10_4
+#define AMEVCNTVOFF15_EL2	S3_4_C13_C10_5
+#define AMEVCNTVOFF16_EL2	S3_4_C13_C10_6
+#define AMEVCNTVOFF17_EL2	S3_4_C13_C10_7
+#define AMEVCNTVOFF18_EL2	S3_4_C13_C11_0
+#define AMEVCNTVOFF19_EL2	S3_4_C13_C11_1
+#define AMEVCNTVOFF1A_EL2	S3_4_C13_C11_2
+#define AMEVCNTVOFF1B_EL2	S3_4_C13_C11_3
+#define AMEVCNTVOFF1C_EL2	S3_4_C13_C11_4
+#define AMEVCNTVOFF1D_EL2	S3_4_C13_C11_5
+#define AMEVCNTVOFF1E_EL2	S3_4_C13_C11_6
+#define AMEVCNTVOFF1F_EL2	S3_4_C13_C11_7
+
+/*******************************************************************************
+ * Realm management extension register definitions
+ ******************************************************************************/
+#define GPCCR_EL3			S3_6_C2_C1_6
+#define GPTBR_EL3			S3_6_C2_C1_4
+
+/*******************************************************************************
  * RAS system registers
  ******************************************************************************/
 #define DISR_EL1		S3_0_C12_C1_1
@@ -980,6 +1222,16 @@
 #define GCR_EL1			S3_0_C1_C0_6
 
 /*******************************************************************************
+ * FEAT_HCX - Extended Hypervisor Configuration Register
+ ******************************************************************************/
+#define HCRX_EL2		S3_4_C1_C2_2
+#define HCRX_EL2_FGTnXS_BIT	(UL(1) << 4)
+#define HCRX_EL2_FnXS_BIT	(UL(1) << 3)
+#define HCRX_EL2_EnASR_BIT	(UL(1) << 2)
+#define HCRX_EL2_EnALS_BIT	(UL(1) << 1)
+#define HCRX_EL2_EnAS0_BIT	(UL(1) << 0)
+
+/*******************************************************************************
  * Definitions for DynamicIQ Shared Unit registers
  ******************************************************************************/
 #define CLUSTERPWRDN_EL1	S3_0_c15_c3_6
@@ -989,4 +1241,16 @@
 #define DSU_CLUSTER_PWR_ON	1
 #define DSU_CLUSTER_PWR_MASK	U(1)
 
+/*******************************************************************************
+ * Definitions for CPU Power/Performance Management registers
+ ******************************************************************************/
+
+#define CPUPPMCR_EL3			S3_6_C15_C2_0
+#define CPUPPMCR_EL3_MPMMPINCTL_SHIFT	UINT64_C(0)
+#define CPUPPMCR_EL3_MPMMPINCTL_MASK	UINT64_C(0x1)
+
+#define CPUMPMMCR_EL3			S3_6_C15_C2_1
+#define CPUMPMMCR_EL3_MPMM_EN_SHIFT	UINT64_C(0)
+#define CPUMPMMCR_EL3_MPMM_EN_MASK	UINT64_C(0x1)
+
 #endif /* ARCH_H */
diff --git a/include/arch/aarch64/arch_features.h b/include/arch/aarch64/arch_features.h
index 6b5d326..46cd1c9 100644
--- a/include/arch/aarch64/arch_features.h
+++ b/include/arch/aarch64/arch_features.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -17,6 +17,18 @@
 	return true;
 }
 
+static inline bool is_armv8_1_pan_present(void)
+{
+	return ((read_id_aa64mmfr1_el1() >> ID_AA64MMFR1_EL1_PAN_SHIFT) &
+		ID_AA64MMFR1_EL1_PAN_MASK) != 0U;
+}
+
+static inline bool is_armv8_1_vhe_present(void)
+{
+	return ((read_id_aa64mmfr1_el1() >> ID_AA64MMFR1_EL1_VHE_SHIFT) &
+		ID_AA64MMFR1_EL1_VHE_MASK) != 0U;
+}
+
 static inline bool is_armv8_2_ttcnp_present(void)
 {
 	return ((read_id_aa64mmfr2_el1() >> ID_AA64MMFR2_EL1_CNP_SHIFT) &
@@ -76,6 +88,18 @@
 		ID_AA64MMFR0_EL1_ECV_MASK);
 }
 
+static inline bool is_armv8_5_rng_present(void)
+{
+	return ((read_id_aa64isar0_el1() >> ID_AA64ISAR0_RNDR_SHIFT) &
+		ID_AA64ISAR0_RNDR_MASK);
+}
+
+static inline bool is_armv8_6_feat_amuv1p1_present(void)
+{
+	return (((read_id_aa64pfr0_el1() >> ID_AA64PFR0_AMU_SHIFT) &
+		ID_AA64PFR0_AMU_MASK) >= ID_AA64PFR0_AMU_V1P1);
+}
+
 /*
  * Return MPAM version:
  *
@@ -93,4 +117,21 @@
 		ID_AA64PFR1_MPAM_FRAC_SHIFT) & ID_AA64PFR1_MPAM_FRAC_MASK));
 }
 
+static inline bool is_feat_hcx_present(void)
+{
+	return (((read_id_aa64mmfr1_el1() >> ID_AA64MMFR1_EL1_HCX_SHIFT) &
+		ID_AA64MMFR1_EL1_HCX_MASK) == ID_AA64MMFR1_EL1_HCX_SUPPORTED);
+}
+
+static inline unsigned int get_armv9_2_feat_rme_support(void)
+{
+	/*
+	 * Return the RME version, zero if not supported.  This function can be
+	 * used as both an integer value for the RME version or compared to zero
+	 * to detect RME presence.
+	 */
+	return (unsigned int)(read_id_aa64pfr0_el1() >>
+		ID_AA64PFR0_FEAT_RME_SHIFT) & ID_AA64PFR0_FEAT_RME_MASK;
+}
+
 #endif /* ARCH_FEATURES_H */
diff --git a/include/arch/aarch64/arch_helpers.h b/include/arch/aarch64/arch_helpers.h
index 5d1bc94..733bb23 100644
--- a/include/arch/aarch64/arch_helpers.h
+++ b/include/arch/aarch64/arch_helpers.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -233,8 +233,10 @@
 
 void disable_mmu_el1(void);
 void disable_mmu_el3(void);
+void disable_mpu_el2(void);
 void disable_mmu_icache_el1(void);
 void disable_mmu_icache_el3(void);
+void disable_mpu_icache_el2(void);
 
 /*******************************************************************************
  * Misc. accessor prototypes
@@ -245,6 +247,7 @@
 
 DEFINE_SYSREG_RW_FUNCS(par_el1)
 DEFINE_SYSREG_READ_FUNC(id_pfr1_el1)
+DEFINE_SYSREG_READ_FUNC(id_aa64isar0_el1)
 DEFINE_SYSREG_READ_FUNC(id_aa64isar1_el1)
 DEFINE_SYSREG_READ_FUNC(id_aa64pfr0_el1)
 DEFINE_SYSREG_READ_FUNC(id_aa64pfr1_el1)
@@ -259,6 +262,9 @@
 DEFINE_SYSREG_RW_FUNCS(elr_el1)
 DEFINE_SYSREG_RW_FUNCS(elr_el2)
 DEFINE_SYSREG_RW_FUNCS(elr_el3)
+DEFINE_SYSREG_RW_FUNCS(mdccsr_el0)
+DEFINE_SYSREG_RW_FUNCS(dbgdtrrx_el0)
+DEFINE_SYSREG_RW_FUNCS(dbgdtrtx_el0)
 
 DEFINE_SYSOP_FUNC(wfi)
 DEFINE_SYSOP_FUNC(wfe)
@@ -436,6 +442,8 @@
 DEFINE_SYSREG_READ_FUNC(cntpct_el0)
 DEFINE_SYSREG_RW_FUNCS(cnthctl_el2)
 
+DEFINE_SYSREG_RW_FUNCS(vtcr_el2)
+
 #define get_cntp_ctl_enable(x)  (((x) >> CNTP_CTL_ENABLE_SHIFT) & \
 					CNTP_CTL_ENABLE_MASK)
 #define get_cntp_ctl_imask(x)   (((x) >> CNTP_CTL_IMASK_SHIFT) & \
@@ -484,6 +492,8 @@
 
 DEFINE_RENAME_SYSREG_READ_FUNC(amcfgr_el0, AMCFGR_EL0)
 DEFINE_RENAME_SYSREG_READ_FUNC(amcgcr_el0, AMCGCR_EL0)
+DEFINE_RENAME_SYSREG_READ_FUNC(amcg1idr_el0, AMCG1IDR_EL0)
+DEFINE_RENAME_SYSREG_RW_FUNCS(amcr_el0, AMCR_EL0)
 DEFINE_RENAME_SYSREG_RW_FUNCS(amcntenclr0_el0, AMCNTENCLR0_EL0)
 DEFINE_RENAME_SYSREG_RW_FUNCS(amcntenset0_el0, AMCNTENSET0_EL0)
 DEFINE_RENAME_SYSREG_RW_FUNCS(amcntenclr1_el0, AMCNTENCLR1_EL0)
@@ -499,6 +509,9 @@
 DEFINE_RENAME_SYSREG_WRITE_FUNC(zcr_el3, ZCR_EL3)
 DEFINE_RENAME_SYSREG_WRITE_FUNC(zcr_el2, ZCR_EL2)
 
+DEFINE_RENAME_SYSREG_READ_FUNC(id_aa64smfr0_el1, ID_AA64SMFR0_EL1)
+DEFINE_RENAME_SYSREG_RW_FUNCS(smcr_el3, SMCR_EL3)
+
 DEFINE_RENAME_SYSREG_READ_FUNC(erridr_el1, ERRIDR_EL1)
 DEFINE_RENAME_SYSREG_WRITE_FUNC(errselr_el1, ERRSELR_EL1)
 
@@ -522,9 +535,24 @@
 DEFINE_RENAME_SYSREG_RW_FUNCS(rgsr_el1, RGSR_EL1)
 DEFINE_RENAME_SYSREG_RW_FUNCS(gcr_el1, GCR_EL1)
 
+/* Armv8.5 FEAT_RNG Registers */
+DEFINE_SYSREG_READ_FUNC(rndr)
+DEFINE_SYSREG_READ_FUNC(rndrrs)
+
+/* FEAT_HCX Register */
+DEFINE_RENAME_SYSREG_RW_FUNCS(hcrx_el2, HCRX_EL2)
+
 /* DynamIQ Shared Unit power management */
 DEFINE_RENAME_SYSREG_RW_FUNCS(clusterpwrdn_el1, CLUSTERPWRDN_EL1)
 
+/* CPU Power/Performance Management registers */
+DEFINE_RENAME_SYSREG_RW_FUNCS(cpuppmcr_el3, CPUPPMCR_EL3)
+DEFINE_RENAME_SYSREG_RW_FUNCS(cpumpmmcr_el3, CPUMPMMCR_EL3)
+
+/* Armv9.2 RME Registers */
+DEFINE_RENAME_SYSREG_RW_FUNCS(gptbr_el3, GPTBR_EL3)
+DEFINE_RENAME_SYSREG_RW_FUNCS(gpccr_el3, GPCCR_EL3)
+
 #define IS_IN_EL(x) \
 	(GET_EL(read_CurrentEl()) == MODE_EL##x)
 
@@ -568,7 +596,28 @@
 	}
 }
 
-/* Previously defined accesor functions with incomplete register names  */
+/*
+ * TLBIPAALLOS instruction
+ * (TLB Inivalidate GPT Information by PA,
+ * All Entries, Outer Shareable)
+ */
+static inline void tlbipaallos(void)
+{
+	__asm__("SYS #6,c8,c1,#4");
+}
+
+/*
+ * Invalidate cached copies of GPT entries
+ * from TLBs by physical address
+ *
+ * @pa: the starting address for the range
+ *      of invalidation
+ * @size: size of the range of invalidation
+ */
+void gpt_tlbi_by_pa(uint64_t pa, size_t size);
+
+
+/* Previously defined accessor functions with incomplete register names  */
 
 #define read_current_el()	read_CurrentEl()
 
diff --git a/include/arch/aarch64/asm_macros.S b/include/arch/aarch64/asm_macros.S
index cbb9f0b..7706cd8 100644
--- a/include/arch/aarch64/asm_macros.S
+++ b/include/arch/aarch64/asm_macros.S
@@ -10,10 +10,6 @@
 #include <common/asm_macros_common.S>
 #include <lib/spinlock.h>
 
-#if ENABLE_BTI && !ARM_ARCH_AT_LEAST(8, 5)
-#error Branch Target Identification requires ARM_ARCH_MINOR >= 5
-#endif
-
 /*
  * TLBI instruction with type specifier that implements the workaround for
  * errata 813419 of Cortex-A57 or errata 1286807 of Cortex-A76.
@@ -219,12 +215,12 @@
 	.endm
 
 	/*
-	 * Macro for mitigating against speculative execution beyond ERET.
-	 * If possible use Speculation Barrier instruction defined in ARMv8.5
+	 * Macro for mitigating against speculative execution beyond ERET. Uses the
+	 * speculation barrier instruction introduced by FEAT_SB, if it's enabled.
 	 */
 	.macro exception_return
 	eret
-#if ARM_ARCH_AT_LEAST(8, 5)
+#if ENABLE_FEAT_SB
 	sb
 #else
 	dsb	nsh
diff --git a/include/arch/aarch64/el2_common_macros.S b/include/arch/aarch64/el2_common_macros.S
new file mode 100644
index 0000000..7bf4806
--- /dev/null
+++ b/include/arch/aarch64/el2_common_macros.S
@@ -0,0 +1,422 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EL2_COMMON_MACROS_S
+#define EL2_COMMON_MACROS_S
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <context.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+
+#include <platform_def.h>
+
+	/*
+	 * Helper macro to initialise system registers at EL2.
+	 */
+	.macro el2_arch_init_common
+
+	/* ---------------------------------------------------------------------
+	 * SCTLR_EL2 has already been initialised - read current value before
+	 * modifying.
+	 *
+	 * SCTLR_EL2.I: Enable the instruction cache.
+	 *
+	 * SCTLR_EL2.SA: Enable Stack Alignment check. A SP alignment fault
+	 *  exception is generated if a load or store instruction executed at
+	 *  EL2 uses the SP as the base address and the SP is not aligned to a
+	 *  16-byte boundary.
+	 *
+	 * SCTLR_EL2.A: Enable Alignment fault checking. All instructions that
+	 *  load or store one or more registers have an alignment check that the
+	 *  address being accessed is aligned to the size of the data element(s)
+	 *  being accessed.
+	 * ---------------------------------------------------------------------
+	 */
+	mov	x1, #(SCTLR_I_BIT | SCTLR_A_BIT | SCTLR_SA_BIT)
+	mrs	x0, sctlr_el2
+	orr	x0, x0, x1
+	msr	sctlr_el2, x0
+	isb
+
+	/* ---------------------------------------------------------------------
+	 * Initialise HCR_EL2, setting all fields rather than relying on HW.
+	 * All fields are architecturally UNKNOWN on reset. The following fields
+	 * do not change during the TF lifetime. The remaining fields are set to
+	 * zero here but are updated ahead of transitioning to a lower EL in the
+	 * function cm_init_context_common().
+	 *
+	 * HCR_EL2.TWE: Set to zero so that execution of WFE instructions at
+	 *  EL2, EL1 and EL0 are not trapped to EL2.
+	 *
+	 * HCR_EL2.TWI: Set to zero so that execution of WFI instructions at
+	 *  EL2, EL1 and EL0 are not trapped to EL2.
+	 *
+	 * HCR_EL2.HCD: Set to zero to enable HVC calls at EL1 and above,
+	 *  from both Security states and both Execution states.
+	 *
+	 * HCR_EL2.TEA: Set to one to route External Aborts and SError
+	 * Interrupts to EL2 when executing at any EL.
+	 *
+	 * HCR_EL2.{API,APK}: For Armv8.3 pointer authentication feature,
+	 * disable traps to EL2 when accessing key registers or using
+	 * pointer authentication instructions from lower ELs.
+	 * ---------------------------------------------------------------------
+	 */
+	mov_imm	x0, ((HCR_RESET_VAL | HCR_TEA_BIT) \
+			& ~(HCR_TWE_BIT | HCR_TWI_BIT | HCR_HCD_BIT))
+#if CTX_INCLUDE_PAUTH_REGS
+	/*
+	 * If the pointer authentication registers are saved during world
+	 * switches, enable pointer authentication everywhere, as it is safe to
+	 * do so.
+	 */
+	orr	x0, x0, #(HCR_API_BIT | HCR_APK_BIT)
+#endif  /* CTX_INCLUDE_PAUTH_REGS */
+	msr	hcr_el2, x0
+
+	/* ---------------------------------------------------------------------
+	 * Initialise MDCR_EL2, setting all fields rather than relying on
+	 * hw. Some fields are architecturally UNKNOWN on reset.
+	 *
+	 * MDCR_EL2.TDOSA: Set to zero so that EL2 and EL2 System register
+	 *  access to the powerdown debug registers do not trap to EL2.
+	 *
+	 * MDCR_EL2.TDA: Set to zero to allow EL0, EL1 and EL2 access to the
+	 *  debug registers, other than those registers that are controlled by
+	 *  MDCR_EL2.TDOSA.
+	 *
+	 * MDCR_EL2.TPM: Set to zero so that EL0, EL1, and EL2 System
+	 *  register accesses to all Performance Monitors registers do not trap
+	 *  to EL2.
+	 *
+	 * MDCR_EL2.HPMD: Set to zero so that event counting by the program-
+	 *  mable counters PMEVCNTR<n>_EL0 is prohibited in Secure state. If
+	 *  ARMv8.2 Debug is not implemented this bit does not have any effect
+	 *  on the counters unless there is support for the implementation
+	 *  defined authentication interface
+	 *  ExternalSecureNoninvasiveDebugEnabled().
+	 * ---------------------------------------------------------------------
+	 */
+	mov_imm	x0, ((MDCR_EL2_RESET_VAL | \
+		      MDCR_SPD32(MDCR_SPD32_DISABLE)) \
+		      & ~(MDCR_EL2_HPMD | MDCR_TDOSA_BIT | \
+		      MDCR_TDA_BIT | MDCR_TPM_BIT))
+
+	msr	mdcr_el2, x0
+
+	/* ---------------------------------------------------------------------
+	 * Initialise PMCR_EL0 setting all fields rather than relying
+	 * on hw. Some fields are architecturally UNKNOWN on reset.
+	 *
+	 * PMCR_EL0.DP: Set to one so that the cycle counter,
+	 *  PMCCNTR_EL0 does not count when event counting is prohibited.
+	 *
+	 * PMCR_EL0.X: Set to zero to disable export of events.
+	 *
+	 * PMCR_EL0.D: Set to zero so that, when enabled, PMCCNTR_EL0
+	 *  counts on every clock cycle.
+	 * ---------------------------------------------------------------------
+	 */
+	mov_imm	x0, ((PMCR_EL0_RESET_VAL | PMCR_EL0_DP_BIT) & \
+		    ~(PMCR_EL0_X_BIT | PMCR_EL0_D_BIT))
+
+	msr	pmcr_el0, x0
+
+	/* ---------------------------------------------------------------------
+	 * Enable External Aborts and SError Interrupts now that the exception
+	 * vectors have been setup.
+	 * ---------------------------------------------------------------------
+	 */
+	msr	daifclr, #DAIF_ABT_BIT
+
+	/* ---------------------------------------------------------------------
+	 * Initialise CPTR_EL2, setting all fields rather than relying on hw.
+	 * All fields are architecturally UNKNOWN on reset.
+	 *
+	 * CPTR_EL2.TCPAC: Set to zero so that any accesses to CPACR_EL1 do
+	 * not trap to EL2.
+	 *
+	 * CPTR_EL2.TTA: Set to zero so that System register accesses to the
+	 *  trace registers do not trap to EL2.
+	 *
+	 * CPTR_EL2.TFP: Set to zero so that accesses to the V- or Z- registers
+	 *  by Advanced SIMD, floating-point or SVE instructions (if implemented)
+	 *  do not trap to EL2.
+	 */
+
+	mov_imm x0, (CPTR_EL2_RESET_VAL & ~(TCPAC_BIT | TTA_BIT | TFP_BIT))
+	msr	cptr_el2, x0
+
+	/*
+	 * If Data Independent Timing (DIT) functionality is implemented,
+	 * always enable DIT in EL2
+	 */
+	mrs	x0, id_aa64pfr0_el1
+	ubfx	x0, x0, #ID_AA64PFR0_DIT_SHIFT, #ID_AA64PFR0_DIT_LENGTH
+	cmp	x0, #ID_AA64PFR0_DIT_SUPPORTED
+	bne	1f
+	mov	x0, #DIT_BIT
+	msr	DIT, x0
+1:
+	.endm
+
+/* -----------------------------------------------------------------------------
+ * This is the super set of actions that need to be performed during a cold boot
+ * or a warm boot in EL2. This code is shared by BL1 and BL31.
+ *
+ * This macro will always perform reset handling, architectural initialisations
+ * and stack setup. The rest of the actions are optional because they might not
+ * be needed, depending on the context in which this macro is called. This is
+ * why this macro is parameterised ; each parameter allows to enable/disable
+ * some actions.
+ *
+ *  _init_sctlr:
+ *	Whether the macro needs to initialise SCTLR_EL2, including configuring
+ *      the endianness of data accesses.
+ *
+ *  _warm_boot_mailbox:
+ *	Whether the macro needs to detect the type of boot (cold/warm). The
+ *	detection is based on the platform entrypoint address : if it is zero
+ *	then it is a cold boot, otherwise it is a warm boot. In the latter case,
+ *	this macro jumps on the platform entrypoint address.
+ *
+ *  _secondary_cold_boot:
+ *	Whether the macro needs to identify the CPU that is calling it: primary
+ *	CPU or secondary CPU. The primary CPU will be allowed to carry on with
+ *	the platform initialisations, while the secondaries will be put in a
+ *	platform-specific state in the meantime.
+ *
+ *	If the caller knows this macro will only be called by the primary CPU
+ *	then this parameter can be defined to 0 to skip this step.
+ *
+ * _init_memory:
+ *	Whether the macro needs to initialise the memory.
+ *
+ * _init_c_runtime:
+ *	Whether the macro needs to initialise the C runtime environment.
+ *
+ * _exception_vectors:
+ *	Address of the exception vectors to program in the VBAR_EL2 register.
+ *
+ * _pie_fixup_size:
+ *	Size of memory region to fixup Global Descriptor Table (GDT).
+ *
+ *	A non-zero value is expected when firmware needs GDT to be fixed-up.
+ *
+ * -----------------------------------------------------------------------------
+ */
+	.macro el2_entrypoint_common					\
+		_init_sctlr, _warm_boot_mailbox, _secondary_cold_boot,	\
+		_init_memory, _init_c_runtime, _exception_vectors,	\
+		_pie_fixup_size
+
+	.if \_init_sctlr
+		/* -------------------------------------------------------------
+		 * This is the initialisation of SCTLR_EL2 and so must ensure
+		 * that all fields are explicitly set rather than relying on hw.
+		 * Some fields reset to an IMPLEMENTATION DEFINED value and
+		 * others are architecturally UNKNOWN on reset.
+		 *
+		 * SCTLR.EE: Set the CPU endianness before doing anything that
+		 *  might involve memory reads or writes. Set to zero to select
+		 *  Little Endian.
+		 *
+		 * SCTLR_EL2.WXN: For the EL2 translation regime, this field can
+		 *  force all memory regions that are writeable to be treated as
+		 *  XN (Execute-never). Set to zero so that this control has no
+		 *  effect on memory access permissions.
+		 *
+		 * SCTLR_EL2.SA: Set to zero to disable Stack Alignment check.
+		 *
+		 * SCTLR_EL2.A: Set to zero to disable Alignment fault checking.
+		 *
+		 * SCTLR.DSSBS: Set to zero to disable speculation store bypass
+		 *  safe behaviour upon exception entry to EL2.
+		 * -------------------------------------------------------------
+		 */
+		mov_imm	x0, (SCTLR_RESET_VAL & ~(SCTLR_EE_BIT | SCTLR_WXN_BIT \
+				| SCTLR_SA_BIT | SCTLR_A_BIT | SCTLR_DSSBS_BIT))
+		msr	sctlr_el2, x0
+		isb
+	.endif /* _init_sctlr */
+
+#if DISABLE_MTPMU
+		bl	mtpmu_disable
+#endif
+
+	.if \_warm_boot_mailbox
+		/* -------------------------------------------------------------
+		 * This code will be executed for both warm and cold resets.
+		 * Now is the time to distinguish between the two.
+		 * Query the platform entrypoint address and if it is not zero
+		 * then it means it is a warm boot so jump to this address.
+		 * -------------------------------------------------------------
+		 */
+		bl	plat_get_my_entrypoint
+		cbz	x0, do_cold_boot
+		br	x0
+
+	do_cold_boot:
+	.endif /* _warm_boot_mailbox */
+
+	.if \_pie_fixup_size
+#if ENABLE_PIE
+		/*
+		 * ------------------------------------------------------------
+		 * If PIE is enabled fixup the Global descriptor Table only
+		 * once during primary core cold boot path.
+		 *
+		 * Compile time base address, required for fixup, is calculated
+		 * using "pie_fixup" label present within first page.
+		 * ------------------------------------------------------------
+		 */
+	pie_fixup:
+		ldr	x0, =pie_fixup
+		and	x0, x0, #~(PAGE_SIZE_MASK)
+		mov_imm	x1, \_pie_fixup_size
+		add	x1, x1, x0
+		bl	fixup_gdt_reloc
+#endif /* ENABLE_PIE */
+	.endif /* _pie_fixup_size */
+
+	/* ---------------------------------------------------------------------
+	 * Set the exception vectors.
+	 * ---------------------------------------------------------------------
+	 */
+	adr	x0, \_exception_vectors
+	msr	vbar_el2, x0
+	isb
+
+	/* ---------------------------------------------------------------------
+	 * It is a cold boot.
+	 * Perform any processor specific actions upon reset e.g. cache, TLB
+	 * invalidations etc.
+	 * ---------------------------------------------------------------------
+	 */
+	bl	reset_handler
+
+	el2_arch_init_common
+
+	.if \_secondary_cold_boot
+		/* -------------------------------------------------------------
+		 * Check if this is a primary or secondary CPU cold boot.
+		 * The primary CPU will set up the platform while the
+		 * secondaries are placed in a platform-specific state until the
+		 * primary CPU performs the necessary actions to bring them out
+		 * of that state and allows entry into the OS.
+		 * -------------------------------------------------------------
+		 */
+		bl	plat_is_my_cpu_primary
+		cbnz	w0, do_primary_cold_boot
+
+		/* This is a cold boot on a secondary CPU */
+		bl	plat_secondary_cold_boot_setup
+		/* plat_secondary_cold_boot_setup() is not supposed to return */
+		bl	el2_panic
+	do_primary_cold_boot:
+	.endif /* _secondary_cold_boot */
+
+	/* ---------------------------------------------------------------------
+	 * Initialize memory now. Secondary CPU initialization won't get to this
+	 * point.
+	 * ---------------------------------------------------------------------
+	 */
+
+	.if \_init_memory
+		bl	platform_mem_init
+	.endif /* _init_memory */
+
+	/* ---------------------------------------------------------------------
+	 * Init C runtime environment:
+	 *   - Zero-initialise the NOBITS sections. There are 2 of them:
+	 *       - the .bss section;
+	 *       - the coherent memory section (if any).
+	 *   - Relocate the data section from ROM to RAM, if required.
+	 * ---------------------------------------------------------------------
+	 */
+	.if \_init_c_runtime
+		adrp	x0, __BSS_START__
+		add	x0, x0, :lo12:__BSS_START__
+
+		adrp	x1, __BSS_END__
+		add	x1, x1, :lo12:__BSS_END__
+		sub	x1, x1, x0
+		bl	zeromem
+
+#if defined(IMAGE_BL1) || (defined(IMAGE_BL2) && BL2_AT_EL3 && BL2_IN_XIP_MEM)
+		adrp	x0, __DATA_RAM_START__
+		add	x0, x0, :lo12:__DATA_RAM_START__
+		adrp	x1, __DATA_ROM_START__
+		add	x1, x1, :lo12:__DATA_ROM_START__
+		adrp	x2, __DATA_RAM_END__
+		add	x2, x2, :lo12:__DATA_RAM_END__
+		sub	x2, x2, x0
+		bl	memcpy16
+#endif
+	.endif /* _init_c_runtime */
+
+	/* ---------------------------------------------------------------------
+	 * Use SP_EL0 for the C runtime stack.
+	 * ---------------------------------------------------------------------
+	 */
+	msr	spsel, #0
+
+	/* ---------------------------------------------------------------------
+	 * Allocate a stack whose memory will be marked as Normal-IS-WBWA when
+	 * the MMU is enabled. There is no risk of reading stale stack memory
+	 * after enabling the MMU as only the primary CPU is running at the
+	 * moment.
+	 * ---------------------------------------------------------------------
+	 */
+	bl	plat_set_my_stack
+
+#if STACK_PROTECTOR_ENABLED
+	.if \_init_c_runtime
+	bl	update_stack_protector_canary
+	.endif /* _init_c_runtime */
+#endif
+	.endm
+
+	.macro	apply_at_speculative_wa
+#if ERRATA_SPECULATIVE_AT
+	/*
+	 * Explicitly save x30 so as to free up a register and to enable
+	 * branching and also, save x29 which will be used in the called
+	 * function
+	 */
+	stp	x29, x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X29]
+	bl	save_and_update_ptw_el1_sys_regs
+	ldp	x29, x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X29]
+#endif
+	.endm
+
+	.macro	restore_ptw_el1_sys_regs
+#if ERRATA_SPECULATIVE_AT
+	/* -----------------------------------------------------------
+	 * In case of ERRATA_SPECULATIVE_AT, must follow below order
+	 * to ensure that page table walk is not enabled until
+	 * restoration of all EL1 system registers. TCR_EL1 register
+	 * should be updated at the end which restores previous page
+	 * table walk setting of stage1 i.e.(TCR_EL1.EPDx) bits. ISB
+	 * ensures that CPU does below steps in order.
+	 *
+	 * 1. Ensure all other system registers are written before
+	 *    updating SCTLR_EL1 using ISB.
+	 * 2. Restore SCTLR_EL1 register.
+	 * 3. Ensure SCTLR_EL1 written successfully using ISB.
+	 * 4. Restore TCR_EL1 register.
+	 * -----------------------------------------------------------
+	 */
+	isb
+	ldp	x28, x29, [sp, #CTX_EL1_SYSREGS_OFFSET + CTX_SCTLR_EL1]
+	msr	sctlr_el1, x28
+	isb
+	msr	tcr_el1, x29
+#endif
+	.endm
+
+#endif /* EL2_COMMON_MACROS_S */
diff --git a/include/arch/aarch64/el3_common_macros.S b/include/arch/aarch64/el3_common_macros.S
index 6f4143c..f29def7 100644
--- a/include/arch/aarch64/el3_common_macros.S
+++ b/include/arch/aarch64/el3_common_macros.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -88,6 +88,13 @@
 	 */
 	orr	x0, x0, #(SCR_API_BIT | SCR_APK_BIT)
 #endif
+#if ENABLE_RME
+	/*
+	 * TODO: Settting the EEL2 bit to allow EL3 access to secure only registers
+	 * in context management. This will need to be refactored.
+	 */
+	orr	x0, x0, #SCR_EEL2_BIT
+#endif
 	msr	scr_el3, x0
 
 	/* ---------------------------------------------------------------------
@@ -113,21 +120,44 @@
 	 *
 	 * MDCR_EL3.SCCD: Set to one so that cycle counting by PMCCNTR_EL0 is
 	 *  prohibited in Secure state. This bit is RES0 in versions of the
-	 *  architecture earlier than ARMv8.5, setting it to 1 doesn't have any
-	 *  effect on them.
+	 *  architecture with FEAT_PMUv3p5 not implemented, setting it to 1
+	 *  doesn't have any effect on them.
+	 *
+	 * MDCR_EL3.MCCD: Set to one so that cycle counting by PMCCNTR_EL0 is
+	 *  prohibited in EL3. This bit is RES0 in versions of the
+	 *  architecture with FEAT_PMUv3p7 not implemented, setting it to 1
+	 *  doesn't have any effect on them.
 	 *
 	 * MDCR_EL3.SPME: Set to zero so that event counting by the programmable
 	 *  counters PMEVCNTR<n>_EL0 is prohibited in Secure state. If ARMv8.2
 	 *  Debug is not implemented this bit does not have any effect on the
 	 *  counters unless there is support for the implementation defined
 	 *  authentication interface ExternalSecureNoninvasiveDebugEnabled().
+	 *
+	 * MDCR_EL3.NSTB, MDCR_EL3.NSTBE: Set to zero so that Trace Buffer
+	 *  owning security state is Secure state. If FEAT_TRBE is implemented,
+	 *  accesses to Trace Buffer control registers at EL2 and EL1 in any
+	 *  security state generates trap exceptions to EL3.
+	 *  If FEAT_TRBE is not implemented, these bits are RES0.
+	 *
+	 * MDCR_EL3.TTRF: Set to one so that access to trace filter control
+	 *  registers in non-monitor mode generate EL3 trap exception,
+	 *  unless the access generates a higher priority exception when trace
+	 *  filter control(FEAT_TRF) is implemented.
+	 *  When FEAT_TRF is not implemented, this bit is RES0.
 	 * ---------------------------------------------------------------------
 	 */
 	mov_imm	x0, ((MDCR_EL3_RESET_VAL | MDCR_SDD_BIT | \
-		      MDCR_SPD32(MDCR_SPD32_DISABLE) | MDCR_SCCD_BIT) & \
-		    ~(MDCR_SPME_BIT | MDCR_TDOSA_BIT | MDCR_TDA_BIT | \
-		      MDCR_TPM_BIT))
+		      MDCR_SPD32(MDCR_SPD32_DISABLE) | MDCR_SCCD_BIT | \
+		      MDCR_MCCD_BIT) & ~(MDCR_SPME_BIT | MDCR_TDOSA_BIT | \
+		      MDCR_TDA_BIT | MDCR_TPM_BIT | MDCR_NSTB(MDCR_NSTB_EL1) | \
+		      MDCR_NSTBE | MDCR_TTRF_BIT))
 
+	mrs	x1, id_aa64dfr0_el1
+	ubfx	x1, x1, #ID_AA64DFR0_TRACEFILT_SHIFT, #ID_AA64DFR0_TRACEFILT_LENGTH
+	cbz	x1, 1f
+	orr	x0, x0, #MDCR_TTRF_BIT
+1:
 	msr	mdcr_el3, x0
 
 	/* ---------------------------------------------------------------------
@@ -174,14 +204,35 @@
 	 * CPTR_EL3.TCPAC: Set to zero so that any accesses to CPACR_EL1,
 	 *  CPTR_EL2, CPACR, or HCPTR do not trap to EL3.
 	 *
+	 * CPTR_EL3.TTA: Set to one so that accesses to the trace system
+	 *  registers trap to EL3 from all exception levels and security
+	 *  states when system register trace is implemented.
+	 *  When system register trace is not implemented, this bit is RES0 and
+	 *  hence set to zero.
+	 *
 	 * CPTR_EL3.TTA: Set to zero so that System register accesses to the
 	 *  trace registers do not trap to EL3.
 	 *
 	 * CPTR_EL3.TFP: Set to zero so that accesses to the V- or Z- registers
 	 *  by Advanced SIMD, floating-point or SVE instructions (if implemented)
 	 *  do not trap to EL3.
+	 *
+	 * CPTR_EL3.TAM: Set to one so that Activity Monitor access is
+	 *  trapped to EL3 by default.
+	 *
+	 * CPTR_EL3.EZ: Set to zero so that all SVE functionality is trapped
+	 *  to EL3 by default.
+	 *
+	 * CPTR_EL3.ESM: Set to zero so that all SME functionality is trapped
+	 *  to EL3 by default.
 	 */
+
 	mov_imm x0, (CPTR_EL3_RESET_VAL & ~(TCPAC_BIT | TTA_BIT | TFP_BIT))
+	mrs	x1, id_aa64dfr0_el1
+	ubfx	x1, x1, #ID_AA64DFR0_TRACEVER_SHIFT, #ID_AA64DFR0_TRACEVER_LENGTH
+	cbz	x1, 1f
+	orr	x0, x0, #TTA_BIT
+1:
 	msr	cptr_el3, x0
 
 	/*
@@ -277,6 +328,10 @@
 		isb
 	.endif /* _init_sctlr */
 
+#if DISABLE_MTPMU
+		bl	mtpmu_disable
+#endif
+
 	.if \_warm_boot_mailbox
 		/* -------------------------------------------------------------
 		 * This code will be executed for both warm and cold resets.
@@ -320,6 +375,7 @@
 	msr	vbar_el3, x0
 	isb
 
+#if !(defined(IMAGE_BL2) && ENABLE_RME)
 	/* ---------------------------------------------------------------------
 	 * It is a cold boot.
 	 * Perform any processor specific actions upon reset e.g. cache, TLB
@@ -327,6 +383,7 @@
 	 * ---------------------------------------------------------------------
 	 */
 	bl	reset_handler
+#endif
 
 	el3_arch_init_common
 
@@ -369,17 +426,31 @@
 	 * ---------------------------------------------------------------------
 	 */
 	.if \_init_c_runtime
-#if defined(IMAGE_BL31) || (defined(IMAGE_BL2) && BL2_AT_EL3 && BL2_INV_DCACHE)
+#if defined(IMAGE_BL31) || (defined(IMAGE_BL2) && \
+	((BL2_AT_EL3 && BL2_INV_DCACHE) || ENABLE_RME))
 		/* -------------------------------------------------------------
 		 * Invalidate the RW memory used by the BL31 image. This
 		 * includes the data and NOBITS sections. This is done to
 		 * safeguard against possible corruption of this memory by
 		 * dirty cache lines in a system cache as a result of use by
-		 * an earlier boot loader stage.
+		 * an earlier boot loader stage. If PIE is enabled however,
+		 * RO sections including the GOT may be modified during
+                 * pie fixup. Therefore, to be on the safe side, invalidate
+		 * the entire image region if PIE is enabled.
 		 * -------------------------------------------------------------
 		 */
+#if ENABLE_PIE
+#if SEPARATE_CODE_AND_RODATA
+		adrp	x0, __TEXT_START__
+		add	x0, x0, :lo12:__TEXT_START__
+#else
+		adrp	x0, __RO_START__
+		add	x0, x0, :lo12:__RO_START__
+#endif /* SEPARATE_CODE_AND_RODATA */
+#else
 		adrp	x0, __RW_START__
 		add	x0, x0, :lo12:__RW_START__
+#endif /* ENABLE_PIE */
 		adrp	x1, __RW_END__
 		add	x1, x1, :lo12:__RW_END__
 		sub	x1, x1, x0
diff --git a/include/bl31/bl31.h b/include/bl31/bl31.h
index 3deb0a5..1d58ef9 100644
--- a/include/bl31/bl31.h
+++ b/include/bl31/bl31.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -19,6 +19,7 @@
 uint32_t bl31_get_next_image_type(void);
 void bl31_prepare_next_image_entry(void);
 void bl31_register_bl32_init(int32_t (*func)(void));
+void bl31_register_rmm_init(int32_t (*func)(void));
 void bl31_warm_entrypoint(void);
 void bl31_main(void);
 void bl31_lib_init(void);
diff --git a/include/common/bl_common.h b/include/common/bl_common.h
index 77fb1f6..8cb4990 100644
--- a/include/common/bl_common.h
+++ b/include/common/bl_common.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -106,6 +106,10 @@
 IMPORT_SYM(uintptr_t, __RO_START__,		BL_CODE_BASE);
 IMPORT_SYM(uintptr_t, __RO_END__,		BL_CODE_END);
 #endif
+#if SEPARATE_NOBITS_REGION
+IMPORT_SYM(uintptr_t, __NOBITS_START__,		BL_NOBITS_BASE);
+IMPORT_SYM(uintptr_t, __NOBITS_END__,		BL_NOBITS_END);
+#endif
 IMPORT_SYM(uintptr_t, __RW_END__,		BL_END);
 
 #if defined(IMAGE_BL1)
@@ -122,6 +126,8 @@
 IMPORT_SYM(uintptr_t, __BL31_END__,		BL31_END);
 #elif defined(IMAGE_BL32)
 IMPORT_SYM(uintptr_t, __BL32_END__,		BL32_END);
+#elif defined(IMAGE_RMM)
+IMPORT_SYM(uintptr_t, __RMM_END__,		RMM_END);
 #endif /* IMAGE_BLX */
 
 /* The following symbols are only exported from the BL2 at EL3 linker script. */
diff --git a/include/common/bl_common.ld.h b/include/common/bl_common.ld.h
index ab3391a..5147e37 100644
--- a/include/common/bl_common.ld.h
+++ b/include/common/bl_common.ld.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -105,10 +105,18 @@
  * .rela.dyn needs to come after .data for the read-elf utility to parse
  * this section correctly.
  */
+#if __aarch64__
+#define RELA_DYN_NAME		.rela.dyn
+#define RELOC_SECTIONS_PATTERN	*(.rela*)
+#else
+#define RELA_DYN_NAME		.rel.dyn
+#define RELOC_SECTIONS_PATTERN	*(.rel*)
+#endif
+
 #define RELA_SECTION					\
-	.rela.dyn : ALIGN(STRUCT_ALIGN) {		\
+	RELA_DYN_NAME : ALIGN(STRUCT_ALIGN) {		\
 		__RELA_START__ = .;			\
-		*(.rela*)				\
+		RELOC_SECTIONS_PATTERN			\
 		__RELA_END__ = .;			\
 	}
 
diff --git a/include/common/debug.h b/include/common/debug.h
index ed0e8bf..a7ca0d7 100644
--- a/include/common/debug.h
+++ b/include/common/debug.h
@@ -61,8 +61,10 @@
 
 #if LOG_LEVEL >= LOG_LEVEL_ERROR
 # define ERROR(...)	tf_log(LOG_MARKER_ERROR __VA_ARGS__)
+# define ERROR_NL()	tf_log_newline(LOG_MARKER_ERROR)
 #else
 # define ERROR(...)	no_tf_log(LOG_MARKER_ERROR __VA_ARGS__)
+# define ERROR_NL()
 #endif
 
 #if LOG_LEVEL >= LOG_LEVEL_NOTICE
@@ -109,6 +111,7 @@
 void __dead2 __stack_chk_fail(void);
 
 void tf_log(const char *fmt, ...) __printflike(1, 2);
+void tf_log_newline(const char log_fmt[2]);
 void tf_log_set_max_level(unsigned int log_level);
 
 #endif /* __ASSEMBLER__ */
diff --git a/include/common/ep_info.h b/include/common/ep_info.h
index 4bfa1fa..771572c 100644
--- a/include/common/ep_info.h
+++ b/include/common/ep_info.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -18,14 +18,21 @@
 
 #define SECURE		EP_SECURE
 #define NON_SECURE	EP_NON_SECURE
+#define REALM		EP_REALM
+#if ENABLE_RME
+#define sec_state_is_valid(s)	(((s) == SECURE) ||	\
+				((s) == NON_SECURE) ||	\
+				((s) == REALM))
+#else
 #define sec_state_is_valid(s) (((s) == SECURE) || ((s) == NON_SECURE))
+#endif
 
 #define PARAM_EP_SECURITY_MASK	EP_SECURITY_MASK
 
 #define NON_EXECUTABLE	EP_NON_EXECUTABLE
 #define EXECUTABLE	EP_EXECUTABLE
 
-/* Secure or Non-secure image */
+/* Get/set security state of an image */
 #define GET_SECURITY_STATE(x) ((x) & EP_SECURITY_MASK)
 #define SET_SECURITY_STATE(x, security) \
 			((x) = ((x) & ~EP_SECURITY_MASK) | (security))
diff --git a/include/common/fdt_fixup.h b/include/common/fdt_fixup.h
index 2e9d49d..7a590b2 100644
--- a/include/common/fdt_fixup.h
+++ b/include/common/fdt_fixup.h
@@ -7,13 +7,15 @@
 #ifndef FDT_FIXUP_H
 #define FDT_FIXUP_H
 
+#define INVALID_BASE_ADDR	((uintptr_t)~0UL)
+
 int dt_add_psci_node(void *fdt);
 int dt_add_psci_cpu_enable_methods(void *fdt);
 int fdt_add_reserved_memory(void *dtb, const char *node_name,
 			    uintptr_t base, size_t size);
 int fdt_add_cpus_node(void *dtb, unsigned int afflv0,
 		      unsigned int afflv1, unsigned int afflv2);
-int fdt_adjust_gic_redist(void *dtb, unsigned int nr_cores,
+int fdt_adjust_gic_redist(void *dtb, unsigned int nr_cores, uintptr_t gicr_base,
 			  unsigned int gicr_frame_size);
 
 #endif /* FDT_FIXUP_H */
diff --git a/include/common/fdt_wrappers.h b/include/common/fdt_wrappers.h
index a571092..9c7180c 100644
--- a/include/common/fdt_wrappers.h
+++ b/include/common/fdt_wrappers.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -24,6 +24,8 @@
 			  unsigned int cells, uint32_t *value);
 int fdtw_read_string(const void *dtb, int node, const char *prop,
 		char *str, size_t size);
+int fdtw_read_uuid(const void *dtb, int node, const char *prop,
+		   unsigned int length, uint8_t *uuid);
 int fdtw_write_inplace_cells(void *dtb, int node, const char *prop,
 		unsigned int cells, void *value);
 int fdtw_read_bytes(const void *dtb, int node, const char *prop,
@@ -39,6 +41,9 @@
 uint64_t fdtw_translate_address(const void *dtb, int bus_node,
 				uint64_t base_address);
 
+int fdtw_for_each_cpu(const void *fdt,
+		      int (*callback)(const void *dtb, int node, uintptr_t mpidr));
+
 static inline uint32_t fdt_blob_size(const void *dtb)
 {
 	const uint32_t *dtb_header = dtb;
@@ -46,4 +51,9 @@
 	return fdt32_to_cpu(dtb_header[1]);
 }
 
+#define fdt_for_each_compatible_node(dtb, node, compatible_str)       \
+for (node = fdt_node_offset_by_compatible(dtb, -1, compatible_str);   \
+     node >= 0;                                                       \
+     node = fdt_node_offset_by_compatible(dtb, node, compatible_str))
+
 #endif /* FDT_WRAPPERS_H */
diff --git a/include/common/tbbr/cot_def.h b/include/common/tbbr/cot_def.h
index 6ce7f80..800ad07 100644
--- a/include/common/tbbr/cot_def.h
+++ b/include/common/tbbr/cot_def.h
@@ -7,6 +7,10 @@
 #ifndef COT_DEF_H
 #define COT_DEF_H
 
+#ifdef MBEDTLS_CONFIG_FILE
+#include MBEDTLS_CONFIG_FILE
+#endif
+
 /* TBBR CoT definitions */
 #if defined(SPD_spmd)
 #define COT_MAX_VERIFIED_PARAMS		8
diff --git a/include/common/tbbr/tbbr_img_def.h b/include/common/tbbr/tbbr_img_def.h
index bd125e6..e1c8c29 100644
--- a/include/common/tbbr/tbbr_img_def.h
+++ b/include/common/tbbr/tbbr_img_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -21,9 +21,17 @@
 #define SP_PKG7_ID			(MAX_IMAGE_IDS + 8)
 #define SP_PKG8_ID			(MAX_IMAGE_IDS + 9)
 #define MAX_SP_IDS			U(8)
-#define MAX_NUMBER_IDS			(MAX_IMAGE_IDS + MAX_SP_IDS + U(2))
+#define MAX_IMG_IDS_WITH_SPMDS		(MAX_IMAGE_IDS + MAX_SP_IDS + U(2))
 #else
-#define MAX_NUMBER_IDS			MAX_IMAGE_IDS
+#define MAX_IMG_IDS_WITH_SPMDS		MAX_IMAGE_IDS
+#endif
+
+#ifdef PLAT_TBBR_IMG_DEF
+#include <plat_tbbr_img_def.h>
+#endif
+
+#ifndef MAX_NUMBER_IDS
+#define MAX_NUMBER_IDS			MAX_IMG_IDS_WITH_SPMDS
 #endif
 
 #endif /* TBBR_IMG_DEF_H */
diff --git a/include/common/tf_crc32.h b/include/common/tf_crc32.h
new file mode 100644
index 0000000..38c56a5
--- /dev/null
+++ b/include/common/tf_crc32.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TF_CRC32_H
+#define TF_CRC32_H
+
+#include <stddef.h>
+#include <stdint.h>
+
+/* compute CRC using Arm intrinsic function */
+uint32_t tf_crc32(uint32_t crc, const unsigned char *buf, size_t size);
+
+#endif /* TF_CRC32_H */
diff --git a/include/common/uuid.h b/include/common/uuid.h
new file mode 100644
index 0000000..5651d0d
--- /dev/null
+++ b/include/common/uuid.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef UUID_H
+#define UUID_H
+
+#define UUID_BYTES_LENGTH	16
+#define UUID_STRING_LENGTH	36
+
+int read_uuid(uint8_t *dest, char *uuid);
+
+#endif /* UUID_H */
diff --git a/include/drivers/allwinner/axp.h b/include/drivers/allwinner/axp.h
index 9c0035f..222820b 100644
--- a/include/drivers/allwinner/axp.h
+++ b/include/drivers/allwinner/axp.h
@@ -9,6 +9,10 @@
 
 #include <stdint.h>
 
+#define AXP20X_MODE_REG 0x3e
+#define AXP20X_MODE_I2C 0x00
+#define AXP20X_MODE_RSB 0x7c
+
 #define NA 0xff
 
 enum {
diff --git a/include/drivers/arm/arm_gicv3_common.h b/include/drivers/arm/arm_gicv3_common.h
index b88b59f..d1e93be 100644
--- a/include/drivers/arm/arm_gicv3_common.h
+++ b/include/drivers/arm/arm_gicv3_common.h
@@ -17,4 +17,12 @@
 #define WAKER_SL_BIT		(1U << WAKER_SL_SHIFT)
 #define WAKER_QSC_BIT		(1U << WAKER_QSC_SHIFT)
 
+#define IIDR_MODEL_ARM_GIC_600		U(0x0200043b)
+#define IIDR_MODEL_ARM_GIC_600AE	U(0x0300043b)
+#define IIDR_MODEL_ARM_GIC_700		U(0x0400043b)
+
+#define PIDR_COMPONENT_ARM_DIST		U(0x492)
+#define PIDR_COMPONENT_ARM_REDIST	U(0x493)
+#define PIDR_COMPONENT_ARM_ITS		U(0x494)
+
 #endif /* ARM_GICV3_COMMON_H */
diff --git a/include/drivers/arm/css/scmi.h b/include/drivers/arm/css/scmi.h
index e8a2863..9dd08e5 100644
--- a/include/drivers/arm/css/scmi.h
+++ b/include/drivers/arm/css/scmi.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,7 +16,7 @@
 
 /* Supported SCMI Protocol Versions */
 #define SCMI_AP_CORE_PROTO_VER			MAKE_SCMI_VERSION(1, 0)
-#define SCMI_PWR_DMN_PROTO_VER			MAKE_SCMI_VERSION(1, 0)
+#define SCMI_PWR_DMN_PROTO_VER			MAKE_SCMI_VERSION(2, 0)
 #define SCMI_SYS_PWR_PROTO_VER			MAKE_SCMI_VERSION(1, 0)
 
 #define GET_SCMI_MAJOR_VER(ver)			(((ver) >> 16) & 0xffff)
@@ -25,10 +25,16 @@
 #define MAKE_SCMI_VERSION(maj, min)	\
 			((((maj) & 0xffff) << 16) | ((min) & 0xffff))
 
-/* Macro to check if the driver is compatible with the SCMI version reported */
+/*
+ * Check that the driver's version is same or higher than the reported SCMI
+ * version. We accept lower major version numbers, as all affected protocols
+ * so far stay backwards compatible. This might need to be revisited in the
+ * future.
+ */
 #define is_scmi_version_compatible(drv, scmi)				\
+	((GET_SCMI_MAJOR_VER(drv) > GET_SCMI_MAJOR_VER(scmi)) ||	\
 	((GET_SCMI_MAJOR_VER(drv) == GET_SCMI_MAJOR_VER(scmi)) &&	\
-	(GET_SCMI_MINOR_VER(drv) <= GET_SCMI_MINOR_VER(scmi)))
+	(GET_SCMI_MINOR_VER(drv) <= GET_SCMI_MINOR_VER(scmi))))
 
 /* SCMI Protocol identifiers */
 #define SCMI_PWR_DMN_PROTO_ID			0x11
diff --git a/include/drivers/arm/dcc.h b/include/drivers/arm/dcc.h
new file mode 100644
index 0000000..1f1fd03
--- /dev/null
+++ b/include/drivers/arm/dcc.h
@@ -0,0 +1,19 @@
+/*
+ * Copyright (c) 2021,  Xilinx Inc.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef DCC_H
+#define DCC_H
+
+#include <stdint.h>
+#include <drivers/console.h>
+
+/*
+ * Initialize a new dcc console instance and register it with the console
+ * framework.
+ */
+int console_dcc_register(void);
+
+#endif /* DCC */
diff --git a/include/drivers/arm/ethosn.h b/include/drivers/arm/ethosn.h
new file mode 100644
index 0000000..9310733
--- /dev/null
+++ b/include/drivers/arm/ethosn.h
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef ETHOSN_H
+#define ETHOSN_H
+
+#include <lib/smccc.h>
+
+/* Function numbers */
+#define ETHOSN_FNUM_VERSION		U(0x50)
+#define ETHOSN_FNUM_IS_SEC		U(0x51)
+#define ETHOSN_FNUM_HARD_RESET		U(0x52)
+#define ETHOSN_FNUM_SOFT_RESET		U(0x53)
+/* 0x54-0x5F reserved for future use */
+
+/* SMC64 function IDs */
+#define ETHOSN_FID_64(func_num)		U(0xC2000000 | func_num)
+#define ETHOSN_FID_VERSION_64		ETHOSN_FID_64(ETHOSN_FNUM_VERSION)
+#define ETHOSN_FID_IS_SEC_64		ETHOSN_FID_64(ETHOSN_FNUM_IS_SEC)
+#define ETHOSN_FID_HARD_RESET_64	ETHOSN_FID_64(ETHOSN_FNUM_HARD_RESET)
+#define ETHOSN_FID_SOFT_RESET_64	ETHOSN_FID_64(ETHOSN_FNUM_SOFT_RESET)
+
+/* SMC32 function IDs */
+#define ETHOSN_FID_32(func_num)		U(0x82000000 | func_num)
+#define ETHOSN_FID_VERSION_32		ETHOSN_FID_32(ETHOSN_FNUM_VERSION)
+#define ETHOSN_FID_IS_SEC_32		ETHOSN_FID_32(ETHOSN_FNUM_IS_SEC)
+#define ETHOSN_FID_HARD_RESET_32	ETHOSN_FID_32(ETHOSN_FNUM_HARD_RESET)
+#define ETHOSN_FID_SOFT_RESET_32	ETHOSN_FID_32(ETHOSN_FNUM_SOFT_RESET)
+
+#define ETHOSN_NUM_SMC_CALLS	8
+
+/* Macro to identify function calls */
+#define ETHOSN_FID_MASK		U(0xFFF0)
+#define ETHOSN_FID_VALUE	U(0x50)
+#define is_ethosn_fid(_fid) (((_fid) & ETHOSN_FID_MASK) == ETHOSN_FID_VALUE)
+
+/* Service version  */
+#define ETHOSN_VERSION_MAJOR U(1)
+#define ETHOSN_VERSION_MINOR U(0)
+
+/* Return codes for function calls */
+#define ETHOSN_SUCCESS			 0
+#define ETHOSN_NOT_SUPPORTED		-1
+/* -2 Reserved for NOT_REQUIRED */
+/* -3 Reserved for INVALID_PARAMETER */
+#define ETHOSN_FAILURE			-4
+#define ETHOSN_UNKNOWN_CORE_ADDRESS	-5
+
+uintptr_t ethosn_smc_handler(uint32_t smc_fid,
+			     u_register_t core_addr,
+			     u_register_t x2,
+			     u_register_t x3,
+			     u_register_t x4,
+			     void *cookie,
+			     void *handle,
+			     u_register_t flags);
+
+#endif  /* ETHOSN_H */
diff --git a/include/drivers/arm/gic600ae_fmu.h b/include/drivers/arm/gic600ae_fmu.h
new file mode 100644
index 0000000..691ffc7
--- /dev/null
+++ b/include/drivers/arm/gic600ae_fmu.h
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef GIC600AE_FMU_H
+#define GIC600AE_FMU_H
+
+/*******************************************************************************
+ * GIC600-AE FMU register offsets and constants
+ ******************************************************************************/
+#define GICFMU_ERRFR_LO		U(0x000)
+#define GICFMU_ERRFR_HI		U(0x004)
+#define GICFMU_ERRCTLR_LO	U(0x008)
+#define GICFMU_ERRCTLR_HI	U(0x00C)
+#define GICFMU_ERRSTATUS_LO	U(0x010)
+#define GICFMU_ERRSTATUS_HI	U(0x014)
+#define GICFMU_ERRGSR_LO	U(0xE00)
+#define GICFMU_ERRGSR_HI	U(0xE04)
+#define GICFMU_KEY		U(0xEA0)
+#define GICFMU_PINGCTLR		U(0xEA4)
+#define GICFMU_PINGNOW		U(0xEA8)
+#define GICFMU_SMEN		U(0xEB0)
+#define GICFMU_SMINJERR		U(0xEB4)
+#define GICFMU_PINGMASK_LO	U(0xEC0)
+#define GICFMU_PINGMASK_HI	U(0xEC4)
+#define GICFMU_STATUS		U(0xF00)
+#define GICFMU_ERRIDR		U(0xFC8)
+
+/* ERRCTLR bits */
+#define FMU_ERRCTLR_ED_BIT	BIT(0)
+#define FMU_ERRCTLR_CE_EN_BIT	BIT(1)
+#define FMU_ERRCTLR_UI_BIT	BIT(2)
+#define FMU_ERRCTLR_CI_BIT	BIT(3)
+
+/* SMEN constants */
+#define FMU_SMEN_BLK_SHIFT	U(8)
+#define FMU_SMEN_SMID_SHIFT	U(24)
+
+/* Error record IDs */
+#define FMU_BLK_GICD		U(0)
+#define FMU_BLK_SPICOL		U(1)
+#define FMU_BLK_WAKERQ		U(2)
+#define FMU_BLK_ITS0		U(4)
+#define FMU_BLK_ITS1		U(5)
+#define FMU_BLK_ITS2		U(6)
+#define FMU_BLK_ITS3		U(7)
+#define FMU_BLK_ITS4		U(8)
+#define FMU_BLK_ITS5		U(9)
+#define FMU_BLK_ITS6		U(10)
+#define FMU_BLK_ITS7		U(11)
+#define FMU_BLK_PPI0		U(12)
+#define FMU_BLK_PPI1		U(13)
+#define FMU_BLK_PPI2		U(14)
+#define FMU_BLK_PPI3		U(15)
+#define FMU_BLK_PPI4		U(16)
+#define FMU_BLK_PPI5		U(17)
+#define FMU_BLK_PPI6		U(18)
+#define FMU_BLK_PPI7		U(19)
+#define FMU_BLK_PPI8		U(20)
+#define FMU_BLK_PPI9		U(21)
+#define FMU_BLK_PPI10		U(22)
+#define FMU_BLK_PPI11		U(23)
+#define FMU_BLK_PPI12		U(24)
+#define FMU_BLK_PPI13		U(25)
+#define FMU_BLK_PPI14		U(26)
+#define FMU_BLK_PPI15		U(27)
+#define FMU_BLK_PPI16		U(28)
+#define FMU_BLK_PPI17		U(29)
+#define FMU_BLK_PPI18		U(30)
+#define FMU_BLK_PPI19		U(31)
+#define FMU_BLK_PPI20		U(32)
+#define FMU_BLK_PPI21		U(33)
+#define FMU_BLK_PPI22		U(34)
+#define FMU_BLK_PPI23		U(35)
+#define FMU_BLK_PPI24		U(36)
+#define FMU_BLK_PPI25		U(37)
+#define FMU_BLK_PPI26		U(38)
+#define FMU_BLK_PPI27		U(39)
+#define FMU_BLK_PPI28		U(40)
+#define FMU_BLK_PPI29		U(41)
+#define FMU_BLK_PPI30		U(42)
+#define FMU_BLK_PPI31		U(43)
+#define FMU_BLK_PRESENT_MASK	U(0xFFFFFFFFFFF)
+
+/* Safety Mechamism limit */
+#define FMU_SMID_GICD_MAX	U(33)
+#define FMU_SMID_SPICOL_MAX	U(5)
+#define FMU_SMID_WAKERQ_MAX	U(2)
+#define FMU_SMID_ITS_MAX	U(14)
+#define FMU_SMID_PPI_MAX	U(12)
+
+/* MBIST Safety Mechanism ID */
+#define GICD_MBIST_REQ_ERROR	U(23)
+#define GICD_FMU_CLKGATE_ERROR	U(33)
+#define PPI_MBIST_REQ_ERROR	U(10)
+#define PPI_FMU_CLKGATE_ERROR	U(12)
+#define ITS_MBIST_REQ_ERROR	U(13)
+#define ITS_FMU_CLKGATE_ERROR	U(14)
+
+/* ERRSTATUS bits */
+#define FMU_ERRSTATUS_V_BIT	BIT(30)
+#define FMU_ERRSTATUS_UE_BIT	BIT(29)
+#define FMU_ERRSTATUS_OV_BIT	BIT(27)
+#define FMU_ERRSTATUS_CE_BITS	(BIT(25) | BIT(24))
+#define FMU_ERRSTATUS_CLEAR	(FMU_ERRSTATUS_V_BIT | FMU_ERRSTATUS_UE_BIT | \
+				 FMU_ERRSTATUS_OV_BIT | FMU_ERRSTATUS_CE_BITS)
+
+/* PINGCTLR constants */
+#define FMU_PINGCTLR_INTDIFF_SHIFT	U(16)
+#define FMU_PINGCTLR_TIMEOUTVAL_SHIFT	U(4)
+#define FMU_PINGCTLR_EN_BIT		BIT(0)
+
+#ifndef __ASSEMBLER__
+
+#include <stdint.h>
+
+#include <arch_helpers.h>
+
+/*******************************************************************************
+ * GIC600 FMU EL3 driver API
+ ******************************************************************************/
+uint64_t gic_fmu_read_errfr(uintptr_t base, unsigned int n);
+uint64_t gic_fmu_read_errctlr(uintptr_t base, unsigned int n);
+uint64_t gic_fmu_read_errstatus(uintptr_t base, unsigned int n);
+uint64_t gic_fmu_read_errgsr(uintptr_t base);
+uint32_t gic_fmu_read_pingctlr(uintptr_t base);
+uint32_t gic_fmu_read_pingnow(uintptr_t base);
+uint64_t gic_fmu_read_pingmask(uintptr_t base);
+uint32_t gic_fmu_read_status(uintptr_t base);
+uint32_t gic_fmu_read_erridr(uintptr_t base);
+void gic_fmu_write_errctlr(uintptr_t base, unsigned int n, uint64_t val);
+void gic_fmu_write_errstatus(uintptr_t base, unsigned int n, uint64_t val);
+void gic_fmu_write_pingctlr(uintptr_t base, uint32_t val);
+void gic_fmu_write_pingnow(uintptr_t base, uint32_t val);
+void gic_fmu_write_smen(uintptr_t base, uint32_t val);
+void gic_fmu_write_sminjerr(uintptr_t base, uint32_t val);
+void gic_fmu_write_pingmask(uintptr_t base, uint64_t val);
+
+void gic600_fmu_init(uint64_t base, uint64_t blk_present_mask, bool errctlr_ce_en, bool errctlr_ue_en);
+void gic600_fmu_enable_ping(uint64_t base, uint64_t blk_present_mask,
+		unsigned int timeout_val, unsigned int interval_diff);
+void gic600_fmu_print_sm_info(uint64_t base, unsigned int blk, unsigned int smid);
+
+#endif /* __ASSEMBLER__ */
+
+#endif /* GIC600AE_FMU_H */
diff --git a/include/drivers/arm/gicv3.h b/include/drivers/arm/gicv3.h
index d8ac4cb..5efefb6 100644
--- a/include/drivers/arm/gicv3.h
+++ b/include/drivers/arm/gicv3.h
@@ -104,6 +104,8 @@
 #define GICD_IROUTER		U(0x6000)
 #define GICD_IROUTERE		U(0x8000)
 
+#define GICD_PIDR0_GICV3	U(0xffe0)
+#define GICD_PIDR1_GICV3	U(0xffe4)
 #define GICD_PIDR2_GICV3	U(0xffe8)
 
 #define IGRPMODR_SHIFT		5
@@ -153,11 +155,8 @@
 /*******************************************************************************
  * Common GIC Redistributor interface registers & constants
  ******************************************************************************/
-#if GIC_ENABLE_V4_EXTN
-#define GICR_PCPUBASE_SHIFT	0x12
-#else
-#define GICR_PCPUBASE_SHIFT	0x11
-#endif
+#define GICR_V4_PCPUBASE_SHIFT	0x12
+#define GICR_V3_PCPUBASE_SHIFT	0x11
 #define GICR_SGIBASE_OFFSET	U(65536)	/* 64 KB */
 #define GICR_CTLR		U(0x0)
 #define GICR_IIDR		U(0x04)
@@ -212,12 +211,14 @@
 #define TYPER_AFF_VAL_SHIFT	32
 #define TYPER_PROC_NUM_SHIFT	8
 #define TYPER_LAST_SHIFT	4
+#define TYPER_VLPI_SHIFT	1
 
 #define TYPER_AFF_VAL_MASK	U(0xffffffff)
 #define TYPER_PROC_NUM_MASK	U(0xffff)
 #define TYPER_LAST_MASK		U(0x1)
 
 #define TYPER_LAST_BIT		BIT_32(TYPER_LAST_SHIFT)
+#define TYPER_VLPI_BIT		BIT_32(TYPER_VLPI_SHIFT)
 
 #define TYPER_PPI_NUM_SHIFT	U(27)
 #define TYPER_PPI_NUM_MASK	U(0x1f)
@@ -302,6 +303,8 @@
 #define GITS_CTLR_ENABLED_BIT		BIT_32(0)
 #define GITS_CTLR_QUIESCENT_BIT		BIT_32(1)
 
+#define GITS_TYPER_VSGI			BIT_64(39)
+
 #ifndef __ASSEMBLER__
 
 #include <stdbool.h>
@@ -312,6 +315,21 @@
 #include <drivers/arm/gic_common.h>
 #include <lib/utils_def.h>
 
+static inline uintptr_t gicv3_redist_size(uint64_t typer_val)
+{
+#if GIC_ENABLE_V4_EXTN
+	if ((typer_val & TYPER_VLPI_BIT) != 0U) {
+		return 1U << GICR_V4_PCPUBASE_SHIFT;
+	} else {
+		return 1U << GICR_V3_PCPUBASE_SHIFT;
+	}
+#else
+	return 1U << GICR_V3_PCPUBASE_SHIFT;
+#endif
+}
+
+unsigned int gicv3_get_component_partnum(const uintptr_t gic_frame);
+
 static inline bool gicv3_is_intr_id_special_identifier(unsigned int id)
 {
 	return (id >= PENDING_G1S_INTID) && (id <= GIC_SPURIOUS_INTERRUPT);
diff --git a/include/drivers/arm/tzc400.h b/include/drivers/arm/tzc400.h
index 32aeb03..765c130 100644
--- a/include/drivers/arm/tzc400.h
+++ b/include/drivers/arm/tzc400.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -65,8 +65,8 @@
 #define FAIL_CONTROL_NS_SECURE			U(0)
 #define FAIL_CONTROL_NS_NONSECURE		U(1)
 #define FAIL_CONTROL_PRIV_SHIFT			20
-#define FAIL_CONTROL_PRIV_PRIV			U(0)
-#define FAIL_CONTROL_PRIV_UNPRIV		U(1)
+#define FAIL_CONTROL_PRIV_UNPRIV		U(0)
+#define FAIL_CONTROL_PRIV_PRIV			U(1)
 
 /*
  * FAIL_ID_ID_MASK depends on AID_WIDTH which is platform specific.
@@ -80,11 +80,8 @@
 
 /* Filter enable bits in a TZC */
 #define TZC_400_REGION_ATTR_F_EN_MASK		U(0xf)
-#define TZC_400_REGION_ATTR_FILTER_BIT(x)				\
-				((U(1) << (x)) << TZC_REGION_ATTR_F_EN_SHIFT)
-#define TZC_400_REGION_ATTR_FILTER_BIT_ALL				\
-				(TZC_400_REGION_ATTR_F_EN_MASK <<	\
-				TZC_REGION_ATTR_F_EN_SHIFT)
+#define TZC_400_REGION_ATTR_FILTER_BIT(x)	(U(1) << (x))
+#define TZC_400_REGION_ATTR_FILTER_BIT_ALL	TZC_400_REGION_ATTR_F_EN_MASK
 
 /*
  * All TZC region configuration registers are placed one after another. It
@@ -93,6 +90,8 @@
 #define TZC_400_REGION_SIZE			U(0x20)
 #define TZC_400_ACTION_OFF			U(0x4)
 
+#define FILTER_OFFSET				U(0x10)
+
 #ifndef __ASSEMBLER__
 
 #include <cdefs.h>
@@ -110,9 +109,11 @@
 			  unsigned long long region_top,
 			  unsigned int sec_attr,
 			  unsigned int nsaid_permissions);
+void tzc400_update_filters(unsigned int region, unsigned int filters);
 void tzc400_set_action(unsigned int action);
 void tzc400_enable_filters(void);
 void tzc400_disable_filters(void);
+int tzc400_it_handler(void);
 
 static inline void tzc_init(uintptr_t base)
 {
diff --git a/include/drivers/brcm/i2c/i2c.h b/include/drivers/brcm/i2c/i2c.h
new file mode 100644
index 0000000..24d42e2
--- /dev/null
+++ b/include/drivers/brcm/i2c/i2c.h
@@ -0,0 +1,161 @@
+/*
+ * Copyright (c) 2016 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef I2C_H
+#define I2C_H
+
+#include <stdint.h>
+
+#define I2C_SPEED_100KHz	100000
+#define I2C_SPEED_400KHz	400000
+#define I2C_SPEED_DEFAULT	I2C_SPEED_100KHz
+
+/*
+ * Function Name:    i2c_probe
+ *
+ * Description:
+ *	This function probes the I2C bus for the existence of the specified
+ *	device.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_probe(uint32_t bus_id, uint8_t devaddr);
+
+/*
+ * Function Name:    i2c_init
+ *
+ * Description:
+ *	This function initializes the SMBUS.
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *	speed  - I2C bus speed in Hz
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_init(uint32_t bus_id, int speed);
+
+/*
+ * Function Name:    i2c_set_bus_speed
+ *
+ * Description:
+ *	This function configures the SMBUS speed
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *	speed  - I2C bus speed in Hz
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_set_bus_speed(uint32_t bus_id, uint32_t speed);
+
+/*
+ * Function Name:    i2c_get_bus_speed
+ *
+ * Description:
+ *	This function returns the SMBUS speed.
+ *
+ * Parameters:
+ *	bus_id - I2C bus ID
+ *
+ * Return:
+ *	Bus speed in Hz, 0 on failure
+ */
+uint32_t i2c_get_bus_speed(uint32_t bus_id);
+
+/*
+ * Function Name:    i2c_recv_byte
+ *
+ * Description:
+ *	This function reads I2C data from a device without specifying
+ *	a command regsiter.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	value   - Data Read
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_recv_byte(uint32_t bus_id, uint8_t devaddr, uint8_t *value);
+
+/*
+ * Function Name:    i2c_send_byte
+ *
+ * Description:
+ *	This function send I2C data to a device without specifying
+ *	a command regsiter.
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	value   - Data Send
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_send_byte(uint32_t bus_id, uint8_t devaddr, uint8_t value);
+
+/*
+ * Function Name:    i2c_read
+ *
+ * Description:
+ *	This function reads I2C data from a device with a designated
+ *	command register
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	addr    - Register Offset
+ *	alen    - Address Length, 1 for byte, 2 for word (not supported)
+ *	buffer  - Data Buffer
+ *	len     - Data Length in bytes
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_read(uint32_t bus_id,
+	     uint8_t devaddr,
+	     uint32_t addr,
+	     int alen,
+	     uint8_t *buffer,
+	     int len);
+
+/*
+ * Function Name:    i2c_write
+ *
+ * Description:
+ *	This function write I2C data to a device with a designated
+ *	command register
+ *
+ * Parameters:
+ *	bus_id  - I2C bus ID
+ *	devaddr - Device Address
+ *	addr    - Register Offset
+ *	alen    - Address Length, 1 for byte, 2 for word (not supported)
+ *	buffer  - Data Buffer
+ *	len     - Data Length in bytes
+ *
+ * Return:
+ *	0 on success, or -1 on failure.
+ */
+int i2c_write(uint32_t bus_id,
+	      uint8_t devaddr,
+	      uint32_t addr,
+	      int alen,
+	      uint8_t *buffer,
+	      int len);
+
+
+#endif /* I2C_H */
diff --git a/include/drivers/brcm/i2c/i2c_regs.h b/include/drivers/brcm/i2c/i2c_regs.h
new file mode 100644
index 0000000..74ea824
--- /dev/null
+++ b/include/drivers/brcm/i2c/i2c_regs.h
@@ -0,0 +1,271 @@
+/*
+ * Copyright (c) 2016 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef I2C_REGS
+#define I2C_REGS
+
+/* SMBUS Config register */
+#define SMB_CFG_REG				0x0U
+
+#define SMB_CFG_RST_MASK			0x80000000U
+#define SMB_CFG_RST_SHIFT			31U
+
+#define SMB_CFG_SMBEN_MASK			0x40000000U
+#define SMB_CFG_SMBEN_SHIFT			30U
+
+#define SMB_CFG_BITBANGEN_MASK			0x20000000U
+#define SMB_CFG_BITBANGEN_SHIFT			29U
+
+#define SMB_CFG_EN_NIC_SMBADDR0_MASK		0x10000000U
+#define SMB_CFG_EN_NIC_SMBADDR0_SHIFT		28U
+
+#define SMB_CFG_PROMISCMODE_MASK		0x08000000U
+#define SMB_CFG_PROMISCMODE_SHIFT		27U
+
+#define SMB_CFG_TSTMPCNTEN_MASK			0x04000000U
+#define SMB_CFG_TSTMPCNTEN_SHIFT		26U
+
+#define SMB_CFG_MSTRRTRYCNT_MASK		0x000F0000U
+#define SMB_CFG_MSTRRTRYCNT_SHIFT		16U
+
+/* SMBUS Timing config register */
+#define SMB_TIMGCFG_REG				0x4U
+
+#define SMB_TIMGCFG_MODE400_MASK		0x80000000U
+#define SMB_TIMGCFG_MODE400_SHIFT		31U
+
+#define SMB_TIMGCFG_RNDSLVSTR_MASK		0x7F000000U
+#define SMB_TIMGCFG_RNDSLVSTR_SHIFT		24U
+
+#define SMB_TIMGCFG_PERSLVSTR_MASK		0x00FF0000U
+#define SMB_TIMGCFG_PERSLVSTR_SHIFT		16U
+
+#define SMB_TIMGCFG_IDLTIME_MASK		0x0000FF00U
+#define SMB_TIMGCFG_IDLTIME_SHIFT		8U
+
+/* SMBUS Slave address register */
+#define SMB_ADDR_REG				0x8U
+
+#define SMB_EN_NIC_SMBADDR3_MASK		0x80000000U
+#define SMB_EN_NIC_SMBADDR3_SHIFT		31U
+
+#define SMB_NIC_SMBADDR3_MASK			0x7F000000U
+#define SMB_NIC_SMBADDR3_SHIFT			24U
+
+#define SMB_EN_NIC_SMBADDR2_MASK		0x00800000U
+#define SMB_EN_NIC_SMBADDR2_SHIFT		23U
+
+#define SMB_NIC_SMBADDR2_MASK			0x007F0000U
+#define SMB_NIC_SMBADDR2_SHIFT			16U
+
+#define SMB_EN_NIC_SMBADDR1_MASK		0x00008000U
+#define SMB_EN_NIC_SMBADDR1_SHIFT		15U
+
+#define SMB_NIC_SMBADDR1_MASK			0x00007F00U
+#define SMB_NIC_SMBADDR1_SHIFT			8U
+
+#define SMB_EN_NIC_SMBADDR0_MASK		0x00000080U
+#define SMB_EN_NIC_SMBADDR0_SHIFT		7U
+
+#define SMB_NIC_SMBADDR0_MASK			0x0000007FU
+#define SMB_NIC_SMBADDR0_SHIFT			0U
+
+/* SMBUS Master FIFO control register */
+#define SMB_MSTRFIFOCTL_REG			0xCU
+
+#define SMB_MSTRRXFIFOFLSH_MASK			0x80000000U
+#define SMB_MSTRRXFIFOFLSH_SHIFT		31U
+
+#define SMB_MSTRTXFIFOFLSH_MASK			0x40000000U
+#define SMB_MSTRTXFIFOFLSH_SHIFT		30U
+
+#define SMB_MSTRRXPKTCNT_MASK			0x007F0000U
+#define SMB_MSTRRXPKTCNT_SHIFT			16U
+
+#define SMB_MSTRRXFIFOTHR_MASK			0x00003F00U
+#define SMB_MSTRRXFIFOTHR_SHIFT			8U
+
+/* SMBUS Slave FIFO control register */
+#define SMB_SLVFIFOCTL_REG			0x10U
+
+#define SMB_SLVRXFIFOFLSH_MASK			0x80000000U
+#define SMB_SLVRXFIFOFLSH_SHIFT			31U
+
+#define SMB_SLVTXFIFOFLSH_MASK			0x40000000U
+#define SMB_SLVTXFIFOFLSH_SHIFT			30U
+
+#define SMB_SLVRXPKTCNT_MASK			0x007F0000U
+#define SMB_SLVRXPKTCNT_SHIFT			16U
+
+#define SMB_SLVRXFIFOTHR_MASK			0x00003F00U
+#define SMB_SLVRXFIFOTHR_SHIFT			8U
+
+/* SMBUS Bit-bang mode control register */
+#define SMB_BITBANGCTL_REG			0x14U
+
+#define SMB_SMBCLKIN_MASK			0x80000000U
+#define SMB_SMBCLKIN_SHIFT			31U
+
+#define SMB_SMBCLKOUTEN_MASK			0x40000000U
+#define SMB_SMBCLKOUTEN_SHIFT			30U
+
+#define SMB_SMBDATAIN_MASK			0x20000000U
+#define SMB_SMBDATAIN_SHIFT			29U
+
+#define SMB_SMBDATAOUTEN_MASK			0x10000000U
+#define SMB_SMBDATAOUTEN_SHIFT			28U
+
+/* SMBUS Master command register */
+#define SMB_MSTRCMD_REG				0x30U
+
+#define SMB_MSTRSTARTBUSYCMD_MASK		0x80000000U
+#define SMB_MSTRSTARTBUSYCMD_SHIFT		31U
+
+#define SMB_MSTRABORT_MASK			0x40000000U
+#define SMB_MSTRABORT_SHIFT			30U
+
+#define SMB_MSTRSTS_MASK			0x0E000000U
+#define SMB_MSTRSTS_SHIFT			25U
+
+#define SMB_MSTRSMBUSPROTO_MASK			0x00001E00U
+#define SMB_MSTRSMBUSPROTO_SHIFT		9U
+
+#define SMB_MSTRPEC_MASK			0x00000100U
+#define SMB_MSTRPEC_SHIFT			8U
+
+#define SMB_MSTRRDBYTECNT_MASK			0x000000FFU
+#define SMB_MSTRRDBYTECNT_SHIFT			0U
+
+/* SMBUS Slave command register */
+#define SMB_SLVCMD_REG				0x34U
+
+#define SMB_SLVSTARTBUSYCMD_MASK		0x80000000U
+#define SMB_SLVSTARTBUSYCMD_SHIFT		31U
+
+#define SMB_SLVABORT_MASK			0x40000000U
+#define SMB_SLVABORT_SHIFT			30U
+
+#define SMB_SLVSTS_MASK				0x03800000U
+#define SMB_SLVSTS_SHIFT			23U
+
+#define SMB_SLVPEC_MASK				0x00000100U
+#define SMB_SLVPEC_SHIFT			8U
+
+/* SMBUS Event enable register */
+#define SMB_EVTEN_REG				0x38U
+
+#define SMB_MSTRRXFIFOFULLEN_MASK		0x80000000U
+#define SMB_MSTRRXFIFOFULLEN_SHIFT		31U
+
+#define SMB_MSTRRXFIFOTHRHITEN_MASK		0x40000000U
+#define SMB_MSTRRXFIFOTHRHITEN_SHIFT		30U
+
+#define SMB_MSTRRXEVTEN_MASK			0x20000000U
+#define SMB_MSTRRXEVTEN_SHIFT			29U
+
+#define SMB_MSTRSTARTBUSYEN_MASK		0x10000000U
+#define SMB_MSTRSTARTBUSYEN_SHIFT		28U
+
+#define SMB_MSTRTXUNDEN_MASK			0x08000000U
+#define SMB_MSTRTXUNDEN_SHIFT			27U
+
+#define SMB_SLVRXFIFOFULLEN_MASK		0x04000000U
+#define SMB_SLVRXFIFOFULLEN_SHIFT		26U
+
+#define SMB_SLVRXFIFOTHRHITEN_MASK		0x02000000U
+#define SMB_SLVRXFIFOTHRHITEN_SHIFT		25U
+
+#define SMB_SLVRXEVTEN_MASK			0x01000000U
+#define SMB_SLVRXEVTEN_SHIFT			24U
+
+#define SMB_SLVSTARTBUSYEN_MASK			0x00800000U
+#define SMB_SLVSTARTBUSYEN_SHIFT		23U
+
+#define SMB_SLVTXUNDEN_MASK			0x00400000U
+#define SMB_SLVTXUNDEN_SHIFT			22U
+
+#define SMB_SLVRDEVTEN_MASK			0x00200000U
+#define SMB_SLVRDEVTEN_SHIFT			21U
+
+/* SMBUS Event status register */
+#define SMB_EVTSTS_REG				0x3CU
+
+#define SMB_MSTRRXFIFOFULLSTS_MASK		0x80000000U
+#define SMB_MSTRRXFIFOFULLSTS_SHIFT		31U
+
+#define SMB_MSTRRXFIFOTHRHITSTS_MASK		0x40000000U
+#define SMB_MSTRRXFIFOTHRHITSTS_SHIFT		30U
+
+#define SMB_MSTRRXEVTSTS_MASK			0x20000000U
+#define SMB_MSTRRXEVTSTS_SHIFT			29U
+
+#define SMB_MSTRSTARTBUSYSTS_MASK		0x10000000U
+#define SMB_MSTRSTARTBUSYSTS_SHIFT		28U
+
+#define SMB_MSTRTXUNDSTS_MASK			0x08000000U
+#define SMB_MSTRTXUNDSTS_SHIFT			27U
+
+#define SMB_SLVRXFIFOFULLSTS_MASK		0x04000000U
+#define SMB_SLVRXFIFOFULLSTS_SHIFT		26U
+
+#define SMB_SLVRXFIFOTHRHITSTS_MASK		0x02000000U
+#define SMB_SLVRXFIFOTHRHITSTS_SHIFT		25U
+
+#define SMB_SLVRXEVTSTS_MASK			0x01000000U
+#define SMB_SLVRXEVTSTS_SHIFT			24U
+
+#define SMB_SLVSTARTBUSYSTS_MASK		0x00800000U
+#define SMB_SLVSTARTBUSYSTS_SHIFT		23U
+
+#define SMB_SLVTXUNDSTS_MASK			0x00400000U
+#define SMB_SLVTXUNDSTS_SHIFT			22U
+
+#define SMB_SLVRDEVTSTS_MASK			0x00200000U
+#define SMB_SLVRDEVTSTS_SHIFT			21U
+
+/* SMBUS Master data write register */
+#define SMB_MSTRDATAWR_REG			0x40U
+
+#define SMB_MSTRWRSTS_MASK			0x80000000U
+#define SMB_MSTRWRSTS_SHIFT			31U
+
+#define SMB_MSTRWRDATA_MASK			0x000000FFU
+#define SMB_MSTRWRDATA_SHIFT			0U
+
+/* SMBUS Master data read register */
+#define SMB_MSTRDATARD_REG			0x44U
+
+#define SMB_MSTRRDSTS_MASK			0xC0000000U
+#define SMB_MSTRRDSTS_SHIFT			30U
+
+#define SMB_MSTRRDPECERR_MASK			0x20000000U
+#define SMB_MSTRRDPECERR_SHIFT			29U
+
+#define SMB_MSTRRDDATA_MASK			0x000000FFU
+#define SMB_MSTRRDDATA_SHIFT			0U
+
+/* SMBUS Slave data write register */
+#define SMB_SLVDATAWR_REG			0x48U
+
+#define SMB_SLVWRSTS_MASK			0x80000000U
+#define SMB_SLVWRSTS_SHIFT			31U
+
+#define SMB_SLVWRDATA_MASK			0x000000FFU
+#define SMB_SLVWRDATA_SHIFT			0U
+
+/* SMBUS Slave data read register */
+#define SMB_SLVDATARD_REG			0x4CU
+
+#define SMB_SLVRDSTS_MASK			0xC0000000U
+#define SMB_SLVRDSTS_SHIFT			30U
+
+#define SMB_SLVRDERRSTS_MASK			0x30000000U
+#define SMB_SLVRDERRSTS_SHIFT			28U
+
+#define SMB_SLVRDDATA_MASK			0x000000FFU
+#define SMB_SLVRDDATA_SHIFT			0U
+
+#endif /* I2C_REGS */
diff --git a/include/drivers/brcm/mdio/mdio.h b/include/drivers/brcm/mdio/mdio.h
new file mode 100644
index 0000000..b27c7b3
--- /dev/null
+++ b/include/drivers/brcm/mdio/mdio.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2016 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MDIO_H
+#define MDIO_H
+
+#define CMIC_MIIM_PARAM		(PLAT_CMIC_MIIM_BASE + 0x23cU)
+#define MDIO_PARAM_MIIM_CYCLE	29U
+#define MDIO_PARAM_INTERNAL_SEL	25U
+#define MDIO_PARAM_BUSID	22U
+#define MDIO_PARAM_BUSID_MASK	0x7U
+#define MDIO_PARAM_C45_SEL	21U
+#define MDIO_PARAM_PHYID	16U
+#define MDIO_PARAM_PHYID_MASK	0x1FU
+#define MDIO_PARAM_DATA		0U
+#define MDIO_PARAM_DATA_MASK	0xFFFFU
+#define CMIC_MIIM_READ_DATA	(PLAT_CMIC_MIIM_BASE + 0x240U)
+#define MDIO_READ_DATA_MASK	0xffffU
+#define CMIC_MIIM_ADDRESS	(PLAT_CMIC_MIIM_BASE + 0x244U)
+#define CMIC_MIIM_CTRL		(PLAT_CMIC_MIIM_BASE + 0x248U)
+#define MDIO_CTRL_WRITE_OP	0x1U
+#define MDIO_CTRL_READ_OP	0x2U
+#define CMIC_MIIM_STAT		(PLAT_CMIC_MIIM_BASE + 0x24cU)
+#define MDIO_STAT_DONE		1U
+
+int mdio_write(uint16_t busid, uint16_t phyid, uint32_t reg, uint16_t val);
+int mdio_read(uint16_t busid, uint16_t phyid, uint32_t reg);
+#endif /* MDIO_H */
diff --git a/include/drivers/brcm/usbh_xhci_regs.h b/include/drivers/brcm/usbh_xhci_regs.h
new file mode 100644
index 0000000..93dec7b
--- /dev/null
+++ b/include/drivers/brcm/usbh_xhci_regs.h
@@ -0,0 +1,4809 @@
+/*
+ * Copyright (c) 2017 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+
+#ifndef USBH_XHCI_REGS_H
+#define USBH_XHCI_REGS_H
+
+#include <lib/mmio.h>
+#include <platform_def.h>
+
+#define XHCI_LEN (8096U)
+
+#define XHC_CPLIVER_OFFSET			0x000U
+#define XHC_SPARAMS1_OFFSET			0x004U
+#define XHC_SPARAMS2_OFFSET			0x008U
+#define XHC_SPARAMS3_OFFSET			0x00cU
+#define XHC_CPARAMS1_OFFSET			0x010U
+#define XHC_DBOFF_OFFSET			0x014U
+#define XHC_RTOFF_OFFSET			0x018U
+#define XHC_CPARAMS2_OFFSET			0x01cU
+#define XHC_USBCMD_OFFSET			0x020U
+#define XHC_USBSTS_OFFSET			0x024U
+#define XHC_PAGESIZE_OFFSET			0x028U
+#define XHC_DNCTRL_OFFSET			0x034U
+#define XHC_CRCRL_OFFSET			0x038U
+#define XHC_CRCRH_OFFSET			0x03cU
+#define XHC_DCBAAPL_OFFSET			0x050U
+#define XHC_DCBAAPH_OFFSET			0x054U
+#define XHC_CONFIG_OFFSET			0x058U
+#define XHC_PORTSC1_OFFSET			0x420U
+#define XHC_PORTPM1_OFFSET			0x424U
+#define XHC_PORTLC1_OFFSET			0x428U
+#define XHC_PORTSC2_OFFSET			0x430U
+#define XHC_PORTPM2_OFFSET			0x434U
+#define XHC_PORTLC2_OFFSET			0x43cU
+#define XHC_PORTSC3_OFFSET			0x440U
+#define XHC_PORTPM3_OFFSET			0x444U
+#define XHC_PORTLI3_OFFSET			0x44cU
+#define XHC_MFINDEX_OFFSET			0x4a0U
+#define XHC_IMAN0_OFFSET			0x4c0U
+#define XHC_IMOD0_OFFSET			0x4c4U
+#define XHC_ERSTSZ0_OFFSET			0x4c8U
+#define XHC_ERSTBAL0_OFFSET			0x4d0U
+#define XHC_ERSTBAH0_OFFSET			0x4d4U
+#define XHC_ERDPL0_OFFSET			0x4d8U
+#define XHC_ERDPH0_OFFSET			0x4dcU
+#define XHC_IMAN1_OFFSET			0x4e0U
+#define XHC_IMOD1_OFFSET			0x4e4U
+#define XHC_ERSTSZ1_OFFSET			0x4e8U
+#define XHC_ERSTBAL1_OFFSET			0x4f0U
+#define XHC_ERSTBAH1_OFFSET			0x4f4U
+#define XHC_ERDPL1_OFFSET			0x4f8U
+#define XHC_ERDPH1_OFFSET			0x4fcU
+#define XHC_DBLCMD_OFFSET			0x8c0U
+#define XHC_DBLDVX1_OFFSET			0x8c4U
+#define XHC_DBLDVX2_OFFSET			0x8c8U
+#define XHC_DBLDVX3_OFFSET			0x8ccU
+#define XHC_DBLDVX4_OFFSET			0x8d0U
+#define XHC_DBLDVX5_OFFSET			0x8d4U
+#define XHC_DBLDVX6_OFFSET			0x8d8U
+#define XHC_DBLDVX7_OFFSET			0x8dcU
+#define XHC_DBLDVX8_OFFSET			0x8e0U
+#define XHC_DBLDVX9_OFFSET			0x8e4U
+#define XHC_DBLDVX10_OFFSET			0x8e8U
+#define XHC_DBLDVX11_OFFSET			0x8ecU
+#define XHC_DBLDVX12_OFFSET			0x8f0U
+#define XHC_DBLDVX13_OFFSET			0x8f4U
+#define XHC_DBLDVX14_OFFSET			0x8f8U
+#define XHC_DBLDVX15_OFFSET			0x8fcU
+#define XHC_DBLDVX16_OFFSET			0x900U
+#define XHC_ECHSPT3_OFFSET			0x940U
+#define XHC_PNSTR3_OFFSET			0x944U
+#define XHC_PSUM3_OFFSET			0x948U
+#define XHC_PTSLTYP3_OFFSET			0x94cU
+#define XHC_ECHSPT2_OFFSET			0x950U
+#define XHC_PNSTR2_OFFSET			0x954U
+#define XHC_PSUM2_OFFSET			0x958U
+#define XHC_PTSLTYP2_OFFSET			0x95cU
+#define XHC_ECHRSVP_OFFSET			0x960U
+#define XHC_ECHRSVI_OFFSET			0x968U
+#define XHC_ECHRSVM_OFFSET			0xae8U
+#define XHC_ECHRSVD_OFFSET			0xaf8U
+#define XHC_ECHRSVO_OFFSET			0xb38U
+#define XHC_ECHCTT_OFFSET			0xbf0U
+#define XHC_CTTMTS0_OFFSET			0xbf8U
+#define XHC_CTTMTS1_OFFSET			0xbfcU
+#define XHC_ECHBIU_OFFSET			0xc00U
+#define XHC_BIUSPC_OFFSET			0xc04U
+#define XHC_AXIWRA_OFFSET			0xc08U
+#define XHC_AXIRDA_OFFSET			0xc0cU
+#define XHC_AXILPM_OFFSET			0xc10U
+#define XHC_AXIQOS_OFFSET			0xc14U
+#define XHC_ECHCSR_OFFSET			0xc20U
+#define XHC_CSRSPC_OFFSET			0xc24U
+#define XHC_ECHAIU_OFFSET			0xc30U
+#define XHC_AIUDMA_OFFSET			0xc34U
+#define XHC_AIUFLA_OFFSET			0xc38U
+#define XHC_AIUCFG_OFFSET			0xc3cU
+#define XHC_ECHFSC_OFFSET			0xc40U
+#define XHC_FSCPOC_OFFSET			0xc54U
+#define XHC_FSCGOC_OFFSET			0xc58U
+#define XHC_FSCNOC_OFFSET			0xc5cU
+#define XHC_FSCAIC_OFFSET			0xc60U
+#define XHC_FSCPIC_OFFSET			0xc64U
+#define XHC_FSCGIC_OFFSET			0xc68U
+#define XHC_FSCNIC_OFFSET			0xc6cU
+#define XHC_ECHPRT_OFFSET			0xc70U
+#define XHC_PRTHSC_OFFSET			0xc78U
+#define XHC_PRTHSR_OFFSET			0xc7cU
+#define XHC_ECHRHS_OFFSET			0xc80U
+#define XHC_RHSDES_OFFSET			0xc84U
+#define XHC_RHSHSC0_OFFSET			0xc90U
+#define XHC_RHSHSR0_OFFSET			0xc94U
+#define XHC_RHSHSC1_OFFSET			0xc98U
+#define XHC_RHSHSR1_OFFSET			0xc9cU
+#define XHC_RHSHSC2_OFFSET			0xca0U
+#define XHC_RHSHSR2_OFFSET			0xca4U
+#define XHC_RHSHSC3_OFFSET			0xca8U
+#define XHC_RHSHSR3_OFFSET			0xcacU
+#define XHC_ECHSSP_OFFSET			0xcb0U
+#define XHC_SSPVER_OFFSET			0xcb4U
+#define XHC_SSPMGN_OFFSET			0xcb8U
+#define XHC_ECHFSC2_OFFSET			0xcc0U
+#define XHC_FSC2POC_OFFSET			0xcd4U
+#define XHC_FSC2GOC_OFFSET			0xcd8U
+#define XHC_FSC2NOC_OFFSET			0xcdcU
+#define XHC_FSC2AIC_OFFSET			0xce0U
+#define XHC_FSC2PIC_OFFSET			0xce4U
+#define XHC_FSC2GIC_OFFSET			0xce8U
+#define XHC_FSC2NIC_OFFSET			0xcecU
+#define XHC_ECHPRT2_OFFSET			0xcf0U
+#define XHC_PRT2HSC_OFFSET			0xcf8U
+#define XHC_PRT2HSR_OFFSET			0xcfcU
+#define XHC_ECHRH2_OFFSET			0xd00U
+#define XHC_RH2DES_OFFSET			0xd04U
+#define XHC_RH2HSC0_OFFSET			0xd10U
+#define XHC_RH2HSR0_OFFSET			0xd14U
+#define XHC_RH2HSC1_OFFSET			0xd18U
+#define XHC_RH2HSR1_OFFSET			0xd1cU
+#define XHC_RH2HSC2_OFFSET			0xd20U
+#define XHC_RH2HSR2_OFFSET			0xd24U
+#define XHC_RH2HSC3_OFFSET			0xd28U
+#define XHC_RH2HSR3_OFFSET			0xd2cU
+#define XHC_ECHU2P_OFFSET			0xd30U
+#define XHC_U2PVER_OFFSET			0xd34U
+#define XHC_U2PMGN_OFFSET			0xd38U
+#define XHC_ECHRSV2_OFFSET			0xd40U
+#define XHC_ECHIRA_OFFSET			0xf90U
+#define XHC_IRAADR_OFFSET			0xf98U
+#define XHC_IRADAT_OFFSET			0xf9cU
+#define XHC_ECHHST_OFFSET			0xfa0U
+#define XHC_HSTDBG_OFFSET			0xfa4U
+#define XHC_HSTNPL_OFFSET			0xfa8U
+#define XHC_HSTNPH_OFFSET			0xfacU
+#define XHC_ECHRBV_OFFSET			0xfb0U
+#define XHC_RBVPDT_OFFSET			0xfb4U
+#define XHC_RBVMGN_OFFSET			0xfbcU
+
+#define XHC_CPLIVER_BASE			0x000U
+#define XHC_CPLIVER__IVH_L			31U
+#define XHC_CPLIVER__IVH_R			24U
+#define XHC_CPLIVER__IVH_WIDTH			8U
+#define XHC_CPLIVER__IVH_RESETVALUE		0x01U
+#define XHC_CPLIVER__IVL_L			23U
+#define XHC_CPLIVER__IVL_R			16U
+#define XHC_CPLIVER__IVL_WIDTH			8U
+#define XHC_CPLIVER__IVL_RESETVALUE		0x10U
+#define XHC_CPLIVER__reserved_L			15U
+#define XHC_CPLIVER__reserved_R			8U
+#define XHC_CPLIVER__reserved_WIDTH		8U
+#define XHC_CPLIVER__reserved_RESETVALUE	0x00U
+#define XHC_CPLIVER__CPL_L			7U
+#define XHC_CPLIVER__CPL_R			0U
+#define XHC_CPLIVER__CPL_WIDTH			8U
+#define XHC_CPLIVER__CPL_RESETVALUE		0x00U
+#define XHC_CPLIVER_WIDTH			32U
+#define XHC_CPLIVER__WIDTH			32U
+#define XHC_CPLIVER_ALL_L			31U
+#define XHC_CPLIVER_ALL_R			0U
+#define XHC_CPLIVER__ALL_L			31U
+#define XHC_CPLIVER__ALL_R			0U
+#define XHC_CPLIVER_DATAMASK			0xffffffffU
+#define XHC_CPLIVER_RDWRMASK			0x00000000U
+#define XHC_CPLIVER_RESETVALUE			0x01100000U
+
+#define XHC_SPARAMS1_OFFSET			0x004U
+#define XHC_SPARAMS1_BASE			0x004U
+#define XHC_SPARAMS1__NPTS_L			31U
+#define XHC_SPARAMS1__NPTS_R			24U
+#define XHC_SPARAMS1__NPTS_WIDTH		8U
+#define XHC_SPARAMS1__NPTS_RESETVALUE		0x00U
+#define XHC_SPARAMS1__reserved_L		23U
+#define XHC_SPARAMS1__reserved_R		19U
+#define XHC_SPARAMS1__reserved_WIDTH		5U
+#define XHC_SPARAMS1__reserved_RESETVALUE	0x0U
+#define XHC_SPARAMS1__MITS_L			18U
+#define XHC_SPARAMS1__MITS_R			8U
+#define XHC_SPARAMS1__MITS_WIDTH		11U
+#define XHC_SPARAMS1__MITS_RESETVALUE		0x1U
+#define XHC_SPARAMS1__MSLS_L			7U
+#define XHC_SPARAMS1__MSLS_R			0U
+#define XHC_SPARAMS1__MSLS_WIDTH		8U
+#define XHC_SPARAMS1__MSLS_RESETVALUE		0x00U
+#define XHC_SPARAMS1_WIDTH			32U
+#define XHC_SPARAMS1__WIDTH			32U
+#define XHC_SPARAMS1_ALL_L			31U
+#define XHC_SPARAMS1_ALL_R			0U
+#define XHC_SPARAMS1__ALL_L			31U
+#define XHC_SPARAMS1__ALL_R			0U
+#define XHC_SPARAMS1_DATAMASK			0xffffffffU
+#define XHC_SPARAMS1_RDWRMASK			0x00000000U
+#define XHC_SPARAMS1_RESETVALUE			0x00000100U
+
+#define XHC_SPARAMS2_OFFSET			0x008U
+#define XHC_SPARAMS2_BASE			0x008U
+#define XHC_SPARAMS2__MSPBSL_L			31U
+#define XHC_SPARAMS2__MSPBSL_R			27U
+#define XHC_SPARAMS2__MSPBSL_WIDTH		5U
+#define XHC_SPARAMS2__MSPBSL_RESETVALUE		0x0U
+#define XHC_SPARAMS2__SPR			26U
+#define XHC_SPARAMS2__SPR_L			26U
+#define XHC_SPARAMS2__SPR_R			26U
+#define XHC_SPARAMS2__SPR_WIDTH			1U
+#define XHC_SPARAMS2__SPR_RESETVALUE		0x1U
+#define XHC_SPARAMS2__MSPBSH_L			25U
+#define XHC_SPARAMS2__MSPBSH_R			21U
+#define XHC_SPARAMS2__MSPBSH_WIDTH		5U
+#define XHC_SPARAMS2__MSPBSH_RESETVALUE		0x0U
+#define XHC_SPARAMS2__reserved_L		20U
+#define XHC_SPARAMS2__reserved_R		8U
+#define XHC_SPARAMS2__reserved_WIDTH		13U
+#define XHC_SPARAMS2__reserved_RESETVALUE	0x0U
+#define XHC_SPARAMS2__MERST_L			7U
+#define XHC_SPARAMS2__MERST_R			4U
+#define XHC_SPARAMS2__MERST_WIDTH		4U
+#define XHC_SPARAMS2__MERST_RESETVALUE		0x0U
+#define XHC_SPARAMS2__IST_L			3U
+#define XHC_SPARAMS2__IST_R			0U
+#define XHC_SPARAMS2__IST_WIDTH			4U
+#define XHC_SPARAMS2__IST_RESETVALUE		0x0U
+#define XHC_SPARAMS2_WIDTH			32U
+#define XHC_SPARAMS2__WIDTH			32U
+#define XHC_SPARAMS2_ALL_L			31U
+#define XHC_SPARAMS2_ALL_R			0U
+#define XHC_SPARAMS2__ALL_L			31U
+#define XHC_SPARAMS2__ALL_R			0U
+#define XHC_SPARAMS2_DATAMASK			0xffffffffU
+#define XHC_SPARAMS2_RDWRMASK			0x00000000U
+#define XHC_SPARAMS2_RESETVALUE			0x04000000U
+
+#define XHC_SPARAMS3_OFFSET			0x00cU
+#define XHC_SPARAMS3_BASE			0x00cU
+#define XHC_SPARAMS3__U2L_L			31U
+#define XHC_SPARAMS3__U2L_R			16U
+#define XHC_SPARAMS3__U2L_WIDTH			16U
+#define XHC_SPARAMS3__U2L_RESETVALUE		0x0000U
+#define XHC_SPARAMS3__reserved_L		15U
+#define XHC_SPARAMS3__reserved_R		8U
+#define XHC_SPARAMS3__reserved_WIDTH		8U
+#define XHC_SPARAMS3__reserved_RESETVALUE	0x00U
+#define XHC_SPARAMS3__U1L_L			7U
+#define XHC_SPARAMS3__U1L_R			0U
+#define XHC_SPARAMS3__U1L_WIDTH			8U
+#define XHC_SPARAMS3__U1L_RESETVALUE		0x00U
+#define XHC_SPARAMS3_WIDTH			32U
+#define XHC_SPARAMS3__WIDTH			32U
+#define XHC_SPARAMS3_ALL_L			31U
+#define XHC_SPARAMS3_ALL_R			0U
+#define XHC_SPARAMS3__ALL_L			31U
+#define XHC_SPARAMS3__ALL_R			0U
+#define XHC_SPARAMS3_DATAMASK			0xffffffffU
+#define XHC_SPARAMS3_RDWRMASK			0x00000000U
+#define XHC_SPARAMS3_RESETVALUE			0x00000000U
+
+#define XHC_CPARAMS1_OFFSET			0x010U
+#define XHC_CPARAMS1_BASE			0x010U
+#define XHC_CPARAMS1__XECP_L			31U
+#define XHC_CPARAMS1__XECP_R			16U
+#define XHC_CPARAMS1__XECP_WIDTH		16U
+#define XHC_CPARAMS1__XECP_RESETVALUE		0x0000U
+#define XHC_CPARAMS1__MPSA_L			15U
+#define XHC_CPARAMS1__MPSA_R			12U
+#define XHC_CPARAMS1__MPSA_WIDTH		4U
+#define XHC_CPARAMS1__MPSA_RESETVALUE		0x0U
+#define XHC_CPARAMS1__CFC			11U
+#define XHC_CPARAMS1__CFC_L			11U
+#define XHC_CPARAMS1__CFC_R			11U
+#define XHC_CPARAMS1__CFC_WIDTH			1U
+#define XHC_CPARAMS1__CFC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__SEC			10U
+#define XHC_CPARAMS1__SEC_L			10U
+#define XHC_CPARAMS1__SEC_R			10U
+#define XHC_CPARAMS1__SEC_WIDTH			1U
+#define XHC_CPARAMS1__SEC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__SPC			9U
+#define XHC_CPARAMS1__SPC_L			9U
+#define XHC_CPARAMS1__SPC_R			9U
+#define XHC_CPARAMS1__SPC_WIDTH			1U
+#define XHC_CPARAMS1__SPC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__PAE			8U
+#define XHC_CPARAMS1__PAE_L			8U
+#define XHC_CPARAMS1__PAE_R			8U
+#define XHC_CPARAMS1__PAE_WIDTH			1U
+#define XHC_CPARAMS1__PAE_RESETVALUE		0x1U
+#define XHC_CPARAMS1__NSS			7U
+#define XHC_CPARAMS1__NSS_L			7U
+#define XHC_CPARAMS1__NSS_R			7U
+#define XHC_CPARAMS1__NSS_WIDTH			1U
+#define XHC_CPARAMS1__NSS_RESETVALUE		0x0U
+#define XHC_CPARAMS1__LTC			6U
+#define XHC_CPARAMS1__LTC_L			6U
+#define XHC_CPARAMS1__LTC_R			6U
+#define XHC_CPARAMS1__LTC_WIDTH			1U
+#define XHC_CPARAMS1__LTC_RESETVALUE		0x1U
+#define XHC_CPARAMS1__LRC			5U
+#define XHC_CPARAMS1__LRC_L			5U
+#define XHC_CPARAMS1__LRC_R			5U
+#define XHC_CPARAMS1__LRC_WIDTH			1U
+#define XHC_CPARAMS1__LRC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__PIND			4U
+#define XHC_CPARAMS1__PIND_L			4U
+#define XHC_CPARAMS1__PIND_R			4U
+#define XHC_CPARAMS1__PIND_WIDTH		1U
+#define XHC_CPARAMS1__PIND_RESETVALUE		0x0U
+
+#define XHC_CPARAMS1__PPC_L			3U
+#define XHC_CPARAMS1__PPC_R			3U
+#define XHC_CPARAMS1__PPC_WIDTH			1U
+#define XHC_CPARAMS1__PPC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__CSZ			2U
+#define XHC_CPARAMS1__CSZ_L			2U
+#define XHC_CPARAMS1__CSZ_R			2U
+#define XHC_CPARAMS1__CSZ_WIDTH			1U
+#define XHC_CPARAMS1__CSZ_RESETVALUE		0x1U
+#define XHC_CPARAMS1__BNC			1U
+#define XHC_CPARAMS1__BNC_L			1U
+#define XHC_CPARAMS1__BNC_R			1U
+#define XHC_CPARAMS1__BNC_WIDTH			1U
+#define XHC_CPARAMS1__BNC_RESETVALUE		0x0U
+#define XHC_CPARAMS1__AC64			0U
+#define XHC_CPARAMS1__AC64_L			0U
+#define XHC_CPARAMS1__AC64_R			0U
+#define XHC_CPARAMS1__AC64_WIDTH		1U
+#define XHC_CPARAMS1__AC64_RESETVALUE		0x0U
+#define XHC_CPARAMS1_WIDTH			32U
+#define XHC_CPARAMS1__WIDTH			32U
+#define XHC_CPARAMS1_ALL_L			31U
+#define XHC_CPARAMS1_ALL_R			0U
+#define XHC_CPARAMS1__ALL_L			31U
+#define XHC_CPARAMS1__ALL_R			0U
+#define XHC_CPARAMS1_DATAMASK			0xffffffffU
+#define XHC_CPARAMS1_RDWRMASK			0x00000000U
+#define XHC_CPARAMS1_RESETVALUE			0x00000144U
+
+#define XHC_DBOFF_OFFSET			0x014U
+#define XHC_DBOFF_BASE				0x014U
+#define XHC_DBOFF__DBO_L			15U
+#define XHC_DBOFF__DBO_R			2U
+#define XHC_DBOFF__DBO_WIDTH			14U
+#define XHC_DBOFF__DBO_RESETVALUE		0x0U
+#define XHC_DBOFF__reserved_L			1U
+#define XHC_DBOFF__reserved_R			0U
+#define XHC_DBOFF__reserved_WIDTH		2U
+#define XHC_DBOFF__reserved_RESETVALUE		0x0U
+#define XHC_DBOFF__RESERVED_L			31U
+#define XHC_DBOFF__RESERVED_R			16U
+#define XHC_DBOFF_WIDTH				16U
+#define XHC_DBOFF__WIDTH			16U
+#define XHC_DBOFF_ALL_L				15U
+#define XHC_DBOFF_ALL_R				0U
+#define XHC_DBOFF__ALL_L			15U
+#define XHC_DBOFF__ALL_R			0U
+#define XHC_DBOFF_DATAMASK			0x0000ffffU
+#define XHC_DBOFF_RDWRMASK			0xffff0000U
+#define XHC_DBOFF_RESETVALUE			0x0000U
+
+#define XHC_RTOFF_OFFSET			0x018U
+#define XHC_RTOFF_BASE				0x018U
+#define XHC_RTOFF__RTO_L			15U
+#define XHC_RTOFF__RTO_R			5U
+#define XHC_RTOFF__RTO_WIDTH			11U
+#define XHC_RTOFF__RTO_RESETVALUE		0x0U
+#define XHC_RTOFF__reserved_L			4U
+#define XHC_RTOFF__reserved_R			0U
+#define XHC_RTOFF__reserved_WIDTH		5U
+#define XHC_RTOFF__reserved_RESETVALUE		0x0U
+#define XHC_RTOFF__RESERVED_L			31U
+#define XHC_RTOFF__RESERVED_R			16U
+#define XHC_RTOFF_WIDTH				16U
+#define XHC_RTOFF__WIDTH			16U
+#define XHC_RTOFF_ALL_L				15U
+#define XHC_RTOFF_ALL_R				0U
+#define XHC_RTOFF__ALL_L			15U
+#define XHC_RTOFF__ALL_R			0U
+#define XHC_RTOFF_DATAMASK			0x0000ffffU
+#define XHC_RTOFF_RDWRMASK			0xffff0000U
+#define XHC_RTOFF_RESETVALUE			0x0000U
+
+#define XHC_CPARAMS2_OFFSET			0x01cU
+#define XHC_CPARAMS2_BASE			0x01cU
+#define XHC_CPARAMS2__reserved_L		31U
+#define XHC_CPARAMS2__reserved_R		6U
+#define XHC_CPARAMS2__reserved_WIDTH		26U
+#define XHC_CPARAMS2__reserved_RESETVALUE	0x0U
+#define XHC_CPARAMS2__CIC			5U
+#define XHC_CPARAMS2__CIC_L			5U
+#define XHC_CPARAMS2__CIC_R			5U
+#define XHC_CPARAMS2__CIC_WIDTH			1U
+#define XHC_CPARAMS2__CIC_RESETVALUE		0x0U
+#define XHC_CPARAMS2__LEC			4U
+#define XHC_CPARAMS2__LEC_L			4U
+#define XHC_CPARAMS2__LEC_R			4U
+#define XHC_CPARAMS2__LEC_WIDTH			1U
+#define XHC_CPARAMS2__LEC_RESETVALUE		0x0U
+#define XHC_CPARAMS2__CTC			3U
+#define XHC_CPARAMS2__CTC_L			3U
+#define XHC_CPARAMS2__CTC_R			3U
+#define XHC_CPARAMS2__CTC_WIDTH			1U
+#define XHC_CPARAMS2__CTC_RESETVALUE		0x0U
+#define XHC_CPARAMS2__FSC			2U
+#define XHC_CPARAMS2__FSC_L			2U
+#define XHC_CPARAMS2__FSC_R			2U
+#define XHC_CPARAMS2__FSC_WIDTH			1U
+#define XHC_CPARAMS2__FSC_RESETVALUE		0x0U
+#define XHC_CPARAMS2__CMC			1U
+#define XHC_CPARAMS2__CMC_L			1U
+#define XHC_CPARAMS2__CMC_R			1U
+#define XHC_CPARAMS2__CMC_WIDTH			1U
+#define XHC_CPARAMS2__CMC_RESETVALUE		0x0U
+#define XHC_CPARAMS2__U3C			0U
+#define XHC_CPARAMS2__U3C_L			0U
+#define XHC_CPARAMS2__U3C_R			0U
+#define XHC_CPARAMS2__U3C_WIDTH			1U
+#define XHC_CPARAMS2__U3C_RESETVALUE		0x0U
+#define XHC_CPARAMS2_WIDTH			32U
+#define XHC_CPARAMS2__WIDTH			32U
+#define XHC_CPARAMS2_ALL_L			31U
+#define XHC_CPARAMS2_ALL_R			0U
+#define XHC_CPARAMS2__ALL_L			31U
+#define XHC_CPARAMS2__ALL_R			0U
+#define XHC_CPARAMS2_DATAMASK			0xffffffffU
+#define XHC_CPARAMS2_RDWRMASK			0x00000000U
+#define XHC_CPARAMS2_RESETVALUE			0x00000000U
+
+#define XHC_USBCMD_OFFSET			0x020U
+#define XHC_USBCMD_BASE				0x020U
+#define XHC_USBCMD__CME				13U
+#define XHC_USBCMD__CME_L			13U
+#define XHC_USBCMD__CME_R			13U
+#define XHC_USBCMD__CME_WIDTH			1U
+#define XHC_USBCMD__CME_RESETVALUE		0x0U
+#define XHC_USBCMD__SPE				12U
+#define XHC_USBCMD__SPE_L			12U
+#define XHC_USBCMD__SPE_R			12U
+#define XHC_USBCMD__SPE_WIDTH			1U
+#define XHC_USBCMD__SPE_RESETVALUE		0x0U
+#define XHC_USBCMD__EU3S			11U
+#define XHC_USBCMD__EU3S_L			11U
+#define XHC_USBCMD__EU3S_R			11U
+#define XHC_USBCMD__EU3S_WIDTH			1U
+#define XHC_USBCMD__EU3S_RESETVALUE		0x0U
+#define XHC_USBCMD__EWE				10U
+#define XHC_USBCMD__EWE_L			10U
+#define XHC_USBCMD__EWE_R			10U
+#define XHC_USBCMD__EWE_WIDTH			1U
+#define XHC_USBCMD__EWE_RESETVALUE		0x0U
+#define XHC_USBCMD__CRS				9U
+#define XHC_USBCMD__CRS_L			9U
+#define XHC_USBCMD__CRS_R			9U
+#define XHC_USBCMD__CRS_WIDTH			1U
+#define XHC_USBCMD__CRS_RESETVALUE		0x0U
+#define XHC_USBCMD__CSS				8U
+#define XHC_USBCMD__CSS_L			8U
+#define XHC_USBCMD__CSS_R			8U
+#define XHC_USBCMD__CSS_WIDTH			1U
+#define XHC_USBCMD__CSS_RESETVALUE		0x0U
+#define XHC_USBCMD__LRST			7U
+#define XHC_USBCMD__LRST_L			7U
+#define XHC_USBCMD__LRST_R			7U
+#define XHC_USBCMD__LRST_WIDTH			1U
+#define XHC_USBCMD__LRST_RESETVALUE		0x0U
+#define XHC_USBCMD__reserved_L			6U
+#define XHC_USBCMD__reserved_R			4U
+#define XHC_USBCMD__reserved_WIDTH		3U
+#define XHC_USBCMD__reserved_RESETVALUE		0x0U
+#define XHC_USBCMD__HSEE			3U
+#define XHC_USBCMD__HSEE_L			3U
+#define XHC_USBCMD__HSEE_R			3U
+#define XHC_USBCMD__HSEE_WIDTH			1U
+#define XHC_USBCMD__HSEE_RESETVALUE		0x0U
+#define XHC_USBCMD__INTE			2U
+#define XHC_USBCMD__INTE_L			2U
+#define XHC_USBCMD__INTE_R			2U
+#define XHC_USBCMD__INTE_WIDTH			1U
+#define XHC_USBCMD__INTE_RESETVALUE		0x0U
+#define XHC_USBCMD__RST				1U
+#define XHC_USBCMD__RST_L			1U
+#define XHC_USBCMD__RST_R			1U
+#define XHC_USBCMD__RST_WIDTH			1U
+#define XHC_USBCMD__RST_RESETVALUE		0x0U
+#define XHC_USBCMD__RS				0U
+#define XHC_USBCMD__RS_L			0U
+#define XHC_USBCMD__RS_R			0U
+#define XHC_USBCMD__RS_WIDTH			1U
+#define XHC_USBCMD__RS_RESETVALUE		0x0U
+#define XHC_USBCMD__RESERVED_L			31U
+#define XHC_USBCMD__RESERVED_R			14U
+#define XHC_USBCMD_WIDTH			14U
+#define XHC_USBCMD__WIDTH			14U
+#define XHC_USBCMD_ALL_L			13U
+#define XHC_USBCMD_ALL_R			0U
+#define XHC_USBCMD__ALL_L			13U
+#define XHC_USBCMD__ALL_R			0U
+#define XHC_USBCMD_DATAMASK			0x00003fffU
+#define XHC_USBCMD_RDWRMASK			0xffffc000U
+#define XHC_USBCMD_RESETVALUE			0x0000U
+
+#define XHC_USBSTS_OFFSET			0x024U
+#define XHC_USBSTS_BASE				0x024U
+#define XHC_USBSTS__CE				12U
+#define XHC_USBSTS__CE_L			12U
+#define XHC_USBSTS__CE_R			12U
+#define XHC_USBSTS__CE_WIDTH			1U
+#define XHC_USBSTS__CE_RESETVALUE		0x0U
+#define XHC_USBSTS__CNR				11U
+#define XHC_USBSTS__CNR_L			11U
+#define XHC_USBSTS__CNR_R			11U
+#define XHC_USBSTS__CNR_WIDTH			1U
+#define XHC_USBSTS__CNR_RESETVALUE		0x1U
+
+#define XHC_USBSTS__SRE				10U
+#define XHC_USBSTS__SRE_L			10U
+#define XHC_USBSTS__SRE_R			10U
+#define XHC_USBSTS__SRE_WIDTH			1U
+#define XHC_USBSTS__SRE_RESETVALUE		0x0U
+#define XHC_USBSTS__RSS				9U
+#define XHC_USBSTS__RSS_L			9U
+#define XHC_USBSTS__RSS_R			9U
+#define XHC_USBSTS__RSS_WIDTH			1U
+#define XHC_USBSTS__RSS_RESETVALUE		0x0U
+#define XHC_USBSTS__SSS				8U
+#define XHC_USBSTS__SSS_L			8U
+#define XHC_USBSTS__SSS_R			8U
+#define XHC_USBSTS__SSS_WIDTH			1U
+#define XHC_USBSTS__SSS_RESETVALUE		0x0U
+#define XHC_USBSTS__PCD				4U
+#define XHC_USBSTS__PCD_L			4U
+#define XHC_USBSTS__PCD_R			4U
+#define XHC_USBSTS__PCD_WIDTH			1U
+#define XHC_USBSTS__PCD_RESETVALUE		0x0U
+#define XHC_USBSTS__EINT			3U
+#define XHC_USBSTS__EINT_L			3U
+#define XHC_USBSTS__EINT_R			3U
+#define XHC_USBSTS__EINT_WIDTH			1U
+#define XHC_USBSTS__EINT_RESETVALUE		0x0U
+#define XHC_USBSTS__HSE				2U
+#define XHC_USBSTS__HSE_L			2U
+#define XHC_USBSTS__HSE_R			2U
+#define XHC_USBSTS__HSE_WIDTH			1U
+#define XHC_USBSTS__HSE_RESETVALUE		0x0U
+#define XHC_USBSTS__reserved			1U
+#define XHC_USBSTS__reserved_L			1U
+#define XHC_USBSTS__reserved_R			1U
+#define XHC_USBSTS__reserved_WIDTH		1U
+#define XHC_USBSTS__reserved_RESETVALUE		0x0U
+
+#define XHC_USBSTS__CH_L			0U
+#define XHC_USBSTS__CH_R			0U
+#define XHC_USBSTS__CH_WIDTH			1U
+#define XHC_USBSTS__CH_RESETVALUE		0x1U
+#define XHC_USBSTS__RESERVED_L			31U
+#define XHC_USBSTS__RESERVED_R			13U
+#define XHC_USBSTS_WIDTH			13U
+#define XHC_USBSTS__WIDTH			13U
+#define XHC_USBSTS_ALL_L			12U
+#define XHC_USBSTS_ALL_R			0U
+#define XHC_USBSTS__ALL_L			12U
+#define XHC_USBSTS__ALL_R			0U
+#define XHC_USBSTS_DATAMASK			0x00001f1fU
+#define XHC_USBSTS_RDWRMASK			0xffffe0e0U
+#define XHC_USBSTS_RESETVALUE			0x0801U
+
+#define XHC_PAGESIZE_OFFSET			0x028U
+#define XHC_PAGESIZE_BASE			0x028U
+#define XHC_PAGESIZE__reserved_L		31U
+#define XHC_PAGESIZE__reserved_R		16U
+#define XHC_PAGESIZE__reserved_WIDTH		16U
+#define XHC_PAGESIZE__reserved_RESETVALUE	0x0000U
+#define XHC_PAGESIZE__PS_L			15U
+#define XHC_PAGESIZE__PS_R			0U
+#define XHC_PAGESIZE__PS_WIDTH			16U
+#define XHC_PAGESIZE__PS_RESETVALUE		0x0000U
+#define XHC_PAGESIZE_WIDTH			32U
+#define XHC_PAGESIZE__WIDTH			32U
+#define XHC_PAGESIZE_ALL_L			31U
+#define XHC_PAGESIZE_ALL_R			0U
+#define XHC_PAGESIZE__ALL_L			31U
+#define XHC_PAGESIZE__ALL_R			0U
+#define XHC_PAGESIZE_DATAMASK			0xffffffffU
+#define XHC_PAGESIZE_RDWRMASK			0x00000000U
+#define XHC_PAGESIZE_RESETVALUE			0x00000000U
+
+#define XHC_DNCTRL_OFFSET			0x034U
+#define XHC_DNCTRL_BASE				0x034U
+#define XHC_DNCTRL__reserved_L			31U
+#define XHC_DNCTRL__reserved_R			16U
+#define XHC_DNCTRL__reserved_WIDTH		16U
+#define XHC_DNCTRL__reserved_RESETVALUE		0x0000U
+#define XHC_DNCTRL__DNE_L			15U
+#define XHC_DNCTRL__DNE_R			0U
+#define XHC_DNCTRL__DNE_WIDTH			16U
+#define XHC_DNCTRL__DNE_RESETVALUE		0x0000U
+#define XHC_DNCTRL_WIDTH			32U
+#define XHC_DNCTRL__WIDTH			32U
+#define XHC_DNCTRL_ALL_L			31U
+#define XHC_DNCTRL_ALL_R			0U
+#define XHC_DNCTRL__ALL_L			31U
+#define XHC_DNCTRL__ALL_R			0U
+#define XHC_DNCTRL_DATAMASK			0xffffffffU
+#define XHC_DNCTRL_RDWRMASK			0x00000000U
+#define XHC_DNCTRL_RESETVALUE			0x00000000U
+
+#define XHC_CRCRL_OFFSET			0x038U
+#define XHC_CRCRL_BASE				0x038U
+#define XHC_CRCRL__CRPL_L			31U
+#define XHC_CRCRL__CRPL_R			6U
+#define XHC_CRCRL__CRPL_WIDTH			26U
+#define XHC_CRCRL__CRPL_RESETVALUE		0x0U
+#define XHC_CRCRL__reserved_L			5U
+#define XHC_CRCRL__reserved_R			4U
+#define XHC_CRCRL__reserved_WIDTH		2U
+#define XHC_CRCRL__reserved_RESETVALUE		0x0U
+#define XHC_CRCRL__CRR				3U
+#define XHC_CRCRL__CRR_L			3U
+#define XHC_CRCRL__CRR_R			3U
+#define XHC_CRCRL__CRR_WIDTH			1U
+#define XHC_CRCRL__CRR_RESETVALUE		0x0U
+#define XHC_CRCRL__CA				2U
+#define XHC_CRCRL__CA_L				2U
+#define XHC_CRCRL__CA_R				2U
+#define XHC_CRCRL__CA_WIDTH			1U
+#define XHC_CRCRL__CA_RESETVALUE		0x0U
+#define XHC_CRCRL__CS				1U
+#define XHC_CRCRL__CS_L				1U
+#define XHC_CRCRL__CS_R				1U
+#define XHC_CRCRL__CS_WIDTH			1U
+#define XHC_CRCRL__CS_RESETVALUE		0x0U
+#define XHC_CRCRL__RCS				0U
+#define XHC_CRCRL__RCS_L			0U
+#define XHC_CRCRL__RCS_R			0U
+#define XHC_CRCRL__RCS_WIDTH			1U
+#define XHC_CRCRL__RCS_RESETVALUE		0x0U
+#define XHC_CRCRL_WIDTH				32U
+#define XHC_CRCRL__WIDTH			32U
+#define XHC_CRCRL_ALL_L				31U
+#define XHC_CRCRL_ALL_R				0U
+#define XHC_CRCRL__ALL_L			31U
+#define XHC_CRCRL__ALL_R			0U
+#define XHC_CRCRL_DATAMASK			0xffffffffU
+#define XHC_CRCRL_RDWRMASK			0x00000000U
+#define XHC_CRCRL_RESETVALUE			0x00000000U
+
+#define XHC_CRCRH_OFFSET			0x03cU
+#define XHC_CRCRH_BASE				0x03cU
+#define XHC_CRCRH__CRPH_L			31U
+#define XHC_CRCRH__CRPH_R			0U
+#define XHC_CRCRH__CRPH_WIDTH			32U
+#define XHC_CRCRH__CRPH_RESETVALUE		0x00000000U
+#define XHC_CRCRH_WIDTH				32U
+#define XHC_CRCRH__WIDTH			32U
+#define XHC_CRCRH_ALL_L				31U
+#define XHC_CRCRH_ALL_R				0U
+#define XHC_CRCRH__ALL_L			31U
+#define XHC_CRCRH__ALL_R			0U
+#define XHC_CRCRH_DATAMASK			0xffffffffU
+#define XHC_CRCRH_RDWRMASK			0x00000000U
+#define XHC_CRCRH_RESETVALUE			0x00000000U
+
+#define XHC_DCBAAPL_OFFSET			0x050U
+#define XHC_DCBAAPL_BASE			0x050U
+#define XHC_DCBAAPL__DCAL_L			31U
+#define XHC_DCBAAPL__DCAL_R			6U
+#define XHC_DCBAAPL__DCAL_WIDTH			26U
+#define XHC_DCBAAPL__DCAL_RESETVALUE		0x0U
+
+#define XHC_DCBAAPL__reserved_L			5U
+#define XHC_DCBAAPL__reserved_R			0U
+#define XHC_DCBAAPL__reserved_WIDTH		6U
+#define XHC_DCBAAPL__reserved_RESETVALUE	0x0U
+#define XHC_DCBAAPL_WIDTH			32U
+#define XHC_DCBAAPL__WIDTH			32U
+#define XHC_DCBAAPL_ALL_L			31U
+#define XHC_DCBAAPL_ALL_R			0U
+#define XHC_DCBAAPL__ALL_L			31U
+#define XHC_DCBAAPL__ALL_R			0U
+#define XHC_DCBAAPL_DATAMASK			0xffffffffU
+#define XHC_DCBAAPL_RDWRMASK			0x00000000U
+#define XHC_DCBAAPL_RESETVALUE			0x00000000U
+
+#define XHC_DCBAAPH_OFFSET			0x054U
+#define XHC_DCBAAPH_BASE			0x054U
+#define XHC_DCBAAPH__DCAH_L			31U
+#define XHC_DCBAAPH__DCAH_R			0U
+#define XHC_DCBAAPH__DCAH_WIDTH			32U
+#define XHC_DCBAAPH__DCAH_RESETVALUE		0x00000000U
+#define XHC_DCBAAPH_WIDTH			32U
+#define XHC_DCBAAPH__WIDTH			32U
+#define XHC_DCBAAPH_ALL_L			31U
+#define XHC_DCBAAPH_ALL_R			0U
+#define XHC_DCBAAPH__ALL_L			31U
+#define XHC_DCBAAPH__ALL_R			0U
+#define XHC_DCBAAPH_DATAMASK			0xffffffffU
+#define XHC_DCBAAPH_RDWRMASK			0x00000000U
+#define XHC_DCBAAPH_RESETVALUE			0x00000000U
+
+#define XHC_CONFIG_OFFSET			0x058U
+#define XHC_CONFIG_BASE				0x058U
+#define XHC_CONFIG__reserved_L			31U
+#define XHC_CONFIG__reserved_R			10U
+#define XHC_CONFIG__reserved_WIDTH		22U
+#define XHC_CONFIG__reserved_RESETVALUE		0x0U
+#define XHC_CONFIG__CIE				9U
+#define XHC_CONFIG__CIE_L			9U
+#define XHC_CONFIG__CIE_R			9U
+#define XHC_CONFIG__CIE_WIDTH			1U
+#define XHC_CONFIG__CIE_RESETVALUE		0x0U
+#define XHC_CONFIG__U3E				8U
+#define XHC_CONFIG__U3E_L			8U
+#define XHC_CONFIG__U3E_R			8U
+#define XHC_CONFIG__U3E_WIDTH			1U
+#define XHC_CONFIG__U3E_RESETVALUE		0x0U
+#define XHC_CONFIG__MSE_L			7U
+#define XHC_CONFIG__MSE_R			0U
+#define XHC_CONFIG__MSE_WIDTH			8U
+#define XHC_CONFIG__MSE_RESETVALUE		0x00U
+#define XHC_CONFIG_WIDTH			32U
+#define XHC_CONFIG__WIDTH			32U
+#define XHC_CONFIG_ALL_L			31U
+#define XHC_CONFIG_ALL_R			0U
+#define XHC_CONFIG__ALL_L			31U
+#define XHC_CONFIG__ALL_R			0U
+#define XHC_CONFIG_DATAMASK			0xffffffffU
+#define XHC_CONFIG_RDWRMASK			0x00000000U
+#define XHC_CONFIG_RESETVALUE			0x00000000U
+
+#define XHC_PORTSC1_OFFSET			0x420U
+#define XHC_PORTSC1_BASE			0x420U
+
+#define XHC_PORTSC1__WPR_L			31U
+#define XHC_PORTSC1__WPR_R			31U
+#define XHC_PORTSC1__WPR_WIDTH			1U
+#define XHC_PORTSC1__WPR_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__DNR_L			30U
+#define XHC_PORTSC1__DNR_R			30U
+#define XHC_PORTSC1__DNR_WIDTH			1U
+#define XHC_PORTSC1__DNR_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__WOE_L			27U
+#define XHC_PORTSC1__WOE_R			27U
+#define XHC_PORTSC1__WOE_WIDTH			1U
+#define XHC_PORTSC1__WOE_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__WDE_L			26U
+#define XHC_PORTSC1__WDE_R			26U
+#define XHC_PORTSC1__WDE_WIDTH			1U
+#define XHC_PORTSC1__WDE_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__WCE_L			25U
+#define XHC_PORTSC1__WCE_R			25U
+#define XHC_PORTSC1__WCE_WIDTH			1U
+#define XHC_PORTSC1__WCE_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__CAS_L			24U
+#define XHC_PORTSC1__CAS_R			24U
+#define XHC_PORTSC1__CAS_WIDTH			1U
+#define XHC_PORTSC1__CAS_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__CEC_L			23U
+#define XHC_PORTSC1__CEC_R			23U
+#define XHC_PORTSC1__CEC_WIDTH			1U
+#define XHC_PORTSC1__CEC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__PLC_L			22U
+#define XHC_PORTSC1__PLC_R			22U
+#define XHC_PORTSC1__PLC_WIDTH			1U
+#define XHC_PORTSC1__PLC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__PRC_L			21U
+#define XHC_PORTSC1__PRC_R			21U
+#define XHC_PORTSC1__PRC_WIDTH			1U
+#define XHC_PORTSC1__PRC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__OCC_L			20U
+#define XHC_PORTSC1__OCC_R			20U
+#define XHC_PORTSC1__OCC_WIDTH			1U
+#define XHC_PORTSC1__OCC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__WRC_L			19U
+#define XHC_PORTSC1__WRC_R			19U
+#define XHC_PORTSC1__WRC_WIDTH			1U
+#define XHC_PORTSC1__WRC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__PEC_L			18U
+#define XHC_PORTSC1__PEC_R			18U
+#define XHC_PORTSC1__PEC_WIDTH			1U
+#define XHC_PORTSC1__PEC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__CSC_L			17U
+#define XHC_PORTSC1__CSC_R			17U
+#define XHC_PORTSC1__CSC_WIDTH			1U
+#define XHC_PORTSC1__CSC_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__LWS_L			16U
+#define XHC_PORTSC1__LWS_R			16U
+#define XHC_PORTSC1__LWS_WIDTH			1U
+#define XHC_PORTSC1__LWS_RESETVALUE		0x0U
+#define XHC_PORTSC1__PIC_L			15U
+#define XHC_PORTSC1__PIC_R			14U
+#define XHC_PORTSC1__PIC_WIDTH			2U
+#define XHC_PORTSC1__PIC_RESETVALUE		0x0U
+#define XHC_PORTSC1__PS_L			13U
+#define XHC_PORTSC1__PS_R			10U
+#define XHC_PORTSC1__PS_WIDTH			4U
+#define XHC_PORTSC1__PS_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__PP_L			9U
+#define XHC_PORTSC1__PP_R			9U
+#define XHC_PORTSC1__PP_WIDTH			1U
+#define XHC_PORTSC1__PP_RESETVALUE		0x0U
+#define XHC_PORTSC1__PLS_L			8U
+#define XHC_PORTSC1__PLS_R			5U
+#define XHC_PORTSC1__PLS_WIDTH			4U
+#define XHC_PORTSC1__PLS_RESETVALUE		0x5U
+
+#define XHC_PORTSC1__PRST_L			4U
+#define XHC_PORTSC1__PRST_R			4U
+#define XHC_PORTSC1__PRST_WIDTH			1U
+#define XHC_PORTSC1__PRST_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__OCA_L			3U
+#define XHC_PORTSC1__OCA_R			3U
+#define XHC_PORTSC1__OCA_WIDTH			1U
+#define XHC_PORTSC1__OCA_RESETVALUE		0x0U
+#define XHC_PORTSC1__reserved			2U
+#define XHC_PORTSC1__reserved_L			2U
+#define XHC_PORTSC1__reserved_R			2U
+#define XHC_PORTSC1__reserved_WIDTH		1U
+#define XHC_PORTSC1__reserved_RESETVALUE	0x0U
+
+#define XHC_PORTSC1__PED_L			1U
+#define XHC_PORTSC1__PED_R			1U
+#define XHC_PORTSC1__PED_WIDTH			1U
+#define XHC_PORTSC1__PED_RESETVALUE		0x0U
+
+#define XHC_PORTSC1__CCS_L			0U
+#define XHC_PORTSC1__CCS_R			0U
+#define XHC_PORTSC1__CCS_WIDTH			1U
+#define XHC_PORTSC1__CCS_RESETVALUE		0x0U
+#define XHC_PORTSC1__RESERVED_L			29U
+#define XHC_PORTSC1__RESERVED_R			28U
+#define XHC_PORTSC1_WIDTH			32U
+#define XHC_PORTSC1__WIDTH			32U
+#define XHC_PORTSC1_ALL_L			31U
+#define XHC_PORTSC1_ALL_R			0U
+#define XHC_PORTSC1__ALL_L			31U
+#define XHC_PORTSC1__ALL_R			0U
+#define XHC_PORTSC1_DATAMASK			0xcfffffffU
+#define XHC_PORTSC1_RDWRMASK			0x30000000U
+#define XHC_PORTSC1_RESETVALUE			0x000000a0U
+
+#define XHC_PORTPM1_OFFSET			0x424U
+#define XHC_PORTPM1_BASE			0x424U
+#define XHC_PORTPM1__reserved_L			31U
+#define XHC_PORTPM1__reserved_R			17U
+#define XHC_PORTPM1__reserved_WIDTH		15U
+#define XHC_PORTPM1__reserved_RESETVALUE	0x0U
+#define XHC_PORTPM1__FLA			16U
+#define XHC_PORTPM1__FLA_L			16U
+#define XHC_PORTPM1__FLA_R			16U
+#define XHC_PORTPM1__FLA_WIDTH			1U
+#define XHC_PORTPM1__FLA_RESETVALUE		0x0U
+#define XHC_PORTPM1__U2T_L			15U
+#define XHC_PORTPM1__U2T_R			8U
+#define XHC_PORTPM1__U2T_WIDTH			8U
+#define XHC_PORTPM1__U2T_RESETVALUE		0x00U
+#define XHC_PORTPM1__U1T_L			7U
+#define XHC_PORTPM1__U1T_R			0U
+#define XHC_PORTPM1__U1T_WIDTH			8U
+#define XHC_PORTPM1__U1T_RESETVALUE		0x00U
+#define XHC_PORTPM1_WIDTH			32U
+#define XHC_PORTPM1__WIDTH			32U
+#define XHC_PORTPM1_ALL_L			31U
+#define XHC_PORTPM1_ALL_R			0U
+#define XHC_PORTPM1__ALL_L			31U
+#define XHC_PORTPM1__ALL_R			0U
+#define XHC_PORTPM1_DATAMASK			0xffffffffU
+#define XHC_PORTPM1_RDWRMASK			0x00000000U
+#define XHC_PORTPM1_RESETVALUE			0x00000000U
+
+#define XHC_PORTLC1_OFFSET			0x428U
+#define XHC_PORTLC1_BASE			0x428U
+#define XHC_PORTLC1__reserved_L			31U
+#define XHC_PORTLC1__reserved_R			0U
+#define XHC_PORTLC1__reserved_WIDTH		32U
+#define XHC_PORTLC1__reserved_RESETVALUE	0x00000000U
+#define XHC_PORTLC1_WIDTH			32U
+#define XHC_PORTLC1__WIDTH			32U
+#define XHC_PORTLC1_ALL_L			31U
+#define XHC_PORTLC1_ALL_R			0U
+#define XHC_PORTLC1__ALL_L			31U
+#define XHC_PORTLC1__ALL_R			0U
+#define XHC_PORTLC1_DATAMASK			0xffffffffU
+#define XHC_PORTLC1_RDWRMASK			0x00000000U
+#define XHC_PORTLC1_RESETVALUE			0x00000000U
+
+#define XHC_PORTSC2_OFFSET			0x430U
+#define XHC_PORTSC2_BASE			0x430U
+#define XHC_PORTSC2__WPR			31U
+#define XHC_PORTSC2__WPR_L			31U
+#define XHC_PORTSC2__WPR_R			31U
+#define XHC_PORTSC2__WPR_WIDTH			1U
+#define XHC_PORTSC2__WPR_RESETVALUE		0x0U
+#define XHC_PORTSC2__DNR			30U
+#define XHC_PORTSC2__DNR_L			30U
+#define XHC_PORTSC2__DNR_R			30U
+#define XHC_PORTSC2__DNR_WIDTH			1U
+#define XHC_PORTSC2__DNR_RESETVALUE		0x0U
+#define XHC_PORTSC2__WOE			27U
+#define XHC_PORTSC2__WOE_L			27U
+#define XHC_PORTSC2__WOE_R			27U
+#define XHC_PORTSC2__WOE_WIDTH			1U
+#define XHC_PORTSC2__WOE_RESETVALUE		0x0U
+#define XHC_PORTSC2__WDE			26U
+#define XHC_PORTSC2__WDE_L			26U
+#define XHC_PORTSC2__WDE_R			26U
+#define XHC_PORTSC2__WDE_WIDTH			1U
+#define XHC_PORTSC2__WDE_RESETVALUE		0x0U
+#define XHC_PORTSC2__WCE			25U
+#define XHC_PORTSC2__WCE_L			25U
+#define XHC_PORTSC2__WCE_R			25U
+#define XHC_PORTSC2__WCE_WIDTH			1U
+#define XHC_PORTSC2__WCE_RESETVALUE		0x0U
+#define XHC_PORTSC2__CAS			24U
+#define XHC_PORTSC2__CAS_L			24U
+#define XHC_PORTSC2__CAS_R			24U
+#define XHC_PORTSC2__CAS_WIDTH			1U
+#define XHC_PORTSC2__CAS_RESETVALUE		0x0U
+#define XHC_PORTSC2__CEC			23U
+#define XHC_PORTSC2__CEC_L			23U
+#define XHC_PORTSC2__CEC_R			23U
+#define XHC_PORTSC2__CEC_WIDTH			1U
+#define XHC_PORTSC2__CEC_RESETVALUE		0x0U
+#define XHC_PORTSC2__PLC			22U
+#define XHC_PORTSC2__PLC_L			22U
+#define XHC_PORTSC2__PLC_R			22U
+#define XHC_PORTSC2__PLC_WIDTH			1U
+#define XHC_PORTSC2__PLC_RESETVALUE		0x0U
+#define XHC_PORTSC2__PRC			21U
+#define XHC_PORTSC2__PRC_L			21U
+#define XHC_PORTSC2__PRC_R			21U
+#define XHC_PORTSC2__PRC_WIDTH			1U
+#define XHC_PORTSC2__PRC_RESETVALUE		0x0U
+#define XHC_PORTSC2__OCC			20U
+#define XHC_PORTSC2__OCC_L			20U
+#define XHC_PORTSC2__OCC_R			20U
+#define XHC_PORTSC2__OCC_WIDTH			1U
+#define XHC_PORTSC2__OCC_RESETVALUE		0x0U
+#define XHC_PORTSC2__WRC			19U
+#define XHC_PORTSC2__WRC_L			19U
+#define XHC_PORTSC2__WRC_R			19U
+#define XHC_PORTSC2__WRC_WIDTH			1U
+#define XHC_PORTSC2__WRC_RESETVALUE		0x0U
+#define XHC_PORTSC2__PEC			18U
+#define XHC_PORTSC2__PEC_L			18U
+#define XHC_PORTSC2__PEC_R			18U
+#define XHC_PORTSC2__PEC_WIDTH			1U
+#define XHC_PORTSC2__PEC_RESETVALUE		0x0U
+#define XHC_PORTSC2__CSC			17U
+#define XHC_PORTSC2__CSC_L			17U
+#define XHC_PORTSC2__CSC_R			17U
+#define XHC_PORTSC2__CSC_WIDTH			1U
+#define XHC_PORTSC2__CSC_RESETVALUE		0x0U
+#define XHC_PORTSC2__LWS			16U
+#define XHC_PORTSC2__LWS_L			16U
+#define XHC_PORTSC2__LWS_R			16U
+#define XHC_PORTSC2__LWS_WIDTH			1U
+#define XHC_PORTSC2__LWS_RESETVALUE		0x0U
+#define XHC_PORTSC2__PIC_L			15U
+#define XHC_PORTSC2__PIC_R			14U
+#define XHC_PORTSC2__PIC_WIDTH			2U
+#define XHC_PORTSC2__PIC_RESETVALUE		0x0U
+#define XHC_PORTSC2__PS_L			13U
+#define XHC_PORTSC2__PS_R			10U
+#define XHC_PORTSC2__PS_WIDTH			4U
+#define XHC_PORTSC2__PS_RESETVALUE		0x0U
+#define XHC_PORTSC2__PP				9U
+#define XHC_PORTSC2__PP_L			9U
+#define XHC_PORTSC2__PP_R			9U
+#define XHC_PORTSC2__PP_WIDTH			1U
+#define XHC_PORTSC2__PP_RESETVALUE		0x0U
+#define XHC_PORTSC2__PLS_L			8U
+#define XHC_PORTSC2__PLS_R			5U
+#define XHC_PORTSC2__PLS_WIDTH			4U
+#define XHC_PORTSC2__PLS_RESETVALUE		0x5U
+
+#define XHC_PORTSC2__PRST_L			4U
+#define XHC_PORTSC2__PRST_R			4U
+#define XHC_PORTSC2__PRST_WIDTH			1U
+#define XHC_PORTSC2__PRST_RESETVALUE		0x0U
+#define XHC_PORTSC2__OCA			3U
+#define XHC_PORTSC2__OCA_L			3U
+#define XHC_PORTSC2__OCA_R			3U
+#define XHC_PORTSC2__OCA_WIDTH			1U
+#define XHC_PORTSC2__OCA_RESETVALUE		0x0U
+#define XHC_PORTSC2__reserved			2U
+#define XHC_PORTSC2__reserved_L			2U
+#define XHC_PORTSC2__reserved_R			2U
+#define XHC_PORTSC2__reserved_WIDTH		1U
+#define XHC_PORTSC2__reserved_RESETVALUE	0x0U
+#define XHC_PORTSC2__PED			1U
+#define XHC_PORTSC2__PED_L			1U
+#define XHC_PORTSC2__PED_R			1U
+#define XHC_PORTSC2__PED_WIDTH			1U
+#define XHC_PORTSC2__PED_RESETVALUE		0x0U
+#define XHC_PORTSC2__CCS			0U
+#define XHC_PORTSC2__CCS_L			0U
+#define XHC_PORTSC2__CCS_R			0U
+#define XHC_PORTSC2__CCS_WIDTH			1U
+#define XHC_PORTSC2__CCS_RESETVALUE		0x0U
+#define XHC_PORTSC2__RESERVED_L			29U
+#define XHC_PORTSC2__RESERVED_R			28U
+#define XHC_PORTSC2_WIDTH			32U
+#define XHC_PORTSC2__WIDTH			32U
+#define XHC_PORTSC2_ALL_L			31U
+#define XHC_PORTSC2_ALL_R			0U
+#define XHC_PORTSC2__ALL_L			31U
+#define XHC_PORTSC2__ALL_R			0U
+#define XHC_PORTSC2_DATAMASK			0xcfffffffU
+#define XHC_PORTSC2_RDWRMASK			0x30000000U
+#define XHC_PORTSC2_RESETVALUE			0x000000a0U
+
+#define XHC_PORTPM2_OFFSET			0x434U
+#define XHC_PORTPM2_BASE			0x434U
+#define XHC_PORTPM2__PTC_L			31U
+#define XHC_PORTPM2__PTC_R			28U
+#define XHC_PORTPM2__PTC_WIDTH			4U
+#define XHC_PORTPM2__PTC_RESETVALUE		0x0U
+#define XHC_PORTPM2__reserved_L			27U
+#define XHC_PORTPM2__reserved_R			17U
+#define XHC_PORTPM2__reserved_WIDTH		11U
+#define XHC_PORTPM2__reserved_RESETVALUE	0x0U
+#define XHC_PORTPM2__HLE			16U
+#define XHC_PORTPM2__HLE_L			16U
+#define XHC_PORTPM2__HLE_R			16U
+#define XHC_PORTPM2__HLE_WIDTH			1U
+#define XHC_PORTPM2__HLE_RESETVALUE		0x0U
+#define XHC_PORTPM2__L1DS_L			15U
+#define XHC_PORTPM2__L1DS_R			8U
+#define XHC_PORTPM2__L1DS_WIDTH			8U
+#define XHC_PORTPM2__L1DS_RESETVALUE		0x00U
+#define XHC_PORTPM2__BESL_L			7U
+#define XHC_PORTPM2__BESL_R			4U
+#define XHC_PORTPM2__BESL_WIDTH			4U
+#define XHC_PORTPM2__BESL_RESETVALUE		0x0U
+#define XHC_PORTPM2__RWE			3U
+#define XHC_PORTPM2__RWE_L			3U
+#define XHC_PORTPM2__RWE_R			3U
+#define XHC_PORTPM2__RWE_WIDTH			1U
+#define XHC_PORTPM2__RWE_RESETVALUE		0x0U
+#define XHC_PORTPM2__L1S_L			2U
+#define XHC_PORTPM2__L1S_R			0U
+#define XHC_PORTPM2__L1S_WIDTH			3U
+#define XHC_PORTPM2__L1S_RESETVALUE		0x0U
+#define XHC_PORTPM2_WIDTH			32U
+#define XHC_PORTPM2__WIDTH			32U
+#define XHC_PORTPM2_ALL_L			31U
+#define XHC_PORTPM2_ALL_R			0U
+#define XHC_PORTPM2__ALL_L			31U
+#define XHC_PORTPM2__ALL_R			0U
+#define XHC_PORTPM2_DATAMASK			0xffffffffU
+#define XHC_PORTPM2_RDWRMASK			0x00000000U
+#define XHC_PORTPM2_RESETVALUE			0x00000000U
+
+#define XHC_PORTLC2_OFFSET			0x43cU
+#define XHC_PORTLC2_BASE			0x43cU
+#define XHC_PORTLC2__reserved_L			31U
+#define XHC_PORTLC2__reserved_R			14U
+#define XHC_PORTLC2__reserved_WIDTH		18U
+#define XHC_PORTLC2__reserved_RESETVALUE	0x0U
+#define XHC_PORTLC2__BESLD_L			13U
+#define XHC_PORTLC2__BESLD_R			10U
+#define XHC_PORTLC2__BESLD_WIDTH		4U
+#define XHC_PORTLC2__BESLD_RESETVALUE		0x0U
+#define XHC_PORTLC2__L1T_L			9U
+#define XHC_PORTLC2__L1T_R			2U
+#define XHC_PORTLC2__L1T_WIDTH			8U
+#define XHC_PORTLC2__L1T_RESETVALUE		0x00U
+#define XHC_PORTLC2__HIRDM_L			1U
+#define XHC_PORTLC2__HIRDM_R			0U
+#define XHC_PORTLC2__HIRDM_WIDTH		2U
+#define XHC_PORTLC2__HIRDM_RESETVALUE		0x0U
+#define XHC_PORTLC2_WIDTH			32U
+#define XHC_PORTLC2__WIDTH			32U
+#define XHC_PORTLC2_ALL_L			31U
+#define XHC_PORTLC2_ALL_R			0U
+#define XHC_PORTLC2__ALL_L			31U
+#define XHC_PORTLC2__ALL_R			0U
+#define XHC_PORTLC2_DATAMASK			0xffffffffU
+#define XHC_PORTLC2_RDWRMASK			0x00000000U
+#define XHC_PORTLC2_RESETVALUE			0x00000000U
+
+#define XHC_PORTSC3_OFFSET			0x440U
+#define XHC_PORTSC3_BASE			0x440U
+#define XHC_PORTSC3__WPR			31U
+#define XHC_PORTSC3__WPR_L			31U
+#define XHC_PORTSC3__WPR_R			31U
+#define XHC_PORTSC3__WPR_WIDTH			1U
+#define XHC_PORTSC3__WPR_RESETVALUE		0x0U
+#define XHC_PORTSC3__DNR			30U
+#define XHC_PORTSC3__DNR_L			30U
+#define XHC_PORTSC3__DNR_R			30U
+#define XHC_PORTSC3__DNR_WIDTH			1U
+#define XHC_PORTSC3__DNR_RESETVALUE		0x0U
+#define XHC_PORTSC3__WOE			27U
+#define XHC_PORTSC3__WOE_L			27U
+#define XHC_PORTSC3__WOE_R			27U
+#define XHC_PORTSC3__WOE_WIDTH			1U
+#define XHC_PORTSC3__WOE_RESETVALUE		0x0U
+#define XHC_PORTSC3__WDE			26U
+#define XHC_PORTSC3__WDE_L			26U
+#define XHC_PORTSC3__WDE_R			26U
+#define XHC_PORTSC3__WDE_WIDTH			1U
+#define XHC_PORTSC3__WDE_RESETVALUE		0x0U
+#define XHC_PORTSC3__WCE			25U
+#define XHC_PORTSC3__WCE_L			25U
+#define XHC_PORTSC3__WCE_R			25U
+#define XHC_PORTSC3__WCE_WIDTH			1U
+#define XHC_PORTSC3__WCE_RESETVALUE		0x0U
+#define XHC_PORTSC3__CAS			24U
+#define XHC_PORTSC3__CAS_L			24U
+#define XHC_PORTSC3__CAS_R			24U
+#define XHC_PORTSC3__CAS_WIDTH			1U
+#define XHC_PORTSC3__CAS_RESETVALUE		0x0U
+#define XHC_PORTSC3__CEC			23U
+#define XHC_PORTSC3__CEC_L			23U
+#define XHC_PORTSC3__CEC_R			23U
+#define XHC_PORTSC3__CEC_WIDTH			1U
+#define XHC_PORTSC3__CEC_RESETVALUE		0x0U
+#define XHC_PORTSC3__PLC			22U
+#define XHC_PORTSC3__PLC_L			22U
+#define XHC_PORTSC3__PLC_R			22U
+#define XHC_PORTSC3__PLC_WIDTH			1U
+#define XHC_PORTSC3__PLC_RESETVALUE		0x0U
+#define XHC_PORTSC3__PRC			21U
+#define XHC_PORTSC3__PRC_L			21U
+#define XHC_PORTSC3__PRC_R			21U
+#define XHC_PORTSC3__PRC_WIDTH			1U
+#define XHC_PORTSC3__PRC_RESETVALUE		0x0U
+#define XHC_PORTSC3__OCC			20U
+#define XHC_PORTSC3__OCC_L			20U
+#define XHC_PORTSC3__OCC_R			20U
+#define XHC_PORTSC3__OCC_WIDTH			1U
+#define XHC_PORTSC3__OCC_RESETVALUE		0x0U
+#define XHC_PORTSC3__WRC			19U
+#define XHC_PORTSC3__WRC_L			19U
+#define XHC_PORTSC3__WRC_R			19U
+#define XHC_PORTSC3__WRC_WIDTH			1U
+#define XHC_PORTSC3__WRC_RESETVALUE		0x0U
+#define XHC_PORTSC3__PEC			18U
+#define XHC_PORTSC3__PEC_L			18U
+#define XHC_PORTSC3__PEC_R			18U
+#define XHC_PORTSC3__PEC_WIDTH			1U
+#define XHC_PORTSC3__PEC_RESETVALUE		0x0U
+#define XHC_PORTSC3__CSC			17U
+#define XHC_PORTSC3__CSC_L			17U
+#define XHC_PORTSC3__CSC_R			17U
+#define XHC_PORTSC3__CSC_WIDTH			1U
+#define XHC_PORTSC3__CSC_RESETVALUE		0x0U
+#define XHC_PORTSC3__LWS			16U
+#define XHC_PORTSC3__LWS_L			16U
+#define XHC_PORTSC3__LWS_R			16U
+#define XHC_PORTSC3__LWS_WIDTH			1U
+#define XHC_PORTSC3__LWS_RESETVALUE		0x0U
+#define XHC_PORTSC3__PIC_L			15U
+#define XHC_PORTSC3__PIC_R			14U
+#define XHC_PORTSC3__PIC_WIDTH			2U
+#define XHC_PORTSC3__PIC_RESETVALUE		0x0U
+#define XHC_PORTSC3__PS_L			13U
+#define XHC_PORTSC3__PS_R			10U
+#define XHC_PORTSC3__PS_WIDTH			4U
+#define XHC_PORTSC3__PS_RESETVALUE		0x0U
+#define XHC_PORTSC3__PP				9U
+#define XHC_PORTSC3__PP_L			9U
+#define XHC_PORTSC3__PP_R			9U
+#define XHC_PORTSC3__PP_WIDTH			1U
+#define XHC_PORTSC3__PP_RESETVALUE		0x0U
+#define XHC_PORTSC3__PLS_L			8U
+#define XHC_PORTSC3__PLS_R			5U
+#define XHC_PORTSC3__PLS_WIDTH			4U
+#define XHC_PORTSC3__PLS_RESETVALUE		0x5U
+#define XHC_PORTSC3__PR				4U
+#define XHC_PORTSC3__PR_L			4U
+#define XHC_PORTSC3__PR_R			4U
+#define XHC_PORTSC3__PR_WIDTH			1U
+#define XHC_PORTSC3__PR_RESETVALUE		0x0U
+#define XHC_PORTSC3__OCA			3U
+#define XHC_PORTSC3__OCA_L			3U
+#define XHC_PORTSC3__OCA_R			3U
+#define XHC_PORTSC3__OCA_WIDTH			1U
+#define XHC_PORTSC3__OCA_RESETVALUE		0x0U
+#define XHC_PORTSC3__reserved			2U
+#define XHC_PORTSC3__reserved_L			2U
+#define XHC_PORTSC3__reserved_R			2U
+#define XHC_PORTSC3__reserved_WIDTH		1U
+#define XHC_PORTSC3__reserved_RESETVALUE	0x0U
+#define XHC_PORTSC3__PED			1U
+#define XHC_PORTSC3__PED_L			1U
+#define XHC_PORTSC3__PED_R			1U
+#define XHC_PORTSC3__PED_WIDTH			1U
+#define XHC_PORTSC3__PED_RESETVALUE		0x0U
+#define XHC_PORTSC3__CCS			0U
+#define XHC_PORTSC3__CCS_L			0U
+#define XHC_PORTSC3__CCS_R			0U
+#define XHC_PORTSC3__CCS_WIDTH			1U
+#define XHC_PORTSC3__CCS_RESETVALUE		0x0U
+#define XHC_PORTSC3__RESERVED_L			29U
+#define XHC_PORTSC3__RESERVED_R			28U
+#define XHC_PORTSC3_WIDTH			32U
+#define XHC_PORTSC3__WIDTH			32U
+#define XHC_PORTSC3_ALL_L			31U
+#define XHC_PORTSC3_ALL_R			0U
+#define XHC_PORTSC3__ALL_L			31U
+#define XHC_PORTSC3__ALL_R			0U
+#define XHC_PORTSC3_DATAMASK			0xcfffffffU
+#define XHC_PORTSC3_RDWRMASK			0x30000000U
+#define XHC_PORTSC3_RESETVALUE			0x000000a0U
+
+#define XHC_PORTPM3_OFFSET			0x444U
+#define XHC_PORTPM3_BASE			0x444U
+#define XHC_PORTPM3__PTC_L			31U
+#define XHC_PORTPM3__PTC_R			28U
+#define XHC_PORTPM3__PTC_WIDTH			4U
+#define XHC_PORTPM3__PTC_RESETVALUE		0x0U
+#define XHC_PORTPM3__reserved_L			27U
+#define XHC_PORTPM3__reserved_R			17U
+#define XHC_PORTPM3__reserved_WIDTH		11U
+#define XHC_PORTPM3__reserved_RESETVALUE	0x0U
+#define XHC_PORTPM3__HLE			16U
+#define XHC_PORTPM3__HLE_L			16U
+#define XHC_PORTPM3__HLE_R			16U
+#define XHC_PORTPM3__HLE_WIDTH			1U
+#define XHC_PORTPM3__HLE_RESETVALUE		0x0U
+#define XHC_PORTPM3__L1DS_L			15U
+#define XHC_PORTPM3__L1DS_R			8U
+#define XHC_PORTPM3__L1DS_WIDTH			8U
+#define XHC_PORTPM3__L1DS_RESETVALUE		0x00U
+#define XHC_PORTPM3__BESL_L			7U
+#define XHC_PORTPM3__BESL_R			4U
+#define XHC_PORTPM3__BESL_WIDTH			4U
+#define XHC_PORTPM3__BESL_RESETVALUE		0x0U
+#define XHC_PORTPM3__RWE			3U
+#define XHC_PORTPM3__RWE_L			3U
+#define XHC_PORTPM3__RWE_R			3U
+#define XHC_PORTPM3__RWE_WIDTH			1U
+#define XHC_PORTPM3__RWE_RESETVALUE		0x0U
+#define XHC_PORTPM3__L1S_L			2U
+#define XHC_PORTPM3__L1S_R			0U
+#define XHC_PORTPM3__L1S_WIDTH			3U
+#define XHC_PORTPM3__L1S_RESETVALUE		0x0U
+#define XHC_PORTPM3_WIDTH			32U
+#define XHC_PORTPM3__WIDTH			32U
+#define XHC_PORTPM3_ALL_L			31U
+#define XHC_PORTPM3_ALL_R			0U
+#define XHC_PORTPM3__ALL_L			31U
+#define XHC_PORTPM3__ALL_R			0U
+#define XHC_PORTPM3_DATAMASK			0xffffffffU
+#define XHC_PORTPM3_RDWRMASK			0x00000000U
+#define XHC_PORTPM3_RESETVALUE			0x00000000U
+
+#define XHC_PORTLI3_OFFSET			0x44cU
+#define XHC_PORTLI3_BASE			0x44cU
+#define XHC_PORTLI3__reserved_L			31U
+#define XHC_PORTLI3__reserved_R			0U
+#define XHC_PORTLI3__reserved_WIDTH		32U
+#define XHC_PORTLI3__reserved_RESETVALUE	0x00000000U
+#define XHC_PORTLI3_WIDTH			32U
+#define XHC_PORTLI3__WIDTH			32U
+#define XHC_PORTLI3_ALL_L			31U
+#define XHC_PORTLI3_ALL_R			0U
+#define XHC_PORTLI3__ALL_L			31U
+#define XHC_PORTLI3__ALL_R			0U
+#define XHC_PORTLI3_DATAMASK			0xffffffffU
+#define XHC_PORTLI3_RDWRMASK			0x00000000U
+#define XHC_PORTLI3_RESETVALUE			0x00000000U
+
+#define XHC_MFINDEX_OFFSET			0x4a0U
+#define XHC_MFINDEX_BASE			0x4a0U
+#define XHC_MFINDEX__reserved_L			31U
+#define XHC_MFINDEX__reserved_R			14U
+#define XHC_MFINDEX__reserved_WIDTH		18U
+#define XHC_MFINDEX__reserved_RESETVALUE	0x0U
+#define XHC_MFINDEX__MFI_L			13U
+#define XHC_MFINDEX__MFI_R			0U
+#define XHC_MFINDEX__MFI_WIDTH			14U
+#define XHC_MFINDEX__MFI_RESETVALUE		0x0U
+#define XHC_MFINDEX_WIDTH			32U
+#define XHC_MFINDEX__WIDTH			32U
+#define XHC_MFINDEX_ALL_L			31U
+#define XHC_MFINDEX_ALL_R			0U
+#define XHC_MFINDEX__ALL_L			31U
+#define XHC_MFINDEX__ALL_R			0U
+#define XHC_MFINDEX_DATAMASK			0xffffffffU
+#define XHC_MFINDEX_RDWRMASK			0x00000000U
+#define XHC_MFINDEX_RESETVALUE			0x00000000U
+
+#define XHC_IMAN0_OFFSET			0x4c0U
+#define XHC_IMAN0_BASE				0x4c0U
+#define XHC_IMAN0__reserved_L			31U
+#define XHC_IMAN0__reserved_R			2U
+#define XHC_IMAN0__reserved_WIDTH		30U
+#define XHC_IMAN0__reserved_RESETVALUE		0x0U
+#define XHC_IMAN0__IE				1U
+#define XHC_IMAN0__IE_L				1U
+#define XHC_IMAN0__IE_R				1U
+#define XHC_IMAN0__IE_WIDTH			1U
+#define XHC_IMAN0__IE_RESETVALUE		0x0U
+#define XHC_IMAN0__IP				0U
+#define XHC_IMAN0__IP_L				0U
+#define XHC_IMAN0__IP_R				0U
+#define XHC_IMAN0__IP_WIDTH			1U
+#define XHC_IMAN0__IP_RESETVALUE		0x0U
+#define XHC_IMAN0_WIDTH				32U
+#define XHC_IMAN0__WIDTH			32U
+#define XHC_IMAN0_ALL_L				31U
+#define XHC_IMAN0_ALL_R				0U
+#define XHC_IMAN0__ALL_L			31U
+#define XHC_IMAN0__ALL_R			0U
+#define XHC_IMAN0_DATAMASK			0xffffffffU
+#define XHC_IMAN0_RDWRMASK			0x00000000U
+#define XHC_IMAN0_RESETVALUE			0x00000000U
+
+#define XHC_IMOD0_OFFSET			0x4c4U
+#define XHC_IMOD0_BASE				0x4c4U
+#define XHC_IMOD0__IMODC_L			31U
+#define XHC_IMOD0__IMODC_R			16U
+#define XHC_IMOD0__IMODC_WIDTH			16U
+#define XHC_IMOD0__IMODC_RESETVALUE		0x0000U
+#define XHC_IMOD0__IMODI_L			15U
+#define XHC_IMOD0__IMODI_R			0U
+#define XHC_IMOD0__IMODI_WIDTH			16U
+#define XHC_IMOD0__IMODI_RESETVALUE		0x4000U
+#define XHC_IMOD0_WIDTH				32U
+#define XHC_IMOD0__WIDTH			32U
+#define XHC_IMOD0_ALL_L				31U
+#define XHC_IMOD0_ALL_R				0U
+#define XHC_IMOD0__ALL_L			31U
+#define XHC_IMOD0__ALL_R			0U
+#define XHC_IMOD0_DATAMASK			0xffffffffU
+#define XHC_IMOD0_RDWRMASK			0x00000000U
+#define XHC_IMOD0_RESETVALUE			0x00004000U
+
+#define XHC_ERSTSZ0_OFFSET			0x4c8U
+#define XHC_ERSTSZ0_BASE			0x4c8U
+#define XHC_ERSTSZ0__reserved_L			31U
+#define XHC_ERSTSZ0__reserved_R			16U
+#define XHC_ERSTSZ0__reserved_WIDTH		16U
+#define XHC_ERSTSZ0__reserved_RESETVALUE	0x0000U
+#define XHC_ERSTSZ0__TSZ_L			15U
+#define XHC_ERSTSZ0__TSZ_R			0U
+#define XHC_ERSTSZ0__TSZ_WIDTH			16U
+#define XHC_ERSTSZ0__TSZ_RESETVALUE		0x0000U
+#define XHC_ERSTSZ0_WIDTH			32U
+#define XHC_ERSTSZ0__WIDTH			32U
+#define XHC_ERSTSZ0_ALL_L			31U
+#define XHC_ERSTSZ0_ALL_R			0U
+#define XHC_ERSTSZ0__ALL_L			31U
+#define XHC_ERSTSZ0__ALL_R			0U
+#define XHC_ERSTSZ0_DATAMASK			0xffffffffU
+#define XHC_ERSTSZ0_RDWRMASK			0x00000000U
+#define XHC_ERSTSZ0_RESETVALUE			0x00000000U
+
+#define XHC_ERSTBAL0_OFFSET			0x4d0U
+#define XHC_ERSTBAL0_BASE			0x4d0U
+#define XHC_ERSTBAL0__BAL_L			31U
+#define XHC_ERSTBAL0__BAL_R			4U
+#define XHC_ERSTBAL0__BAL_WIDTH			28U
+#define XHC_ERSTBAL0__BAL_RESETVALUE		0x0000000U
+#define XHC_ERSTBAL0__reserved_L		3U
+#define XHC_ERSTBAL0__reserved_R		0U
+#define XHC_ERSTBAL0__reserved_WIDTH		4U
+#define XHC_ERSTBAL0__reserved_RESETVALUE	0x0U
+#define XHC_ERSTBAL0_WIDTH			32U
+#define XHC_ERSTBAL0__WIDTH			32U
+#define XHC_ERSTBAL0_ALL_L			31U
+#define XHC_ERSTBAL0_ALL_R			0U
+#define XHC_ERSTBAL0__ALL_L			31U
+#define XHC_ERSTBAL0__ALL_R			0U
+#define XHC_ERSTBAL0_DATAMASK			0xffffffffU
+#define XHC_ERSTBAL0_RDWRMASK			0x00000000U
+#define XHC_ERSTBAL0_RESETVALUE			0x00000000U
+
+#define XHC_ERSTBAH0_OFFSET			0x4d4U
+#define XHC_ERSTBAH0_BASE			0x4d4U
+#define XHC_ERSTBAH0__BAH_L			31U
+#define XHC_ERSTBAH0__BAH_R			0U
+#define XHC_ERSTBAH0__BAH_WIDTH			32U
+#define XHC_ERSTBAH0__BAH_RESETVALUE		0x00000000U
+#define XHC_ERSTBAH0_WIDTH			32U
+#define XHC_ERSTBAH0__WIDTH			32U
+#define XHC_ERSTBAH0_ALL_L			31U
+#define XHC_ERSTBAH0_ALL_R			0U
+#define XHC_ERSTBAH0__ALL_L			31U
+#define XHC_ERSTBAH0__ALL_R			0U
+#define XHC_ERSTBAH0_DATAMASK			0xffffffffU
+#define XHC_ERSTBAH0_RDWRMASK			0x00000000U
+#define XHC_ERSTBAH0_RESETVALUE			0x00000000U
+
+#define XHC_ERDPL0_OFFSET			0x4d8U
+#define XHC_ERDPL0_BASE				0x4d8U
+#define XHC_ERDPL0__DPL_L			31U
+#define XHC_ERDPL0__DPL_R			4U
+#define XHC_ERDPL0__DPL_WIDTH			28U
+#define XHC_ERDPL0__DPL_RESETVALUE		0x0000000U
+#define XHC_ERDPL0__EHB				3U
+#define XHC_ERDPL0__EHB_L			3U
+#define XHC_ERDPL0__EHB_R			3U
+#define XHC_ERDPL0__EHB_WIDTH			1U
+#define XHC_ERDPL0__EHB_RESETVALUE		0x0U
+#define XHC_ERDPL0__DESI_L			2U
+#define XHC_ERDPL0__DESI_R			0U
+#define XHC_ERDPL0__DESI_WIDTH			3U
+#define XHC_ERDPL0__DESI_RESETVALUE		0x0U
+#define XHC_ERDPL0_WIDTH			32U
+#define XHC_ERDPL0__WIDTH			32U
+#define XHC_ERDPL0_ALL_L			31U
+#define XHC_ERDPL0_ALL_R			0U
+#define XHC_ERDPL0__ALL_L			31U
+#define XHC_ERDPL0__ALL_R			0U
+#define XHC_ERDPL0_DATAMASK			0xffffffffU
+#define XHC_ERDPL0_RDWRMASK			0x00000000U
+#define XHC_ERDPL0_RESETVALUE			0x00000000U
+
+#define XHC_ERDPH0_OFFSET			0x4dcU
+#define XHC_ERDPH0_BASE				0x4dcU
+#define XHC_ERDPH0__DPH_L			31U
+#define XHC_ERDPH0__DPH_R			0U
+#define XHC_ERDPH0__DPH_WIDTH			32U
+#define XHC_ERDPH0__DPH_RESETVALUE		0x00000000U
+#define XHC_ERDPH0_WIDTH			32U
+#define XHC_ERDPH0__WIDTH			32U
+#define XHC_ERDPH0_ALL_L			31U
+#define XHC_ERDPH0_ALL_R			0U
+#define XHC_ERDPH0__ALL_L			31U
+#define XHC_ERDPH0__ALL_R			0U
+#define XHC_ERDPH0_DATAMASK			0xffffffffU
+#define XHC_ERDPH0_RDWRMASK			0x00000000U
+#define XHC_ERDPH0_RESETVALUE			0x00000000U
+
+#define XHC_IMAN1_OFFSET			0x4e0U
+#define XHC_IMAN1_BASE				0x4e0U
+#define XHC_IMAN1__reserved_L			31U
+#define XHC_IMAN1__reserved_R			2U
+#define XHC_IMAN1__reserved_WIDTH		30U
+#define XHC_IMAN1__reserved_RESETVALUE		0x0U
+#define XHC_IMAN1__IE				1U
+#define XHC_IMAN1__IE_L				1U
+#define XHC_IMAN1__IE_R				1U
+#define XHC_IMAN1__IE_WIDTH			1U
+#define XHC_IMAN1__IE_RESETVALUE		0x0U
+#define XHC_IMAN1__IP				0U
+#define XHC_IMAN1__IP_L				0U
+#define XHC_IMAN1__IP_R				0U
+#define XHC_IMAN1__IP_WIDTH			1U
+#define XHC_IMAN1__IP_RESETVALUE		0x0U
+#define XHC_IMAN1_WIDTH				32U
+#define XHC_IMAN1__WIDTH			32U
+#define XHC_IMAN1_ALL_L				31U
+#define XHC_IMAN1_ALL_R				0U
+#define XHC_IMAN1__ALL_L			31U
+#define XHC_IMAN1__ALL_R			0U
+#define XHC_IMAN1_DATAMASK			0xffffffffU
+#define XHC_IMAN1_RDWRMASK			0x00000000U
+#define XHC_IMAN1_RESETVALUE			0x00000000U
+
+#define XHC_IMOD1_OFFSET			0x4e4U
+#define XHC_IMOD1_BASE				0x4e4U
+#define XHC_IMOD1__IMODC_L			31U
+#define XHC_IMOD1__IMODC_R			16U
+#define XHC_IMOD1__IMODC_WIDTH			16U
+#define XHC_IMOD1__IMODC_RESETVALUE		0x0000U
+#define XHC_IMOD1__IMODI_L			15U
+#define XHC_IMOD1__IMODI_R			0U
+#define XHC_IMOD1__IMODI_WIDTH			16U
+#define XHC_IMOD1__IMODI_RESETVALUE		0x4000U
+#define XHC_IMOD1_WIDTH				32U
+#define XHC_IMOD1__WIDTH			32U
+#define XHC_IMOD1_ALL_L				31U
+#define XHC_IMOD1_ALL_R				0U
+#define XHC_IMOD1__ALL_L			31U
+#define XHC_IMOD1__ALL_R			0U
+#define XHC_IMOD1_DATAMASK			0xffffffffU
+#define XHC_IMOD1_RDWRMASK			0x00000000U
+#define XHC_IMOD1_RESETVALUE			0x00004000U
+
+#define XHC_ERSTSZ1_OFFSET			0x4e8U
+#define XHC_ERSTSZ1_BASE			0x4e8U
+#define XHC_ERSTSZ1__reserved_L			31U
+#define XHC_ERSTSZ1__reserved_R			16U
+#define XHC_ERSTSZ1__reserved_WIDTH		16U
+#define XHC_ERSTSZ1__reserved_RESETVALUE	0x0000U
+#define XHC_ERSTSZ1__TSZ_L			15U
+#define XHC_ERSTSZ1__TSZ_R			0U
+#define XHC_ERSTSZ1__TSZ_WIDTH			16U
+#define XHC_ERSTSZ1__TSZ_RESETVALUE		0x0000U
+#define XHC_ERSTSZ1_WIDTH			32U
+#define XHC_ERSTSZ1__WIDTH			32U
+#define XHC_ERSTSZ1_ALL_L			31U
+#define XHC_ERSTSZ1_ALL_R			0U
+#define XHC_ERSTSZ1__ALL_L			31U
+#define XHC_ERSTSZ1__ALL_R			0U
+#define XHC_ERSTSZ1_DATAMASK			0xffffffffU
+#define XHC_ERSTSZ1_RDWRMASK			0x00000000U
+#define XHC_ERSTSZ1_RESETVALUE			0x00000000U
+
+#define XHC_ERSTBAL1_OFFSET			0x4f0U
+#define XHC_ERSTBAL1_BASE			0x4f0U
+#define XHC_ERSTBAL1__BAL_L			31U
+#define XHC_ERSTBAL1__BAL_R			4U
+#define XHC_ERSTBAL1__BAL_WIDTH			28U
+#define XHC_ERSTBAL1__BAL_RESETVALUE		0x0000000U
+#define XHC_ERSTBAL1__reserved_L		3U
+#define XHC_ERSTBAL1__reserved_R		0U
+#define XHC_ERSTBAL1__reserved_WIDTH		4U
+#define XHC_ERSTBAL1__reserved_RESETVALUE	0x0U
+#define XHC_ERSTBAL1_WIDTH			32U
+#define XHC_ERSTBAL1__WIDTH			32U
+#define XHC_ERSTBAL1_ALL_L			31U
+#define XHC_ERSTBAL1_ALL_R			0U
+#define XHC_ERSTBAL1__ALL_L			31U
+#define XHC_ERSTBAL1__ALL_R			0U
+#define XHC_ERSTBAL1_DATAMASK			0xffffffffU
+#define XHC_ERSTBAL1_RDWRMASK			0x00000000U
+#define XHC_ERSTBAL1_RESETVALUE			0x00000000U
+
+#define XHC_ERSTBAH1_OFFSET			0x4f4U
+#define XHC_ERSTBAH1_BASE			0x4f4U
+#define XHC_ERSTBAH1__BAH_L			31U
+#define XHC_ERSTBAH1__BAH_R			0U
+#define XHC_ERSTBAH1__BAH_WIDTH			32U
+#define XHC_ERSTBAH1__BAH_RESETVALUE		0x00000000U
+#define XHC_ERSTBAH1_WIDTH			32U
+#define XHC_ERSTBAH1__WIDTH			32U
+#define XHC_ERSTBAH1_ALL_L			31U
+#define XHC_ERSTBAH1_ALL_R			0U
+#define XHC_ERSTBAH1__ALL_L			31U
+#define XHC_ERSTBAH1__ALL_R			0U
+#define XHC_ERSTBAH1_DATAMASK			0xffffffffU
+#define XHC_ERSTBAH1_RDWRMASK			0x00000000U
+#define XHC_ERSTBAH1_RESETVALUE			0x00000000U
+
+#define XHC_ERDPL1_OFFSET			0x4f8U
+#define XHC_ERDPL1_BASE				0x4f8U
+#define XHC_ERDPL1__DPL_L			31U
+#define XHC_ERDPL1__DPL_R			4U
+#define XHC_ERDPL1__DPL_WIDTH			28U
+#define XHC_ERDPL1__DPL_RESETVALUE		0x0000000U
+#define XHC_ERDPL1__EHB				3U
+#define XHC_ERDPL1__EHB_L			3U
+#define XHC_ERDPL1__EHB_R			3U
+#define XHC_ERDPL1__EHB_WIDTH			1U
+#define XHC_ERDPL1__EHB_RESETVALUE		0x0U
+#define XHC_ERDPL1__DESI_L			2U
+#define XHC_ERDPL1__DESI_R			0U
+#define XHC_ERDPL1__DESI_WIDTH			3U
+#define XHC_ERDPL1__DESI_RESETVALUE		0x0U
+#define XHC_ERDPL1_WIDTH			32U
+#define XHC_ERDPL1__WIDTH			32U
+#define XHC_ERDPL1_ALL_L			31U
+#define XHC_ERDPL1_ALL_R			0U
+#define XHC_ERDPL1__ALL_L			31U
+#define XHC_ERDPL1__ALL_R			0U
+#define XHC_ERDPL1_DATAMASK			0xffffffffU
+#define XHC_ERDPL1_RDWRMASK			0x00000000U
+#define XHC_ERDPL1_RESETVALUE			0x00000000U
+
+#define XHC_ERDPH1_OFFSET			0x4fcU
+#define XHC_ERDPH1_BASE				0x4fcU
+#define XHC_ERDPH1__DPH_L			31U
+#define XHC_ERDPH1__DPH_R			0U
+#define XHC_ERDPH1__DPH_WIDTH			32U
+#define XHC_ERDPH1__DPH_RESETVALUE		0x00000000U
+#define XHC_ERDPH1_WIDTH			32U
+#define XHC_ERDPH1__WIDTH			32U
+#define XHC_ERDPH1_ALL_L			31U
+#define XHC_ERDPH1_ALL_R			0U
+#define XHC_ERDPH1__ALL_L			31U
+#define XHC_ERDPH1__ALL_R			0U
+#define XHC_ERDPH1_DATAMASK			0xffffffffU
+#define XHC_ERDPH1_RDWRMASK			0x00000000U
+#define XHC_ERDPH1_RESETVALUE			0x00000000U
+
+#define XHC_DBLCMD_OFFSET			0x8c0U
+#define XHC_DBLCMD_BASE				0x8c0U
+#define XHC_DBLCMD__SID_L			31U
+#define XHC_DBLCMD__SID_R			16U
+#define XHC_DBLCMD__SID_WIDTH			16U
+#define XHC_DBLCMD__SID_RESETVALUE		0x0000U
+#define XHC_DBLCMD__reserved_L			15U
+#define XHC_DBLCMD__reserved_R			8U
+#define XHC_DBLCMD__reserved_WIDTH		8U
+#define XHC_DBLCMD__reserved_RESETVALUE		0x00U
+#define XHC_DBLCMD__TGT_L			7U
+#define XHC_DBLCMD__TGT_R			0U
+#define XHC_DBLCMD__TGT_WIDTH			8U
+#define XHC_DBLCMD__TGT_RESETVALUE		0x00U
+#define XHC_DBLCMD_WIDTH			32U
+#define XHC_DBLCMD__WIDTH			32U
+#define XHC_DBLCMD_ALL_L			31U
+#define XHC_DBLCMD_ALL_R			0U
+#define XHC_DBLCMD__ALL_L			31U
+#define XHC_DBLCMD__ALL_R			0U
+#define XHC_DBLCMD_DATAMASK			0xffffffffU
+#define XHC_DBLCMD_RDWRMASK			0x00000000U
+#define XHC_DBLCMD_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX1_OFFSET			0x8c4U
+#define XHC_DBLDVX1_BASE			0x8c4U
+#define XHC_DBLDVX1__SID_L			31U
+#define XHC_DBLDVX1__SID_R			16U
+#define XHC_DBLDVX1__SID_WIDTH			16U
+#define XHC_DBLDVX1__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX1__reserved_L			15U
+#define XHC_DBLDVX1__reserved_R			8U
+#define XHC_DBLDVX1__reserved_WIDTH		8U
+#define XHC_DBLDVX1__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX1__TGT_L			7U
+#define XHC_DBLDVX1__TGT_R			0U
+#define XHC_DBLDVX1__TGT_WIDTH			8U
+#define XHC_DBLDVX1__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX1_WIDTH			32U
+#define XHC_DBLDVX1__WIDTH			32U
+#define XHC_DBLDVX1_ALL_L			31U
+#define XHC_DBLDVX1_ALL_R			0U
+#define XHC_DBLDVX1__ALL_L			31U
+#define XHC_DBLDVX1__ALL_R			0U
+#define XHC_DBLDVX1_DATAMASK			0xffffffffU
+#define XHC_DBLDVX1_RDWRMASK			0x00000000U
+#define XHC_DBLDVX1_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX2_OFFSET			0x8c8U
+#define XHC_DBLDVX2_BASE			0x8c8U
+#define XHC_DBLDVX2__SID_L			31U
+#define XHC_DBLDVX2__SID_R			16U
+#define XHC_DBLDVX2__SID_WIDTH			16U
+#define XHC_DBLDVX2__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX2__reserved_L			15U
+#define XHC_DBLDVX2__reserved_R			8U
+#define XHC_DBLDVX2__reserved_WIDTH		8U
+#define XHC_DBLDVX2__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX2__TGT_L			7U
+#define XHC_DBLDVX2__TGT_R			0U
+#define XHC_DBLDVX2__TGT_WIDTH			8U
+#define XHC_DBLDVX2__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX2_WIDTH			32U
+#define XHC_DBLDVX2__WIDTH			32U
+#define XHC_DBLDVX2_ALL_L			31U
+#define XHC_DBLDVX2_ALL_R			0U
+#define XHC_DBLDVX2__ALL_L			31U
+#define XHC_DBLDVX2__ALL_R			0U
+#define XHC_DBLDVX2_DATAMASK			0xffffffffU
+#define XHC_DBLDVX2_RDWRMASK			0x00000000U
+#define XHC_DBLDVX2_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX3_OFFSET			0x8ccU
+#define XHC_DBLDVX3_BASE			0x8ccU
+#define XHC_DBLDVX3__SID_L			31U
+#define XHC_DBLDVX3__SID_R			16U
+#define XHC_DBLDVX3__SID_WIDTH			16U
+#define XHC_DBLDVX3__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX3__reserved_L			15U
+#define XHC_DBLDVX3__reserved_R			8U
+#define XHC_DBLDVX3__reserved_WIDTH		8U
+#define XHC_DBLDVX3__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX3__TGT_L			7U
+#define XHC_DBLDVX3__TGT_R			0U
+#define XHC_DBLDVX3__TGT_WIDTH			8U
+#define XHC_DBLDVX3__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX3_WIDTH			32U
+#define XHC_DBLDVX3__WIDTH			32U
+#define XHC_DBLDVX3_ALL_L			31U
+#define XHC_DBLDVX3_ALL_R			0U
+#define XHC_DBLDVX3__ALL_L			31U
+#define XHC_DBLDVX3__ALL_R			0U
+#define XHC_DBLDVX3_DATAMASK			0xffffffffU
+#define XHC_DBLDVX3_RDWRMASK			0x00000000U
+#define XHC_DBLDVX3_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX4_OFFSET			0x8d0U
+#define XHC_DBLDVX4_BASE			0x8d0U
+#define XHC_DBLDVX4__SID_L			31U
+#define XHC_DBLDVX4__SID_R			16U
+#define XHC_DBLDVX4__SID_WIDTH			16U
+#define XHC_DBLDVX4__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX4__reserved_L			15U
+#define XHC_DBLDVX4__reserved_R			8U
+#define XHC_DBLDVX4__reserved_WIDTH		8U
+#define XHC_DBLDVX4__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX4__TGT_L			7U
+#define XHC_DBLDVX4__TGT_R			0U
+#define XHC_DBLDVX4__TGT_WIDTH			8U
+#define XHC_DBLDVX4__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX4_WIDTH			32U
+#define XHC_DBLDVX4__WIDTH			32U
+#define XHC_DBLDVX4_ALL_L			31U
+#define XHC_DBLDVX4_ALL_R			0U
+#define XHC_DBLDVX4__ALL_L			31U
+#define XHC_DBLDVX4__ALL_R			0U
+#define XHC_DBLDVX4_DATAMASK			0xffffffffU
+#define XHC_DBLDVX4_RDWRMASK			0x00000000U
+#define XHC_DBLDVX4_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX5_OFFSET			0x8d4U
+#define XHC_DBLDVX5_BASE			0x8d4U
+#define XHC_DBLDVX5__SID_L			31U
+#define XHC_DBLDVX5__SID_R			16U
+#define XHC_DBLDVX5__SID_WIDTH			16U
+#define XHC_DBLDVX5__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX5__reserved_L			15U
+#define XHC_DBLDVX5__reserved_R			8U
+#define XHC_DBLDVX5__reserved_WIDTH		8U
+#define XHC_DBLDVX5__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX5__TGT_L			7U
+#define XHC_DBLDVX5__TGT_R			0U
+#define XHC_DBLDVX5__TGT_WIDTH			8U
+#define XHC_DBLDVX5__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX5_WIDTH			32U
+#define XHC_DBLDVX5__WIDTH			32U
+#define XHC_DBLDVX5_ALL_L			31U
+#define XHC_DBLDVX5_ALL_R			0U
+#define XHC_DBLDVX5__ALL_L			31U
+#define XHC_DBLDVX5__ALL_R			0U
+#define XHC_DBLDVX5_DATAMASK			0xffffffffU
+#define XHC_DBLDVX5_RDWRMASK			0x00000000U
+#define XHC_DBLDVX5_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX6_OFFSET			0x8d8U
+#define XHC_DBLDVX6_BASE			0x8d8U
+#define XHC_DBLDVX6__SID_L			31U
+#define XHC_DBLDVX6__SID_R			16U
+#define XHC_DBLDVX6__SID_WIDTH			16U
+#define XHC_DBLDVX6__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX6__reserved_L			15U
+#define XHC_DBLDVX6__reserved_R			8U
+#define XHC_DBLDVX6__reserved_WIDTH		8U
+#define XHC_DBLDVX6__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX6__TGT_L			7U
+#define XHC_DBLDVX6__TGT_R			0U
+#define XHC_DBLDVX6__TGT_WIDTH			8U
+#define XHC_DBLDVX6__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX6_WIDTH			32U
+#define XHC_DBLDVX6__WIDTH			32U
+#define XHC_DBLDVX6_ALL_L			31U
+#define XHC_DBLDVX6_ALL_R			0U
+#define XHC_DBLDVX6__ALL_L			31U
+#define XHC_DBLDVX6__ALL_R			0U
+#define XHC_DBLDVX6_DATAMASK			0xffffffffU
+#define XHC_DBLDVX6_RDWRMASK			0x00000000U
+#define XHC_DBLDVX6_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX7_OFFSET			0x8dcU
+#define XHC_DBLDVX7_BASE			0x8dcU
+#define XHC_DBLDVX7__SID_L			31U
+#define XHC_DBLDVX7__SID_R			16U
+#define XHC_DBLDVX7__SID_WIDTH			16U
+#define XHC_DBLDVX7__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX7__reserved_L			15U
+#define XHC_DBLDVX7__reserved_R			8U
+#define XHC_DBLDVX7__reserved_WIDTH		8U
+#define XHC_DBLDVX7__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX7__TGT_L			7U
+#define XHC_DBLDVX7__TGT_R			0U
+#define XHC_DBLDVX7__TGT_WIDTH			8U
+#define XHC_DBLDVX7__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX7_WIDTH			32U
+#define XHC_DBLDVX7__WIDTH			32U
+#define XHC_DBLDVX7_ALL_L			31U
+#define XHC_DBLDVX7_ALL_R			0U
+#define XHC_DBLDVX7__ALL_L			31U
+#define XHC_DBLDVX7__ALL_R			0U
+#define XHC_DBLDVX7_DATAMASK			0xffffffffU
+#define XHC_DBLDVX7_RDWRMASK			0x00000000U
+#define XHC_DBLDVX7_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX8_OFFSET			0x8e0U
+#define XHC_DBLDVX8_BASE			0x8e0U
+#define XHC_DBLDVX8__SID_L			31U
+#define XHC_DBLDVX8__SID_R			16U
+#define XHC_DBLDVX8__SID_WIDTH			16U
+#define XHC_DBLDVX8__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX8__reserved_L			15U
+#define XHC_DBLDVX8__reserved_R			8U
+#define XHC_DBLDVX8__reserved_WIDTH		8U
+#define XHC_DBLDVX8__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX8__TGT_L			7U
+#define XHC_DBLDVX8__TGT_R			0U
+#define XHC_DBLDVX8__TGT_WIDTH			8U
+#define XHC_DBLDVX8__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX8_WIDTH			32U
+#define XHC_DBLDVX8__WIDTH			32U
+#define XHC_DBLDVX8_ALL_L			31U
+#define XHC_DBLDVX8_ALL_R			0U
+#define XHC_DBLDVX8__ALL_L			31U
+#define XHC_DBLDVX8__ALL_R			0U
+#define XHC_DBLDVX8_DATAMASK			0xffffffffU
+#define XHC_DBLDVX8_RDWRMASK			0x00000000U
+#define XHC_DBLDVX8_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX9_OFFSET			0x8e4U
+#define XHC_DBLDVX9_BASE			0x8e4U
+#define XHC_DBLDVX9__SID_L			31U
+#define XHC_DBLDVX9__SID_R			16U
+#define XHC_DBLDVX9__SID_WIDTH			16U
+#define XHC_DBLDVX9__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX9__reserved_L			15U
+#define XHC_DBLDVX9__reserved_R			8U
+#define XHC_DBLDVX9__reserved_WIDTH		8U
+#define XHC_DBLDVX9__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX9__TGT_L			7U
+#define XHC_DBLDVX9__TGT_R			0U
+#define XHC_DBLDVX9__TGT_WIDTH			8U
+#define XHC_DBLDVX9__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX9_WIDTH			32U
+#define XHC_DBLDVX9__WIDTH			32U
+#define XHC_DBLDVX9_ALL_L			31U
+#define XHC_DBLDVX9_ALL_R			0U
+#define XHC_DBLDVX9__ALL_L			31U
+#define XHC_DBLDVX9__ALL_R			0U
+#define XHC_DBLDVX9_DATAMASK			0xffffffffU
+#define XHC_DBLDVX9_RDWRMASK			0x00000000U
+#define XHC_DBLDVX9_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX10_OFFSET			0x8e8U
+#define XHC_DBLDVX10_BASE			0x8e8U
+#define XHC_DBLDVX10__SID_L			31U
+#define XHC_DBLDVX10__SID_R			16U
+#define XHC_DBLDVX10__SID_WIDTH			16U
+#define XHC_DBLDVX10__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX10__reserved_L		15U
+#define XHC_DBLDVX10__reserved_R		8U
+#define XHC_DBLDVX10__reserved_WIDTH		8U
+#define XHC_DBLDVX10__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX10__TGT_L			7U
+#define XHC_DBLDVX10__TGT_R			0U
+#define XHC_DBLDVX10__TGT_WIDTH			8U
+#define XHC_DBLDVX10__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX10_WIDTH			32U
+#define XHC_DBLDVX10__WIDTH			32U
+#define XHC_DBLDVX10_ALL_L			31U
+#define XHC_DBLDVX10_ALL_R			0U
+#define XHC_DBLDVX10__ALL_L			31U
+#define XHC_DBLDVX10__ALL_R			0U
+#define XHC_DBLDVX10_DATAMASK			0xffffffffU
+#define XHC_DBLDVX10_RDWRMASK			0x00000000U
+#define XHC_DBLDVX10_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX11_OFFSET			0x8ecU
+#define XHC_DBLDVX11_BASE			0x8ecU
+#define XHC_DBLDVX11__SID_L			31U
+#define XHC_DBLDVX11__SID_R			16U
+#define XHC_DBLDVX11__SID_WIDTH			16U
+#define XHC_DBLDVX11__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX11__reserved_L		15U
+#define XHC_DBLDVX11__reserved_R		8U
+#define XHC_DBLDVX11__reserved_WIDTH		8U
+#define XHC_DBLDVX11__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX11__TGT_L			7U
+#define XHC_DBLDVX11__TGT_R			0U
+#define XHC_DBLDVX11__TGT_WIDTH			8U
+#define XHC_DBLDVX11__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX11_WIDTH			32U
+#define XHC_DBLDVX11__WIDTH			32U
+#define XHC_DBLDVX11_ALL_L			31U
+#define XHC_DBLDVX11_ALL_R			0U
+#define XHC_DBLDVX11__ALL_L			31U
+#define XHC_DBLDVX11__ALL_R			0U
+#define XHC_DBLDVX11_DATAMASK			0xffffffffU
+#define XHC_DBLDVX11_RDWRMASK			0x00000000U
+#define XHC_DBLDVX11_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX12_OFFSET			0x8f0U
+#define XHC_DBLDVX12_BASE			0x8f0U
+#define XHC_DBLDVX12__SID_L			31U
+#define XHC_DBLDVX12__SID_R			16U
+#define XHC_DBLDVX12__SID_WIDTH			16U
+#define XHC_DBLDVX12__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX12__reserved_L		15U
+#define XHC_DBLDVX12__reserved_R		8U
+#define XHC_DBLDVX12__reserved_WIDTH		8U
+#define XHC_DBLDVX12__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX12__TGT_L			7U
+#define XHC_DBLDVX12__TGT_R			0U
+#define XHC_DBLDVX12__TGT_WIDTH			8U
+#define XHC_DBLDVX12__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX12_WIDTH			32U
+#define XHC_DBLDVX12__WIDTH			32U
+#define XHC_DBLDVX12_ALL_L			31U
+#define XHC_DBLDVX12_ALL_R			0U
+#define XHC_DBLDVX12__ALL_L			31U
+#define XHC_DBLDVX12__ALL_R			0U
+#define XHC_DBLDVX12_DATAMASK			0xffffffffU
+#define XHC_DBLDVX12_RDWRMASK			0x00000000U
+#define XHC_DBLDVX12_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX13_OFFSET			0x8f4U
+#define XHC_DBLDVX13_BASE			0x8f4U
+#define XHC_DBLDVX13__SID_L			31U
+#define XHC_DBLDVX13__SID_R			16U
+#define XHC_DBLDVX13__SID_WIDTH			16U
+#define XHC_DBLDVX13__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX13__reserved_L		15U
+#define XHC_DBLDVX13__reserved_R		8U
+#define XHC_DBLDVX13__reserved_WIDTH		8U
+#define XHC_DBLDVX13__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX13__TGT_L			7U
+#define XHC_DBLDVX13__TGT_R			0U
+#define XHC_DBLDVX13__TGT_WIDTH			8U
+#define XHC_DBLDVX13__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX13_WIDTH			32U
+#define XHC_DBLDVX13__WIDTH			32U
+#define XHC_DBLDVX13_ALL_L			31U
+#define XHC_DBLDVX13_ALL_R			0U
+#define XHC_DBLDVX13__ALL_L			31U
+#define XHC_DBLDVX13__ALL_R			0U
+#define XHC_DBLDVX13_DATAMASK			0xffffffffU
+#define XHC_DBLDVX13_RDWRMASK			0x00000000U
+#define XHC_DBLDVX13_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX14_OFFSET			0x8f8U
+#define XHC_DBLDVX14_BASE			0x8f8U
+#define XHC_DBLDVX14__SID_L			31U
+#define XHC_DBLDVX14__SID_R			16U
+#define XHC_DBLDVX14__SID_WIDTH			16U
+#define XHC_DBLDVX14__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX14__reserved_L		15U
+#define XHC_DBLDVX14__reserved_R		8U
+#define XHC_DBLDVX14__reserved_WIDTH		8U
+#define XHC_DBLDVX14__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX14__TGT_L			7U
+#define XHC_DBLDVX14__TGT_R			0U
+#define XHC_DBLDVX14__TGT_WIDTH			8U
+#define XHC_DBLDVX14__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX14_WIDTH			32U
+#define XHC_DBLDVX14__WIDTH			32U
+#define XHC_DBLDVX14_ALL_L			31U
+#define XHC_DBLDVX14_ALL_R			0U
+#define XHC_DBLDVX14__ALL_L			31U
+#define XHC_DBLDVX14__ALL_R			0U
+#define XHC_DBLDVX14_DATAMASK			0xffffffffU
+#define XHC_DBLDVX14_RDWRMASK			0x00000000U
+#define XHC_DBLDVX14_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX15_OFFSET			0x8fcU
+#define XHC_DBLDVX15_BASE			0x8fcU
+#define XHC_DBLDVX15__SID_L			31U
+#define XHC_DBLDVX15__SID_R			16U
+#define XHC_DBLDVX15__SID_WIDTH			16U
+#define XHC_DBLDVX15__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX15__reserved_L		15U
+#define XHC_DBLDVX15__reserved_R		8U
+#define XHC_DBLDVX15__reserved_WIDTH		8U
+#define XHC_DBLDVX15__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX15__TGT_L			7U
+#define XHC_DBLDVX15__TGT_R			0U
+#define XHC_DBLDVX15__TGT_WIDTH			8U
+#define XHC_DBLDVX15__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX15_WIDTH			32U
+#define XHC_DBLDVX15__WIDTH			32U
+#define XHC_DBLDVX15_ALL_L			31U
+#define XHC_DBLDVX15_ALL_R			0U
+#define XHC_DBLDVX15__ALL_L			31U
+#define XHC_DBLDVX15__ALL_R			0U
+#define XHC_DBLDVX15_DATAMASK			0xffffffffU
+#define XHC_DBLDVX15_RDWRMASK			0x00000000U
+#define XHC_DBLDVX15_RESETVALUE			0x00000000U
+
+#define XHC_DBLDVX16_OFFSET			0x900U
+#define XHC_DBLDVX16_BASE			0x900U
+#define XHC_DBLDVX16__SID_L			31U
+#define XHC_DBLDVX16__SID_R			16U
+#define XHC_DBLDVX16__SID_WIDTH			16U
+#define XHC_DBLDVX16__SID_RESETVALUE		0x0000U
+#define XHC_DBLDVX16__reserved_L		15U
+#define XHC_DBLDVX16__reserved_R		8U
+#define XHC_DBLDVX16__reserved_WIDTH		8U
+#define XHC_DBLDVX16__reserved_RESETVALUE	0x00U
+#define XHC_DBLDVX16__TGT_L			7U
+#define XHC_DBLDVX16__TGT_R			0U
+#define XHC_DBLDVX16__TGT_WIDTH			8U
+#define XHC_DBLDVX16__TGT_RESETVALUE		0x00U
+#define XHC_DBLDVX16_WIDTH			32U
+#define XHC_DBLDVX16__WIDTH			32U
+#define XHC_DBLDVX16_ALL_L			31U
+#define XHC_DBLDVX16_ALL_R			0U
+#define XHC_DBLDVX16__ALL_L			31U
+#define XHC_DBLDVX16__ALL_R			0U
+#define XHC_DBLDVX16_DATAMASK			0xffffffffU
+#define XHC_DBLDVX16_RDWRMASK			0x00000000U
+#define XHC_DBLDVX16_RESETVALUE			0x00000000U
+
+#define XHC_ECHSPT3_OFFSET			0x940U
+#define XHC_ECHSPT3_BASE			0x940U
+#define XHC_ECHSPT3__RMAJ_L			31U
+#define XHC_ECHSPT3__RMAJ_R			24U
+#define XHC_ECHSPT3__RMAJ_WIDTH			8U
+#define XHC_ECHSPT3__RMAJ_RESETVALUE		0x00U
+#define XHC_ECHSPT3__RMIN_L			23U
+#define XHC_ECHSPT3__RMIN_R			16U
+#define XHC_ECHSPT3__RMIN_WIDTH			8U
+#define XHC_ECHSPT3__RMIN_RESETVALUE		0x00U
+#define XHC_ECHSPT3__NCP_L			15U
+#define XHC_ECHSPT3__NCP_R			8U
+#define XHC_ECHSPT3__NCP_WIDTH			8U
+#define XHC_ECHSPT3__NCP_RESETVALUE		0x00U
+#define XHC_ECHSPT3__CID_L			7U
+#define XHC_ECHSPT3__CID_R			0U
+#define XHC_ECHSPT3__CID_WIDTH			8U
+#define XHC_ECHSPT3__CID_RESETVALUE		0x02U
+#define XHC_ECHSPT3_WIDTH			32U
+#define XHC_ECHSPT3__WIDTH			32U
+#define XHC_ECHSPT3_ALL_L			31U
+#define XHC_ECHSPT3_ALL_R			0U
+#define XHC_ECHSPT3__ALL_L			31U
+#define XHC_ECHSPT3__ALL_R			0U
+#define XHC_ECHSPT3_DATAMASK			0xffffffffU
+#define XHC_ECHSPT3_RDWRMASK			0x00000000U
+#define XHC_ECHSPT3_RESETVALUE			0x00000002U
+
+#define XHC_PNSTR3_OFFSET			0x944U
+#define XHC_PNSTR3_BASE				0x944U
+#define XHC_PNSTR3__STR_L			31U
+#define XHC_PNSTR3__STR_R			0U
+#define XHC_PNSTR3__STR_WIDTH			32U
+#define XHC_PNSTR3__STR_RESETVALUE		0x20425355U
+#define XHC_PNSTR3_WIDTH			32U
+#define XHC_PNSTR3__WIDTH			32U
+#define XHC_PNSTR3_ALL_L			31U
+#define XHC_PNSTR3_ALL_R			0U
+#define XHC_PNSTR3__ALL_L			31U
+#define XHC_PNSTR3__ALL_R			0U
+#define XHC_PNSTR3_DATAMASK			0xffffffffU
+#define XHC_PNSTR3_RDWRMASK			0x00000000U
+#define XHC_PNSTR3_RESETVALUE			0x20425355U
+
+#define XHC_PSUM3_OFFSET			0x948U
+#define XHC_PSUM3_BASE				0x948U
+#define XHC_PSUM3__PSIC_L			31U
+#define XHC_PSUM3__PSIC_R			28U
+#define XHC_PSUM3__PSIC_WIDTH			4U
+#define XHC_PSUM3__PSIC_RESETVALUE		0x0U
+#define XHC_PSUM3__MHD_L			27U
+#define XHC_PSUM3__MHD_R			25U
+#define XHC_PSUM3__MHD_WIDTH			3U
+#define XHC_PSUM3__MHD_RESETVALUE		0x0U
+#define XHC_PSUM3__BLC				20U
+#define XHC_PSUM3__BLC_L			20U
+#define XHC_PSUM3__BLC_R			20U
+#define XHC_PSUM3__BLC_WIDTH			1U
+#define XHC_PSUM3__BLC_RESETVALUE		0x0U
+#define XHC_PSUM3__HLC				19U
+#define XHC_PSUM3__HLC_L			19U
+#define XHC_PSUM3__HLC_R			19U
+#define XHC_PSUM3__HLC_WIDTH			1U
+#define XHC_PSUM3__HLC_RESETVALUE		0x1U
+#define XHC_PSUM3__IHI				18U
+#define XHC_PSUM3__IHI_L			18U
+#define XHC_PSUM3__IHI_R			18U
+#define XHC_PSUM3__IHI_WIDTH			1U
+#define XHC_PSUM3__IHI_RESETVALUE		0x0U
+#define XHC_PSUM3__HSO				17U
+#define XHC_PSUM3__HSO_L			17U
+#define XHC_PSUM3__HSO_R			17U
+#define XHC_PSUM3__HSO_WIDTH			1U
+#define XHC_PSUM3__HSO_RESETVALUE		0x0U
+#define XHC_PSUM3__reserved			16U
+#define XHC_PSUM3__reserved_L			16U
+#define XHC_PSUM3__reserved_R			16U
+#define XHC_PSUM3__reserved_WIDTH		1U
+#define XHC_PSUM3__reserved_RESETVALUE		0x0U
+#define XHC_PSUM3__CPC_L			15U
+#define XHC_PSUM3__CPC_R			8U
+#define XHC_PSUM3__CPC_WIDTH			8U
+#define XHC_PSUM3__CPC_RESETVALUE		0x00U
+#define XHC_PSUM3__CPO_L			7U
+#define XHC_PSUM3__CPO_R			0U
+#define XHC_PSUM3__CPO_WIDTH			8U
+#define XHC_PSUM3__CPO_RESETVALUE		0x00U
+#define XHC_PSUM3__RESERVED_L			24U
+#define XHC_PSUM3__RESERVED_R			21U
+#define XHC_PSUM3_WIDTH				32U
+#define XHC_PSUM3__WIDTH			32U
+#define XHC_PSUM3_ALL_L				31U
+#define XHC_PSUM3_ALL_R				0U
+#define XHC_PSUM3__ALL_L			31U
+#define XHC_PSUM3__ALL_R			0U
+#define XHC_PSUM3_DATAMASK			0xfe1fffffU
+#define XHC_PSUM3_RDWRMASK			0x01e00000U
+#define XHC_PSUM3_RESETVALUE			0x00080000U
+
+#define XHC_PTSLTYP3_OFFSET			0x94cU
+#define XHC_PTSLTYP3_BASE			0x94cU
+#define XHC_PTSLTYP3__reserved_L		31U
+#define XHC_PTSLTYP3__reserved_R		5U
+#define XHC_PTSLTYP3__reserved_WIDTH		27U
+#define XHC_PTSLTYP3__reserved_RESETVALUE	0x0U
+#define XHC_PTSLTYP3__PST_L			4U
+#define XHC_PTSLTYP3__PST_R			0U
+#define XHC_PTSLTYP3__PST_WIDTH			5U
+#define XHC_PTSLTYP3__PST_RESETVALUE		0x0U
+#define XHC_PTSLTYP3_WIDTH			32U
+#define XHC_PTSLTYP3__WIDTH			32U
+#define XHC_PTSLTYP3_ALL_L			31U
+#define XHC_PTSLTYP3_ALL_R			0U
+#define XHC_PTSLTYP3__ALL_L			31U
+#define XHC_PTSLTYP3__ALL_R			0U
+#define XHC_PTSLTYP3_DATAMASK			0xffffffffU
+#define XHC_PTSLTYP3_RDWRMASK			0x00000000U
+#define XHC_PTSLTYP3_RESETVALUE			0x00000000U
+
+#define XHC_ECHSPT2_OFFSET			0x950U
+#define XHC_ECHSPT2_BASE			0x950U
+#define XHC_ECHSPT2__RMAJ_L			31U
+#define XHC_ECHSPT2__RMAJ_R			24U
+#define XHC_ECHSPT2__RMAJ_WIDTH			8U
+#define XHC_ECHSPT2__RMAJ_RESETVALUE		0x00U
+#define XHC_ECHSPT2__RMIN_L			23U
+#define XHC_ECHSPT2__RMIN_R			16U
+#define XHC_ECHSPT2__RMIN_WIDTH			8U
+#define XHC_ECHSPT2__RMIN_RESETVALUE		0x00U
+#define XHC_ECHSPT2__NCP_L			15U
+#define XHC_ECHSPT2__NCP_R			8U
+#define XHC_ECHSPT2__NCP_WIDTH			8U
+#define XHC_ECHSPT2__NCP_RESETVALUE		0x00U
+#define XHC_ECHSPT2__CID_L			7U
+#define XHC_ECHSPT2__CID_R			0U
+#define XHC_ECHSPT2__CID_WIDTH			8U
+#define XHC_ECHSPT2__CID_RESETVALUE		0x02U
+#define XHC_ECHSPT2_WIDTH			32U
+#define XHC_ECHSPT2__WIDTH			32U
+#define XHC_ECHSPT2_ALL_L			31U
+#define XHC_ECHSPT2_ALL_R			0U
+#define XHC_ECHSPT2__ALL_L			31U
+#define XHC_ECHSPT2__ALL_R			0U
+#define XHC_ECHSPT2_DATAMASK			0xffffffffU
+#define XHC_ECHSPT2_RDWRMASK			0x00000000U
+#define XHC_ECHSPT2_RESETVALUE			0x00000002U
+
+#define XHC_PNSTR2_OFFSET			0x954U
+#define XHC_PNSTR2_BASE				0x954U
+#define XHC_PNSTR2__STR_L			31U
+#define XHC_PNSTR2__STR_R			0U
+#define XHC_PNSTR2__STR_WIDTH			32U
+#define XHC_PNSTR2__STR_RESETVALUE		0x20425355U
+#define XHC_PNSTR2_WIDTH			32U
+#define XHC_PNSTR2__WIDTH			32U
+#define XHC_PNSTR2_ALL_L			31U
+#define XHC_PNSTR2_ALL_R			0U
+#define XHC_PNSTR2__ALL_L			31U
+#define XHC_PNSTR2__ALL_R			0U
+#define XHC_PNSTR2_DATAMASK			0xffffffffU
+#define XHC_PNSTR2_RDWRMASK			0x00000000U
+#define XHC_PNSTR2_RESETVALUE			0x20425355U
+
+#define XHC_PSUM2_OFFSET			0x958U
+#define XHC_PSUM2_BASE				0x958U
+#define XHC_PSUM2__PSIC_L			31U
+#define XHC_PSUM2__PSIC_R			28U
+#define XHC_PSUM2__PSIC_WIDTH			4U
+#define XHC_PSUM2__PSIC_RESETVALUE		0x0U
+#define XHC_PSUM2__MHD_L			27U
+#define XHC_PSUM2__MHD_R			25U
+#define XHC_PSUM2__MHD_WIDTH			3U
+#define XHC_PSUM2__MHD_RESETVALUE		0x0U
+#define XHC_PSUM2__BLC				20U
+#define XHC_PSUM2__BLC_L			20U
+#define XHC_PSUM2__BLC_R			20U
+#define XHC_PSUM2__BLC_WIDTH			1U
+#define XHC_PSUM2__BLC_RESETVALUE		0x0U
+#define XHC_PSUM2__HLC				19U
+#define XHC_PSUM2__HLC_L			19U
+#define XHC_PSUM2__HLC_R			19U
+#define XHC_PSUM2__HLC_WIDTH			1U
+#define XHC_PSUM2__HLC_RESETVALUE		0x1U
+#define XHC_PSUM2__IHI				18U
+#define XHC_PSUM2__IHI_L			18U
+#define XHC_PSUM2__IHI_R			18U
+#define XHC_PSUM2__IHI_WIDTH			1U
+#define XHC_PSUM2__IHI_RESETVALUE		0x0U
+#define XHC_PSUM2__HSO				17U
+#define XHC_PSUM2__HSO_L			17U
+#define XHC_PSUM2__HSO_R			17U
+#define XHC_PSUM2__HSO_WIDTH			1U
+#define XHC_PSUM2__HSO_RESETVALUE		0x0U
+#define XHC_PSUM2__reserved			16U
+#define XHC_PSUM2__reserved_L			16U
+#define XHC_PSUM2__reserved_R			16U
+#define XHC_PSUM2__reserved_WIDTH		1U
+#define XHC_PSUM2__reserved_RESETVALUE		0x0U
+#define XHC_PSUM2__CPC_L			15U
+#define XHC_PSUM2__CPC_R			8U
+#define XHC_PSUM2__CPC_WIDTH			8U
+#define XHC_PSUM2__CPC_RESETVALUE		0x00U
+#define XHC_PSUM2__CPO_L			7U
+#define XHC_PSUM2__CPO_R			0U
+#define XHC_PSUM2__CPO_WIDTH			8U
+#define XHC_PSUM2__CPO_RESETVALUE		0x00U
+#define XHC_PSUM2__RESERVED_L			24U
+#define XHC_PSUM2__RESERVED_R			21U
+#define XHC_PSUM2_WIDTH				32U
+#define XHC_PSUM2__WIDTH			32U
+#define XHC_PSUM2_ALL_L				31U
+#define XHC_PSUM2_ALL_R				0U
+#define XHC_PSUM2__ALL_L			31U
+#define XHC_PSUM2__ALL_R			0U
+#define XHC_PSUM2_DATAMASK			0xfe1fffffU
+#define XHC_PSUM2_RDWRMASK			0x01e00000U
+#define XHC_PSUM2_RESETVALUE			0x00080000U
+
+#define XHC_PTSLTYP2_OFFSET			0x95cU
+#define XHC_PTSLTYP2_BASE			0x95cU
+#define XHC_PTSLTYP2__reserved_L		31U
+#define XHC_PTSLTYP2__reserved_R		5U
+#define XHC_PTSLTYP2__reserved_WIDTH		27U
+#define XHC_PTSLTYP2__reserved_RESETVALUE	0x0U
+#define XHC_PTSLTYP2__PST_L			4U
+#define XHC_PTSLTYP2__PST_R			0U
+#define XHC_PTSLTYP2__PST_WIDTH			5U
+#define XHC_PTSLTYP2__PST_RESETVALUE		0x0U
+#define XHC_PTSLTYP2_WIDTH			32U
+#define XHC_PTSLTYP2__WIDTH			32U
+#define XHC_PTSLTYP2_ALL_L			31U
+#define XHC_PTSLTYP2_ALL_R			0U
+#define XHC_PTSLTYP2__ALL_L			31U
+#define XHC_PTSLTYP2__ALL_R			0U
+#define XHC_PTSLTYP2_DATAMASK			0xffffffffU
+#define XHC_PTSLTYP2_RDWRMASK			0x00000000U
+#define XHC_PTSLTYP2_RESETVALUE			0x00000000U
+
+#define XHC_ECHRSVP_OFFSET			0x960U
+#define XHC_ECHRSVP_BASE			0x960U
+#define XHC_ECHRSVP__reserved_L			31U
+#define XHC_ECHRSVP__reserved_R			16U
+#define XHC_ECHRSVP__reserved_WIDTH		16U
+#define XHC_ECHRSVP__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSVP__NCP_L			15U
+#define XHC_ECHRSVP__NCP_R			8U
+#define XHC_ECHRSVP__NCP_WIDTH			8U
+#define XHC_ECHRSVP__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSVP__CID_L			7U
+#define XHC_ECHRSVP__CID_R			0U
+#define XHC_ECHRSVP__CID_WIDTH			8U
+#define XHC_ECHRSVP__CID_RESETVALUE		0xffU
+#define XHC_ECHRSVP_WIDTH			32U
+#define XHC_ECHRSVP__WIDTH			32U
+#define XHC_ECHRSVP_ALL_L			31U
+#define XHC_ECHRSVP_ALL_R			0U
+#define XHC_ECHRSVP__ALL_L			31U
+#define XHC_ECHRSVP__ALL_R			0U
+#define XHC_ECHRSVP_DATAMASK			0xffffffffU
+#define XHC_ECHRSVP_RDWRMASK			0x00000000U
+#define XHC_ECHRSVP_RESETVALUE			0x000000ffU
+
+#define XHC_ECHRSVI_OFFSET			0x968U
+#define XHC_ECHRSVI_BASE			0x968U
+#define XHC_ECHRSVI__reserved_L			31U
+#define XHC_ECHRSVI__reserved_R			16U
+#define XHC_ECHRSVI__reserved_WIDTH		16U
+#define XHC_ECHRSVI__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSVI__NCP_L			15U
+#define XHC_ECHRSVI__NCP_R			8U
+#define XHC_ECHRSVI__NCP_WIDTH			8U
+#define XHC_ECHRSVI__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSVI__CID_L			7U
+#define XHC_ECHRSVI__CID_R			0U
+#define XHC_ECHRSVI__CID_WIDTH			8U
+#define XHC_ECHRSVI__CID_RESETVALUE		0xffU
+#define XHC_ECHRSVI_WIDTH			32U
+#define XHC_ECHRSVI__WIDTH			32U
+#define XHC_ECHRSVI_ALL_L			31U
+#define XHC_ECHRSVI_ALL_R			0U
+#define XHC_ECHRSVI__ALL_L			31U
+#define XHC_ECHRSVI__ALL_R			0U
+#define XHC_ECHRSVI_DATAMASK			0xffffffffU
+#define XHC_ECHRSVI_RDWRMASK			0x00000000U
+#define XHC_ECHRSVI_RESETVALUE			0x000000ffU
+
+#define XHC_ECHRSVM_OFFSET			0xae8U
+#define XHC_ECHRSVM_BASE			0xae8U
+#define XHC_ECHRSVM__reserved_L			31U
+#define XHC_ECHRSVM__reserved_R			16U
+#define XHC_ECHRSVM__reserved_WIDTH		16U
+#define XHC_ECHRSVM__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSVM__NCP_L			15U
+#define XHC_ECHRSVM__NCP_R			8U
+#define XHC_ECHRSVM__NCP_WIDTH			8U
+#define XHC_ECHRSVM__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSVM__CID_L			7U
+#define XHC_ECHRSVM__CID_R			0U
+#define XHC_ECHRSVM__CID_WIDTH			8U
+#define XHC_ECHRSVM__CID_RESETVALUE		0xffU
+#define XHC_ECHRSVM_WIDTH			32U
+#define XHC_ECHRSVM__WIDTH			32U
+#define XHC_ECHRSVM_ALL_L			31U
+#define XHC_ECHRSVM_ALL_R			0U
+#define XHC_ECHRSVM__ALL_L			31U
+#define XHC_ECHRSVM__ALL_R			0U
+#define XHC_ECHRSVM_DATAMASK			0xffffffffU
+#define XHC_ECHRSVM_RDWRMASK			0x00000000U
+#define XHC_ECHRSVM_RESETVALUE			0x000000ffU
+
+#define XHC_ECHRSVD_OFFSET			0xaf8U
+#define XHC_ECHRSVD_BASE			0xaf8U
+#define XHC_ECHRSVD__reserved_L			31U
+#define XHC_ECHRSVD__reserved_R			16U
+#define XHC_ECHRSVD__reserved_WIDTH		16U
+#define XHC_ECHRSVD__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSVD__NCP_L			15U
+#define XHC_ECHRSVD__NCP_R			8U
+#define XHC_ECHRSVD__NCP_WIDTH			8U
+#define XHC_ECHRSVD__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSVD__CID_L			7U
+#define XHC_ECHRSVD__CID_R			0U
+#define XHC_ECHRSVD__CID_WIDTH			8U
+#define XHC_ECHRSVD__CID_RESETVALUE		0xffU
+#define XHC_ECHRSVD_WIDTH			32U
+#define XHC_ECHRSVD__WIDTH			32U
+#define XHC_ECHRSVD_ALL_L			31U
+#define XHC_ECHRSVD_ALL_R			0U
+#define XHC_ECHRSVD__ALL_L			31U
+#define XHC_ECHRSVD__ALL_R			0U
+#define XHC_ECHRSVD_DATAMASK			0xffffffffU
+#define XHC_ECHRSVD_RDWRMASK			0x00000000U
+#define XHC_ECHRSVD_RESETVALUE			0x000000ffU
+
+#define XHC_ECHRSVO_OFFSET			0xb38U
+#define XHC_ECHRSVO_BASE			0xb38U
+#define XHC_ECHRSVO__reserved_L			31U
+#define XHC_ECHRSVO__reserved_R			16U
+#define XHC_ECHRSVO__reserved_WIDTH		16U
+#define XHC_ECHRSVO__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSVO__NCP_L			15U
+#define XHC_ECHRSVO__NCP_R			8U
+#define XHC_ECHRSVO__NCP_WIDTH			8U
+#define XHC_ECHRSVO__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSVO__CID_L			7U
+#define XHC_ECHRSVO__CID_R			0U
+#define XHC_ECHRSVO__CID_WIDTH			8U
+#define XHC_ECHRSVO__CID_RESETVALUE		0xffU
+#define XHC_ECHRSVO_WIDTH			32U
+#define XHC_ECHRSVO__WIDTH			32U
+#define XHC_ECHRSVO_ALL_L			31U
+#define XHC_ECHRSVO_ALL_R			0U
+#define XHC_ECHRSVO__ALL_L			31U
+#define XHC_ECHRSVO__ALL_R			0U
+#define XHC_ECHRSVO_DATAMASK			0xffffffffU
+#define XHC_ECHRSVO_RDWRMASK			0x00000000U
+#define XHC_ECHRSVO_RESETVALUE			0x000000ffU
+
+#define XHC_ECHCTT_OFFSET			0xbf0U
+#define XHC_ECHCTT_BASE				0xbf0U
+#define XHC_ECHCTT__reserved_L			31U
+#define XHC_ECHCTT__reserved_R			16U
+#define XHC_ECHCTT__reserved_WIDTH		16U
+#define XHC_ECHCTT__reserved_RESETVALUE		0x0000U
+#define XHC_ECHCTT__NCP_L			15U
+#define XHC_ECHCTT__NCP_R			8U
+#define XHC_ECHCTT__NCP_WIDTH			8U
+#define XHC_ECHCTT__NCP_RESETVALUE		0x04U
+#define XHC_ECHCTT__CID_L			7U
+#define XHC_ECHCTT__CID_R			0U
+#define XHC_ECHCTT__CID_WIDTH			8U
+#define XHC_ECHCTT__CID_RESETVALUE		0xe0U
+#define XHC_ECHCTT_WIDTH			32U
+#define XHC_ECHCTT__WIDTH			32U
+#define XHC_ECHCTT_ALL_L			31U
+#define XHC_ECHCTT_ALL_R			0U
+#define XHC_ECHCTT__ALL_L			31U
+#define XHC_ECHCTT__ALL_R			0U
+#define XHC_ECHCTT_DATAMASK			0xffffffffU
+#define XHC_ECHCTT_RDWRMASK			0x00000000U
+#define XHC_ECHCTT_RESETVALUE			0x000004e0U
+
+#define XHC_CTTMTS0_OFFSET			0xbf8U
+#define XHC_CTTMTS0_BASE			0xbf8U
+#define XHC_CTTMTS0__DCM			31U
+#define XHC_CTTMTS0__DCM_L			31U
+#define XHC_CTTMTS0__DCM_R			31U
+#define XHC_CTTMTS0__DCM_WIDTH			1U
+#define XHC_CTTMTS0__DCM_RESETVALUE		0x0U
+#define XHC_CTTMTS0__reserved_L			30U
+#define XHC_CTTMTS0__reserved_R			10U
+#define XHC_CTTMTS0__reserved_WIDTH		21U
+#define XHC_CTTMTS0__reserved_RESETVALUE	0x0U
+#define XHC_CTTMTS0__SLA_L			9U
+#define XHC_CTTMTS0__SLA_R			0U
+#define XHC_CTTMTS0__SLA_WIDTH			10U
+#define XHC_CTTMTS0__SLA_RESETVALUE		0x0U
+#define XHC_CTTMTS0_WIDTH			32U
+#define XHC_CTTMTS0__WIDTH			32U
+#define XHC_CTTMTS0_ALL_L			31U
+#define XHC_CTTMTS0_ALL_R			0U
+#define XHC_CTTMTS0__ALL_L			31U
+#define XHC_CTTMTS0__ALL_R			0U
+#define XHC_CTTMTS0_DATAMASK			0xffffffffU
+#define XHC_CTTMTS0_RDWRMASK			0x00000000U
+#define XHC_CTTMTS0_RESETVALUE			0x00000000U
+
+#define XHC_CTTMTS1_OFFSET			0xbfcU
+#define XHC_CTTMTS1_BASE			0xbfcU
+#define XHC_CTTMTS1__TXF_L			25U
+#define XHC_CTTMTS1__TXF_R			16U
+#define XHC_CTTMTS1__TXF_WIDTH			10U
+#define XHC_CTTMTS1__TXF_RESETVALUE		0x0U
+#define XHC_CTTMTS1__reserved_L			15U
+#define XHC_CTTMTS1__reserved_R			10U
+#define XHC_CTTMTS1__reserved_WIDTH		6U
+#define XHC_CTTMTS1__reserved_RESETVALUE	0x0U
+#define XHC_CTTMTS1__RXF_L			9U
+#define XHC_CTTMTS1__RXF_R			0U
+#define XHC_CTTMTS1__RXF_WIDTH			10U
+#define XHC_CTTMTS1__RXF_RESETVALUE		0x0U
+#define XHC_CTTMTS1__RESERVED_L			31U
+#define XHC_CTTMTS1__RESERVED_R			26U
+#define XHC_CTTMTS1_WIDTH			26U
+#define XHC_CTTMTS1__WIDTH			26U
+#define XHC_CTTMTS1_ALL_L			25U
+#define XHC_CTTMTS1_ALL_R			0U
+#define XHC_CTTMTS1__ALL_L			25U
+#define XHC_CTTMTS1__ALL_R			0U
+#define XHC_CTTMTS1_DATAMASK			0x03ffffffU
+#define XHC_CTTMTS1_RDWRMASK			0xfc000000U
+#define XHC_CTTMTS1_RESETVALUE			0x0000000U
+
+#define XHC_ECHBIU_OFFSET			0xc00U
+#define XHC_ECHBIU_BASE				0xc00U
+#define XHC_ECHBIU__CLK_L			31U
+#define XHC_ECHBIU__CLK_R			21U
+#define XHC_ECHBIU__CLK_WIDTH			11U
+#define XHC_ECHBIU__CLK_RESETVALUE		0x0U
+#define XHC_ECHBIU__reserved_L			20U
+#define XHC_ECHBIU__reserved_R			19U
+#define XHC_ECHBIU__reserved_WIDTH		2U
+#define XHC_ECHBIU__reserved_RESETVALUE		0x0U
+#define XHC_ECHBIU__WID_L			18U
+#define XHC_ECHBIU__WID_R			16U
+#define XHC_ECHBIU__WID_WIDTH			3U
+#define XHC_ECHBIU__WID_RESETVALUE		0x0U
+#define XHC_ECHBIU__NCP_L			15U
+#define XHC_ECHBIU__NCP_R			8U
+#define XHC_ECHBIU__NCP_WIDTH			8U
+#define XHC_ECHBIU__NCP_RESETVALUE		0x08U
+#define XHC_ECHBIU__CID_L			7U
+#define XHC_ECHBIU__CID_R			0U
+#define XHC_ECHBIU__CID_WIDTH			8U
+#define XHC_ECHBIU__CID_RESETVALUE		0xc0U
+#define XHC_ECHBIU_WIDTH			32U
+#define XHC_ECHBIU__WIDTH			32U
+#define XHC_ECHBIU_ALL_L			31U
+#define XHC_ECHBIU_ALL_R			0U
+#define XHC_ECHBIU__ALL_L			31U
+#define XHC_ECHBIU__ALL_R			0U
+#define XHC_ECHBIU_DATAMASK			0xffffffffU
+#define XHC_ECHBIU_RDWRMASK			0x00000000U
+#define XHC_ECHBIU_RESETVALUE			0x000008c0U
+
+#define XHC_BIUSPC_OFFSET			0xc04U
+#define XHC_BIUSPC_BASE				0xc04U
+#define XHC_BIUSPC__MAJ_L			31U
+#define XHC_BIUSPC__MAJ_R			28U
+#define XHC_BIUSPC__MAJ_WIDTH			4U
+#define XHC_BIUSPC__MAJ_RESETVALUE		0x0U
+#define XHC_BIUSPC__MIN_L			27U
+#define XHC_BIUSPC__MIN_R			24U
+#define XHC_BIUSPC__MIN_WIDTH			4U
+#define XHC_BIUSPC__MIN_RESETVALUE		0x0U
+#define XHC_BIUSPC__RLS_L			23U
+#define XHC_BIUSPC__RLS_R			20U
+#define XHC_BIUSPC__RLS_WIDTH			4U
+#define XHC_BIUSPC__RLS_RESETVALUE		0x0U
+#define XHC_BIUSPC__reserved_L			19U
+#define XHC_BIUSPC__reserved_R			4U
+#define XHC_BIUSPC__reserved_WIDTH		16U
+#define XHC_BIUSPC__reserved_RESETVALUE		0x0000U
+#define XHC_BIUSPC__SPI_L			3U
+#define XHC_BIUSPC__SPI_R			2U
+#define XHC_BIUSPC__SPI_WIDTH			2U
+#define XHC_BIUSPC__SPI_RESETVALUE		0x3U
+#define XHC_BIUSPC__TYP_L			1U
+#define XHC_BIUSPC__TYP_R			0U
+#define XHC_BIUSPC__TYP_WIDTH			2U
+#define XHC_BIUSPC__TYP_RESETVALUE		0x0U
+#define XHC_BIUSPC_WIDTH			32U
+#define XHC_BIUSPC__WIDTH			32U
+#define XHC_BIUSPC_ALL_L			31U
+#define XHC_BIUSPC_ALL_R			0U
+#define XHC_BIUSPC__ALL_L			31U
+#define XHC_BIUSPC__ALL_R			0U
+#define XHC_BIUSPC_DATAMASK			0xffffffffU
+#define XHC_BIUSPC_RDWRMASK			0x00000000U
+#define XHC_BIUSPC_RESETVALUE			0x0000000cU
+
+#define XHC_AXIWRA_OFFSET			0xc08U
+#define XHC_AXIWRA_BASE				0xc08U
+#define XHC_AXIWRA__WTS_L			31U
+#define XHC_AXIWRA__WTS_R			28U
+#define XHC_AXIWRA__WTS_WIDTH			4U
+#define XHC_AXIWRA__WTS_RESETVALUE		0x2U
+#define XHC_AXIWRA__WUA_L			24U
+#define XHC_AXIWRA__WUA_R			16U
+#define XHC_AXIWRA__WUA_WIDTH			9U
+#define XHC_AXIWRA__WUA_RESETVALUE		0x0U
+#define XHC_AXIWRA__reserved_L			15U
+#define XHC_AXIWRA__reserved_R			10U
+#define XHC_AXIWRA__reserved_WIDTH		6U
+#define XHC_AXIWRA__reserved_RESETVALUE		0x0U
+#define XHC_AXIWRA__BYP				9U
+#define XHC_AXIWRA__BYP_L			9U
+#define XHC_AXIWRA__BYP_R			9U
+#define XHC_AXIWRA__BYP_WIDTH			1U
+#define XHC_AXIWRA__BYP_RESETVALUE		0x0U
+#define XHC_AXIWRA__WSA_L			8U
+#define XHC_AXIWRA__WSA_R			0U
+#define XHC_AXIWRA__WSA_WIDTH			9U
+#define XHC_AXIWRA__WSA_RESETVALUE		0x0U
+#define XHC_AXIWRA__RESERVED_L			27U
+#define XHC_AXIWRA__RESERVED_R			25U
+#define XHC_AXIWRA_WIDTH			32U
+#define XHC_AXIWRA__WIDTH			32U
+#define XHC_AXIWRA_ALL_L			31U
+#define XHC_AXIWRA_ALL_R			0U
+#define XHC_AXIWRA__ALL_L			31U
+#define XHC_AXIWRA__ALL_R			0U
+#define XHC_AXIWRA_DATAMASK			0xf1ffffffU
+#define XHC_AXIWRA_RDWRMASK			0x0e000000U
+#define XHC_AXIWRA_RESETVALUE			0x20000000U
+
+#define XHC_AXIRDA_OFFSET			0xc0cU
+#define XHC_AXIRDA_BASE				0xc0cU
+#define XHC_AXIRDA__RTS_L			31U
+#define XHC_AXIRDA__RTS_R			28U
+#define XHC_AXIRDA__RTS_WIDTH			4U
+#define XHC_AXIRDA__RTS_RESETVALUE		0x2U
+#define XHC_AXIRDA__RFPC			27U
+#define XHC_AXIRDA__RFPC_L			27U
+#define XHC_AXIRDA__RFPC_R			27U
+#define XHC_AXIRDA__RFPC_WIDTH			1U
+#define XHC_AXIRDA__RFPC_RESETVALUE		0x0U
+#define XHC_AXIRDA__RUA_L			24U
+#define XHC_AXIRDA__RUA_R			16U
+#define XHC_AXIRDA__RUA_WIDTH			9U
+#define XHC_AXIRDA__RUA_RESETVALUE		0x0U
+#define XHC_AXIRDA__reserved_L			15U
+#define XHC_AXIRDA__reserved_R			9U
+#define XHC_AXIRDA__reserved_WIDTH		7U
+#define XHC_AXIRDA__reserved_RESETVALUE		0x0U
+#define XHC_AXIRDA__RSA_L			8U
+#define XHC_AXIRDA__RSA_R			0U
+#define XHC_AXIRDA__RSA_WIDTH			9U
+#define XHC_AXIRDA__RSA_RESETVALUE		0x0U
+#define XHC_AXIRDA__RESERVED_L			26U
+#define XHC_AXIRDA__RESERVED_R			25U
+#define XHC_AXIRDA_WIDTH			32U
+#define XHC_AXIRDA__WIDTH			32U
+#define XHC_AXIRDA_ALL_L			31U
+#define XHC_AXIRDA_ALL_R			0U
+#define XHC_AXIRDA__ALL_L			31U
+#define XHC_AXIRDA__ALL_R			0U
+#define XHC_AXIRDA_DATAMASK			0xf9ffffffU
+#define XHC_AXIRDA_RDWRMASK			0x06000000U
+#define XHC_AXIRDA_RESETVALUE			0x20000000U
+
+#define XHC_AXILPM_OFFSET			0xc10U
+#define XHC_AXILPM_BASE				0xc10U
+#define XHC_AXILPM__ENB				31U
+#define XHC_AXILPM__ENB_L			31U
+#define XHC_AXILPM__ENB_R			31U
+#define XHC_AXILPM__ENB_WIDTH			1U
+#define XHC_AXILPM__ENB_RESETVALUE		0x0U
+#define XHC_AXILPM__reserved_L			30U
+#define XHC_AXILPM__reserved_R			3U
+#define XHC_AXILPM__reserved_WIDTH		28U
+#define XHC_AXILPM__reserved_RESETVALUE		0x0000000U
+#define XHC_AXILPM__ITT_L			2U
+#define XHC_AXILPM__ITT_R			0U
+#define XHC_AXILPM__ITT_WIDTH			3U
+#define XHC_AXILPM__ITT_RESETVALUE		0x0U
+#define XHC_AXILPM_WIDTH			32U
+#define XHC_AXILPM__WIDTH			32U
+#define XHC_AXILPM_ALL_L			31U
+#define XHC_AXILPM_ALL_R			0U
+#define XHC_AXILPM__ALL_L			31U
+#define XHC_AXILPM__ALL_R			0U
+#define XHC_AXILPM_DATAMASK			0xffffffffU
+#define XHC_AXILPM_RDWRMASK			0x00000000U
+#define XHC_AXILPM_RESETVALUE			0x00000000U
+
+#define XHC_AXIQOS_OFFSET			0xc14U
+#define XHC_AXIQOS_BASE				0xc14U
+#define XHC_AXIQOS__WQOS3_L			31U
+#define XHC_AXIQOS__WQOS3_R			28U
+#define XHC_AXIQOS__WQOS3_WIDTH			4U
+#define XHC_AXIQOS__WQOS3_RESETVALUE		0x0U
+#define XHC_AXIQOS__WQOS2_L			27U
+#define XHC_AXIQOS__WQOS2_R			24U
+#define XHC_AXIQOS__WQOS2_WIDTH			4U
+#define XHC_AXIQOS__WQOS2_RESETVALUE		0x0U
+#define XHC_AXIQOS__WQOS1_L			23U
+#define XHC_AXIQOS__WQOS1_R			20U
+#define XHC_AXIQOS__WQOS1_WIDTH			4U
+#define XHC_AXIQOS__WQOS1_RESETVALUE		0x0U
+#define XHC_AXIQOS__WQOS0_L			19U
+#define XHC_AXIQOS__WQOS0_R			16U
+#define XHC_AXIQOS__WQOS0_WIDTH			4U
+#define XHC_AXIQOS__WQOS0_RESETVALUE		0x0U
+#define XHC_AXIQOS__RQOS3_L			15U
+#define XHC_AXIQOS__RQOS3_R			12U
+#define XHC_AXIQOS__RQOS3_WIDTH			4U
+#define XHC_AXIQOS__RQOS3_RESETVALUE		0x0U
+#define XHC_AXIQOS__RQOS2_L			11U
+#define XHC_AXIQOS__RQOS2_R			8U
+#define XHC_AXIQOS__RQOS2_WIDTH			4U
+#define XHC_AXIQOS__RQOS2_RESETVALUE		0x0U
+#define XHC_AXIQOS__RQOS1_L			7U
+#define XHC_AXIQOS__RQOS1_R			4U
+#define XHC_AXIQOS__RQOS1_WIDTH			4U
+#define XHC_AXIQOS__RQOS1_RESETVALUE		0x0U
+#define XHC_AXIQOS__RQOS0_L			3U
+#define XHC_AXIQOS__RQOS0_R			0U
+#define XHC_AXIQOS__RQOS0_WIDTH			4U
+#define XHC_AXIQOS__RQOS0_RESETVALUE		0x0U
+#define XHC_AXIQOS_WIDTH			32U
+#define XHC_AXIQOS__WIDTH			32U
+#define XHC_AXIQOS_ALL_L			31U
+#define XHC_AXIQOS_ALL_R			0U
+#define XHC_AXIQOS__ALL_L			31U
+#define XHC_AXIQOS__ALL_R			0U
+#define XHC_AXIQOS_DATAMASK			0xffffffffU
+#define XHC_AXIQOS_RDWRMASK			0x00000000U
+#define XHC_AXIQOS_RESETVALUE			0x00000000U
+
+#define XHC_ECHCSR_OFFSET			0xc20U
+#define XHC_ECHCSR_BASE				0xc20U
+#define XHC_ECHCSR__CLK_L			31U
+#define XHC_ECHCSR__CLK_R			21U
+#define XHC_ECHCSR__CLK_WIDTH			11U
+#define XHC_ECHCSR__CLK_RESETVALUE		0x0U
+#define XHC_ECHCSR__reserved_L			20U
+#define XHC_ECHCSR__reserved_R			19U
+#define XHC_ECHCSR__reserved_WIDTH		2U
+#define XHC_ECHCSR__reserved_RESETVALUE		0x0U
+#define XHC_ECHCSR__WID_L			18U
+#define XHC_ECHCSR__WID_R			16U
+#define XHC_ECHCSR__WID_WIDTH			3U
+#define XHC_ECHCSR__WID_RESETVALUE		0x0U
+#define XHC_ECHCSR__NCP_L			15U
+#define XHC_ECHCSR__NCP_R			8U
+#define XHC_ECHCSR__NCP_WIDTH			8U
+#define XHC_ECHCSR__NCP_RESETVALUE		0x04U
+#define XHC_ECHCSR__CID_L			7U
+#define XHC_ECHCSR__CID_R			0U
+#define XHC_ECHCSR__CID_WIDTH			8U
+#define XHC_ECHCSR__CID_RESETVALUE		0xc1U
+#define XHC_ECHCSR_WIDTH			32U
+#define XHC_ECHCSR__WIDTH			32U
+#define XHC_ECHCSR_ALL_L			31U
+#define XHC_ECHCSR_ALL_R			0U
+#define XHC_ECHCSR__ALL_L			31U
+#define XHC_ECHCSR__ALL_R			0U
+#define XHC_ECHCSR_DATAMASK			0xffffffffU
+#define XHC_ECHCSR_RDWRMASK			0x00000000U
+#define XHC_ECHCSR_RESETVALUE			0x000004c1U
+
+#define XHC_CSRSPC_OFFSET			0xc24U
+#define XHC_CSRSPC_BASE				0xc24U
+#define XHC_CSRSPC__MAJ_L			31U
+#define XHC_CSRSPC__MAJ_R			28U
+#define XHC_CSRSPC__MAJ_WIDTH			4U
+#define XHC_CSRSPC__MAJ_RESETVALUE		0x0U
+#define XHC_CSRSPC__MIN_L			27U
+#define XHC_CSRSPC__MIN_R			24U
+#define XHC_CSRSPC__MIN_WIDTH			4U
+#define XHC_CSRSPC__MIN_RESETVALUE		0x0U
+#define XHC_CSRSPC__RLS_L			23U
+#define XHC_CSRSPC__RLS_R			20U
+#define XHC_CSRSPC__RLS_WIDTH			4U
+#define XHC_CSRSPC__RLS_RESETVALUE		0x0U
+#define XHC_CSRSPC__reserved_L			19U
+#define XHC_CSRSPC__reserved_R			3U
+#define XHC_CSRSPC__reserved_WIDTH		17U
+#define XHC_CSRSPC__reserved_RESETVALUE		0x0U
+#define XHC_CSRSPC__ASP				2U
+#define XHC_CSRSPC__ASP_L			2U
+#define XHC_CSRSPC__ASP_R			2U
+#define XHC_CSRSPC__ASP_WIDTH			1U
+#define XHC_CSRSPC__ASP_RESETVALUE		0x0U
+#define XHC_CSRSPC__TYP_L			1U
+#define XHC_CSRSPC__TYP_R			0U
+#define XHC_CSRSPC__TYP_WIDTH			2U
+#define XHC_CSRSPC__TYP_RESETVALUE		0x0U
+#define XHC_CSRSPC_WIDTH			32U
+#define XHC_CSRSPC__WIDTH			32U
+#define XHC_CSRSPC_ALL_L			31U
+#define XHC_CSRSPC_ALL_R			0U
+#define XHC_CSRSPC__ALL_L			31U
+#define XHC_CSRSPC__ALL_R			0U
+#define XHC_CSRSPC_DATAMASK			0xffffffffU
+#define XHC_CSRSPC_RDWRMASK			0x00000000U
+#define XHC_CSRSPC_RESETVALUE			0x00000000U
+
+#define XHC_ECHAIU_OFFSET			0xc30U
+#define XHC_ECHAIU_BASE				0xc30U
+#define XHC_ECHAIU__DMA_L			31U
+#define XHC_ECHAIU__DMA_R			30U
+#define XHC_ECHAIU__DMA_WIDTH			2U
+#define XHC_ECHAIU__DMA_RESETVALUE		0x1U
+#define XHC_ECHAIU__PBRS_L			29U
+#define XHC_ECHAIU__PBRS_R			28U
+#define XHC_ECHAIU__PBRS_WIDTH			2U
+#define XHC_ECHAIU__PBRS_RESETVALUE		0x0U
+#define XHC_ECHAIU__PBR2_L			27U
+#define XHC_ECHAIU__PBR2_R			26U
+#define XHC_ECHAIU__PBR2_WIDTH			2U
+#define XHC_ECHAIU__PBR2_RESETVALUE		0x0U
+#define XHC_ECHAIU__SCHS_L			25U
+#define XHC_ECHAIU__SCHS_R			24U
+#define XHC_ECHAIU__SCHS_WIDTH			2U
+#define XHC_ECHAIU__SCHS_RESETVALUE		0x0U
+#define XHC_ECHAIU__SCH2_L			23U
+#define XHC_ECHAIU__SCH2_R			22U
+#define XHC_ECHAIU__SCH2_WIDTH			2U
+#define XHC_ECHAIU__SCH2_RESETVALUE		0x0U
+#define XHC_ECHAIU__CHMS_L			21U
+#define XHC_ECHAIU__CHMS_R			20U
+#define XHC_ECHAIU__CHMS_WIDTH			2U
+#define XHC_ECHAIU__CHMS_RESETVALUE		0x3U
+#define XHC_ECHAIU__CHM2_L			19U
+#define XHC_ECHAIU__CHM2_R			18U
+#define XHC_ECHAIU__CHM2_WIDTH			2U
+#define XHC_ECHAIU__CHM2_RESETVALUE		0x0U
+#define XHC_ECHAIU__reserved_L			17U
+#define XHC_ECHAIU__reserved_R			16U
+#define XHC_ECHAIU__reserved_WIDTH		2U
+#define XHC_ECHAIU__reserved_RESETVALUE		0x0U
+#define XHC_ECHAIU__NCP_L			15U
+#define XHC_ECHAIU__NCP_R			8U
+#define XHC_ECHAIU__NCP_WIDTH			8U
+#define XHC_ECHAIU__NCP_RESETVALUE		0x04U
+#define XHC_ECHAIU__CID_L			7U
+#define XHC_ECHAIU__CID_R			0U
+#define XHC_ECHAIU__CID_WIDTH			8U
+#define XHC_ECHAIU__CID_RESETVALUE		0xc2U
+#define XHC_ECHAIU_WIDTH			32U
+#define XHC_ECHAIU__WIDTH			32U
+#define XHC_ECHAIU_ALL_L			31U
+#define XHC_ECHAIU_ALL_R			0U
+#define XHC_ECHAIU__ALL_L			31U
+#define XHC_ECHAIU__ALL_R			0U
+#define XHC_ECHAIU_DATAMASK			0xffffffffU
+#define XHC_ECHAIU_RDWRMASK			0x00000000U
+#define XHC_ECHAIU_RESETVALUE			0x403004c2U
+
+#define XHC_AIUDMA_OFFSET			0xc34U
+#define XHC_AIUDMA_BASE				0xc34U
+#define XHC_AIUDMA__WRMB_L			31U
+#define XHC_AIUDMA__WRMB_R			28U
+#define XHC_AIUDMA__WRMB_WIDTH			4U
+#define XHC_AIUDMA__WRMB_RESETVALUE		0x0U
+#define XHC_AIUDMA__WRD_L			27U
+#define XHC_AIUDMA__WRD_R			26U
+#define XHC_AIUDMA__WRD_WIDTH			2U
+#define XHC_AIUDMA__WRD_RESETVALUE		0x0U
+#define XHC_AIUDMA__WED_L			25U
+#define XHC_AIUDMA__WED_R			24U
+#define XHC_AIUDMA__WED_WIDTH			2U
+#define XHC_AIUDMA__WED_RESETVALUE		0x0U
+#define XHC_AIUDMA__WMS_L			23U
+#define XHC_AIUDMA__WMS_R			22U
+#define XHC_AIUDMA__WMS_WIDTH			2U
+#define XHC_AIUDMA__WMS_RESETVALUE		0x0U
+#define XHC_AIUDMA__WMI_L			21U
+#define XHC_AIUDMA__WMI_R			20U
+#define XHC_AIUDMA__WMI_WIDTH			2U
+#define XHC_AIUDMA__WMI_RESETVALUE		0x0U
+#define XHC_AIUDMA__WPF_L			19U
+#define XHC_AIUDMA__WPF_R			16U
+#define XHC_AIUDMA__WPF_WIDTH			4U
+#define XHC_AIUDMA__WPF_RESETVALUE		0x6U
+#define XHC_AIUDMA__RRMB_L			15U
+#define XHC_AIUDMA__RRMB_R			12U
+#define XHC_AIUDMA__RRMB_WIDTH			4U
+#define XHC_AIUDMA__RRMB_RESETVALUE		0x0U
+#define XHC_AIUDMA__RTD_L			11U
+#define XHC_AIUDMA__RTD_R			10U
+#define XHC_AIUDMA__RTD_WIDTH			2U
+#define XHC_AIUDMA__RTD_RESETVALUE		0x0U
+#define XHC_AIUDMA__RTF_L			9U
+#define XHC_AIUDMA__RTF_R			8U
+#define XHC_AIUDMA__RTF_WIDTH			2U
+#define XHC_AIUDMA__RTF_RESETVALUE		0x0U
+#define XHC_AIUDMA__RM_S_L			7U
+#define XHC_AIUDMA__RM_S_R			6U
+#define XHC_AIUDMA__RM_S_WIDTH			2U
+#define XHC_AIUDMA__RM_S_RESETVALUE		0x0U
+#define XHC_AIUDMA__TFBS_L			5U
+#define XHC_AIUDMA__TFBS_R			3U
+#define XHC_AIUDMA__TFBS_WIDTH			3U
+#define XHC_AIUDMA__TFBS_RESETVALUE		0x0U
+#define XHC_AIUDMA__reserved_L			2U
+#define XHC_AIUDMA__reserved_R			0U
+#define XHC_AIUDMA__reserved_WIDTH		3U
+#define XHC_AIUDMA__reserved_RESETVALUE		0x0U
+#define XHC_AIUDMA_WIDTH			32U
+#define XHC_AIUDMA__WIDTH			32U
+#define XHC_AIUDMA_ALL_L			31U
+#define XHC_AIUDMA_ALL_R			0U
+#define XHC_AIUDMA__ALL_L			31U
+#define XHC_AIUDMA__ALL_R			0U
+#define XHC_AIUDMA_DATAMASK			0xffffffffU
+#define XHC_AIUDMA_RDWRMASK			0x00000000U
+#define XHC_AIUDMA_RESETVALUE			0x00060000U
+
+#define XHC_AIUFLA_OFFSET			0xc38U
+#define XHC_AIUFLA_BASE				0xc38U
+#define XHC_AIUFLA__ACLK_L			31U
+#define XHC_AIUFLA__ACLK_R			23U
+#define XHC_AIUFLA__ACLK_WIDTH			9U
+#define XHC_AIUFLA__ACLK_RESETVALUE		0x0U
+#define XHC_AIUFLA__MFLV_L			22U
+#define XHC_AIUFLA__MFLV_R			7U
+#define XHC_AIUFLA__MFLV_WIDTH			16U
+#define XHC_AIUFLA__MFLV_RESETVALUE		0x0000U
+#define XHC_AIUFLA__NFC				6U
+#define XHC_AIUFLA__NFC_L			6U
+#define XHC_AIUFLA__NFC_R			6U
+#define XHC_AIUFLA__NFC_WIDTH			1U
+#define XHC_AIUFLA__NFC_RESETVALUE		0x1U
+#define XHC_AIUFLA__FLADJ_L			5U
+#define XHC_AIUFLA__FLADJ_R			0U
+#define XHC_AIUFLA__FLADJ_WIDTH			6U
+#define XHC_AIUFLA__FLADJ_RESETVALUE		0x20U
+#define XHC_AIUFLA_WIDTH			32U
+#define XHC_AIUFLA__WIDTH			32U
+#define XHC_AIUFLA_ALL_L			31U
+#define XHC_AIUFLA_ALL_R			0U
+#define XHC_AIUFLA__ALL_L			31U
+#define XHC_AIUFLA__ALL_R			0U
+#define XHC_AIUFLA_DATAMASK			0xffffffffU
+#define XHC_AIUFLA_RDWRMASK			0x00000000U
+#define XHC_AIUFLA_RESETVALUE			0x00000060U
+
+#define XHC_AIUCFG_OFFSET			0xc3cU
+#define XHC_AIUCFG_BASE				0xc3cU
+#define XHC_AIUCFG__ISO_L			30U
+#define XHC_AIUCFG__ISO_R			28U
+#define XHC_AIUCFG__ISO_WIDTH			3U
+#define XHC_AIUCFG__ISO_RESETVALUE		0x0U
+#define XHC_AIUCFG__EPC_L			26U
+#define XHC_AIUCFG__EPC_R			24U
+#define XHC_AIUCFG__EPC_WIDTH			3U
+#define XHC_AIUCFG__EPC_RESETVALUE		0x5U
+#define XHC_AIUCFG__PTQ_L			22U
+#define XHC_AIUCFG__PTQ_R			20U
+#define XHC_AIUCFG__PTQ_WIDTH			3U
+#define XHC_AIUCFG__PTQ_RESETVALUE		0x3U
+#define XHC_AIUCFG__NTQ_L			18U
+#define XHC_AIUCFG__NTQ_R			16U
+#define XHC_AIUCFG__NTQ_WIDTH			3U
+#define XHC_AIUCFG__NTQ_RESETVALUE		0x3U
+#define XHC_AIUCFG__HID				15U
+#define XHC_AIUCFG__HID_L			15U
+#define XHC_AIUCFG__HID_R			15U
+#define XHC_AIUCFG__HID_WIDTH			1U
+#define XHC_AIUCFG__HID_RESETVALUE		0x0U
+#define XHC_AIUCFG__EPS_L			14U
+#define XHC_AIUCFG__EPS_R			12U
+#define XHC_AIUCFG__EPS_WIDTH			3U
+#define XHC_AIUCFG__EPS_RESETVALUE		0x0U
+#define XHC_AIUCFG__reserved_L			11U
+#define XHC_AIUCFG__reserved_R			9U
+#define XHC_AIUCFG__reserved_WIDTH		3U
+#define XHC_AIUCFG__reserved_RESETVALUE		0x0U
+#define XHC_AIUCFG__PEP2_L			8U
+#define XHC_AIUCFG__PEP2_R			6U
+#define XHC_AIUCFG__PEP2_WIDTH			3U
+#define XHC_AIUCFG__PEP2_RESETVALUE		0x4U
+#define XHC_AIUCFG__MELADJ_L			5U
+#define XHC_AIUCFG__MELADJ_R			0U
+#define XHC_AIUCFG__MELADJ_WIDTH		6U
+#define XHC_AIUCFG__MELADJ_RESETVALUE		0x0U
+#define XHC_AIUCFG__RESERVED_0			31U
+#define XHC_AIUCFG__RESERVED_0_L		31U
+#define XHC_AIUCFG__RESERVED_0_R		31U
+#define XHC_AIUCFG__RESERVED_1			27U
+#define XHC_AIUCFG__RESERVED_1_L		27U
+#define XHC_AIUCFG__RESERVED_1_R		27U
+#define XHC_AIUCFG__RESERVED_2			23U
+#define XHC_AIUCFG__RESERVED_2_L		23U
+#define XHC_AIUCFG__RESERVED_2_R		23U
+#define XHC_AIUCFG__RESERVED_3			19U
+#define XHC_AIUCFG__RESERVED_3_L		19U
+#define XHC_AIUCFG__RESERVED_3_R		19U
+#define XHC_AIUCFG_WIDTH			31U
+#define XHC_AIUCFG__WIDTH			31U
+#define XHC_AIUCFG_ALL_L			30U
+#define XHC_AIUCFG_ALL_R			0U
+#define XHC_AIUCFG__ALL_L			30U
+#define XHC_AIUCFG__ALL_R			0U
+#define XHC_AIUCFG_DATAMASK			0x7777ffffU
+#define XHC_AIUCFG_RDWRMASK			0x88880000U
+#define XHC_AIUCFG_RESETVALUE			0x05330100U
+
+#define XHC_ECHFSC_OFFSET			0xc40U
+#define XHC_ECHFSC_BASE				0xc40U
+#define XHC_ECHFSC__reserved_L			31U
+#define XHC_ECHFSC__reserved_R			24U
+#define XHC_ECHFSC__reserved_WIDTH		8U
+#define XHC_ECHFSC__reserved_RESETVALUE		0x00U
+#define XHC_ECHFSC__WRMB_L			23U
+#define XHC_ECHFSC__WRMB_R			20U
+#define XHC_ECHFSC__WRMB_WIDTH			4U
+#define XHC_ECHFSC__WRMB_RESETVALUE		0x0U
+#define XHC_ECHFSC__RRMB_L			19U
+#define XHC_ECHFSC__RRMB_R			16U
+#define XHC_ECHFSC__RRMB_WIDTH			4U
+#define XHC_ECHFSC__RRMB_RESETVALUE		0x0U
+#define XHC_ECHFSC__NCP_L			15U
+#define XHC_ECHFSC__NCP_R			8U
+#define XHC_ECHFSC__NCP_WIDTH			8U
+#define XHC_ECHFSC__NCP_RESETVALUE		0x50U
+#define XHC_ECHFSC__CID_L			7U
+#define XHC_ECHFSC__CID_R			0U
+#define XHC_ECHFSC__CID_WIDTH			8U
+#define XHC_ECHFSC__CID_RESETVALUE		0xc3U
+#define XHC_ECHFSC_WIDTH			32U
+#define XHC_ECHFSC__WIDTH			32U
+#define XHC_ECHFSC_ALL_L			31U
+#define XHC_ECHFSC_ALL_R			0U
+#define XHC_ECHFSC__ALL_L			31U
+#define XHC_ECHFSC__ALL_R			0U
+#define XHC_ECHFSC_DATAMASK			0xffffffffU
+#define XHC_ECHFSC_RDWRMASK			0x00000000U
+#define XHC_ECHFSC_RESETVALUE			0x000050c3U
+
+#define XHC_FSCPOC_OFFSET			0xc54U
+#define XHC_FSCPOC_BASE				0xc54U
+#define XHC_FSCPOC__NCS_L			31U
+#define XHC_FSCPOC__NCS_R			28U
+#define XHC_FSCPOC__NCS_WIDTH			4U
+#define XHC_FSCPOC__NCS_RESETVALUE		0x0U
+#define XHC_FSCPOC__FSIZ_L			22U
+#define XHC_FSCPOC__FSIZ_R			18U
+#define XHC_FSCPOC__FSIZ_WIDTH			5U
+#define XHC_FSCPOC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSCPOC__PSIZ_L			16U
+#define XHC_FSCPOC__PSIZ_R			12U
+#define XHC_FSCPOC__PSIZ_WIDTH			5U
+#define XHC_FSCPOC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSCPOC__reserved_L			11U
+#define XHC_FSCPOC__reserved_R			5U
+#define XHC_FSCPOC__reserved_WIDTH		7U
+#define XHC_FSCPOC__reserved_RESETVALUE		0x0U
+#define XHC_FSCPOC__TSIZ_L			4U
+#define XHC_FSCPOC__TSIZ_R			0U
+#define XHC_FSCPOC__TSIZ_WIDTH			5U
+#define XHC_FSCPOC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCPOC__RESERVED_L			27U
+#define XHC_FSCPOC__RESERVED_R			23U
+#define XHC_FSCPOC_WIDTH			32U
+#define XHC_FSCPOC__WIDTH			32U
+#define XHC_FSCPOC_ALL_L			31U
+#define XHC_FSCPOC_ALL_R			0U
+#define XHC_FSCPOC__ALL_L			31U
+#define XHC_FSCPOC__ALL_R			0U
+#define XHC_FSCPOC_DATAMASK			0xf07dffffU
+#define XHC_FSCPOC_RDWRMASK			0x0f820000U
+#define XHC_FSCPOC_RESETVALUE			0x00000000U
+
+#define XHC_FSCGOC_OFFSET			0xc58U
+#define XHC_FSCGOC_BASE				0xc58U
+#define XHC_FSCGOC__NCS_L			31U
+#define XHC_FSCGOC__NCS_R			28U
+#define XHC_FSCGOC__NCS_WIDTH			4U
+#define XHC_FSCGOC__NCS_RESETVALUE		0x0U
+#define XHC_FSCGOC__FSIZ_L			22U
+#define XHC_FSCGOC__FSIZ_R			18U
+#define XHC_FSCGOC__FSIZ_WIDTH			5U
+#define XHC_FSCGOC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSCGOC__PSIZ_L			16U
+#define XHC_FSCGOC__PSIZ_R			12U
+#define XHC_FSCGOC__PSIZ_WIDTH			5U
+#define XHC_FSCGOC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSCGOC__reserved_L			11U
+#define XHC_FSCGOC__reserved_R			5U
+#define XHC_FSCGOC__reserved_WIDTH		7U
+#define XHC_FSCGOC__reserved_RESETVALUE		0x0U
+#define XHC_FSCGOC__TSIZ_L			4U
+#define XHC_FSCGOC__TSIZ_R			0U
+#define XHC_FSCGOC__TSIZ_WIDTH			5U
+#define XHC_FSCGOC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCGOC__RESERVED_L			27U
+#define XHC_FSCGOC__RESERVED_R			23U
+#define XHC_FSCGOC_WIDTH			32U
+#define XHC_FSCGOC__WIDTH			32U
+#define XHC_FSCGOC_ALL_L			31U
+#define XHC_FSCGOC_ALL_R			0U
+#define XHC_FSCGOC__ALL_L			31U
+#define XHC_FSCGOC__ALL_R			0U
+#define XHC_FSCGOC_DATAMASK			0xf07dffffU
+#define XHC_FSCGOC_RDWRMASK			0x0f820000U
+#define XHC_FSCGOC_RESETVALUE			0x00000000U
+
+#define XHC_FSCNOC_OFFSET			0xc5cU
+#define XHC_FSCNOC_BASE				0xc5cU
+#define XHC_FSCNOC__NCS_L			31U
+#define XHC_FSCNOC__NCS_R			28U
+#define XHC_FSCNOC__NCS_WIDTH			4U
+#define XHC_FSCNOC__NCS_RESETVALUE		0x0U
+#define XHC_FSCNOC__FSIZ_L			22U
+#define XHC_FSCNOC__FSIZ_R			18U
+#define XHC_FSCNOC__FSIZ_WIDTH			5U
+#define XHC_FSCNOC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSCNOC__PSIZ_L			16U
+#define XHC_FSCNOC__PSIZ_R			12U
+#define XHC_FSCNOC__PSIZ_WIDTH			5U
+#define XHC_FSCNOC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSCNOC__reserved_L			11U
+#define XHC_FSCNOC__reserved_R			5U
+#define XHC_FSCNOC__reserved_WIDTH		7U
+#define XHC_FSCNOC__reserved_RESETVALUE		0x0U
+#define XHC_FSCNOC__TSIZ_L			4U
+#define XHC_FSCNOC__TSIZ_R			0U
+#define XHC_FSCNOC__TSIZ_WIDTH			5U
+#define XHC_FSCNOC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCNOC__RESERVED_L			27U
+#define XHC_FSCNOC__RESERVED_R			23U
+#define XHC_FSCNOC_WIDTH			32U
+#define XHC_FSCNOC__WIDTH			32U
+#define XHC_FSCNOC_ALL_L			31U
+#define XHC_FSCNOC_ALL_R			0U
+#define XHC_FSCNOC__ALL_L			31U
+#define XHC_FSCNOC__ALL_R			0U
+#define XHC_FSCNOC_DATAMASK			0xf07dffffU
+#define XHC_FSCNOC_RDWRMASK			0x0f820000U
+#define XHC_FSCNOC_RESETVALUE			0x00000000U
+
+#define XHC_FSCAIC_OFFSET			0xc60U
+#define XHC_FSCAIC_BASE				0xc60U
+#define XHC_FSCAIC__FSIZ_L			22U
+#define XHC_FSCAIC__FSIZ_R			18U
+#define XHC_FSCAIC__FSIZ_WIDTH			5U
+#define XHC_FSCAIC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSCAIC__PSIZ_L			16U
+#define XHC_FSCAIC__PSIZ_R			12U
+#define XHC_FSCAIC__PSIZ_WIDTH			5U
+#define XHC_FSCAIC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSCAIC__reserved_L			11U
+#define XHC_FSCAIC__reserved_R			0U
+#define XHC_FSCAIC__reserved_WIDTH		12U
+#define XHC_FSCAIC__reserved_RESETVALUE		0x000U
+#define XHC_FSCAIC__RESERVED_L			31U
+#define XHC_FSCAIC__RESERVED_R			23U
+#define XHC_FSCAIC_WIDTH			23U
+#define XHC_FSCAIC__WIDTH			23U
+#define XHC_FSCAIC_ALL_L			22U
+#define XHC_FSCAIC_ALL_R			0U
+#define XHC_FSCAIC__ALL_L			22U
+#define XHC_FSCAIC__ALL_R			0U
+#define XHC_FSCAIC_DATAMASK			0x007dffffU
+#define XHC_FSCAIC_RDWRMASK			0xff820000U
+#define XHC_FSCAIC_RESETVALUE			0x000000U
+
+#define XHC_FSCPIC_OFFSET			0xc64U
+#define XHC_FSCPIC_BASE				0xc64U
+#define XHC_FSCPIC__NCS_L			31U
+#define XHC_FSCPIC__NCS_R			28U
+#define XHC_FSCPIC__NCS_WIDTH			4U
+#define XHC_FSCPIC__NCS_RESETVALUE		0x0U
+#define XHC_FSCPIC__reserved_L			27U
+#define XHC_FSCPIC__reserved_R			5U
+#define XHC_FSCPIC__reserved_WIDTH		23U
+#define XHC_FSCPIC__reserved_RESETVALUE		0x0U
+#define XHC_FSCPIC__TSIZ_L			4U
+#define XHC_FSCPIC__TSIZ_R			0U
+#define XHC_FSCPIC__TSIZ_WIDTH			5U
+#define XHC_FSCPIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCPIC_WIDTH			32U
+#define XHC_FSCPIC__WIDTH			32U
+#define XHC_FSCPIC_ALL_L			31U
+#define XHC_FSCPIC_ALL_R			0U
+#define XHC_FSCPIC__ALL_L			31U
+#define XHC_FSCPIC__ALL_R			0U
+#define XHC_FSCPIC_DATAMASK			0xffffffffU
+#define XHC_FSCPIC_RDWRMASK			0x00000000U
+#define XHC_FSCPIC_RESETVALUE			0x00000000U
+
+#define XHC_FSCGIC_OFFSET			0xc68U
+#define XHC_FSCGIC_BASE				0xc68U
+#define XHC_FSCGIC__NCS_L			31U
+#define XHC_FSCGIC__NCS_R			28U
+#define XHC_FSCGIC__NCS_WIDTH			4U
+#define XHC_FSCGIC__NCS_RESETVALUE		0x0U
+#define XHC_FSCGIC__reserved_L			27U
+#define XHC_FSCGIC__reserved_R			5U
+#define XHC_FSCGIC__reserved_WIDTH		23U
+#define XHC_FSCGIC__reserved_RESETVALUE		0x0U
+#define XHC_FSCGIC__TSIZ_L			4U
+#define XHC_FSCGIC__TSIZ_R			0U
+#define XHC_FSCGIC__TSIZ_WIDTH			5U
+#define XHC_FSCGIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCGIC_WIDTH			32U
+#define XHC_FSCGIC__WIDTH			32U
+#define XHC_FSCGIC_ALL_L			31U
+#define XHC_FSCGIC_ALL_R			0U
+#define XHC_FSCGIC__ALL_L			31U
+#define XHC_FSCGIC__ALL_R			0U
+#define XHC_FSCGIC_DATAMASK			0xffffffffU
+#define XHC_FSCGIC_RDWRMASK			0x00000000U
+#define XHC_FSCGIC_RESETVALUE			0x00000000U
+
+#define XHC_FSCNIC_OFFSET			0xc6cU
+#define XHC_FSCNIC_BASE				0xc6cU
+#define XHC_FSCNIC__NCS_L			31U
+#define XHC_FSCNIC__NCS_R			28U
+#define XHC_FSCNIC__NCS_WIDTH			4U
+#define XHC_FSCNIC__NCS_RESETVALUE		0x0U
+#define XHC_FSCNIC__reserved_L			27U
+#define XHC_FSCNIC__reserved_R			5U
+#define XHC_FSCNIC__reserved_WIDTH		23U
+#define XHC_FSCNIC__reserved_RESETVALUE		0x0U
+#define XHC_FSCNIC__TSIZ_L			4U
+#define XHC_FSCNIC__TSIZ_R			0U
+#define XHC_FSCNIC__TSIZ_WIDTH			5U
+#define XHC_FSCNIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSCNIC_WIDTH			32U
+#define XHC_FSCNIC__WIDTH			32U
+#define XHC_FSCNIC_ALL_L			31U
+#define XHC_FSCNIC_ALL_R			0U
+#define XHC_FSCNIC__ALL_L			31U
+#define XHC_FSCNIC__ALL_R			0U
+#define XHC_FSCNIC_DATAMASK			0xffffffffU
+#define XHC_FSCNIC_RDWRMASK			0x00000000U
+#define XHC_FSCNIC_RESETVALUE			0x00000000U
+
+#define XHC_ECHPRT_OFFSET			0xc70U
+#define XHC_ECHPRT_BASE				0xc70U
+#define XHC_ECHPRT__TDP				31U
+#define XHC_ECHPRT__TDP_L			31U
+#define XHC_ECHPRT__TDP_R			31U
+#define XHC_ECHPRT__TDP_WIDTH			1U
+#define XHC_ECHPRT__TDP_RESETVALUE		0x0U
+#define XHC_ECHPRT__RDP				30U
+#define XHC_ECHPRT__RDP_L			30U
+#define XHC_ECHPRT__RDP_R			30U
+#define XHC_ECHPRT__RDP_WIDTH			1U
+#define XHC_ECHPRT__RDP_RESETVALUE		0x0U
+#define XHC_ECHPRT__reserved_L			29U
+#define XHC_ECHPRT__reserved_R			25U
+#define XHC_ECHPRT__reserved_WIDTH		5U
+#define XHC_ECHPRT__reserved_RESETVALUE		0x0U
+#define XHC_ECHPRT__MFT_L			24U
+#define XHC_ECHPRT__MFT_R			17U
+#define XHC_ECHPRT__MFT_WIDTH			8U
+#define XHC_ECHPRT__MFT_RESETVALUE		0x7dU
+#define XHC_ECHPRT__HST				16U
+#define XHC_ECHPRT__HST_L			16U
+#define XHC_ECHPRT__HST_R			16U
+#define XHC_ECHPRT__HST_WIDTH			1U
+#define XHC_ECHPRT__HST_RESETVALUE		0x0U
+#define XHC_ECHPRT__NCP_L			15U
+#define XHC_ECHPRT__NCP_R			8U
+#define XHC_ECHPRT__NCP_WIDTH			8U
+#define XHC_ECHPRT__NCP_RESETVALUE		0x04U
+#define XHC_ECHPRT__CID_L			7U
+#define XHC_ECHPRT__CID_R			0U
+#define XHC_ECHPRT__CID_WIDTH			8U
+#define XHC_ECHPRT__CID_RESETVALUE		0xc4U
+#define XHC_ECHPRT_WIDTH			32U
+#define XHC_ECHPRT__WIDTH			32U
+#define XHC_ECHPRT_ALL_L			31U
+#define XHC_ECHPRT_ALL_R			0U
+#define XHC_ECHPRT__ALL_L			31U
+#define XHC_ECHPRT__ALL_R			0U
+#define XHC_ECHPRT_DATAMASK			0xffffffffU
+#define XHC_ECHPRT_RDWRMASK			0x00000000U
+#define XHC_ECHPRT_RESETVALUE			0x00fa04c4U
+
+#define XHC_PRTHSC_OFFSET			0xc78U
+#define XHC_PRTHSC_BASE				0xc78U
+#define XHC_PRTHSC__TMR_L			31U
+#define XHC_PRTHSC__TMR_R			16U
+#define XHC_PRTHSC__TMR_WIDTH			16U
+#define XHC_PRTHSC__TMR_RESETVALUE		0x0000U
+#define XHC_PRTHSC__RSL_L			7U
+#define XHC_PRTHSC__RSL_R			6U
+#define XHC_PRTHSC__RSL_WIDTH			2U
+#define XHC_PRTHSC__RSL_RESETVALUE		0x0U
+#define XHC_PRTHSC__AS_M_L			5U
+#define XHC_PRTHSC__AS_M_R			4U
+#define XHC_PRTHSC__AS_M_WIDTH			2U
+#define XHC_PRTHSC__AS_M_RESETVALUE		0x0U
+#define XHC_PRTHSC__CMD_L			3U
+#define XHC_PRTHSC__CMD_R			2U
+#define XHC_PRTHSC__CMD_WIDTH			2U
+#define XHC_PRTHSC__CMD_RESETVALUE		0x0U
+#define XHC_PRTHSC__reserved			1U
+#define XHC_PRTHSC__reserved_L			1U
+#define XHC_PRTHSC__reserved_R			1U
+#define XHC_PRTHSC__reserved_WIDTH		1U
+#define XHC_PRTHSC__reserved_RESETVALUE		0x0U
+#define XHC_PRTHSC__STB				0U
+#define XHC_PRTHSC__STB_L			0U
+#define XHC_PRTHSC__STB_R			0U
+#define XHC_PRTHSC__STB_WIDTH			1U
+#define XHC_PRTHSC__STB_RESETVALUE		0x0U
+#define XHC_PRTHSC__RESERVED_L			15U
+#define XHC_PRTHSC__RESERVED_R			8U
+#define XHC_PRTHSC_WIDTH			32U
+#define XHC_PRTHSC__WIDTH			32U
+#define XHC_PRTHSC_ALL_L			31U
+#define XHC_PRTHSC_ALL_R			0U
+#define XHC_PRTHSC__ALL_L			31U
+#define XHC_PRTHSC__ALL_R			0U
+#define XHC_PRTHSC_DATAMASK			0xffff00ffU
+#define XHC_PRTHSC_RDWRMASK			0x0000ff00U
+#define XHC_PRTHSC_RESETVALUE			0x00000000U
+
+#define XHC_PRTHSR_OFFSET			0xc7cU
+#define XHC_PRTHSR_BASE				0xc7cU
+#define XHC_PRTHSR__RDLY_L			31U
+#define XHC_PRTHSR__RDLY_R			24U
+#define XHC_PRTHSR__RDLY_WIDTH			8U
+#define XHC_PRTHSR__RDLY_RESETVALUE		0x00U
+#define XHC_PRTHSR__TDPP_L			23U
+#define XHC_PRTHSR__TDPP_R			16U
+#define XHC_PRTHSR__TDPP_WIDTH			8U
+#define XHC_PRTHSR__TDPP_RESETVALUE		0x00U
+#define XHC_PRTHSR__RDPP_L			15U
+#define XHC_PRTHSR__RDPP_R			8U
+#define XHC_PRTHSR__RDPP_WIDTH			8U
+#define XHC_PRTHSR__RDPP_RESETVALUE		0x00U
+#define XHC_PRTHSR__TRTY_L			7U
+#define XHC_PRTHSR__TRTY_R			0U
+#define XHC_PRTHSR__TRTY_WIDTH			8U
+#define XHC_PRTHSR__TRTY_RESETVALUE		0x00U
+#define XHC_PRTHSR_WIDTH			32U
+#define XHC_PRTHSR__WIDTH			32U
+#define XHC_PRTHSR_ALL_L			31U
+#define XHC_PRTHSR_ALL_R			0U
+#define XHC_PRTHSR__ALL_L			31U
+#define XHC_PRTHSR__ALL_R			0U
+#define XHC_PRTHSR_DATAMASK			0xffffffffU
+#define XHC_PRTHSR_RDWRMASK			0x00000000U
+#define XHC_PRTHSR_RESETVALUE			0x00000000U
+
+#define XHC_ECHRHS_OFFSET			0xc80U
+#define XHC_ECHRHS_BASE				0xc80U
+#define XHC_ECHRHS__RPO_L			30U
+#define XHC_ECHRHS__RPO_R			24U
+#define XHC_ECHRHS__RPO_WIDTH			7U
+#define XHC_ECHRHS__RPO_RESETVALUE		0x0U
+#define XHC_ECHRHS__reserved_L			23U
+#define XHC_ECHRHS__reserved_R			22U
+#define XHC_ECHRHS__reserved_WIDTH		2U
+#define XHC_ECHRHS__reserved_RESETVALUE		0x0U
+#define XHC_ECHRHS__RPN_L			21U
+#define XHC_ECHRHS__RPN_R			20U
+#define XHC_ECHRHS__RPN_WIDTH			2U
+#define XHC_ECHRHS__RPN_RESETVALUE		0x0U
+#define XHC_ECHRHS__DNR_L			19U
+#define XHC_ECHRHS__DNR_R			16U
+#define XHC_ECHRHS__DNR_WIDTH			4U
+#define XHC_ECHRHS__DNR_RESETVALUE		0x0U
+#define XHC_ECHRHS__NCP_L			15U
+#define XHC_ECHRHS__NCP_R			8U
+#define XHC_ECHRHS__NCP_WIDTH			8U
+#define XHC_ECHRHS__NCP_RESETVALUE		0x0cU
+#define XHC_ECHRHS__CID_L			7U
+#define XHC_ECHRHS__CID_R			0U
+#define XHC_ECHRHS__CID_WIDTH			8U
+#define XHC_ECHRHS__CID_RESETVALUE		0xc8U
+#define XHC_ECHRHS__RESERVED			31U
+#define XHC_ECHRHS__RESERVED_L			31U
+#define XHC_ECHRHS__RESERVED_R			31U
+#define XHC_ECHRHS_WIDTH			31U
+#define XHC_ECHRHS__WIDTH			31U
+#define XHC_ECHRHS_ALL_L			30U
+#define XHC_ECHRHS_ALL_R			0U
+#define XHC_ECHRHS__ALL_L			30U
+#define XHC_ECHRHS__ALL_R			0U
+#define XHC_ECHRHS_DATAMASK			0x7fffffffU
+#define XHC_ECHRHS_RDWRMASK			0x80000000U
+#define XHC_ECHRHS_RESETVALUE			0x00000cc8U
+
+#define XHC_RHSDES_OFFSET			0xc84U
+#define XHC_RHSDES_BASE				0xc84U
+#define XHC_RHSDES__PIS3_L			31U
+#define XHC_RHSDES__PIS3_R			30U
+#define XHC_RHSDES__PIS3_WIDTH			2U
+#define XHC_RHSDES__PIS3_RESETVALUE		0x0U
+#define XHC_RHSDES__HIST3			24U
+#define XHC_RHSDES__HIST3_L			24U
+#define XHC_RHSDES__HIST3_R			24U
+#define XHC_RHSDES__HIST3_WIDTH			1U
+#define XHC_RHSDES__HIST3_RESETVALUE		0x0U
+#define XHC_RHSDES__PIS2_L			23U
+#define XHC_RHSDES__PIS2_R			22U
+#define XHC_RHSDES__PIS2_WIDTH			2U
+#define XHC_RHSDES__PIS2_RESETVALUE		0x0U
+#define XHC_RHSDES__HIST2			16U
+#define XHC_RHSDES__HIST2_L			16U
+#define XHC_RHSDES__HIST2_R			16U
+#define XHC_RHSDES__HIST2_WIDTH			1U
+#define XHC_RHSDES__HIST2_RESETVALUE		0x0U
+#define XHC_RHSDES__PIS1_L			15U
+#define XHC_RHSDES__PIS1_R			14U
+#define XHC_RHSDES__PIS1_WIDTH			2U
+#define XHC_RHSDES__PIS1_RESETVALUE		0x0U
+#define XHC_RHSDES__HIST1			8U
+#define XHC_RHSDES__HIST1_L			8U
+#define XHC_RHSDES__HIST1_R			8U
+#define XHC_RHSDES__HIST1_WIDTH			1U
+#define XHC_RHSDES__HIST1_RESETVALUE		0x0U
+#define XHC_RHSDES__PIS0_L			7U
+#define XHC_RHSDES__PIS0_R			6U
+#define XHC_RHSDES__PIS0_WIDTH			2U
+#define XHC_RHSDES__PIS0_RESETVALUE		0x0U
+#define XHC_RHSDES__reserved_L			5U
+#define XHC_RHSDES__reserved_R			1U
+#define XHC_RHSDES__reserved_WIDTH		5U
+#define XHC_RHSDES__reserved_RESETVALUE		0x0U
+#define XHC_RHSDES__HIST0			0U
+#define XHC_RHSDES__HIST0_L			0U
+#define XHC_RHSDES__HIST0_R			0U
+#define XHC_RHSDES__HIST0_WIDTH			1U
+#define XHC_RHSDES__HIST0_RESETVALUE		0x0U
+#define XHC_RHSDES__RESERVED_0_L		29U
+#define XHC_RHSDES__RESERVED_0_R		25U
+#define XHC_RHSDES__RESERVED_1_L		21U
+#define XHC_RHSDES__RESERVED_1_R		17U
+#define XHC_RHSDES__RESERVED_2_L		13U
+#define XHC_RHSDES__RESERVED_2_R		9U
+#define XHC_RHSDES__RESERVED_L			29U
+#define XHC_RHSDES__RESERVED_R			25U
+#define XHC_RHSDES_WIDTH			32U
+#define XHC_RHSDES__WIDTH			32U
+#define XHC_RHSDES_ALL_L			31U
+#define XHC_RHSDES_ALL_R			0U
+#define XHC_RHSDES__ALL_L			31U
+#define XHC_RHSDES__ALL_R			0U
+#define XHC_RHSDES_DATAMASK			0xc1c1c1ffU
+#define XHC_RHSDES_RDWRMASK			0x3e3e3e00U
+#define XHC_RHSDES_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSC0_OFFSET			0xc90U
+#define XHC_RHSHSC0_BASE			0xc90U
+#define XHC_RHSHSC0__TMR_L			31U
+#define XHC_RHSHSC0__TMR_R			16U
+#define XHC_RHSHSC0__TMR_WIDTH			16U
+#define XHC_RHSHSC0__TMR_RESETVALUE		0x0000U
+#define XHC_RHSHSC0__RSL_L			7U
+#define XHC_RHSHSC0__RSL_R			6U
+#define XHC_RHSHSC0__RSL_WIDTH			2U
+#define XHC_RHSHSC0__RSL_RESETVALUE		0x0U
+#define XHC_RHSHSC0__AS_M_L			5U
+#define XHC_RHSHSC0__AS_M_R			4U
+#define XHC_RHSHSC0__AS_M_WIDTH			2U
+#define XHC_RHSHSC0__AS_M_RESETVALUE		0x0U
+#define XHC_RHSHSC0__CMD_L			3U
+#define XHC_RHSHSC0__CMD_R			2U
+#define XHC_RHSHSC0__CMD_WIDTH			2U
+#define XHC_RHSHSC0__CMD_RESETVALUE		0x0U
+#define XHC_RHSHSC0__reserved			1U
+#define XHC_RHSHSC0__reserved_L			1U
+#define XHC_RHSHSC0__reserved_R			1U
+#define XHC_RHSHSC0__reserved_WIDTH		1U
+#define XHC_RHSHSC0__reserved_RESETVALUE	0x0U
+#define XHC_RHSHSC0__STB			0U
+#define XHC_RHSHSC0__STB_L			0U
+#define XHC_RHSHSC0__STB_R			0U
+#define XHC_RHSHSC0__STB_WIDTH			1U
+#define XHC_RHSHSC0__STB_RESETVALUE		0x0U
+#define XHC_RHSHSC0__RESERVED_L			15U
+#define XHC_RHSHSC0__RESERVED_R			8U
+#define XHC_RHSHSC0_WIDTH			32U
+#define XHC_RHSHSC0__WIDTH			32U
+#define XHC_RHSHSC0_ALL_L			31U
+#define XHC_RHSHSC0_ALL_R			0U
+#define XHC_RHSHSC0__ALL_L			31U
+#define XHC_RHSHSC0__ALL_R			0U
+#define XHC_RHSHSC0_DATAMASK			0xffff00ffU
+#define XHC_RHSHSC0_RDWRMASK			0x0000ff00U
+#define XHC_RHSHSC0_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSR0_OFFSET			0xc94U
+#define XHC_RHSHSR0_BASE			0xc94U
+#define XHC_RHSHSR0__C2U_L			31U
+#define XHC_RHSHSR0__C2U_R			24U
+#define XHC_RHSHSR0__C2U_WIDTH			8U
+#define XHC_RHSHSR0__C2U_RESETVALUE		0x00U
+#define XHC_RHSHSR0__C1U_L			23U
+#define XHC_RHSHSR0__C1U_R			16U
+#define XHC_RHSHSR0__C1U_WIDTH			8U
+#define XHC_RHSHSR0__C1U_RESETVALUE		0x00U
+#define XHC_RHSHSR0__RCV_L			15U
+#define XHC_RHSHSR0__RCV_R			8U
+#define XHC_RHSHSR0__RCV_WIDTH			8U
+#define XHC_RHSHSR0__RCV_RESETVALUE		0x00U
+#define XHC_RHSHSR0__RTY_L			7U
+#define XHC_RHSHSR0__RTY_R			0U
+#define XHC_RHSHSR0__RTY_WIDTH			8U
+#define XHC_RHSHSR0__RTY_RESETVALUE		0x00U
+#define XHC_RHSHSR0_WIDTH			32U
+#define XHC_RHSHSR0__WIDTH			32U
+#define XHC_RHSHSR0_ALL_L			31U
+#define XHC_RHSHSR0_ALL_R			0U
+#define XHC_RHSHSR0__ALL_L			31U
+#define XHC_RHSHSR0__ALL_R			0U
+#define XHC_RHSHSR0_DATAMASK			0xffffffffU
+#define XHC_RHSHSR0_RDWRMASK			0x00000000U
+#define XHC_RHSHSR0_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSC1_OFFSET			0xc98U
+#define XHC_RHSHSC1_BASE			0xc98U
+#define XHC_RHSHSC1__TMR_L			31U
+#define XHC_RHSHSC1__TMR_R			16U
+#define XHC_RHSHSC1__TMR_WIDTH			16U
+#define XHC_RHSHSC1__TMR_RESETVALUE		0x0000U
+#define XHC_RHSHSC1__RSL_L			7U
+#define XHC_RHSHSC1__RSL_R			6U
+#define XHC_RHSHSC1__RSL_WIDTH			2U
+#define XHC_RHSHSC1__RSL_RESETVALUE		0x0U
+#define XHC_RHSHSC1__AS_M_L			5U
+#define XHC_RHSHSC1__AS_M_R			4U
+#define XHC_RHSHSC1__AS_M_WIDTH			2U
+#define XHC_RHSHSC1__AS_M_RESETVALUE		0x0U
+#define XHC_RHSHSC1__CMD_L			3U
+#define XHC_RHSHSC1__CMD_R			2U
+#define XHC_RHSHSC1__CMD_WIDTH			2U
+#define XHC_RHSHSC1__CMD_RESETVALUE		0x0U
+#define XHC_RHSHSC1__reserved			1U
+#define XHC_RHSHSC1__reserved_L			1U
+#define XHC_RHSHSC1__reserved_R			1U
+#define XHC_RHSHSC1__reserved_WIDTH		1U
+#define XHC_RHSHSC1__reserved_RESETVALUE	0x0U
+#define XHC_RHSHSC1__STB			0U
+#define XHC_RHSHSC1__STB_L			0U
+#define XHC_RHSHSC1__STB_R			0U
+#define XHC_RHSHSC1__STB_WIDTH			1U
+#define XHC_RHSHSC1__STB_RESETVALUE		0x0U
+#define XHC_RHSHSC1__RESERVED_L			15U
+#define XHC_RHSHSC1__RESERVED_R			8U
+#define XHC_RHSHSC1_WIDTH			32U
+#define XHC_RHSHSC1__WIDTH			32U
+#define XHC_RHSHSC1_ALL_L			31U
+#define XHC_RHSHSC1_ALL_R			0U
+#define XHC_RHSHSC1__ALL_L			31U
+#define XHC_RHSHSC1__ALL_R			0U
+#define XHC_RHSHSC1_DATAMASK			0xffff00ffU
+#define XHC_RHSHSC1_RDWRMASK			0x0000ff00U
+#define XHC_RHSHSC1_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSR1_OFFSET			0xc9cU
+#define XHC_RHSHSR1_BASE			0xc9cU
+#define XHC_RHSHSR1__C2U_L			31U
+#define XHC_RHSHSR1__C2U_R			24U
+#define XHC_RHSHSR1__C2U_WIDTH			8U
+#define XHC_RHSHSR1__C2U_RESETVALUE		0x00U
+#define XHC_RHSHSR1__C1U_L			23U
+#define XHC_RHSHSR1__C1U_R			16U
+#define XHC_RHSHSR1__C1U_WIDTH			8U
+#define XHC_RHSHSR1__C1U_RESETVALUE		0x00U
+#define XHC_RHSHSR1__RCV_L			15U
+#define XHC_RHSHSR1__RCV_R			8U
+#define XHC_RHSHSR1__RCV_WIDTH			8U
+#define XHC_RHSHSR1__RCV_RESETVALUE		0x00U
+#define XHC_RHSHSR1__RTY_L			7U
+#define XHC_RHSHSR1__RTY_R			0U
+#define XHC_RHSHSR1__RTY_WIDTH			8U
+#define XHC_RHSHSR1__RTY_RESETVALUE		0x00U
+#define XHC_RHSHSR1_WIDTH			32U
+#define XHC_RHSHSR1__WIDTH			32U
+#define XHC_RHSHSR1_ALL_L			31U
+#define XHC_RHSHSR1_ALL_R			0U
+#define XHC_RHSHSR1__ALL_L			31U
+#define XHC_RHSHSR1__ALL_R			0U
+#define XHC_RHSHSR1_DATAMASK			0xffffffffU
+#define XHC_RHSHSR1_RDWRMASK			0x00000000U
+#define XHC_RHSHSR1_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSC2_OFFSET			0xca0U
+#define XHC_RHSHSC2_BASE			0xca0U
+#define XHC_RHSHSC2__TMR_L			31U
+#define XHC_RHSHSC2__TMR_R			16U
+#define XHC_RHSHSC2__TMR_WIDTH			16U
+#define XHC_RHSHSC2__TMR_RESETVALUE		0x0000U
+#define XHC_RHSHSC2__RSL_L			7U
+#define XHC_RHSHSC2__RSL_R			6U
+#define XHC_RHSHSC2__RSL_WIDTH			2U
+#define XHC_RHSHSC2__RSL_RESETVALUE		0x0U
+#define XHC_RHSHSC2__AS_M_L			5U
+#define XHC_RHSHSC2__AS_M_R			4U
+#define XHC_RHSHSC2__AS_M_WIDTH			2U
+#define XHC_RHSHSC2__AS_M_RESETVALUE		0x0U
+#define XHC_RHSHSC2__CMD_L			3U
+#define XHC_RHSHSC2__CMD_R			2U
+#define XHC_RHSHSC2__CMD_WIDTH			2U
+#define XHC_RHSHSC2__CMD_RESETVALUE		0x0U
+#define XHC_RHSHSC2__reserved			1U
+#define XHC_RHSHSC2__reserved_L			1U
+#define XHC_RHSHSC2__reserved_R			1U
+#define XHC_RHSHSC2__reserved_WIDTH		1U
+#define XHC_RHSHSC2__reserved_RESETVALUE	0x0U
+#define XHC_RHSHSC2__STB			0U
+#define XHC_RHSHSC2__STB_L			0U
+#define XHC_RHSHSC2__STB_R			0U
+#define XHC_RHSHSC2__STB_WIDTH			1U
+#define XHC_RHSHSC2__STB_RESETVALUE		0x0U
+#define XHC_RHSHSC2__RESERVED_L			15U
+#define XHC_RHSHSC2__RESERVED_R			8U
+#define XHC_RHSHSC2_WIDTH			32U
+#define XHC_RHSHSC2__WIDTH			32U
+#define XHC_RHSHSC2_ALL_L			31U
+#define XHC_RHSHSC2_ALL_R			0U
+#define XHC_RHSHSC2__ALL_L			31U
+#define XHC_RHSHSC2__ALL_R			0U
+#define XHC_RHSHSC2_DATAMASK			0xffff00ffU
+#define XHC_RHSHSC2_RDWRMASK			0x0000ff00U
+#define XHC_RHSHSC2_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSR2_OFFSET			0xca4U
+#define XHC_RHSHSR2_BASE			0xca4U
+#define XHC_RHSHSR2__C2U_L			31U
+#define XHC_RHSHSR2__C2U_R			24U
+#define XHC_RHSHSR2__C2U_WIDTH			8U
+#define XHC_RHSHSR2__C2U_RESETVALUE		0x00U
+#define XHC_RHSHSR2__C1U_L			23U
+#define XHC_RHSHSR2__C1U_R			16U
+#define XHC_RHSHSR2__C1U_WIDTH			8U
+#define XHC_RHSHSR2__C1U_RESETVALUE		0x00U
+#define XHC_RHSHSR2__RCV_L			15U
+#define XHC_RHSHSR2__RCV_R			8U
+#define XHC_RHSHSR2__RCV_WIDTH			8U
+#define XHC_RHSHSR2__RCV_RESETVALUE		0x00U
+#define XHC_RHSHSR2__RTY_L			7U
+#define XHC_RHSHSR2__RTY_R			0U
+#define XHC_RHSHSR2__RTY_WIDTH			8U
+#define XHC_RHSHSR2__RTY_RESETVALUE		0x00U
+#define XHC_RHSHSR2_WIDTH			32U
+#define XHC_RHSHSR2__WIDTH			32U
+#define XHC_RHSHSR2_ALL_L			31U
+#define XHC_RHSHSR2_ALL_R			0U
+#define XHC_RHSHSR2__ALL_L			31U
+#define XHC_RHSHSR2__ALL_R			0U
+#define XHC_RHSHSR2_DATAMASK			0xffffffffU
+#define XHC_RHSHSR2_RDWRMASK			0x00000000U
+#define XHC_RHSHSR2_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSC3_OFFSET			0xca8U
+#define XHC_RHSHSC3_BASE			0xca8U
+#define XHC_RHSHSC3__TMR_L			31U
+#define XHC_RHSHSC3__TMR_R			16U
+#define XHC_RHSHSC3__TMR_WIDTH			16U
+#define XHC_RHSHSC3__TMR_RESETVALUE		0x0000U
+#define XHC_RHSHSC3__RSL_L			7U
+#define XHC_RHSHSC3__RSL_R			6U
+#define XHC_RHSHSC3__RSL_WIDTH			2U
+#define XHC_RHSHSC3__RSL_RESETVALUE		0x0U
+#define XHC_RHSHSC3__AS_M_L			5U
+#define XHC_RHSHSC3__AS_M_R			4U
+#define XHC_RHSHSC3__AS_M_WIDTH			2U
+#define XHC_RHSHSC3__AS_M_RESETVALUE		0x0U
+#define XHC_RHSHSC3__CMD_L			3U
+#define XHC_RHSHSC3__CMD_R			2U
+#define XHC_RHSHSC3__CMD_WIDTH			2U
+#define XHC_RHSHSC3__CMD_RESETVALUE		0x0U
+#define XHC_RHSHSC3__reserved			1U
+#define XHC_RHSHSC3__reserved_L			1U
+#define XHC_RHSHSC3__reserved_R			1U
+#define XHC_RHSHSC3__reserved_WIDTH		1U
+#define XHC_RHSHSC3__reserved_RESETVALUE	0x0U
+#define XHC_RHSHSC3__STB			0U
+#define XHC_RHSHSC3__STB_L			0U
+#define XHC_RHSHSC3__STB_R			0U
+#define XHC_RHSHSC3__STB_WIDTH			1U
+#define XHC_RHSHSC3__STB_RESETVALUE		0x0U
+#define XHC_RHSHSC3__RESERVED_L			15U
+#define XHC_RHSHSC3__RESERVED_R			8U
+#define XHC_RHSHSC3_WIDTH			32U
+#define XHC_RHSHSC3__WIDTH			32U
+#define XHC_RHSHSC3_ALL_L			31U
+#define XHC_RHSHSC3_ALL_R			0U
+#define XHC_RHSHSC3__ALL_L			31U
+#define XHC_RHSHSC3__ALL_R			0U
+#define XHC_RHSHSC3_DATAMASK			0xffff00ffU
+#define XHC_RHSHSC3_RDWRMASK			0x0000ff00U
+#define XHC_RHSHSC3_RESETVALUE			0x00000000U
+
+#define XHC_RHSHSR3_OFFSET			0xcacU
+#define XHC_RHSHSR3_BASE			0xcacU
+#define XHC_RHSHSR3__C2U_L			31U
+#define XHC_RHSHSR3__C2U_R			24U
+#define XHC_RHSHSR3__C2U_WIDTH			8U
+#define XHC_RHSHSR3__C2U_RESETVALUE		0x00U
+#define XHC_RHSHSR3__C1U_L			23U
+#define XHC_RHSHSR3__C1U_R			16U
+#define XHC_RHSHSR3__C1U_WIDTH			8U
+#define XHC_RHSHSR3__C1U_RESETVALUE		0x00U
+#define XHC_RHSHSR3__RCV_L			15U
+#define XHC_RHSHSR3__RCV_R			8U
+#define XHC_RHSHSR3__RCV_WIDTH			8U
+#define XHC_RHSHSR3__RCV_RESETVALUE		0x00U
+#define XHC_RHSHSR3__RTY_L			7U
+#define XHC_RHSHSR3__RTY_R			0U
+#define XHC_RHSHSR3__RTY_WIDTH			8U
+#define XHC_RHSHSR3__RTY_RESETVALUE		0x00U
+#define XHC_RHSHSR3_WIDTH			32U
+#define XHC_RHSHSR3__WIDTH			32U
+#define XHC_RHSHSR3_ALL_L			31U
+#define XHC_RHSHSR3_ALL_R			0U
+#define XHC_RHSHSR3__ALL_L			31U
+#define XHC_RHSHSR3__ALL_R			0U
+#define XHC_RHSHSR3_DATAMASK			0xffffffffU
+#define XHC_RHSHSR3_RDWRMASK			0x00000000U
+#define XHC_RHSHSR3_RESETVALUE			0x00000000U
+
+#define XHC_ECHSSP_OFFSET			0xcb0U
+#define XHC_ECHSSP_BASE				0xcb0U
+#define XHC_ECHSSP__reserved_L			31U
+#define XHC_ECHSSP__reserved_R			16U
+#define XHC_ECHSSP__reserved_WIDTH		16U
+#define XHC_ECHSSP__reserved_RESETVALUE		0x0000U
+#define XHC_ECHSSP__NCP_L			15U
+#define XHC_ECHSSP__NCP_R			8U
+#define XHC_ECHSSP__NCP_WIDTH			8U
+#define XHC_ECHSSP__NCP_RESETVALUE		0x04U
+#define XHC_ECHSSP__CID_L			7U
+#define XHC_ECHSSP__CID_R			0U
+#define XHC_ECHSSP__CID_WIDTH			8U
+#define XHC_ECHSSP__CID_RESETVALUE		0xc6U
+#define XHC_ECHSSP_WIDTH			32U
+#define XHC_ECHSSP__WIDTH			32U
+#define XHC_ECHSSP_ALL_L			31U
+#define XHC_ECHSSP_ALL_R			0U
+#define XHC_ECHSSP__ALL_L			31U
+#define XHC_ECHSSP__ALL_R			0U
+#define XHC_ECHSSP_DATAMASK			0xffffffffU
+#define XHC_ECHSSP_RDWRMASK			0x00000000U
+#define XHC_ECHSSP_RESETVALUE			0x000004c6U
+
+#define XHC_SSPVER_OFFSET			0xcb4U
+#define XHC_SSPVER_BASE				0xcb4U
+#define XHC_SSPVER__MAJ_L			31U
+#define XHC_SSPVER__MAJ_R			28U
+#define XHC_SSPVER__MAJ_WIDTH			4U
+#define XHC_SSPVER__MAJ_RESETVALUE		0x0U
+#define XHC_SSPVER__MIN_L			27U
+#define XHC_SSPVER__MIN_R			24U
+#define XHC_SSPVER__MIN_WIDTH			4U
+#define XHC_SSPVER__MIN_RESETVALUE		0x0U
+#define XHC_SSPVER__RLS_L			23U
+#define XHC_SSPVER__RLS_R			20U
+#define XHC_SSPVER__RLS_WIDTH			4U
+#define XHC_SSPVER__RLS_RESETVALUE		0x0U
+#define XHC_SSPVER__reserved_L			19U
+#define XHC_SSPVER__reserved_R			0U
+#define XHC_SSPVER__reserved_WIDTH		20U
+#define XHC_SSPVER__reserved_RESETVALUE		0x00000U
+#define XHC_SSPVER_WIDTH			32U
+#define XHC_SSPVER__WIDTH			32U
+#define XHC_SSPVER_ALL_L			31U
+#define XHC_SSPVER_ALL_R			0U
+#define XHC_SSPVER__ALL_L			31U
+#define XHC_SSPVER__ALL_R			0U
+#define XHC_SSPVER_DATAMASK			0xffffffffU
+#define XHC_SSPVER_RDWRMASK			0x00000000U
+#define XHC_SSPVER_RESETVALUE			0x00000000U
+
+#define XHC_SSPMGN_OFFSET			0xcb8U
+#define XHC_SSPMGN_BASE				0xcb8U
+#define XHC_SSPMGN__MGN_L			31U
+#define XHC_SSPMGN__MGN_R			0U
+#define XHC_SSPMGN__MGN_WIDTH			32U
+#define XHC_SSPMGN__MGN_RESETVALUE		0x4b535040U
+#define XHC_SSPMGN_WIDTH			32U
+#define XHC_SSPMGN__WIDTH			32U
+#define XHC_SSPMGN_ALL_L			31U
+#define XHC_SSPMGN_ALL_R			0U
+#define XHC_SSPMGN__ALL_L			31U
+#define XHC_SSPMGN__ALL_R			0U
+#define XHC_SSPMGN_DATAMASK			0xffffffffU
+#define XHC_SSPMGN_RDWRMASK			0x00000000U
+#define XHC_SSPMGN_RESETVALUE			0x4b535040U
+
+#define XHC_ECHFSC2_OFFSET			0xcc0U
+#define XHC_ECHFSC2_BASE			0xcc0U
+#define XHC_ECHFSC2__reserved_L			31U
+#define XHC_ECHFSC2__reserved_R			16U
+#define XHC_ECHFSC2__reserved_WIDTH		16U
+#define XHC_ECHFSC2__reserved_RESETVALUE	0x0000U
+#define XHC_ECHFSC2__NCP_L			15U
+#define XHC_ECHFSC2__NCP_R			8U
+#define XHC_ECHFSC2__NCP_WIDTH			8U
+#define XHC_ECHFSC2__NCP_RESETVALUE		0x50U
+#define XHC_ECHFSC2__CID_L			7U
+#define XHC_ECHFSC2__CID_R			0U
+#define XHC_ECHFSC2__CID_WIDTH			8U
+#define XHC_ECHFSC2__CID_RESETVALUE		0xc7U
+#define XHC_ECHFSC2_WIDTH			32U
+#define XHC_ECHFSC2__WIDTH			32U
+#define XHC_ECHFSC2_ALL_L			31U
+#define XHC_ECHFSC2_ALL_R			0U
+#define XHC_ECHFSC2__ALL_L			31U
+#define XHC_ECHFSC2__ALL_R			0U
+#define XHC_ECHFSC2_DATAMASK			0xffffffffU
+#define XHC_ECHFSC2_RDWRMASK			0x00000000U
+#define XHC_ECHFSC2_RESETVALUE			0x000050c7U
+
+#define XHC_FSC2POC_OFFSET			0xcd4U
+#define XHC_FSC2POC_BASE			0xcd4U
+#define XHC_FSC2POC__NCS_L			31U
+#define XHC_FSC2POC__NCS_R			28U
+#define XHC_FSC2POC__NCS_WIDTH			4U
+#define XHC_FSC2POC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2POC__FSIZ_L			22U
+#define XHC_FSC2POC__FSIZ_R			18U
+#define XHC_FSC2POC__FSIZ_WIDTH			5U
+#define XHC_FSC2POC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSC2POC__PSIZ_L			16U
+#define XHC_FSC2POC__PSIZ_R			12U
+#define XHC_FSC2POC__PSIZ_WIDTH			5U
+#define XHC_FSC2POC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSC2POC__reserved_L			11U
+#define XHC_FSC2POC__reserved_R			5U
+#define XHC_FSC2POC__reserved_WIDTH		7U
+#define XHC_FSC2POC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2POC__TSIZ_L			4U
+#define XHC_FSC2POC__TSIZ_R			0U
+#define XHC_FSC2POC__TSIZ_WIDTH			5U
+#define XHC_FSC2POC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2POC__RESERVED_L			27U
+#define XHC_FSC2POC__RESERVED_R			23U
+#define XHC_FSC2POC_WIDTH			32U
+#define XHC_FSC2POC__WIDTH			32U
+#define XHC_FSC2POC_ALL_L			31U
+#define XHC_FSC2POC_ALL_R			0U
+#define XHC_FSC2POC__ALL_L			31U
+#define XHC_FSC2POC__ALL_R			0U
+#define XHC_FSC2POC_DATAMASK			0xf07dffffU
+#define XHC_FSC2POC_RDWRMASK			0x0f820000U
+#define XHC_FSC2POC_RESETVALUE			0x00000000U
+
+#define XHC_FSC2GOC_OFFSET			0xcd8U
+#define XHC_FSC2GOC_BASE			0xcd8U
+#define XHC_FSC2GOC__NCS_L			31U
+#define XHC_FSC2GOC__NCS_R			28U
+#define XHC_FSC2GOC__NCS_WIDTH			4U
+#define XHC_FSC2GOC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2GOC__FSIZ_L			22U
+#define XHC_FSC2GOC__FSIZ_R			18U
+#define XHC_FSC2GOC__FSIZ_WIDTH			5U
+#define XHC_FSC2GOC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSC2GOC__PSIZ_L			16U
+#define XHC_FSC2GOC__PSIZ_R			12U
+#define XHC_FSC2GOC__PSIZ_WIDTH			5U
+#define XHC_FSC2GOC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSC2GOC__reserved_L			11U
+#define XHC_FSC2GOC__reserved_R			5U
+#define XHC_FSC2GOC__reserved_WIDTH		7U
+#define XHC_FSC2GOC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2GOC__TSIZ_L			4U
+#define XHC_FSC2GOC__TSIZ_R			0U
+#define XHC_FSC2GOC__TSIZ_WIDTH			5U
+#define XHC_FSC2GOC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2GOC__RESERVED_L			27U
+#define XHC_FSC2GOC__RESERVED_R			23U
+#define XHC_FSC2GOC_WIDTH			32U
+#define XHC_FSC2GOC__WIDTH			32U
+#define XHC_FSC2GOC_ALL_L			31U
+#define XHC_FSC2GOC_ALL_R			0U
+#define XHC_FSC2GOC__ALL_L			31U
+#define XHC_FSC2GOC__ALL_R			0U
+#define XHC_FSC2GOC_DATAMASK			0xf07dffffU
+#define XHC_FSC2GOC_RDWRMASK			0x0f820000U
+#define XHC_FSC2GOC_RESETVALUE			0x00000000U
+
+#define XHC_FSC2NOC_OFFSET			0xcdcU
+#define XHC_FSC2NOC_BASE			0xcdcU
+#define XHC_FSC2NOC__NCS_L			31U
+#define XHC_FSC2NOC__NCS_R			28U
+#define XHC_FSC2NOC__NCS_WIDTH			4U
+#define XHC_FSC2NOC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2NOC__FSIZ_L			22U
+#define XHC_FSC2NOC__FSIZ_R			18U
+#define XHC_FSC2NOC__FSIZ_WIDTH			5U
+#define XHC_FSC2NOC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSC2NOC__PSIZ_L			16U
+#define XHC_FSC2NOC__PSIZ_R			12U
+#define XHC_FSC2NOC__PSIZ_WIDTH			5U
+#define XHC_FSC2NOC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSC2NOC__reserved_L			11U
+#define XHC_FSC2NOC__reserved_R			5U
+#define XHC_FSC2NOC__reserved_WIDTH		7U
+#define XHC_FSC2NOC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2NOC__TSIZ_L			4U
+#define XHC_FSC2NOC__TSIZ_R			0U
+#define XHC_FSC2NOC__TSIZ_WIDTH			5U
+#define XHC_FSC2NOC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2NOC__RESERVED_L			27U
+#define XHC_FSC2NOC__RESERVED_R			23U
+#define XHC_FSC2NOC_WIDTH			32U
+#define XHC_FSC2NOC__WIDTH			32U
+#define XHC_FSC2NOC_ALL_L			31U
+#define XHC_FSC2NOC_ALL_R			0U
+#define XHC_FSC2NOC__ALL_L			31U
+#define XHC_FSC2NOC__ALL_R			0U
+#define XHC_FSC2NOC_DATAMASK			0xf07dffffU
+#define XHC_FSC2NOC_RDWRMASK			0x0f820000U
+#define XHC_FSC2NOC_RESETVALUE			0x00000000U
+
+#define XHC_FSC2AIC_OFFSET			0xce0U
+#define XHC_FSC2AIC_BASE			0xce0U
+#define XHC_FSC2AIC__FSIZ_L			22U
+#define XHC_FSC2AIC__FSIZ_R			18U
+#define XHC_FSC2AIC__FSIZ_WIDTH			5U
+#define XHC_FSC2AIC__FSIZ_RESETVALUE		0x0U
+#define XHC_FSC2AIC__PSIZ_L			16U
+#define XHC_FSC2AIC__PSIZ_R			12U
+#define XHC_FSC2AIC__PSIZ_WIDTH			5U
+#define XHC_FSC2AIC__PSIZ_RESETVALUE		0x0U
+#define XHC_FSC2AIC__reserved_L			11U
+#define XHC_FSC2AIC__reserved_R			0U
+#define XHC_FSC2AIC__reserved_WIDTH		12U
+#define XHC_FSC2AIC__reserved_RESETVALUE	0x000U
+#define XHC_FSC2AIC__RESERVED_L			31U
+#define XHC_FSC2AIC__RESERVED_R			23U
+#define XHC_FSC2AIC_WIDTH			23U
+#define XHC_FSC2AIC__WIDTH			23U
+#define XHC_FSC2AIC_ALL_L			22U
+#define XHC_FSC2AIC_ALL_R			0U
+#define XHC_FSC2AIC__ALL_L			22U
+#define XHC_FSC2AIC__ALL_R			0U
+#define XHC_FSC2AIC_DATAMASK			0x007dffffU
+#define XHC_FSC2AIC_RDWRMASK			0xff820000U
+#define XHC_FSC2AIC_RESETVALUE			0x000000U
+
+#define XHC_FSC2PIC_OFFSET			0xce4U
+#define XHC_FSC2PIC_BASE			0xce4U
+#define XHC_FSC2PIC__NCS_L			31U
+#define XHC_FSC2PIC__NCS_R			28U
+#define XHC_FSC2PIC__NCS_WIDTH			4U
+#define XHC_FSC2PIC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2PIC__reserved_L			27U
+#define XHC_FSC2PIC__reserved_R			5U
+#define XHC_FSC2PIC__reserved_WIDTH		23U
+#define XHC_FSC2PIC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2PIC__TSIZ_L			4U
+#define XHC_FSC2PIC__TSIZ_R			0U
+#define XHC_FSC2PIC__TSIZ_WIDTH			5U
+#define XHC_FSC2PIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2PIC_WIDTH			32U
+#define XHC_FSC2PIC__WIDTH			32U
+#define XHC_FSC2PIC_ALL_L			31U
+#define XHC_FSC2PIC_ALL_R			0U
+#define XHC_FSC2PIC__ALL_L			31U
+#define XHC_FSC2PIC__ALL_R			0U
+#define XHC_FSC2PIC_DATAMASK			0xffffffffU
+#define XHC_FSC2PIC_RDWRMASK			0x00000000U
+#define XHC_FSC2PIC_RESETVALUE			0x00000000U
+
+#define XHC_FSC2GIC_OFFSET			0xce8U
+#define XHC_FSC2GIC_BASE			0xce8U
+#define XHC_FSC2GIC__NCS_L			31U
+#define XHC_FSC2GIC__NCS_R			28U
+#define XHC_FSC2GIC__NCS_WIDTH			4U
+#define XHC_FSC2GIC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2GIC__reserved_L			27U
+#define XHC_FSC2GIC__reserved_R			5U
+#define XHC_FSC2GIC__reserved_WIDTH		23U
+#define XHC_FSC2GIC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2GIC__TSIZ_L			4U
+#define XHC_FSC2GIC__TSIZ_R			0U
+#define XHC_FSC2GIC__TSIZ_WIDTH			5U
+#define XHC_FSC2GIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2GIC_WIDTH			32U
+#define XHC_FSC2GIC__WIDTH			32U
+#define XHC_FSC2GIC_ALL_L			31U
+#define XHC_FSC2GIC_ALL_R			0U
+#define XHC_FSC2GIC__ALL_L			31U
+#define XHC_FSC2GIC__ALL_R			0U
+#define XHC_FSC2GIC_DATAMASK			0xffffffffU
+#define XHC_FSC2GIC_RDWRMASK			0x00000000U
+#define XHC_FSC2GIC_RESETVALUE			0x00000000U
+
+#define XHC_FSC2NIC_OFFSET			0xcecU
+#define XHC_FSC2NIC_BASE			0xcecU
+#define XHC_FSC2NIC__NCS_L			31U
+#define XHC_FSC2NIC__NCS_R			28U
+#define XHC_FSC2NIC__NCS_WIDTH			4U
+#define XHC_FSC2NIC__NCS_RESETVALUE		0x0U
+#define XHC_FSC2NIC__reserved_L			27U
+#define XHC_FSC2NIC__reserved_R			5U
+#define XHC_FSC2NIC__reserved_WIDTH		23U
+#define XHC_FSC2NIC__reserved_RESETVALUE	0x0U
+#define XHC_FSC2NIC__TSIZ_L			4U
+#define XHC_FSC2NIC__TSIZ_R			0U
+#define XHC_FSC2NIC__TSIZ_WIDTH			5U
+#define XHC_FSC2NIC__TSIZ_RESETVALUE		0x0U
+#define XHC_FSC2NIC_WIDTH			32U
+#define XHC_FSC2NIC__WIDTH			32U
+#define XHC_FSC2NIC_ALL_L			31U
+#define XHC_FSC2NIC_ALL_R			0U
+#define XHC_FSC2NIC__ALL_L			31U
+#define XHC_FSC2NIC__ALL_R			0U
+#define XHC_FSC2NIC_DATAMASK			0xffffffffU
+#define XHC_FSC2NIC_RDWRMASK			0x00000000U
+#define XHC_FSC2NIC_RESETVALUE			0x00000000U
+
+#define XHC_ECHPRT2_OFFSET			0xcf0U
+#define XHC_ECHPRT2_BASE			0xcf0U
+#define XHC_ECHPRT2__HDP			31U
+#define XHC_ECHPRT2__HDP_L			31U
+#define XHC_ECHPRT2__HDP_R			31U
+#define XHC_ECHPRT2__HDP_WIDTH			1U
+#define XHC_ECHPRT2__HDP_RESETVALUE		0x0U
+#define XHC_ECHPRT2__FDP			30U
+#define XHC_ECHPRT2__FDP_L			30U
+#define XHC_ECHPRT2__FDP_R			30U
+#define XHC_ECHPRT2__FDP_WIDTH			1U
+#define XHC_ECHPRT2__FDP_RESETVALUE		0x0U
+#define XHC_ECHPRT2__reserved_L			29U
+#define XHC_ECHPRT2__reserved_R			17U
+#define XHC_ECHPRT2__reserved_WIDTH		13U
+#define XHC_ECHPRT2__reserved_RESETVALUE	0x0U
+#define XHC_ECHPRT2__HST			16U
+#define XHC_ECHPRT2__HST_L			16U
+#define XHC_ECHPRT2__HST_R			16U
+#define XHC_ECHPRT2__HST_WIDTH			1U
+#define XHC_ECHPRT2__HST_RESETVALUE		0x0U
+#define XHC_ECHPRT2__NCP_L			15U
+#define XHC_ECHPRT2__NCP_R			8U
+#define XHC_ECHPRT2__NCP_WIDTH			8U
+#define XHC_ECHPRT2__NCP_RESETVALUE		0x04U
+#define XHC_ECHPRT2__CID_L			7U
+#define XHC_ECHPRT2__CID_R			0U
+#define XHC_ECHPRT2__CID_WIDTH			8U
+#define XHC_ECHPRT2__CID_RESETVALUE		0xc8U
+#define XHC_ECHPRT2_WIDTH			32U
+#define XHC_ECHPRT2__WIDTH			32U
+#define XHC_ECHPRT2_ALL_L			31U
+#define XHC_ECHPRT2_ALL_R			0U
+#define XHC_ECHPRT2__ALL_L			31U
+#define XHC_ECHPRT2__ALL_R			0U
+#define XHC_ECHPRT2_DATAMASK			0xffffffffU
+#define XHC_ECHPRT2_RDWRMASK			0x00000000U
+#define XHC_ECHPRT2_RESETVALUE			0x000004c8U
+
+#define XHC_PRT2HSC_OFFSET			0xcf8U
+#define XHC_PRT2HSC_BASE			0xcf8U
+#define XHC_PRT2HSC__TMR_L			31U
+#define XHC_PRT2HSC__TMR_R			16U
+#define XHC_PRT2HSC__TMR_WIDTH			16U
+#define XHC_PRT2HSC__TMR_RESETVALUE		0x0000U
+#define XHC_PRT2HSC__RSL_L			7U
+#define XHC_PRT2HSC__RSL_R			6U
+#define XHC_PRT2HSC__RSL_WIDTH			2U
+#define XHC_PRT2HSC__RSL_RESETVALUE		0x0U
+#define XHC_PRT2HSC__AS_M_L			5U
+#define XHC_PRT2HSC__AS_M_R			4U
+#define XHC_PRT2HSC__AS_M_WIDTH			2U
+#define XHC_PRT2HSC__AS_M_RESETVALUE		0x0U
+#define XHC_PRT2HSC__CMD_L			3U
+#define XHC_PRT2HSC__CMD_R			2U
+#define XHC_PRT2HSC__CMD_WIDTH			2U
+#define XHC_PRT2HSC__CMD_RESETVALUE		0x0U
+#define XHC_PRT2HSC__reserved			1U
+#define XHC_PRT2HSC__reserved_L			1U
+#define XHC_PRT2HSC__reserved_R			1U
+#define XHC_PRT2HSC__reserved_WIDTH		1U
+#define XHC_PRT2HSC__reserved_RESETVALUE	0x0U
+#define XHC_PRT2HSC__STB			0U
+#define XHC_PRT2HSC__STB_L			0U
+#define XHC_PRT2HSC__STB_R			0U
+#define XHC_PRT2HSC__STB_WIDTH			1U
+#define XHC_PRT2HSC__STB_RESETVALUE		0x0U
+#define XHC_PRT2HSC__RESERVED_L			15U
+#define XHC_PRT2HSC__RESERVED_R			8U
+#define XHC_PRT2HSC_WIDTH			32U
+#define XHC_PRT2HSC__WIDTH			32U
+#define XHC_PRT2HSC_ALL_L			31U
+#define XHC_PRT2HSC_ALL_R			0U
+#define XHC_PRT2HSC__ALL_L			31U
+#define XHC_PRT2HSC__ALL_R			0U
+#define XHC_PRT2HSC_DATAMASK			0xffff00ffU
+#define XHC_PRT2HSC_RDWRMASK			0x0000ff00U
+#define XHC_PRT2HSC_RESETVALUE			0x00000000U
+
+#define XHC_PRT2HSR_OFFSET			0xcfcU
+#define XHC_PRT2HSR_BASE			0xcfcU
+#define XHC_PRT2HSR__RNAK_L			31U
+#define XHC_PRT2HSR__RNAK_R			24U
+#define XHC_PRT2HSR__RNAK_WIDTH			8U
+#define XHC_PRT2HSR__RNAK_RESETVALUE		0x00U
+#define XHC_PRT2HSR__HSTX_L			23U
+#define XHC_PRT2HSR__HSTX_R			16U
+#define XHC_PRT2HSR__HSTX_WIDTH			8U
+#define XHC_PRT2HSR__HSTX_RESETVALUE		0x00U
+#define XHC_PRT2HSR__HSRX_L			15U
+#define XHC_PRT2HSR__HSRX_R			8U
+#define XHC_PRT2HSR__HSRX_WIDTH			8U
+#define XHC_PRT2HSR__HSRX_RESETVALUE		0x00U
+#define XHC_PRT2HSR__SPLT_L			7U
+#define XHC_PRT2HSR__SPLT_R			0U
+#define XHC_PRT2HSR__SPLT_WIDTH			8U
+#define XHC_PRT2HSR__SPLT_RESETVALUE		0x00U
+#define XHC_PRT2HSR_WIDTH			32U
+#define XHC_PRT2HSR__WIDTH			32U
+#define XHC_PRT2HSR_ALL_L			31U
+#define XHC_PRT2HSR_ALL_R			0U
+#define XHC_PRT2HSR__ALL_L			31U
+#define XHC_PRT2HSR__ALL_R			0U
+#define XHC_PRT2HSR_DATAMASK			0xffffffffU
+#define XHC_PRT2HSR_RDWRMASK			0x00000000U
+#define XHC_PRT2HSR_RESETVALUE			0x00000000U
+
+#define XHC_ECHRH2_OFFSET			0xd00U
+#define XHC_ECHRH2_BASE				0xd00U
+#define XHC_ECHRH2__MTT				31U
+#define XHC_ECHRH2__MTT_L			31U
+#define XHC_ECHRH2__MTT_R			31U
+#define XHC_ECHRH2__MTT_WIDTH			1U
+#define XHC_ECHRH2__MTT_RESETVALUE		0x0U
+#define XHC_ECHRH2__RPO_L			30U
+#define XHC_ECHRH2__RPO_R			24U
+#define XHC_ECHRH2__RPO_WIDTH			7U
+#define XHC_ECHRH2__RPO_RESETVALUE		0x0U
+#define XHC_ECHRH2__reserved_L			23U
+#define XHC_ECHRH2__reserved_R			22U
+#define XHC_ECHRH2__reserved_WIDTH		2U
+#define XHC_ECHRH2__reserved_RESETVALUE		0x0U
+#define XHC_ECHRH2__RPN_L			21U
+#define XHC_ECHRH2__RPN_R			20U
+#define XHC_ECHRH2__RPN_WIDTH			2U
+#define XHC_ECHRH2__RPN_RESETVALUE		0x0U
+#define XHC_ECHRH2__DNR_L			19U
+#define XHC_ECHRH2__DNR_R			16U
+#define XHC_ECHRH2__DNR_WIDTH			4U
+#define XHC_ECHRH2__DNR_RESETVALUE		0x0U
+#define XHC_ECHRH2__NCP_L			15U
+#define XHC_ECHRH2__NCP_R			8U
+#define XHC_ECHRH2__NCP_WIDTH			8U
+#define XHC_ECHRH2__NCP_RESETVALUE		0x0cU
+#define XHC_ECHRH2__CID_L			7U
+#define XHC_ECHRH2__CID_R			0U
+#define XHC_ECHRH2__CID_WIDTH			8U
+#define XHC_ECHRH2__CID_RESETVALUE		0xc9U
+#define XHC_ECHRH2_WIDTH			32U
+#define XHC_ECHRH2__WIDTH			32U
+#define XHC_ECHRH2_ALL_L			31U
+#define XHC_ECHRH2_ALL_R			0U
+#define XHC_ECHRH2__ALL_L			31U
+#define XHC_ECHRH2__ALL_R			0U
+#define XHC_ECHRH2_DATAMASK			0xffffffffU
+#define XHC_ECHRH2_RDWRMASK			0x00000000U
+#define XHC_ECHRH2_RESETVALUE			0x00000cc9U
+
+#define XHC_RH2DES_OFFSET			0xd04U
+#define XHC_RH2DES_BASE				0xd04U
+#define XHC_RH2DES__PIS3_L			31U
+#define XHC_RH2DES__PIS3_R			30U
+#define XHC_RH2DES__PIS3_WIDTH			2U
+#define XHC_RH2DES__PIS3_RESETVALUE		0x0U
+#define XHC_RH2DES__HIST3			24U
+#define XHC_RH2DES__HIST3_L			24U
+#define XHC_RH2DES__HIST3_R			24U
+#define XHC_RH2DES__HIST3_WIDTH			1U
+#define XHC_RH2DES__HIST3_RESETVALUE		0x0U
+#define XHC_RH2DES__PIS2_L			23U
+#define XHC_RH2DES__PIS2_R			22U
+#define XHC_RH2DES__PIS2_WIDTH			2U
+#define XHC_RH2DES__PIS2_RESETVALUE		0x0U
+#define XHC_RH2DES__HIST2			16U
+#define XHC_RH2DES__HIST2_L			16U
+#define XHC_RH2DES__HIST2_R			16U
+#define XHC_RH2DES__HIST2_WIDTH			1U
+#define XHC_RH2DES__HIST2_RESETVALUE		0x0U
+#define XHC_RH2DES__PIS1_L			15U
+#define XHC_RH2DES__PIS1_R			14U
+#define XHC_RH2DES__PIS1_WIDTH			2U
+#define XHC_RH2DES__PIS1_RESETVALUE		0x0U
+#define XHC_RH2DES__HIST1			8U
+#define XHC_RH2DES__HIST1_L			8U
+#define XHC_RH2DES__HIST1_R			8U
+#define XHC_RH2DES__HIST1_WIDTH			1U
+#define XHC_RH2DES__HIST1_RESETVALUE		0x0U
+#define XHC_RH2DES__PIS0_L			7U
+#define XHC_RH2DES__PIS0_R			6U
+#define XHC_RH2DES__PIS0_WIDTH			2U
+#define XHC_RH2DES__PIS0_RESETVALUE		0x0U
+#define XHC_RH2DES__reserved_L			5U
+#define XHC_RH2DES__reserved_R			1U
+#define XHC_RH2DES__reserved_WIDTH		5U
+#define XHC_RH2DES__reserved_RESETVALUE		0x0U
+#define XHC_RH2DES__HIST0			0U
+#define XHC_RH2DES__HIST0_L			0U
+#define XHC_RH2DES__HIST0_R			0U
+#define XHC_RH2DES__HIST0_WIDTH			1U
+#define XHC_RH2DES__HIST0_RESETVALUE		0x0U
+#define XHC_RH2DES__RESERVED_0_L		29U
+#define XHC_RH2DES__RESERVED_0_R		25U
+#define XHC_RH2DES__RESERVED_1_L		21U
+#define XHC_RH2DES__RESERVED_1_R		17U
+#define XHC_RH2DES__RESERVED_2_L		13U
+#define XHC_RH2DES__RESERVED_2_R		9U
+#define XHC_RH2DES__RESERVED_L			29U
+#define XHC_RH2DES__RESERVED_R			25U
+#define XHC_RH2DES_WIDTH			32U
+#define XHC_RH2DES__WIDTH			32U
+#define XHC_RH2DES_ALL_L			31U
+#define XHC_RH2DES_ALL_R			0U
+#define XHC_RH2DES__ALL_L			31U
+#define XHC_RH2DES__ALL_R			0U
+#define XHC_RH2DES_DATAMASK			0xc1c1c1ffU
+#define XHC_RH2DES_RDWRMASK			0x3e3e3e00U
+#define XHC_RH2DES_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSC0_OFFSET			0xd10U
+#define XHC_RH2HSC0_BASE			0xd10U
+#define XHC_RH2HSC0__TMR_L			31U
+#define XHC_RH2HSC0__TMR_R			16U
+#define XHC_RH2HSC0__TMR_WIDTH			16U
+#define XHC_RH2HSC0__TMR_RESETVALUE		0x0000U
+#define XHC_RH2HSC0__RSL_L			7U
+#define XHC_RH2HSC0__RSL_R			6U
+#define XHC_RH2HSC0__RSL_WIDTH			2U
+#define XHC_RH2HSC0__RSL_RESETVALUE		0x0U
+#define XHC_RH2HSC0__AS_M_L			5U
+#define XHC_RH2HSC0__AS_M_R			4U
+#define XHC_RH2HSC0__AS_M_WIDTH			2U
+#define XHC_RH2HSC0__AS_M_RESETVALUE		0x0U
+#define XHC_RH2HSC0__CMD_L			3U
+#define XHC_RH2HSC0__CMD_R			2U
+#define XHC_RH2HSC0__CMD_WIDTH			2U
+#define XHC_RH2HSC0__CMD_RESETVALUE		0x0U
+#define XHC_RH2HSC0__reserved			1U
+#define XHC_RH2HSC0__reserved_L			1U
+#define XHC_RH2HSC0__reserved_R			1U
+#define XHC_RH2HSC0__reserved_WIDTH		1U
+#define XHC_RH2HSC0__reserved_RESETVALUE	0x0U
+#define XHC_RH2HSC0__STB			0U
+#define XHC_RH2HSC0__STB_L			0U
+#define XHC_RH2HSC0__STB_R			0U
+#define XHC_RH2HSC0__STB_WIDTH			1U
+#define XHC_RH2HSC0__STB_RESETVALUE		0x0U
+#define XHC_RH2HSC0__RESERVED_L			15U
+#define XHC_RH2HSC0__RESERVED_R			8U
+#define XHC_RH2HSC0_WIDTH			32U
+#define XHC_RH2HSC0__WIDTH			32U
+#define XHC_RH2HSC0_ALL_L			31U
+#define XHC_RH2HSC0_ALL_R			0U
+#define XHC_RH2HSC0__ALL_L			31U
+#define XHC_RH2HSC0__ALL_R			0U
+#define XHC_RH2HSC0_DATAMASK			0xffff00ffU
+#define XHC_RH2HSC0_RDWRMASK			0x0000ff00U
+#define XHC_RH2HSC0_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSR0_OFFSET			0xd14U
+#define XHC_RH2HSR0_BASE			0xd14U
+#define XHC_RH2HSR0__C2U_L			31U
+#define XHC_RH2HSR0__C2U_R			24U
+#define XHC_RH2HSR0__C2U_WIDTH			8U
+#define XHC_RH2HSR0__C2U_RESETVALUE		0x00U
+#define XHC_RH2HSR0__C1U_L			23U
+#define XHC_RH2HSR0__C1U_R			16U
+#define XHC_RH2HSR0__C1U_WIDTH			8U
+#define XHC_RH2HSR0__C1U_RESETVALUE		0x00U
+#define XHC_RH2HSR0__reserved_L			15U
+#define XHC_RH2HSR0__reserved_R			8U
+#define XHC_RH2HSR0__reserved_WIDTH		8U
+#define XHC_RH2HSR0__reserved_RESETVALUE	0x00U
+#define XHC_RH2HSR0__RTY_L			7U
+#define XHC_RH2HSR0__RTY_R			0U
+#define XHC_RH2HSR0__RTY_WIDTH			8U
+#define XHC_RH2HSR0__RTY_RESETVALUE		0x00U
+#define XHC_RH2HSR0_WIDTH			32U
+#define XHC_RH2HSR0__WIDTH			32U
+#define XHC_RH2HSR0_ALL_L			31U
+#define XHC_RH2HSR0_ALL_R			0U
+#define XHC_RH2HSR0__ALL_L			31U
+#define XHC_RH2HSR0__ALL_R			0U
+#define XHC_RH2HSR0_DATAMASK			0xffffffffU
+#define XHC_RH2HSR0_RDWRMASK			0x00000000U
+#define XHC_RH2HSR0_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSC1_OFFSET			0xd18U
+#define XHC_RH2HSC1_BASE			0xd18U
+#define XHC_RH2HSC1__TMR_L			31U
+#define XHC_RH2HSC1__TMR_R			16U
+#define XHC_RH2HSC1__TMR_WIDTH			16U
+#define XHC_RH2HSC1__TMR_RESETVALUE		0x0000U
+#define XHC_RH2HSC1__RSL_L			7U
+#define XHC_RH2HSC1__RSL_R			6U
+#define XHC_RH2HSC1__RSL_WIDTH			2U
+#define XHC_RH2HSC1__RSL_RESETVALUE		0x0U
+#define XHC_RH2HSC1__AS_M_L			5U
+#define XHC_RH2HSC1__AS_M_R			4U
+#define XHC_RH2HSC1__AS_M_WIDTH			2U
+#define XHC_RH2HSC1__AS_M_RESETVALUE		0x0U
+#define XHC_RH2HSC1__CMD_L			3U
+#define XHC_RH2HSC1__CMD_R			2U
+#define XHC_RH2HSC1__CMD_WIDTH			2U
+#define XHC_RH2HSC1__CMD_RESETVALUE		0x0U
+#define XHC_RH2HSC1__reserved			1U
+#define XHC_RH2HSC1__reserved_L			1U
+#define XHC_RH2HSC1__reserved_R			1U
+#define XHC_RH2HSC1__reserved_WIDTH		1U
+#define XHC_RH2HSC1__reserved_RESETVALUE	0x0U
+#define XHC_RH2HSC1__STB			0U
+#define XHC_RH2HSC1__STB_L			0U
+#define XHC_RH2HSC1__STB_R			0U
+#define XHC_RH2HSC1__STB_WIDTH			1U
+#define XHC_RH2HSC1__STB_RESETVALUE		0x0U
+#define XHC_RH2HSC1__RESERVED_L			15U
+#define XHC_RH2HSC1__RESERVED_R			8U
+#define XHC_RH2HSC1_WIDTH			32U
+#define XHC_RH2HSC1__WIDTH			32U
+#define XHC_RH2HSC1_ALL_L			31U
+#define XHC_RH2HSC1_ALL_R			0U
+#define XHC_RH2HSC1__ALL_L			31U
+#define XHC_RH2HSC1__ALL_R			0U
+#define XHC_RH2HSC1_DATAMASK			0xffff00ffU
+#define XHC_RH2HSC1_RDWRMASK			0x0000ff00U
+#define XHC_RH2HSC1_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSR1_OFFSET			0xd1cU
+#define XHC_RH2HSR1_BASE			0xd1cU
+#define XHC_RH2HSR1__C2U_L			31U
+#define XHC_RH2HSR1__C2U_R			24U
+#define XHC_RH2HSR1__C2U_WIDTH			8U
+#define XHC_RH2HSR1__C2U_RESETVALUE		0x00U
+#define XHC_RH2HSR1__C1U_L			23U
+#define XHC_RH2HSR1__C1U_R			16U
+#define XHC_RH2HSR1__C1U_WIDTH			8U
+#define XHC_RH2HSR1__C1U_RESETVALUE		0x00U
+#define XHC_RH2HSR1__reserved_L			15U
+#define XHC_RH2HSR1__reserved_R			8U
+#define XHC_RH2HSR1__reserved_WIDTH		8U
+#define XHC_RH2HSR1__reserved_RESETVALUE	0x00U
+#define XHC_RH2HSR1__RTY_L			7U
+#define XHC_RH2HSR1__RTY_R			0U
+#define XHC_RH2HSR1__RTY_WIDTH			8U
+#define XHC_RH2HSR1__RTY_RESETVALUE		0x00U
+#define XHC_RH2HSR1_WIDTH			32U
+#define XHC_RH2HSR1__WIDTH			32U
+#define XHC_RH2HSR1_ALL_L			31U
+#define XHC_RH2HSR1_ALL_R			0U
+#define XHC_RH2HSR1__ALL_L			31U
+#define XHC_RH2HSR1__ALL_R			0U
+#define XHC_RH2HSR1_DATAMASK			0xffffffffU
+#define XHC_RH2HSR1_RDWRMASK			0x00000000U
+#define XHC_RH2HSR1_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSC2_OFFSET			0xd20U
+#define XHC_RH2HSC2_BASE			0xd20U
+#define XHC_RH2HSC2__TMR_L			31U
+#define XHC_RH2HSC2__TMR_R			16U
+#define XHC_RH2HSC2__TMR_WIDTH			16U
+#define XHC_RH2HSC2__TMR_RESETVALUE		0x0000U
+#define XHC_RH2HSC2__RSL_L			7U
+#define XHC_RH2HSC2__RSL_R			6U
+#define XHC_RH2HSC2__RSL_WIDTH			2U
+#define XHC_RH2HSC2__RSL_RESETVALUE		0x0U
+#define XHC_RH2HSC2__AS_M_L			5U
+#define XHC_RH2HSC2__AS_M_R			4U
+#define XHC_RH2HSC2__AS_M_WIDTH			2U
+#define XHC_RH2HSC2__AS_M_RESETVALUE		0x0U
+#define XHC_RH2HSC2__CMD_L			3U
+#define XHC_RH2HSC2__CMD_R			2U
+#define XHC_RH2HSC2__CMD_WIDTH			2U
+#define XHC_RH2HSC2__CMD_RESETVALUE		0x0U
+#define XHC_RH2HSC2__reserved			1U
+#define XHC_RH2HSC2__reserved_L			1U
+#define XHC_RH2HSC2__reserved_R			1U
+#define XHC_RH2HSC2__reserved_WIDTH		1U
+#define XHC_RH2HSC2__reserved_RESETVALUE	0x0U
+#define XHC_RH2HSC2__STB			0U
+#define XHC_RH2HSC2__STB_L			0U
+#define XHC_RH2HSC2__STB_R			0U
+#define XHC_RH2HSC2__STB_WIDTH			1U
+#define XHC_RH2HSC2__STB_RESETVALUE		0x0U
+#define XHC_RH2HSC2__RESERVED_L			15U
+#define XHC_RH2HSC2__RESERVED_R			8U
+#define XHC_RH2HSC2_WIDTH			32U
+#define XHC_RH2HSC2__WIDTH			32U
+#define XHC_RH2HSC2_ALL_L			31U
+#define XHC_RH2HSC2_ALL_R			0U
+#define XHC_RH2HSC2__ALL_L			31U
+#define XHC_RH2HSC2__ALL_R			0U
+#define XHC_RH2HSC2_DATAMASK			0xffff00ffU
+#define XHC_RH2HSC2_RDWRMASK			0x0000ff00U
+#define XHC_RH2HSC2_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSR2_OFFSET			0xd24U
+#define XHC_RH2HSR2_BASE			0xd24U
+#define XHC_RH2HSR2__C2U_L			31U
+#define XHC_RH2HSR2__C2U_R			24U
+#define XHC_RH2HSR2__C2U_WIDTH			8U
+#define XHC_RH2HSR2__C2U_RESETVALUE		0x00U
+#define XHC_RH2HSR2__C1U_L			23U
+#define XHC_RH2HSR2__C1U_R			16U
+#define XHC_RH2HSR2__C1U_WIDTH			8U
+#define XHC_RH2HSR2__C1U_RESETVALUE		0x00U
+#define XHC_RH2HSR2__reserved_L			15U
+#define XHC_RH2HSR2__reserved_R			8U
+#define XHC_RH2HSR2__reserved_WIDTH		8U
+#define XHC_RH2HSR2__reserved_RESETVALUE	0x00U
+#define XHC_RH2HSR2__RTY_L			7U
+#define XHC_RH2HSR2__RTY_R			0U
+#define XHC_RH2HSR2__RTY_WIDTH			8U
+#define XHC_RH2HSR2__RTY_RESETVALUE		0x00U
+#define XHC_RH2HSR2_WIDTH			32U
+#define XHC_RH2HSR2__WIDTH			32U
+#define XHC_RH2HSR2_ALL_L			31U
+#define XHC_RH2HSR2_ALL_R			0U
+#define XHC_RH2HSR2__ALL_L			31U
+#define XHC_RH2HSR2__ALL_R			0U
+#define XHC_RH2HSR2_DATAMASK			0xffffffffU
+#define XHC_RH2HSR2_RDWRMASK			0x00000000U
+#define XHC_RH2HSR2_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSC3_OFFSET			0xd28U
+#define XHC_RH2HSC3_BASE			0xd28U
+#define XHC_RH2HSC3__TMR_L			31U
+#define XHC_RH2HSC3__TMR_R			16U
+#define XHC_RH2HSC3__TMR_WIDTH			16U
+#define XHC_RH2HSC3__TMR_RESETVALUE		0x0000U
+#define XHC_RH2HSC3__RSL_L			7U
+#define XHC_RH2HSC3__RSL_R			6U
+#define XHC_RH2HSC3__RSL_WIDTH			2U
+#define XHC_RH2HSC3__RSL_RESETVALUE		0x0U
+#define XHC_RH2HSC3__AS_M_L			5U
+#define XHC_RH2HSC3__AS_M_R			4U
+#define XHC_RH2HSC3__AS_M_WIDTH			2U
+#define XHC_RH2HSC3__AS_M_RESETVALUE		0x0U
+#define XHC_RH2HSC3__CMD_L			3U
+#define XHC_RH2HSC3__CMD_R			2U
+#define XHC_RH2HSC3__CMD_WIDTH			2U
+#define XHC_RH2HSC3__CMD_RESETVALUE		0x0U
+#define XHC_RH2HSC3__reserved			1U
+#define XHC_RH2HSC3__reserved_L			1U
+#define XHC_RH2HSC3__reserved_R			1U
+#define XHC_RH2HSC3__reserved_WIDTH		1U
+#define XHC_RH2HSC3__reserved_RESETVALUE	0x0U
+#define XHC_RH2HSC3__STB			0U
+#define XHC_RH2HSC3__STB_L			0U
+#define XHC_RH2HSC3__STB_R			0U
+#define XHC_RH2HSC3__STB_WIDTH			1U
+#define XHC_RH2HSC3__STB_RESETVALUE		0x0U
+#define XHC_RH2HSC3__RESERVED_L			15U
+#define XHC_RH2HSC3__RESERVED_R			8U
+#define XHC_RH2HSC3_WIDTH			32U
+#define XHC_RH2HSC3__WIDTH			32U
+#define XHC_RH2HSC3_ALL_L			31U
+#define XHC_RH2HSC3_ALL_R			0U
+#define XHC_RH2HSC3__ALL_L			31U
+#define XHC_RH2HSC3__ALL_R			0U
+#define XHC_RH2HSC3_DATAMASK			0xffff00ffU
+#define XHC_RH2HSC3_RDWRMASK			0x0000ff00U
+#define XHC_RH2HSC3_RESETVALUE			0x00000000U
+
+#define XHC_RH2HSR3_OFFSET			0xd2cU
+#define XHC_RH2HSR3_BASE			0xd2cU
+#define XHC_RH2HSR3__C2U_L			31U
+#define XHC_RH2HSR3__C2U_R			24U
+#define XHC_RH2HSR3__C2U_WIDTH			8U
+#define XHC_RH2HSR3__C2U_RESETVALUE		0x00U
+#define XHC_RH2HSR3__C1U_L			23U
+#define XHC_RH2HSR3__C1U_R			16U
+#define XHC_RH2HSR3__C1U_WIDTH			8U
+#define XHC_RH2HSR3__C1U_RESETVALUE		0x00U
+#define XHC_RH2HSR3__reserved_L			15U
+#define XHC_RH2HSR3__reserved_R			8U
+#define XHC_RH2HSR3__reserved_WIDTH		8U
+#define XHC_RH2HSR3__reserved_RESETVALUE	0x00U
+#define XHC_RH2HSR3__RTY_L			7U
+#define XHC_RH2HSR3__RTY_R			0U
+#define XHC_RH2HSR3__RTY_WIDTH			8U
+#define XHC_RH2HSR3__RTY_RESETVALUE		0x00U
+#define XHC_RH2HSR3_WIDTH			32U
+#define XHC_RH2HSR3__WIDTH			32U
+#define XHC_RH2HSR3_ALL_L			31U
+#define XHC_RH2HSR3_ALL_R			0U
+#define XHC_RH2HSR3__ALL_L			31U
+#define XHC_RH2HSR3__ALL_R			0U
+#define XHC_RH2HSR3_DATAMASK			0xffffffffU
+#define XHC_RH2HSR3_RDWRMASK			0x00000000U
+#define XHC_RH2HSR3_RESETVALUE			0x00000000U
+
+#define XHC_ECHU2P_OFFSET			0xd30U
+#define XHC_ECHU2P_BASE				0xd30U
+#define XHC_ECHU2P__reserved_L			31U
+#define XHC_ECHU2P__reserved_R			16U
+#define XHC_ECHU2P__reserved_WIDTH		16U
+#define XHC_ECHU2P__reserved_RESETVALUE		0x0000U
+#define XHC_ECHU2P__NCP_L			15U
+#define XHC_ECHU2P__NCP_R			8U
+#define XHC_ECHU2P__NCP_WIDTH			8U
+#define XHC_ECHU2P__NCP_RESETVALUE		0x04U
+#define XHC_ECHU2P__CID_L			7U
+#define XHC_ECHU2P__CID_R			0U
+#define XHC_ECHU2P__CID_WIDTH			8U
+#define XHC_ECHU2P__CID_RESETVALUE		0xcaU
+#define XHC_ECHU2P_WIDTH			32U
+#define XHC_ECHU2P__WIDTH			32U
+#define XHC_ECHU2P_ALL_L			31U
+#define XHC_ECHU2P_ALL_R			0U
+#define XHC_ECHU2P__ALL_L			31U
+#define XHC_ECHU2P__ALL_R			0U
+#define XHC_ECHU2P_DATAMASK			0xffffffffU
+#define XHC_ECHU2P_RDWRMASK			0x00000000U
+#define XHC_ECHU2P_RESETVALUE			0x000004caU
+
+#define XHC_U2PVER_OFFSET			0xd34U
+#define XHC_U2PVER_BASE				0xd34U
+#define XHC_U2PVER__MAJ_L			31U
+#define XHC_U2PVER__MAJ_R			28U
+#define XHC_U2PVER__MAJ_WIDTH			4U
+#define XHC_U2PVER__MAJ_RESETVALUE		0x0U
+#define XHC_U2PVER__MIN_L			27U
+#define XHC_U2PVER__MIN_R			24U
+#define XHC_U2PVER__MIN_WIDTH			4U
+#define XHC_U2PVER__MIN_RESETVALUE		0x0U
+#define XHC_U2PVER__RLS_L			23U
+#define XHC_U2PVER__RLS_R			20U
+#define XHC_U2PVER__RLS_WIDTH			4U
+#define XHC_U2PVER__RLS_RESETVALUE		0x0U
+#define XHC_U2PVER__reserved_L			19U
+#define XHC_U2PVER__reserved_R			0U
+#define XHC_U2PVER__reserved_WIDTH		20U
+#define XHC_U2PVER__reserved_RESETVALUE		0x00000U
+#define XHC_U2PVER_WIDTH			32U
+#define XHC_U2PVER__WIDTH			32U
+#define XHC_U2PVER_ALL_L			31U
+#define XHC_U2PVER_ALL_R			0U
+#define XHC_U2PVER__ALL_L			31U
+#define XHC_U2PVER__ALL_R			0U
+#define XHC_U2PVER_DATAMASK			0xffffffffU
+#define XHC_U2PVER_RDWRMASK			0x00000000U
+#define XHC_U2PVER_RESETVALUE			0x00000000U
+
+#define XHC_U2PMGN_OFFSET			0xd38U
+#define XHC_U2PMGN_BASE				0xd38U
+#define XHC_U2PMGN__MGN_L			31U
+#define XHC_U2PMGN__MGN_R			0U
+#define XHC_U2PMGN__MGN_WIDTH			32U
+#define XHC_U2PMGN__MGN_RESETVALUE		0x4b534b4dU
+#define XHC_U2PMGN_WIDTH			32U
+#define XHC_U2PMGN__WIDTH			32U
+#define XHC_U2PMGN_ALL_L			31U
+#define XHC_U2PMGN_ALL_R			0U
+#define XHC_U2PMGN__ALL_L			31U
+#define XHC_U2PMGN__ALL_R			0U
+#define XHC_U2PMGN_DATAMASK			0xffffffffU
+#define XHC_U2PMGN_RDWRMASK			0x00000000U
+#define XHC_U2PMGN_RESETVALUE			0x4b534b4dU
+
+#define XHC_ECHRSV2_OFFSET			0xd40U
+#define XHC_ECHRSV2_BASE			0xd40U
+#define XHC_ECHRSV2__reserved_L			31U
+#define XHC_ECHRSV2__reserved_R			16U
+#define XHC_ECHRSV2__reserved_WIDTH		16U
+#define XHC_ECHRSV2__reserved_RESETVALUE	0x0000U
+#define XHC_ECHRSV2__NCP_L			15U
+#define XHC_ECHRSV2__NCP_R			8U
+#define XHC_ECHRSV2__NCP_WIDTH			8U
+#define XHC_ECHRSV2__NCP_RESETVALUE		0x00U
+#define XHC_ECHRSV2__CID_L			7U
+#define XHC_ECHRSV2__CID_R			0U
+#define XHC_ECHRSV2__CID_WIDTH			8U
+#define XHC_ECHRSV2__CID_RESETVALUE		0xffU
+#define XHC_ECHRSV2_WIDTH			32U
+#define XHC_ECHRSV2__WIDTH			32U
+#define XHC_ECHRSV2_ALL_L			31U
+#define XHC_ECHRSV2_ALL_R			0U
+#define XHC_ECHRSV2__ALL_L			31U
+#define XHC_ECHRSV2__ALL_R			0U
+#define XHC_ECHRSV2_DATAMASK			0xffffffffU
+#define XHC_ECHRSV2_RDWRMASK			0x00000000U
+#define XHC_ECHRSV2_RESETVALUE			0x000000ffU
+
+#define XHC_ECHIRA_OFFSET			0xf90U
+#define XHC_ECHIRA_BASE				0xf90U
+#define XHC_ECHIRA__reserved_L			31U
+#define XHC_ECHIRA__reserved_R			16U
+#define XHC_ECHIRA__reserved_WIDTH		16U
+#define XHC_ECHIRA__reserved_RESETVALUE		0x0000U
+#define XHC_ECHIRA__NCP_L			15U
+#define XHC_ECHIRA__NCP_R			8U
+#define XHC_ECHIRA__NCP_WIDTH			8U
+#define XHC_ECHIRA__NCP_RESETVALUE		0x04U
+#define XHC_ECHIRA__CID_L			7U
+#define XHC_ECHIRA__CID_R			0U
+#define XHC_ECHIRA__CID_WIDTH			8U
+#define XHC_ECHIRA__CID_RESETVALUE		0xfdU
+#define XHC_ECHIRA_WIDTH			32U
+#define XHC_ECHIRA__WIDTH			32U
+#define XHC_ECHIRA_ALL_L			31U
+#define XHC_ECHIRA_ALL_R			0U
+#define XHC_ECHIRA__ALL_L			31U
+#define XHC_ECHIRA__ALL_R			0U
+#define XHC_ECHIRA_DATAMASK			0xffffffffU
+#define XHC_ECHIRA_RDWRMASK			0x00000000U
+#define XHC_ECHIRA_RESETVALUE			0x000004fdU
+
+#define XHC_IRAADR_OFFSET			0xf98U
+#define XHC_IRAADR_BASE				0xf98U
+#define XHC_IRAADR__ADR_L			23U
+#define XHC_IRAADR__ADR_R			2U
+#define XHC_IRAADR__ADR_WIDTH			22U
+#define XHC_IRAADR__ADR_RESETVALUE		0x0U
+#define XHC_IRAADR__reserved			1U
+#define XHC_IRAADR__reserved_L			1U
+#define XHC_IRAADR__reserved_R			1U
+#define XHC_IRAADR__reserved_WIDTH		1U
+#define XHC_IRAADR__reserved_RESETVALUE		0x0U
+#define XHC_IRAADR__MOD				0U
+#define XHC_IRAADR__MOD_L			0U
+#define XHC_IRAADR__MOD_R			0U
+#define XHC_IRAADR__MOD_WIDTH			1U
+#define XHC_IRAADR__MOD_RESETVALUE		0x0U
+#define XHC_IRAADR__RESERVED_L			31U
+#define XHC_IRAADR__RESERVED_R			24U
+#define XHC_IRAADR_WIDTH			24U
+#define XHC_IRAADR__WIDTH			24U
+#define XHC_IRAADR_ALL_L			23U
+#define XHC_IRAADR_ALL_R			0U
+#define XHC_IRAADR__ALL_L			23U
+#define XHC_IRAADR__ALL_R			0U
+#define XHC_IRAADR_DATAMASK			0x00ffffffU
+#define XHC_IRAADR_RDWRMASK			0xff000000U
+#define XHC_IRAADR_RESETVALUE			0x000000U
+
+#define XHC_IRADAT_OFFSET			0xf9cU
+#define XHC_IRADAT_BASE			0xf9cU
+#define XHC_IRADAT__DAT_L			31U
+#define XHC_IRADAT__DAT_R			0U
+#define XHC_IRADAT__DAT_WIDTH			32U
+#define XHC_IRADAT__DAT_RESETVALUE			0x00000000U
+#define XHC_IRADAT_WIDTH			32U
+#define XHC_IRADAT__WIDTH			32U
+#define XHC_IRADAT_ALL_L			31U
+#define XHC_IRADAT_ALL_R			0U
+#define XHC_IRADAT__ALL_L			31U
+#define XHC_IRADAT__ALL_R			0U
+#define XHC_IRADAT_DATAMASK			0xffffffffU
+#define XHC_IRADAT_RDWRMASK			0x00000000U
+#define XHC_IRADAT_RESETVALUE			0x00000000U
+
+
+#define XHC_ECHHST_OFFSET			0xfa0U
+#define XHC_ECHHST_BASE				0xfa0U
+#define XHC_ECHHST__CCC				31U
+#define XHC_ECHHST__CCC_L			31U
+#define XHC_ECHHST__CCC_R			31U
+#define XHC_ECHHST__CCC_WIDTH			1U
+#define XHC_ECHHST__CCC_RESETVALUE		0x1U
+#define XHC_ECHHST__PME				30U
+#define XHC_ECHHST__PME_L			30U
+#define XHC_ECHHST__PME_R			30U
+#define XHC_ECHHST__PME_WIDTH			1U
+#define XHC_ECHHST__PME_RESETVALUE		0x0U
+#define XHC_ECHHST__AUX_L			29U
+#define XHC_ECHHST__AUX_R			24U
+#define XHC_ECHHST__AUX_WIDTH			6U
+#define XHC_ECHHST__AUX_RESETVALUE		0x0U
+#define XHC_ECHHST__IRA				20U
+#define XHC_ECHHST__IRA_L			20U
+#define XHC_ECHHST__IRA_R			20U
+#define XHC_ECHHST__IRA_WIDTH			1U
+#define XHC_ECHHST__IRA_RESETVALUE		0x0U
+#define XHC_ECHHST__ULS				19U
+#define XHC_ECHHST__ULS_L			19U
+#define XHC_ECHHST__ULS_R			19U
+#define XHC_ECHHST__ULS_WIDTH			1U
+#define XHC_ECHHST__ULS_RESETVALUE		0x0U
+#define XHC_ECHHST__reserved			18U
+#define XHC_ECHHST__reserved_L			18U
+#define XHC_ECHHST__reserved_R			18U
+#define XHC_ECHHST__reserved_WIDTH		1U
+#define XHC_ECHHST__reserved_RESETVALUE		0x0U
+#define XHC_ECHHST__TEDA			17U
+#define XHC_ECHHST__TEDA_L			17U
+#define XHC_ECHHST__TEDA_R			17U
+#define XHC_ECHHST__TEDA_WIDTH			1U
+#define XHC_ECHHST__TEDA_RESETVALUE		0x0U
+#define XHC_ECHHST__FSW				16U
+#define XHC_ECHHST__FSW_L			16U
+#define XHC_ECHHST__FSW_R			16U
+#define XHC_ECHHST__FSW_WIDTH			1U
+#define XHC_ECHHST__FSW_RESETVALUE		0x1U
+#define XHC_ECHHST__NCP_L			15U
+#define XHC_ECHHST__NCP_R			8U
+#define XHC_ECHHST__NCP_WIDTH			8U
+#define XHC_ECHHST__NCP_RESETVALUE		0x04U
+#define XHC_ECHHST__CID_L			7U
+#define XHC_ECHHST__CID_R			0U
+#define XHC_ECHHST__CID_WIDTH			8U
+#define XHC_ECHHST__CID_RESETVALUE		0xfcU
+#define XHC_ECHHST__RESERVED_L			23U
+#define XHC_ECHHST__RESERVED_R			21U
+#define XHC_ECHHST_WIDTH			32U
+#define XHC_ECHHST__WIDTH			32U
+#define XHC_ECHHST_ALL_L			31U
+#define XHC_ECHHST_ALL_R			0U
+#define XHC_ECHHST__ALL_L			31U
+#define XHC_ECHHST__ALL_R			0U
+#define XHC_ECHHST_DATAMASK			0xff1fffffU
+#define XHC_ECHHST_RDWRMASK			0x00e00000U
+#define XHC_ECHHST_RESETVALUE			0x800104fcU
+
+#define XHC_HSTDBG_OFFSET			0xfa4U
+#define XHC_HSTDBG_BASE				0xfa4U
+#define XHC_HSTDBG__ETE				31U
+#define XHC_HSTDBG__ETE_L			31U
+#define XHC_HSTDBG__ETE_R			31U
+#define XHC_HSTDBG__ETE_WIDTH			1U
+#define XHC_HSTDBG__ETE_RESETVALUE		0x0U
+#define XHC_HSTDBG__reserved_L			30U
+#define XHC_HSTDBG__reserved_R			16U
+#define XHC_HSTDBG__reserved_WIDTH		15U
+#define XHC_HSTDBG__reserved_RESETVALUE		0x0U
+#define XHC_HSTDBG__OUTP_L			15U
+#define XHC_HSTDBG__OUTP_R			8U
+#define XHC_HSTDBG__OUTP_WIDTH			8U
+#define XHC_HSTDBG__OUTP_RESETVALUE		0x00U
+#define XHC_HSTDBG__INP_L			7U
+#define XHC_HSTDBG__INP_R			0U
+#define XHC_HSTDBG__INP_WIDTH			8U
+#define XHC_HSTDBG__INP_RESETVALUE		0x00U
+#define XHC_HSTDBG_WIDTH			32U
+#define XHC_HSTDBG__WIDTH			32U
+#define XHC_HSTDBG_ALL_L			31U
+#define XHC_HSTDBG_ALL_R			0U
+#define XHC_HSTDBG__ALL_L			31U
+#define XHC_HSTDBG__ALL_R			0U
+#define XHC_HSTDBG_DATAMASK			0xffffffffU
+#define XHC_HSTDBG_RDWRMASK			0x00000000U
+#define XHC_HSTDBG_RESETVALUE			0x00000000U
+
+#define XHC_HSTNPL_OFFSET			0xfa8U
+#define XHC_HSTNPL_BASE				0xfa8U
+#define XHC_HSTNPL__NPL_L			31U
+#define XHC_HSTNPL__NPL_R			9U
+#define XHC_HSTNPL__NPL_WIDTH			23U
+#define XHC_HSTNPL__NPL_RESETVALUE		0x0U
+#define XHC_HSTNPL__reserved_L			8U
+#define XHC_HSTNPL__reserved_R			0U
+#define XHC_HSTNPL__reserved_WIDTH		9U
+#define XHC_HSTNPL__reserved_RESETVALUE		0x0U
+#define XHC_HSTNPL_WIDTH			32U
+#define XHC_HSTNPL__WIDTH			32U
+#define XHC_HSTNPL_ALL_L			31U
+#define XHC_HSTNPL_ALL_R			0U
+#define XHC_HSTNPL__ALL_L			31U
+#define XHC_HSTNPL__ALL_R			0U
+#define XHC_HSTNPL_DATAMASK			0xffffffffU
+#define XHC_HSTNPL_RDWRMASK			0x00000000U
+#define XHC_HSTNPL_RESETVALUE			0x00000000U
+
+#define XHC_HSTNPH_OFFSET			0xfacU
+#define XHC_HSTNPH_BASE				0xfacU
+#define XHC_HSTNPH__NPH_L			31U
+#define XHC_HSTNPH__NPH_R			0U
+#define XHC_HSTNPH__NPH_WIDTH			32U
+#define XHC_HSTNPH__NPH_RESETVALUE		0x00000000U
+#define XHC_HSTNPH_WIDTH			32U
+#define XHC_HSTNPH__WIDTH			32U
+#define XHC_HSTNPH_ALL_L			31U
+#define XHC_HSTNPH_ALL_R			0U
+#define XHC_HSTNPH__ALL_L			31U
+#define XHC_HSTNPH__ALL_R			0U
+#define XHC_HSTNPH_DATAMASK			0xffffffffU
+#define XHC_HSTNPH_RDWRMASK			0x00000000U
+#define XHC_HSTNPH_RESETVALUE			0x00000000U
+
+#define XHC_ECHRBV_OFFSET			0xfb0U
+#define XHC_ECHRBV_BASE				0xfb0U
+#define XHC_ECHRBV__MAJ_L			31U
+#define XHC_ECHRBV__MAJ_R			28U
+#define XHC_ECHRBV__MAJ_WIDTH			4U
+#define XHC_ECHRBV__MAJ_RESETVALUE		0x0U
+#define XHC_ECHRBV__MIN_L			27U
+#define XHC_ECHRBV__MIN_R			24U
+#define XHC_ECHRBV__MIN_WIDTH			4U
+#define XHC_ECHRBV__MIN_RESETVALUE		0x0U
+#define XHC_ECHRBV__RLS_L			23U
+#define XHC_ECHRBV__RLS_R			16U
+#define XHC_ECHRBV__RLS_WIDTH			8U
+#define XHC_ECHRBV__RLS_RESETVALUE		0x00U
+#define XHC_ECHRBV__NCP_L			15U
+#define XHC_ECHRBV__NCP_R			8U
+#define XHC_ECHRBV__NCP_WIDTH			8U
+#define XHC_ECHRBV__NCP_RESETVALUE		0x00U
+#define XHC_ECHRBV__CID_L			7U
+#define XHC_ECHRBV__CID_R			0U
+#define XHC_ECHRBV__CID_WIDTH			8U
+#define XHC_ECHRBV__CID_RESETVALUE		0xfeU
+#define XHC_ECHRBV_WIDTH			32U
+#define XHC_ECHRBV__WIDTH			32U
+#define XHC_ECHRBV_ALL_L			31U
+#define XHC_ECHRBV_ALL_R			0U
+#define XHC_ECHRBV__ALL_L			31U
+#define XHC_ECHRBV__ALL_R			0U
+#define XHC_ECHRBV_DATAMASK			0xffffffffU
+#define XHC_ECHRBV_RDWRMASK			0x00000000U
+#define XHC_ECHRBV_RESETVALUE			0x000000feU
+
+#define XHC_RBVPDT_OFFSET			0xfb4U
+#define XHC_RBVPDT_BASE				0xfb4U
+#define XHC_RBVPDT__VDR_L			31U
+#define XHC_RBVPDT__VDR_R			16U
+#define XHC_RBVPDT__VDR_WIDTH			16U
+#define XHC_RBVPDT__VDR_RESETVALUE		0x0a5cU
+#define XHC_RBVPDT__PDT_L			15U
+#define XHC_RBVPDT__PDT_R			0U
+#define XHC_RBVPDT__PDT_WIDTH			16U
+#define XHC_RBVPDT__PDT_RESETVALUE		0x0000U
+#define XHC_RBVPDT_WIDTH			32U
+#define XHC_RBVPDT__WIDTH			32U
+#define XHC_RBVPDT_ALL_L			31U
+#define XHC_RBVPDT_ALL_R			0U
+#define XHC_RBVPDT__ALL_L			31U
+#define XHC_RBVPDT__ALL_R			0U
+#define XHC_RBVPDT_DATAMASK			0xffffffffU
+#define XHC_RBVPDT_RDWRMASK			0x00000000U
+#define XHC_RBVPDT_RESETVALUE			0x0a5c0000U
+
+#define XHC_RBVMGN_OFFSET			0xfbcU
+#define XHC_RBVMGN_BASE				0xfbcU
+#define XHC_RBVMGN__MGN_L			31U
+#define XHC_RBVMGN__MGN_R			0U
+#define XHC_RBVMGN__MGN_WIDTH			32U
+#define XHC_RBVMGN__MGN_RESETVALUE		0x52535354U
+#define XHC_RBVMGN_WIDTH			32U
+#define XHC_RBVMGN__WIDTH			32U
+#define XHC_RBVMGN_ALL_L			31U
+#define XHC_RBVMGN_ALL_R			0U
+#define XHC_RBVMGN__ALL_L			31U
+#define XHC_RBVMGN__ALL_R			0U
+#define XHC_RBVMGN_DATAMASK			0xffffffffU
+#define XHC_RBVMGN_RDWRMASK			0x00000000U
+#define XHC_RBVMGN_RESETVALUE			0x52535354U
+
+/* PORTSC field defines */
+#define XHC_PORTSC__PS_LINK_STATE_U0		0U
+#define XHC_PORTSC__PS_LINK_STATE_U1		1U
+#define XHC_PORTSC__PS_LINK_STATE_U2		2U
+#define XHC_PORTSC__PS_LINK_STATE_U3		3U
+#define XHC_PORTSC__PS_LINK_STATE_DISABLED	4U
+#define XHC_PORTSC__PS_LINK_STATE_RX_DETECT	5U
+#define XHC_PORTSC__PS_LINK_STATE_INACTIVE	6U
+#define XHC_PORTSC__PS_LINK_STATE_POLLING	7U
+#define XHC_PORTSC__PS_LINK_STATE_RECOVERY	8U
+#define XHC_PORTSC__PS_LINK_STATE_HOT_RESET	9U
+#define XHC_PORTSC__PS_LINK_STATE_COMPLIANCE	10U
+#define XHC_PORTSC__PS_LINK_STATE_TEST		11U
+#define XHC_PORTSC__PS_LINK_STATE_RESUME	15U
+
+#define XHC_PORTSC__PS_SPEED_UNDEFINED		0U
+#define XHC_PORTSC__PS_FS			1U
+#define XHC_PORTSC__PS_LS			2U
+#define XHC_PORTSC__PS_HS			3U
+#define XHC_PORTSC__PS_SS			4U
+
+/* macros and inline functions */
+
+/* write 64bit ptr 'p' to destination 'd' with offset 'v' */
+inline void WRITE64_REG_PTRL(uint32_t r, uint32_t *p)
+{
+	uint32_t *ptr = (uint32_t *) (uint64_t) (XHC_BASE + r);
+
+	*ptr = (uint32_t) ((uint64_t) p & (uint64_t) 0xffffffffU);
+}
+
+inline void WRITE64_REG_PTRH(uint32_t r, uint32_t *p)
+{
+	uint32_t *ptr = (uint32_t *) (uint64_t) (XHC_BASE + r);
+
+	*ptr = (uint32_t) ((uint64_t) p >> 32U);
+}
+
+#define XHC_REG_RD(addr)   mmio_read_32(XHC_BASE + addr)
+
+#define XHC_REG_WR(addr, val) mmio_write_32(XHC_BASE+addr, val)
+
+#endif				/* USBH_XHCI_REGS_H */
+
diff --git a/include/drivers/cadence/cdns_uart.h b/include/drivers/cadence/cdns_uart.h
index 46ba466..30ca910 100644
--- a/include/drivers/cadence/cdns_uart.h
+++ b/include/drivers/cadence/cdns_uart.h
@@ -21,6 +21,7 @@
 #define R_UART_SR		0x2C
 #define UART_SR_INTR_REMPTY_BIT	1
 #define UART_SR_INTR_TFUL_BIT	4
+#define UART_SR_INTR_TEMPTY_BIT	3
 
 #define R_UART_TX	0x30
 #define R_UART_RX	0x30
diff --git a/include/drivers/fwu/fwu.h b/include/drivers/fwu/fwu.h
new file mode 100644
index 0000000..ae06da9
--- /dev/null
+++ b/include/drivers/fwu/fwu.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FWU_H
+#define FWU_H
+
+#include <stdbool.h>
+
+void fwu_init(void);
+bool fwu_is_trial_run_state(void);
+
+#endif /* FWU_H */
diff --git a/include/drivers/fwu/fwu_metadata.h b/include/drivers/fwu/fwu_metadata.h
new file mode 100644
index 0000000..2e88de5
--- /dev/null
+++ b/include/drivers/fwu/fwu_metadata.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * FWU metadata information as per the specification section 4.1:
+ * https://developer.arm.com/documentation/den0118/a/
+ *
+ */
+
+#ifndef FWU_METADATA_H
+#define FWU_METADATA_H
+
+#include <stdint.h>
+#include <tools_share/uuid.h>
+
+/* Properties of image in a bank */
+struct fwu_image_properties {
+
+	/* UUID of the image in this bank */
+	uuid_t img_uuid;
+
+	/* [0]: bit describing the image acceptance status –
+	 *      1 means the image is accepted
+	 * [31:1]: MBZ
+	 */
+	uint32_t accepted;
+
+	/* reserved (MBZ) */
+	uint32_t reserved;
+
+} __packed;
+
+/* Image entry information */
+struct fwu_image_entry {
+
+	/* UUID identifying the image type */
+	uuid_t img_type_uuid;
+
+	/* UUID of the storage volume where the image is located */
+	uuid_t location_uuid;
+
+	/* Properties of images with img_type_uuid in the different FW banks */
+	struct fwu_image_properties img_props[NR_OF_FW_BANKS];
+
+} __packed;
+
+/*
+ * FWU metadata filled by the updater and consumed by TF-A for
+ * various purposes as below:
+ * 1. Get active FW bank.
+ * 2. Rollback to previous working FW bank.
+ * 3. Get properties of all images present in all banks.
+ */
+struct fwu_metadata {
+
+	/* Metadata CRC value */
+	uint32_t crc_32;
+
+	/* Metadata version */
+	uint32_t version;
+
+	/* Bank index with which device boots */
+	uint32_t active_index;
+
+	/* Previous bank index with which device booted successfully */
+	uint32_t previous_active_index;
+
+	/* Image entry information */
+	struct fwu_image_entry img_entry[NR_OF_IMAGES_IN_FW_BANK];
+
+} __packed;
+
+#endif /* FWU_METADATA_H */
diff --git a/include/drivers/io/io_mtd.h b/include/drivers/io/io_mtd.h
index 1395ff6..2b5d9b1 100644
--- a/include/drivers/io/io_mtd.h
+++ b/include/drivers/io/io_mtd.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -44,11 +44,22 @@
 	 * Return 0 on success, a negative error code otherwise.
 	 */
 	int (*write)(unsigned int offset, uintptr_t buffer, size_t length);
+
+	/*
+	 * Look for an offset to be added to the given offset.
+	 *
+	 * @base: Base address of the area.
+	 * @offset: Offset in bytes to start read operation.
+	 * @extra_offset: [out] Offset to be added to the previous offset.
+	 * Return 0 on success, a negative error code otherwise.
+	 */
+	int (*seek)(uintptr_t base, unsigned int offset, size_t *extra_offset);
 } io_mtd_ops_t;
 
 typedef struct io_mtd_dev_spec {
 	unsigned long long device_size;
 	unsigned int erase_size;
+	size_t offset;
 	io_mtd_ops_t ops;
 } io_mtd_dev_spec_t;
 
diff --git a/include/drivers/marvell/mochi/cp110_setup.h b/include/drivers/marvell/mochi/cp110_setup.h
index 11dc4e0..4a69257 100644
--- a/include/drivers/marvell/mochi/cp110_setup.h
+++ b/include/drivers/marvell/mochi/cp110_setup.h
@@ -31,6 +31,9 @@
 #define MAX_STREAM_ID_PER_CP		(0x10)
 #define STREAM_ID_BASE			(0x40)
 
+#define MVEBU_SECUREBOOT_CTRL_REG	(MVEBU_RFU_BASE + 0x4730)
+#define MVEBU_SECUREBOOT_EN_MASK	BIT(0)
+
 static inline uint32_t cp110_device_id_get(uintptr_t base)
 {
 	/* Returns:
@@ -50,6 +53,12 @@
 		MVEBU_DEVICE_REV_OFFSET;
 }
 
+static inline uint32_t is_secure(void)
+{
+	return !!(mmio_read_32(MVEBU_SECUREBOOT_CTRL_REG) &
+			       MVEBU_SECUREBOOT_EN_MASK);
+}
+
 void cp110_init(uintptr_t cp110_base, uint32_t stream_id);
 void cp110_ble_init(uintptr_t cp110_base);
 void cp110_amb_init(uintptr_t base);
diff --git a/include/drivers/marvell/uart/a3700_console.h b/include/drivers/marvell/uart/a3700_console.h
index 5e3ab05..12d2cdc 100644
--- a/include/drivers/marvell/uart/a3700_console.h
+++ b/include/drivers/marvell/uart/a3700_console.h
@@ -48,11 +48,12 @@
 
 /* Line Status Register bits */
 #define UARTLSR_TXFIFOFULL	(1 << 11)	/* Tx Fifo Full */
+#define UARTLSR_TXEMPTY		(1 << 6)	/* Tx Empty */
+#define UARTLSR_RXRDY		(1 << 4)	/* Rx Ready */
 
 /* UART Control Register bits */
 #define UART_CTRL_RXFIFO_RESET	(1 << 14)
 #define UART_CTRL_TXFIFO_RESET	(1 << 15)
-#define UARTLSR_TXFIFOEMPTY	(1 << 6)
 
 #ifndef __ASSEMBLER__
 
diff --git a/include/drivers/measured_boot/event_log.h b/include/drivers/measured_boot/event_log.h
deleted file mode 100644
index efde117..0000000
--- a/include/drivers/measured_boot/event_log.h
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef EVENT_LOG_H
-#define EVENT_LOG_H
-
-#include <stdint.h>
-
-#include <common/debug.h>
-#include <drivers/measured_boot/tcg.h>
-
-/*
- * Set Event Log debug level to one of:
- *
- * LOG_LEVEL_ERROR
- * LOG_LEVEL_INFO
- * LOG_LEVEL_WARNING
- * LOG_LEVEL_VERBOSE
- */
-#if EVENT_LOG_LEVEL   == LOG_LEVEL_ERROR
-#define	LOG_EVENT	ERROR
-#elif EVENT_LOG_LEVEL == LOG_LEVEL_NOTICE
-#define	LOG_EVENT	NOTICE
-#elif EVENT_LOG_LEVEL == LOG_LEVEL_WARNING
-#define	LOG_EVENT	WARN
-#elif EVENT_LOG_LEVEL == LOG_LEVEL_INFO
-#define	LOG_EVENT	INFO
-#elif EVENT_LOG_LEVEL == LOG_LEVEL_VERBOSE
-#define	LOG_EVENT	VERBOSE
-#else
-#error "Not supported EVENT_LOG_LEVEL"
-#endif
-
-/* Number of hashing algorithms supported */
-#define HASH_ALG_COUNT	1U
-
-#define	INVALID_ID	MAX_NUMBER_IDS
-
-#define MEMBER_SIZE(type, member) sizeof(((type *)0)->member)
-
-#define BL2_STRING			"BL_2"
-#define BL31_STRING			"BL_31"
-#define BL32_STRING			"BL_32"
-#define	BL32_EXTRA1_IMAGE_STRING	"BL32_EXTRA1_IMAGE"
-#define	BL32_EXTRA2_IMAGE_STRING	"BL32_EXTRA2_IMAGE"
-#define BL33_STRING			"BL_33"
-#define GPT_IMAGE_STRING		"GPT"
-#define HW_CONFIG_STRING		"HW_CONFIG"
-#define NT_FW_CONFIG_STRING		"NT_FW_CONFIG"
-#define SCP_BL2_IMAGE_STRING		"SCP_BL2_IMAGE"
-#define SOC_FW_CONFIG_STRING		"SOC_FW_CONFIG"
-#define STM32_IMAGE_STRING		"STM32"
-#define	TOS_FW_CONFIG_STRING		"TOS_FW_CONFIG"
-
-typedef struct {
-	unsigned int id;
-	const char *name;
-	unsigned int pcr;
-} image_data_t;
-
-typedef struct {
-	const image_data_t *images_data;
-	int (*set_nt_fw_info)(uintptr_t config_base,
-#ifdef SPD_opteed
-				uintptr_t log_addr,
-#endif
-				size_t log_size, uintptr_t *ns_log_addr);
-	int (*set_tos_fw_info)(uintptr_t config_base, uintptr_t log_addr,
-				size_t log_size);
-} measured_boot_data_t;
-
-#define	ID_EVENT_SIZE	(sizeof(id_event_headers_t) + \
-			(sizeof(id_event_algorithm_size_t) * HASH_ALG_COUNT) + \
-			sizeof(id_event_struct_data_t))
-
-#define	LOC_EVENT_SIZE	(sizeof(event2_header_t) + \
-			sizeof(tpmt_ha) + TCG_DIGEST_SIZE + \
-			sizeof(event2_data_t) + \
-			sizeof(startup_locality_event_t))
-
-#define	LOG_MIN_SIZE	(ID_EVENT_SIZE + LOC_EVENT_SIZE)
-
-#define EVENT2_HDR_SIZE	(sizeof(event2_header_t) + \
-			sizeof(tpmt_ha) + TCG_DIGEST_SIZE + \
-			sizeof(event2_data_t))
-
-/* Functions' declarations */
-void event_log_init(void);
-int event_log_finalise(uint8_t **log_addr, size_t *log_size);
-void dump_event_log(uint8_t *log_addr, size_t log_size);
-const measured_boot_data_t *plat_get_measured_boot_data(void);
-int tpm_record_measurement(uintptr_t data_base, uint32_t data_size,
-			   uint32_t data_id);
-#endif /* EVENT_LOG_H */
diff --git a/include/drivers/measured_boot/event_log/event_log.h b/include/drivers/measured_boot/event_log/event_log.h
new file mode 100644
index 0000000..c6eb29c
--- /dev/null
+++ b/include/drivers/measured_boot/event_log/event_log.h
@@ -0,0 +1,111 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EVENT_LOG_H
+#define EVENT_LOG_H
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <common/tbbr/tbbr_img_def.h>
+#include <drivers/measured_boot/event_log/tcg.h>
+
+/*
+ * Set Event Log debug level to one of:
+ *
+ * LOG_LEVEL_ERROR
+ * LOG_LEVEL_INFO
+ * LOG_LEVEL_WARNING
+ * LOG_LEVEL_VERBOSE
+ */
+#if EVENT_LOG_LEVEL   == LOG_LEVEL_ERROR
+#define	LOG_EVENT	ERROR
+#elif EVENT_LOG_LEVEL == LOG_LEVEL_NOTICE
+#define	LOG_EVENT	NOTICE
+#elif EVENT_LOG_LEVEL == LOG_LEVEL_WARNING
+#define	LOG_EVENT	WARN
+#elif EVENT_LOG_LEVEL == LOG_LEVEL_INFO
+#define	LOG_EVENT	INFO
+#elif EVENT_LOG_LEVEL == LOG_LEVEL_VERBOSE
+#define	LOG_EVENT	VERBOSE
+#else
+#error "Not supported EVENT_LOG_LEVEL"
+#endif
+
+/* Number of hashing algorithms supported */
+#define HASH_ALG_COUNT	1U
+
+#define	INVALID_ID	MAX_NUMBER_IDS
+
+#define MEMBER_SIZE(type, member) sizeof(((type *)0)->member)
+
+/*
+ * Each event log entry has some metadata (i.e. a string) that identifies
+ * what is measured.These macros define these strings.
+ * Note that these strings follow the standardization recommendations
+ * defined in the Arm Server Base Security Guide (a.k.a. SBSG, Arm DEN 0086),
+ * where applicable. They should not be changed in the code.
+ * Where the SBSG does not make recommendations, we are free to choose any
+ * naming convention.
+ * The key thing is to choose meaningful strings so that when the TPM event
+ * log is used in attestation, the different components can be identified.
+ */
+#define EVLOG_BL2_STRING		"BL_2"
+#define EVLOG_BL31_STRING		"SECURE_RT_EL3"
+#if defined(SPD_opteed)
+#define EVLOG_BL32_STRING		"SECURE_RT_EL1_OPTEE"
+#elif defined(SPD_tspd)
+#define EVLOG_BL32_STRING		"SECURE_RT_EL1_TSPD"
+#elif defined(SPD_tlkd)
+#define EVLOG_BL32_STRING		"SECURE_RT_EL1_TLKD"
+#elif defined(SPD_trusty)
+#define EVLOG_BL32_STRING		"SECURE_RT_EL1_TRUSTY"
+#else
+#define EVLOG_BL32_STRING		"SECURE_RT_EL1_UNKNOWN"
+#endif
+#define	EVLOG_BL32_EXTRA1_STRING	"SECURE_RT_EL1_OPTEE_EXTRA1"
+#define	EVLOG_BL32_EXTRA2_STRING	"SECURE_RT_EL1_OPTEE_EXTRA2"
+#define EVLOG_BL33_STRING		"BL_33"
+#define EVLOG_FW_CONFIG_STRING		"FW_CONFIG"
+#define EVLOG_HW_CONFIG_STRING		"HW_CONFIG"
+#define EVLOG_NT_FW_CONFIG_STRING	"NT_FW_CONFIG"
+#define EVLOG_SCP_BL2_STRING		"SYS_CTRL_2"
+#define EVLOG_SOC_FW_CONFIG_STRING	"SOC_FW_CONFIG"
+#define EVLOG_STM32_STRING		"STM32"
+#define EVLOG_TB_FW_CONFIG_STRING	"TB_FW_CONFIG"
+#define	EVLOG_TOS_FW_CONFIG_STRING	"TOS_FW_CONFIG"
+
+typedef struct {
+	unsigned int id;
+	const char *name;
+	unsigned int pcr;
+} event_log_metadata_t;
+
+#define	ID_EVENT_SIZE	(sizeof(id_event_headers_t) + \
+			(sizeof(id_event_algorithm_size_t) * HASH_ALG_COUNT) + \
+			sizeof(id_event_struct_data_t))
+
+#define	LOC_EVENT_SIZE	(sizeof(event2_header_t) + \
+			sizeof(tpmt_ha) + TCG_DIGEST_SIZE + \
+			sizeof(event2_data_t) + \
+			sizeof(startup_locality_event_t))
+
+#define	LOG_MIN_SIZE	(ID_EVENT_SIZE + LOC_EVENT_SIZE)
+
+#define EVENT2_HDR_SIZE	(sizeof(event2_header_t) + \
+			sizeof(tpmt_ha) + TCG_DIGEST_SIZE + \
+			sizeof(event2_data_t))
+
+/* Functions' declarations */
+void event_log_init(uint8_t *event_log_start, uint8_t *event_log_finish);
+void event_log_write_header(void);
+void dump_event_log(uint8_t *log_addr, size_t log_size);
+const event_log_metadata_t *plat_event_log_get_metadata(void);
+int event_log_measure_and_record(uintptr_t data_base, uint32_t data_size,
+				 uint32_t data_id);
+size_t event_log_get_cur_size(uint8_t *event_log_start);
+
+#endif /* EVENT_LOG_H */
diff --git a/include/drivers/measured_boot/tcg.h b/include/drivers/measured_boot/event_log/tcg.h
similarity index 100%
rename from include/drivers/measured_boot/tcg.h
rename to include/drivers/measured_boot/event_log/tcg.h
diff --git a/include/drivers/measured_boot/measured_boot.h b/include/drivers/measured_boot/measured_boot.h
deleted file mode 100644
index f8769ab..0000000
--- a/include/drivers/measured_boot/measured_boot.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef MEASURED_BOOT_H
-#define MEASURED_BOOT_H
-
-#include <stdint.h>
-
-#include <drivers/measured_boot/event_log.h>
-
-/* Platform specific table of image IDs, names and PCRs */
-extern const image_data_t images_data[];
-
-/* Functions' declarations */
-void measured_boot_init(void);
-void measured_boot_finish(void);
-
-#endif /* MEASURED_BOOT_H */
diff --git a/include/drivers/mmc.h b/include/drivers/mmc.h
index 7611f01..834a80f 100644
--- a/include/drivers/mmc.h
+++ b/include/drivers/mmc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -60,10 +60,16 @@
 #define CMD_EXTCSD_PARTITION_CONFIG	179
 #define CMD_EXTCSD_BUS_WIDTH		183
 #define CMD_EXTCSD_HS_TIMING		185
+#define CMD_EXTCSD_PART_SWITCH_TIME	199
 #define CMD_EXTCSD_SEC_CNT		212
 
+#define EXT_CSD_PART_CONFIG_ACC_MASK	GENMASK(2, 0)
 #define PART_CFG_BOOT_PARTITION1_ENABLE	(U(1) << 3)
-#define PART_CFG_PARTITION1_ACCESS	(U(1) << 0)
+#define PART_CFG_BOOT_PARTITION1_ACCESS (U(1) << 0)
+#define PART_CFG_BOOT_PART_EN_MASK		GENMASK(5, 3)
+#define PART_CFG_BOOT_PART_EN_SHIFT		3
+#define PART_CFG_CURRENT_BOOT_PARTITION(x)	(((x) & PART_CFG_BOOT_PART_EN_MASK) >> \
+	PART_CFG_BOOT_PART_EN_SHIFT)
 
 /* Values in EXT CSD register */
 #define MMC_BUS_WIDTH_1			U(0)
@@ -230,6 +236,7 @@
 size_t mmc_rpmb_read_blocks(int lba, uintptr_t buf, size_t size);
 size_t mmc_rpmb_write_blocks(int lba, const uintptr_t buf, size_t size);
 size_t mmc_rpmb_erase_blocks(int lba, size_t size);
+size_t mmc_boot_part_read_blocks(int lba, uintptr_t buf, size_t size);
 int mmc_init(const struct mmc_ops *ops_ptr, unsigned int clk,
 	     unsigned int width, unsigned int flags,
 	     struct mmc_device_info *device_info);
diff --git a/include/drivers/nand.h b/include/drivers/nand.h
index 1dbb008..1b78ad4 100644
--- a/include/drivers/nand.h
+++ b/include/drivers/nand.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -46,6 +46,16 @@
 	      size_t *length_read);
 
 /*
+ * Look for an extra offset to be added in case of bad blocks
+ *
+ * @base: Base address of the area
+ * @offset: Byte offset to read from in device
+ * @extra_offset: [out] Extra offset to be added if bad blocks are found
+ * Return: 0 on success, a negative errno on failure
+ */
+int nand_seek_bb(uintptr_t base, unsigned int offset, size_t *extra_offset);
+
+/*
  * Get NAND device instance
  *
  * Return: NAND device instance reference
diff --git a/include/drivers/nxp/auth/csf_hdr_parser/csf_hdr.h b/include/drivers/nxp/auth/csf_hdr_parser/csf_hdr.h
new file mode 100644
index 0000000..ae56d3b
--- /dev/null
+++ b/include/drivers/nxp/auth/csf_hdr_parser/csf_hdr.h
@@ -0,0 +1,155 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef CSF_HDR_H
+#define CSF_HDR_H
+
+#include "caam.h"
+#include "hash.h"
+#include "rsa.h"
+
+/* Barker code size in bytes */
+#define CSF_BARKER_LEN	4	/* barker code length in ESBC uboot client */
+				/* header */
+
+#ifdef CSF_HDR_CH3
+struct csf_hdr {
+	uint8_t barker[CSF_BARKER_LEN];	/* 0x00 Barker code */
+	uint32_t srk_tbl_off;		/* 0x04 SRK Table Offset */
+
+	struct {
+		uint8_t num_srk;	/* 0x08 No. of keys */
+		uint8_t srk_sel;	/*  Key no. to be used */
+		uint8_t reserve;	/* 0x0a rseerved */
+	} len_kr;
+	uint8_t ie_flag;
+
+	uint32_t uid_flag;
+
+	uint32_t psign;			/* 0x10 signature offset */
+	uint32_t sign_len;			/* 0x14 length of signature */
+
+	union {
+		struct {
+			uint32_t sg_table_offset; /* 0x18 SG Table Offset */
+			uint32_t sg_entries;	  /* 0x1c no of entries in SG */
+		} sg_isbc;
+		uint64_t img_addr;	/* 64 bit pointer to ESBC Image */
+	};
+
+	union {
+		struct {
+			uint32_t img_size;   /* ESBC client img size in bytes */
+			uint32_t ie_key_sel;
+		} img;
+		uint64_t entry_point;	  /* 0x20-0x24 ESBC entry point */
+	};
+
+	uint32_t fsl_uid_0;			/* 0x28 Freescale unique id 0 */
+	uint32_t fsl_uid_1;			/* 0x2c Freescale unique id 1 */
+	uint32_t oem_uid_0;			/* 0x30 OEM unique id 0 */
+	uint32_t oem_uid_1;			/* 0x34 OEM unique id 1 */
+	uint32_t oem_uid_2;			/* 0x38 OEM unique id 2 */
+	uint32_t oem_uid_3;			/* 0x3c OEM unique id 3 */
+	uint32_t oem_uid_4;			/* 0x40 OEM unique id 4 */
+
+	uint32_t reserved[3];		/* 0x44 - 0x4f */
+};
+
+/* Srk table and key revocation check */
+#define UNREVOCABLE_KEY	8
+#define REVOC_KEY_ALIGN 7
+#define MAX_KEY_ENTRIES 8
+
+#else
+
+/* CSF header for Chassis 2 */
+struct csf_hdr {
+	uint8_t barker[CSF_BARKER_LEN];	/* barker code */
+	union {
+		uint32_t pkey;		/* public key offset */
+		uint32_t srk_tbl_off;
+	};
+
+	union {
+		uint32_t key_len;		/* pub key length in bytes */
+		struct {
+			uint32_t srk_table_flag:8;
+			uint32_t srk_sel:8;
+			uint32_t num_srk:16;
+		} len_kr;
+	};
+
+	uint32_t psign;		/* signature offset */
+	uint32_t sign_len;		/* length of the signature in bytes */
+
+	/* SG Table used by ISBC header */
+	union {
+		struct {
+			uint32_t sg_table_offset; /* 0x14 SG Table Offset */
+			uint32_t sg_entries;	/* no of entries in SG table */
+		} sg_isbc;
+		struct {
+			uint32_t reserved1;	/* Reserved field */
+			uint32_t img_size;	/* ESBC img size in bytes */
+		} img;
+	};
+
+	uint32_t entry_point;		/* ESBC client entry point */
+	uint32_t reserved2;		/* Scatter gather flag */
+	uint32_t uid_flag;
+	uint32_t fsl_uid_0;
+	uint32_t oem_uid_0;
+	uint32_t reserved3[2];
+	uint32_t fsl_uid_1;
+	uint32_t oem_uid_1;
+
+	/* The entries below aren't present in ISBC header */
+	uint64_t img_addr;	/* 64 bit pointer to ESBC Image */
+	uint32_t ie_flag;
+	uint32_t ie_key_sel;
+};
+
+/* Srk table and key revocation check */
+#define UNREVOCABLE_KEY	4
+#define REVOC_KEY_ALIGN 3
+#define MAX_KEY_ENTRIES 4
+
+#endif
+
+struct srk_table {
+	uint32_t key_len;
+	uint8_t pkey[2 * RSA_4K_KEY_SZ_BYTES];
+};
+
+/*
+ * This struct contains the following fields
+ * length of the segment
+ * Destination Target ID
+ * source address
+ * destination address
+ */
+struct sg_table {
+	uint32_t len;			/* Length of Image */
+	uint32_t res1;
+	union {
+		uint64_t src_addr;	/* SRC Address of Image */
+		struct {
+			uint32_t src_addr;
+			uint32_t dst_addr;
+		} img;
+	};
+};
+
+int validate_esbc_header(void *img_hdr, void **img_key, uint32_t *key_len,
+			 void **img_sign, uint32_t *sign_len,
+			 enum sig_alg *algo);
+
+int calc_img_hash(struct csf_hdr *hdr, void *img_addr, uint32_t img_size,
+		  uint8_t *img_hash, uint32_t *hash_len);
+
+#endif
diff --git a/include/drivers/nxp/console/plat_console.h b/include/drivers/nxp/console/plat_console.h
new file mode 100644
index 0000000..8b1b23a
--- /dev/null
+++ b/include/drivers/nxp/console/plat_console.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_CONSOLE_H
+#define PLAT_CONSOLE_H
+
+#include <stdint.h>
+#include <drivers/console.h>
+
+#if (NXP_CONSOLE == NS16550)
+/*
+ * NXP specific UART - 16550 configuration
+ *
+ * Initialize a NXP 16550 console instance and register it with the console
+ * framework. The |console| pointer must point to storage that will be valid
+ * for the lifetime of the console, such as a global or static local variable.
+ * Its contents will be reinitialized from scratch.
+ * When |clock| has a value of 0, the UART will *not* be initialised. This
+ * means the UART should already be enabled and the baudrate and clock setup
+ * should have been done already, either by platform specific code or by
+ * previous firmware stages. The |baud| parameter will be ignored in this
+ * case as well.
+ */
+int nxp_console_16550_register(uintptr_t baseaddr, uint32_t clock,
+			       uint32_t baud, console_t *console);
+#endif
+/*
+ * Function to initialize platform's console
+ * and register with console framework
+ */
+void plat_console_init(uintptr_t nxp_console_addr, uint32_t uart_clk_div,
+			uint32_t baud);
+
+#endif
diff --git a/include/drivers/nxp/crypto/caam/caam.h b/include/drivers/nxp/crypto/caam/caam.h
new file mode 100644
index 0000000..4984b54
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/caam.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef CAAM_H
+#define CAAM_H
+
+#include "caam_io.h"
+#include "sec_jr_driver.h"
+
+
+/* Job ring 3 is reserved for usage by sec firmware */
+#define DEFAULT_JR	3
+
+#if defined(CONFIG_CHASSIS_3_2) || defined(CONFIG_CHASSIS_2)
+#define CAAM_JR0_OFFSET			0x10000
+#define CAAM_JR1_OFFSET			0x20000
+#define CAAM_JR2_OFFSET			0x30000
+#define CAAM_JR3_OFFSET			0x40000
+#endif
+
+enum sig_alg {
+	RSA,
+	ECC
+};
+
+/* This function does basic SEC Initialization */
+int sec_init(uintptr_t nxp_caam_addr);
+int config_sec_block(void);
+uintptr_t get_caam_addr(void);
+
+/* This function is used to submit jobs to JR */
+int run_descriptor_jr(struct job_descriptor *desc);
+
+/* This function is used to instatiate the HW RNG is already not instantiated */
+int hw_rng_instantiate(void);
+
+/* This function is used to return random bytes of byte_len from HW RNG */
+int get_rand_bytes_hw(uint8_t *bytes, int byte_len);
+
+/* This function is used to set the hw unique key from HW CAAM */
+int get_hw_unq_key_blob_hw(uint8_t *hw_key, int size);
+
+/* This function is used to fetch random number from
+ * CAAM of length either of 4 bytes or 8 bytes depending
+ * rngWidth value.
+ */
+unsigned long long get_random(int rngWidth);
+
+#endif /* CAAM_H */
diff --git a/include/drivers/nxp/crypto/caam/caam_io.h b/include/drivers/nxp/crypto/caam/caam_io.h
new file mode 100644
index 0000000..b68f836
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/caam_io.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef CAAM_IO_H
+#define CAAM_IO_H
+
+#include <endian.h>
+#include <lib/mmio.h>
+
+typedef unsigned long long phys_addr_t;
+typedef unsigned long long phys_size_t;
+
+/* Return higher 32 bits of physical address */
+#define PHYS_ADDR_HI(phys_addr) \
+	    (uint32_t)(((uint64_t)phys_addr) >> 32)
+
+/* Return lower 32 bits of physical address */
+#define PHYS_ADDR_LO(phys_addr) \
+	    (uint32_t)(((uint64_t)phys_addr) & 0xFFFFFFFF)
+
+#ifdef NXP_SEC_BE
+#define sec_in32(a)	bswap32(mmio_read_32((uintptr_t)(a)))
+#define sec_out32(a, v)	mmio_write_32((uintptr_t)(a), bswap32(v))
+#define sec_in64(addr)  (					\
+	((uint64_t)sec_in32((uintptr_t)(addr)) << 32) |	\
+	(sec_in32(((uintptr_t)(addr)) + 4)))
+#define sec_out64(addr, val) ({					\
+	sec_out32(((uintptr_t)(addr)), (uint32_t)((val) >> 32));	\
+	sec_out32(((uintptr_t)(addr)) + 4, (uint32_t)(val)); })
+#elif defined(NXP_SEC_LE)
+#define sec_in32(a)	mmio_read_32((uintptr_t)(a))
+#define sec_out32(a, v)	mmio_write_32((uintptr_t)(a), (v))
+#define sec_in64(addr)	(					\
+	((uint64_t)sec_in32((uintptr_t)(addr) + 4) << 32) |	\
+	(sec_in32((uintptr_t)(addr))))
+#define sec_out64(addr, val) ({						\
+	sec_out32(((uintptr_t)(addr)) + 4, (uint32_t)((val) >> 32));	\
+	sec_out32(((uintptr_t)(addr)), (uint32_t)(val)); })
+#else
+#error Please define CCSR SEC register endianness
+#endif
+
+static inline void *ptov(phys_addr_t *ptr)
+{
+	return (void *)ptr;
+}
+
+static inline phys_addr_t *vtop(void *ptr)
+{
+	return (phys_addr_t *)ptr;
+}
+#endif /* CAAM_IO_H */
diff --git a/include/drivers/nxp/crypto/caam/hash.h b/include/drivers/nxp/crypto/caam/hash.h
new file mode 100644
index 0000000..9136dca
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/hash.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef __HASH_H__
+#define __HASH_H__
+
+#include <stdbool.h>
+
+/* List of hash algorithms */
+enum hash_algo {
+	SHA1 = 0,
+	SHA256
+};
+
+/* number of bytes in the SHA256-256 digest */
+#define SHA256_DIGEST_SIZE 32
+
+/*
+ * number of words in the digest - Digest is kept internally
+ * as 8 32-bit words
+ */
+#define _SHA256_DIGEST_LENGTH 8
+
+/*
+ * block length - A block, treated as a sequence of
+ * 32-bit words
+ */
+#define SHA256_BLOCK_LENGTH 16
+
+/* number of bytes in the block */
+#define SHA256_DATA_SIZE 64
+
+#define MAX_SG		12
+
+struct sg_entry {
+#if defined(NXP_SEC_LE)
+	uint32_t addr_lo;	/* Memory Address - lo */
+	uint32_t addr_hi;	/* Memory Address of start of buffer - hi */
+#else
+	uint32_t addr_hi;	/* Memory Address of start of buffer - hi */
+	uint32_t addr_lo;	/* Memory Address - lo */
+#endif
+
+	uint32_t len_flag;	/* Length of the data in the frame */
+#define SG_ENTRY_LENGTH_MASK	0x3FFFFFFF
+#define SG_ENTRY_EXTENSION_BIT	0x80000000
+#define SG_ENTRY_FINAL_BIT	0x40000000
+	uint32_t bpid_offset;
+#define SG_ENTRY_BPID_MASK	0x00FF0000
+#define SG_ENTRY_BPID_SHIFT	16
+#define SG_ENTRY_OFFSET_MASK	0x00001FFF
+#define SG_ENTRY_OFFSET_SHIFT	0
+};
+
+/*
+ * SHA256-256 context
+ * contain the following fields
+ * State
+ * count low
+ * count high
+ * block data buffer
+ * index to the buffer
+ */
+struct hash_ctx {
+	struct sg_entry sg_tbl[MAX_SG];
+	uint32_t hash_desc[64];
+	uint8_t hash[SHA256_DIGEST_SIZE];
+	uint32_t sg_num;
+	uint32_t len;
+	uint8_t *data;
+	enum hash_algo algo;
+	bool active;
+};
+
+int hash_init(enum hash_algo algo, void **ctx);
+int hash_update(enum hash_algo algo, void *context, void *data_ptr,
+		unsigned int data_len);
+int hash_final(enum hash_algo algo, void *context, void *hash_ptr,
+	       unsigned int hash_len);
+
+#endif
diff --git a/include/drivers/nxp/crypto/caam/jobdesc.h b/include/drivers/nxp/crypto/caam/jobdesc.h
new file mode 100644
index 0000000..efef228
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/jobdesc.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef __JOBDESC_H
+#define __JOBDESC_H
+
+#include <rsa.h>
+
+#define DESC_LEN_MASK		0x7f
+#define DESC_START_SHIFT	16
+
+#define KEY_BLOB_SIZE 32
+#define MAC_SIZE 16
+
+#define KEY_IDNFR_SZ_BYTES 16
+#define CLASS_SHIFT 25
+#define CLASS_2	(0x02 << CLASS_SHIFT)
+
+#define CMD_SHIFT		27
+#define CMD_OPERATION		(U(0x10) << CMD_SHIFT)
+
+#define OP_TYPE_SHIFT		24
+#define OP_TYPE_ENCAP_PROTOCOL	(0x07 << OP_TYPE_SHIFT)
+
+/* Assuming OP_TYPE = OP_TYPE_UNI_PROTOCOL */
+#define OP_PCLID_SHIFT		16
+#define OP_PCLID_BLOB		(0x0d << OP_PCLID_SHIFT)
+
+#define BLOB_PROTO_INFO		 0x00000002
+
+uint32_t desc_length(uint32_t *desc);
+
+int cnstr_rng_jobdesc(uint32_t *desc, uint32_t state_handle,
+		      uint32_t *add_inp, uint32_t add_ip_len,
+		      uint8_t *out_data, uint32_t len);
+
+int cnstr_rng_instantiate_jobdesc(uint32_t *desc);
+
+/* Construct descriptor to generate hw key blob */
+int cnstr_hw_encap_blob_jobdesc(uint32_t *desc,
+				uint8_t *key_idnfr, uint32_t key_sz,
+				uint32_t key_class, uint8_t *plain_txt,
+				uint32_t in_sz, uint8_t *enc_blob,
+				uint32_t out_sz, uint32_t operation);
+
+void cnstr_hash_jobdesc(uint32_t *desc, uint8_t *msg, uint32_t msgsz,
+			uint8_t *digest);
+
+void cnstr_jobdesc_pkha_rsaexp(uint32_t *desc,
+			       struct pk_in_params *pkin, uint8_t *out,
+			       uint32_t out_siz);
+#endif
diff --git a/include/drivers/nxp/crypto/caam/jr_driver_config.h b/include/drivers/nxp/crypto/caam/jr_driver_config.h
new file mode 100644
index 0000000..1b3c447
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/jr_driver_config.h
@@ -0,0 +1,205 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _JR_DRIVER_CONFIG_H_
+#define _JR_DRIVER_CONFIG_H_
+
+/* Helper defines  */
+
+ /* Define used for setting a flag on  */
+#define  ON  1
+ /* Define used for setting a flag off  */
+#define  OFF 0
+
+ /* SEC is configured to start work in polling mode,  */
+#define SEC_STARTUP_POLLING_MODE     0
+/*
+ * SEC is configured to start work in interrupt mode,
+ *  when configured for NAPI notification style.
+ */
+#define SEC_STARTUP_INTERRUPT_MODE   1
+
+/*
+ * SEC driver will use ONLY interrupts to receive notifications
+ * for processed packets from SEC engine hardware.
+ */
+#define SEC_NOTIFICATION_TYPE_IRQ   1
+/*
+ * SEC driver will use ONLY polling to receive notifications
+ * for processed packets from SEC engine hardware.
+ */
+#define SEC_NOTIFICATION_TYPE_POLL  2
+
+/*
+ * Determines how SEC user space driver will receive notifications
+ * for processed packets from SEC engine.
+ * Valid values are: #SEC_NOTIFICATION_TYPE_POLL, #SEC_NOTIFICATION_TYPE_IRQ
+ */
+#define SEC_NOTIFICATION_TYPE   SEC_NOTIFICATION_TYPE_POLL
+
+ /* Maximum number of job rings supported by SEC hardware  */
+#define MAX_SEC_JOB_RINGS         1
+
+/*
+ * Size of cryptographic context that is used directly in communicating
+ *  with SEC device.
+ *  SEC device works only with physical addresses. This is the maximum size
+ *  for a SEC descriptor ( = 64 words).
+ */
+
+#define SEC_CRYPTO_DESCRIPTOR_SIZE  256
+
+/*
+ * Size of job descriptor submitted to SEC device for each packet to be
+ *  processed.
+ *  Job descriptor contains 3 DMA address pointers:
+ *      - to shared descriptor, to input buffer and to output buffer.
+ *  The job descriptor contains other SEC specific commands as well:
+ *      - HEADER command, SEQ IN PTR command SEQ OUT PTR command and opaque
+ *        data, each measuring 4 bytes.
+ *  Job descriptor size, depending on physical address representation:
+ *      - 32 bit - size is 28 bytes - cacheline-aligned size is 64 bytes
+ *      - 36 bit - size is 40 bytes - cacheline-aligned size is 64 bytes
+ *  @note: Job descriptor must be cacheline-aligned to ensure efficient memory
+ *  access.
+ *  @note: If other format is used for job descriptor, then the size must be
+ *  revised.
+ */
+
+#define SEC_JOB_DESCRIPTOR_SIZE		64
+
+/*
+ * Size of one entry in the input ring of a job ring.
+ *  Input ring contains pointers to job descriptors.
+ *  The memory used for an input ring and output ring must be physically
+ *  contiguous.
+ */
+
+#define SEC_JOB_INPUT_RING_ENTRY_SIZE	sizeof(phys_addr_t)
+
+/*
+ * Size of one entry in the output ring of a job ring.
+ *  Output ring entry is a pointer to a job descriptor followed by a 4 byte
+ *  status word.
+ *  The memory used for an input ring and output ring must be physically
+ *  contiguous.
+ *  @note If desired to use also the optional SEQ OUT indication in output
+ *  ring entries, then 4 more bytes must be added to the size.
+ */
+
+#define SEC_JOB_OUTPUT_RING_ENTRY_SIZE	(SEC_JOB_INPUT_RING_ENTRY_SIZE + 4)
+
+ /* DMA memory required for an input ring of a job ring.  */
+#define SEC_DMA_MEM_INPUT_RING_SIZE	\
+		((SEC_JOB_INPUT_RING_ENTRY_SIZE) * (SEC_JOB_RING_SIZE))
+
+/*
+ * DMA memory required for an output ring of a job ring.
+ *  Required extra 4 byte for status word per each entry.
+ */
+#define SEC_DMA_MEM_OUTPUT_RING_SIZE	\
+		((SEC_JOB_OUTPUT_RING_ENTRY_SIZE) * (SEC_JOB_RING_SIZE))
+
+ /* DMA memory required for descriptors of a job ring.  */
+#define SEC_DMA_MEM_DESCRIPTORS		\
+		((SEC_CRYPTO_DESCRIPTOR_SIZE)*(SEC_JOB_RING_SIZE))
+
+ /* DMA memory required for a job ring, including both input output rings.  */
+#define SEC_DMA_MEM_JOB_RING_SIZE	\
+		((SEC_DMA_MEM_INPUT_RING_SIZE) +	\
+		(SEC_DMA_MEM_OUTPUT_RING_SIZE))
+
+/*
+ * When calling sec_init() UA will provide an area of virtual memory
+ *  of size #SEC_DMA_MEMORY_SIZE to be  used internally by the driver
+ *  to allocate data (like SEC descriptors) that needs to be passed to
+ *  SEC device in physical addressing and later on retrieved from SEC device.
+ *  At initialization the UA provides specialized ptov/vtop functions/macros to
+ *  translate addresses allocated from this memory area.
+ */
+#define SEC_DMA_MEMORY_SIZE		\
+		((SEC_DMA_MEM_JOB_RING_SIZE) * (MAX_SEC_JOB_RINGS))
+
+/*
+ * SEC DEVICE related configuration.
+
+ * Enable/Disable logging support at compile time.
+ * Valid values:
+ * ON - enable logging
+ * OFF - disable logging
+ * The messages are logged at stdout.
+ */
+
+#define SEC_DRIVER_LOGGING OFF
+
+/*
+ * Configure logging level at compile time.
+ * Valid values:
+ * SEC_DRIVER_LOG_ERROR - log only errors
+ * SEC_DRIVER_LOG_INFO  - log errors and info messages
+ * SEC_DRIVER_LOG_DEBUG - log errors, info and debug messages
+ */
+
+#define SEC_DRIVER_LOGGING_LEVEL SEC_DRIVER_LOG_DEBUG
+
+/*
+ * SEC JOB RING related configuration.
+
+ * Configure the size of the JOB RING.
+ * The maximum size of the ring is hardware limited to 1024.
+ * However the number of packets in flight in a time interval of
+ * 1ms can be calculated
+ * from the traffic rate (Mbps) and packet size.
+ * Here it was considered a packet size of 40 bytes.
+ * @note Round up to nearest power of 2 for optimized update
+ * of producer/consumer indexes of each job ring
+ * \todo Should set to 750, according to the calculation above, but
+ * the JR size must be power of 2, thus the next closest value must
+ * be chosen (i.e. 512 since 1024 is not available)
+ * For firmware choose this to be 16
+ */
+
+#define SEC_JOB_RING_SIZE    16
+
+/*
+ * Interrupt coalescing related configuration.
+ * NOTE: SEC hardware enabled interrupt
+ * coalescing is not supported on SEC version 3.1!
+ * SEC version 4.4 has support for interrupt
+ * coalescing.
+ */
+
+#if SEC_NOTIFICATION_TYPE != SEC_NOTIFICATION_TYPE_POLL
+
+#define SEC_INT_COALESCING_ENABLE   ON
+/*
+ * Interrupt Coalescing Descriptor Count Threshold.
+ * While interrupt coalescing is enabled (ICEN=1), this value determines
+ * how many Descriptors are completed before raising an interrupt.
+ * Valid values for this field are from 0 to 255.
+ * Note that a value of 1 functionally defeats the advantages of interrupt
+ * coalescing since the threshold value is reached each time that a
+ * Job Descriptor is completed. A value of 0 is treated in the same
+ * manner as a value of 1.
+ *
+ */
+#define SEC_INTERRUPT_COALESCING_DESCRIPTOR_COUNT_THRESH  10
+
+/*
+ * Interrupt Coalescing Timer Threshold.
+ * While interrupt coalescing is enabled (ICEN=1), this value determines the
+ * maximum amount of time after processing a Descriptor before raising an
+ * interrupt.
+ * The threshold value is represented in units equal to 64 CAAM interface
+ * clocks. Valid values for this field are from 1 to 65535.
+ * A value of 0 results in behavior identical to that when interrupt
+ * coalescing is disabled.
+ */
+#define SEC_INTERRUPT_COALESCING_TIMER_THRESH  100
+#endif /* SEC_NOTIFICATION_TYPE_POLL  */
+
+#endif /* _JR_DRIVER_CONFIG_H_  */
diff --git a/include/drivers/nxp/crypto/caam/rsa.h b/include/drivers/nxp/crypto/caam/rsa.h
new file mode 100644
index 0000000..dd9ecdc
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/rsa.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _RSA_H__
+#define _RSA_H__
+
+/* RSA key size defines */
+#define RSA_4K_KEY_SZ       4096
+#define RSA_4K_KEY_SZ_BYTES (RSA_4K_KEY_SZ/8)
+#define RSA_2K_KEY_SZ       2048
+#define RSA_2K_KEY_SZ_BYTES (RSA_2K_KEY_SZ/8)
+#define RSA_1K_KEY_SZ       1024
+#define RSA_1K_KEY_SZ_BYTES (RSA_1K_KEY_SZ/8)
+
+#define SHA256_BYTES        (256/8)
+
+struct pk_in_params {
+	uint8_t *e;
+	uint32_t e_siz;
+	uint8_t *n;
+	uint32_t n_siz;
+	uint8_t *a;
+	uint32_t a_siz;
+	uint8_t *b;
+	uint32_t b_siz;
+};
+
+struct rsa_context {
+	struct pk_in_params pkin;
+};
+
+int rsa_verify_signature(void *hash_ptr, unsigned int hash_len,
+			 void *sig_ptr, unsigned int sig_len,
+			 void *pk_ptr, unsigned int pk_len);
+
+#endif
diff --git a/include/drivers/nxp/crypto/caam/sec_hw_specific.h b/include/drivers/nxp/crypto/caam/sec_hw_specific.h
new file mode 100644
index 0000000..a4fc022
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/sec_hw_specific.h
@@ -0,0 +1,506 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _SEC_HW_SPECIFIC_H_
+#define _SEC_HW_SPECIFIC_H_
+
+#include "caam.h"
+#include "sec_jr_driver.h"
+
+ /* DEFINES AND MACROS */
+
+/* Used to retry resetting a job ring in SEC hardware. */
+#define SEC_TIMEOUT 100000
+
+/*
+ * Offset to the registers of a job ring.
+ *Is different for each job ring.
+ */
+#define CHAN_BASE(jr)   ((phys_addr_t)(jr)->register_base_addr)
+
+#define unlikely(x)	 __builtin_expect(!!(x), 0)
+
+#define SEC_JOB_RING_IS_FULL(pi, ci, ring_max_size, ring_threshold)    \
+	((((pi) + 1 + ((ring_max_size) - (ring_threshold))) &	\
+	  (ring_max_size - 1))  == ((ci)))
+
+#define SEC_CIRCULAR_COUNTER(x, max)   (((x) + 1) & (max - 1))
+
+ /* Struct representing various job ring registers */
+struct jobring_regs {
+#ifdef NXP_SEC_BE
+	unsigned int irba_h;
+	unsigned int irba_l;
+#else
+	unsigned int irba_l;
+	unsigned int irba_h;
+#endif
+	unsigned int rsvd1;
+	unsigned int irs;
+	unsigned int rsvd2;
+	unsigned int irsa;
+	unsigned int rsvd3;
+	unsigned int irja;
+#ifdef NXP_SEC_BE
+	unsigned int orba_h;
+	unsigned int orba_l;
+#else
+	unsigned int orba_l;
+	unsigned int orba_h;
+#endif
+	unsigned int rsvd4;
+	unsigned int ors;
+	unsigned int rsvd5;
+	unsigned int orjr;
+	unsigned int rsvd6;
+	unsigned int orsf;
+	unsigned int rsvd7;
+	unsigned int jrsta;
+	unsigned int rsvd8;
+	unsigned int jrint;
+	unsigned int jrcfg0;
+	unsigned int jrcfg1;
+	unsigned int rsvd9;
+	unsigned int irri;
+	unsigned int rsvd10;
+	unsigned int orwi;
+	unsigned int rsvd11;
+	unsigned int jrcr;
+};
+
+ /* Offsets representing common SEC Registers */
+#define SEC_REG_MCFGR_OFFSET		0x0004
+#define SEC_REG_SCFGR_OFFSET		0x000C
+#define SEC_REG_JR0ICIDR_MS_OFFSET	0x0010
+#define SEC_REG_JR0ICIDR_LS_OFFSET	0x0014
+#define SEC_REG_JR1ICIDR_MS_OFFSET	0x0018
+#define SEC_REG_JR1ICIDR_LS_OFFSET	0x001C
+#define SEC_REG_JR2ICIDR_MS_OFFSET	0x0020
+#define SEC_REG_JR2ICIDR_LS_OFFSET	0x0024
+#define SEC_REG_JR3ICIDR_MS_OFFSET	0x0028
+#define SEC_REG_JR3ICIDR_LS_OFFSET	0x002C
+#define SEC_REG_JRSTARTR_OFFSET		0x005C
+#define SEC_REG_CTPR_MS_OFFSET		0x0FA8
+
+ /* Offsets  representing various RNG registers */
+#define RNG_REG_RTMCTL_OFFSET		0x0600
+#define RNG_REG_RTSDCTL_OFFSET		0x0610
+#define RNG_REG_RTFRQMIN_OFFSET		0x0618
+#define RNG_REG_RTFRQMAX_OFFSET		0x061C
+#define RNG_REG_RDSTA_OFFSET		0x06C0
+#define ALG_AAI_SH_SHIFT		4
+
+ /* SEC Registers Bitmasks */
+#define	MCFGR_PS_SHIFT			16
+#define	MCFGR_AWCACHE_SHIFT			 8
+#define	MCFGR_AWCACHE_MASK	(0xF << MCFGR_AWCACHE_SHIFT)
+#define	MCFGR_ARCACHE_SHIFT			12
+#define	MCFGR_ARCACHE_MASK	(0xF << MCFGR_ARCACHE_SHIFT)
+
+#define SCFGR_RNGSH0		0x00000200
+#define	SCFGR_VIRT_EN		0x00008000
+
+#define JRICID_MS_LICID		0x80000000
+#define JRICID_MS_LAMTD		0x00020000
+#define JRICID_MS_AMTDT		0x00010000
+#define JRICID_MS_TZ		0x00008000
+#define JRICID_LS_SDID_MASK	0x00000FFF
+#define JRICID_LS_NSEQID_MASK	0x0FFF0000
+#define JRICID_LS_NSEQID_SHIFT		16
+#define JRICID_LS_SEQID_MASK	0x00000FFF
+
+#define JRSTARTR_STARTJR0	0x00000001
+#define JRSTARTR_STARTJR1	0x00000002
+#define JRSTARTR_STARTJR2	0x00000004
+#define JRSTARTR_STARTJR3	0x00000008
+
+#define CTPR_VIRT_EN_POR	0x00000002
+#define CTPR_VIRT_EN_INC	0x00000001
+
+ /* RNG RDSTA bitmask */
+#define RNG_STATE0_HANDLE_INSTANTIATED	0x00000001
+#define RTMCTL_PRGM 0x00010000	/* 1 -> program mode, 0 -> run mode */
+ /* use von Neumann data in both entropy shifter and statistical checker */
+#define RTMCTL_SAMP_MODE_VON_NEUMANN_ES_SC	 0
+ /* use raw data in both entropy shifter and statistical checker */
+#define RTMCTL_SAMP_MODE_RAW_ES_SC			 1
+ /* use von Neumann data in entropy shifter, raw data in statistical checker */
+#define RTMCTL_SAMP_MODE_VON_NEUMANN_ES_RAW_SC 2
+ /* invalid combination */
+#define RTMCTL_SAMP_MODE_INVALID			   3
+#define RTSDCTL_ENT_DLY_MIN	3200
+#define RTSDCTL_ENT_DLY_MAX	12800
+#define RTSDCTL_ENT_DLY_SHIFT	16
+#define RTSDCTL_ENT_DLY_MASK	(U(0xffff) << RTSDCTL_ENT_DLY_SHIFT)
+#define RTFRQMAX_DISABLE	   (1 << 20)
+
+ /* Constants for error handling on job ring */
+#define JR_REG_JRINT_ERR_TYPE_SHIFT	8
+#define JR_REG_JRINT_ERR_ORWI_SHIFT	16
+#define JR_REG_JRINIT_JRE_SHIFT			1
+
+#define JRINT_JRE			(1 << JR_REG_JRINIT_JRE_SHIFT)
+#define JRINT_ERR_WRITE_STATUS		(1 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_BAD_INPUT_BASE	(3 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_BAD_OUTPUT_BASE	(4 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_WRITE_2_IRBA		(5 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_WRITE_2_ORBA		(6 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_RES_B4_HALT		(7 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_REM_TOO_MANY		(8 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_ADD_TOO_MANY		(9 << JR_REG_JRINT_ERR_TYPE_SHIFT)
+#define JRINT_ERR_HALT_MASK		0x0C
+#define JRINT_ERR_HALT_INPROGRESS	0x04
+#define JRINT_ERR_HALT_COMPLETE		0x08
+
+#define JR_REG_JRCR_VAL_RESET		0x00000001
+
+#define JR_REG_JRCFG_LO_ICTT_SHIFT	0x10
+#define JR_REG_JRCFG_LO_ICDCT_SHIFT	0x08
+#define JR_REG_JRCFG_LO_ICEN_EN		0x02
+#define JR_REG_JRCFG_LO_IMSK_EN		0x01
+
+ /* Constants for Descriptor Processing errors */
+#define SEC_HW_ERR_SSRC_NO_SRC			0x00
+#define SEC_HW_ERR_SSRC_CCB_ERR			0x02
+#define SEC_HW_ERR_SSRC_JMP_HALT_U	0x03
+#define SEC_HW_ERR_SSRC_DECO		0x04
+#define SEC_HW_ERR_SSRC_JR		0x06
+#define SEC_HW_ERR_SSRC_JMP_HALT_COND   0x07
+
+#define SEC_HW_ERR_DECO_HFN_THRESHOLD   0xF1
+#define SEC_HW_ERR_CCB_ICV_CHECK_FAIL   0x0A
+
+ /* Macros for extracting error codes for the job ring */
+
+#define JR_REG_JRINT_ERR_TYPE_EXTRACT(value)			\
+				((value) & 0x00000F00)
+
+#define JR_REG_JRINT_ERR_ORWI_EXTRACT(value)			\
+				(((value) & 0x3FFF0000) >>	\
+				 JR_REG_JRINT_ERR_ORWI_SHIFT)
+
+#define JR_REG_JRINT_JRE_EXTRACT(value)				\
+				((value) & JRINT_JRE)
+
+ /* Macros for manipulating JR registers */
+typedef union {
+	uint64_t m_whole;
+	struct {
+#ifdef NXP_SEC_BE
+		uint32_t high;
+		uint32_t low;
+#else
+		uint32_t low;
+		uint32_t high;
+#endif
+	} m_halves;
+} ptr_addr_t;
+
+#if defined(CONFIG_PHYS_64BIT)
+#define sec_read_addr(a)		sec_in64((a))
+#define sec_write_addr(a, v)	sec_out64((a), (v))
+#else
+#define sec_read_addr(a)		sec_in32((a))
+#define sec_write_addr(a, v)		sec_out32((a), (v))
+#endif
+
+#define JR_REG(name, jr)	(CHAN_BASE(jr) + JR_REG_##name##_OFFSET)
+#define JR_REG_LO(name, jr)	(CHAN_BASE(jr) + JR_REG_##name##_OFFSET_LO)
+
+#define GET_JR_REG(name, jr)	(sec_in32(JR_REG(name, (jr))))
+#define GET_JR_REG_LO(name, jr)	(sec_in32(JR_REG_LO(name, (jr))))
+
+#define SET_JR_REG(name, jr, val)		\
+		(sec_out32(JR_REG(name, (jr)), (val)))
+
+#define SET_JR_REG_LO(name, jr, val)	\
+		(sec_out32(JR_REG_LO(name, (jr)), (val)))
+
+ /* STRUCTURES AND OTHER TYPEDEFS */
+ /*  Lists the possible states for a job ring. */
+typedef enum sec_job_ring_state_e {
+	SEC_JOB_RING_STATE_STARTED,	/* Job ring is initialized */
+	SEC_JOB_RING_STATE_RESET,	/* Job ring reset is in progres */
+} sec_job_ring_state_t;
+
+struct sec_job_ring_t {
+	/*
+	 * Consumer index for job ring (jobs array).
+	 * @note: cidx and pidx are accessed from
+	 * different threads.
+	 * Place the cidx and pidx inside the structure
+	 *  so that they lay on different cachelines, to
+	 * avoid false sharing between threads when the
+	 * threads run on different cores!
+	 */
+	uint32_t cidx;
+
+	/* Producer index for job ring (jobs array) */
+	uint32_t pidx;
+
+	/*  Ring of input descriptors. Size of array is power of 2 to allow
+	 * fast update of producer/consumer indexes with  bitwise operations.
+	 */
+	phys_addr_t *input_ring;
+
+	/*  Ring of output descriptors. */
+	struct sec_outring_entry *output_ring;
+
+	/* The file descriptor used for polling for interrupts notifications */
+	uint32_t irq_fd;
+
+	/* Model used by SEC Driver to receive  notifications from SEC.
+	 *  Can be either of the three:
+	 * #SEC_NOTIFICATION_TYPE_IRQ or
+	 * #SEC_NOTIFICATION_TYPE_POLL
+	 */
+	uint32_t jr_mode;
+	/* Base address for SEC's register memory for this job ring. */
+	void *register_base_addr;
+	/* notifies if coelescing is enabled for the job ring */
+	uint8_t coalescing_en;
+	/* The state of this job ring */
+	sec_job_ring_state_t jr_state;
+};
+
+ /* Forward structure declaration */
+typedef struct sec_job_ring_t sec_job_ring_t;
+
+struct sec_outring_entry {
+	phys_addr_t desc;	/* Pointer to completed descriptor */
+	uint32_t status;	/* Status for completed descriptor */
+} __packed;
+
+ /* Lists the states possible for the SEC user space driver. */
+typedef enum sec_driver_state_e {
+	SEC_DRIVER_STATE_IDLE,	/*< Driver not initialized */
+	SEC_DRIVER_STATE_STARTED,	/*< Driver initialized and */
+	SEC_DRIVER_STATE_RELEASE,	/*< Driver release is in progress */
+} sec_driver_state_t;
+
+ /* Union describing the possible error codes that */
+ /* can be set in the descriptor status word */
+
+union hw_error_code {
+	uint32_t error;
+	union {
+		struct {
+			uint32_t ssrc:4;
+			uint32_t ssed_val:28;
+		} __packed value;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t res:28;
+		} __packed no_status_src;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t jmp:1;
+			uint32_t res:11;
+			uint32_t desc_idx:8;
+			uint32_t cha_id:4;
+			uint32_t err_id:4;
+		} __packed ccb_status_src;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t jmp:1;
+			uint32_t res:11;
+			uint32_t desc_idx:8;
+			uint32_t offset:8;
+		} __packed jmp_halt_user_src;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t jmp:1;
+			uint32_t res:11;
+			uint32_t desc_idx:8;
+			uint32_t desc_err:8;
+		} __packed deco_src;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t res:17;
+			uint32_t naddr:3;
+			uint32_t desc_err:8;
+		} __packed jr_src;
+		struct {
+			uint32_t ssrc:4;
+			uint32_t jmp:1;
+			uint32_t res:11;
+			uint32_t desc_idx:8;
+			uint32_t cond:8;
+		} __packed jmp_halt_cond_src;
+	} __packed error_desc;
+} __packed;
+
+ /* FUNCTION PROTOTYPES */
+
+/*
+ * @brief Initialize a job ring/channel in SEC device.
+ * Write configuration register/s to properly initialize a job ring.
+ *
+ * @param [in] job_ring     The job ring
+ *
+ * @retval 0 for success
+ * @retval other for error
+ */
+int hw_reset_job_ring(sec_job_ring_t *job_ring);
+
+/*
+ * @brief Reset a job ring/channel in SEC device.
+ * Write configuration register/s to reset a job ring.
+ *
+ * @param [in] job_ring     The job ring
+ *
+ * @retval 0 for success
+ * @retval -1 in case job ring reset failed
+ */
+int hw_shutdown_job_ring(sec_job_ring_t *job_ring);
+
+/*
+ * @brief Handle a job ring/channel error in SEC device.
+ * Identify the error type and clear error bits if required.
+ *
+ * @param [in]  job_ring    The job ring
+ * @param [in]  sec_error_code  error code as first read from SEC engine
+ */
+
+void hw_handle_job_ring_error(sec_job_ring_t *job_ring,
+			      uint32_t sec_error_code);
+/*
+ * @brief Handle a job ring error in the device.
+ * Identify the error type and printout a explanatory
+ * messages.
+ *
+ * @param [in]  job_ring    The job ring
+ *
+ */
+
+int hw_job_ring_error(sec_job_ring_t *job_ring);
+
+/* @brief Set interrupt coalescing parameters on the Job Ring.
+ * @param [in]  job_ring       The job ring
+ * @param [in]  irq_coalesing_timer
+ *                             Interrupt coalescing timer threshold.
+ *                     This value determines the maximum
+ *                     amount of time after processing a descriptor
+ *                     before raising an interrupt.
+ * @param [in]  irq_coalescing_count
+ *                             Interrupt coalescing count threshold.
+ *                     This value determines how many descriptors
+ *                     are completed before raising an interrupt.
+ */
+
+int hw_job_ring_set_coalescing_param(sec_job_ring_t *job_ring,
+				     uint16_t irq_coalescing_timer,
+				     uint8_t irq_coalescing_count);
+
+/* @brief Enable interrupt coalescing on a job ring
+ * @param [in]  job_ring       The job ring
+ */
+
+int hw_job_ring_enable_coalescing(sec_job_ring_t *job_ring);
+
+/*
+ * @brief Disable interrupt coalescing on a job ring
+ * @param [in]  job_ring       The job ring
+ */
+
+int hw_job_ring_disable_coalescing(sec_job_ring_t *job_ring);
+
+/*
+ * @brief Poll the HW for already processed jobs in the JR
+ * and notify the available jobs to UA.
+ *
+ * @param [in]  job_ring            The job ring to poll.
+ * @param [in]  limit               The maximum number of jobs to notify.
+ *                                  If set to negative value, all available
+ *                                  jobs are notified.
+ *
+ * @retval >=0 for No of jobs notified to UA.
+ * @retval -1 for error
+ */
+
+int hw_poll_job_ring(struct sec_job_ring_t *job_ring, int32_t limit);
+
+/* @brief Poll the HW for already processed jobs in the JR
+ * and silently discard the available jobs or notify them to UA
+ * with indicated error code.
+
+ * @param [in,out]  job_ring        The job ring to poll.
+ * @param [in]  do_notify           Can be #TRUE or #FALSE.
+ *                                 Indicates if descriptors to be discarded
+ *                                  or notified to UA with given error_code.
+ * @param [in]  error_code          The detailed SEC error code.
+ * @param [out] notified_descs        Number of notified descriptors.
+ *                                 Can be NULL if do_notify is #FALSE
+ */
+void hw_flush_job_ring(struct sec_job_ring_t *job_ring,
+		       uint32_t do_notify,
+		       uint32_t error_code, uint32_t *notified_descs);
+
+/*
+ * @brief Flush job rings of any processed descs.
+ * The processed descs are silently dropped,
+ *  WITHOUT being notified to UA.
+ */
+void flush_job_rings(void);
+
+/*
+ * @brief Handle desc that generated error in SEC engine.
+ * Identify the exact type of error and handle the error.
+ * Depending on the error type, the job ring could be reset.
+ * All descs that are submitted for processing on this job ring
+ * are notified to User Application with error status and detailed error code.
+
+ * @param [in]  job_ring            Job ring
+ * @param [in]  sec_error_code      Error code read from job ring's Channel
+ *                                 Status Register
+ * @param [out] notified_descs      Number of notified descs. Can be NULL if
+ *                                 do_notify is #FALSE
+ * @param [out] do_driver_shutdown  If set to #TRUE, then UA is returned code
+ *                                 #SEC_PROCESSING_ERROR
+ *                                  which is indication that UA must call
+ *                                  sec_release() after this.
+ */
+void sec_handle_desc_error(struct sec_job_ring_t *job_ring,
+			   uint32_t sec_error_code,
+			   uint32_t *notified_descs,
+			   uint32_t *do_driver_shutdown);
+
+/*
+ * @brief Release the software and hardware resources tied to a job ring.
+ * @param [in] job_ring The job ring
+ * @retval  0 for success
+ * @retval  -1 for error
+ */
+int shutdown_job_ring(struct sec_job_ring_t *job_ring);
+
+/*
+ * @brief Enable irqs on associated job ring.
+ * @param [in] job_ring The job ring
+ * @retval  0 for success
+ * @retval  -1 for error
+ */
+int jr_enable_irqs(struct sec_job_ring_t *job_ring);
+
+/*
+ * @brief Disable irqs on associated job ring.
+ * @param [in] job_ring The job ring
+ * @retval  0 for success
+ * @retval  -1 for error
+ */
+int jr_disable_irqs(struct sec_job_ring_t *job_ring);
+
+ /*
+  * IRJA - Input Ring Jobs Added Register shows
+  * how many new jobs were added to the Input Ring.
+  */
+static inline void hw_enqueue_desc_on_job_ring(struct jobring_regs *regs,
+					       int num)
+{
+	sec_out32(&regs->irja, num);
+}
+
+#endif /* _SEC_HW_SPECIFIC_H_ */
diff --git a/include/drivers/nxp/crypto/caam/sec_jr_driver.h b/include/drivers/nxp/crypto/caam/sec_jr_driver.h
new file mode 100644
index 0000000..57e0fa0
--- /dev/null
+++ b/include/drivers/nxp/crypto/caam/sec_jr_driver.h
@@ -0,0 +1,178 @@
+/*
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _JR_DRIVER_H_
+#define _JR_DRIVER_H_
+
+#include "jr_driver_config.h"
+
+/* The maximum size of a SEC descriptor, in WORDs (32 bits). */
+#define MAX_DESC_SIZE_WORDS		64
+
+#define CAAM_TIMEOUT   200000	/* ms */
+
+/* Return codes for JR user space driver APIs */
+typedef enum sec_return_code_e {
+	SEC_SUCCESS = 0,
+	SEC_INVALID_INPUT_PARAM,
+	SEC_OUT_OF_MEMORY,
+	SEC_DESCRIPTOR_IN_FLIGHT,
+	SEC_LAST_DESCRIPTOR_IN_FLIGHT,
+	SEC_PROCESSING_ERROR,
+	SEC_DESC_PROCESSING_ERROR,
+	SEC_JR_IS_FULL,
+	SEC_DRIVER_RELEASE_IN_PROGRESS,
+	SEC_DRIVER_ALREADY_INITIALIZED,
+	SEC_DRIVER_NOT_INITIALIZED,
+	SEC_JOB_RING_RESET_IN_PROGRESS,
+	SEC_RESET_ENGINE_FAILED,
+	SEC_ENABLE_IRQS_FAILED,
+	SEC_DISABLE_IRQS_FAILED,
+	SEC_RETURN_CODE_MAX_VALUE,
+} sec_return_code_t;
+
+/* STRUCTURES AND OTHER TYPEDEFS */
+
+/*
+ * @brief Function called by JR User Space driver to notify every processed
+ *         descriptor.
+ *
+ * Callback provided by the User Application.
+ * Callback is invoked by JR User Space driver for each descriptor processed by
+ * SEC
+ * @param [in] status          Status word indicating processing result for
+ *                                this descriptor.
+ * @param [in] arg               Opaque data passed by User Application
+ *                                It is opaque from JR driver's point of view.
+ * @param [in] job_ring           The job ring handle on which the processed
+ *                               descriptor word was enqueued
+ */
+typedef void (*user_callback) (uint32_t *desc, uint32_t status,
+			       void *arg, void *job_ring);
+
+/*
+ * Structure encompassing a job descriptor which is to be processed
+ * by SEC. User should also initialise this structure with the callback
+ * function pointer which will be called by driver after recieving proccessed
+ * descriptor from SEC. User data is also passed in this data structure which
+ * will be sent as an argument to the user callback function.
+ */
+struct job_descriptor {
+	uint32_t desc[MAX_DESC_SIZE_WORDS];
+	void *arg;
+	user_callback callback;
+};
+
+/*
+ * @brief Initialize the JR User Space driver.
+ * This function will handle initialization of sec library
+ * along with registering platform specific callbacks,
+ * as well as local data initialization.
+ * Call once during application startup.
+ * @note Global SEC initialization is done in SEC kernel driver.
+ * @note The hardware IDs of the initialized Job Rings are opaque to the UA.
+ * The exact Job Rings used by this library are decided between SEC user
+ * space driver and SEC kernel driver. A static partitioning of Job Rings is
+ * assumed, configured in DTS(device tree specification) file.
+ * @param [in] platform_cb     Registering the platform specific
+ *                             callbacks with driver
+ * @retval ::0                 for successful execution
+ * @retval ::-1                failure
+ */
+int sec_jr_lib_init(void);
+
+/*
+ * @brief Initialize the software and hardware resources tied to a job ring.
+ * @param [in] jr_mode;        Model to be used by SEC Driver to receive
+ *                             notifications from SEC.  Can be either
+ *                             SEC_NOTIFICATION_TYPE_IRQ or
+ *                             SEC_NOTIFICATION_TYPE_POLL
+ * @param [in] irq_coalescing_timer This value determines the maximum
+ *                                     amount of time after processing a
+ *                                     descriptor before raising an interrupt.
+ * @param [in] irq_coalescing_count This value determines how many
+ *                                     descriptors are completed before
+ *                                     raising an interrupt.
+ * @param [in] reg_base_addr   The job ring base address register
+ * @param [in] irq_id          The job ring interrupt identification number.
+ * @retval  job_ring_handle for successful job ring configuration
+ * @retval  NULL on error
+ */
+void *init_job_ring(uint8_t jr_mode,
+		    uint16_t irq_coalescing_timer,
+		    uint8_t irq_coalescing_count,
+		    void *reg_base_addr, uint32_t irq_id);
+
+/*
+ * @brief Release the resources used by the JR User Space driver.
+ * Reset and release SEC's job rings indicated by the User Application at
+ * init_job_ring() and free any memory allocated internally.
+ * Call once during application tear down.
+ * @note In case there are any descriptors in-flight (descriptors received by
+ * JR driver for processing and for which no response was yet provided to UA),
+ * the descriptors are discarded without any notifications to User Application.
+ * @retval ::0                 is returned for a successful execution
+ * @retval ::-1                is returned if JR driver release is in progress
+ */
+int sec_release(void);
+
+/*
+ * @brief Submit a descriptor for SEC processing.
+ * This function creates a "job" which is meant to instruct SEC HW
+ * to perform the processing on the input buffer. The "job" is enqueued
+ * in the Job Ring associated. The function will return after the "job"
+ * enqueue is finished. The function will not wait for SEC to
+ * start or/and finish the "job" processing.
+ * After the processing is finished the SEC HW writes the processing result
+ * to the provided output buffer.
+ * The Caller must poll JR driver using jr_dequeue()
+ * to receive notifications of the processing completion
+ * status. The notifications are received by caller by means of callback
+ * (see ::user_callback).
+ * @param [in]  job_ring_handle   The handle of the job ring on which
+ *                                descriptor is to be enqueued
+ * @param [in]  job_descriptor    The job descriptor structure of type
+ *                                struct job_descriptor. This structure
+ *                                should be filled with job descriptor along
+ *                                with callback function to be called after
+ *                                processing of descriptor and some
+ *                                opaque data passed to be passed to the
+ *                                callback function
+ *
+ * @retval ::0                 is returned for successful execution
+ * @retval ::-1                is returned if there is some enqueue failure
+ */
+int enq_jr_desc(void *job_ring_handle, struct job_descriptor *jobdescr);
+
+/*
+ * @brief Polls for available descriptors processed by SEC on a specific
+ * Job Ring
+ * This function polls the SEC Job Rings and delivers processed descriptors
+ * Each processed descriptor has a user_callback registered.
+ * This user_callback is invoked for each processed descriptor.
+ * The polling is stopped when "limit" descriptors are notified or when
+ * there are no more descriptors to notify.
+ * @note The dequeue_jr() API cannot be called from within a user_callback
+ * function
+ * @param [in]  job_ring_handle    The Job Ring handle.
+ * @param [in]  limit              This value represents the maximum number
+ *                                 of processed descriptors that can be
+ *                                 notified API call on this Job Ring.
+ *                                 Note that fewer descriptors may be notified
+ *                                 if enough processed descriptors are not
+ *                                 available.
+ *                                 If limit has a negative value, then all
+ *                                 ready descriptors will be notified.
+ *
+ * @retval :: >=0                  is returned where retval is the total
+ *                                 Number of descriptors notified
+ *                                 during this function call.
+ * @retval :: -1                   is returned in case of some error
+ */
+int dequeue_jr(void *job_ring_handle, int32_t limit);
+
+#endif /* _JR_DRIVER_H_  */
diff --git a/include/drivers/nxp/csu/csu.h b/include/drivers/nxp/csu/csu.h
new file mode 100644
index 0000000..3a43e45
--- /dev/null
+++ b/include/drivers/nxp/csu/csu.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef CSU_H
+#define CSU_H
+
+#define CSU_SEC_ACCESS_REG_OFFSET	(0x0021CU)
+
+/* Macros defining access permissions to configure
+ * the regions controlled by Central Security Unit.
+ */
+enum csu_cslx_access {
+	CSU_NS_SUP_R = (0x8U),
+	CSU_NS_SUP_W = (0x80U),
+	CSU_NS_SUP_RW = (0x88U),
+	CSU_NS_USER_R = (0x4U),
+	CSU_NS_USER_W = (0x40U),
+	CSU_NS_USER_RW = (0x44U),
+	CSU_S_SUP_R = (0x2U),
+	CSU_S_SUP_W = (0x20U),
+	CSU_S_SUP_RW = (0x22U),
+	CSU_S_USER_R = (0x1U),
+	CSU_S_USER_W = (0x10U),
+	CSU_S_USER_RW = (0x11U),
+	CSU_ALL_RW = (0xffU),
+};
+
+struct csu_ns_dev_st {
+	uintptr_t ind;
+	uint32_t val;
+};
+
+void enable_layerscape_ns_access(struct csu_ns_dev_st *csu_ns_dev,
+				 uint32_t num, uintptr_t nxp_csu_addr);
+
+#endif
diff --git a/include/drivers/nxp/dcfg/dcfg.h b/include/drivers/nxp/dcfg/dcfg.h
new file mode 100644
index 0000000..524450a
--- /dev/null
+++ b/include/drivers/nxp/dcfg/dcfg.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DCFG_H
+#define DCFG_H
+
+#include <endian.h>
+
+#if defined(CONFIG_CHASSIS_2)
+#include <dcfg_lsch2.h>
+#elif defined(CONFIG_CHASSIS_3_2)
+#include <dcfg_lsch3.h>
+#endif
+
+#ifdef NXP_GUR_BE
+#define gur_in32(a)		bswap32(mmio_read_32((uintptr_t)(a)))
+#define gur_out32(a, v)		mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_GUR_LE)
+#define gur_in32(a)		mmio_read_32((uintptr_t)(a))
+#define gur_out32(a, v)		mmio_write_32((uintptr_t)(a), v)
+#else
+#error Please define CCSR GUR register endianness
+#endif
+
+typedef struct {
+	union {
+		uint32_t val;
+		struct {
+			uint32_t min_ver:4;
+			uint32_t maj_ver:4;
+#if defined(CONFIG_CHASSIS_3) || defined(CONFIG_CHASSIS_3_2)
+			uint32_t personality:6;
+			uint32_t rsv1:2;
+#elif defined(CONFIG_CHASSIS_2)
+			uint32_t personality:8;
+
+#endif
+#if defined(CONFIG_CHASSIS_3) || defined(CONFIG_CHASSIS_3_2)
+			uint32_t dev_id:6;
+			uint32_t rsv2:2;
+			uint32_t family:4;
+#elif defined(CONFIG_CHASSIS_2)
+			uint32_t dev_id:12;
+#endif
+			uint32_t mfr_id;
+		} __packed bf;
+		struct {
+			uint32_t maj_min:8;
+			uint32_t version; /* SoC version without major and minor info */
+		} __packed bf_ver;
+	} __packed svr_reg;
+	bool sec_enabled;
+	bool is_populated;
+} soc_info_t;
+
+typedef struct {
+	bool is_populated;
+	uint8_t ocram_present;
+	uint8_t ddrc1_present;
+#if defined(CONFIG_CHASSIS_3) || defined(CONFIG_CHASSIS_3_2)
+	uint8_t ddrc2_present;
+#endif
+} devdisr5_info_t;
+
+typedef struct {
+	uint32_t porsr1;
+	uintptr_t g_nxp_dcfg_addr;
+	unsigned long nxp_sysclk_freq;
+	unsigned long nxp_ddrclk_freq;
+	unsigned int nxp_plat_clk_divider;
+} dcfg_init_info_t;
+
+
+struct sysinfo {
+	unsigned long freq_platform;
+	unsigned long freq_ddr_pll0;
+	unsigned long freq_ddr_pll1;
+};
+
+int get_clocks(struct sysinfo *sys);
+
+/* Read the PORSR1 register */
+uint32_t read_reg_porsr1(void);
+
+/*******************************************************************************
+ * Returns true if secur eboot is enabled on board
+ * mode = 0  (development mode - sb_en = 1)
+ * mode = 1 (production mode - ITS = 1)
+ ******************************************************************************/
+bool check_boot_mode_secure(uint32_t *mode);
+
+const soc_info_t *get_soc_info();
+const devdisr5_info_t *get_devdisr5_info();
+
+void dcfg_init(dcfg_init_info_t *dcfg_init_data);
+bool is_sec_enabled(void);
+
+void error_handler(int error_code);
+#endif /*	DCFG_H	*/
diff --git a/include/drivers/nxp/dcfg/dcfg_lsch2.h b/include/drivers/nxp/dcfg/dcfg_lsch2.h
new file mode 100644
index 0000000..1e56729
--- /dev/null
+++ b/include/drivers/nxp/dcfg/dcfg_lsch2.h
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DCFG_LSCH2_H
+#define DCFG_LSCH2_H
+
+/* dcfg block register offsets and bitfields */
+#define DCFG_PORSR1_OFFSET		0x00
+#define DCFG_DEVDISR1_OFFSET		0x070
+#define DCFG_DEVDISR4_OFFSET		0x07C
+#define DCFG_DEVDISR5_OFFSET		0x080
+#define DCFG_COREDISR_OFFSET		0x094
+#define RCWSR0_OFFSET			0x100
+#define RCWSR5_OFFSET			0x118
+#define DCFG_BOOTLOCPTRL_OFFSET		0x400
+#define DCFG_BOOTLOCPTRH_OFFSET		0x404
+#define DCFG_COREDISABLEDSR_OFFSET	0x990
+#define DCFG_SCRATCH4_OFFSET		0x20C
+#define DCFG_SVR_OFFSET			0x0A4
+#define DCFG_BRR_OFFSET			0x0E4
+
+#define DCFG_RSTCR_OFFSET		0x0B0
+#define RSTCR_RESET_REQ			0x2
+
+#define DCFG_RSTRQSR1_OFFSET		0x0C8
+#define DCFG_RSTRQMR1_OFFSET		0x0C0
+
+/* DCFG DCSR Macros */
+#define DCFG_DCSR_PORCR1_OFFSET		0x0
+
+#define SVR_MFR_ID_MASK			0xF0000000
+#define SVR_MFR_ID_SHIFT		28
+#define SVR_DEV_ID_MASK			0xFFF0000
+#define SVR_DEV_ID_SHIFT		16
+#define SVR_PERSONALITY_MASK		0xFF00
+#define SVR_PERSONALITY_SHIFT		8
+#define SVR_SEC_MASK			0x100
+#define SVR_SEC_SHIFT			8
+#define SVR_MAJ_VER_MASK		0xF0
+#define SVR_MAJ_VER_SHIFT		4
+#define SVR_MIN_VER_MASK		0xF
+
+#define DISR5_DDRC1_MASK		0x1
+#define DISR5_OCRAM_MASK		0x40
+
+/* DCFG regsiters bit masks */
+#define RCWSR0_SYS_PLL_RAT_SHIFT	25
+#define RCWSR0_SYS_PLL_RAT_MASK		0x1f
+#define RCWSR0_MEM_PLL_RAT_SHIFT	16
+#define RCWSR0_MEM_PLL_RAT_MASK		0x3f
+#define RCWSR0_MEM2_PLL_RAT_SHIFT	18
+#define RCWSR0_MEM2_PLL_RAT_MASK	0x3f
+
+#define RCWSR_SB_EN_OFFSET		RCWSR5_OFFSET
+#define RCWSR_SBEN_MASK			0x1
+#define RCWSR_SBEN_SHIFT		21
+
+/* RCW SRC NAND */
+#define RCW_SRC_NAND_MASK		(0x100)
+#define RCW_SRC_NAND_VAL		(0x100)
+#define NAND_RESERVED_MASK		(0xFC)
+#define NAND_RESERVED_1			(0x0)
+#define NAND_RESERVED_2			(0x80)
+
+/* RCW SRC NOR */
+#define RCW_SRC_NOR_MASK		(0x1F0)
+#define NOR_8B_VAL			(0x10)
+#define NOR_16B_VAL			(0x20)
+#define SD_VAL				(0x40)
+#define QSPI_VAL1			(0x44)
+#define QSPI_VAL2			(0x45)
+
+#endif /*	DCFG_LSCH2_H	*/
diff --git a/include/drivers/nxp/dcfg/dcfg_lsch3.h b/include/drivers/nxp/dcfg/dcfg_lsch3.h
new file mode 100644
index 0000000..cde86fe
--- /dev/null
+++ b/include/drivers/nxp/dcfg/dcfg_lsch3.h
@@ -0,0 +1,80 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DCFG_LSCH3_H
+#define DCFG_LSCH3_H
+
+/* dcfg block register offsets and bitfields */
+#define DCFG_PORSR1_OFFSET			0x00
+
+#define DCFG_DEVDISR1_OFFSET			0x70
+#define DCFG_DEVDISR1_SEC	(1 << 22)
+
+#define DCFG_DEVDISR2_OFFSET			0x74
+
+#define DCFG_DEVDISR3_OFFSET			0x78
+#define DCFG_DEVDISR3_QBMAIN	(1 << 12)
+
+#define DCFG_DEVDISR4_OFFSET			0x7C
+#define DCFG_DEVDISR4_SPI_QSPI	(1 << 4 | 1 << 5)
+
+#define DCFG_DEVDISR5_OFFSET			0x80
+#define DISR5_DDRC1_MASK	0x1
+#define DISR5_DDRC2_MASK	0x2
+#define DISR5_OCRAM_MASK	0x1000
+#define DEVDISR5_MASK_ALL_MEM	0x00001003
+#define DEVDISR5_MASK_DDR	0x00000003
+#define DEVDISR5_MASK_DBG	0x00000400
+
+#define DCFG_DEVDISR6_OFFSET			0x84
+//#define DEVDISR6_MASK             0x00000001
+
+#define DCFG_COREDISR_OFFSET			0x94
+
+#define DCFG_SVR_OFFSET				0x0A4
+#define SVR_MFR_ID_MASK		0xF0000000
+#define SVR_MFR_ID_SHIFT	28
+#define SVR_FAMILY_MASK		0xF000000
+#define SVR_FAMILY_SHIFT	24
+#define SVR_DEV_ID_MASK		0x3F0000
+#define SVR_DEV_ID_SHIFT	16
+#define SVR_PERSONALITY_MASK	0x3E00
+#define SVR_PERSONALITY_SHIFT	9
+#define SVR_SEC_MASK		0x100
+#define SVR_SEC_SHIFT		8
+#define SVR_MAJ_VER_MASK	0xF0
+#define SVR_MAJ_VER_SHIFT	4
+#define SVR_MIN_VER_MASK	0xF
+
+#define RCWSR0_OFFSET				0x100
+#define RCWSR0_SYS_PLL_RAT_SHIFT	2
+#define RCWSR0_SYS_PLL_RAT_MASK		0x1f
+#define RCWSR0_MEM_PLL_RAT_SHIFT	10
+#define RCWSR0_MEM_PLL_RAT_MASK		0x3f
+#define RCWSR0_MEM2_PLL_RAT_SHIFT	18
+#define RCWSR0_MEM2_PLL_RAT_MASK	0x3f
+
+#define RCWSR5_OFFSET				0x110
+#define RCWSR9_OFFSET				0x120
+#define RCWSR_SB_EN_OFFSET	RCWSR9_OFFSET
+#define RCWSR_SBEN_MASK		0x1
+#define RCWSR_SBEN_SHIFT	10
+
+#define RCW_SR27_OFFSET				0x168
+/* DCFG register to dump error code */
+#define DCFG_SCRATCH4_OFFSET			0x20C
+#define DCFG_SCRATCHRW5_OFFSET			0x210
+#define DCFG_SCRATCHRW6_OFFSET			0x214
+#define DCFG_SCRATCHRW7_OFFSET			0x218
+#define DCFG_BOOTLOCPTRL_OFFSET			0x400
+#define DCFG_BOOTLOCPTRH_OFFSET			0x404
+#define DCFG_COREDISABLEDSR_OFFSET		0x990
+
+/* Reset module bit field */
+#define RSTCR_RESET_REQ         0x2
+
+#endif /*	DCFG_LSCH3_H	*/
diff --git a/include/drivers/nxp/dcfg/scfg.h b/include/drivers/nxp/dcfg/scfg.h
new file mode 100644
index 0000000..ef6ed6b
--- /dev/null
+++ b/include/drivers/nxp/dcfg/scfg.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SCFG_H
+#define SCFG_H
+
+#ifdef CONFIG_CHASSIS_2
+
+/* SCFG register offsets */
+#define SCFG_CORE0_SFT_RST_OFFSET	0x0130
+#define SCFG_SNPCNFGCR_OFFSET		0x01A4
+#define SCFG_CORESRENCR_OFFSET		0x0204
+#define SCFG_RVBAR0_0_OFFSET		0x0220
+#define SCFG_RVBAR0_1_OFFSET		0x0224
+#define SCFG_COREBCR_OFFSET		0x0680
+#define SCFG_RETREQCR_OFFSET		0x0424
+
+#define SCFG_COREPMCR_OFFSET		0x042C
+#define COREPMCR_WFIL2			0x1
+
+#define SCFG_GIC400_ADDR_ALIGN_OFFSET	0x0188
+#define SCFG_BOOTLOCPTRH_OFFSET		0x0600
+#define SCFG_BOOTLOCPTRL_OFFSET		0x0604
+#define SCFG_SCRATCHRW2_OFFSET		0x0608
+#define SCFG_SCRATCHRW3_OFFSET		0x060C
+
+/* SCFG bit fields */
+#define SCFG_SNPCNFGCR_SECRDSNP		0x80000000
+#define SCFG_SNPCNFGCR_SECWRSNP         0x40000000
+#endif /* CONFIG_CHASSIS_2 */
+
+#ifndef __ASSEMBLER__
+#include <endian.h>
+#include <lib/mmio.h>
+
+#ifdef NXP_SCFG_BE
+#define scfg_in32(a)		bswap32(mmio_read_32((uintptr_t)(a)))
+#define scfg_out32(a, v)	mmio_write_32((uintptr_t)(a), bswap32(v))
+#define scfg_setbits32(a, v)	mmio_setbits_32((uintptr_t)(a), v)
+#define scfg_clrbits32(a, v)	mmio_clrbits_32((uintptr_t)(a), v)
+#define scfg_clrsetbits32(a, clear, set)	\
+				mmio_clrsetbits_32((uintptr_t)(a), clear, set)
+#elif defined(NXP_SCFG_LE)
+#define scfg_in32(a)		mmio_read_32((uintptr_t)(a))
+#define scfg_out32(a, v)	mmio_write_32((uintptr_t)(a), v)
+#define scfg_setbits32(a, v)	mmio_setbits_32((uintptr_t)(a), v)
+#define scfg_clrbits32(a, v)	mmio_clrbits_32((uintptr_t)(a), v)
+#define scfg_clrsetbits32(a, clear, set)	\
+				mmio_clrsetbits_32((uintptr_t)(a), clear, set)
+#else
+#error Please define CCSR SCFG register endianness
+#endif
+#endif	/*	__ASSEMBLER__	*/
+
+#endif	/* SCFG_H */
diff --git a/include/drivers/nxp/ddr/ddr.h b/include/drivers/nxp/ddr/ddr.h
new file mode 100644
index 0000000..0ef2870
--- /dev/null
+++ b/include/drivers/nxp/ddr/ddr.h
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_H
+#define DDR_H
+
+#include "ddr_io.h"
+#include "dimm.h"
+#include "immap.h"
+
+#ifndef DDRC_NUM_CS
+#define DDRC_NUM_CS 4
+#endif
+
+/*
+ * This is irrespective of what is the number of DDR controller,
+ * number of DIMM used. This is set to maximum
+ * Max controllers = 2
+ * Max num of DIMM per controlle = 2
+ * MAX NUM CS = 4
+ * Not to be changed.
+ */
+#define MAX_DDRC_NUM	2
+#define MAX_DIMM_NUM	2
+#define MAX_CS_NUM	4
+
+#include "opts.h"
+#include "regs.h"
+#include "utility.h"
+
+#ifdef DDR_DEBUG
+#define debug(...) INFO(__VA_ARGS__)
+#else
+#define debug(...) VERBOSE(__VA_ARGS__)
+#endif
+
+#ifndef DDRC_NUM_DIMM
+#define DDRC_NUM_DIMM 1
+#endif
+
+#define CONFIG_CS_PER_SLOT \
+	(DDRC_NUM_CS / DDRC_NUM_DIMM)
+
+/* Record of register values computed */
+struct ddr_cfg_regs {
+	struct {
+		unsigned int bnds;
+		unsigned int config;
+		unsigned int config_2;
+	} cs[MAX_CS_NUM];
+	unsigned int dec[10];
+	unsigned int timing_cfg[10];
+	unsigned int sdram_cfg[3];
+	unsigned int sdram_mode[16];
+	unsigned int md_cntl;
+	unsigned int interval;
+	unsigned int data_init;
+	unsigned int clk_cntl;
+	unsigned int init_addr;
+	unsigned int init_ext_addr;
+	unsigned int zq_cntl;
+	unsigned int wrlvl_cntl[3];
+	unsigned int ddr_sr_cntr;
+	unsigned int sdram_rcw[6];
+	unsigned int dq_map[4];
+	unsigned int eor;
+	unsigned int cdr[2];
+	unsigned int err_disable;
+	unsigned int err_int_en;
+	unsigned int tx_cfg[4];
+	unsigned int debug[64];
+};
+
+struct ddr_conf {
+	int dimm_in_use[MAX_DIMM_NUM];
+	int cs_in_use;	/* bitmask, bit 0 for cs0, bit 1 for cs1, etc. */
+	int cs_on_dimm[MAX_DIMM_NUM];	/* bitmask */
+	unsigned long long cs_base_addr[MAX_CS_NUM];
+	unsigned long long cs_size[MAX_CS_NUM];
+	unsigned long long base_addr;
+	unsigned long long total_mem;
+};
+
+struct ddr_info {
+	unsigned long clk;
+	unsigned long long mem_base;
+	unsigned int num_ctlrs;
+	unsigned int dimm_on_ctlr;
+	struct dimm_params dimm;
+	struct memctl_opt opt;
+	struct ddr_conf conf;
+	struct ddr_cfg_regs ddr_reg;
+	struct ccsr_ddr *ddr[MAX_DDRC_NUM];
+	uint16_t *phy[MAX_DDRC_NUM];
+	int *spd_addr;
+	unsigned int ip_rev;
+	uintptr_t phy_gen2_fw_img_buf;
+	void *img_loadr;
+	int warm_boot_flag;
+};
+
+struct rc_timing {
+	unsigned int speed_bin;
+	unsigned int clk_adj;
+	unsigned int wrlvl;
+};
+
+struct board_timing {
+	unsigned int rc;
+	struct rc_timing const *p;
+	unsigned int add1;
+	unsigned int add2;
+};
+
+enum warm_boot {
+	DDR_COLD_BOOT = 0,
+	DDR_WARM_BOOT = 1,
+	DDR_WRM_BOOT_NT_SUPPORTED = -1,
+};
+
+int disable_unused_ddrc(struct ddr_info *priv, int mask,
+			uintptr_t nxp_ccn_hn_f0_addr);
+int ddr_board_options(struct ddr_info *priv);
+int compute_ddrc(const unsigned long clk,
+		 const struct memctl_opt *popts,
+		 const struct ddr_conf *conf,
+		 struct ddr_cfg_regs *ddr,
+		 const struct dimm_params *dimm_params,
+		 const unsigned int ip_rev);
+int compute_ddr_phy(struct ddr_info *priv);
+int ddrc_set_regs(const unsigned long clk,
+		  const struct ddr_cfg_regs *regs,
+		  const struct ccsr_ddr *ddr,
+		  int twopass);
+int cal_board_params(struct ddr_info *priv,
+		     const struct board_timing *dimm,
+		     int len);
+/* return bit mask of used DIMM(s) */
+int ddr_get_ddr_params(struct dimm_params *pdimm, struct ddr_conf *conf);
+long long dram_init(struct ddr_info *priv
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+		    , uintptr_t nxp_ccn_hn_f0_addr
+#endif
+		);
+long long board_static_ddr(struct ddr_info *info);
+
+#endif	/* DDR_H */
diff --git a/include/drivers/nxp/ddr/ddr_io.h b/include/drivers/nxp/ddr/ddr_io.h
new file mode 100644
index 0000000..fbd7e97
--- /dev/null
+++ b/include/drivers/nxp/ddr/ddr_io.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_IO_H
+#define DDR_IO_H
+
+#include <endian.h>
+
+#include <lib/mmio.h>
+
+#define min(a, b)  (((a) > (b)) ? (b) : (a))
+
+#define max(a, b)  (((a) > (b)) ? (a) : (b))
+
+/* macro for memory barrier */
+#define mb()		asm volatile("dsb sy" : : : "memory")
+
+#ifdef NXP_DDR_BE
+#define ddr_in32(a)			bswap32(mmio_read_32((uintptr_t)(a)))
+#define ddr_out32(a, v)			mmio_write_32((uintptr_t)(a),\
+							bswap32(v))
+#elif defined(NXP_DDR_LE)
+#define ddr_in32(a)			mmio_read_32((uintptr_t)(a))
+#define ddr_out32(a, v)			mmio_write_32((uintptr_t)(a), v)
+#else
+#error Please define CCSR DDR register endianness
+#endif
+
+#define ddr_setbits32(a, v)		ddr_out32((a), ddr_in32(a) | (v))
+#define ddr_clrbits32(a, v)		ddr_out32((a), ddr_in32(a) & ~(v))
+#define ddr_clrsetbits32(a, c, s)	ddr_out32((a), (ddr_in32(a) & ~(c)) \
+						  | (s))
+
+#endif /*	DDR_IO_H	*/
diff --git a/include/drivers/nxp/ddr/dimm.h b/include/drivers/nxp/ddr/dimm.h
new file mode 100644
index 0000000..fcae179
--- /dev/null
+++ b/include/drivers/nxp/ddr/dimm.h
@@ -0,0 +1,330 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DIMM_H
+#define DIMM_H
+
+#define SPD_MEMTYPE_DDR4        0x0C
+
+#define DDR4_SPD_MODULETYPE_MASK        0x0f
+#define DDR4_SPD_MODULETYPE_EXT         0x00
+#define DDR4_SPD_RDIMM			0x01
+#define DDR4_SPD_UDIMM			0x02
+#define DDR4_SPD_SO_DIMM		0x03
+#define DDR4_SPD_LRDIMM			0x04
+#define DDR4_SPD_MINI_RDIMM		0x05
+#define DDR4_SPD_MINI_UDIMM		0x06
+#define DDR4_SPD_72B_SO_RDIMM		0x08
+#define DDR4_SPD_72B_SO_UDIMM		0x09
+#define DDR4_SPD_16B_SO_DIMM		0x0c
+#define DDR4_SPD_32B_SO_DIMM		0x0d
+
+#define SPD_SPA0_ADDRESS		0x36
+#define SPD_SPA1_ADDRESS		0x37
+
+#define spd_to_ps(mtb, ftb)	\
+	((mtb) * pdimm->mtb_ps + ((ftb) * pdimm->ftb_10th_ps) / 10)
+
+#ifdef DDR_DEBUG
+#define dump_spd(spd, len) {				\
+	register int i;					\
+	register unsigned char *buf = (void *)(spd);	\
+							\
+	for (i = 0; i < (len); i++) {			\
+		print_uint(i);				\
+		puts("\t: 0x");				\
+		print_hex(buf[i]);			\
+		puts("\n");				\
+	}						\
+}
+#else
+#define dump_spd(spd, len) {}
+#endif
+
+/* From JEEC Standard No. 21-C release 23A */
+struct ddr4_spd {
+	/* General Section: Bytes 0-127 */
+	unsigned char info_size_crc;	/*  0 # bytes */
+	unsigned char spd_rev;		/*  1 Total # bytes of SPD */
+	unsigned char mem_type;		/*  2 Key Byte / mem type */
+	unsigned char module_type;	/*  3 Key Byte / Module Type */
+	unsigned char density_banks;	/*  4 Density and Banks	*/
+	unsigned char addressing;	/*  5 Addressing */
+	unsigned char package_type;	/*  6 Package type */
+	unsigned char opt_feature;	/*  7 Optional features */
+	unsigned char thermal_ref;	/*  8 Thermal and refresh */
+	unsigned char oth_opt_features;	/*  9 Other optional features */
+	unsigned char res_10;		/* 10 Reserved */
+	unsigned char module_vdd;	/* 11 Module nominal voltage */
+	unsigned char organization;	/* 12 Module Organization */
+	unsigned char bus_width;	/* 13 Module Memory Bus Width */
+	unsigned char therm_sensor;	/* 14 Module Thermal Sensor */
+	unsigned char ext_type;		/* 15 Extended module type */
+	unsigned char res_16;
+	unsigned char timebases;	/* 17 MTb and FTB */
+	unsigned char tck_min;		/* 18 tCKAVGmin */
+	unsigned char tck_max;		/* 19 TCKAVGmax */
+	unsigned char caslat_b1;	/* 20 CAS latencies, 1st byte */
+	unsigned char caslat_b2;	/* 21 CAS latencies, 2nd byte */
+	unsigned char caslat_b3;	/* 22 CAS latencies, 3rd byte */
+	unsigned char caslat_b4;	/* 23 CAS latencies, 4th byte */
+	unsigned char taa_min;		/* 24 Min CAS Latency Time */
+	unsigned char trcd_min;		/* 25 Min RAS# to CAS# Delay Time */
+	unsigned char trp_min;		/* 26 Min Row Precharge Delay Time */
+	unsigned char tras_trc_ext;	/* 27 Upper Nibbles for tRAS and tRC */
+	unsigned char tras_min_lsb;	/* 28 tRASmin, lsb */
+	unsigned char trc_min_lsb;	/* 29 tRCmin, lsb */
+	unsigned char trfc1_min_lsb;	/* 30 Min Refresh Recovery Delay Time */
+	unsigned char trfc1_min_msb;	/* 31 Min Refresh Recovery Delay Time */
+	unsigned char trfc2_min_lsb;	/* 32 Min Refresh Recovery Delay Time */
+	unsigned char trfc2_min_msb;	/* 33 Min Refresh Recovery Delay Time */
+	unsigned char trfc4_min_lsb;	/* 34 Min Refresh Recovery Delay Time */
+	unsigned char trfc4_min_msb;	/* 35 Min Refresh Recovery Delay Time */
+	unsigned char tfaw_msb;		/* 36 Upper Nibble for tFAW */
+	unsigned char tfaw_min;		/* 37 tFAW, lsb */
+	unsigned char trrds_min;	/* 38 tRRD_Smin, MTB */
+	unsigned char trrdl_min;	/* 39 tRRD_Lmin, MTB */
+	unsigned char tccdl_min;	/* 40 tCCS_Lmin, MTB */
+	unsigned char res_41[60-41];	/* 41 Rserved */
+	unsigned char mapping[78-60];	/* 60~77 Connector to SDRAM bit map */
+	unsigned char res_78[117-78];	/* 78~116, Reserved */
+	signed char fine_tccdl_min;	/* 117 Fine offset for tCCD_Lmin */
+	signed char fine_trrdl_min;	/* 118 Fine offset for tRRD_Lmin */
+	signed char fine_trrds_min;	/* 119 Fine offset for tRRD_Smin */
+	signed char fine_trc_min;	/* 120 Fine offset for tRCmin */
+	signed char fine_trp_min;	/* 121 Fine offset for tRPmin */
+	signed char fine_trcd_min;	/* 122 Fine offset for tRCDmin */
+	signed char fine_taa_min;	/* 123 Fine offset for tAAmin */
+	signed char fine_tck_max;	/* 124 Fine offset for tCKAVGmax */
+	signed char fine_tck_min;	/* 125 Fine offset for tCKAVGmin */
+	/* CRC: Bytes 126-127 */
+	unsigned char crc[2];		/* 126-127 SPD CRC */
+
+	/* Module-Specific Section: Bytes 128-255 */
+	union {
+		struct {
+			/* 128 (Unbuffered) Module Nominal Height */
+			unsigned char mod_height;
+			/* 129 (Unbuffered) Module Maximum Thickness */
+			unsigned char mod_thickness;
+			/* 130 (Unbuffered) Reference Raw Card Used */
+			unsigned char ref_raw_card;
+			/* 131 (Unbuffered) Address Mapping from
+			 *     Edge Connector to DRAM
+			 */
+			unsigned char addr_mapping;
+			/* 132~253 (Unbuffered) Reserved */
+			unsigned char res_132[254-132];
+			/* 254~255 CRC */
+			unsigned char crc[2];
+		} unbuffered;
+		struct {
+			/* 128 (Registered) Module Nominal Height */
+			unsigned char mod_height;
+			/* 129 (Registered) Module Maximum Thickness */
+			unsigned char mod_thickness;
+			/* 130 (Registered) Reference Raw Card Used */
+			unsigned char ref_raw_card;
+			/* 131 DIMM Module Attributes */
+			unsigned char modu_attr;
+			/* 132 RDIMM Thermal Heat Spreader Solution */
+			unsigned char thermal;
+			/* 133 Register Manufacturer ID Code, LSB */
+			unsigned char reg_id_lo;
+			/* 134 Register Manufacturer ID Code, MSB */
+			unsigned char reg_id_hi;
+			/* 135 Register Revision Number */
+			unsigned char reg_rev;
+			/* 136 Address mapping from register to DRAM */
+			unsigned char reg_map;
+			unsigned char ca_stren;
+			unsigned char clk_stren;
+			/* 139~253 Reserved */
+			unsigned char res_139[254-139];
+			/* 254~255 CRC */
+			unsigned char crc[2];
+		} registered;
+		struct {
+			/* 128 (Loadreduced) Module Nominal Height */
+			unsigned char mod_height;
+			/* 129 (Loadreduced) Module Maximum Thickness */
+			unsigned char mod_thickness;
+			/* 130 (Loadreduced) Reference Raw Card Used */
+			unsigned char ref_raw_card;
+			/* 131 DIMM Module Attributes */
+			unsigned char modu_attr;
+			/* 132 RDIMM Thermal Heat Spreader Solution */
+			unsigned char thermal;
+			/* 133 Register Manufacturer ID Code, LSB */
+			unsigned char reg_id_lo;
+			/* 134 Register Manufacturer ID Code, MSB */
+			unsigned char reg_id_hi;
+			/* 135 Register Revision Number */
+			unsigned char reg_rev;
+			/* 136 Address mapping from register to DRAM */
+			unsigned char reg_map;
+			/* 137 Register Output Drive Strength for CMD/Add*/
+			unsigned char reg_drv;
+			/* 138 Register Output Drive Strength for CK */
+			unsigned char reg_drv_ck;
+			/* 139 Data Buffer Revision Number */
+			unsigned char data_buf_rev;
+			/* 140 DRAM VrefDQ for Package Rank 0 */
+			unsigned char vrefqe_r0;
+			/* 141 DRAM VrefDQ for Package Rank 1 */
+			unsigned char vrefqe_r1;
+			/* 142 DRAM VrefDQ for Package Rank 2 */
+			unsigned char vrefqe_r2;
+			/* 143 DRAM VrefDQ for Package Rank 3 */
+			unsigned char vrefqe_r3;
+			/* 144 Data Buffer VrefDQ for DRAM Interface */
+			unsigned char data_intf;
+			/*
+			 * 145 Data Buffer MDQ Drive Strength and RTT
+			 * for data rate <= 1866
+			 */
+			unsigned char data_drv_1866;
+			/*
+			 * 146 Data Buffer MDQ Drive Strength and RTT
+			 * for 1866 < data rate <= 2400
+			 */
+			unsigned char data_drv_2400;
+			/*
+			 * 147 Data Buffer MDQ Drive Strength and RTT
+			 * for 2400 < data rate <= 3200
+			 */
+			unsigned char data_drv_3200;
+			/* 148 DRAM Drive Strength */
+			unsigned char dram_drv;
+			/*
+			 * 149 DRAM ODT (RTT_WR, RTT_NOM)
+			 * for data rate <= 1866
+			 */
+			unsigned char dram_odt_1866;
+			/*
+			 * 150 DRAM ODT (RTT_WR, RTT_NOM)
+			 * for 1866 < data rate <= 2400
+			 */
+			unsigned char dram_odt_2400;
+			/*
+			 * 151 DRAM ODT (RTT_WR, RTT_NOM)
+			 * for 2400 < data rate <= 3200
+			 */
+			unsigned char dram_odt_3200;
+			/*
+			 * 152 DRAM ODT (RTT_PARK)
+			 * for data rate <= 1866
+			 */
+			unsigned char dram_odt_park_1866;
+			/*
+			 * 153 DRAM ODT (RTT_PARK)
+			 * for 1866 < data rate <= 2400
+			 */
+			unsigned char dram_odt_park_2400;
+			/*
+			 * 154 DRAM ODT (RTT_PARK)
+			 * for 2400 < data rate <= 3200
+			 */
+			unsigned char dram_odt_park_3200;
+			unsigned char res_155[254-155];	/* Reserved */
+			/* 254~255 CRC */
+			unsigned char crc[2];
+		} loadreduced;
+		unsigned char uc[128]; /* 128-255 Module-Specific Section */
+	} mod_section;
+
+	unsigned char res_256[320-256];	/* 256~319 Reserved */
+
+	/* Module supplier's data: Byte 320~383 */
+	unsigned char mmid_lsb;		/* 320 Module MfgID Code LSB */
+	unsigned char mmid_msb;		/* 321 Module MfgID Code MSB */
+	unsigned char mloc;		/* 322 Mfg Location */
+	unsigned char mdate[2];		/* 323~324 Mfg Date */
+	unsigned char sernum[4];	/* 325~328 Module Serial Number */
+	unsigned char mpart[20];	/* 329~348 Mfg's Module Part Number */
+	unsigned char mrev;		/* 349 Module Revision Code */
+	unsigned char dmid_lsb;		/* 350 DRAM MfgID Code LSB */
+	unsigned char dmid_msb;		/* 351 DRAM MfgID Code MSB */
+	unsigned char stepping;		/* 352 DRAM stepping */
+	unsigned char msd[29];		/* 353~381 Mfg's Specific Data */
+	unsigned char res_382[2];	/* 382~383 Reserved */
+};
+
+/* Parameters for a DDR dimm computed from the SPD */
+struct dimm_params {
+	/* DIMM organization parameters */
+	char mpart[19];		/* guaranteed null terminated */
+
+	unsigned int n_ranks;
+	unsigned int die_density;
+	unsigned long long rank_density;
+	unsigned long long capacity;
+	unsigned int primary_sdram_width;
+	unsigned int ec_sdram_width;
+	unsigned int rdimm;
+	unsigned int package_3ds;	/* number of dies in 3DS */
+	unsigned int device_width;	/* x4, x8, x16 components */
+	unsigned int rc;
+
+	/* SDRAM device parameters */
+	unsigned int n_row_addr;
+	unsigned int n_col_addr;
+	unsigned int edc_config;	/* 0 = none, 1 = parity, 2 = ECC */
+	unsigned int bank_addr_bits;
+	unsigned int bank_group_bits;
+	unsigned int burst_lengths_bitmask;	/* BL=4 bit 2, BL=8 = bit 3 */
+
+	/* mirrored DIMMs */
+	unsigned int mirrored_dimm;	/* only for ddr3 */
+
+	/* DIMM timing parameters */
+
+	int mtb_ps;	/* medium timebase ps */
+	int ftb_10th_ps; /* fine timebase, in 1/10 ps */
+	int taa_ps;	/* minimum CAS latency time */
+	int tfaw_ps;	/* four active window delay */
+
+	/*
+	 * SDRAM clock periods
+	 * The range for these are 1000-10000 so a short should be sufficient
+	 */
+	int tckmin_x_ps;
+	int tckmax_ps;
+
+	/* SPD-defined CAS latencies */
+	unsigned int caslat_x;
+
+	/* basic timing parameters */
+	int trcd_ps;
+	int trp_ps;
+	int tras_ps;
+
+	int trfc1_ps;
+	int trfc2_ps;
+	int trfc4_ps;
+	int trrds_ps;
+	int trrdl_ps;
+	int tccdl_ps;
+	int trfc_slr_ps;
+
+	int trc_ps;	/* maximum = 254 ns + .75 ns = 254750 ps */
+	int twr_ps;	/* 15ns  for all speed bins */
+
+	unsigned int refresh_rate_ps;
+	unsigned int extended_op_srt;
+
+	/* RDIMM */
+	unsigned char rcw[16];	/* Register Control Word 0-15 */
+	unsigned int dq_mapping[18];
+	unsigned int dq_mapping_ors;
+};
+
+int read_spd(unsigned char chip, void *buf, int len);
+int crc16(unsigned char *ptr, int count);
+int cal_dimm_params(const struct ddr4_spd *spd, struct dimm_params *pdimm);
+
+#endif /* DIMM_H */
diff --git a/include/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.h b/include/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.h
new file mode 100644
index 0000000..31db552
--- /dev/null
+++ b/include/drivers/nxp/ddr/fsl-mmdc/fsl_mmdc.h
@@ -0,0 +1,173 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef FSL_MMDC_H
+#define FSL_MMDC_H
+
+/* PHY Write Leveling Configuration and Error Status Register (MPWLGCR) */
+#define MPWLGCR_HW_WL_EN		(1 << 0)
+
+/* PHY Pre-defined Compare and CA delay-line Configuration (MPPDCMPR2) */
+#define MPPDCMPR2_MPR_COMPARE_EN	(1 << 0)
+
+
+/* MMDC PHY Read DQS gating control register 0 (MPDGCTRL0) */
+#define AUTO_RD_DQS_GATING_CALIBRATION_EN	(1 << 28)
+
+/* MMDC PHY Read Delay HW Calibration Control Register (MPRDDLHWCTL) */
+#define MPRDDLHWCTL_AUTO_RD_CALIBRATION_EN	(1 << 4)
+
+/* MMDC Core Power Saving Control and Status Register (MMDC_MAPSR) */
+#define MMDC_MAPSR_PWR_SAV_CTRL_STAT	0x00001067
+
+/* MMDC Core Refresh Control Register (MMDC_MDREF) */
+#define MDREF_START_REFRESH	(1 << 0)
+
+/* MMDC Core Special Command Register (MDSCR) */
+#define CMD_ADDR_MSB_MR_OP(x)	(x << 24)
+#define CMD_ADDR_LSB_MR_ADDR(x)	(x << 16)
+#define MDSCR_DISABLE_CFG_REQ	(0 << 15)
+#define MDSCR_ENABLE_CON_REQ	(1 << 15)
+#define MDSCR_CON_ACK		(1 << 14)
+#define MDSCR_WL_EN		(1 << 9)
+#define	CMD_NORMAL		(0 << 4)
+#define	CMD_PRECHARGE		(1 << 4)
+#define	CMD_AUTO_REFRESH	(2 << 4)
+#define	CMD_LOAD_MODE_REG	(3 << 4)
+#define	CMD_ZQ_CALIBRATION	(4 << 4)
+#define	CMD_PRECHARGE_BANK_OPEN	(5 << 4)
+#define	CMD_MRR			(6 << 4)
+#define CMD_BANK_ADDR_0		0x0
+#define CMD_BANK_ADDR_1		0x1
+#define CMD_BANK_ADDR_2		0x2
+#define CMD_BANK_ADDR_3		0x3
+#define CMD_BANK_ADDR_4		0x4
+#define CMD_BANK_ADDR_5		0x5
+#define CMD_BANK_ADDR_6		0x6
+#define CMD_BANK_ADDR_7		0x7
+
+/* MMDC Core Control Register (MDCTL) */
+#define MDCTL_SDE0		(U(1) << 31)
+#define MDCTL_SDE1		(1 << 30)
+
+/* MMDC PHY ZQ HW control register (MMDC_MPZQHWCTRL) */
+#define MPZQHWCTRL_ZQ_HW_FORCE	(1 << 16)
+
+/* MMDC PHY Measure Unit Register (MMDC_MPMUR0) */
+#define MMDC_MPMUR0_FRC_MSR	(1 << 11)
+
+/* MMDC PHY Read delay-lines Configuration Register (MMDC_MPRDDLCTL) */
+/* default 64 for a quarter cycle delay */
+#define MMDC_MPRDDLCTL_DEFAULT_DELAY	0x40404040
+
+/* MMDC Registers */
+struct mmdc_regs {
+	unsigned int mdctl;
+	unsigned int mdpdc;
+	unsigned int mdotc;
+	unsigned int mdcfg0;
+	unsigned int mdcfg1;
+	unsigned int mdcfg2;
+	unsigned int mdmisc;
+	unsigned int mdscr;
+	unsigned int mdref;
+	unsigned int res1[2];
+	unsigned int mdrwd;
+	unsigned int mdor;
+	unsigned int mdmrr;
+	unsigned int mdcfg3lp;
+	unsigned int mdmr4;
+	unsigned int mdasp;
+	unsigned int res2[239];
+	unsigned int maarcr;
+	unsigned int mapsr;
+	unsigned int maexidr0;
+	unsigned int maexidr1;
+	unsigned int madpcr0;
+	unsigned int madpcr1;
+	unsigned int madpsr0;
+	unsigned int madpsr1;
+	unsigned int madpsr2;
+	unsigned int madpsr3;
+	unsigned int madpsr4;
+	unsigned int madpsr5;
+	unsigned int masbs0;
+	unsigned int masbs1;
+	unsigned int res3[2];
+	unsigned int magenp;
+	unsigned int res4[239];
+	unsigned int mpzqhwctrl;
+	unsigned int mpzqswctrl;
+	unsigned int mpwlgcr;
+	unsigned int mpwldectrl0;
+	unsigned int mpwldectrl1;
+	unsigned int mpwldlst;
+	unsigned int mpodtctrl;
+	unsigned int mprddqby0dl;
+	unsigned int mprddqby1dl;
+	unsigned int mprddqby2dl;
+	unsigned int mprddqby3dl;
+	unsigned int mpwrdqby0dl;
+	unsigned int mpwrdqby1dl;
+	unsigned int mpwrdqby2dl;
+	unsigned int mpwrdqby3dl;
+	unsigned int mpdgctrl0;
+	unsigned int mpdgctrl1;
+	unsigned int mpdgdlst0;
+	unsigned int mprddlctl;
+	unsigned int mprddlst;
+	unsigned int mpwrdlctl;
+	unsigned int mpwrdlst;
+	unsigned int mpsdctrl;
+	unsigned int mpzqlp2ctl;
+	unsigned int mprddlhwctl;
+	unsigned int mpwrdlhwctl;
+	unsigned int mprddlhwst0;
+	unsigned int mprddlhwst1;
+	unsigned int mpwrdlhwst0;
+	unsigned int mpwrdlhwst1;
+	unsigned int mpwlhwerr;
+	unsigned int mpdghwst0;
+	unsigned int mpdghwst1;
+	unsigned int mpdghwst2;
+	unsigned int mpdghwst3;
+	unsigned int mppdcmpr1;
+	unsigned int mppdcmpr2;
+	unsigned int mpswdar0;
+	unsigned int mpswdrdr0;
+	unsigned int mpswdrdr1;
+	unsigned int mpswdrdr2;
+	unsigned int mpswdrdr3;
+	unsigned int mpswdrdr4;
+	unsigned int mpswdrdr5;
+	unsigned int mpswdrdr6;
+	unsigned int mpswdrdr7;
+	unsigned int mpmur0;
+	unsigned int mpwrcadl;
+	unsigned int mpdccr;
+};
+
+struct fsl_mmdc_info {
+	unsigned int mdctl;
+	unsigned int mdpdc;
+	unsigned int mdotc;
+	unsigned int mdcfg0;
+	unsigned int mdcfg1;
+	unsigned int mdcfg2;
+	unsigned int mdmisc;
+	unsigned int mdref;
+	unsigned int mdrwd;
+	unsigned int mdor;
+	unsigned int mdasp;
+	unsigned int mpodtctrl;
+	unsigned int mpzqhwctrl;
+	unsigned int mprddlctl;
+};
+
+void mmdc_init(const struct fsl_mmdc_info *priv, uintptr_t nxp_ddr_addr);
+
+#endif /* FSL_MMDC_H */
diff --git a/include/drivers/nxp/ddr/immap.h b/include/drivers/nxp/ddr/immap.h
new file mode 100644
index 0000000..83b4de6
--- /dev/null
+++ b/include/drivers/nxp/ddr/immap.h
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_IMMAP_H
+#define DDR_IMMAP_H
+
+#define	DDR_DBUS_64		0
+#define	DDR_DBUS_32		1
+#define	DDR_DBUS_16		2
+
+/*
+ * DDRC register file for DDRC 5.0 and above
+ */
+struct ccsr_ddr {
+	struct {
+		unsigned int a;		 /* 0x0, 0x8, 0x10, 0x18 */
+		unsigned int res;	 /* 0x4, 0xc, 0x14, 0x1c */
+	} bnds[4];
+	unsigned char	res_20[0x40 - 0x20];
+	unsigned int	dec[10];	 /* 0x40 */
+	unsigned char	res_68[0x80 - 0x68];
+	unsigned int	csn_cfg[4];	 /* 0x80, 0x84, 0x88, 0x8c */
+	unsigned char	res_90[48];
+	unsigned int	csn_cfg_2[4];	 /* 0xc0, 0xc4, 0xc8, 0xcc */
+	unsigned char	res_d0[48];
+	unsigned int	timing_cfg_3;	 /* SDRAM Timing Configuration 3 */
+	unsigned int	timing_cfg_0;	 /* SDRAM Timing Configuration 0 */
+	unsigned int	timing_cfg_1;	 /* SDRAM Timing Configuration 1 */
+	unsigned int	timing_cfg_2;	 /* SDRAM Timing Configuration 2 */
+	unsigned int	sdram_cfg;	 /* SDRAM Control Configuration */
+	unsigned int	sdram_cfg_2;	 /* SDRAM Control Configuration 2 */
+	unsigned int	sdram_mode;	 /* SDRAM Mode Configuration */
+	unsigned int	sdram_mode_2;	 /* SDRAM Mode Configuration 2 */
+	unsigned int	sdram_md_cntl;	 /* SDRAM Mode Control */
+	unsigned int	sdram_interval;	 /* SDRAM Interval Configuration */
+	unsigned int	sdram_data_init; /* SDRAM Data initialization */
+	unsigned char	res_12c[4];
+	unsigned int	sdram_clk_cntl;	 /* SDRAM Clock Control */
+	unsigned char	res_134[20];
+	unsigned int	init_addr;	 /* training init addr */
+	unsigned int	init_ext_addr;	 /* training init extended addr */
+	unsigned char	res_150[16];
+	unsigned int	timing_cfg_4;	 /* SDRAM Timing Configuration 4 */
+	unsigned int	timing_cfg_5;	 /* SDRAM Timing Configuration 5 */
+	unsigned int	timing_cfg_6;	 /* SDRAM Timing Configuration 6 */
+	unsigned int	timing_cfg_7;	 /* SDRAM Timing Configuration 7 */
+	unsigned int	zq_cntl;	 /* ZQ calibration control*/
+	unsigned int	wrlvl_cntl;	 /* write leveling control*/
+	unsigned char	reg_178[4];
+	unsigned int	ddr_sr_cntr;	 /* self refresh counter */
+	unsigned int	ddr_sdram_rcw_1; /* Control Words 1 */
+	unsigned int	ddr_sdram_rcw_2; /* Control Words 2 */
+	unsigned char	reg_188[8];
+	unsigned int	ddr_wrlvl_cntl_2; /* write leveling control 2 */
+	unsigned int	ddr_wrlvl_cntl_3; /* write leveling control 3 */
+	unsigned char	res_198[0x1a0-0x198];
+	unsigned int	ddr_sdram_rcw_3;
+	unsigned int	ddr_sdram_rcw_4;
+	unsigned int	ddr_sdram_rcw_5;
+	unsigned int	ddr_sdram_rcw_6;
+	unsigned char	res_1b0[0x200-0x1b0];
+	unsigned int	sdram_mode_3;	 /* SDRAM Mode Configuration 3 */
+	unsigned int	sdram_mode_4;	 /* SDRAM Mode Configuration 4 */
+	unsigned int	sdram_mode_5;	 /* SDRAM Mode Configuration 5 */
+	unsigned int	sdram_mode_6;	 /* SDRAM Mode Configuration 6 */
+	unsigned int	sdram_mode_7;	 /* SDRAM Mode Configuration 7 */
+	unsigned int	sdram_mode_8;	 /* SDRAM Mode Configuration 8 */
+	unsigned char	res_218[0x220-0x218];
+	unsigned int	sdram_mode_9;	 /* SDRAM Mode Configuration 9 */
+	unsigned int	sdram_mode_10;	 /* SDRAM Mode Configuration 10 */
+	unsigned int	sdram_mode_11;	 /* SDRAM Mode Configuration 11 */
+	unsigned int	sdram_mode_12;	 /* SDRAM Mode Configuration 12 */
+	unsigned int	sdram_mode_13;	 /* SDRAM Mode Configuration 13 */
+	unsigned int	sdram_mode_14;	 /* SDRAM Mode Configuration 14 */
+	unsigned int	sdram_mode_15;	 /* SDRAM Mode Configuration 15 */
+	unsigned int	sdram_mode_16;	 /* SDRAM Mode Configuration 16 */
+	unsigned char	res_240[0x250-0x240];
+	unsigned int	timing_cfg_8;	 /* SDRAM Timing Configuration 8 */
+	unsigned int	timing_cfg_9;	 /* SDRAM Timing Configuration 9 */
+	unsigned int	timing_cfg_10;	 /* SDRAM Timing COnfigurtion 10 */
+	unsigned char   res_258[0x260-0x25c];
+	unsigned int	sdram_cfg_3;
+	unsigned char	res_264[0x270-0x264];
+	unsigned int	sdram_md_cntl_2;
+	unsigned char	res_274[0x400-0x274];
+	unsigned int	dq_map[4];
+	unsigned char	res_410[0x800-0x410];
+	unsigned int	tx_cfg[4];
+	unsigned char	res_810[0xb20-0x810];
+	unsigned int	ddr_dsr1;	 /* Debug Status 1 */
+	unsigned int	ddr_dsr2;	 /* Debug Status 2 */
+	unsigned int	ddr_cdr1;	 /* Control Driver 1 */
+	unsigned int	ddr_cdr2;	 /* Control Driver 2 */
+	unsigned char	res_b30[200];
+	unsigned int	ip_rev1;	 /* IP Block Revision 1 */
+	unsigned int	ip_rev2;	 /* IP Block Revision 2 */
+	unsigned int	eor;		 /* Enhanced Optimization Register */
+	unsigned char	res_c04[252];
+	unsigned int	mtcr;		 /* Memory Test Control Register */
+	unsigned char	res_d04[28];
+	unsigned int	mtp[10];	 /* Memory Test Patterns */
+	unsigned char	res_d48[184];
+	unsigned int	data_err_inject_hi; /* Data Path Err Injection Mask Hi*/
+	unsigned int	data_err_inject_lo;/* Data Path Err Injection Mask Lo*/
+	unsigned int	ecc_err_inject;	 /* Data Path Err Injection Mask ECC */
+	unsigned char	res_e0c[20];
+	unsigned int	capture_data_hi; /* Data Path Read Capture High */
+	unsigned int	capture_data_lo; /* Data Path Read Capture Low */
+	unsigned int	capture_ecc;	 /* Data Path Read Capture ECC */
+	unsigned char	res_e2c[20];
+	unsigned int	err_detect;	 /* Error Detect */
+	unsigned int	err_disable;	 /* Error Disable */
+	unsigned int	err_int_en;
+	unsigned int	capture_attributes; /* Error Attrs Capture */
+	unsigned int	capture_address; /* Error Addr Capture */
+	unsigned int	capture_ext_address; /* Error Extended Addr Capture */
+	unsigned int	err_sbe;	 /* Single-Bit ECC Error Management */
+	unsigned char	res_e5c[164];
+	unsigned int	debug[64];	 /* debug_1 to debug_64 */
+};
+#endif /* DDR_IMMAP_H */
diff --git a/include/drivers/nxp/ddr/opts.h b/include/drivers/nxp/ddr/opts.h
new file mode 100644
index 0000000..f32891b
--- /dev/null
+++ b/include/drivers/nxp/ddr/opts.h
@@ -0,0 +1,119 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_OPTS_H
+#define DDR_OPTS_H
+
+#define SDRAM_TYPE_DDR4		5	/* sdram_cfg register */
+
+#define DDR_BC4			4	/* burst chop */
+#define DDR_OTF			6	/* on-the-fly BC4 and BL8 */
+#define DDR_BL8			8	/* burst length 8 */
+
+#define DDR4_RTT_OFF		0
+#define DDR4_RTT_60_OHM		1	/* RZQ/4 */
+#define DDR4_RTT_120_OHM	2	/* RZQ/2 */
+#define DDR4_RTT_40_OHM		3	/* RZQ/6 */
+#define DDR4_RTT_240_OHM	4	/* RZQ/1 */
+#define DDR4_RTT_48_OHM		5	/* RZQ/5 */
+#define DDR4_RTT_80_OHM		6	/* RZQ/3 */
+#define DDR4_RTT_34_OHM		7	/* RZQ/7 */
+#define DDR4_RTT_WR_OFF		0
+#define DDR4_RTT_WR_120_OHM	1
+#define DDR4_RTT_WR_240_OHM	2
+#define DDR4_RTT_WR_HZ		3
+#define DDR4_RTT_WR_80_OHM	4
+#define DDR_ODT_NEVER		0x0
+#define DDR_ODT_CS		0x1
+#define DDR_ODT_ALL_OTHER_CS	0x2
+#define DDR_ODT_OTHER_DIMM	0x3
+#define DDR_ODT_ALL		0x4
+#define DDR_ODT_SAME_DIMM	0x5
+#define DDR_ODT_CS_AND_OTHER_DIMM 0x6
+#define DDR_ODT_OTHER_CS_ONSAMEDIMM 0x7
+#define DDR_BA_INTLV_CS01	0x40
+#define DDR_BA_INTLV_CS0123	0x64
+#define DDR_BA_NONE		0
+#define DDR_256B_INTLV		0x8
+
+struct memctl_opt {
+	int rdimm;
+	unsigned int dbw_cap_shift;
+	struct local_opts_s {
+		unsigned int auto_precharge;
+		unsigned int odt_rd_cfg;
+		unsigned int odt_wr_cfg;
+		unsigned int odt_rtt_norm;
+		unsigned int odt_rtt_wr;
+	} cs_odt[DDRC_NUM_CS];
+	int ctlr_intlv;
+	unsigned int ctlr_intlv_mode;
+	unsigned int ba_intlv;
+	int addr_hash;
+	int ecc_mode;
+	int ctlr_init_ecc;
+	int self_refresh_in_sleep;
+	int self_refresh_irq_en;
+	int dynamic_power;
+	/* memory data width 0 = 64-bit, 1 = 32-bit, 2 = 16-bit */
+	unsigned int data_bus_dimm;
+	unsigned int data_bus_used;	/* on individual board */
+	unsigned int burst_length;	/* BC4, OTF and BL8 */
+	int otf_burst_chop_en;
+	int mirrored_dimm;
+	int quad_rank_present;
+	int output_driver_impedance;
+	int ap_en;
+	int x4_en;
+
+	int caslat_override;
+	unsigned int caslat_override_value;
+	int addt_lat_override;
+	unsigned int addt_lat_override_value;
+
+	unsigned int clk_adj;
+	unsigned int cpo_sample;
+	unsigned int wr_data_delay;
+
+	unsigned int cswl_override;
+	unsigned int wrlvl_override;
+	unsigned int wrlvl_sample;
+	unsigned int wrlvl_start;
+	unsigned int wrlvl_ctl_2;
+	unsigned int wrlvl_ctl_3;
+
+	int half_strength_drive_en;
+	int twot_en;
+	int threet_en;
+	unsigned int bstopre;
+	unsigned int tfaw_ps;
+
+	int rtt_override;
+	unsigned int rtt_override_value;
+	unsigned int rtt_wr_override_value;
+	unsigned int rtt_park;
+
+	int auto_self_refresh_en;
+	unsigned int sr_it;
+	unsigned int ddr_cdr1;
+	unsigned int ddr_cdr2;
+
+	unsigned int trwt_override;
+	unsigned int trwt;
+	unsigned int twrt;
+	unsigned int trrt;
+	unsigned int twwt;
+
+	unsigned int vref_phy;
+	unsigned int vref_dimm;
+	unsigned int odt;
+	unsigned int phy_tx_impedance;
+	unsigned int phy_atx_impedance;
+	unsigned int skip2d;
+};
+
+#endif /* DDR_OPTS_H */
diff --git a/include/drivers/nxp/ddr/regs.h b/include/drivers/nxp/ddr/regs.h
new file mode 100644
index 0000000..e85fd8f
--- /dev/null
+++ b/include/drivers/nxp/ddr/regs.h
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_REG_H
+#define DDR_REG_H
+
+#define SDRAM_CS_CONFIG_EN		0x80000000
+
+/* DDR_SDRAM_CFG - DDR SDRAM Control Configuration
+ */
+#define SDRAM_CFG_MEM_EN		0x80000000
+#define SDRAM_CFG_SREN			0x40000000
+#define SDRAM_CFG_ECC_EN		0x20000000
+#define SDRAM_CFG_RD_EN			0x10000000
+#define SDRAM_CFG_SDRAM_TYPE_MASK	0x07000000
+#define SDRAM_CFG_SDRAM_TYPE_SHIFT	24
+#define SDRAM_CFG_DYN_PWR		0x00200000
+#define SDRAM_CFG_DBW_MASK		0x00180000
+#define SDRAM_CFG_DBW_SHIFT		19
+#define SDRAM_CFG_32_BW			0x00080000
+#define SDRAM_CFG_16_BW			0x00100000
+#define SDRAM_CFG_8_BW			0x00180000
+#define SDRAM_CFG_8_BE			0x00040000
+#define SDRAM_CFG_2T_EN			0x00008000
+#define SDRAM_CFG_MEM_HLT		0x00000002
+#define SDRAM_CFG_BI			0x00000001
+
+#define SDRAM_CFG2_FRC_SR		0x80000000
+#define SDRAM_CFG2_FRC_SR_CLEAR		~(SDRAM_CFG2_FRC_SR)
+#define SDRAM_CFG2_D_INIT		0x00000010
+#define SDRAM_CFG2_AP_EN		0x00000020
+#define SDRAM_CFG2_ODT_ONLY_READ	2
+
+#define SDRAM_CFG3_DDRC_RST		0x80000000
+
+#define SDRAM_INTERVAL_REFINT	0xFFFF0000
+#define SDRAM_INTERVAL_REFINT_CLEAR	~(SDRAM_INTERVAL_REFINT)
+#define SDRAM_INTERVAL_BSTOPRE	0x3FFF
+
+/* DDR_MD_CNTL */
+#define MD_CNTL_MD_EN		0x80000000
+#define MD_CNTL_CS_SEL(x)	(((x) & 0x7) << 28)
+#define MD_CNTL_MD_SEL(x)	(((x) & 0xf) << 24)
+#define MD_CNTL_CKE(x)		(((x) & 0x3) << 20)
+
+/* DDR_CDR1 */
+#define DDR_CDR1_DHC_EN	0x80000000
+#define DDR_CDR1_ODT_SHIFT	17
+#define DDR_CDR1_ODT_MASK	0x6
+#define DDR_CDR2_ODT_MASK	0x1
+#define DDR_CDR1_ODT(x) ((x & DDR_CDR1_ODT_MASK) << DDR_CDR1_ODT_SHIFT)
+#define DDR_CDR2_ODT(x) (x & DDR_CDR2_ODT_MASK)
+#define DDR_CDR2_VREF_OVRD(x)	(0x00008080 | ((((x) - 37) & 0x3F) << 8))
+#define DDR_CDR2_VREF_TRAIN_EN	0x00000080
+#define DDR_CDR2_VREF_RANGE_2	0x00000040
+#define DDR_CDR_ODT_OFF		0x0
+#define DDR_CDR_ODT_100ohm	0x1
+#define DDR_CDR_ODT_120OHM	0x2
+#define DDR_CDR_ODT_80ohm	0x3
+#define DDR_CDR_ODT_60ohm	0x4
+#define DDR_CDR_ODT_40ohm	0x5
+#define DDR_CDR_ODT_50ohm	0x6
+#define DDR_CDR_ODT_30ohm	0x7
+
+
+/* DDR ERR_DISABLE */
+#define DDR_ERR_DISABLE_APED	(1 << 8)  /* Address parity error disable */
+#define DDR_ERR_DISABLE_SBED	(1 << 2)  /* Address parity error disable */
+#define DDR_ERR_DISABLE_MBED	(1 << 3)  /* Address parity error disable */
+
+/* Mode Registers */
+#define DDR_MR5_CA_PARITY_LAT_4_CLK	0x1 /* for DDR4-1600/1866/2133 */
+#define DDR_MR5_CA_PARITY_LAT_5_CLK	0x2 /* for DDR4-2400 */
+
+/* DDR DSR2  register */
+#define DDR_DSR_2_PHY_INIT_CMPLT	0x4
+
+/* SDRAM TIMING_CFG_10 register */
+#define DDR_TIMING_CFG_10_T_STAB	0x7FFF
+
+/* DEBUG 2 register */
+#define DDR_DBG_2_MEM_IDLE		0x00000002
+
+/* DEBUG 26 register */
+#define DDR_DEBUG_26_BIT_6		(0x1 << 6)
+#define DDR_DEBUG_26_BIT_7		(0x1 << 7)
+#define DDR_DEBUG_26_BIT_12		(0x1 << 12)
+#define DDR_DEBUG_26_BIT_13		(0x1 << 13)
+#define DDR_DEBUG_26_BIT_14		(0x1 << 14)
+#define DDR_DEBUG_26_BIT_15		(0x1 << 15)
+#define DDR_DEBUG_26_BIT_16		(0x1 << 16)
+#define DDR_DEBUG_26_BIT_17		(0x1 << 17)
+#define DDR_DEBUG_26_BIT_18		(0x1 << 18)
+#define DDR_DEBUG_26_BIT_19		(0x1 << 19)
+#define DDR_DEBUG_26_BIT_24		(0x1 << 24)
+#define DDR_DEBUG_26_BIT_25		(0x1 << 25)
+
+#define DDR_DEBUG_26_BIT_24_CLEAR	~(DDR_DEBUG_26_BIT_24)
+
+/* DEBUG_29 register */
+#define DDR_TX_BD_DIS	(1 << 10) /* Transmit Bit Deskew Disable */
+
+#define DDR_INIT_ADDR_EXT_UIA	(1 << 31)
+
+#endif /* DDR_REG_H */
diff --git a/include/drivers/nxp/ddr/utility.h b/include/drivers/nxp/ddr/utility.h
new file mode 100644
index 0000000..2e22ad5
--- /dev/null
+++ b/include/drivers/nxp/ddr/utility.h
@@ -0,0 +1,24 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef UTILITY_H
+#define UTILITY_H
+
+#include <dcfg.h>
+
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+#define CCN_HN_F_SAM_CTL		0x8
+#define CCN_HN_F_REGION_SIZE		0x10000
+#endif
+
+unsigned long get_ddr_freq(struct sysinfo *sys, int ctrl_num);
+unsigned int get_memory_clk_ps(unsigned long clk);
+unsigned int picos_to_mclk(unsigned long data_rate, unsigned int picos);
+unsigned int get_ddrc_version(const struct ccsr_ddr *ddr);
+void print_ddr_info(struct ccsr_ddr *ddr);
+
+#endif
diff --git a/include/drivers/nxp/flexspi/flash_info.h b/include/drivers/nxp/flexspi/flash_info.h
new file mode 100644
index 0000000..d0ffc86
--- /dev/null
+++ b/include/drivers/nxp/flexspi/flash_info.h
@@ -0,0 +1,89 @@
+// SPDX-License-Identifier: BSD-3-Clause
+/*
+ *  Copyright 2020-2021 NXP
+ */
+
+/**
+ * @Flash info
+ *
+ */
+#ifndef FLASH_INFO_H
+#define FLASH_INFO_H
+
+#define SZ_16M_BYTES			0x1000000U
+
+/* Start of "if defined(CONFIG_MT25QU512A)" */
+#if defined(CONFIG_MT25QU512A)
+#define F_SECTOR_64K			0x10000U
+#define F_PAGE_256			0x100U
+#define F_SECTOR_4K			0x1000U
+#define F_FLASH_SIZE_BYTES		0x4000000U
+#define F_SECTOR_ERASE_SZ		F_SECTOR_64K
+#ifdef CONFIG_FSPI_4K_ERASE
+#define F_SECTOR_ERASE_SZ		F_SECTOR_4K
+#endif
+
+/* End of "if defined(CONFIG_MT25QU512A)" */
+
+/* Start of "if defined(CONFIG_MX25U25645G)" */
+#elif defined(CONFIG_MX25U25645G)
+#define F_SECTOR_64K			0x10000U
+#define F_PAGE_256			0x100U
+#define F_SECTOR_4K			0x1000U
+#define F_FLASH_SIZE_BYTES		0x2000000U
+#define F_SECTOR_ERASE_SZ		F_SECTOR_64K
+#ifdef CONFIG_FSPI_4K_ERASE
+#define F_SECTOR_ERASE_SZ		F_SECTOR_4K
+#endif
+
+/* End of "if defined(CONFIG_MX25U25645G)" */
+
+/* Start of "if defined(CONFIG_MX25U51245G)" */
+#elif defined(CONFIG_MX25U51245G)
+#define F_SECTOR_64K			0x10000U
+#define F_PAGE_256			0x100U
+#define F_SECTOR_4K			0x1000U
+#define F_FLASH_SIZE_BYTES		0x4000000U
+#define F_SECTOR_ERASE_SZ		F_SECTOR_64K
+#ifdef CONFIG_FSPI_4K_ERASE
+#define F_SECTOR_ERASE_SZ		F_SECTOR_4K
+#endif
+
+/* End of "if defined(CONFIG_MX25U51245G)" */
+
+/* Start of "if defined(CONFIG_MT35XU512A)" */
+#elif defined(CONFIG_MT35XU512A)
+#define F_SECTOR_128K			0x20000U
+#define F_SECTOR_32K			0x8000U
+#define F_PAGE_256			0x100U
+#define F_SECTOR_4K			0x1000U
+#define F_FLASH_SIZE_BYTES		0x4000000U
+#define F_SECTOR_ERASE_SZ		F_SECTOR_128K
+#ifdef CONFIG_FSPI_4K_ERASE
+#define F_SECTOR_ERASE_SZ		F_SECTOR_4K
+#endif
+/* If Warm boot is enabled for the platform,
+ * count of arm instruction N-OP(s) to mark
+ * the completion of write operation to flash;
+ * varies from one flash to other.
+ */
+#ifdef NXP_WARM_BOOT
+#define FLASH_WR_COMP_WAIT_BY_NOP_COUNT	0x20000
+#endif
+
+/* End of "if defined(CONFIG_MT35XU512A)" */
+
+/* Start of #elif defined(CONFIG_MT35XU02G) */
+#elif defined(CONFIG_MT35XU02G)
+#define F_SECTOR_128K			0x20000U
+#define F_PAGE_256			0x100U
+#define F_SECTOR_4K			0x1000U
+#define F_FLASH_SIZE_BYTES		0x10000000U
+#define F_SECTOR_ERASE_SZ		F_SECTOR_128K
+#ifdef CONFIG_FSPI_4K_ERASE
+#define F_SECTOR_ERASE_SZ		F_SECTOR_4K
+#endif
+
+#endif /* End of #elif defined(CONFIG_MT35XU02G) */
+
+#endif /* FLASH_INFO_H */
diff --git a/include/drivers/nxp/flexspi/fspi_api.h b/include/drivers/nxp/flexspi/fspi_api.h
new file mode 100644
index 0000000..d0de543
--- /dev/null
+++ b/include/drivers/nxp/flexspi/fspi_api.h
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+
+/*!
+ * @file	fspi_api.h
+ * @brief	This file contains the FlexSPI/FSPI API to communicate
+ *		to attached Slave device.
+ * @addtogroup	FSPI_API
+ * @{
+ */
+
+#ifndef FSPI_API_H
+#define FSPI_API_H
+
+#if DEBUG_FLEXSPI
+#define SZ_57M			0x3900000u
+#endif
+
+/*!
+ * Basic set of APIs.
+ */
+
+/*!
+ * @details AHB read/IP Read, decision to be internal to API
+ * Minimum Read size = 1Byte
+ * @param[in] src_off source offset from where data to read from flash
+ * @param[out] des Destination location where data needs to be copied
+ * @param[in] len length in Bytes,where 1-word=4-bytes/32-bits
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_read(uint32_t src_off, uint32_t *des, uint32_t len);
+/*!
+ * @details Sector erase, Minimum size
+ * 256KB(0x40000)/128KB(0x20000)/64K(0x10000)/4K(0x1000)
+ * depending upon flash, Calls xspi_wren() internally
+ * @param[out] erase_offset Destination erase location on flash which
+ * has to be erased, needs to be multiple of 0x40000/0x20000/0x10000
+ * @param[in] erase_len length in bytes in Hex like 0x100000 for 1MB, minimum
+ * erase size is 1 sector(0x40000/0x20000/0x10000)
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_sector_erase(uint32_t erase_offset, uint32_t erase_len);
+/*!
+ * @details IP write, For writing data to flash, calls xspi_wren() internally.
+ * Single/multiple page write can start @any offset, but performance will be low
+ * due to ERRATA
+ * @param[out] dst_off Destination location on flash where data needs to
+ * be written
+ * @param[in] src source offset from where data to be read
+ * @param[in] len length in bytes,where 1-word=4-bytes/32-bits
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_write(uint32_t dst_off, void *src, uint32_t len);
+/*!
+ * @details fspi_init, Init function.
+ * @param[in] uint32_t base_reg_addr
+ * @param[in] uint32_t flash_start_addr
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int fspi_init(uint32_t base_reg_addr, uint32_t flash_start_addr);
+/*!
+ * @details is_flash_busy, Check if any erase or write or lock is
+ * pending on flash/slave
+ * @param[in] void
+ *
+ * @return TRUE/FLASE
+ */
+bool is_flash_busy(void);
+
+/*!
+ * Advanced set of APIs.
+ */
+
+/*!
+ * @details Write enable, to be used by advance users only.
+ * Step 1 for sending write commands to flash.
+ * @param[in] dst_off destination offset where data will be written
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_wren(uint32_t dst_off);
+/*!
+ * @details AHB read, meaning direct memory mapped access to flash,
+ * Minimum Read size = 1Byte
+ * @param[in] src_off source offset from where data to read from flash,
+ * needs to be word aligned
+ * @param[out] des Destination location where data needs to be copied
+ * @param[in] len length in Bytes,where 1-word=4-bytes/32-bits
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_ahb_read(uint32_t src_off, uint32_t *des, uint32_t len);
+/*!
+ * @details IP read, READ via RX buffer from flash, minimum READ size = 1Byte
+ * @param[in] src_off source offset from where data to be read from flash
+ * @param[out] des Destination location where data needs to be copied
+ * @param[in] len length in Bytes,where 1-word=4-bytes/32-bits
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_ip_read(uint32_t src_off, uint32_t *des, uint32_t len);
+/*!
+ * @details CHIP erase, Erase complete chip in one go
+ *
+ * @return XSPI_SUCCESS or error code
+ */
+int xspi_bulk_erase(void);
+
+/*!
+ * Add test cases to confirm flash read/erase/write functionality.
+ */
+void fspi_test(uint32_t fspi_test_addr, uint32_t size, int extra);
+#endif /* FSPI_API_H */
diff --git a/include/drivers/nxp/flexspi/xspi_error_codes.h b/include/drivers/nxp/flexspi/xspi_error_codes.h
new file mode 100644
index 0000000..18b31eb
--- /dev/null
+++ b/include/drivers/nxp/flexspi/xspi_error_codes.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+/* error codes */
+#ifndef XSPI_ERROR_CODES_H
+#define XSPI_ERROR_CODES_H
+
+#include <errno.h>
+
+typedef enum {
+	XSPI_SUCCESS                     = 0,
+	XSPI_READ_FAIL			 = ELAST + 1,
+	XSPI_ERASE_FAIL,
+	XSPI_IP_READ_FAIL,
+	XSPI_AHB_READ_FAIL,
+	XSPI_IP_WRITE_FAIL,
+	XSPI_AHB_WRITE_FAIL,
+	XSPI_BLOCK_TIMEOUT,
+	XSPI_UNALIGN_ADDR,
+	XSPI_UNALIGN_SIZE,
+} XSPI_STATUS_CODES;
+#undef ELAST
+#define ELAST XSPI_STATUS_CODES.XSPI_UNALIGN_SIZE
+#endif
diff --git a/include/drivers/nxp/gic/gicv2/plat_gic.h b/include/drivers/nxp/gic/gicv2/plat_gic.h
new file mode 100644
index 0000000..ff34744
--- /dev/null
+++ b/include/drivers/nxp/gic/gicv2/plat_gic.h
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_GICV2_H
+#define PLAT_GICV2_H
+
+#include <drivers/arm/gicv2.h>
+
+ /* register offsets */
+#define GICD_CTLR_OFFSET          0x0
+#define GICD_CPENDSGIR3_OFFSET    0xF1C
+#define GICD_SPENDSGIR3_OFFSET    0xF2C
+#define GICD_SGIR_OFFSET          0xF00
+#define GICD_IGROUPR0_OFFSET      0x080
+#define GICD_TYPER_OFFSET         0x0004
+#define GICD_ISENABLER0_OFFSET    0x0100
+#define GICD_ICENABLER0_OFFSET    0x0180
+#define GICD_IPRIORITYR3_OFFSET   0x040C
+#define GICD_ISENABLERn_OFFSET    0x0100
+#define GICD_ISACTIVER0_OFFSET    0x300
+
+#define GICC_CTLR_OFFSET          0x0
+#define GICC_PMR_OFFSET           0x0004
+#define GICC_IAR_OFFSET           0x000C
+#define GICC_DIR_OFFSET           0x1000
+#define GICC_EOIR_OFFSET          0x0010
+
+ /* bitfield masks */
+#define GICC_CTLR_EN_GRP0           0x1
+#define GICC_CTLR_EN_GRP1           0x2
+#define GICC_CTLR_EOImodeS_MASK     0x200
+#define GICC_CTLR_DIS_BYPASS        0x60
+#define GICC_CTLR_CBPR_MASK         0x10
+#define GICC_CTLR_FIQ_EN_MASK       0x8
+#define GICC_CTLR_ACKCTL_MASK       0x4
+#define GICC_PMR_FILTER             0xFF
+
+#define GICD_CTLR_EN_GRP0           0x1
+#define GICD_CTLR_EN_GRP1           0x2
+#define GICD_IGROUP0_SGI15          0x8000
+#define GICD_ISENABLE0_SGI15        0x8000
+#define GICD_ICENABLE0_SGI15        0x8000
+#define GICD_ISACTIVER0_SGI15       0x8000
+#define GICD_CPENDSGIR_CLR_MASK     0xFF000000
+#define GICD_IPRIORITY_SGI15_MASK   0xFF000000
+#define GICD_SPENDSGIR3_SGI15_MASK  0xFF000000
+#define GICD_SPENDSGIR3_SGI15_OFFSET  0x18
+
+#ifndef __ASSEMBLER__
+
+/* GIC common API's */
+void plat_ls_gic_driver_init(const uintptr_t nxp_gicd_addr,
+			     const uintptr_t nxp_gicc_addr,
+			     uint8_t plat_core_count,
+			     interrupt_prop_t *ls_interrupt_props,
+			     uint8_t ls_interrupt_prop_count,
+			     uint32_t *target_mask_array);
+void plat_ls_gic_init(void);
+void plat_ls_gic_cpuif_enable(void);
+void plat_ls_gic_cpuif_disable(void);
+void plat_ls_gic_redistif_on(void);
+void plat_ls_gic_redistif_off(void);
+void plat_gic_pcpu_init(void);
+/* GIC utility functions */
+void get_gic_offset(uint32_t *gicc_base, uint32_t *gicd_base);
+#endif
+
+#endif /* PLAT_GICV2_H */
diff --git a/include/drivers/nxp/gic/gicv3/plat_gic.h b/include/drivers/nxp/gic/gicv3/plat_gic.h
new file mode 100644
index 0000000..f4e12de
--- /dev/null
+++ b/include/drivers/nxp/gic/gicv3/plat_gic.h
@@ -0,0 +1,114 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_GICV3_H
+#define PLAT_GICV3_H
+
+#include <drivers/arm/gicv3.h>
+
+ /* offset between redistributors */
+#define GIC_RD_OFFSET       0x00020000
+ /* offset between SGI's */
+#define GIC_SGI_OFFSET      0x00020000
+ /* offset from rd base to sgi base */
+#define GIC_RD_2_SGI_OFFSET 0x00010000
+
+ /* register offsets */
+#define GICD_CTLR_OFFSET        0x0
+#define GICD_CLR_SPI_SR         0x58
+#define GICD_IGROUPR_2          0x88
+#define GICD_ISENABLER_2        0x108
+#define GICD_ICENABLER_2        0x188
+#define GICD_ICPENDR_2          0x288
+#define GICD_ICACTIVER_2        0x388
+#define GICD_IPRIORITYR_22      0x458
+#define GICD_ICFGR_5            0xC14
+#define GICD_IGRPMODR_2         0xD08
+
+#define GICD_IROUTER60_OFFSET   0x61e0
+#define GICD_IROUTER76_OFFSET   0x6260
+#define GICD_IROUTER89_OFFSET   0x62C8
+#define GICD_IROUTER112_OFFSET  0x6380
+#define GICD_IROUTER113_OFFSET  0x6388
+
+#define GICR_ICENABLER0_OFFSET  0x180
+#define GICR_CTLR_OFFSET        0x0
+#define GICR_IGROUPR0_OFFSET    0x80
+#define GICR_IGRPMODR0_OFFSET   0xD00
+#define GICR_IPRIORITYR3_OFFSET 0x40C
+#define GICR_ICPENDR0_OFFSET    0x280
+#define GICR_ISENABLER0_OFFSET  0x100
+#define GICR_TYPER_OFFSET       0x8
+#define GICR_WAKER_OFFSET       0x14
+#define GICR_ICACTIVER0_OFFSET  0x380
+#define GICR_ICFGR0_OFFSET      0xC00
+
+ /* bitfield masks */
+#define GICD_CTLR_EN_GRP_MASK   0x7
+#define GICD_CTLR_EN_GRP_1NS    0x2
+#define GICD_CTLR_EN_GRP_1S     0x4
+#define GICD_CTLR_EN_GRP_0      0x1
+#define GICD_CTLR_ARE_S_MASK    0x10
+#define GICD_CTLR_RWP           0x80000000
+
+#define GICR_ICENABLER0_SGI15   0x00008000
+#define GICR_CTLR_RWP           0x8
+#define GICR_CTLR_DPG0_MASK     0x2000000
+#define GICR_IGROUPR0_SGI15     0x00008000
+#define GICR_IGRPMODR0_SGI15    0x00008000
+#define GICR_ISENABLER0_SGI15   0x00008000
+#define GICR_IPRIORITYR3_SGI15_MASK  0xFF000000
+#define GICR_ICPENDR0_SGI15     0x8000
+
+#define GIC_SPI_89_MASK         0x02000000
+#define GIC_SPI89_PRIORITY_MASK 0xFF00
+#define GIC_IRM_SPI89           0x80000000
+
+#define GICD_IROUTER_VALUE      0x100
+#define GICR_WAKER_SLEEP_BIT    0x2
+#define GICR_WAKER_ASLEEP       (1 << 2 | 1 << 1)
+
+#define ICC_SRE_EL3_SRE          0x1
+#define ICC_IGRPEN0_EL1_EN       0x1
+#define ICC_CTLR_EL3_CBPR_EL1S   0x1
+#define ICC_CTLR_EL3_RM          0x20
+#define ICC_CTLR_EL3_EOIMODE_EL3 0x4
+#define ICC_CTLR_EL3_PMHE        0x40
+#define ICC_PMR_EL1_P_FILTER     0xFF
+#define ICC_IAR0_EL1_SGI15       0xF
+#define ICC_SGI0R_EL1_INTID      0x0F000000
+#define ICC_IAR0_INTID_SPI_89    0x59
+
+#define  ICC_IGRPEN1_EL1 S3_0_C12_C12_7
+#define  ICC_PMR_EL1     S3_0_C4_C6_0
+#define  ICC_SRE_EL3     S3_6_C12_C12_5
+#define  ICC_CTLR_EL3    S3_6_C12_C12_4
+#define  ICC_SRE_EL2     S3_4_C12_C9_5
+#define  ICC_CTLR_EL1    S3_0_C12_C12_4
+
+#ifndef __ASSEMBLER__
+
+/* GIC common API's */
+typedef unsigned int (*my_core_pos_fn)(void);
+
+void plat_ls_gic_driver_init(const uintptr_t nxp_gicd_addr,
+			     const uintptr_t nxp_gicr_addr,
+			     uint8_t plat_core_count,
+			     interrupt_prop_t *ls_interrupt_props,
+			     uint8_t ls_interrupt_prop_count,
+			     uintptr_t *target_mask_array,
+			     mpidr_hash_fn mpidr_to_core_pos);
+//void plat_ls_gic_driver_init(void);
+void plat_ls_gic_init(void);
+void plat_ls_gic_cpuif_enable(void);
+void plat_ls_gic_cpuif_disable(void);
+void plat_ls_gic_redistif_on(void);
+void plat_ls_gic_redistif_off(void);
+void plat_gic_pcpu_init(void);
+#endif
+
+#endif /* PLAT_GICV3_H */
diff --git a/include/drivers/nxp/gpio/nxp_gpio.h b/include/drivers/nxp/gpio/nxp_gpio.h
new file mode 100644
index 0000000..df75840
--- /dev/null
+++ b/include/drivers/nxp/gpio/nxp_gpio.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_GPIO_H
+#define PLAT_GPIO_H
+
+#include <endian.h>
+#include <lib/mmio.h>
+
+/* GPIO Register offset */
+#define GPIO_SEL_MASK		0x7F
+#define GPIO_BIT_MASK		0x1F
+#define GPDIR_REG_OFFSET	0x0
+#define GPDAT_REG_OFFSET	0x8
+
+#define GPIO_ID_BASE_ADDR_SHIFT 5U
+#define GPIO_BITS_PER_BASE_REG	32U
+
+#define GPIO_0			0
+#define GPIO_1			1
+#define GPIO_2			2
+#define GPIO_3			3
+
+#define GPIO_SUCCESS		0x0
+#define GPIO_FAILURE		0x1
+
+#ifdef NXP_GPIO_BE
+#define gpio_read32(a)           bswap32(mmio_read_32((uintptr_t)(a)))
+#define gpio_write32(a, v)       mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_GPIO_LE)
+#define gpio_read32(a)           mmio_read_32((uintptr_t)(a))
+#define gpio_write32(a, v)       mmio_write_32((uintptr_t)(a), (v))
+#else
+#error Please define GPIO register endianness
+#endif
+
+typedef struct {
+	uintptr_t gpio1_base_addr;
+	uintptr_t gpio2_base_addr;
+	uintptr_t gpio3_base_addr;
+	uintptr_t gpio4_base_addr;
+} gpio_init_info_t;
+
+void gpio_init(gpio_init_info_t *gpio_init_data);
+uint32_t *select_gpio_n_bitnum(uint32_t povdd_gpio, uint32_t *bit_num);
+int clr_gpio_bit(uint32_t *gpio_base_addr, uint32_t bit_num);
+int set_gpio_bit(uint32_t *gpio_base_addr, uint32_t bit_num);
+
+#endif /* PLAT_GPIO_H */
diff --git a/include/drivers/nxp/i2c/i2c.h b/include/drivers/nxp/i2c/i2c.h
new file mode 100644
index 0000000..85e6eb4
--- /dev/null
+++ b/include/drivers/nxp/i2c/i2c.h
@@ -0,0 +1,52 @@
+/*
+ * Copyright 2016-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+
+#ifndef I2C_H
+#define I2C_H
+
+#include <lib/mmio.h>
+
+#define I2C_TIMEOUT	1000	/* ms */
+
+#define I2C_FD_CONSERV	0x7e
+#define I2C_CR_DIS	(1 << 7)
+#define I2C_CR_EN	(0 << 7)
+#define I2C_CR_MA	(1 << 5)
+#define I2C_CR_TX	(1 << 4)
+#define I2C_CR_TX_NAK	(1 << 3)
+#define I2C_CR_RSTA	(1 << 2)
+#define I2C_SR_BB	(1 << 5)
+#define I2C_SR_IDLE	(0 << 5)
+#define I2C_SR_AL	(1 << 4)
+#define I2C_SR_IF	(1 << 1)
+#define I2C_SR_RX_NAK	(1 << 0)
+#define I2C_SR_RST	(I2C_SR_AL | I2C_SR_IF)
+
+#define I2C_GLITCH_EN	0x8
+
+#define i2c_in(a)	mmio_read_8((uintptr_t)(a))
+#define i2c_out(a, v)	mmio_write_8((uintptr_t)(a), (v))
+
+struct ls_i2c {
+	unsigned char ad;	/* I2c Bus Address Register */
+	unsigned char fd;	/* I2c Bus Frequency Dividor Register */
+	unsigned char cr;	/* I2c Bus Control Register */
+	unsigned char sr;	/* I2c Bus Status Register */
+	unsigned char dr;	/* I2C Bus Data I/O Register */
+	unsigned char ic;	/* I2C Bus Interrupt Config Register */
+	unsigned char dbg;	/* I2C Bus Debug Register */
+};
+
+void i2c_init(uintptr_t nxp_i2c_addr);
+int i2c_read(unsigned char chip, int addr, int alen,
+	     unsigned char *buf, int len);
+int i2c_write(unsigned char chip, int addr, int alen,
+	      const unsigned char *buf, int len);
+int i2c_probe_chip(unsigned char chip);
+
+#endif /* I2C_H */
diff --git a/include/drivers/nxp/interconnect/ls_interconnect.h b/include/drivers/nxp/interconnect/ls_interconnect.h
new file mode 100644
index 0000000..777089c
--- /dev/null
+++ b/include/drivers/nxp/interconnect/ls_interconnect.h
@@ -0,0 +1,19 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef LS_INTERCONNECT_H
+#define LS_INTERCONNECT_H
+
+#if (INTERCONNECT == CCI400)
+#define CCI_TERMINATE_BARRIER_TX	0x8
+#endif
+
+/* Interconnect CCI/CCN functions */
+void plat_ls_interconnect_enter_coherency(unsigned int num_clusters);
+void plat_ls_interconnect_exit_coherency(void);
+
+#endif
diff --git a/include/drivers/nxp/pmu/pmu.h b/include/drivers/nxp/pmu/pmu.h
new file mode 100644
index 0000000..28199e8
--- /dev/null
+++ b/include/drivers/nxp/pmu/pmu.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PMU_H
+#define PMU_H
+
+/* PMU Registers' OFFSET */
+#define PMU_PCPW20SR_OFFSET		0x830
+#define PMU_CLL2FLUSHSETR_OFFSET	0x1110
+#define PMU_CLSL2FLUSHCLRR_OFFSET	0x1114
+#define PMU_CLL2FLUSHSR_OFFSET		0x1118
+#define PMU_POWMGTCSR_VAL		(1 << 20)
+
+/* PMU Registers */
+#define CORE_TIMEBASE_ENBL_OFFSET	0x8A0
+#define CLUST_TIMER_BASE_ENBL_OFFSET	0x18A0
+
+#define PMU_IDLE_CLUSTER_MASK		0x2
+#define PMU_FLUSH_CLUSTER_MASK		0x2
+#define PMU_IDLE_CORE_MASK		0xfe
+
+/* pmu register offsets and bitmaps */
+#define PMU_POWMGTDCR0_OFFSET		0xC20
+#define PMU_POWMGTCSR_OFFSET		0x4000
+#define PMU_CLAINACTSETR_OFFSET		0x1100
+#define PMU_CLAINACTCLRR_OFFSET		0x1104
+#define PMU_CLSINACTSETR_OFFSET		0x1108
+#define PMU_CLSINACTCLRR_OFFSET		0x110C
+#define PMU_CLL2FLUSHSETR_OFFSET	0x1110
+#define PMU_CLL2FLUSHCLRR_OFFSET	0x1114
+#define PMU_IPPDEXPCR0_OFFSET		0x4040
+#define PMU_IPPDEXPCR1_OFFSET		0x4044
+#define PMU_IPPDEXPCR2_OFFSET		0x4048
+#define PMU_IPPDEXPCR3_OFFSET		0x404C
+#define PMU_IPPDEXPCR4_OFFSET		0x4050
+#define PMU_IPPDEXPCR5_OFFSET		0x4054
+#define PMU_IPPDEXPCR6_OFFSET		0x4058
+#define PMU_IPSTPCR0_OFFSET		0x4120
+#define PMU_IPSTPCR1_OFFSET		0x4124
+#define PMU_IPSTPCR2_OFFSET		0x4128
+#define PMU_IPSTPCR3_OFFSET		0x412C
+#define PMU_IPSTPCR4_OFFSET		0x4130
+#define PMU_IPSTPCR5_OFFSET		0x4134
+#define PMU_IPSTPCR6_OFFSET		0x4138
+#define PMU_IPSTPACKSR0_OFFSET		0x4140
+#define PMU_IPSTPACKSR1_OFFSET		0x4144
+#define PMU_IPSTPACKSR2_OFFSET		0x4148
+#define PMU_IPSTPACKSR3_OFFSET		0x414C
+#define PMU_IPSTPACKSR4_OFFSET		0x4150
+#define PMU_IPSTPACKSR5_OFFSET		0x4154
+#define PMU_IPSTPACKSR6_OFFSET		0x4158
+
+#define CLAINACT_DISABLE_ACP		0xFF
+#define CLSINACT_DISABLE_SKY		0xFF
+#define POWMGTDCR_STP_OV_EN		0x1
+#define POWMGTCSR_LPM20_REQ		0x00100000
+
+/* Used by PMU */
+#define DEVDISR1_MASK			0x024F3504
+#define DEVDISR2_MASK			0x0003FFFF
+#define DEVDISR3_MASK			0x0000303F
+#define DEVDISR4_MASK			0x0000FFFF
+#define DEVDISR5_MASK			0x00F07603
+#define DEVDISR6_MASK			0x00000001
+
+#ifndef __ASSEMBLER__
+void enable_timer_base_to_cluster(uintptr_t nxp_pmu_addr);
+void enable_core_tb(uintptr_t nxp_pmu_addr);
+#endif /* __ASSEMBLER__ */
+
+#endif
diff --git a/include/drivers/nxp/qspi/qspi.h b/include/drivers/nxp/qspi/qspi.h
new file mode 100644
index 0000000..db11c3b
--- /dev/null
+++ b/include/drivers/nxp/qspi/qspi.h
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef QSPI_H
+#define QSPI_H
+
+#include <endian.h>
+#include <lib/mmio.h>
+
+#define CHS_QSPI_MCR			0x01550000
+#define CHS_QSPI_64LE			0xC
+
+#ifdef NXP_QSPI_BE
+#define qspi_in32(a)           bswap32(mmio_read_32((uintptr_t)(a)))
+#define qspi_out32(a, v)       mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_QSPI_LE)
+#define qspi_in32(a)           mmio_read_32((uintptr_t)(a))
+#define qspi_out32(a, v)       mmio_write_32((uintptr_t)(a), (v))
+#else
+#error Please define CCSR QSPI register endianness
+#endif
+
+int qspi_io_setup(uintptr_t nxp_qspi_flash_addr,
+		  size_t nxp_qspi_flash_size,
+		  uintptr_t fip_offset);
+#endif /* __QSPI_H__ */
diff --git a/include/drivers/nxp/sd/sd_mmc.h b/include/drivers/nxp/sd/sd_mmc.h
new file mode 100644
index 0000000..32b41f1
--- /dev/null
+++ b/include/drivers/nxp/sd/sd_mmc.h
@@ -0,0 +1,337 @@
+/*
+ * Copyright (c) 2015, 2016 Freescale Semiconductor, Inc.
+ * Copyright 2017-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SD_MMC_H
+#define SD_MMC_H
+
+#include <lib/mmio.h>
+
+/* operating freq */
+#define CARD_IDENTIFICATION_FREQ	400000
+#define SD_SS_25MHZ	20000000
+#define SD_HS_50MHZ	40000000
+#define MMC_SS_20MHZ	15000000
+#define MMC_HS_26MHZ	20000000
+#define MMC_HS_52MHZ	40000000
+
+/* Need to check this value ? */
+#define MAX_PLATFORM_CLOCK	800000000
+
+/* eSDHC system control register defines */
+#define ESDHC_SYSCTL_DTOCV(t)		(((t) & 0xF) << 16)
+#define ESDHC_SYSCTL_SDCLKFS(f)		(((f) & 0xFF) << 8)
+#define ESDHC_SYSCTL_DVS(d)		(((d) & 0xF) << 4)
+#define ESDHC_SYSCTL_SDCLKEN		(0x00000008)
+#define ESDHC_SYSCTL_RSTA		(0x01000000)
+
+/* Data timeout counter value. SDHC_CLK x 227 */
+#define TIMEOUT_COUNTER_SDCLK_2_27	0xE
+#define ESDHC_SYSCTL_INITA	0x08000000
+
+/* eSDHC interrupt status enable register defines */
+#define ESDHC_IRQSTATEN_CINS	0x00000040
+#define ESDHC_IRQSTATEN_BWR	0x00000010
+
+/* eSDHC interrupt status register defines */
+#define ESDHC_IRQSTAT_DMAE	(0x10000000)
+#define ESDHC_IRQSTAT_AC12E	(0x01000000)
+#define ESDHC_IRQSTAT_DEBE	(0x00400000)
+#define ESDHC_IRQSTAT_DCE	(0x00200000)
+#define ESDHC_IRQSTAT_DTOE	(0x00100000)
+#define ESDHC_IRQSTAT_CIE	(0x00080000)
+#define ESDHC_IRQSTAT_CEBE	(0x00040000)
+#define ESDHC_IRQSTAT_CCE	(0x00020000)
+#define ESDHC_IRQSTAT_CTOE	(0x00010000)
+#define ESDHC_IRQSTAT_CINT	(0x00000100)
+#define ESDHC_IRQSTAT_CRM	(0x00000080)
+#define ESDHC_IRQSTAT_CINS	(0x00000040)
+#define ESDHC_IRQSTAT_BRR	(0x00000020)
+#define ESDHC_IRQSTAT_BWR	(0x00000010)
+#define ESDHC_IRQSTAT_DINT	(0x00000008)
+#define ESDHC_IRQSTAT_BGE	(0x00000004)
+#define ESDHC_IRQSTAT_TC	(0x00000002)
+#define ESDHC_IRQSTAT_CC	(0x00000001)
+#define ESDHC_IRQSTAT_CMD_ERR	(ESDHC_IRQSTAT_CIE |\
+			ESDHC_IRQSTAT_CEBE |\
+			ESDHC_IRQSTAT_CCE)
+#define ESDHC_IRQSTAT_DATA_ERR	(ESDHC_IRQSTAT_DEBE |\
+			ESDHC_IRQSTAT_DCE |\
+			ESDHC_IRQSTAT_DTOE)
+#define ESDHC_IRQSTAT_CLEAR_ALL	(0xFFFFFFFF)
+
+/* eSDHC present state register defines */
+#define ESDHC_PRSSTAT_CLSL	0x00800000
+#define ESDHC_PRSSTAT_WPSPL	0x00080000
+#define ESDHC_PRSSTAT_CDPL	0x00040000
+#define ESDHC_PRSSTAT_CINS	0x00010000
+#define ESDHC_PRSSTAT_BREN	0x00000800
+#define ESDHC_PRSSTAT_BWEN	0x00000400
+#define ESDHC_PRSSTAT_RTA	0x00000200
+#define ESDHC_PRSSTAT_WTA	0x00000100
+#define ESDHC_PRSSTAT_SDOFF	0x00000080
+#define ESDHC_PRSSTAT_PEROFF	0x00000040
+#define ESDHC_PRSSTAT_HCKOFF	0x00000020
+#define ESDHC_PRSSTAT_IPGOFF	0x00000010
+#define ESDHC_PRSSTAT_DLA	0x00000004
+#define ESDHC_PRSSTAT_CDIHB	0x00000002
+#define ESDHC_PRSSTAT_CIHB	0x00000001
+
+/* eSDHC protocol control register defines */
+#define ESDHC_PROCTL_EMODE_LE	0x00000020
+#define ESDHC_PROCTL_DTW_1BIT	0x00000000
+#define ESDHC_PROCTL_DTW_4BIT	0x00000002
+#define ESDHC_PROCTL_DTW_8BIT	0x00000004
+
+/* Watermark Level Register (WML) */
+#define ESDHC_WML_RD_WML(w)	((w) & 0x7F)
+#define ESDHC_WML_WR_WML(w)	(((w) & 0x7F) << 16)
+#define ESDHC_WML_RD_BRST(w)	(((w) & 0xF) << 8)
+#define ESDHC_WML_WR_BRST(w)	(((w) & 0xF) << 24)
+#define ESDHC_WML_WR_BRST_MASK	(0x0F000000)
+#define ESDHC_WML_RD_BRST_MASK	(0x00000F00)
+#define ESDHC_WML_RD_WML_MASK	(0x0000007F)
+#define ESDHC_WML_WR_WML_MASK	(0x007F0000)
+#define WML_512_BYTES		(0x0)
+#define BURST_128_BYTES	(0x0)
+
+/* eSDHC control register define */
+#define ESDHC_DCR_SNOOP		0x00000040
+
+/* ESDHC Block attributes register */
+#define ESDHC_BLKATTR_BLKCNT(c)	(((c) & 0xffff) << 16)
+#define ESDHC_BLKATTR_BLKSZE(s)	((s) & 0xfff)
+
+/* Transfer Type Register */
+#define ESDHC_XFERTYP_CMD(c)	(((c) & 0x3F) << 24)
+#define ESDHC_XFERTYP_CMDTYP_NORMAL	(0x0)
+#define ESDHC_XFERTYP_CMDTYP_SUSPEND	(0x00400000)
+#define ESDHC_XFERTYP_CMDTYP_RESUME	(0x00800000)
+#define ESDHC_XFERTYP_CMDTYP_ABORT	(0x00C00000)
+#define ESDHC_XFERTYP_DPSEL	(0x00200000)
+#define ESDHC_XFERTYP_CICEN	(0x00100000)
+#define ESDHC_XFERTYP_CCCEN	(0x00080000)
+#define ESDHC_XFERTYP_RSPTYP_NONE	(0x0)
+#define ESDHC_XFERTYP_RSPTYP_136	(0x00010000)
+#define ESDHC_XFERTYP_RSPTYP_48	(0x00020000)
+#define ESDHC_XFERTYP_RSPTYP_48_BUSY	(0x00030000)
+#define ESDHC_XFERTYP_MSBSEL	(0x00000020)
+#define ESDHC_XFERTYP_DTDSEL	(0x00000010)
+#define ESDHC_XFERTYP_AC12EN	(0x00000004)
+#define ESDHC_XFERTYP_BCEN	(0x00000002)
+#define ESDHC_XFERTYP_DMAEN	(0x00000001)
+
+#define MMC_VDD_HIGH_VOLTAGE	0x00000100
+
+/* command index */
+#define CMD0	0
+#define CMD1	1
+#define CMD2	2
+#define CMD3	3
+#define CMD5	5
+#define CMD6	6
+#define CMD7	7
+#define CMD8	8
+#define CMD9	9
+#define CMD12	12
+#define CMD13	13
+#define CMD14	14
+#define CMD16	16
+#define CMD17	17
+#define CMD18	18
+#define CMD19	19
+#define CMD24	24
+#define CMD41	41
+#define CMD42	42
+#define CMD51	51
+#define CMD55	55
+#define CMD56	56
+#define ACMD6	CMD6
+#define ACMD13	CMD13
+#define ACMD41	CMD41
+#define ACMD42	CMD42
+#define ACMD51	CMD51
+
+/* commands abbreviations */
+#define CMD_GO_IDLE_STATE	CMD0
+#define CMD_MMC_SEND_OP_COND	CMD1
+#define CMD_ALL_SEND_CID	CMD2
+#define CMD_SEND_RELATIVE_ADDR	CMD3
+#define CMD_SET_DSR	CMD4
+#define CMD_SWITCH_FUNC	CMD6
+#define CMD_SELECT_CARD	CMD7
+#define CMD_DESELECT_CARD	CMD7
+#define CMD_SEND_IF_COND	CMD8
+#define CMD_MMC_SEND_EXT_CSD	CMD8
+#define CMD_SEND_CSD	CMD9
+#define CMD_SEND_CID	CMD10
+#define CMD_STOP_TRANSMISSION	CMD12
+#define CMD_SEND_STATUS	CMD13
+#define CMD_BUS_TEST_R	CMD14
+#define CMD_GO_INACTIVE_STATE	CMD15
+#define CMD_SET_BLOCKLEN	CMD16
+#define CMD_READ_SINGLE_BLOCK	CMD17
+#define CMD_READ_MULTIPLE_BLOCK	CMD18
+#define CMD_WRITE_SINGLE_BLOCK	CMD24
+#define CMD_BUS_TEST_W	CMD19
+#define CMD_APP_CMD	CMD55
+#define CMD_GEN_CMD	CMD56
+#define CMD_SET_BUS_WIDTH	ACMD6
+#define CMD_SD_STATUS	ACMD13
+#define CMD_SD_SEND_OP_COND	ACMD41
+#define CMD_SET_CLR_CARD_DETECT	ACMD42
+#define CMD_SEND_SCR	ACMD51
+
+/* MMC card spec version */
+#define MMC_CARD_VERSION_1_2	0
+#define MMC_CARD_VERSION_1_4	1
+#define MMC_CARD_VERSION_2_X	2
+#define MMC_CARD_VERSION_3_X	3
+#define MMC_CARD_VERSION_4_X	4
+
+/* SD Card Spec Version */
+/* May need to add version 3 here? */
+#define SD_CARD_VERSION_1_0	0
+#define SD_CARD_VERSION_1_10	1
+#define SD_CARD_VERSION_2_0	2
+
+/* card types */
+#define MMC_CARD	0
+#define SD_CARD		1
+#define NOT_SD_CARD	MMC_CARD
+
+/* Card rca */
+#define SD_MMC_CARD_RCA	0x1
+#define BLOCK_LEN_512	512
+
+/* card state */
+#define STATE_IDLE	0
+#define STATE_READY	1
+#define STATE_IDENT	2
+#define STATE_STBY	3
+#define STATE_TRAN	4
+#define STATE_DATA	5
+#define STATE_RCV	6
+#define STATE_PRG	7
+#define STATE_DIS	8
+
+/* Card OCR register */
+/* VDD voltage window 1,65 to 1.95 */
+#define MMC_OCR_VDD_165_195	0x00000080
+/* VDD voltage window 2.7-2.8 */
+#define MMC_OCR_VDD_FF8	0x00FF8000
+#define MMC_OCR_CCS	0x40000000/* Card Capacity */
+#define MMC_OCR_BUSY	0x80000000/* busy bit */
+#define SD_OCR_HCS	0x40000000/* High capacity host */
+#define MMC_OCR_SECTOR_MODE	0x40000000/* Access Mode as Sector */
+
+/* mmc Switch function */
+#define SET_EXT_CSD_HS_TIMING	0x03B90100/* set High speed */
+
+/* check supports switching or not */
+#define SD_SWITCH_FUNC_CHECK_MODE	0x00FFFFF1
+#define SD_SWITCH_FUNC_SWITCH_MODE	0x80FFFFF1/* switch */
+#define SD_SWITCH_FUNC_HIGH_SPEED	0x02/* HIGH SPEED FUNC */
+#define SWITCH_ERROR		0x00000080
+
+/* errors in sending commands */
+#define RESP_TIMEOUT	0x1
+#define COMMAND_ERROR	0x2
+/* error in response */
+#define R1_ERROR	(1 << 19)
+#define R1_CURRENT_STATE(x)	(((x) & 0x00001E00) >> 9)
+
+/* Host Controller Capabilities */
+#define ESDHC_HOSTCAPBLT_DMAS           (0x00400000)
+
+
+/* SD/MMC memory map */
+struct esdhc_regs {
+	uint32_t dsaddr;	/* dma system address */
+	uint32_t blkattr;	/* Block attributes */
+	uint32_t cmdarg;	/* Command argument */
+	uint32_t xfertyp;	/* Command transfer type */
+	uint32_t cmdrsp[4];	/* Command response0,1,2,3 */
+	uint32_t datport;	/* Data buffer access port */
+	uint32_t prsstat;	/* Present state */
+	uint32_t proctl;	/* Protocol control */
+	uint32_t sysctl;	/* System control */
+	uint32_t irqstat;	/* Interrupt status */
+	uint32_t irqstaten;	/* Interrupt status enable */
+	uint32_t irqsigen;	/* Interrupt signal enable */
+	uint32_t autoc12err;	/* Auto CMD12 status */
+	uint32_t hostcapblt;	/* Host controller capabilities */
+	uint32_t wml;	/* Watermark level */
+	uint32_t res1[2];
+	uint32_t fevt;	/* Force event */
+	uint32_t res2;
+	uint32_t adsaddrl;
+	uint32_t adsaddrh;
+	uint32_t res3[39];
+	uint32_t hostver;	/* Host controller version */
+	uint32_t res4;
+	uint32_t dmaerr;	/* DMA error address */
+	uint32_t dmaerrh;	/* DMA error address high */
+	uint32_t dmaerrattr; /* DMA error atrribute */
+	uint32_t res5;
+	uint32_t hostcapblt2;/* Host controller capabilities2 */
+	uint32_t res6[2];
+	uint32_t tcr;	/* Tuning control */
+	uint32_t res7[7];
+	uint32_t dirctrl;	/* Direction control */
+	uint32_t ccr;	/* Clock control */
+	uint32_t res8[177];
+	uint32_t ctl;	/* Control register */
+};
+
+/* SD/MMC card attributes */
+struct card_attributes {
+	uint32_t type;	/* sd or mmc card */
+	uint32_t version;	/* version */
+	uint32_t block_len;	/* block length */
+	uint32_t bus_freq;	/* sdhc bus frequency */
+	uint16_t rca;	/* relative card address */
+	uint8_t is_high_capacity;	/* high capacity */
+};
+
+struct mmc {
+	struct esdhc_regs *esdhc_regs;
+	struct card_attributes card;
+
+	uint32_t block_len;
+	uint32_t voltages_caps;	/* supported voltaes */
+	uint32_t dma_support;	/* DMA support */
+};
+
+enum cntrl_num {
+	SDHC1 = 0,
+	SDHC2
+};
+
+int sd_emmc_init(uintptr_t *block_dev_spec,
+			uintptr_t nxp_esdhc_addr,
+			size_t nxp_sd_block_offset,
+			size_t nxp_sd_block_size,
+			bool card_detect);
+
+int esdhc_emmc_init(struct mmc *mmc, bool card_detect);
+int esdhc_read(struct mmc *mmc, uint32_t src_offset, uintptr_t dst,
+	       size_t size);
+int esdhc_write(struct mmc *mmc, uintptr_t src, uint32_t dst_offset,
+		size_t size);
+
+#ifdef NXP_ESDHC_BE
+#define esdhc_in32(a)           bswap32(mmio_read_32((uintptr_t)(a)))
+#define esdhc_out32(a, v)       mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_ESDHC_LE)
+#define esdhc_in32(a)           mmio_read_32((uintptr_t)(a))
+#define esdhc_out32(a, v)       mmio_write_32((uintptr_t)(a), (v))
+#else
+#error Please define CCSR ESDHC register endianness
+#endif
+
+#endif /*SD_MMC_H*/
diff --git a/include/drivers/nxp/sec_mon/snvs.h b/include/drivers/nxp/sec_mon/snvs.h
new file mode 100644
index 0000000..4455383
--- /dev/null
+++ b/include/drivers/nxp/sec_mon/snvs.h
@@ -0,0 +1,86 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SNVS_H
+#define SNVS_H
+
+
+#ifndef __ASSEMBLER__
+
+#include <endian.h>
+#include <stdbool.h>
+
+#include <lib/mmio.h>
+
+struct snvs_regs {
+	uint32_t reserved1;
+	uint32_t hp_com;		/* 0x04 SNVS_HP Command Register */
+	uint32_t reserved2[3];
+	uint32_t hp_stat;		/* 0x14 SNVS_HP Status Register */
+};
+
+#ifdef NXP_SNVS_BE
+#define snvs_read32(a)           bswap32(mmio_read_32((uintptr_t)(a)))
+#define snvs_write32(a, v)       mmio_write_32((uintptr_t)(a), bswap32((v)))
+#elif defined(NXP_SNVS_LE)
+#define snvs_read32(a)           mmio_read_32((uintptr_t)(a))
+#define snvs_write32(a, v)       mmio_write_32((uintptr_t)(a), (v))
+#else
+#error Please define CCSR SNVS register endianness
+#endif
+
+void snvs_init(uintptr_t nxp_snvs_addr);
+uint32_t get_snvs_state(void);
+void transition_snvs_non_secure(void);
+void transition_snvs_soft_fail(void);
+uint32_t transition_snvs_trusted(void);
+uint32_t transition_snvs_secure(void);
+
+uint32_t snvs_read_lp_gpr_bit(uint32_t offset, uint32_t bit_pos);
+void snvs_write_lp_gpr_bit(uint32_t offset, uint32_t bit_pos, bool flag_val);
+
+void snvs_disable_zeroize_lp_gpr(void);
+
+#if defined(NXP_NV_SW_MAINT_LAST_EXEC_DATA) && defined(NXP_COINED_BB)
+uint32_t snvs_read_app_data(void);
+uint32_t snvs_read_app_data_bit(uint32_t bit_pos);
+void snvs_clear_app_data(void);
+void snvs_write_app_data_bit(uint32_t bit_pos);
+#endif
+
+#endif	/*  __ASSEMBLER__  */
+
+/* SSM_ST field in SNVS status reg */
+#define HPSTS_CHECK_SSM_ST	0x900	/* SNVS is in check state */
+#define HPSTS_NON_SECURE_SSM_ST	0xb00	/* SNVS is in non secure state */
+#define HPSTS_TRUST_SSM_ST	0xd00	/* SNVS is in trusted state */
+#define HPSTS_SECURE_SSM_ST	0xf00	/* SNVS is in secure state */
+#define HPSTS_SOFT_FAIL_SSM_ST	0x300	/* SNVS is in soft fail state */
+#define HPSTS_MASK_SSM_ST	0xf00	/* SSM_ST field mask in SNVS reg */
+
+/* SNVS register bits */
+#define HPCOM_SW_SV		0x100	/* Security Violation bit */
+#define HPCOM_SW_FSV		0x200	/* Fatal Security Violation bit */
+#define HPCOM_SSM_ST		0x1	/* SSM_ST field in SNVS command reg */
+#define HPCOM_SSM_ST_DIS	0x2	/* Disable Secure to Trusted State */
+#define HPCOM_SSM_SFNS_DIS	0x4	/* Disable Soft Fail to Non-Secure */
+
+#define NXP_LP_GPR0_OFFSET	0x90
+#define NXP_LPCR_OFFSET		0x38
+#define NXP_GPR_Z_DIS_BIT	24
+
+#ifdef NXP_COINED_BB
+
+#ifndef NXP_APP_DATA_LP_GPR_OFFSET
+#define NXP_APP_DATA_LP_GPR_OFFSET NXP_LP_GPR0_OFFSET
+#endif
+
+#define NXP_LPGPR_ZEROTH_BIT		0
+
+#endif	/* NXP_COINED_BB */
+
+#endif	/* SNVS_H  */
diff --git a/include/drivers/nxp/sfp/fuse_prov.h b/include/drivers/nxp/sfp/fuse_prov.h
new file mode 100644
index 0000000..e015318
--- /dev/null
+++ b/include/drivers/nxp/sfp/fuse_prov.h
@@ -0,0 +1,83 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#if !defined(FUSE_PROV_H) && defined(POLICY_FUSE_PROVISION)
+#define FUSE_PROV_H
+
+#include <endian.h>
+#include <lib/mmio.h>
+
+#define MASK_NONE		U(0xFFFFFFFF)
+#define ERROR_WRITE		U(0xA)
+#define ERROR_ALREADY_BLOWN	U(0xB)
+
+/* Flag bit shifts */
+#define FLAG_POVDD_SHIFT	U(0)
+#define FLAG_SYSCFG_SHIFT	U(1)
+#define FLAG_SRKH_SHIFT		U(2)
+#define FLAG_MC_SHIFT		U(3)
+#define FLAG_DCV0_SHIFT		U(4)
+#define FLAG_DCV1_SHIFT		U(5)
+#define FLAG_DRV0_SHIFT		U(6)
+#define FLAG_DRV1_SHIFT		U(7)
+#define FLAG_OUID0_SHIFT	U(8)
+#define FLAG_OUID1_SHIFT	U(9)
+#define FLAG_OUID2_SHIFT	U(10)
+#define FLAG_OUID3_SHIFT	U(11)
+#define FLAG_OUID4_SHIFT	U(12)
+#define FLAG_DBG_LVL_SHIFT	U(13)
+#define FLAG_OTPMK_SHIFT	U(16)
+#define FLAG_OUID_MASK		U(0x1F)
+#define FLAG_DEBUG_MASK		U(0xF)
+#define FLAG_OTPMK_MASK		U(0xF)
+
+/* OTPMK flag values */
+#define PROG_OTPMK_MIN		U(0x0)
+#define PROG_OTPMK_RANDOM	U(0x1)
+#define PROG_OTPMK_USER		U(0x2)
+#define PROG_OTPMK_RANDOM_MIN	U(0x5)
+#define PROG_OTPMK_USER_MIN	U(0x6)
+#define PROG_NO_OTPMK		U(0x8)
+
+#define OTPMK_MIM_BITS_MASK	U(0xF0000000)
+
+/* System configuration bit shifts */
+#define SCB_WP_SHIFT		U(0)
+#define SCB_ITS_SHIFT		U(2)
+#define SCB_NSEC_SHIFT		U(4)
+#define SCB_ZD_SHIFT		U(5)
+#define SCB_K0_SHIFT		U(15)
+#define SCB_K1_SHIFT		U(14)
+#define SCB_K2_SHIFT		U(13)
+#define SCB_K3_SHIFT		U(12)
+#define SCB_K4_SHIFT		U(11)
+#define SCB_K5_SHIFT		U(10)
+#define SCB_K6_SHIFT		U(9)
+#define SCB_FR0_SHIFT		U(30)
+#define SCB_FR1_SHIFT		U(31)
+
+/* Fuse Header Structure */
+struct fuse_hdr_t {
+	uint8_t barker[4];          /* 0x00 Barker code */
+	uint32_t flags;             /* 0x04 Script flags */
+	uint32_t povdd_gpio;        /* 0x08 GPIO for POVDD */
+	uint32_t otpmk[8];          /* 0x0C-0x2B OTPMK */
+	uint32_t srkh[8];           /* 0x2C-0x4B SRKH */
+	uint32_t oem_uid[5];        /* 0x4C-0x5F OEM unique id's */
+	uint32_t dcv[2];            /* 0x60-0x67 Debug Challenge */
+	uint32_t drv[2];            /* 0x68-0x6F Debug Response */
+	uint32_t ospr1;             /* 0x70 OSPR1 */
+	uint32_t sc;                /* 0x74 OSPR0 (System Configuration) */
+	uint32_t reserved[2];       /* 0x78-0x7F Reserved */
+};
+
+/* Function to do fuse provisioning */
+int provision_fuses(unsigned long long fuse_scr_addr,
+		    bool en_povdd_status);
+
+#define EFUSE_POWERUP_DELAY_mSec	U(25)
+#endif	/* FUSE_PROV_H  */
diff --git a/include/drivers/nxp/sfp/sfp.h b/include/drivers/nxp/sfp/sfp.h
new file mode 100644
index 0000000..2cb4c7d
--- /dev/null
+++ b/include/drivers/nxp/sfp/sfp.h
@@ -0,0 +1,100 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SFP_H
+#define SFP_H
+
+#include <endian.h>
+#include <lib/mmio.h>
+
+/* SFP Configuration Register Offsets */
+#define SFP_INGR_OFFSET		U(0x20)
+#define SFP_SVHESR_OFFSET	U(0x24)
+#define SFP_SFPCR_OFFSET	U(0x28)
+#define SFP_VER_OFFSET		U(0x38)
+
+/* SFP Hamming register masks for OTPMK and DRV */
+#define SFP_SVHESR_DRV_MASK	U(0x7F)
+#define SFP_SVHESR_OTPMK_MASK	U(0x7FC00)
+
+/* SFP commands */
+#define SFP_INGR_READFB_CMD	U(0x1)
+#define SFP_INGR_PROGFB_CMD	U(0x2)
+#define SFP_INGR_ERROR_MASK	U(0x100)
+
+/* SFPCR Masks */
+#define SFP_SFPCR_WD		U(0x80000000)
+#define SFP_SFPCR_WDL		U(0x40000000)
+
+/* SFPCR Masks */
+#define SFP_SFPCR_WD		U(0x80000000)
+#define SFP_SFPCR_WDL		U(0x40000000)
+
+#define SFP_FUSE_REGS_OFFSET	U(0x200)
+
+#ifdef NXP_SFP_VER_3_4
+#define OSPR0_SC_MASK		U(0xC000FE35)
+#elif defined(NXP_SFP_VER_3_2)
+#define OSPR0_SC_MASK		U(0x0000E035)
+#endif
+
+#if defined(NXP_SFP_VER_3_4)
+#define OSPR_KEY_REVOC_SHIFT	U(9)
+#define OSPR_KEY_REVOC_MASK	U(0x0000fe00)
+#elif defined(NXP_SFP_VER_3_2)
+#define OSPR_KEY_REVOC_SHIFT	U(13)
+#define OSPR_KEY_REVOC_MASK	U(0x0000e000)
+#endif /* NXP_SFP_VER_3_4 */
+
+#define OSPR1_MC_MASK		U(0xFFFF0000)
+#define OSPR1_DBG_LVL_MASK	U(0x00000007)
+
+#define OSPR_ITS_MASK		U(0x00000004)
+#define OSPR_WP_MASK		U(0x00000001)
+
+#define MAX_OEM_UID		U(5)
+#define SRK_HASH_SIZE		U(32)
+
+/* SFP CCSR Register Map */
+struct sfp_ccsr_regs_t {
+	uint32_t ospr;			/* 0x200 OSPR0 */
+	uint32_t ospr1;			/* 0x204 OSPR1 */
+	uint32_t dcv[2];		/* 0x208 Debug Challenge Value */
+	uint32_t drv[2];		/* 0x210 Debug Response Value */
+	uint32_t fswpr;			/* 0x218 FSL Section Write Protect */
+	uint32_t fsl_uid[2];		/* 0x21c FSL UID 0 */
+	uint32_t isbcr;			/* 0x224 ISBC Configuration */
+	uint32_t fsspr[3];		/* 0x228 FSL Scratch Pad */
+	uint32_t otpmk[8];		/* 0x234 OTPMK */
+	uint32_t srk_hash[SRK_HASH_SIZE/sizeof(uint32_t)];
+					/* 0x254 Super Root Key Hash */
+	uint32_t oem_uid[MAX_OEM_UID];	/* 0x274 OEM UID 0 */
+};
+
+uintptr_t get_sfp_addr(void);
+void sfp_init(uintptr_t nxp_sfp_addr);
+uint32_t *get_sfp_srk_hash(void);
+int sfp_check_its(void);
+int sfp_check_oem_wp(void);
+uint32_t get_key_revoc(void);
+void set_sfp_wr_disable(void);
+int sfp_program_fuses(void);
+
+uint32_t sfp_read_oem_uid(uint8_t oem_uid);
+uint32_t sfp_write_oem_uid(uint8_t oem_uid, uint32_t sfp_val);
+
+#ifdef NXP_SFP_BE
+#define sfp_read32(a)           bswap32(mmio_read_32((uintptr_t)(a)))
+#define sfp_write32(a, v)       mmio_write_32((uintptr_t)(a), bswap32(v))
+#elif defined(NXP_SFP_LE)
+#define sfp_read32(a)           mmio_read_32((uintptr_t)(a))
+#define sfp_write32(a, v)       mmio_write_32((uintptr_t)(a), (v))
+#else
+#error Please define CCSR SFP register endianness
+#endif
+
+#endif/* SFP_H */
diff --git a/include/drivers/nxp/sfp/sfp_error_codes.h b/include/drivers/nxp/sfp/sfp_error_codes.h
new file mode 100644
index 0000000..7be7a27
--- /dev/null
+++ b/include/drivers/nxp/sfp/sfp_error_codes.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SFP_ERROR_CODES_H
+#define SFP_ERROR_CODES_H
+
+ /* Error codes */
+#define ERROR_FUSE_BARKER		0x1
+#define ERROR_READFB_CMD		0x2
+#define ERROR_PROGFB_CMD		0x3
+#define ERROR_SRKH_ALREADY_BLOWN	0x4
+#define ERROR_SRKH_WRITE		0x5
+#define ERROR_OEMUID_ALREADY_BLOWN	0x6
+#define ERROR_OEMUID_WRITE		0x7
+#define ERROR_DCV_ALREADY_BLOWN		0x8
+#define ERROR_DCV_WRITE			0x9
+#define ERROR_DRV_ALREADY_BLOWN		0xa
+#define ERROR_DRV_HAMMING_ERROR		0xb
+#define ERROR_DRV_WRITE			0x18
+#define ERROR_OTPMK_ALREADY_BLOWN	0xc
+#define ERROR_OTPMK_HAMMING_ERROR	0xd
+#define ERROR_OTPMK_USER_MIN		0xe
+#define ERROR_OSPR1_ALREADY_BLOWN	0xf
+#define ERROR_OSPR1_WRITE		0x10
+#define ERROR_SC_ALREADY_BLOWN		0x11
+#define ERROR_SC_WRITE			0x12
+#define ERROR_POVDD_GPIO_FAIL		0x13
+#define ERROR_GPIO_SET_FAIL		0x14
+#define ERROR_GPIO_RESET_FAIL		0x15
+#define ERROR_OTPMK_SEC_DISABLED	0x16
+#define ERROR_OTPMK_SEC_ERROR		0x17
+#define ERROR_OTPMK_WRITE		0x19
+#define PLAT_ERROR_ENABLE_POVDD		0x20
+#define PLAT_ERROR_DISABLE_POVDD	0x21
+
+#endif /* SFP_ERROR_CODES_H */
diff --git a/include/drivers/nxp/smmu/nxp_smmu.h b/include/drivers/nxp/smmu/nxp_smmu.h
new file mode 100644
index 0000000..d64c33b
--- /dev/null
+++ b/include/drivers/nxp/smmu/nxp_smmu.h
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef NXP_SMMU_H
+#define NXP_SMMU_H
+
+#define SMMU_SCR0		(0x0)
+#define SMMU_NSCR0		(0x400)
+
+#define SCR0_CLIENTPD_MASK	0x00000001
+#define SCR0_USFCFG_MASK	0x00000400
+
+static inline void bypass_smmu(uintptr_t smmu_base_addr)
+{
+	uint32_t val;
+
+	val = (mmio_read_32(smmu_base_addr + SMMU_SCR0) | SCR0_CLIENTPD_MASK) &
+		~(SCR0_USFCFG_MASK);
+	mmio_write_32((smmu_base_addr + SMMU_SCR0), val);
+
+	val = (mmio_read_32(smmu_base_addr + SMMU_NSCR0) | SCR0_CLIENTPD_MASK) &
+		~(SCR0_USFCFG_MASK);
+	mmio_write_32((smmu_base_addr + SMMU_NSCR0), val);
+}
+
+#endif
diff --git a/include/drivers/nxp/timer/nxp_timer.h b/include/drivers/nxp/timer/nxp_timer.h
new file mode 100644
index 0000000..280e5b2
--- /dev/null
+++ b/include/drivers/nxp/timer/nxp_timer.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#
+#ifndef NXP_TIMER_H
+#define NXP_TIMER_H
+
+ /* System Counter Offset and Bit Mask */
+#define SYS_COUNTER_CNTCR_OFFSET	0x0
+#define SYS_COUNTER_CNTCR_EN		0x00000001
+#define CNTCR_EN_MASK			0x1
+
+#ifndef __ASSEMBLER__
+uint64_t get_timer_val(uint64_t start);
+
+#ifdef IMAGE_BL31
+void ls_configure_sys_timer(uintptr_t ls_sys_timctl_base,
+			    uint8_t ls_config_cntacr,
+			    uint8_t plat_ls_ns_timer_frame_id);
+void enable_init_timer(void);
+#endif
+
+/*
+ * Initialise the nxp on-chip free rolling usec counter as the delay
+ * timer.
+ */
+void delay_timer_init(uintptr_t nxp_timer_addr);
+void ls_bl31_timer_init(uintptr_t nxp_timer_addr);
+#endif	/* __ASSEMBLER__ */
+
+#endif /* NXP_TIMER_H */
diff --git a/include/drivers/nxp/tzc/plat_tzc400.h b/include/drivers/nxp/tzc/plat_tzc400.h
new file mode 100644
index 0000000..1b8e3a4
--- /dev/null
+++ b/include/drivers/nxp/tzc/plat_tzc400.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#if !defined(PLAT_TZC400_H) && defined(IMAGE_BL2)
+#define PLAT_TZC400_H
+
+#include <tzc400.h>
+
+/* Structure to configure TZC Regions' boundaries and attributes. */
+struct tzc400_reg {
+	uint8_t reg_filter_en;
+	unsigned long long start_addr;
+	unsigned long long end_addr;
+	unsigned int sec_attr;
+	unsigned int nsaid_permissions;
+};
+
+#define TZC_REGION_NS_NONE	0x00000000U
+
+/* NXP Platforms do not support NS Access ID (NSAID) based non-secure access.
+ * Supports only non secure through generic NS ACCESS ID
+ */
+#define TZC_NS_ACCESS_ID	0xFFFFFFFFU
+
+/* Number of DRAM regions to be configured
+ * for the platform can be over-written.
+ *
+ * Array tzc400_reg_list too, needs be over-written
+ * if there is any changes to default DRAM region
+ * configuration.
+ */
+#ifndef MAX_NUM_TZC_REGION
+/* 3 regions:
+ *  Region 0(default),
+ *  Region 1 (DRAM0, Secure Memory),
+ *  Region 2 (DRAM0, Shared memory)
+ */
+#define MAX_NUM_TZC_REGION	NUM_DRAM_REGIONS + 3
+#define DEFAULT_TZASC_CONFIG	1
+#endif
+
+void mem_access_setup(uintptr_t base, uint32_t total_regions,
+		      struct tzc400_reg *tzc400_reg_list);
+int populate_tzc400_reg_list(struct tzc400_reg *tzc400_reg_list,
+			     int dram_idx, int list_idx,
+			     uint64_t dram_start_addr,
+			     uint64_t dram_size,
+			     uint32_t secure_dram_sz,
+			     uint32_t shrd_dram_sz);
+
+#endif /* PLAT_TZC400_H */
diff --git a/include/drivers/rambus/trng_ip_76.h b/include/drivers/rambus/trng_ip_76.h
new file mode 100644
index 0000000..6de8fc7
--- /dev/null
+++ b/include/drivers/rambus/trng_ip_76.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright (c) 2020, Marvell Technology Group Ltd. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+
+#ifndef __TRNG_IP_76_H__
+#define __TRNG_IP_76_H__
+
+#include <stdbool.h>
+#include <stdint.h>
+
+int32_t eip76_rng_read_rand_buf(void *data, bool wait);
+int32_t eip76_rng_probe(uintptr_t base_addr);
+int32_t eip76_rng_get_random(uint8_t *data, uint32_t len);
+
+#endif /* __TRNG_IP_76_H__ */
diff --git a/include/drivers/st/scmi-msg.h b/include/drivers/scmi-msg.h
similarity index 100%
rename from include/drivers/st/scmi-msg.h
rename to include/drivers/scmi-msg.h
diff --git a/include/drivers/st/scmi.h b/include/drivers/scmi.h
similarity index 100%
rename from include/drivers/st/scmi.h
rename to include/drivers/scmi.h
diff --git a/include/drivers/st/io_mmc.h b/include/drivers/st/io_mmc.h
index b35b4b5..6179e89 100644
--- a/include/drivers/st/io_mmc.h
+++ b/include/drivers/st/io_mmc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,6 +9,10 @@
 
 #include <drivers/io/io_driver.h>
 
+struct io_mmc_dev_spec {
+	bool use_boot_part;
+};
+
 int register_io_dev_mmc(const io_dev_connector_t **dev_con);
 
 #endif /* IO_MMC_H */
diff --git a/include/drivers/st/stm32mp1_ddr_regs.h b/include/drivers/st/stm32mp1_ddr_regs.h
index 342239a..01d6638 100644
--- a/include/drivers/st/stm32mp1_ddr_regs.h
+++ b/include/drivers/st/stm32mp1_ddr_regs.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause
  */
@@ -284,7 +284,7 @@
 #define DDRCTRL_PWRCTL_EN_DFI_DRAM_CLK_DISABLE	BIT(3)
 #define DDRCTRL_PWRCTL_SELFREF_SW		BIT(5)
 
-#define DDRCTRL_PWRTMG_SELFREF_TO_X32_MASK	GENMASK(19, 12)
+#define DDRCTRL_PWRTMG_SELFREF_TO_X32_MASK	GENMASK(23, 16)
 #define DDRCTRL_PWRTMG_SELFREF_TO_X32_0		BIT(16)
 
 #define DDRCTRL_RFSHCTL3_DIS_AUTO_REFRESH	BIT(0)
diff --git a/include/drivers/st/stm32mp1_rcc.h b/include/drivers/st/stm32mp1_rcc.h
index 2ffc3b2..14f93fd 100644
--- a/include/drivers/st/stm32mp1_rcc.h
+++ b/include/drivers/st/stm32mp1_rcc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2015-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,488 +9,397 @@
 
 #include <lib/utils_def.h>
 
-#define RCC_TZCR			U(0x00)
-#define RCC_OCENSETR			U(0x0C)
-#define RCC_OCENCLRR			U(0x10)
-#define RCC_HSICFGR			U(0x18)
-#define RCC_CSICFGR			U(0x1C)
-#define RCC_MPCKSELR			U(0x20)
-#define RCC_ASSCKSELR			U(0x24)
-#define RCC_RCK12SELR			U(0x28)
-#define RCC_MPCKDIVR			U(0x2C)
-#define RCC_AXIDIVR			U(0x30)
-#define RCC_APB4DIVR			U(0x3C)
-#define RCC_APB5DIVR			U(0x40)
-#define RCC_RTCDIVR			U(0x44)
-#define RCC_MSSCKSELR			U(0x48)
-#define RCC_PLL1CR			U(0x80)
-#define RCC_PLL1CFGR1			U(0x84)
-#define RCC_PLL1CFGR2			U(0x88)
-#define RCC_PLL1FRACR			U(0x8C)
-#define RCC_PLL1CSGR			U(0x90)
-#define RCC_PLL2CR			U(0x94)
-#define RCC_PLL2CFGR1			U(0x98)
-#define RCC_PLL2CFGR2			U(0x9C)
-#define RCC_PLL2FRACR			U(0xA0)
-#define RCC_PLL2CSGR			U(0xA4)
-#define RCC_I2C46CKSELR			U(0xC0)
-#define RCC_SPI6CKSELR			U(0xC4)
-#define RCC_UART1CKSELR			U(0xC8)
-#define RCC_RNG1CKSELR			U(0xCC)
-#define RCC_CPERCKSELR			U(0xD0)
-#define RCC_STGENCKSELR			U(0xD4)
-#define RCC_DDRITFCR			U(0xD8)
-#define RCC_MP_BOOTCR			U(0x100)
-#define RCC_MP_SREQSETR			U(0x104)
-#define RCC_MP_SREQCLRR			U(0x108)
-#define RCC_MP_GCR			U(0x10C)
-#define RCC_MP_APRSTCR			U(0x110)
-#define RCC_MP_APRSTSR			U(0x114)
-#define RCC_BDCR			U(0x140)
-#define RCC_RDLSICR			U(0x144)
-#define RCC_APB4RSTSETR			U(0x180)
-#define RCC_APB4RSTCLRR			U(0x184)
-#define RCC_APB5RSTSETR			U(0x188)
-#define RCC_APB5RSTCLRR			U(0x18C)
-#define RCC_AHB5RSTSETR			U(0x190)
-#define RCC_AHB5RSTCLRR			U(0x194)
-#define RCC_AHB6RSTSETR			U(0x198)
-#define RCC_AHB6RSTCLRR			U(0x19C)
-#define RCC_TZAHB6RSTSETR		U(0x1A0)
-#define RCC_TZAHB6RSTCLRR		U(0x1A4)
-#define RCC_MP_APB4ENSETR		U(0x200)
-#define RCC_MP_APB4ENCLRR		U(0x204)
-#define RCC_MP_APB5ENSETR		U(0x208)
-#define RCC_MP_APB5ENCLRR		U(0x20C)
-#define RCC_MP_AHB5ENSETR		U(0x210)
-#define RCC_MP_AHB5ENCLRR		U(0x214)
-#define RCC_MP_AHB6ENSETR		U(0x218)
-#define RCC_MP_AHB6ENCLRR		U(0x21C)
-#define RCC_MP_TZAHB6ENSETR		U(0x220)
-#define RCC_MP_TZAHB6ENCLRR		U(0x224)
-#define RCC_MC_APB4ENSETR		U(0x280)
-#define RCC_MC_APB4ENCLRR		U(0x284)
-#define RCC_MC_APB5ENSETR		U(0x288)
-#define RCC_MC_APB5ENCLRR		U(0x28C)
-#define RCC_MC_AHB5ENSETR		U(0x290)
-#define RCC_MC_AHB5ENCLRR		U(0x294)
-#define RCC_MC_AHB6ENSETR		U(0x298)
-#define RCC_MC_AHB6ENCLRR		U(0x29C)
-#define RCC_MP_APB4LPENSETR		U(0x300)
-#define RCC_MP_APB4LPENCLRR		U(0x304)
-#define RCC_MP_APB5LPENSETR		U(0x308)
-#define RCC_MP_APB5LPENCLRR		U(0x30C)
-#define RCC_MP_AHB5LPENSETR		U(0x310)
-#define RCC_MP_AHB5LPENCLRR		U(0x314)
-#define RCC_MP_AHB6LPENSETR		U(0x318)
-#define RCC_MP_AHB6LPENCLRR		U(0x31C)
-#define RCC_MP_TZAHB6LPENSETR		U(0x320)
-#define RCC_MP_TZAHB6LPENCLRR		U(0x324)
-#define RCC_MC_APB4LPENSETR		U(0x380)
-#define RCC_MC_APB4LPENCLRR		U(0x384)
-#define RCC_MC_APB5LPENSETR		U(0x388)
-#define RCC_MC_APB5LPENCLRR		U(0x38C)
-#define RCC_MC_AHB5LPENSETR		U(0x390)
-#define RCC_MC_AHB5LPENCLRR		U(0x394)
-#define RCC_MC_AHB6LPENSETR		U(0x398)
-#define RCC_MC_AHB6LPENCLRR		U(0x39C)
-#define RCC_BR_RSTSCLRR			U(0x400)
-#define RCC_MP_GRSTCSETR		U(0x404)
-#define RCC_MP_RSTSCLRR			U(0x408)
-#define RCC_MP_IWDGFZSETR		U(0x40C)
-#define RCC_MP_IWDGFZCLRR		U(0x410)
-#define RCC_MP_CIER			U(0x414)
-#define RCC_MP_CIFR			U(0x418)
-#define RCC_PWRLPDLYCR			U(0x41C)
-#define RCC_MP_RSTSSETR			U(0x420)
-#define RCC_MCO1CFGR			U(0x800)
-#define RCC_MCO2CFGR			U(0x804)
-#define RCC_OCRDYR			U(0x808)
-#define RCC_DBGCFGR			U(0x80C)
-#define RCC_RCK3SELR			U(0x820)
-#define RCC_RCK4SELR			U(0x824)
-#define RCC_TIMG1PRER			U(0x828)
-#define RCC_TIMG2PRER			U(0x82C)
-#define RCC_MCUDIVR			U(0x830)
-#define RCC_APB1DIVR			U(0x834)
-#define RCC_APB2DIVR			U(0x838)
-#define RCC_APB3DIVR			U(0x83C)
-#define RCC_PLL3CR			U(0x880)
-#define RCC_PLL3CFGR1			U(0x884)
-#define RCC_PLL3CFGR2			U(0x888)
-#define RCC_PLL3FRACR			U(0x88C)
-#define RCC_PLL3CSGR			U(0x890)
-#define RCC_PLL4CR			U(0x894)
-#define RCC_PLL4CFGR1			U(0x898)
-#define RCC_PLL4CFGR2			U(0x89C)
-#define RCC_PLL4FRACR			U(0x8A0)
-#define RCC_PLL4CSGR			U(0x8A4)
-#define RCC_I2C12CKSELR			U(0x8C0)
-#define RCC_I2C35CKSELR			U(0x8C4)
-#define RCC_SAI1CKSELR			U(0x8C8)
-#define RCC_SAI2CKSELR			U(0x8CC)
-#define RCC_SAI3CKSELR			U(0x8D0)
-#define RCC_SAI4CKSELR			U(0x8D4)
-#define RCC_SPI2S1CKSELR		U(0x8D8)
-#define RCC_SPI2S23CKSELR		U(0x8DC)
-#define RCC_SPI45CKSELR			U(0x8E0)
-#define RCC_UART6CKSELR			U(0x8E4)
-#define RCC_UART24CKSELR		U(0x8E8)
-#define RCC_UART35CKSELR		U(0x8EC)
-#define RCC_UART78CKSELR		U(0x8F0)
-#define RCC_SDMMC12CKSELR		U(0x8F4)
-#define RCC_SDMMC3CKSELR		U(0x8F8)
-#define RCC_ETHCKSELR			U(0x8FC)
-#define RCC_QSPICKSELR			U(0x900)
-#define RCC_FMCCKSELR			U(0x904)
-#define RCC_FDCANCKSELR			U(0x90C)
-#define RCC_SPDIFCKSELR			U(0x914)
-#define RCC_CECCKSELR			U(0x918)
-#define RCC_USBCKSELR			U(0x91C)
-#define RCC_RNG2CKSELR			U(0x920)
-#define RCC_DSICKSELR			U(0x924)
-#define RCC_ADCCKSELR			U(0x928)
-#define RCC_LPTIM45CKSELR		U(0x92C)
-#define RCC_LPTIM23CKSELR		U(0x930)
-#define RCC_LPTIM1CKSELR		U(0x934)
-#define RCC_APB1RSTSETR			U(0x980)
-#define RCC_APB1RSTCLRR			U(0x984)
-#define RCC_APB2RSTSETR			U(0x988)
-#define RCC_APB2RSTCLRR			U(0x98C)
-#define RCC_APB3RSTSETR			U(0x990)
-#define RCC_APB3RSTCLRR			U(0x994)
-#define RCC_AHB2RSTSETR			U(0x998)
-#define RCC_AHB2RSTCLRR			U(0x99C)
-#define RCC_AHB3RSTSETR			U(0x9A0)
-#define RCC_AHB3RSTCLRR			U(0x9A4)
-#define RCC_AHB4RSTSETR			U(0x9A8)
-#define RCC_AHB4RSTCLRR			U(0x9AC)
-#define RCC_MP_APB1ENSETR		U(0xA00)
-#define RCC_MP_APB1ENCLRR		U(0xA04)
-#define RCC_MP_APB2ENSETR		U(0xA08)
-#define RCC_MP_APB2ENCLRR		U(0xA0C)
-#define RCC_MP_APB3ENSETR		U(0xA10)
-#define RCC_MP_APB3ENCLRR		U(0xA14)
-#define RCC_MP_AHB2ENSETR		U(0xA18)
-#define RCC_MP_AHB2ENCLRR		U(0xA1C)
-#define RCC_MP_AHB3ENSETR		U(0xA20)
-#define RCC_MP_AHB3ENCLRR		U(0xA24)
-#define RCC_MP_AHB4ENSETR		U(0xA28)
-#define RCC_MP_AHB4ENCLRR		U(0xA2C)
-#define RCC_MP_MLAHBENSETR		U(0xA38)
-#define RCC_MP_MLAHBENCLRR		U(0xA3C)
-#define RCC_MC_APB1ENSETR		U(0xA80)
-#define RCC_MC_APB1ENCLRR		U(0xA84)
-#define RCC_MC_APB2ENSETR		U(0xA88)
-#define RCC_MC_APB2ENCLRR		U(0xA8C)
-#define RCC_MC_APB3ENSETR		U(0xA90)
-#define RCC_MC_APB3ENCLRR		U(0xA94)
-#define RCC_MC_AHB2ENSETR		U(0xA98)
-#define RCC_MC_AHB2ENCLRR		U(0xA9C)
-#define RCC_MC_AHB3ENSETR		U(0xAA0)
-#define RCC_MC_AHB3ENCLRR		U(0xAA4)
-#define RCC_MC_AHB4ENSETR		U(0xAA8)
-#define RCC_MC_AHB4ENCLRR		U(0xAAC)
-#define RCC_MC_AXIMENSETR		U(0xAB0)
-#define RCC_MC_AXIMENCLRR		U(0xAB4)
-#define RCC_MC_MLAHBENSETR		U(0xAB8)
-#define RCC_MC_MLAHBENCLRR		U(0xABC)
-#define RCC_MP_APB1LPENSETR		U(0xB00)
-#define RCC_MP_APB1LPENCLRR		U(0xB04)
-#define RCC_MP_APB2LPENSETR		U(0xB08)
-#define RCC_MP_APB2LPENCLRR		U(0xB0C)
-#define RCC_MP_APB3LPENSETR		U(0xB10)
-#define RCC_MP_APB3LPENCLRR		U(0xB14)
-#define RCC_MP_AHB2LPENSETR		U(0xB18)
-#define RCC_MP_AHB2LPENCLRR		U(0xB1C)
-#define RCC_MP_AHB3LPENSETR		U(0xB20)
-#define RCC_MP_AHB3LPENCLRR		U(0xB24)
-#define RCC_MP_AHB4LPENSETR		U(0xB28)
-#define RCC_MP_AHB4LPENCLRR		U(0xB2C)
-#define RCC_MP_AXIMLPENSETR		U(0xB30)
-#define RCC_MP_AXIMLPENCLRR		U(0xB34)
-#define RCC_MP_MLAHBLPENSETR		U(0xB38)
-#define RCC_MP_MLAHBLPENCLRR		U(0xB3C)
-#define RCC_MC_APB1LPENSETR		U(0xB80)
-#define RCC_MC_APB1LPENCLRR		U(0xB84)
-#define RCC_MC_APB2LPENSETR		U(0xB88)
-#define RCC_MC_APB2LPENCLRR		U(0xB8C)
-#define RCC_MC_APB3LPENSETR		U(0xB90)
-#define RCC_MC_APB3LPENCLRR		U(0xB94)
-#define RCC_MC_AHB2LPENSETR		U(0xB98)
-#define RCC_MC_AHB2LPENCLRR		U(0xB9C)
-#define RCC_MC_AHB3LPENSETR		U(0xBA0)
-#define RCC_MC_AHB3LPENCLRR		U(0xBA4)
-#define RCC_MC_AHB4LPENSETR		U(0xBA8)
-#define RCC_MC_AHB4LPENCLRR		U(0xBAC)
-#define RCC_MC_AXIMLPENSETR		U(0xBB0)
-#define RCC_MC_AXIMLPENCLRR		U(0xBB4)
-#define RCC_MC_MLAHBLPENSETR		U(0xBB8)
-#define RCC_MC_MLAHBLPENCLRR		U(0xBBC)
-#define RCC_MC_RSTSCLRR			U(0xC00)
-#define RCC_MC_CIER			U(0xC14)
-#define RCC_MC_CIFR			U(0xC18)
-#define RCC_VERR			U(0xFF4)
-#define RCC_IDR				U(0xFF8)
-#define RCC_SIDR			U(0xFFC)
+#define RCC_TZCR				U(0x00)
+#define RCC_OCENSETR				U(0x0C)
+#define RCC_OCENCLRR				U(0x10)
+#define RCC_HSICFGR				U(0x18)
+#define RCC_CSICFGR				U(0x1C)
+#define RCC_MPCKSELR				U(0x20)
+#define RCC_ASSCKSELR				U(0x24)
+#define RCC_RCK12SELR				U(0x28)
+#define RCC_MPCKDIVR				U(0x2C)
+#define RCC_AXIDIVR				U(0x30)
+#define RCC_APB4DIVR				U(0x3C)
+#define RCC_APB5DIVR				U(0x40)
+#define RCC_RTCDIVR				U(0x44)
+#define RCC_MSSCKSELR				U(0x48)
+#define RCC_PLL1CR				U(0x80)
+#define RCC_PLL1CFGR1				U(0x84)
+#define RCC_PLL1CFGR2				U(0x88)
+#define RCC_PLL1FRACR				U(0x8C)
+#define RCC_PLL1CSGR				U(0x90)
+#define RCC_PLL2CR				U(0x94)
+#define RCC_PLL2CFGR1				U(0x98)
+#define RCC_PLL2CFGR2				U(0x9C)
+#define RCC_PLL2FRACR				U(0xA0)
+#define RCC_PLL2CSGR				U(0xA4)
+#define RCC_I2C46CKSELR				U(0xC0)
+#define RCC_SPI6CKSELR				U(0xC4)
+#define RCC_UART1CKSELR				U(0xC8)
+#define RCC_RNG1CKSELR				U(0xCC)
+#define RCC_CPERCKSELR				U(0xD0)
+#define RCC_STGENCKSELR				U(0xD4)
+#define RCC_DDRITFCR				U(0xD8)
+#define RCC_MP_BOOTCR				U(0x100)
+#define RCC_MP_SREQSETR				U(0x104)
+#define RCC_MP_SREQCLRR				U(0x108)
+#define RCC_MP_GCR				U(0x10C)
+#define RCC_MP_APRSTCR				U(0x110)
+#define RCC_MP_APRSTSR				U(0x114)
+#define RCC_BDCR				U(0x140)
+#define RCC_RDLSICR				U(0x144)
+#define RCC_APB4RSTSETR				U(0x180)
+#define RCC_APB4RSTCLRR				U(0x184)
+#define RCC_APB5RSTSETR				U(0x188)
+#define RCC_APB5RSTCLRR				U(0x18C)
+#define RCC_AHB5RSTSETR				U(0x190)
+#define RCC_AHB5RSTCLRR				U(0x194)
+#define RCC_AHB6RSTSETR				U(0x198)
+#define RCC_AHB6RSTCLRR				U(0x19C)
+#define RCC_TZAHB6RSTSETR			U(0x1A0)
+#define RCC_TZAHB6RSTCLRR			U(0x1A4)
+#define RCC_MP_APB4ENSETR			U(0x200)
+#define RCC_MP_APB4ENCLRR			U(0x204)
+#define RCC_MP_APB5ENSETR			U(0x208)
+#define RCC_MP_APB5ENCLRR			U(0x20C)
+#define RCC_MP_AHB5ENSETR			U(0x210)
+#define RCC_MP_AHB5ENCLRR			U(0x214)
+#define RCC_MP_AHB6ENSETR			U(0x218)
+#define RCC_MP_AHB6ENCLRR			U(0x21C)
+#define RCC_MP_TZAHB6ENSETR			U(0x220)
+#define RCC_MP_TZAHB6ENCLRR			U(0x224)
+#define RCC_MC_APB4ENSETR			U(0x280)
+#define RCC_MC_APB4ENCLRR			U(0x284)
+#define RCC_MC_APB5ENSETR			U(0x288)
+#define RCC_MC_APB5ENCLRR			U(0x28C)
+#define RCC_MC_AHB5ENSETR			U(0x290)
+#define RCC_MC_AHB5ENCLRR			U(0x294)
+#define RCC_MC_AHB6ENSETR			U(0x298)
+#define RCC_MC_AHB6ENCLRR			U(0x29C)
+#define RCC_MP_APB4LPENSETR			U(0x300)
+#define RCC_MP_APB4LPENCLRR			U(0x304)
+#define RCC_MP_APB5LPENSETR			U(0x308)
+#define RCC_MP_APB5LPENCLRR			U(0x30C)
+#define RCC_MP_AHB5LPENSETR			U(0x310)
+#define RCC_MP_AHB5LPENCLRR			U(0x314)
+#define RCC_MP_AHB6LPENSETR			U(0x318)
+#define RCC_MP_AHB6LPENCLRR			U(0x31C)
+#define RCC_MP_TZAHB6LPENSETR			U(0x320)
+#define RCC_MP_TZAHB6LPENCLRR			U(0x324)
+#define RCC_MC_APB4LPENSETR			U(0x380)
+#define RCC_MC_APB4LPENCLRR			U(0x384)
+#define RCC_MC_APB5LPENSETR			U(0x388)
+#define RCC_MC_APB5LPENCLRR			U(0x38C)
+#define RCC_MC_AHB5LPENSETR			U(0x390)
+#define RCC_MC_AHB5LPENCLRR			U(0x394)
+#define RCC_MC_AHB6LPENSETR			U(0x398)
+#define RCC_MC_AHB6LPENCLRR			U(0x39C)
+#define RCC_BR_RSTSCLRR				U(0x400)
+#define RCC_MP_GRSTCSETR			U(0x404)
+#define RCC_MP_RSTSCLRR				U(0x408)
+#define RCC_MP_IWDGFZSETR			U(0x40C)
+#define RCC_MP_IWDGFZCLRR			U(0x410)
+#define RCC_MP_CIER				U(0x414)
+#define RCC_MP_CIFR				U(0x418)
+#define RCC_PWRLPDLYCR				U(0x41C)
+#define RCC_MP_RSTSSETR				U(0x420)
+#define RCC_MCO1CFGR				U(0x800)
+#define RCC_MCO2CFGR				U(0x804)
+#define RCC_OCRDYR				U(0x808)
+#define RCC_DBGCFGR				U(0x80C)
+#define RCC_RCK3SELR				U(0x820)
+#define RCC_RCK4SELR				U(0x824)
+#define RCC_TIMG1PRER				U(0x828)
+#define RCC_TIMG2PRER				U(0x82C)
+#define RCC_MCUDIVR				U(0x830)
+#define RCC_APB1DIVR				U(0x834)
+#define RCC_APB2DIVR				U(0x838)
+#define RCC_APB3DIVR				U(0x83C)
+#define RCC_PLL3CR				U(0x880)
+#define RCC_PLL3CFGR1				U(0x884)
+#define RCC_PLL3CFGR2				U(0x888)
+#define RCC_PLL3FRACR				U(0x88C)
+#define RCC_PLL3CSGR				U(0x890)
+#define RCC_PLL4CR				U(0x894)
+#define RCC_PLL4CFGR1				U(0x898)
+#define RCC_PLL4CFGR2				U(0x89C)
+#define RCC_PLL4FRACR				U(0x8A0)
+#define RCC_PLL4CSGR				U(0x8A4)
+#define RCC_I2C12CKSELR				U(0x8C0)
+#define RCC_I2C35CKSELR				U(0x8C4)
+#define RCC_SAI1CKSELR				U(0x8C8)
+#define RCC_SAI2CKSELR				U(0x8CC)
+#define RCC_SAI3CKSELR				U(0x8D0)
+#define RCC_SAI4CKSELR				U(0x8D4)
+#define RCC_SPI2S1CKSELR			U(0x8D8)
+#define RCC_SPI2S23CKSELR			U(0x8DC)
+#define RCC_SPI45CKSELR				U(0x8E0)
+#define RCC_UART6CKSELR				U(0x8E4)
+#define RCC_UART24CKSELR			U(0x8E8)
+#define RCC_UART35CKSELR			U(0x8EC)
+#define RCC_UART78CKSELR			U(0x8F0)
+#define RCC_SDMMC12CKSELR			U(0x8F4)
+#define RCC_SDMMC3CKSELR			U(0x8F8)
+#define RCC_ETHCKSELR				U(0x8FC)
+#define RCC_QSPICKSELR				U(0x900)
+#define RCC_FMCCKSELR				U(0x904)
+#define RCC_FDCANCKSELR				U(0x90C)
+#define RCC_SPDIFCKSELR				U(0x914)
+#define RCC_CECCKSELR				U(0x918)
+#define RCC_USBCKSELR				U(0x91C)
+#define RCC_RNG2CKSELR				U(0x920)
+#define RCC_DSICKSELR				U(0x924)
+#define RCC_ADCCKSELR				U(0x928)
+#define RCC_LPTIM45CKSELR			U(0x92C)
+#define RCC_LPTIM23CKSELR			U(0x930)
+#define RCC_LPTIM1CKSELR			U(0x934)
+#define RCC_APB1RSTSETR				U(0x980)
+#define RCC_APB1RSTCLRR				U(0x984)
+#define RCC_APB2RSTSETR				U(0x988)
+#define RCC_APB2RSTCLRR				U(0x98C)
+#define RCC_APB3RSTSETR				U(0x990)
+#define RCC_APB3RSTCLRR				U(0x994)
+#define RCC_AHB2RSTSETR				U(0x998)
+#define RCC_AHB2RSTCLRR				U(0x99C)
+#define RCC_AHB3RSTSETR				U(0x9A0)
+#define RCC_AHB3RSTCLRR				U(0x9A4)
+#define RCC_AHB4RSTSETR				U(0x9A8)
+#define RCC_AHB4RSTCLRR				U(0x9AC)
+#define RCC_MP_APB1ENSETR			U(0xA00)
+#define RCC_MP_APB1ENCLRR			U(0xA04)
+#define RCC_MP_APB2ENSETR			U(0xA08)
+#define RCC_MP_APB2ENCLRR			U(0xA0C)
+#define RCC_MP_APB3ENSETR			U(0xA10)
+#define RCC_MP_APB3ENCLRR			U(0xA14)
+#define RCC_MP_AHB2ENSETR			U(0xA18)
+#define RCC_MP_AHB2ENCLRR			U(0xA1C)
+#define RCC_MP_AHB3ENSETR			U(0xA20)
+#define RCC_MP_AHB3ENCLRR			U(0xA24)
+#define RCC_MP_AHB4ENSETR			U(0xA28)
+#define RCC_MP_AHB4ENCLRR			U(0xA2C)
+#define RCC_MP_MLAHBENSETR			U(0xA38)
+#define RCC_MP_MLAHBENCLRR			U(0xA3C)
+#define RCC_MC_APB1ENSETR			U(0xA80)
+#define RCC_MC_APB1ENCLRR			U(0xA84)
+#define RCC_MC_APB2ENSETR			U(0xA88)
+#define RCC_MC_APB2ENCLRR			U(0xA8C)
+#define RCC_MC_APB3ENSETR			U(0xA90)
+#define RCC_MC_APB3ENCLRR			U(0xA94)
+#define RCC_MC_AHB2ENSETR			U(0xA98)
+#define RCC_MC_AHB2ENCLRR			U(0xA9C)
+#define RCC_MC_AHB3ENSETR			U(0xAA0)
+#define RCC_MC_AHB3ENCLRR			U(0xAA4)
+#define RCC_MC_AHB4ENSETR			U(0xAA8)
+#define RCC_MC_AHB4ENCLRR			U(0xAAC)
+#define RCC_MC_AXIMENSETR			U(0xAB0)
+#define RCC_MC_AXIMENCLRR			U(0xAB4)
+#define RCC_MC_MLAHBENSETR			U(0xAB8)
+#define RCC_MC_MLAHBENCLRR			U(0xABC)
+#define RCC_MP_APB1LPENSETR			U(0xB00)
+#define RCC_MP_APB1LPENCLRR			U(0xB04)
+#define RCC_MP_APB2LPENSETR			U(0xB08)
+#define RCC_MP_APB2LPENCLRR			U(0xB0C)
+#define RCC_MP_APB3LPENSETR			U(0xB10)
+#define RCC_MP_APB3LPENCLRR			U(0xB14)
+#define RCC_MP_AHB2LPENSETR			U(0xB18)
+#define RCC_MP_AHB2LPENCLRR			U(0xB1C)
+#define RCC_MP_AHB3LPENSETR			U(0xB20)
+#define RCC_MP_AHB3LPENCLRR			U(0xB24)
+#define RCC_MP_AHB4LPENSETR			U(0xB28)
+#define RCC_MP_AHB4LPENCLRR			U(0xB2C)
+#define RCC_MP_AXIMLPENSETR			U(0xB30)
+#define RCC_MP_AXIMLPENCLRR			U(0xB34)
+#define RCC_MP_MLAHBLPENSETR			U(0xB38)
+#define RCC_MP_MLAHBLPENCLRR			U(0xB3C)
+#define RCC_MC_APB1LPENSETR			U(0xB80)
+#define RCC_MC_APB1LPENCLRR			U(0xB84)
+#define RCC_MC_APB2LPENSETR			U(0xB88)
+#define RCC_MC_APB2LPENCLRR			U(0xB8C)
+#define RCC_MC_APB3LPENSETR			U(0xB90)
+#define RCC_MC_APB3LPENCLRR			U(0xB94)
+#define RCC_MC_AHB2LPENSETR			U(0xB98)
+#define RCC_MC_AHB2LPENCLRR			U(0xB9C)
+#define RCC_MC_AHB3LPENSETR			U(0xBA0)
+#define RCC_MC_AHB3LPENCLRR			U(0xBA4)
+#define RCC_MC_AHB4LPENSETR			U(0xBA8)
+#define RCC_MC_AHB4LPENCLRR			U(0xBAC)
+#define RCC_MC_AXIMLPENSETR			U(0xBB0)
+#define RCC_MC_AXIMLPENCLRR			U(0xBB4)
+#define RCC_MC_MLAHBLPENSETR			U(0xBB8)
+#define RCC_MC_MLAHBLPENCLRR			U(0xBBC)
+#define RCC_MC_RSTSCLRR				U(0xC00)
+#define RCC_MC_CIER				U(0xC14)
+#define RCC_MC_CIFR				U(0xC18)
+#define RCC_VERR				U(0xFF4)
+#define RCC_IDR					U(0xFF8)
+#define RCC_SIDR				U(0xFFC)
 
-#define RCC_OFFSET_MASK			GENMASK(11, 0)
+/* RCC_TZCR register fields */
+#define RCC_TZCR_TZEN				BIT(0)
+#define RCC_TZCR_MCKPROT			BIT(1)
 
-/* Values for RCC_TZCR register */
-#define RCC_TZCR_TZEN			BIT(0)
-#define RCC_TZCR_MCKPROT		BIT(1)
+/* RCC_OCENSETR register fields */
+#define RCC_OCENSETR_HSION			BIT(0)
+#define RCC_OCENSETR_HSIKERON			BIT(1)
+#define RCC_OCENSETR_CSION			BIT(4)
+#define RCC_OCENSETR_CSIKERON			BIT(5)
+#define RCC_OCENSETR_DIGBYP			BIT(7)
+#define RCC_OCENSETR_HSEON			BIT(8)
+#define RCC_OCENSETR_HSEKERON			BIT(9)
+#define RCC_OCENSETR_HSEBYP			BIT(10)
+#define RCC_OCENSETR_HSECSSON			BIT(11)
 
-/* Used for most of RCC_<x>SELR registers */
-#define RCC_SELR_SRC_MASK		GENMASK(2, 0)
-#define RCC_SELR_REFCLK_SRC_MASK	GENMASK(1, 0)
-#define RCC_SELR_SRCRDY			BIT(31)
+/* RCC_OCENCLRR register fields */
+#define RCC_OCENCLRR_HSION			BIT(0)
+#define RCC_OCENCLRR_HSIKERON			BIT(1)
+#define RCC_OCENCLRR_CSION			BIT(4)
+#define RCC_OCENCLRR_CSIKERON			BIT(5)
+#define RCC_OCENCLRR_DIGBYP			BIT(7)
+#define RCC_OCENCLRR_HSEON			BIT(8)
+#define RCC_OCENCLRR_HSEKERON			BIT(9)
+#define RCC_OCENCLRR_HSEBYP			BIT(10)
 
-/* Values of RCC_MPCKSELR register */
-#define RCC_MPCKSELR_HSI		0x00000000
-#define RCC_MPCKSELR_HSE		0x00000001
-#define RCC_MPCKSELR_PLL		0x00000002
-#define RCC_MPCKSELR_PLL_MPUDIV		0x00000003
-#define RCC_MPCKSELR_MPUSRC_MASK	GENMASK(1, 0)
-#define RCC_MPCKSELR_MPUSRC_SHIFT	0
+/* RCC_HSICFGR register fields */
+#define RCC_HSICFGR_HSIDIV_MASK			GENMASK(1, 0)
+#define RCC_HSICFGR_HSIDIV_SHIFT		0
+#define RCC_HSICFGR_HSITRIM_MASK		GENMASK(14, 8)
+#define RCC_HSICFGR_HSITRIM_SHIFT		8
+#define RCC_HSICFGR_HSICAL_MASK			GENMASK(24, 16)
+#define RCC_HSICFGR_HSICAL_SHIFT		16
+#define RCC_HSICFGR_HSICAL_TEMP_MASK		GENMASK(27, 25)
 
-/* Values of RCC_ASSCKSELR register */
-#define RCC_ASSCKSELR_HSI		0x00000000
-#define RCC_ASSCKSELR_HSE		0x00000001
-#define RCC_ASSCKSELR_PLL		0x00000002
+/* RCC_CSICFGR register fields */
+#define RCC_CSICFGR_CSITRIM_MASK		GENMASK(12, 8)
+#define RCC_CSICFGR_CSITRIM_SHIFT		8
+#define RCC_CSICFGR_CSICAL_MASK			GENMASK(23, 16)
+#define RCC_CSICFGR_CSICAL_SHIFT		16
 
-/* Values of RCC_MSSCKSELR register */
-#define RCC_MSSCKSELR_HSI		0x00000000
-#define RCC_MSSCKSELR_HSE		0x00000001
-#define RCC_MSSCKSELR_CSI		0x00000002
-#define RCC_MSSCKSELR_PLL		0x00000003
-
-/* Values of RCC_CPERCKSELR register */
-#define RCC_CPERCKSELR_HSI		0x00000000
-#define RCC_CPERCKSELR_CSI		0x00000001
-#define RCC_CPERCKSELR_HSE		0x00000002
-#define RCC_CPERCKSELR_PERSRC_MASK	GENMASK(1, 0)
-#define RCC_CPERCKSELR_PERSRC_SHIFT	0
-
-/* Used for most of DIVR register: max div for RTC */
-#define RCC_DIVR_DIV_MASK		GENMASK(5, 0)
-#define RCC_DIVR_DIVRDY			BIT(31)
-
-/* Masks for specific DIVR registers */
-#define RCC_APBXDIV_MASK		GENMASK(2, 0)
-#define RCC_MPUDIV_MASK			GENMASK(2, 0)
-#define RCC_AXIDIV_MASK			GENMASK(2, 0)
-#define RCC_MCUDIV_MASK			GENMASK(3, 0)
-
-/* Used for TIMER Prescaler */
-#define RCC_TIMGXPRER_TIMGXPRE		BIT(0)
-
-/* Offset between RCC_MP_xxxENSETR and RCC_MP_xxxENCLRR registers */
-#define RCC_MP_ENCLRR_OFFSET		U(4)
-
-/* Offset between RCC_xxxRSTSETR and RCC_xxxRSTCLRR registers */
-#define RCC_RSTCLRR_OFFSET		U(4)
-
-/* Fields of RCC_BDCR register */
-#define RCC_BDCR_LSEON			BIT(0)
-#define RCC_BDCR_LSEBYP			BIT(1)
-#define RCC_BDCR_LSERDY			BIT(2)
-#define RCC_BDCR_DIGBYP			BIT(3)
-#define RCC_BDCR_LSEDRV_MASK		GENMASK(5, 4)
-#define RCC_BDCR_LSEDRV_SHIFT		4
-#define RCC_BDCR_LSECSSON		BIT(8)
-#define RCC_BDCR_RTCCKEN		BIT(20)
-#define RCC_BDCR_RTCSRC_MASK		GENMASK(17, 16)
-#define RCC_BDCR_RTCSRC_SHIFT		16
-#define RCC_BDCR_VSWRST			BIT(31)
-
-/* Fields of RCC_RDLSICR register */
-#define RCC_RDLSICR_LSION		BIT(0)
-#define RCC_RDLSICR_LSIRDY		BIT(1)
-
-/* Used for all RCC_PLL<n>CR registers */
-#define RCC_PLLNCR_PLLON		BIT(0)
-#define RCC_PLLNCR_PLLRDY		BIT(1)
-#define RCC_PLLNCR_SSCG_CTRL		BIT(2)
-#define RCC_PLLNCR_DIVPEN		BIT(4)
-#define RCC_PLLNCR_DIVQEN		BIT(5)
-#define RCC_PLLNCR_DIVREN		BIT(6)
-#define RCC_PLLNCR_DIVEN_SHIFT		4
-
-/* Used for all RCC_PLL<n>CFGR1 registers */
-#define RCC_PLLNCFGR1_DIVM_SHIFT	16
-#define RCC_PLLNCFGR1_DIVM_MASK		GENMASK(21, 16)
-#define RCC_PLLNCFGR1_DIVN_SHIFT	0
-#define RCC_PLLNCFGR1_DIVN_MASK		GENMASK(8, 0)
-/* Only for PLL3 and PLL4 */
-#define RCC_PLLNCFGR1_IFRGE_SHIFT	24
-#define RCC_PLLNCFGR1_IFRGE_MASK	GENMASK(25, 24)
-
-/* Used for all RCC_PLL<n>CFGR2 registers */
-#define RCC_PLLNCFGR2_DIVX_MASK		GENMASK(6, 0)
-#define RCC_PLLNCFGR2_DIVP_SHIFT	0
-#define RCC_PLLNCFGR2_DIVP_MASK		GENMASK(6, 0)
-#define RCC_PLLNCFGR2_DIVQ_SHIFT	8
-#define RCC_PLLNCFGR2_DIVQ_MASK		GENMASK(14, 8)
-#define RCC_PLLNCFGR2_DIVR_SHIFT	16
-#define RCC_PLLNCFGR2_DIVR_MASK		GENMASK(22, 16)
-
-/* Used for all RCC_PLL<n>FRACR registers */
-#define RCC_PLLNFRACR_FRACV_SHIFT	3
-#define RCC_PLLNFRACR_FRACV_MASK	GENMASK(15, 3)
-#define RCC_PLLNFRACR_FRACLE		BIT(16)
-
-/* Used for all RCC_PLL<n>CSGR registers */
-#define RCC_PLLNCSGR_INC_STEP_SHIFT	16
-#define RCC_PLLNCSGR_INC_STEP_MASK	GENMASK(30, 16)
-#define RCC_PLLNCSGR_MOD_PER_SHIFT	0
-#define RCC_PLLNCSGR_MOD_PER_MASK	GENMASK(12, 0)
-#define RCC_PLLNCSGR_SSCG_MODE_SHIFT	15
-#define RCC_PLLNCSGR_SSCG_MODE_MASK	BIT(15)
-
-/* Used for RCC_OCENSETR and RCC_OCENCLRR registers */
-#define RCC_OCENR_HSION			BIT(0)
-#define RCC_OCENR_HSIKERON		BIT(1)
-#define RCC_OCENR_CSION			BIT(4)
-#define RCC_OCENR_CSIKERON		BIT(5)
-#define RCC_OCENR_DIGBYP		BIT(7)
-#define RCC_OCENR_HSEON			BIT(8)
-#define RCC_OCENR_HSEKERON		BIT(9)
-#define RCC_OCENR_HSEBYP		BIT(10)
-#define RCC_OCENR_HSECSSON		BIT(11)
-
-/* Fields of RCC_OCRDYR register */
-#define RCC_OCRDYR_HSIRDY		BIT(0)
-#define RCC_OCRDYR_HSIDIVRDY		BIT(2)
-#define RCC_OCRDYR_CSIRDY		BIT(4)
-#define RCC_OCRDYR_HSERDY		BIT(8)
-
-/* Fields of RCC_DDRITFCR register */
-#define RCC_DDRITFCR_DDRC1EN		BIT(0)
-#define RCC_DDRITFCR_DDRC1LPEN		BIT(1)
-#define RCC_DDRITFCR_DDRC2EN		BIT(2)
-#define RCC_DDRITFCR_DDRC2LPEN		BIT(3)
-#define RCC_DDRITFCR_DDRPHYCEN		BIT(4)
-#define RCC_DDRITFCR_DDRPHYCLPEN	BIT(5)
-#define RCC_DDRITFCR_DDRCAPBEN		BIT(6)
-#define RCC_DDRITFCR_DDRCAPBLPEN	BIT(7)
-#define RCC_DDRITFCR_AXIDCGEN		BIT(8)
-#define RCC_DDRITFCR_DDRPHYCAPBEN	BIT(9)
-#define RCC_DDRITFCR_DDRPHYCAPBLPEN	BIT(10)
-#define RCC_DDRITFCR_DDRCAPBRST		BIT(14)
-#define RCC_DDRITFCR_DDRCAXIRST		BIT(15)
-#define RCC_DDRITFCR_DDRCORERST		BIT(16)
-#define RCC_DDRITFCR_DPHYAPBRST		BIT(17)
-#define RCC_DDRITFCR_DPHYRST		BIT(18)
-#define RCC_DDRITFCR_DPHYCTLRST		BIT(19)
-#define RCC_DDRITFCR_DDRCKMOD_MASK	GENMASK(22, 20)
-#define RCC_DDRITFCR_DDRCKMOD_SHIFT	20
-#define RCC_DDRITFCR_DDRCKMOD_SSR	0
-#define RCC_DDRITFCR_DDRCKMOD_ASR1	BIT(20)
-#define RCC_DDRITFCR_DDRCKMOD_HSR1	BIT(21)
-#define RCC_DDRITFCR_GSKPCTRL		BIT(24)
-
-/* Fields of RCC_HSICFGR register */
-#define RCC_HSICFGR_HSIDIV_MASK		GENMASK(1, 0)
-#define RCC_HSICFGR_HSITRIM_SHIFT	8
-#define RCC_HSICFGR_HSITRIM_MASK	GENMASK(14, 8)
-#define RCC_HSICFGR_HSICAL_SHIFT	16
-#define RCC_HSICFGR_HSICAL_MASK		GENMASK(27, 16)
-
-/* Fields of RCC_CSICFGR register */
-#define RCC_CSICFGR_CSITRIM_SHIFT	8
-#define RCC_CSICFGR_CSITRIM_MASK	GENMASK(12, 8)
-#define RCC_CSICFGR_CSICAL_SHIFT	16
-#define RCC_CSICFGR_CSICAL_MASK		GENMASK(23, 16)
-
-/* Used for RCC_MCO related operations */
-#define RCC_MCOCFG_MCOON		BIT(12)
-#define RCC_MCOCFG_MCODIV_MASK		GENMASK(7, 4)
-#define RCC_MCOCFG_MCODIV_SHIFT		4
-#define RCC_MCOCFG_MCOSRC_MASK		GENMASK(2, 0)
-
-/* Fields of RCC_DBGCFGR register */
-#define RCC_DBGCFGR_DBGCKEN		BIT(8)
-
-/* RCC register fields for reset reasons */
-#define RCC_MP_RSTSCLRR_PORRSTF		BIT(0)
-#define RCC_MP_RSTSCLRR_BORRSTF		BIT(1)
-#define RCC_MP_RSTSCLRR_PADRSTF		BIT(2)
-#define RCC_MP_RSTSCLRR_HCSSRSTF	BIT(3)
-#define RCC_MP_RSTSCLRR_VCORERSTF	BIT(4)
-#define RCC_MP_RSTSCLRR_MPSYSRSTF	BIT(6)
-#define RCC_MP_RSTSCLRR_MCSYSRSTF	BIT(7)
-#define RCC_MP_RSTSCLRR_IWDG1RSTF	BIT(8)
-#define RCC_MP_RSTSCLRR_IWDG2RSTF	BIT(9)
-#define RCC_MP_RSTSCLRR_STDBYRSTF	BIT(11)
-#define RCC_MP_RSTSCLRR_CSTDBYRSTF	BIT(12)
-#define RCC_MP_RSTSCLRR_MPUP0RSTF	BIT(13)
-#define RCC_MP_RSTSCLRR_MPUP1RSTF	BIT(14)
-
-/* Global Reset Register */
-#define RCC_MP_GRSTCSETR_MPSYSRST	BIT(0)
-#define RCC_MP_GRSTCSETR_MCURST		BIT(1)
-#define RCC_MP_GRSTCSETR_MPUP0RST	BIT(4)
-#define RCC_MP_GRSTCSETR_MPUP1RST	BIT(5)
-
-/* Clock Source Interrupt Flag Register */
-#define RCC_MP_CIFR_MASK		U(0x110F1F)
-#define RCC_MP_CIFR_LSIRDYF		BIT(0)
-#define RCC_MP_CIFR_LSERDYF		BIT(1)
-#define RCC_MP_CIFR_HSIRDYF		BIT(2)
-#define RCC_MP_CIFR_HSERDYF		BIT(3)
-#define RCC_MP_CIFR_CSIRDYF		BIT(4)
-#define RCC_MP_CIFR_PLL1DYF		BIT(8)
-#define RCC_MP_CIFR_PLL2DYF		BIT(9)
-#define RCC_MP_CIFR_PLL3DYF		BIT(10)
-#define RCC_MP_CIFR_PLL4DYF		BIT(11)
-#define RCC_MP_CIFR_WKUPF		BIT(20)
-
-/* Stop Request Set Register */
-#define RCC_MP_SREQSETR_STPREQ_P0	BIT(0)
-#define RCC_MP_SREQSETR_STPREQ_P1	BIT(1)
-
-/* Stop Request Clear Register */
-#define RCC_MP_SREQCLRR_STPREQ_P0	BIT(0)
-#define RCC_MP_SREQCLRR_STPREQ_P1	BIT(1)
-
-/* Values of RCC_UART24CKSELR register */
-#define RCC_UART24CKSELR_HSI		0x00000002
-
-/* Values of RCC_MP_APB1ENSETR register */
-#define RCC_MP_APB1ENSETR_UART4EN	BIT(16)
-
-/* Values of RCC_MP_APB5ENSETR register */
-#define RCC_MP_APB5ENSETR_SPI6EN	BIT(0)
-#define RCC_MP_APB5ENSETR_I2C4EN	BIT(2)
-#define RCC_MP_APB5ENSETR_I2C6EN	BIT(3)
-#define RCC_MP_APB5ENSETR_USART1EN	BIT(4)
-#define RCC_MP_APB5ENSETR_RTCAPBEN	BIT(8)
-#define RCC_MP_APB5ENSETR_IWDG1APBEN	BIT(15)
-
-/* Values of RCC_MP_AHB4ENSETR register */
-#define RCC_MP_AHB4ENSETR_GPIOGEN	BIT(6)
-#define RCC_MP_AHB4ENSETR_GPIOHEN	BIT(7)
-
-/* Values of RCC_MP_AHB5ENSETR register */
-#define RCC_MP_AHB5ENSETR_GPIOZEN	BIT(0)
-#define RCC_MP_AHB5ENSETR_CRYP1EN	BIT(4)
-#define RCC_MP_AHB5ENSETR_HASH1EN	BIT(5)
-#define RCC_MP_AHB5ENSETR_RNG1EN	BIT(6)
-
-/* Values of RCC_MP_IWDGFZSETR register */
-#define RCC_MP_IWDGFZSETR_IWDG1		BIT(0)
-#define RCC_MP_IWDGFZSETR_IWDG2		BIT(1)
-
-/* Values of RCC_PWRLPDLYCR register */
-#define RCC_PWRLPDLYCR_PWRLP_DLY_MASK	GENMASK(21, 0)
+/* RCC_MPCKSELR register fields */
+#define RCC_MPCKSELR_HSI			0x00000000
+#define RCC_MPCKSELR_HSE			0x00000001
+#define RCC_MPCKSELR_PLL			0x00000002
+#define RCC_MPCKSELR_PLL_MPUDIV			0x00000003
+#define RCC_MPCKSELR_MPUSRC_MASK		GENMASK(1, 0)
+#define RCC_MPCKSELR_MPUSRC_SHIFT		0
+#define RCC_MPCKSELR_MPUSRCRDY			BIT(31)
 
 /* RCC_ASSCKSELR register fields */
+#define RCC_ASSCKSELR_HSI			0x00000000
+#define RCC_ASSCKSELR_HSE			0x00000001
+#define RCC_ASSCKSELR_PLL			0x00000002
 #define RCC_ASSCKSELR_AXISSRC_MASK		GENMASK(2, 0)
 #define RCC_ASSCKSELR_AXISSRC_SHIFT		0
+#define RCC_ASSCKSELR_AXISSRCRDY		BIT(31)
+
+/* RCC_RCK12SELR register fields */
+#define RCC_RCK12SELR_PLL12SRC_MASK		GENMASK(1, 0)
+#define RCC_RCK12SELR_PLL12SRC_SHIFT		0
+#define RCC_RCK12SELR_PLL12SRCRDY		BIT(31)
+
+/* RCC_MPCKDIVR register fields */
+#define RCC_MPCKDIVR_MPUDIV_MASK		GENMASK(2, 0)
+#define RCC_MPCKDIVR_MPUDIV_SHIFT		0
+#define RCC_MPCKDIVR_MPUDIVRDY			BIT(31)
+
+/* RCC_AXIDIVR register fields */
+#define RCC_AXIDIVR_AXIDIV_MASK			GENMASK(2, 0)
+#define RCC_AXIDIVR_AXIDIV_SHIFT		0
+#define RCC_AXIDIVR_AXIDIVRDY			BIT(31)
+
+/* RCC_APB4DIVR register fields */
+#define RCC_APB4DIVR_APB4DIV_MASK		GENMASK(2, 0)
+#define RCC_APB4DIVR_APB4DIV_SHIFT		0
+#define RCC_APB4DIVR_APB4DIVRDY			BIT(31)
+
+/* RCC_APB5DIVR register fields */
+#define RCC_APB5DIVR_APB5DIV_MASK		GENMASK(2, 0)
+#define RCC_APB5DIVR_APB5DIV_SHIFT		0
+#define RCC_APB5DIVR_APB5DIVRDY			BIT(31)
+
+/* RCC_RTCDIVR register fields */
+#define RCC_RTCDIVR_RTCDIV_MASK			GENMASK(5, 0)
+#define RCC_RTCDIVR_RTCDIV_SHIFT		0
 
 /* RCC_MSSCKSELR register fields */
+#define RCC_MSSCKSELR_HSI			0x00000000
+#define RCC_MSSCKSELR_HSE			0x00000001
+#define RCC_MSSCKSELR_CSI			0x00000002
+#define RCC_MSSCKSELR_PLL			0x00000003
 #define RCC_MSSCKSELR_MCUSSRC_MASK		GENMASK(1, 0)
 #define RCC_MSSCKSELR_MCUSSRC_SHIFT		0
+#define RCC_MSSCKSELR_MCUSSRCRDY		BIT(31)
+
+/* RCC_PLL1CR register fields */
+#define RCC_PLL1CR_PLLON			BIT(0)
+#define RCC_PLL1CR_PLL1RDY			BIT(1)
+#define RCC_PLL1CR_SSCG_CTRL			BIT(2)
+#define RCC_PLL1CR_DIVPEN			BIT(4)
+#define RCC_PLL1CR_DIVQEN			BIT(5)
+#define RCC_PLL1CR_DIVREN			BIT(6)
+
+/* RCC_PLL1CFGR1 register fields */
+#define RCC_PLL1CFGR1_DIVN_MASK			GENMASK(8, 0)
+#define RCC_PLL1CFGR1_DIVN_SHIFT		0
+#define RCC_PLL1CFGR1_DIVM1_MASK		GENMASK(21, 16)
+#define RCC_PLL1CFGR1_DIVM1_SHIFT		16
+
+/* RCC_PLL1CFGR2 register fields */
+#define RCC_PLL1CFGR2_DIVP_MASK			GENMASK(6, 0)
+#define RCC_PLL1CFGR2_DIVP_SHIFT		0
+#define RCC_PLL1CFGR2_DIVQ_MASK			GENMASK(14, 8)
+#define RCC_PLL1CFGR2_DIVQ_SHIFT		8
+#define RCC_PLL1CFGR2_DIVR_MASK			GENMASK(22, 16)
+#define RCC_PLL1CFGR2_DIVR_SHIFT		16
+
+/* RCC_PLL1FRACR register fields */
+#define RCC_PLL1FRACR_FRACV_MASK		GENMASK(15, 3)
+#define RCC_PLL1FRACR_FRACV_SHIFT		3
+#define RCC_PLL1FRACR_FRACLE			BIT(16)
+
+/* RCC_PLL1CSGR register fields */
+#define RCC_PLL1CSGR_MOD_PER_MASK		GENMASK(12, 0)
+#define RCC_PLL1CSGR_MOD_PER_SHIFT		0
+#define RCC_PLL1CSGR_TPDFN_DIS			BIT(13)
+#define RCC_PLL1CSGR_RPDFN_DIS			BIT(14)
+#define RCC_PLL1CSGR_SSCG_MODE			BIT(15)
+#define RCC_PLL1CSGR_INC_STEP_MASK		GENMASK(30, 16)
+#define RCC_PLL1CSGR_INC_STEP_SHIFT		16
+
+/* RCC_PLL2CR register fields */
+#define RCC_PLL2CR_PLLON			BIT(0)
+#define RCC_PLL2CR_PLL2RDY			BIT(1)
+#define RCC_PLL2CR_SSCG_CTRL			BIT(2)
+#define RCC_PLL2CR_DIVPEN			BIT(4)
+#define RCC_PLL2CR_DIVQEN			BIT(5)
+#define RCC_PLL2CR_DIVREN			BIT(6)
+
+/* RCC_PLL2CFGR1 register fields */
+#define RCC_PLL2CFGR1_DIVN_MASK			GENMASK(8, 0)
+#define RCC_PLL2CFGR1_DIVN_SHIFT		0
+#define RCC_PLL2CFGR1_DIVM2_MASK		GENMASK(21, 16)
+#define RCC_PLL2CFGR1_DIVM2_SHIFT		16
+
+/* RCC_PLL2CFGR2 register fields */
+#define RCC_PLL2CFGR2_DIVP_MASK			GENMASK(6, 0)
+#define RCC_PLL2CFGR2_DIVP_SHIFT		0
+#define RCC_PLL2CFGR2_DIVQ_MASK			GENMASK(14, 8)
+#define RCC_PLL2CFGR2_DIVQ_SHIFT		8
+#define RCC_PLL2CFGR2_DIVR_MASK			GENMASK(22, 16)
+#define RCC_PLL2CFGR2_DIVR_SHIFT		16
+
+/* RCC_PLL2FRACR register fields */
+#define RCC_PLL2FRACR_FRACV_MASK		GENMASK(15, 3)
+#define RCC_PLL2FRACR_FRACV_SHIFT		3
+#define RCC_PLL2FRACR_FRACLE			BIT(16)
+
+/* RCC_PLL2CSGR register fields */
+#define RCC_PLL2CSGR_MOD_PER_MASK		GENMASK(12, 0)
+#define RCC_PLL2CSGR_MOD_PER_SHIFT		0
+#define RCC_PLL2CSGR_TPDFN_DIS			BIT(13)
+#define RCC_PLL2CSGR_RPDFN_DIS			BIT(14)
+#define RCC_PLL2CSGR_SSCG_MODE			BIT(15)
+#define RCC_PLL2CSGR_INC_STEP_MASK		GENMASK(30, 16)
+#define RCC_PLL2CSGR_INC_STEP_SHIFT		16
 
 /* RCC_I2C46CKSELR register fields */
 #define RCC_I2C46CKSELR_I2C46SRC_MASK		GENMASK(2, 0)
@@ -508,10 +417,751 @@
 #define RCC_RNG1CKSELR_RNG1SRC_MASK		GENMASK(1, 0)
 #define RCC_RNG1CKSELR_RNG1SRC_SHIFT		0
 
+/* RCC_CPERCKSELR register fields */
+#define RCC_CPERCKSELR_HSI			0x00000000
+#define RCC_CPERCKSELR_CSI			0x00000001
+#define RCC_CPERCKSELR_HSE			0x00000002
+#define RCC_CPERCKSELR_CKPERSRC_MASK		GENMASK(1, 0)
+#define RCC_CPERCKSELR_CKPERSRC_SHIFT		0
+
 /* RCC_STGENCKSELR register fields */
 #define RCC_STGENCKSELR_STGENSRC_MASK		GENMASK(1, 0)
 #define RCC_STGENCKSELR_STGENSRC_SHIFT		0
 
+/* RCC_DDRITFCR register fields */
+#define RCC_DDRITFCR_DDRC1EN			BIT(0)
+#define RCC_DDRITFCR_DDRC1LPEN			BIT(1)
+#define RCC_DDRITFCR_DDRC2EN			BIT(2)
+#define RCC_DDRITFCR_DDRC2LPEN			BIT(3)
+#define RCC_DDRITFCR_DDRPHYCEN			BIT(4)
+#define RCC_DDRITFCR_DDRPHYCLPEN		BIT(5)
+#define RCC_DDRITFCR_DDRCAPBEN			BIT(6)
+#define RCC_DDRITFCR_DDRCAPBLPEN		BIT(7)
+#define RCC_DDRITFCR_AXIDCGEN			BIT(8)
+#define RCC_DDRITFCR_DDRPHYCAPBEN		BIT(9)
+#define RCC_DDRITFCR_DDRPHYCAPBLPEN		BIT(10)
+#define RCC_DDRITFCR_KERDCG_DLY_MASK		GENMASK(13, 11)
+#define RCC_DDRITFCR_KERDCG_DLY_SHIFT		11
+#define RCC_DDRITFCR_DDRCAPBRST			BIT(14)
+#define RCC_DDRITFCR_DDRCAXIRST			BIT(15)
+#define RCC_DDRITFCR_DDRCORERST			BIT(16)
+#define RCC_DDRITFCR_DPHYAPBRST			BIT(17)
+#define RCC_DDRITFCR_DPHYRST			BIT(18)
+#define RCC_DDRITFCR_DPHYCTLRST			BIT(19)
+#define RCC_DDRITFCR_DDRCKMOD_MASK		GENMASK(22, 20)
+#define RCC_DDRITFCR_DDRCKMOD_SHIFT		20
+#define RCC_DDRITFCR_DDRCKMOD_SSR		0
+#define RCC_DDRITFCR_DDRCKMOD_ASR1		BIT(20)
+#define RCC_DDRITFCR_DDRCKMOD_HSR1		BIT(21)
+#define RCC_DDRITFCR_GSKPMOD			BIT(23)
+#define RCC_DDRITFCR_GSKPCTRL			BIT(24)
+#define RCC_DDRITFCR_DFILP_WIDTH_MASK		GENMASK(27, 25)
+#define RCC_DDRITFCR_DFILP_WIDTH_SHIFT		25
+#define RCC_DDRITFCR_GSKP_DUR_MASK		GENMASK(31, 28)
+#define RCC_DDRITFCR_GSKP_DUR_SHIFT		28
+
+/* RCC_MP_BOOTCR register fields */
+#define RCC_MP_BOOTCR_MCU_BEN			BIT(0)
+#define RCC_MP_BOOTCR_MPU_BEN			BIT(1)
+
+/* RCC_MP_SREQSETR register fields */
+#define RCC_MP_SREQSETR_STPREQ_P0		BIT(0)
+#define RCC_MP_SREQSETR_STPREQ_P1		BIT(1)
+
+/* RCC_MP_SREQCLRR register fields */
+#define RCC_MP_SREQCLRR_STPREQ_P0		BIT(0)
+#define RCC_MP_SREQCLRR_STPREQ_P1		BIT(1)
+
+/* RCC_MP_GCR register fields */
+#define RCC_MP_GCR_BOOT_MCU			BIT(0)
+
+/* RCC_MP_APRSTCR register fields */
+#define RCC_MP_APRSTCR_RDCTLEN			BIT(0)
+#define RCC_MP_APRSTCR_RSTTO_MASK		GENMASK(14, 8)
+#define RCC_MP_APRSTCR_RSTTO_SHIFT		8
+
+/* RCC_MP_APRSTSR register fields */
+#define RCC_MP_APRSTSR_RSTTOV_MASK		GENMASK(14, 8)
+#define RCC_MP_APRSTSR_RSTTOV_SHIFT		8
+
+/* RCC_BDCR register fields */
+#define RCC_BDCR_LSEON				BIT(0)
+#define RCC_BDCR_LSEBYP				BIT(1)
+#define RCC_BDCR_LSERDY				BIT(2)
+#define RCC_BDCR_DIGBYP				BIT(3)
+#define RCC_BDCR_LSEDRV_MASK			GENMASK(5, 4)
+#define RCC_BDCR_LSEDRV_SHIFT			4
+#define RCC_BDCR_LSECSSON			BIT(8)
+#define RCC_BDCR_LSECSSD			BIT(9)
+#define RCC_BDCR_RTCSRC_MASK			GENMASK(17, 16)
+#define RCC_BDCR_RTCSRC_SHIFT			16
+#define RCC_BDCR_RTCCKEN			BIT(20)
+#define RCC_BDCR_VSWRST				BIT(31)
+
+/* RCC_RDLSICR register fields */
+#define RCC_RDLSICR_LSION			BIT(0)
+#define RCC_RDLSICR_LSIRDY			BIT(1)
+#define RCC_RDLSICR_MRD_MASK			GENMASK(20, 16)
+#define RCC_RDLSICR_MRD_SHIFT			16
+#define RCC_RDLSICR_EADLY_MASK			GENMASK(26, 24)
+#define RCC_RDLSICR_EADLY_SHIFT			24
+#define RCC_RDLSICR_SPARE_MASK			GENMASK(31, 27)
+#define RCC_RDLSICR_SPARE_SHIFT			27
+
+/* RCC_APB4RSTSETR register fields */
+#define RCC_APB4RSTSETR_LTDCRST			BIT(0)
+#define RCC_APB4RSTSETR_DSIRST			BIT(4)
+#define RCC_APB4RSTSETR_DDRPERFMRST		BIT(8)
+#define RCC_APB4RSTSETR_USBPHYRST		BIT(16)
+
+/* RCC_APB4RSTCLRR register fields */
+#define RCC_APB4RSTCLRR_LTDCRST			BIT(0)
+#define RCC_APB4RSTCLRR_DSIRST			BIT(4)
+#define RCC_APB4RSTCLRR_DDRPERFMRST		BIT(8)
+#define RCC_APB4RSTCLRR_USBPHYRST		BIT(16)
+
+/* RCC_APB5RSTSETR register fields */
+#define RCC_APB5RSTSETR_SPI6RST			BIT(0)
+#define RCC_APB5RSTSETR_I2C4RST			BIT(2)
+#define RCC_APB5RSTSETR_I2C6RST			BIT(3)
+#define RCC_APB5RSTSETR_USART1RST		BIT(4)
+#define RCC_APB5RSTSETR_STGENRST		BIT(20)
+
+/* RCC_APB5RSTCLRR register fields */
+#define RCC_APB5RSTCLRR_SPI6RST			BIT(0)
+#define RCC_APB5RSTCLRR_I2C4RST			BIT(2)
+#define RCC_APB5RSTCLRR_I2C6RST			BIT(3)
+#define RCC_APB5RSTCLRR_USART1RST		BIT(4)
+#define RCC_APB5RSTCLRR_STGENRST		BIT(20)
+
+/* RCC_AHB5RSTSETR register fields */
+#define RCC_AHB5RSTSETR_GPIOZRST		BIT(0)
+#define RCC_AHB5RSTSETR_CRYP1RST		BIT(4)
+#define RCC_AHB5RSTSETR_HASH1RST		BIT(5)
+#define RCC_AHB5RSTSETR_RNG1RST			BIT(6)
+#define RCC_AHB5RSTSETR_AXIMCRST		BIT(16)
+
+/* RCC_AHB5RSTCLRR register fields */
+#define RCC_AHB5RSTCLRR_GPIOZRST		BIT(0)
+#define RCC_AHB5RSTCLRR_CRYP1RST		BIT(4)
+#define RCC_AHB5RSTCLRR_HASH1RST		BIT(5)
+#define RCC_AHB5RSTCLRR_RNG1RST			BIT(6)
+#define RCC_AHB5RSTCLRR_AXIMCRST		BIT(16)
+
+/* RCC_AHB6RSTSETR register fields */
+#define RCC_AHB6RSTSETR_GPURST			BIT(5)
+#define RCC_AHB6RSTSETR_ETHMACRST		BIT(10)
+#define RCC_AHB6RSTSETR_FMCRST			BIT(12)
+#define RCC_AHB6RSTSETR_QSPIRST			BIT(14)
+#define RCC_AHB6RSTSETR_SDMMC1RST		BIT(16)
+#define RCC_AHB6RSTSETR_SDMMC2RST		BIT(17)
+#define RCC_AHB6RSTSETR_CRC1RST			BIT(20)
+#define RCC_AHB6RSTSETR_USBHRST			BIT(24)
+
+/* RCC_AHB6RSTCLRR register fields */
+#define RCC_AHB6RSTCLRR_ETHMACRST		BIT(10)
+#define RCC_AHB6RSTCLRR_FMCRST			BIT(12)
+#define RCC_AHB6RSTCLRR_QSPIRST			BIT(14)
+#define RCC_AHB6RSTCLRR_SDMMC1RST		BIT(16)
+#define RCC_AHB6RSTCLRR_SDMMC2RST		BIT(17)
+#define RCC_AHB6RSTCLRR_CRC1RST			BIT(20)
+#define RCC_AHB6RSTCLRR_USBHRST			BIT(24)
+
+/* RCC_TZAHB6RSTSETR register fields */
+#define RCC_TZAHB6RSTSETR_MDMARST		BIT(0)
+
+/* RCC_TZAHB6RSTCLRR register fields */
+#define RCC_TZAHB6RSTCLRR_MDMARST		BIT(0)
+
+/* RCC_MP_APB4ENSETR register fields */
+#define RCC_MP_APB4ENSETR_LTDCEN		BIT(0)
+#define RCC_MP_APB4ENSETR_DSIEN			BIT(4)
+#define RCC_MP_APB4ENSETR_DDRPERFMEN		BIT(8)
+#define RCC_MP_APB4ENSETR_IWDG2APBEN		BIT(15)
+#define RCC_MP_APB4ENSETR_USBPHYEN		BIT(16)
+#define RCC_MP_APB4ENSETR_STGENROEN		BIT(20)
+
+/* RCC_MP_APB4ENCLRR register fields */
+#define RCC_MP_APB4ENCLRR_LTDCEN		BIT(0)
+#define RCC_MP_APB4ENCLRR_DSIEN			BIT(4)
+#define RCC_MP_APB4ENCLRR_DDRPERFMEN		BIT(8)
+#define RCC_MP_APB4ENCLRR_IWDG2APBEN		BIT(15)
+#define RCC_MP_APB4ENCLRR_USBPHYEN		BIT(16)
+#define RCC_MP_APB4ENCLRR_STGENROEN		BIT(20)
+
+/* RCC_MP_APB5ENSETR register fields */
+#define RCC_MP_APB5ENSETR_SPI6EN		BIT(0)
+#define RCC_MP_APB5ENSETR_I2C4EN		BIT(2)
+#define RCC_MP_APB5ENSETR_I2C6EN		BIT(3)
+#define RCC_MP_APB5ENSETR_USART1EN		BIT(4)
+#define RCC_MP_APB5ENSETR_RTCAPBEN		BIT(8)
+#define RCC_MP_APB5ENSETR_TZC1EN		BIT(11)
+#define RCC_MP_APB5ENSETR_TZC2EN		BIT(12)
+#define RCC_MP_APB5ENSETR_TZPCEN		BIT(13)
+#define RCC_MP_APB5ENSETR_IWDG1APBEN		BIT(15)
+#define RCC_MP_APB5ENSETR_BSECEN		BIT(16)
+#define RCC_MP_APB5ENSETR_STGENEN		BIT(20)
+
+/* RCC_MP_APB5ENCLRR register fields */
+#define RCC_MP_APB5ENCLRR_SPI6EN		BIT(0)
+#define RCC_MP_APB5ENCLRR_I2C4EN		BIT(2)
+#define RCC_MP_APB5ENCLRR_I2C6EN		BIT(3)
+#define RCC_MP_APB5ENCLRR_USART1EN		BIT(4)
+#define RCC_MP_APB5ENCLRR_RTCAPBEN		BIT(8)
+#define RCC_MP_APB5ENCLRR_TZC1EN		BIT(11)
+#define RCC_MP_APB5ENCLRR_TZC2EN		BIT(12)
+#define RCC_MP_APB5ENCLRR_TZPCEN		BIT(13)
+#define RCC_MP_APB5ENCLRR_IWDG1APBEN		BIT(15)
+#define RCC_MP_APB5ENCLRR_BSECEN		BIT(16)
+#define RCC_MP_APB5ENCLRR_STGENEN		BIT(20)
+
+/* RCC_MP_AHB5ENSETR register fields */
+#define RCC_MP_AHB5ENSETR_GPIOZEN		BIT(0)
+#define RCC_MP_AHB5ENSETR_CRYP1EN		BIT(4)
+#define RCC_MP_AHB5ENSETR_HASH1EN		BIT(5)
+#define RCC_MP_AHB5ENSETR_RNG1EN		BIT(6)
+#define RCC_MP_AHB5ENSETR_BKPSRAMEN		BIT(8)
+#define RCC_MP_AHB5ENSETR_AXIMCEN		BIT(16)
+
+/* RCC_MP_AHB5ENCLRR register fields */
+#define RCC_MP_AHB5ENCLRR_GPIOZEN		BIT(0)
+#define RCC_MP_AHB5ENCLRR_CRYP1EN		BIT(4)
+#define RCC_MP_AHB5ENCLRR_HASH1EN		BIT(5)
+#define RCC_MP_AHB5ENCLRR_RNG1EN		BIT(6)
+#define RCC_MP_AHB5ENCLRR_BKPSRAMEN		BIT(8)
+#define RCC_MP_AHB5ENCLRR_AXIMCEN		BIT(16)
+
+/* RCC_MP_AHB6ENSETR register fields */
+#define RCC_MP_AHB6ENSETR_MDMAEN		BIT(0)
+#define RCC_MP_AHB6ENSETR_GPUEN			BIT(5)
+#define RCC_MP_AHB6ENSETR_ETHCKEN		BIT(7)
+#define RCC_MP_AHB6ENSETR_ETHTXEN		BIT(8)
+#define RCC_MP_AHB6ENSETR_ETHRXEN		BIT(9)
+#define RCC_MP_AHB6ENSETR_ETHMACEN		BIT(10)
+#define RCC_MP_AHB6ENSETR_FMCEN			BIT(12)
+#define RCC_MP_AHB6ENSETR_QSPIEN		BIT(14)
+#define RCC_MP_AHB6ENSETR_SDMMC1EN		BIT(16)
+#define RCC_MP_AHB6ENSETR_SDMMC2EN		BIT(17)
+#define RCC_MP_AHB6ENSETR_CRC1EN		BIT(20)
+#define RCC_MP_AHB6ENSETR_USBHEN		BIT(24)
+
+/* RCC_MP_AHB6ENCLRR register fields */
+#define RCC_MP_AHB6ENCLRR_MDMAEN		BIT(0)
+#define RCC_MP_AHB6ENCLRR_GPUEN			BIT(5)
+#define RCC_MP_AHB6ENCLRR_ETHCKEN		BIT(7)
+#define RCC_MP_AHB6ENCLRR_ETHTXEN		BIT(8)
+#define RCC_MP_AHB6ENCLRR_ETHRXEN		BIT(9)
+#define RCC_MP_AHB6ENCLRR_ETHMACEN		BIT(10)
+#define RCC_MP_AHB6ENCLRR_FMCEN			BIT(12)
+#define RCC_MP_AHB6ENCLRR_QSPIEN		BIT(14)
+#define RCC_MP_AHB6ENCLRR_SDMMC1EN		BIT(16)
+#define RCC_MP_AHB6ENCLRR_SDMMC2EN		BIT(17)
+#define RCC_MP_AHB6ENCLRR_CRC1EN		BIT(20)
+#define RCC_MP_AHB6ENCLRR_USBHEN		BIT(24)
+
+/* RCC_MP_TZAHB6ENSETR register fields */
+#define RCC_MP_TZAHB6ENSETR_MDMAEN		BIT(0)
+
+/* RCC_MP_TZAHB6ENCLRR register fields */
+#define RCC_MP_TZAHB6ENCLRR_MDMAEN		BIT(0)
+
+/* RCC_MC_APB4ENSETR register fields */
+#define RCC_MC_APB4ENSETR_LTDCEN		BIT(0)
+#define RCC_MC_APB4ENSETR_DSIEN			BIT(4)
+#define RCC_MC_APB4ENSETR_DDRPERFMEN		BIT(8)
+#define RCC_MC_APB4ENSETR_USBPHYEN		BIT(16)
+#define RCC_MC_APB4ENSETR_STGENROEN		BIT(20)
+
+/* RCC_MC_APB4ENCLRR register fields */
+#define RCC_MC_APB4ENCLRR_LTDCEN		BIT(0)
+#define RCC_MC_APB4ENCLRR_DSIEN			BIT(4)
+#define RCC_MC_APB4ENCLRR_DDRPERFMEN		BIT(8)
+#define RCC_MC_APB4ENCLRR_USBPHYEN		BIT(16)
+#define RCC_MC_APB4ENCLRR_STGENROEN		BIT(20)
+
+/* RCC_MC_APB5ENSETR register fields */
+#define RCC_MC_APB5ENSETR_SPI6EN		BIT(0)
+#define RCC_MC_APB5ENSETR_I2C4EN		BIT(2)
+#define RCC_MC_APB5ENSETR_I2C6EN		BIT(3)
+#define RCC_MC_APB5ENSETR_USART1EN		BIT(4)
+#define RCC_MC_APB5ENSETR_RTCAPBEN		BIT(8)
+#define RCC_MC_APB5ENSETR_TZC1EN		BIT(11)
+#define RCC_MC_APB5ENSETR_TZC2EN		BIT(12)
+#define RCC_MC_APB5ENSETR_TZPCEN		BIT(13)
+#define RCC_MC_APB5ENSETR_BSECEN		BIT(16)
+#define RCC_MC_APB5ENSETR_STGENEN		BIT(20)
+
+/* RCC_MC_APB5ENCLRR register fields */
+#define RCC_MC_APB5ENCLRR_SPI6EN		BIT(0)
+#define RCC_MC_APB5ENCLRR_I2C4EN		BIT(2)
+#define RCC_MC_APB5ENCLRR_I2C6EN		BIT(3)
+#define RCC_MC_APB5ENCLRR_USART1EN		BIT(4)
+#define RCC_MC_APB5ENCLRR_RTCAPBEN		BIT(8)
+#define RCC_MC_APB5ENCLRR_TZC1EN		BIT(11)
+#define RCC_MC_APB5ENCLRR_TZC2EN		BIT(12)
+#define RCC_MC_APB5ENCLRR_TZPCEN		BIT(13)
+#define RCC_MC_APB5ENCLRR_BSECEN		BIT(16)
+#define RCC_MC_APB5ENCLRR_STGENEN		BIT(20)
+
+/* RCC_MC_AHB5ENSETR register fields */
+#define RCC_MC_AHB5ENSETR_GPIOZEN		BIT(0)
+#define RCC_MC_AHB5ENSETR_CRYP1EN		BIT(4)
+#define RCC_MC_AHB5ENSETR_HASH1EN		BIT(5)
+#define RCC_MC_AHB5ENSETR_RNG1EN		BIT(6)
+#define RCC_MC_AHB5ENSETR_BKPSRAMEN		BIT(8)
+
+/* RCC_MC_AHB5ENCLRR register fields */
+#define RCC_MC_AHB5ENCLRR_GPIOZEN		BIT(0)
+#define RCC_MC_AHB5ENCLRR_CRYP1EN		BIT(4)
+#define RCC_MC_AHB5ENCLRR_HASH1EN		BIT(5)
+#define RCC_MC_AHB5ENCLRR_RNG1EN		BIT(6)
+#define RCC_MC_AHB5ENCLRR_BKPSRAMEN		BIT(8)
+
+/* RCC_MC_AHB6ENSETR register fields */
+#define RCC_MC_AHB6ENSETR_MDMAEN		BIT(0)
+#define RCC_MC_AHB6ENSETR_GPUEN			BIT(5)
+#define RCC_MC_AHB6ENSETR_ETHCKEN		BIT(7)
+#define RCC_MC_AHB6ENSETR_ETHTXEN		BIT(8)
+#define RCC_MC_AHB6ENSETR_ETHRXEN		BIT(9)
+#define RCC_MC_AHB6ENSETR_ETHMACEN		BIT(10)
+#define RCC_MC_AHB6ENSETR_FMCEN			BIT(12)
+#define RCC_MC_AHB6ENSETR_QSPIEN		BIT(14)
+#define RCC_MC_AHB6ENSETR_SDMMC1EN		BIT(16)
+#define RCC_MC_AHB6ENSETR_SDMMC2EN		BIT(17)
+#define RCC_MC_AHB6ENSETR_CRC1EN		BIT(20)
+#define RCC_MC_AHB6ENSETR_USBHEN		BIT(24)
+
+/* RCC_MC_AHB6ENCLRR register fields */
+#define RCC_MC_AHB6ENCLRR_MDMAEN		BIT(0)
+#define RCC_MC_AHB6ENCLRR_GPUEN			BIT(5)
+#define RCC_MC_AHB6ENCLRR_ETHCKEN		BIT(7)
+#define RCC_MC_AHB6ENCLRR_ETHTXEN		BIT(8)
+#define RCC_MC_AHB6ENCLRR_ETHRXEN		BIT(9)
+#define RCC_MC_AHB6ENCLRR_ETHMACEN		BIT(10)
+#define RCC_MC_AHB6ENCLRR_FMCEN			BIT(12)
+#define RCC_MC_AHB6ENCLRR_QSPIEN		BIT(14)
+#define RCC_MC_AHB6ENCLRR_SDMMC1EN		BIT(16)
+#define RCC_MC_AHB6ENCLRR_SDMMC2EN		BIT(17)
+#define RCC_MC_AHB6ENCLRR_CRC1EN		BIT(20)
+#define RCC_MC_AHB6ENCLRR_USBHEN		BIT(24)
+
+/* RCC_MP_APB4LPENSETR register fields */
+#define RCC_MP_APB4LPENSETR_LTDCLPEN		BIT(0)
+#define RCC_MP_APB4LPENSETR_DSILPEN		BIT(4)
+#define RCC_MP_APB4LPENSETR_DDRPERFMLPEN	BIT(8)
+#define RCC_MP_APB4LPENSETR_IWDG2APBLPEN	BIT(15)
+#define RCC_MP_APB4LPENSETR_USBPHYLPEN		BIT(16)
+#define RCC_MP_APB4LPENSETR_STGENROLPEN		BIT(20)
+#define RCC_MP_APB4LPENSETR_STGENROSTPEN	BIT(21)
+
+/* RCC_MP_APB4LPENCLRR register fields */
+#define RCC_MP_APB4LPENCLRR_LTDCLPEN		BIT(0)
+#define RCC_MP_APB4LPENCLRR_DSILPEN		BIT(4)
+#define RCC_MP_APB4LPENCLRR_DDRPERFMLPEN	BIT(8)
+#define RCC_MP_APB4LPENCLRR_IWDG2APBLPEN	BIT(15)
+#define RCC_MP_APB4LPENCLRR_USBPHYLPEN		BIT(16)
+#define RCC_MP_APB4LPENCLRR_STGENROLPEN		BIT(20)
+#define RCC_MP_APB4LPENCLRR_STGENROSTPEN	BIT(21)
+
+/* RCC_MP_APB5LPENSETR register fields */
+#define RCC_MP_APB5LPENSETR_SPI6LPEN		BIT(0)
+#define RCC_MP_APB5LPENSETR_I2C4LPEN		BIT(2)
+#define RCC_MP_APB5LPENSETR_I2C6LPEN		BIT(3)
+#define RCC_MP_APB5LPENSETR_USART1LPEN		BIT(4)
+#define RCC_MP_APB5LPENSETR_RTCAPBLPEN		BIT(8)
+#define RCC_MP_APB5LPENSETR_TZC1LPEN		BIT(11)
+#define RCC_MP_APB5LPENSETR_TZC2LPEN		BIT(12)
+#define RCC_MP_APB5LPENSETR_TZPCLPEN		BIT(13)
+#define RCC_MP_APB5LPENSETR_IWDG1APBLPEN	BIT(15)
+#define RCC_MP_APB5LPENSETR_BSECLPEN		BIT(16)
+#define RCC_MP_APB5LPENSETR_STGENLPEN		BIT(20)
+#define RCC_MP_APB5LPENSETR_STGENSTPEN		BIT(21)
+
+/* RCC_MP_APB5LPENCLRR register fields */
+#define RCC_MP_APB5LPENCLRR_SPI6LPEN		BIT(0)
+#define RCC_MP_APB5LPENCLRR_I2C4LPEN		BIT(2)
+#define RCC_MP_APB5LPENCLRR_I2C6LPEN		BIT(3)
+#define RCC_MP_APB5LPENCLRR_USART1LPEN		BIT(4)
+#define RCC_MP_APB5LPENCLRR_RTCAPBLPEN		BIT(8)
+#define RCC_MP_APB5LPENCLRR_TZC1LPEN		BIT(11)
+#define RCC_MP_APB5LPENCLRR_TZC2LPEN		BIT(12)
+#define RCC_MP_APB5LPENCLRR_TZPCLPEN		BIT(13)
+#define RCC_MP_APB5LPENCLRR_IWDG1APBLPEN	BIT(15)
+#define RCC_MP_APB5LPENCLRR_BSECLPEN		BIT(16)
+#define RCC_MP_APB5LPENCLRR_STGENLPEN		BIT(20)
+#define RCC_MP_APB5LPENCLRR_STGENSTPEN		BIT(21)
+
+/* RCC_MP_AHB5LPENSETR register fields */
+#define RCC_MP_AHB5LPENSETR_GPIOZLPEN		BIT(0)
+#define RCC_MP_AHB5LPENSETR_CRYP1LPEN		BIT(4)
+#define RCC_MP_AHB5LPENSETR_HASH1LPEN		BIT(5)
+#define RCC_MP_AHB5LPENSETR_RNG1LPEN		BIT(6)
+#define RCC_MP_AHB5LPENSETR_BKPSRAMLPEN		BIT(8)
+
+/* RCC_MP_AHB5LPENCLRR register fields */
+#define RCC_MP_AHB5LPENCLRR_GPIOZLPEN		BIT(0)
+#define RCC_MP_AHB5LPENCLRR_CRYP1LPEN		BIT(4)
+#define RCC_MP_AHB5LPENCLRR_HASH1LPEN		BIT(5)
+#define RCC_MP_AHB5LPENCLRR_RNG1LPEN		BIT(6)
+#define RCC_MP_AHB5LPENCLRR_BKPSRAMLPEN		BIT(8)
+
+/* RCC_MP_AHB6LPENSETR register fields */
+#define RCC_MP_AHB6LPENSETR_MDMALPEN		BIT(0)
+#define RCC_MP_AHB6LPENSETR_GPULPEN		BIT(5)
+#define RCC_MP_AHB6LPENSETR_ETHCKLPEN		BIT(7)
+#define RCC_MP_AHB6LPENSETR_ETHTXLPEN		BIT(8)
+#define RCC_MP_AHB6LPENSETR_ETHRXLPEN		BIT(9)
+#define RCC_MP_AHB6LPENSETR_ETHMACLPEN		BIT(10)
+#define RCC_MP_AHB6LPENSETR_ETHSTPEN		BIT(11)
+#define RCC_MP_AHB6LPENSETR_FMCLPEN		BIT(12)
+#define RCC_MP_AHB6LPENSETR_QSPILPEN		BIT(14)
+#define RCC_MP_AHB6LPENSETR_SDMMC1LPEN		BIT(16)
+#define RCC_MP_AHB6LPENSETR_SDMMC2LPEN		BIT(17)
+#define RCC_MP_AHB6LPENSETR_CRC1LPEN		BIT(20)
+#define RCC_MP_AHB6LPENSETR_USBHLPEN		BIT(24)
+
+/* RCC_MP_AHB6LPENCLRR register fields */
+#define RCC_MP_AHB6LPENCLRR_MDMALPEN		BIT(0)
+#define RCC_MP_AHB6LPENCLRR_GPULPEN		BIT(5)
+#define RCC_MP_AHB6LPENCLRR_ETHCKLPEN		BIT(7)
+#define RCC_MP_AHB6LPENCLRR_ETHTXLPEN		BIT(8)
+#define RCC_MP_AHB6LPENCLRR_ETHRXLPEN		BIT(9)
+#define RCC_MP_AHB6LPENCLRR_ETHMACLPEN		BIT(10)
+#define RCC_MP_AHB6LPENCLRR_ETHSTPEN		BIT(11)
+#define RCC_MP_AHB6LPENCLRR_FMCLPEN		BIT(12)
+#define RCC_MP_AHB6LPENCLRR_QSPILPEN		BIT(14)
+#define RCC_MP_AHB6LPENCLRR_SDMMC1LPEN		BIT(16)
+#define RCC_MP_AHB6LPENCLRR_SDMMC2LPEN		BIT(17)
+#define RCC_MP_AHB6LPENCLRR_CRC1LPEN		BIT(20)
+#define RCC_MP_AHB6LPENCLRR_USBHLPEN		BIT(24)
+
+/* RCC_MP_TZAHB6LPENSETR register fields */
+#define RCC_MP_TZAHB6LPENSETR_MDMALPEN		BIT(0)
+
+/* RCC_MP_TZAHB6LPENCLRR register fields */
+#define RCC_MP_TZAHB6LPENCLRR_MDMALPEN		BIT(0)
+
+/* RCC_MC_APB4LPENSETR register fields */
+#define RCC_MC_APB4LPENSETR_LTDCLPEN		BIT(0)
+#define RCC_MC_APB4LPENSETR_DSILPEN		BIT(4)
+#define RCC_MC_APB4LPENSETR_DDRPERFMLPEN	BIT(8)
+#define RCC_MC_APB4LPENSETR_USBPHYLPEN		BIT(16)
+#define RCC_MC_APB4LPENSETR_STGENROLPEN		BIT(20)
+#define RCC_MC_APB4LPENSETR_STGENROSTPEN	BIT(21)
+
+/* RCC_MC_APB4LPENCLRR register fields */
+#define RCC_MC_APB4LPENCLRR_LTDCLPEN		BIT(0)
+#define RCC_MC_APB4LPENCLRR_DSILPEN		BIT(4)
+#define RCC_MC_APB4LPENCLRR_DDRPERFMLPEN	BIT(8)
+#define RCC_MC_APB4LPENCLRR_USBPHYLPEN		BIT(16)
+#define RCC_MC_APB4LPENCLRR_STGENROLPEN		BIT(20)
+#define RCC_MC_APB4LPENCLRR_STGENROSTPEN	BIT(21)
+
+/* RCC_MC_APB5LPENSETR register fields */
+#define RCC_MC_APB5LPENSETR_SPI6LPEN		BIT(0)
+#define RCC_MC_APB5LPENSETR_I2C4LPEN		BIT(2)
+#define RCC_MC_APB5LPENSETR_I2C6LPEN		BIT(3)
+#define RCC_MC_APB5LPENSETR_USART1LPEN		BIT(4)
+#define RCC_MC_APB5LPENSETR_RTCAPBLPEN		BIT(8)
+#define RCC_MC_APB5LPENSETR_TZC1LPEN		BIT(11)
+#define RCC_MC_APB5LPENSETR_TZC2LPEN		BIT(12)
+#define RCC_MC_APB5LPENSETR_TZPCLPEN		BIT(13)
+#define RCC_MC_APB5LPENSETR_BSECLPEN		BIT(16)
+#define RCC_MC_APB5LPENSETR_STGENLPEN		BIT(20)
+#define RCC_MC_APB5LPENSETR_STGENSTPEN		BIT(21)
+
+/* RCC_MC_APB5LPENCLRR register fields */
+#define RCC_MC_APB5LPENCLRR_SPI6LPEN		BIT(0)
+#define RCC_MC_APB5LPENCLRR_I2C4LPEN		BIT(2)
+#define RCC_MC_APB5LPENCLRR_I2C6LPEN		BIT(3)
+#define RCC_MC_APB5LPENCLRR_USART1LPEN		BIT(4)
+#define RCC_MC_APB5LPENCLRR_RTCAPBLPEN		BIT(8)
+#define RCC_MC_APB5LPENCLRR_TZC1LPEN		BIT(11)
+#define RCC_MC_APB5LPENCLRR_TZC2LPEN		BIT(12)
+#define RCC_MC_APB5LPENCLRR_TZPCLPEN		BIT(13)
+#define RCC_MC_APB5LPENCLRR_BSECLPEN		BIT(16)
+#define RCC_MC_APB5LPENCLRR_STGENLPEN		BIT(20)
+#define RCC_MC_APB5LPENCLRR_STGENSTPEN		BIT(21)
+
+/* RCC_MC_AHB5LPENSETR register fields */
+#define RCC_MC_AHB5LPENSETR_GPIOZLPEN		BIT(0)
+#define RCC_MC_AHB5LPENSETR_CRYP1LPEN		BIT(4)
+#define RCC_MC_AHB5LPENSETR_HASH1LPEN		BIT(5)
+#define RCC_MC_AHB5LPENSETR_RNG1LPEN		BIT(6)
+#define RCC_MC_AHB5LPENSETR_BKPSRAMLPEN		BIT(8)
+
+/* RCC_MC_AHB5LPENCLRR register fields */
+#define RCC_MC_AHB5LPENCLRR_GPIOZLPEN		BIT(0)
+#define RCC_MC_AHB5LPENCLRR_CRYP1LPEN		BIT(4)
+#define RCC_MC_AHB5LPENCLRR_HASH1LPEN		BIT(5)
+#define RCC_MC_AHB5LPENCLRR_RNG1LPEN		BIT(6)
+#define RCC_MC_AHB5LPENCLRR_BKPSRAMLPEN		BIT(8)
+
+/* RCC_MC_AHB6LPENSETR register fields */
+#define RCC_MC_AHB6LPENSETR_MDMALPEN		BIT(0)
+#define RCC_MC_AHB6LPENSETR_GPULPEN		BIT(5)
+#define RCC_MC_AHB6LPENSETR_ETHCKLPEN		BIT(7)
+#define RCC_MC_AHB6LPENSETR_ETHTXLPEN		BIT(8)
+#define RCC_MC_AHB6LPENSETR_ETHRXLPEN		BIT(9)
+#define RCC_MC_AHB6LPENSETR_ETHMACLPEN		BIT(10)
+#define RCC_MC_AHB6LPENSETR_ETHSTPEN		BIT(11)
+#define RCC_MC_AHB6LPENSETR_FMCLPEN		BIT(12)
+#define RCC_MC_AHB6LPENSETR_QSPILPEN		BIT(14)
+#define RCC_MC_AHB6LPENSETR_SDMMC1LPEN		BIT(16)
+#define RCC_MC_AHB6LPENSETR_SDMMC2LPEN		BIT(17)
+#define RCC_MC_AHB6LPENSETR_CRC1LPEN		BIT(20)
+#define RCC_MC_AHB6LPENSETR_USBHLPEN		BIT(24)
+
+/* RCC_MC_AHB6LPENCLRR register fields */
+#define RCC_MC_AHB6LPENCLRR_MDMALPEN		BIT(0)
+#define RCC_MC_AHB6LPENCLRR_GPULPEN		BIT(5)
+#define RCC_MC_AHB6LPENCLRR_ETHCKLPEN		BIT(7)
+#define RCC_MC_AHB6LPENCLRR_ETHTXLPEN		BIT(8)
+#define RCC_MC_AHB6LPENCLRR_ETHRXLPEN		BIT(9)
+#define RCC_MC_AHB6LPENCLRR_ETHMACLPEN		BIT(10)
+#define RCC_MC_AHB6LPENCLRR_ETHSTPEN		BIT(11)
+#define RCC_MC_AHB6LPENCLRR_FMCLPEN		BIT(12)
+#define RCC_MC_AHB6LPENCLRR_QSPILPEN		BIT(14)
+#define RCC_MC_AHB6LPENCLRR_SDMMC1LPEN		BIT(16)
+#define RCC_MC_AHB6LPENCLRR_SDMMC2LPEN		BIT(17)
+#define RCC_MC_AHB6LPENCLRR_CRC1LPEN		BIT(20)
+#define RCC_MC_AHB6LPENCLRR_USBHLPEN		BIT(24)
+
+/* RCC_BR_RSTSCLRR register fields */
+#define RCC_BR_RSTSCLRR_PORRSTF			BIT(0)
+#define RCC_BR_RSTSCLRR_BORRSTF			BIT(1)
+#define RCC_BR_RSTSCLRR_PADRSTF			BIT(2)
+#define RCC_BR_RSTSCLRR_HCSSRSTF		BIT(3)
+#define RCC_BR_RSTSCLRR_VCORERSTF		BIT(4)
+#define RCC_BR_RSTSCLRR_MPSYSRSTF		BIT(6)
+#define RCC_BR_RSTSCLRR_MCSYSRSTF		BIT(7)
+#define RCC_BR_RSTSCLRR_IWDG1RSTF		BIT(8)
+#define RCC_BR_RSTSCLRR_IWDG2RSTF		BIT(9)
+#define RCC_BR_RSTSCLRR_MPUP0RSTF		BIT(13)
+#define RCC_BR_RSTSCLRR_MPUP1RSTF		BIT(14)
+
+/* RCC_MP_GRSTCSETR register fields */
+#define RCC_MP_GRSTCSETR_MPSYSRST		BIT(0)
+#define RCC_MP_GRSTCSETR_MCURST			BIT(1)
+#define RCC_MP_GRSTCSETR_MPUP0RST		BIT(4)
+#define RCC_MP_GRSTCSETR_MPUP1RST		BIT(5)
+
+/* RCC_MP_RSTSCLRR register fields */
+#define RCC_MP_RSTSCLRR_PORRSTF			BIT(0)
+#define RCC_MP_RSTSCLRR_BORRSTF			BIT(1)
+#define RCC_MP_RSTSCLRR_PADRSTF			BIT(2)
+#define RCC_MP_RSTSCLRR_HCSSRSTF		BIT(3)
+#define RCC_MP_RSTSCLRR_VCORERSTF		BIT(4)
+#define RCC_MP_RSTSCLRR_MPSYSRSTF		BIT(6)
+#define RCC_MP_RSTSCLRR_MCSYSRSTF		BIT(7)
+#define RCC_MP_RSTSCLRR_IWDG1RSTF		BIT(8)
+#define RCC_MP_RSTSCLRR_IWDG2RSTF		BIT(9)
+#define RCC_MP_RSTSCLRR_STDBYRSTF		BIT(11)
+#define RCC_MP_RSTSCLRR_CSTDBYRSTF		BIT(12)
+#define RCC_MP_RSTSCLRR_MPUP0RSTF		BIT(13)
+#define RCC_MP_RSTSCLRR_MPUP1RSTF		BIT(14)
+#define RCC_MP_RSTSCLRR_SPARE			BIT(15)
+
+/* RCC_MP_IWDGFZSETR register fields */
+#define RCC_MP_IWDGFZSETR_FZ_IWDG1		BIT(0)
+#define RCC_MP_IWDGFZSETR_FZ_IWDG2		BIT(1)
+
+/* RCC_MP_IWDGFZCLRR register fields */
+#define RCC_MP_IWDGFZCLRR_FZ_IWDG1		BIT(0)
+#define RCC_MP_IWDGFZCLRR_FZ_IWDG2		BIT(1)
+
+/* RCC_MP_CIER register fields */
+#define RCC_MP_CIER_LSIRDYIE			BIT(0)
+#define RCC_MP_CIER_LSERDYIE			BIT(1)
+#define RCC_MP_CIER_HSIRDYIE			BIT(2)
+#define RCC_MP_CIER_HSERDYIE			BIT(3)
+#define RCC_MP_CIER_CSIRDYIE			BIT(4)
+#define RCC_MP_CIER_PLL1DYIE			BIT(8)
+#define RCC_MP_CIER_PLL2DYIE			BIT(9)
+#define RCC_MP_CIER_PLL3DYIE			BIT(10)
+#define RCC_MP_CIER_PLL4DYIE			BIT(11)
+#define RCC_MP_CIER_LSECSSIE			BIT(16)
+#define RCC_MP_CIER_WKUPIE			BIT(20)
+
+/* RCC_MP_CIFR register fields */
+#define RCC_MP_CIFR_MASK			U(0x110F1F)
+#define RCC_MP_CIFR_LSIRDYF			BIT(0)
+#define RCC_MP_CIFR_LSERDYF			BIT(1)
+#define RCC_MP_CIFR_HSIRDYF			BIT(2)
+#define RCC_MP_CIFR_HSERDYF			BIT(3)
+#define RCC_MP_CIFR_CSIRDYF			BIT(4)
+#define RCC_MP_CIFR_PLL1DYF			BIT(8)
+#define RCC_MP_CIFR_PLL2DYF			BIT(9)
+#define RCC_MP_CIFR_PLL3DYF			BIT(10)
+#define RCC_MP_CIFR_PLL4DYF			BIT(11)
+#define RCC_MP_CIFR_LSECSSF			BIT(16)
+#define RCC_MP_CIFR_WKUPF			BIT(20)
+
+/* RCC_PWRLPDLYCR register fields */
+#define RCC_PWRLPDLYCR_PWRLP_DLY_MASK		GENMASK(21, 0)
+#define RCC_PWRLPDLYCR_PWRLP_DLY_SHIFT		0
+#define RCC_PWRLPDLYCR_MCTMPSKP			BIT(24)
+
+/* RCC_MP_RSTSSETR register fields */
+#define RCC_MP_RSTSSETR_PORRSTF			BIT(0)
+#define RCC_MP_RSTSSETR_BORRSTF			BIT(1)
+#define RCC_MP_RSTSSETR_PADRSTF			BIT(2)
+#define RCC_MP_RSTSSETR_HCSSRSTF		BIT(3)
+#define RCC_MP_RSTSSETR_VCORERSTF		BIT(4)
+#define RCC_MP_RSTSSETR_MPSYSRSTF		BIT(6)
+#define RCC_MP_RSTSSETR_MCSYSRSTF		BIT(7)
+#define RCC_MP_RSTSSETR_IWDG1RSTF		BIT(8)
+#define RCC_MP_RSTSSETR_IWDG2RSTF		BIT(9)
+#define RCC_MP_RSTSSETR_STDBYRSTF		BIT(11)
+#define RCC_MP_RSTSSETR_CSTDBYRSTF		BIT(12)
+#define RCC_MP_RSTSSETR_MPUP0RSTF		BIT(13)
+#define RCC_MP_RSTSSETR_MPUP1RSTF		BIT(14)
+#define RCC_MP_RSTSSETR_SPARE			BIT(15)
+
+/* RCC_MCO1CFGR register fields */
+#define RCC_MCO1CFGR_MCO1SEL_MASK		GENMASK(2, 0)
+#define RCC_MCO1CFGR_MCO1SEL_SHIFT		0
+#define RCC_MCO1CFGR_MCO1DIV_MASK		GENMASK(7, 4)
+#define RCC_MCO1CFGR_MCO1DIV_SHIFT		4
+#define RCC_MCO1CFGR_MCO1ON			BIT(12)
+
+/* RCC_MCO2CFGR register fields */
+#define RCC_MCO2CFGR_MCO2SEL_MASK		GENMASK(2, 0)
+#define RCC_MCO2CFGR_MCO2SEL_SHIFT		0
+#define RCC_MCO2CFGR_MCO2DIV_MASK		GENMASK(7, 4)
+#define RCC_MCO2CFGR_MCO2DIV_SHIFT		4
+#define RCC_MCO2CFGR_MCO2ON			BIT(12)
+
+/* RCC_OCRDYR register fields */
+#define RCC_OCRDYR_HSIRDY			BIT(0)
+#define RCC_OCRDYR_HSIDIVRDY			BIT(2)
+#define RCC_OCRDYR_CSIRDY			BIT(4)
+#define RCC_OCRDYR_HSERDY			BIT(8)
+#define RCC_OCRDYR_MPUCKRDY			BIT(23)
+#define RCC_OCRDYR_AXICKRDY			BIT(24)
+#define RCC_OCRDYR_CKREST			BIT(25)
+
+/* RCC_DBGCFGR register fields */
+#define RCC_DBGCFGR_TRACEDIV_MASK		GENMASK(2, 0)
+#define RCC_DBGCFGR_TRACEDIV_SHIFT		0
+#define RCC_DBGCFGR_DBGCKEN			BIT(8)
+#define RCC_DBGCFGR_TRACECKEN			BIT(9)
+#define RCC_DBGCFGR_DBGRST			BIT(12)
+
+/* RCC_RCK3SELR register fields */
+#define RCC_RCK3SELR_PLL3SRC_MASK		GENMASK(1, 0)
+#define RCC_RCK3SELR_PLL3SRC_SHIFT		0
+#define RCC_RCK3SELR_PLL3SRCRDY			BIT(31)
+
+/* RCC_RCK4SELR register fields */
+#define RCC_RCK4SELR_PLL4SRC_MASK		GENMASK(1, 0)
+#define RCC_RCK4SELR_PLL4SRC_SHIFT		0
+#define RCC_RCK4SELR_PLL4SRCRDY			BIT(31)
+
+/* RCC_TIMG1PRER register fields */
+#define RCC_TIMG1PRER_TIMG1PRE			BIT(0)
+#define RCC_TIMG1PRER_TIMG1PRERDY		BIT(31)
+
+/* RCC_TIMG2PRER register fields */
+#define RCC_TIMG2PRER_TIMG2PRE			BIT(0)
+#define RCC_TIMG2PRER_TIMG2PRERDY		BIT(31)
+
+/* RCC_MCUDIVR register fields */
+#define RCC_MCUDIVR_MCUDIV_MASK			GENMASK(3, 0)
+#define RCC_MCUDIVR_MCUDIV_SHIFT		0
+#define RCC_MCUDIVR_MCUDIVRDY			BIT(31)
+
+/* RCC_APB1DIVR register fields */
+#define RCC_APB1DIVR_APB1DIV_MASK		GENMASK(2, 0)
+#define RCC_APB1DIVR_APB1DIV_SHIFT		0
+#define RCC_APB1DIVR_APB1DIVRDY			BIT(31)
+
+/* RCC_APB2DIVR register fields */
+#define RCC_APB2DIVR_APB2DIV_MASK		GENMASK(2, 0)
+#define RCC_APB2DIVR_APB2DIV_SHIFT		0
+#define RCC_APB2DIVR_APB2DIVRDY			BIT(31)
+
+/* RCC_APB3DIVR register fields */
+#define RCC_APB3DIVR_APB3DIV_MASK		GENMASK(2, 0)
+#define RCC_APB3DIVR_APB3DIV_SHIFT		0
+#define RCC_APB3DIVR_APB3DIVRDY			BIT(31)
+
+/* RCC_PLL3CR register fields */
+#define RCC_PLL3CR_PLLON			BIT(0)
+#define RCC_PLL3CR_PLL3RDY			BIT(1)
+#define RCC_PLL3CR_SSCG_CTRL			BIT(2)
+#define RCC_PLL3CR_DIVPEN			BIT(4)
+#define RCC_PLL3CR_DIVQEN			BIT(5)
+#define RCC_PLL3CR_DIVREN			BIT(6)
+
+/* RCC_PLL3CFGR1 register fields */
+#define RCC_PLL3CFGR1_DIVN_MASK			GENMASK(8, 0)
+#define RCC_PLL3CFGR1_DIVN_SHIFT		0
+#define RCC_PLL3CFGR1_DIVM3_MASK		GENMASK(21, 16)
+#define RCC_PLL3CFGR1_DIVM3_SHIFT		16
+#define RCC_PLL3CFGR1_IFRGE_MASK		GENMASK(25, 24)
+#define RCC_PLL3CFGR1_IFRGE_SHIFT		24
+
+/* RCC_PLL3CFGR2 register fields */
+#define RCC_PLL3CFGR2_DIVP_MASK			GENMASK(6, 0)
+#define RCC_PLL3CFGR2_DIVP_SHIFT		0
+#define RCC_PLL3CFGR2_DIVQ_MASK			GENMASK(14, 8)
+#define RCC_PLL3CFGR2_DIVQ_SHIFT		8
+#define RCC_PLL3CFGR2_DIVR_MASK			GENMASK(22, 16)
+#define RCC_PLL3CFGR2_DIVR_SHIFT		16
+
+/* RCC_PLL3FRACR register fields */
+#define RCC_PLL3FRACR_FRACV_MASK		GENMASK(15, 3)
+#define RCC_PLL3FRACR_FRACV_SHIFT		3
+#define RCC_PLL3FRACR_FRACLE			BIT(16)
+
+/* RCC_PLL3CSGR register fields */
+#define RCC_PLL3CSGR_MOD_PER_MASK		GENMASK(12, 0)
+#define RCC_PLL3CSGR_MOD_PER_SHIFT		0
+#define RCC_PLL3CSGR_TPDFN_DIS			BIT(13)
+#define RCC_PLL3CSGR_RPDFN_DIS			BIT(14)
+#define RCC_PLL3CSGR_SSCG_MODE			BIT(15)
+#define RCC_PLL3CSGR_INC_STEP_MASK		GENMASK(30, 16)
+#define RCC_PLL3CSGR_INC_STEP_SHIFT		16
+
+/* RCC_PLL4CR register fields */
+#define RCC_PLL4CR_PLLON			BIT(0)
+#define RCC_PLL4CR_PLL4RDY			BIT(1)
+#define RCC_PLL4CR_SSCG_CTRL			BIT(2)
+#define RCC_PLL4CR_DIVPEN			BIT(4)
+#define RCC_PLL4CR_DIVQEN			BIT(5)
+#define RCC_PLL4CR_DIVREN			BIT(6)
+
+/* RCC_PLL4CFGR1 register fields */
+#define RCC_PLL4CFGR1_DIVN_MASK			GENMASK(8, 0)
+#define RCC_PLL4CFGR1_DIVN_SHIFT		0
+#define RCC_PLL4CFGR1_DIVM4_MASK		GENMASK(21, 16)
+#define RCC_PLL4CFGR1_DIVM4_SHIFT		16
+#define RCC_PLL4CFGR1_IFRGE_MASK		GENMASK(25, 24)
+#define RCC_PLL4CFGR1_IFRGE_SHIFT		24
+
+/* RCC_PLL4CFGR2 register fields */
+#define RCC_PLL4CFGR2_DIVP_MASK			GENMASK(6, 0)
+#define RCC_PLL4CFGR2_DIVP_SHIFT		0
+#define RCC_PLL4CFGR2_DIVQ_MASK			GENMASK(14, 8)
+#define RCC_PLL4CFGR2_DIVQ_SHIFT		8
+#define RCC_PLL4CFGR2_DIVR_MASK			GENMASK(22, 16)
+#define RCC_PLL4CFGR2_DIVR_SHIFT		16
+
+/* RCC_PLL4FRACR register fields */
+#define RCC_PLL4FRACR_FRACV_MASK		GENMASK(15, 3)
+#define RCC_PLL4FRACR_FRACV_SHIFT		3
+#define RCC_PLL4FRACR_FRACLE			BIT(16)
+
+/* RCC_PLL4CSGR register fields */
+#define RCC_PLL4CSGR_MOD_PER_MASK		GENMASK(12, 0)
+#define RCC_PLL4CSGR_MOD_PER_SHIFT		0
+#define RCC_PLL4CSGR_TPDFN_DIS			BIT(13)
+#define RCC_PLL4CSGR_RPDFN_DIS			BIT(14)
+#define RCC_PLL4CSGR_SSCG_MODE			BIT(15)
+#define RCC_PLL4CSGR_INC_STEP_MASK		GENMASK(30, 16)
+#define RCC_PLL4CSGR_INC_STEP_SHIFT		16
+
 /* RCC_I2C12CKSELR register fields */
 #define RCC_I2C12CKSELR_I2C12SRC_MASK		GENMASK(2, 0)
 #define RCC_I2C12CKSELR_I2C12SRC_SHIFT		0
@@ -520,11 +1170,40 @@
 #define RCC_I2C35CKSELR_I2C35SRC_MASK		GENMASK(2, 0)
 #define RCC_I2C35CKSELR_I2C35SRC_SHIFT		0
 
+/* RCC_SAI1CKSELR register fields */
+#define RCC_SAI1CKSELR_SAI1SRC_MASK		GENMASK(2, 0)
+#define RCC_SAI1CKSELR_SAI1SRC_SHIFT		0
+
+/* RCC_SAI2CKSELR register fields */
+#define RCC_SAI2CKSELR_SAI2SRC_MASK		GENMASK(2, 0)
+#define RCC_SAI2CKSELR_SAI2SRC_SHIFT		0
+
+/* RCC_SAI3CKSELR register fields */
+#define RCC_SAI3CKSELR_SAI3SRC_MASK		GENMASK(2, 0)
+#define RCC_SAI3CKSELR_SAI3SRC_SHIFT		0
+
+/* RCC_SAI4CKSELR register fields */
+#define RCC_SAI4CKSELR_SAI4SRC_MASK		GENMASK(2, 0)
+#define RCC_SAI4CKSELR_SAI4SRC_SHIFT		0
+
+/* RCC_SPI2S1CKSELR register fields */
+#define RCC_SPI2S1CKSELR_SPI1SRC_MASK		GENMASK(2, 0)
+#define RCC_SPI2S1CKSELR_SPI1SRC_SHIFT		0
+
+/* RCC_SPI2S23CKSELR register fields */
+#define RCC_SPI2S23CKSELR_SPI23SRC_MASK		GENMASK(2, 0)
+#define RCC_SPI2S23CKSELR_SPI23SRC_SHIFT	0
+
+/* RCC_SPI45CKSELR register fields */
+#define RCC_SPI45CKSELR_SPI45SRC_MASK		GENMASK(2, 0)
+#define RCC_SPI45CKSELR_SPI45SRC_SHIFT		0
+
 /* RCC_UART6CKSELR register fields */
 #define RCC_UART6CKSELR_UART6SRC_MASK		GENMASK(2, 0)
 #define RCC_UART6CKSELR_UART6SRC_SHIFT		0
 
 /* RCC_UART24CKSELR register fields */
+#define RCC_UART24CKSELR_HSI			0x00000002
 #define RCC_UART24CKSELR_UART24SRC_MASK		GENMASK(2, 0)
 #define RCC_UART24CKSELR_UART24SRC_SHIFT	0
 
@@ -547,6 +1226,8 @@
 /* RCC_ETHCKSELR register fields */
 #define RCC_ETHCKSELR_ETHSRC_MASK		GENMASK(1, 0)
 #define RCC_ETHCKSELR_ETHSRC_SHIFT		0
+#define RCC_ETHCKSELR_ETHPTPDIV_MASK		GENMASK(7, 4)
+#define RCC_ETHCKSELR_ETHPTPDIV_SHIFT		4
 
 /* RCC_QSPICKSELR register fields */
 #define RCC_QSPICKSELR_QSPISRC_MASK		GENMASK(1, 0)
@@ -556,10 +1237,1092 @@
 #define RCC_FMCCKSELR_FMCSRC_MASK		GENMASK(1, 0)
 #define RCC_FMCCKSELR_FMCSRC_SHIFT		0
 
+/* RCC_FDCANCKSELR register fields */
+#define RCC_FDCANCKSELR_FDCANSRC_MASK		GENMASK(1, 0)
+#define RCC_FDCANCKSELR_FDCANSRC_SHIFT		0
+
+/* RCC_SPDIFCKSELR register fields */
+#define RCC_SPDIFCKSELR_SPDIFSRC_MASK		GENMASK(1, 0)
+#define RCC_SPDIFCKSELR_SPDIFSRC_SHIFT		0
+
+/* RCC_CECCKSELR register fields */
+#define RCC_CECCKSELR_CECSRC_MASK		GENMASK(1, 0)
+#define RCC_CECCKSELR_CECSRC_SHIFT		0
+
 /* RCC_USBCKSELR register fields */
 #define RCC_USBCKSELR_USBPHYSRC_MASK		GENMASK(1, 0)
 #define RCC_USBCKSELR_USBPHYSRC_SHIFT		0
+#define RCC_USBCKSELR_USBOSRC			BIT(4)
 #define RCC_USBCKSELR_USBOSRC_MASK		BIT(4)
 #define RCC_USBCKSELR_USBOSRC_SHIFT		4
 
+/* RCC_RNG2CKSELR register fields */
+#define RCC_RNG2CKSELR_RNG2SRC_MASK		GENMASK(1, 0)
+#define RCC_RNG2CKSELR_RNG2SRC_SHIFT		0
+
+/* RCC_DSICKSELR register fields */
+#define RCC_DSICKSELR_DSISRC			BIT(0)
+
+/* RCC_ADCCKSELR register fields */
+#define RCC_ADCCKSELR_ADCSRC_MASK		GENMASK(1, 0)
+#define RCC_ADCCKSELR_ADCSRC_SHIFT		0
+
+/* RCC_LPTIM45CKSELR register fields */
+#define RCC_LPTIM45CKSELR_LPTIM45SRC_MASK	GENMASK(2, 0)
+#define RCC_LPTIM45CKSELR_LPTIM45SRC_SHIFT	0
+
+/* RCC_LPTIM23CKSELR register fields */
+#define RCC_LPTIM23CKSELR_LPTIM23SRC_MASK	GENMASK(2, 0)
+#define RCC_LPTIM23CKSELR_LPTIM23SRC_SHIFT	0
+
+/* RCC_LPTIM1CKSELR register fields */
+#define RCC_LPTIM1CKSELR_LPTIM1SRC_MASK		GENMASK(2, 0)
+#define RCC_LPTIM1CKSELR_LPTIM1SRC_SHIFT	0
+
+/* RCC_APB1RSTSETR register fields */
+#define RCC_APB1RSTSETR_TIM2RST			BIT(0)
+#define RCC_APB1RSTSETR_TIM3RST			BIT(1)
+#define RCC_APB1RSTSETR_TIM4RST			BIT(2)
+#define RCC_APB1RSTSETR_TIM5RST			BIT(3)
+#define RCC_APB1RSTSETR_TIM6RST			BIT(4)
+#define RCC_APB1RSTSETR_TIM7RST			BIT(5)
+#define RCC_APB1RSTSETR_TIM12RST		BIT(6)
+#define RCC_APB1RSTSETR_TIM13RST		BIT(7)
+#define RCC_APB1RSTSETR_TIM14RST		BIT(8)
+#define RCC_APB1RSTSETR_LPTIM1RST		BIT(9)
+#define RCC_APB1RSTSETR_SPI2RST			BIT(11)
+#define RCC_APB1RSTSETR_SPI3RST			BIT(12)
+#define RCC_APB1RSTSETR_USART2RST		BIT(14)
+#define RCC_APB1RSTSETR_USART3RST		BIT(15)
+#define RCC_APB1RSTSETR_UART4RST		BIT(16)
+#define RCC_APB1RSTSETR_UART5RST		BIT(17)
+#define RCC_APB1RSTSETR_UART7RST		BIT(18)
+#define RCC_APB1RSTSETR_UART8RST		BIT(19)
+#define RCC_APB1RSTSETR_I2C1RST			BIT(21)
+#define RCC_APB1RSTSETR_I2C2RST			BIT(22)
+#define RCC_APB1RSTSETR_I2C3RST			BIT(23)
+#define RCC_APB1RSTSETR_I2C5RST			BIT(24)
+#define RCC_APB1RSTSETR_SPDIFRST		BIT(26)
+#define RCC_APB1RSTSETR_CECRST			BIT(27)
+#define RCC_APB1RSTSETR_DAC12RST		BIT(29)
+#define RCC_APB1RSTSETR_MDIOSRST		BIT(31)
+
+/* RCC_APB1RSTCLRR register fields */
+#define RCC_APB1RSTCLRR_TIM2RST			BIT(0)
+#define RCC_APB1RSTCLRR_TIM3RST			BIT(1)
+#define RCC_APB1RSTCLRR_TIM4RST			BIT(2)
+#define RCC_APB1RSTCLRR_TIM5RST			BIT(3)
+#define RCC_APB1RSTCLRR_TIM6RST			BIT(4)
+#define RCC_APB1RSTCLRR_TIM7RST			BIT(5)
+#define RCC_APB1RSTCLRR_TIM12RST		BIT(6)
+#define RCC_APB1RSTCLRR_TIM13RST		BIT(7)
+#define RCC_APB1RSTCLRR_TIM14RST		BIT(8)
+#define RCC_APB1RSTCLRR_LPTIM1RST		BIT(9)
+#define RCC_APB1RSTCLRR_SPI2RST			BIT(11)
+#define RCC_APB1RSTCLRR_SPI3RST			BIT(12)
+#define RCC_APB1RSTCLRR_USART2RST		BIT(14)
+#define RCC_APB1RSTCLRR_USART3RST		BIT(15)
+#define RCC_APB1RSTCLRR_UART4RST		BIT(16)
+#define RCC_APB1RSTCLRR_UART5RST		BIT(17)
+#define RCC_APB1RSTCLRR_UART7RST		BIT(18)
+#define RCC_APB1RSTCLRR_UART8RST		BIT(19)
+#define RCC_APB1RSTCLRR_I2C1RST			BIT(21)
+#define RCC_APB1RSTCLRR_I2C2RST			BIT(22)
+#define RCC_APB1RSTCLRR_I2C3RST			BIT(23)
+#define RCC_APB1RSTCLRR_I2C5RST			BIT(24)
+#define RCC_APB1RSTCLRR_SPDIFRST		BIT(26)
+#define RCC_APB1RSTCLRR_CECRST			BIT(27)
+#define RCC_APB1RSTCLRR_DAC12RST		BIT(29)
+#define RCC_APB1RSTCLRR_MDIOSRST		BIT(31)
+
+/* RCC_APB2RSTSETR register fields */
+#define RCC_APB2RSTSETR_TIM1RST			BIT(0)
+#define RCC_APB2RSTSETR_TIM8RST			BIT(1)
+#define RCC_APB2RSTSETR_TIM15RST		BIT(2)
+#define RCC_APB2RSTSETR_TIM16RST		BIT(3)
+#define RCC_APB2RSTSETR_TIM17RST		BIT(4)
+#define RCC_APB2RSTSETR_SPI1RST			BIT(8)
+#define RCC_APB2RSTSETR_SPI4RST			BIT(9)
+#define RCC_APB2RSTSETR_SPI5RST			BIT(10)
+#define RCC_APB2RSTSETR_USART6RST		BIT(13)
+#define RCC_APB2RSTSETR_SAI1RST			BIT(16)
+#define RCC_APB2RSTSETR_SAI2RST			BIT(17)
+#define RCC_APB2RSTSETR_SAI3RST			BIT(18)
+#define RCC_APB2RSTSETR_DFSDMRST		BIT(20)
+#define RCC_APB2RSTSETR_FDCANRST		BIT(24)
+
+/* RCC_APB2RSTCLRR register fields */
+#define RCC_APB2RSTCLRR_TIM1RST			BIT(0)
+#define RCC_APB2RSTCLRR_TIM8RST			BIT(1)
+#define RCC_APB2RSTCLRR_TIM15RST		BIT(2)
+#define RCC_APB2RSTCLRR_TIM16RST		BIT(3)
+#define RCC_APB2RSTCLRR_TIM17RST		BIT(4)
+#define RCC_APB2RSTCLRR_SPI1RST			BIT(8)
+#define RCC_APB2RSTCLRR_SPI4RST			BIT(9)
+#define RCC_APB2RSTCLRR_SPI5RST			BIT(10)
+#define RCC_APB2RSTCLRR_USART6RST		BIT(13)
+#define RCC_APB2RSTCLRR_SAI1RST			BIT(16)
+#define RCC_APB2RSTCLRR_SAI2RST			BIT(17)
+#define RCC_APB2RSTCLRR_SAI3RST			BIT(18)
+#define RCC_APB2RSTCLRR_DFSDMRST		BIT(20)
+#define RCC_APB2RSTCLRR_FDCANRST		BIT(24)
+
+/* RCC_APB3RSTSETR register fields */
+#define RCC_APB3RSTSETR_LPTIM2RST		BIT(0)
+#define RCC_APB3RSTSETR_LPTIM3RST		BIT(1)
+#define RCC_APB3RSTSETR_LPTIM4RST		BIT(2)
+#define RCC_APB3RSTSETR_LPTIM5RST		BIT(3)
+#define RCC_APB3RSTSETR_SAI4RST			BIT(8)
+#define RCC_APB3RSTSETR_SYSCFGRST		BIT(11)
+#define RCC_APB3RSTSETR_VREFRST			BIT(13)
+#define RCC_APB3RSTSETR_TMPSENSRST		BIT(16)
+#define RCC_APB3RSTSETR_PMBCTRLRST		BIT(17)
+
+/* RCC_APB3RSTCLRR register fields */
+#define RCC_APB3RSTCLRR_LPTIM2RST		BIT(0)
+#define RCC_APB3RSTCLRR_LPTIM3RST		BIT(1)
+#define RCC_APB3RSTCLRR_LPTIM4RST		BIT(2)
+#define RCC_APB3RSTCLRR_LPTIM5RST		BIT(3)
+#define RCC_APB3RSTCLRR_SAI4RST			BIT(8)
+#define RCC_APB3RSTCLRR_SYSCFGRST		BIT(11)
+#define RCC_APB3RSTCLRR_VREFRST			BIT(13)
+#define RCC_APB3RSTCLRR_TMPSENSRST		BIT(16)
+#define RCC_APB3RSTCLRR_PMBCTRLRST		BIT(17)
+
+/* RCC_AHB2RSTSETR register fields */
+#define RCC_AHB2RSTSETR_DMA1RST			BIT(0)
+#define RCC_AHB2RSTSETR_DMA2RST			BIT(1)
+#define RCC_AHB2RSTSETR_DMAMUXRST		BIT(2)
+#define RCC_AHB2RSTSETR_ADC12RST		BIT(5)
+#define RCC_AHB2RSTSETR_USBORST			BIT(8)
+#define RCC_AHB2RSTSETR_SDMMC3RST		BIT(16)
+
+/* RCC_AHB2RSTCLRR register fields */
+#define RCC_AHB2RSTCLRR_DMA1RST			BIT(0)
+#define RCC_AHB2RSTCLRR_DMA2RST			BIT(1)
+#define RCC_AHB2RSTCLRR_DMAMUXRST		BIT(2)
+#define RCC_AHB2RSTCLRR_ADC12RST		BIT(5)
+#define RCC_AHB2RSTCLRR_USBORST			BIT(8)
+#define RCC_AHB2RSTCLRR_SDMMC3RST		BIT(16)
+
+/* RCC_AHB3RSTSETR register fields */
+#define RCC_AHB3RSTSETR_DCMIRST			BIT(0)
+#define RCC_AHB3RSTSETR_CRYP2RST		BIT(4)
+#define RCC_AHB3RSTSETR_HASH2RST		BIT(5)
+#define RCC_AHB3RSTSETR_RNG2RST			BIT(6)
+#define RCC_AHB3RSTSETR_CRC2RST			BIT(7)
+#define RCC_AHB3RSTSETR_HSEMRST			BIT(11)
+#define RCC_AHB3RSTSETR_IPCCRST			BIT(12)
+
+/* RCC_AHB3RSTCLRR register fields */
+#define RCC_AHB3RSTCLRR_DCMIRST			BIT(0)
+#define RCC_AHB3RSTCLRR_CRYP2RST		BIT(4)
+#define RCC_AHB3RSTCLRR_HASH2RST		BIT(5)
+#define RCC_AHB3RSTCLRR_RNG2RST			BIT(6)
+#define RCC_AHB3RSTCLRR_CRC2RST			BIT(7)
+#define RCC_AHB3RSTCLRR_HSEMRST			BIT(11)
+#define RCC_AHB3RSTCLRR_IPCCRST			BIT(12)
+
+/* RCC_AHB4RSTSETR register fields */
+#define RCC_AHB4RSTSETR_GPIOARST		BIT(0)
+#define RCC_AHB4RSTSETR_GPIOBRST		BIT(1)
+#define RCC_AHB4RSTSETR_GPIOCRST		BIT(2)
+#define RCC_AHB4RSTSETR_GPIODRST		BIT(3)
+#define RCC_AHB4RSTSETR_GPIOERST		BIT(4)
+#define RCC_AHB4RSTSETR_GPIOFRST		BIT(5)
+#define RCC_AHB4RSTSETR_GPIOGRST		BIT(6)
+#define RCC_AHB4RSTSETR_GPIOHRST		BIT(7)
+#define RCC_AHB4RSTSETR_GPIOIRST		BIT(8)
+#define RCC_AHB4RSTSETR_GPIOJRST		BIT(9)
+#define RCC_AHB4RSTSETR_GPIOKRST		BIT(10)
+
+/* RCC_AHB4RSTCLRR register fields */
+#define RCC_AHB4RSTCLRR_GPIOARST		BIT(0)
+#define RCC_AHB4RSTCLRR_GPIOBRST		BIT(1)
+#define RCC_AHB4RSTCLRR_GPIOCRST		BIT(2)
+#define RCC_AHB4RSTCLRR_GPIODRST		BIT(3)
+#define RCC_AHB4RSTCLRR_GPIOERST		BIT(4)
+#define RCC_AHB4RSTCLRR_GPIOFRST		BIT(5)
+#define RCC_AHB4RSTCLRR_GPIOGRST		BIT(6)
+#define RCC_AHB4RSTCLRR_GPIOHRST		BIT(7)
+#define RCC_AHB4RSTCLRR_GPIOIRST		BIT(8)
+#define RCC_AHB4RSTCLRR_GPIOJRST		BIT(9)
+#define RCC_AHB4RSTCLRR_GPIOKRST		BIT(10)
+
+/* RCC_MP_APB1ENSETR register fields */
+#define RCC_MP_APB1ENSETR_TIM2EN		BIT(0)
+#define RCC_MP_APB1ENSETR_TIM3EN		BIT(1)
+#define RCC_MP_APB1ENSETR_TIM4EN		BIT(2)
+#define RCC_MP_APB1ENSETR_TIM5EN		BIT(3)
+#define RCC_MP_APB1ENSETR_TIM6EN		BIT(4)
+#define RCC_MP_APB1ENSETR_TIM7EN		BIT(5)
+#define RCC_MP_APB1ENSETR_TIM12EN		BIT(6)
+#define RCC_MP_APB1ENSETR_TIM13EN		BIT(7)
+#define RCC_MP_APB1ENSETR_TIM14EN		BIT(8)
+#define RCC_MP_APB1ENSETR_LPTIM1EN		BIT(9)
+#define RCC_MP_APB1ENSETR_SPI2EN		BIT(11)
+#define RCC_MP_APB1ENSETR_SPI3EN		BIT(12)
+#define RCC_MP_APB1ENSETR_USART2EN		BIT(14)
+#define RCC_MP_APB1ENSETR_USART3EN		BIT(15)
+#define RCC_MP_APB1ENSETR_UART4EN		BIT(16)
+#define RCC_MP_APB1ENSETR_UART5EN		BIT(17)
+#define RCC_MP_APB1ENSETR_UART7EN		BIT(18)
+#define RCC_MP_APB1ENSETR_UART8EN		BIT(19)
+#define RCC_MP_APB1ENSETR_I2C1EN		BIT(21)
+#define RCC_MP_APB1ENSETR_I2C2EN		BIT(22)
+#define RCC_MP_APB1ENSETR_I2C3EN		BIT(23)
+#define RCC_MP_APB1ENSETR_I2C5EN		BIT(24)
+#define RCC_MP_APB1ENSETR_SPDIFEN		BIT(26)
+#define RCC_MP_APB1ENSETR_CECEN			BIT(27)
+#define RCC_MP_APB1ENSETR_DAC12EN		BIT(29)
+#define RCC_MP_APB1ENSETR_MDIOSEN		BIT(31)
+
+/* RCC_MP_APB1ENCLRR register fields */
+#define RCC_MP_APB1ENCLRR_TIM2EN		BIT(0)
+#define RCC_MP_APB1ENCLRR_TIM3EN		BIT(1)
+#define RCC_MP_APB1ENCLRR_TIM4EN		BIT(2)
+#define RCC_MP_APB1ENCLRR_TIM5EN		BIT(3)
+#define RCC_MP_APB1ENCLRR_TIM6EN		BIT(4)
+#define RCC_MP_APB1ENCLRR_TIM7EN		BIT(5)
+#define RCC_MP_APB1ENCLRR_TIM12EN		BIT(6)
+#define RCC_MP_APB1ENCLRR_TIM13EN		BIT(7)
+#define RCC_MP_APB1ENCLRR_TIM14EN		BIT(8)
+#define RCC_MP_APB1ENCLRR_LPTIM1EN		BIT(9)
+#define RCC_MP_APB1ENCLRR_SPI2EN		BIT(11)
+#define RCC_MP_APB1ENCLRR_SPI3EN		BIT(12)
+#define RCC_MP_APB1ENCLRR_USART2EN		BIT(14)
+#define RCC_MP_APB1ENCLRR_USART3EN		BIT(15)
+#define RCC_MP_APB1ENCLRR_UART4EN		BIT(16)
+#define RCC_MP_APB1ENCLRR_UART5EN		BIT(17)
+#define RCC_MP_APB1ENCLRR_UART7EN		BIT(18)
+#define RCC_MP_APB1ENCLRR_UART8EN		BIT(19)
+#define RCC_MP_APB1ENCLRR_I2C1EN		BIT(21)
+#define RCC_MP_APB1ENCLRR_I2C2EN		BIT(22)
+#define RCC_MP_APB1ENCLRR_I2C3EN		BIT(23)
+#define RCC_MP_APB1ENCLRR_I2C5EN		BIT(24)
+#define RCC_MP_APB1ENCLRR_SPDIFEN		BIT(26)
+#define RCC_MP_APB1ENCLRR_CECEN			BIT(27)
+#define RCC_MP_APB1ENCLRR_DAC12EN		BIT(29)
+#define RCC_MP_APB1ENCLRR_MDIOSEN		BIT(31)
+
+/* RCC_MP_APB2ENSETR register fields */
+#define RCC_MP_APB2ENSETR_TIM1EN		BIT(0)
+#define RCC_MP_APB2ENSETR_TIM8EN		BIT(1)
+#define RCC_MP_APB2ENSETR_TIM15EN		BIT(2)
+#define RCC_MP_APB2ENSETR_TIM16EN		BIT(3)
+#define RCC_MP_APB2ENSETR_TIM17EN		BIT(4)
+#define RCC_MP_APB2ENSETR_SPI1EN		BIT(8)
+#define RCC_MP_APB2ENSETR_SPI4EN		BIT(9)
+#define RCC_MP_APB2ENSETR_SPI5EN		BIT(10)
+#define RCC_MP_APB2ENSETR_USART6EN		BIT(13)
+#define RCC_MP_APB2ENSETR_SAI1EN		BIT(16)
+#define RCC_MP_APB2ENSETR_SAI2EN		BIT(17)
+#define RCC_MP_APB2ENSETR_SAI3EN		BIT(18)
+#define RCC_MP_APB2ENSETR_DFSDMEN		BIT(20)
+#define RCC_MP_APB2ENSETR_ADFSDMEN		BIT(21)
+#define RCC_MP_APB2ENSETR_FDCANEN		BIT(24)
+
+/* RCC_MP_APB2ENCLRR register fields */
+#define RCC_MP_APB2ENCLRR_TIM1EN		BIT(0)
+#define RCC_MP_APB2ENCLRR_TIM8EN		BIT(1)
+#define RCC_MP_APB2ENCLRR_TIM15EN		BIT(2)
+#define RCC_MP_APB2ENCLRR_TIM16EN		BIT(3)
+#define RCC_MP_APB2ENCLRR_TIM17EN		BIT(4)
+#define RCC_MP_APB2ENCLRR_SPI1EN		BIT(8)
+#define RCC_MP_APB2ENCLRR_SPI4EN		BIT(9)
+#define RCC_MP_APB2ENCLRR_SPI5EN		BIT(10)
+#define RCC_MP_APB2ENCLRR_USART6EN		BIT(13)
+#define RCC_MP_APB2ENCLRR_SAI1EN		BIT(16)
+#define RCC_MP_APB2ENCLRR_SAI2EN		BIT(17)
+#define RCC_MP_APB2ENCLRR_SAI3EN		BIT(18)
+#define RCC_MP_APB2ENCLRR_DFSDMEN		BIT(20)
+#define RCC_MP_APB2ENCLRR_ADFSDMEN		BIT(21)
+#define RCC_MP_APB2ENCLRR_FDCANEN		BIT(24)
+
+/* RCC_MP_APB3ENSETR register fields */
+#define RCC_MP_APB3ENSETR_LPTIM2EN		BIT(0)
+#define RCC_MP_APB3ENSETR_LPTIM3EN		BIT(1)
+#define RCC_MP_APB3ENSETR_LPTIM4EN		BIT(2)
+#define RCC_MP_APB3ENSETR_LPTIM5EN		BIT(3)
+#define RCC_MP_APB3ENSETR_SAI4EN		BIT(8)
+#define RCC_MP_APB3ENSETR_SYSCFGEN		BIT(11)
+#define RCC_MP_APB3ENSETR_VREFEN		BIT(13)
+#define RCC_MP_APB3ENSETR_TMPSENSEN		BIT(16)
+#define RCC_MP_APB3ENSETR_PMBCTRLEN		BIT(17)
+#define RCC_MP_APB3ENSETR_HDPEN			BIT(20)
+
+/* RCC_MP_APB3ENCLRR register fields */
+#define RCC_MP_APB3ENCLRR_LPTIM2EN		BIT(0)
+#define RCC_MP_APB3ENCLRR_LPTIM3EN		BIT(1)
+#define RCC_MP_APB3ENCLRR_LPTIM4EN		BIT(2)
+#define RCC_MP_APB3ENCLRR_LPTIM5EN		BIT(3)
+#define RCC_MP_APB3ENCLRR_SAI4EN		BIT(8)
+#define RCC_MP_APB3ENCLRR_SYSCFGEN		BIT(11)
+#define RCC_MP_APB3ENCLRR_VREFEN		BIT(13)
+#define RCC_MP_APB3ENCLRR_TMPSENSEN		BIT(16)
+#define RCC_MP_APB3ENCLRR_PMBCTRLEN		BIT(17)
+#define RCC_MP_APB3ENCLRR_HDPEN			BIT(20)
+
+/* RCC_MP_AHB2ENSETR register fields */
+#define RCC_MP_AHB2ENSETR_DMA1EN		BIT(0)
+#define RCC_MP_AHB2ENSETR_DMA2EN		BIT(1)
+#define RCC_MP_AHB2ENSETR_DMAMUXEN		BIT(2)
+#define RCC_MP_AHB2ENSETR_ADC12EN		BIT(5)
+#define RCC_MP_AHB2ENSETR_USBOEN		BIT(8)
+#define RCC_MP_AHB2ENSETR_SDMMC3EN		BIT(16)
+
+/* RCC_MP_AHB2ENCLRR register fields */
+#define RCC_MP_AHB2ENCLRR_DMA1EN		BIT(0)
+#define RCC_MP_AHB2ENCLRR_DMA2EN		BIT(1)
+#define RCC_MP_AHB2ENCLRR_DMAMUXEN		BIT(2)
+#define RCC_MP_AHB2ENCLRR_ADC12EN		BIT(5)
+#define RCC_MP_AHB2ENCLRR_USBOEN		BIT(8)
+#define RCC_MP_AHB2ENCLRR_SDMMC3EN		BIT(16)
+
+/* RCC_MP_AHB3ENSETR register fields */
+#define RCC_MP_AHB3ENSETR_DCMIEN		BIT(0)
+#define RCC_MP_AHB3ENSETR_CRYP2EN		BIT(4)
+#define RCC_MP_AHB3ENSETR_HASH2EN		BIT(5)
+#define RCC_MP_AHB3ENSETR_RNG2EN		BIT(6)
+#define RCC_MP_AHB3ENSETR_CRC2EN		BIT(7)
+#define RCC_MP_AHB3ENSETR_HSEMEN		BIT(11)
+#define RCC_MP_AHB3ENSETR_IPCCEN		BIT(12)
+
+/* RCC_MP_AHB3ENCLRR register fields */
+#define RCC_MP_AHB3ENCLRR_DCMIEN		BIT(0)
+#define RCC_MP_AHB3ENCLRR_CRYP2EN		BIT(4)
+#define RCC_MP_AHB3ENCLRR_HASH2EN		BIT(5)
+#define RCC_MP_AHB3ENCLRR_RNG2EN		BIT(6)
+#define RCC_MP_AHB3ENCLRR_CRC2EN		BIT(7)
+#define RCC_MP_AHB3ENCLRR_HSEMEN		BIT(11)
+#define RCC_MP_AHB3ENCLRR_IPCCEN		BIT(12)
+
+/* RCC_MP_AHB4ENSETR register fields */
+#define RCC_MP_AHB4ENSETR_GPIOAEN		BIT(0)
+#define RCC_MP_AHB4ENSETR_GPIOBEN		BIT(1)
+#define RCC_MP_AHB4ENSETR_GPIOCEN		BIT(2)
+#define RCC_MP_AHB4ENSETR_GPIODEN		BIT(3)
+#define RCC_MP_AHB4ENSETR_GPIOEEN		BIT(4)
+#define RCC_MP_AHB4ENSETR_GPIOFEN		BIT(5)
+#define RCC_MP_AHB4ENSETR_GPIOGEN		BIT(6)
+#define RCC_MP_AHB4ENSETR_GPIOHEN		BIT(7)
+#define RCC_MP_AHB4ENSETR_GPIOIEN		BIT(8)
+#define RCC_MP_AHB4ENSETR_GPIOJEN		BIT(9)
+#define RCC_MP_AHB4ENSETR_GPIOKEN		BIT(10)
+
+/* RCC_MP_AHB4ENCLRR register fields */
+#define RCC_MP_AHB4ENCLRR_GPIOAEN		BIT(0)
+#define RCC_MP_AHB4ENCLRR_GPIOBEN		BIT(1)
+#define RCC_MP_AHB4ENCLRR_GPIOCEN		BIT(2)
+#define RCC_MP_AHB4ENCLRR_GPIODEN		BIT(3)
+#define RCC_MP_AHB4ENCLRR_GPIOEEN		BIT(4)
+#define RCC_MP_AHB4ENCLRR_GPIOFEN		BIT(5)
+#define RCC_MP_AHB4ENCLRR_GPIOGEN		BIT(6)
+#define RCC_MP_AHB4ENCLRR_GPIOHEN		BIT(7)
+#define RCC_MP_AHB4ENCLRR_GPIOIEN		BIT(8)
+#define RCC_MP_AHB4ENCLRR_GPIOJEN		BIT(9)
+#define RCC_MP_AHB4ENCLRR_GPIOKEN		BIT(10)
+
+/* RCC_MP_MLAHBENSETR register fields */
+#define RCC_MP_MLAHBENSETR_RETRAMEN		BIT(4)
+
+/* RCC_MP_MLAHBENCLRR register fields */
+#define RCC_MP_MLAHBENCLRR_RETRAMEN		BIT(4)
+
+/* RCC_MC_APB1ENSETR register fields */
+#define RCC_MC_APB1ENSETR_TIM2EN		BIT(0)
+#define RCC_MC_APB1ENSETR_TIM3EN		BIT(1)
+#define RCC_MC_APB1ENSETR_TIM4EN		BIT(2)
+#define RCC_MC_APB1ENSETR_TIM5EN		BIT(3)
+#define RCC_MC_APB1ENSETR_TIM6EN		BIT(4)
+#define RCC_MC_APB1ENSETR_TIM7EN		BIT(5)
+#define RCC_MC_APB1ENSETR_TIM12EN		BIT(6)
+#define RCC_MC_APB1ENSETR_TIM13EN		BIT(7)
+#define RCC_MC_APB1ENSETR_TIM14EN		BIT(8)
+#define RCC_MC_APB1ENSETR_LPTIM1EN		BIT(9)
+#define RCC_MC_APB1ENSETR_SPI2EN		BIT(11)
+#define RCC_MC_APB1ENSETR_SPI3EN		BIT(12)
+#define RCC_MC_APB1ENSETR_USART2EN		BIT(14)
+#define RCC_MC_APB1ENSETR_USART3EN		BIT(15)
+#define RCC_MC_APB1ENSETR_UART4EN		BIT(16)
+#define RCC_MC_APB1ENSETR_UART5EN		BIT(17)
+#define RCC_MC_APB1ENSETR_UART7EN		BIT(18)
+#define RCC_MC_APB1ENSETR_UART8EN		BIT(19)
+#define RCC_MC_APB1ENSETR_I2C1EN		BIT(21)
+#define RCC_MC_APB1ENSETR_I2C2EN		BIT(22)
+#define RCC_MC_APB1ENSETR_I2C3EN		BIT(23)
+#define RCC_MC_APB1ENSETR_I2C5EN		BIT(24)
+#define RCC_MC_APB1ENSETR_SPDIFEN		BIT(26)
+#define RCC_MC_APB1ENSETR_CECEN			BIT(27)
+#define RCC_MC_APB1ENSETR_WWDG1EN		BIT(28)
+#define RCC_MC_APB1ENSETR_DAC12EN		BIT(29)
+#define RCC_MC_APB1ENSETR_MDIOSEN		BIT(31)
+
+/* RCC_MC_APB1ENCLRR register fields */
+#define RCC_MC_APB1ENCLRR_TIM2EN		BIT(0)
+#define RCC_MC_APB1ENCLRR_TIM3EN		BIT(1)
+#define RCC_MC_APB1ENCLRR_TIM4EN		BIT(2)
+#define RCC_MC_APB1ENCLRR_TIM5EN		BIT(3)
+#define RCC_MC_APB1ENCLRR_TIM6EN		BIT(4)
+#define RCC_MC_APB1ENCLRR_TIM7EN		BIT(5)
+#define RCC_MC_APB1ENCLRR_TIM12EN		BIT(6)
+#define RCC_MC_APB1ENCLRR_TIM13EN		BIT(7)
+#define RCC_MC_APB1ENCLRR_TIM14EN		BIT(8)
+#define RCC_MC_APB1ENCLRR_LPTIM1EN		BIT(9)
+#define RCC_MC_APB1ENCLRR_SPI2EN		BIT(11)
+#define RCC_MC_APB1ENCLRR_SPI3EN		BIT(12)
+#define RCC_MC_APB1ENCLRR_USART2EN		BIT(14)
+#define RCC_MC_APB1ENCLRR_USART3EN		BIT(15)
+#define RCC_MC_APB1ENCLRR_UART4EN		BIT(16)
+#define RCC_MC_APB1ENCLRR_UART5EN		BIT(17)
+#define RCC_MC_APB1ENCLRR_UART7EN		BIT(18)
+#define RCC_MC_APB1ENCLRR_UART8EN		BIT(19)
+#define RCC_MC_APB1ENCLRR_I2C1EN		BIT(21)
+#define RCC_MC_APB1ENCLRR_I2C2EN		BIT(22)
+#define RCC_MC_APB1ENCLRR_I2C3EN		BIT(23)
+#define RCC_MC_APB1ENCLRR_I2C5EN		BIT(24)
+#define RCC_MC_APB1ENCLRR_SPDIFEN		BIT(26)
+#define RCC_MC_APB1ENCLRR_CECEN			BIT(27)
+#define RCC_MC_APB1ENCLRR_DAC12EN		BIT(29)
+#define RCC_MC_APB1ENCLRR_MDIOSEN		BIT(31)
+
+/* RCC_MC_APB2ENSETR register fields */
+#define RCC_MC_APB2ENSETR_TIM1EN		BIT(0)
+#define RCC_MC_APB2ENSETR_TIM8EN		BIT(1)
+#define RCC_MC_APB2ENSETR_TIM15EN		BIT(2)
+#define RCC_MC_APB2ENSETR_TIM16EN		BIT(3)
+#define RCC_MC_APB2ENSETR_TIM17EN		BIT(4)
+#define RCC_MC_APB2ENSETR_SPI1EN		BIT(8)
+#define RCC_MC_APB2ENSETR_SPI4EN		BIT(9)
+#define RCC_MC_APB2ENSETR_SPI5EN		BIT(10)
+#define RCC_MC_APB2ENSETR_USART6EN		BIT(13)
+#define RCC_MC_APB2ENSETR_SAI1EN		BIT(16)
+#define RCC_MC_APB2ENSETR_SAI2EN		BIT(17)
+#define RCC_MC_APB2ENSETR_SAI3EN		BIT(18)
+#define RCC_MC_APB2ENSETR_DFSDMEN		BIT(20)
+#define RCC_MC_APB2ENSETR_ADFSDMEN		BIT(21)
+#define RCC_MC_APB2ENSETR_FDCANEN		BIT(24)
+
+/* RCC_MC_APB2ENCLRR register fields */
+#define RCC_MC_APB2ENCLRR_TIM1EN		BIT(0)
+#define RCC_MC_APB2ENCLRR_TIM8EN		BIT(1)
+#define RCC_MC_APB2ENCLRR_TIM15EN		BIT(2)
+#define RCC_MC_APB2ENCLRR_TIM16EN		BIT(3)
+#define RCC_MC_APB2ENCLRR_TIM17EN		BIT(4)
+#define RCC_MC_APB2ENCLRR_SPI1EN		BIT(8)
+#define RCC_MC_APB2ENCLRR_SPI4EN		BIT(9)
+#define RCC_MC_APB2ENCLRR_SPI5EN		BIT(10)
+#define RCC_MC_APB2ENCLRR_USART6EN		BIT(13)
+#define RCC_MC_APB2ENCLRR_SAI1EN		BIT(16)
+#define RCC_MC_APB2ENCLRR_SAI2EN		BIT(17)
+#define RCC_MC_APB2ENCLRR_SAI3EN		BIT(18)
+#define RCC_MC_APB2ENCLRR_DFSDMEN		BIT(20)
+#define RCC_MC_APB2ENCLRR_ADFSDMEN		BIT(21)
+#define RCC_MC_APB2ENCLRR_FDCANEN		BIT(24)
+
+/* RCC_MC_APB3ENSETR register fields */
+#define RCC_MC_APB3ENSETR_LPTIM2EN		BIT(0)
+#define RCC_MC_APB3ENSETR_LPTIM3EN		BIT(1)
+#define RCC_MC_APB3ENSETR_LPTIM4EN		BIT(2)
+#define RCC_MC_APB3ENSETR_LPTIM5EN		BIT(3)
+#define RCC_MC_APB3ENSETR_SAI4EN		BIT(8)
+#define RCC_MC_APB3ENSETR_SYSCFGEN		BIT(11)
+#define RCC_MC_APB3ENSETR_VREFEN		BIT(13)
+#define RCC_MC_APB3ENSETR_TMPSENSEN		BIT(16)
+#define RCC_MC_APB3ENSETR_PMBCTRLEN		BIT(17)
+#define RCC_MC_APB3ENSETR_HDPEN			BIT(20)
+
+/* RCC_MC_APB3ENCLRR register fields */
+#define RCC_MC_APB3ENCLRR_LPTIM2EN		BIT(0)
+#define RCC_MC_APB3ENCLRR_LPTIM3EN		BIT(1)
+#define RCC_MC_APB3ENCLRR_LPTIM4EN		BIT(2)
+#define RCC_MC_APB3ENCLRR_LPTIM5EN		BIT(3)
+#define RCC_MC_APB3ENCLRR_SAI4EN		BIT(8)
+#define RCC_MC_APB3ENCLRR_SYSCFGEN		BIT(11)
+#define RCC_MC_APB3ENCLRR_VREFEN		BIT(13)
+#define RCC_MC_APB3ENCLRR_TMPSENSEN		BIT(16)
+#define RCC_MC_APB3ENCLRR_PMBCTRLEN		BIT(17)
+#define RCC_MC_APB3ENCLRR_HDPEN			BIT(20)
+
+/* RCC_MC_AHB2ENSETR register fields */
+#define RCC_MC_AHB2ENSETR_DMA1EN		BIT(0)
+#define RCC_MC_AHB2ENSETR_DMA2EN		BIT(1)
+#define RCC_MC_AHB2ENSETR_DMAMUXEN		BIT(2)
+#define RCC_MC_AHB2ENSETR_ADC12EN		BIT(5)
+#define RCC_MC_AHB2ENSETR_USBOEN		BIT(8)
+#define RCC_MC_AHB2ENSETR_SDMMC3EN		BIT(16)
+
+/* RCC_MC_AHB2ENCLRR register fields */
+#define RCC_MC_AHB2ENCLRR_DMA1EN		BIT(0)
+#define RCC_MC_AHB2ENCLRR_DMA2EN		BIT(1)
+#define RCC_MC_AHB2ENCLRR_DMAMUXEN		BIT(2)
+#define RCC_MC_AHB2ENCLRR_ADC12EN		BIT(5)
+#define RCC_MC_AHB2ENCLRR_USBOEN		BIT(8)
+#define RCC_MC_AHB2ENCLRR_SDMMC3EN		BIT(16)
+
+/* RCC_MC_AHB3ENSETR register fields */
+#define RCC_MC_AHB3ENSETR_DCMIEN		BIT(0)
+#define RCC_MC_AHB3ENSETR_CRYP2EN		BIT(4)
+#define RCC_MC_AHB3ENSETR_HASH2EN		BIT(5)
+#define RCC_MC_AHB3ENSETR_RNG2EN		BIT(6)
+#define RCC_MC_AHB3ENSETR_CRC2EN		BIT(7)
+#define RCC_MC_AHB3ENSETR_HSEMEN		BIT(11)
+#define RCC_MC_AHB3ENSETR_IPCCEN		BIT(12)
+
+/* RCC_MC_AHB3ENCLRR register fields */
+#define RCC_MC_AHB3ENCLRR_DCMIEN		BIT(0)
+#define RCC_MC_AHB3ENCLRR_CRYP2EN		BIT(4)
+#define RCC_MC_AHB3ENCLRR_HASH2EN		BIT(5)
+#define RCC_MC_AHB3ENCLRR_RNG2EN		BIT(6)
+#define RCC_MC_AHB3ENCLRR_CRC2EN		BIT(7)
+#define RCC_MC_AHB3ENCLRR_HSEMEN		BIT(11)
+#define RCC_MC_AHB3ENCLRR_IPCCEN		BIT(12)
+
+/* RCC_MC_AHB4ENSETR register fields */
+#define RCC_MC_AHB4ENSETR_GPIOAEN		BIT(0)
+#define RCC_MC_AHB4ENSETR_GPIOBEN		BIT(1)
+#define RCC_MC_AHB4ENSETR_GPIOCEN		BIT(2)
+#define RCC_MC_AHB4ENSETR_GPIODEN		BIT(3)
+#define RCC_MC_AHB4ENSETR_GPIOEEN		BIT(4)
+#define RCC_MC_AHB4ENSETR_GPIOFEN		BIT(5)
+#define RCC_MC_AHB4ENSETR_GPIOGEN		BIT(6)
+#define RCC_MC_AHB4ENSETR_GPIOHEN		BIT(7)
+#define RCC_MC_AHB4ENSETR_GPIOIEN		BIT(8)
+#define RCC_MC_AHB4ENSETR_GPIOJEN		BIT(9)
+#define RCC_MC_AHB4ENSETR_GPIOKEN		BIT(10)
+
+/* RCC_MC_AHB4ENCLRR register fields */
+#define RCC_MC_AHB4ENCLRR_GPIOAEN		BIT(0)
+#define RCC_MC_AHB4ENCLRR_GPIOBEN		BIT(1)
+#define RCC_MC_AHB4ENCLRR_GPIOCEN		BIT(2)
+#define RCC_MC_AHB4ENCLRR_GPIODEN		BIT(3)
+#define RCC_MC_AHB4ENCLRR_GPIOEEN		BIT(4)
+#define RCC_MC_AHB4ENCLRR_GPIOFEN		BIT(5)
+#define RCC_MC_AHB4ENCLRR_GPIOGEN		BIT(6)
+#define RCC_MC_AHB4ENCLRR_GPIOHEN		BIT(7)
+#define RCC_MC_AHB4ENCLRR_GPIOIEN		BIT(8)
+#define RCC_MC_AHB4ENCLRR_GPIOJEN		BIT(9)
+#define RCC_MC_AHB4ENCLRR_GPIOKEN		BIT(10)
+
+/* RCC_MC_AXIMENSETR register fields */
+#define RCC_MC_AXIMENSETR_SYSRAMEN		BIT(0)
+
+/* RCC_MC_AXIMENCLRR register fields */
+#define RCC_MC_AXIMENCLRR_SYSRAMEN		BIT(0)
+
+/* RCC_MC_MLAHBENSETR register fields */
+#define RCC_MC_MLAHBENSETR_RETRAMEN		BIT(4)
+
+/* RCC_MC_MLAHBENCLRR register fields */
+#define RCC_MC_MLAHBENCLRR_RETRAMEN		BIT(4)
+
+/* RCC_MP_APB1LPENSETR register fields */
+#define RCC_MP_APB1LPENSETR_TIM2LPEN		BIT(0)
+#define RCC_MP_APB1LPENSETR_TIM3LPEN		BIT(1)
+#define RCC_MP_APB1LPENSETR_TIM4LPEN		BIT(2)
+#define RCC_MP_APB1LPENSETR_TIM5LPEN		BIT(3)
+#define RCC_MP_APB1LPENSETR_TIM6LPEN		BIT(4)
+#define RCC_MP_APB1LPENSETR_TIM7LPEN		BIT(5)
+#define RCC_MP_APB1LPENSETR_TIM12LPEN		BIT(6)
+#define RCC_MP_APB1LPENSETR_TIM13LPEN		BIT(7)
+#define RCC_MP_APB1LPENSETR_TIM14LPEN		BIT(8)
+#define RCC_MP_APB1LPENSETR_LPTIM1LPEN		BIT(9)
+#define RCC_MP_APB1LPENSETR_SPI2LPEN		BIT(11)
+#define RCC_MP_APB1LPENSETR_SPI3LPEN		BIT(12)
+#define RCC_MP_APB1LPENSETR_USART2LPEN		BIT(14)
+#define RCC_MP_APB1LPENSETR_USART3LPEN		BIT(15)
+#define RCC_MP_APB1LPENSETR_UART4LPEN		BIT(16)
+#define RCC_MP_APB1LPENSETR_UART5LPEN		BIT(17)
+#define RCC_MP_APB1LPENSETR_UART7LPEN		BIT(18)
+#define RCC_MP_APB1LPENSETR_UART8LPEN		BIT(19)
+#define RCC_MP_APB1LPENSETR_I2C1LPEN		BIT(21)
+#define RCC_MP_APB1LPENSETR_I2C2LPEN		BIT(22)
+#define RCC_MP_APB1LPENSETR_I2C3LPEN		BIT(23)
+#define RCC_MP_APB1LPENSETR_I2C5LPEN		BIT(24)
+#define RCC_MP_APB1LPENSETR_SPDIFLPEN		BIT(26)
+#define RCC_MP_APB1LPENSETR_CECLPEN		BIT(27)
+#define RCC_MP_APB1LPENSETR_DAC12LPEN		BIT(29)
+#define RCC_MP_APB1LPENSETR_MDIOSLPEN		BIT(31)
+
+/* RCC_MP_APB1LPENCLRR register fields */
+#define RCC_MP_APB1LPENCLRR_TIM2LPEN		BIT(0)
+#define RCC_MP_APB1LPENCLRR_TIM3LPEN		BIT(1)
+#define RCC_MP_APB1LPENCLRR_TIM4LPEN		BIT(2)
+#define RCC_MP_APB1LPENCLRR_TIM5LPEN		BIT(3)
+#define RCC_MP_APB1LPENCLRR_TIM6LPEN		BIT(4)
+#define RCC_MP_APB1LPENCLRR_TIM7LPEN		BIT(5)
+#define RCC_MP_APB1LPENCLRR_TIM12LPEN		BIT(6)
+#define RCC_MP_APB1LPENCLRR_TIM13LPEN		BIT(7)
+#define RCC_MP_APB1LPENCLRR_TIM14LPEN		BIT(8)
+#define RCC_MP_APB1LPENCLRR_LPTIM1LPEN		BIT(9)
+#define RCC_MP_APB1LPENCLRR_SPI2LPEN		BIT(11)
+#define RCC_MP_APB1LPENCLRR_SPI3LPEN		BIT(12)
+#define RCC_MP_APB1LPENCLRR_USART2LPEN		BIT(14)
+#define RCC_MP_APB1LPENCLRR_USART3LPEN		BIT(15)
+#define RCC_MP_APB1LPENCLRR_UART4LPEN		BIT(16)
+#define RCC_MP_APB1LPENCLRR_UART5LPEN		BIT(17)
+#define RCC_MP_APB1LPENCLRR_UART7LPEN		BIT(18)
+#define RCC_MP_APB1LPENCLRR_UART8LPEN		BIT(19)
+#define RCC_MP_APB1LPENCLRR_I2C1LPEN		BIT(21)
+#define RCC_MP_APB1LPENCLRR_I2C2LPEN		BIT(22)
+#define RCC_MP_APB1LPENCLRR_I2C3LPEN		BIT(23)
+#define RCC_MP_APB1LPENCLRR_I2C5LPEN		BIT(24)
+#define RCC_MP_APB1LPENCLRR_SPDIFLPEN		BIT(26)
+#define RCC_MP_APB1LPENCLRR_CECLPEN		BIT(27)
+#define RCC_MP_APB1LPENCLRR_DAC12LPEN		BIT(29)
+#define RCC_MP_APB1LPENCLRR_MDIOSLPEN		BIT(31)
+
+/* RCC_MP_APB2LPENSETR register fields */
+#define RCC_MP_APB2LPENSETR_TIM1LPEN		BIT(0)
+#define RCC_MP_APB2LPENSETR_TIM8LPEN		BIT(1)
+#define RCC_MP_APB2LPENSETR_TIM15LPEN		BIT(2)
+#define RCC_MP_APB2LPENSETR_TIM16LPEN		BIT(3)
+#define RCC_MP_APB2LPENSETR_TIM17LPEN		BIT(4)
+#define RCC_MP_APB2LPENSETR_SPI1LPEN		BIT(8)
+#define RCC_MP_APB2LPENSETR_SPI4LPEN		BIT(9)
+#define RCC_MP_APB2LPENSETR_SPI5LPEN		BIT(10)
+#define RCC_MP_APB2LPENSETR_USART6LPEN		BIT(13)
+#define RCC_MP_APB2LPENSETR_SAI1LPEN		BIT(16)
+#define RCC_MP_APB2LPENSETR_SAI2LPEN		BIT(17)
+#define RCC_MP_APB2LPENSETR_SAI3LPEN		BIT(18)
+#define RCC_MP_APB2LPENSETR_DFSDMLPEN		BIT(20)
+#define RCC_MP_APB2LPENSETR_ADFSDMLPEN		BIT(21)
+#define RCC_MP_APB2LPENSETR_FDCANLPEN		BIT(24)
+
+/* RCC_MP_APB2LPENCLRR register fields */
+#define RCC_MP_APB2LPENCLRR_TIM1LPEN		BIT(0)
+#define RCC_MP_APB2LPENCLRR_TIM8LPEN		BIT(1)
+#define RCC_MP_APB2LPENCLRR_TIM15LPEN		BIT(2)
+#define RCC_MP_APB2LPENCLRR_TIM16LPEN		BIT(3)
+#define RCC_MP_APB2LPENCLRR_TIM17LPEN		BIT(4)
+#define RCC_MP_APB2LPENCLRR_SPI1LPEN		BIT(8)
+#define RCC_MP_APB2LPENCLRR_SPI4LPEN		BIT(9)
+#define RCC_MP_APB2LPENCLRR_SPI5LPEN		BIT(10)
+#define RCC_MP_APB2LPENCLRR_USART6LPEN		BIT(13)
+#define RCC_MP_APB2LPENCLRR_SAI1LPEN		BIT(16)
+#define RCC_MP_APB2LPENCLRR_SAI2LPEN		BIT(17)
+#define RCC_MP_APB2LPENCLRR_SAI3LPEN		BIT(18)
+#define RCC_MP_APB2LPENCLRR_DFSDMLPEN		BIT(20)
+#define RCC_MP_APB2LPENCLRR_ADFSDMLPEN		BIT(21)
+#define RCC_MP_APB2LPENCLRR_FDCANLPEN		BIT(24)
+
+/* RCC_MP_APB3LPENSETR register fields */
+#define RCC_MP_APB3LPENSETR_LPTIM2LPEN		BIT(0)
+#define RCC_MP_APB3LPENSETR_LPTIM3LPEN		BIT(1)
+#define RCC_MP_APB3LPENSETR_LPTIM4LPEN		BIT(2)
+#define RCC_MP_APB3LPENSETR_LPTIM5LPEN		BIT(3)
+#define RCC_MP_APB3LPENSETR_SAI4LPEN		BIT(8)
+#define RCC_MP_APB3LPENSETR_SYSCFGLPEN		BIT(11)
+#define RCC_MP_APB3LPENSETR_VREFLPEN		BIT(13)
+#define RCC_MP_APB3LPENSETR_TMPSENSLPEN		BIT(16)
+#define RCC_MP_APB3LPENSETR_PMBCTRLLPEN		BIT(17)
+
+/* RCC_MP_APB3LPENCLRR register fields */
+#define RCC_MP_APB3LPENCLRR_LPTIM2LPEN		BIT(0)
+#define RCC_MP_APB3LPENCLRR_LPTIM3LPEN		BIT(1)
+#define RCC_MP_APB3LPENCLRR_LPTIM4LPEN		BIT(2)
+#define RCC_MP_APB3LPENCLRR_LPTIM5LPEN		BIT(3)
+#define RCC_MP_APB3LPENCLRR_SAI4LPEN		BIT(8)
+#define RCC_MP_APB3LPENCLRR_SYSCFGLPEN		BIT(11)
+#define RCC_MP_APB3LPENCLRR_VREFLPEN		BIT(13)
+#define RCC_MP_APB3LPENCLRR_TMPSENSLPEN		BIT(16)
+#define RCC_MP_APB3LPENCLRR_PMBCTRLLPEN		BIT(17)
+
+/* RCC_MP_AHB2LPENSETR register fields */
+#define RCC_MP_AHB2LPENSETR_DMA1LPEN		BIT(0)
+#define RCC_MP_AHB2LPENSETR_DMA2LPEN		BIT(1)
+#define RCC_MP_AHB2LPENSETR_DMAMUXLPEN		BIT(2)
+#define RCC_MP_AHB2LPENSETR_ADC12LPEN		BIT(5)
+#define RCC_MP_AHB2LPENSETR_USBOLPEN		BIT(8)
+#define RCC_MP_AHB2LPENSETR_SDMMC3LPEN		BIT(16)
+
+/* RCC_MP_AHB2LPENCLRR register fields */
+#define RCC_MP_AHB2LPENCLRR_DMA1LPEN		BIT(0)
+#define RCC_MP_AHB2LPENCLRR_DMA2LPEN		BIT(1)
+#define RCC_MP_AHB2LPENCLRR_DMAMUXLPEN		BIT(2)
+#define RCC_MP_AHB2LPENCLRR_ADC12LPEN		BIT(5)
+#define RCC_MP_AHB2LPENCLRR_USBOLPEN		BIT(8)
+#define RCC_MP_AHB2LPENCLRR_SDMMC3LPEN		BIT(16)
+
+/* RCC_MP_AHB3LPENSETR register fields */
+#define RCC_MP_AHB3LPENSETR_DCMILPEN		BIT(0)
+#define RCC_MP_AHB3LPENSETR_CRYP2LPEN		BIT(4)
+#define RCC_MP_AHB3LPENSETR_HASH2LPEN		BIT(5)
+#define RCC_MP_AHB3LPENSETR_RNG2LPEN		BIT(6)
+#define RCC_MP_AHB3LPENSETR_CRC2LPEN		BIT(7)
+#define RCC_MP_AHB3LPENSETR_HSEMLPEN		BIT(11)
+#define RCC_MP_AHB3LPENSETR_IPCCLPEN		BIT(12)
+
+/* RCC_MP_AHB3LPENCLRR register fields */
+#define RCC_MP_AHB3LPENCLRR_DCMILPEN		BIT(0)
+#define RCC_MP_AHB3LPENCLRR_CRYP2LPEN		BIT(4)
+#define RCC_MP_AHB3LPENCLRR_HASH2LPEN		BIT(5)
+#define RCC_MP_AHB3LPENCLRR_RNG2LPEN		BIT(6)
+#define RCC_MP_AHB3LPENCLRR_CRC2LPEN		BIT(7)
+#define RCC_MP_AHB3LPENCLRR_HSEMLPEN		BIT(11)
+#define RCC_MP_AHB3LPENCLRR_IPCCLPEN		BIT(12)
+
+/* RCC_MP_AHB4LPENSETR register fields */
+#define RCC_MP_AHB4LPENSETR_GPIOALPEN		BIT(0)
+#define RCC_MP_AHB4LPENSETR_GPIOBLPEN		BIT(1)
+#define RCC_MP_AHB4LPENSETR_GPIOCLPEN		BIT(2)
+#define RCC_MP_AHB4LPENSETR_GPIODLPEN		BIT(3)
+#define RCC_MP_AHB4LPENSETR_GPIOELPEN		BIT(4)
+#define RCC_MP_AHB4LPENSETR_GPIOFLPEN		BIT(5)
+#define RCC_MP_AHB4LPENSETR_GPIOGLPEN		BIT(6)
+#define RCC_MP_AHB4LPENSETR_GPIOHLPEN		BIT(7)
+#define RCC_MP_AHB4LPENSETR_GPIOILPEN		BIT(8)
+#define RCC_MP_AHB4LPENSETR_GPIOJLPEN		BIT(9)
+#define RCC_MP_AHB4LPENSETR_GPIOKLPEN		BIT(10)
+
+/* RCC_MP_AHB4LPENCLRR register fields */
+#define RCC_MP_AHB4LPENCLRR_GPIOALPEN		BIT(0)
+#define RCC_MP_AHB4LPENCLRR_GPIOBLPEN		BIT(1)
+#define RCC_MP_AHB4LPENCLRR_GPIOCLPEN		BIT(2)
+#define RCC_MP_AHB4LPENCLRR_GPIODLPEN		BIT(3)
+#define RCC_MP_AHB4LPENCLRR_GPIOELPEN		BIT(4)
+#define RCC_MP_AHB4LPENCLRR_GPIOFLPEN		BIT(5)
+#define RCC_MP_AHB4LPENCLRR_GPIOGLPEN		BIT(6)
+#define RCC_MP_AHB4LPENCLRR_GPIOHLPEN		BIT(7)
+#define RCC_MP_AHB4LPENCLRR_GPIOILPEN		BIT(8)
+#define RCC_MP_AHB4LPENCLRR_GPIOJLPEN		BIT(9)
+#define RCC_MP_AHB4LPENCLRR_GPIOKLPEN		BIT(10)
+
+/* RCC_MP_AXIMLPENSETR register fields */
+#define RCC_MP_AXIMLPENSETR_SYSRAMLPEN		BIT(0)
+
+/* RCC_MP_AXIMLPENCLRR register fields */
+#define RCC_MP_AXIMLPENCLRR_SYSRAMLPEN		BIT(0)
+
+/* RCC_MP_MLAHBLPENSETR register fields */
+#define RCC_MP_MLAHBLPENSETR_SRAM1LPEN		BIT(0)
+#define RCC_MP_MLAHBLPENSETR_SRAM2LPEN		BIT(1)
+#define RCC_MP_MLAHBLPENSETR_SRAM34LPEN		BIT(2)
+#define RCC_MP_MLAHBLPENSETR_RETRAMLPEN		BIT(4)
+
+/* RCC_MP_MLAHBLPENCLRR register fields */
+#define RCC_MP_MLAHBLPENCLRR_SRAM1LPEN		BIT(0)
+#define RCC_MP_MLAHBLPENCLRR_SRAM2LPEN		BIT(1)
+#define RCC_MP_MLAHBLPENCLRR_SRAM34LPEN		BIT(2)
+#define RCC_MP_MLAHBLPENCLRR_RETRAMLPEN		BIT(4)
+
+/* RCC_MC_APB1LPENSETR register fields */
+#define RCC_MC_APB1LPENSETR_TIM2LPEN		BIT(0)
+#define RCC_MC_APB1LPENSETR_TIM3LPEN		BIT(1)
+#define RCC_MC_APB1LPENSETR_TIM4LPEN		BIT(2)
+#define RCC_MC_APB1LPENSETR_TIM5LPEN		BIT(3)
+#define RCC_MC_APB1LPENSETR_TIM6LPEN		BIT(4)
+#define RCC_MC_APB1LPENSETR_TIM7LPEN		BIT(5)
+#define RCC_MC_APB1LPENSETR_TIM12LPEN		BIT(6)
+#define RCC_MC_APB1LPENSETR_TIM13LPEN		BIT(7)
+#define RCC_MC_APB1LPENSETR_TIM14LPEN		BIT(8)
+#define RCC_MC_APB1LPENSETR_LPTIM1LPEN		BIT(9)
+#define RCC_MC_APB1LPENSETR_SPI2LPEN		BIT(11)
+#define RCC_MC_APB1LPENSETR_SPI3LPEN		BIT(12)
+#define RCC_MC_APB1LPENSETR_USART2LPEN		BIT(14)
+#define RCC_MC_APB1LPENSETR_USART3LPEN		BIT(15)
+#define RCC_MC_APB1LPENSETR_UART4LPEN		BIT(16)
+#define RCC_MC_APB1LPENSETR_UART5LPEN		BIT(17)
+#define RCC_MC_APB1LPENSETR_UART7LPEN		BIT(18)
+#define RCC_MC_APB1LPENSETR_UART8LPEN		BIT(19)
+#define RCC_MC_APB1LPENSETR_I2C1LPEN		BIT(21)
+#define RCC_MC_APB1LPENSETR_I2C2LPEN		BIT(22)
+#define RCC_MC_APB1LPENSETR_I2C3LPEN		BIT(23)
+#define RCC_MC_APB1LPENSETR_I2C5LPEN		BIT(24)
+#define RCC_MC_APB1LPENSETR_SPDIFLPEN		BIT(26)
+#define RCC_MC_APB1LPENSETR_CECLPEN		BIT(27)
+#define RCC_MC_APB1LPENSETR_WWDG1LPEN		BIT(28)
+#define RCC_MC_APB1LPENSETR_DAC12LPEN		BIT(29)
+#define RCC_MC_APB1LPENSETR_MDIOSLPEN		BIT(31)
+
+/* RCC_MC_APB1LPENCLRR register fields */
+#define RCC_MC_APB1LPENCLRR_TIM2LPEN		BIT(0)
+#define RCC_MC_APB1LPENCLRR_TIM3LPEN		BIT(1)
+#define RCC_MC_APB1LPENCLRR_TIM4LPEN		BIT(2)
+#define RCC_MC_APB1LPENCLRR_TIM5LPEN		BIT(3)
+#define RCC_MC_APB1LPENCLRR_TIM6LPEN		BIT(4)
+#define RCC_MC_APB1LPENCLRR_TIM7LPEN		BIT(5)
+#define RCC_MC_APB1LPENCLRR_TIM12LPEN		BIT(6)
+#define RCC_MC_APB1LPENCLRR_TIM13LPEN		BIT(7)
+#define RCC_MC_APB1LPENCLRR_TIM14LPEN		BIT(8)
+#define RCC_MC_APB1LPENCLRR_LPTIM1LPEN		BIT(9)
+#define RCC_MC_APB1LPENCLRR_SPI2LPEN		BIT(11)
+#define RCC_MC_APB1LPENCLRR_SPI3LPEN		BIT(12)
+#define RCC_MC_APB1LPENCLRR_USART2LPEN		BIT(14)
+#define RCC_MC_APB1LPENCLRR_USART3LPEN		BIT(15)
+#define RCC_MC_APB1LPENCLRR_UART4LPEN		BIT(16)
+#define RCC_MC_APB1LPENCLRR_UART5LPEN		BIT(17)
+#define RCC_MC_APB1LPENCLRR_UART7LPEN		BIT(18)
+#define RCC_MC_APB1LPENCLRR_UART8LPEN		BIT(19)
+#define RCC_MC_APB1LPENCLRR_I2C1LPEN		BIT(21)
+#define RCC_MC_APB1LPENCLRR_I2C2LPEN		BIT(22)
+#define RCC_MC_APB1LPENCLRR_I2C3LPEN		BIT(23)
+#define RCC_MC_APB1LPENCLRR_I2C5LPEN		BIT(24)
+#define RCC_MC_APB1LPENCLRR_SPDIFLPEN		BIT(26)
+#define RCC_MC_APB1LPENCLRR_CECLPEN		BIT(27)
+#define RCC_MC_APB1LPENCLRR_WWDG1LPEN		BIT(28)
+#define RCC_MC_APB1LPENCLRR_DAC12LPEN		BIT(29)
+#define RCC_MC_APB1LPENCLRR_MDIOSLPEN		BIT(31)
+
+/* RCC_MC_APB2LPENSETR register fields */
+#define RCC_MC_APB2LPENSETR_TIM1LPEN		BIT(0)
+#define RCC_MC_APB2LPENSETR_TIM8LPEN		BIT(1)
+#define RCC_MC_APB2LPENSETR_TIM15LPEN		BIT(2)
+#define RCC_MC_APB2LPENSETR_TIM16LPEN		BIT(3)
+#define RCC_MC_APB2LPENSETR_TIM17LPEN		BIT(4)
+#define RCC_MC_APB2LPENSETR_SPI1LPEN		BIT(8)
+#define RCC_MC_APB2LPENSETR_SPI4LPEN		BIT(9)
+#define RCC_MC_APB2LPENSETR_SPI5LPEN		BIT(10)
+#define RCC_MC_APB2LPENSETR_USART6LPEN		BIT(13)
+#define RCC_MC_APB2LPENSETR_SAI1LPEN		BIT(16)
+#define RCC_MC_APB2LPENSETR_SAI2LPEN		BIT(17)
+#define RCC_MC_APB2LPENSETR_SAI3LPEN		BIT(18)
+#define RCC_MC_APB2LPENSETR_DFSDMLPEN		BIT(20)
+#define RCC_MC_APB2LPENSETR_ADFSDMLPEN		BIT(21)
+#define RCC_MC_APB2LPENSETR_FDCANLPEN		BIT(24)
+
+/* RCC_MC_APB2LPENCLRR register fields */
+#define RCC_MC_APB2LPENCLRR_TIM1LPEN		BIT(0)
+#define RCC_MC_APB2LPENCLRR_TIM8LPEN		BIT(1)
+#define RCC_MC_APB2LPENCLRR_TIM15LPEN		BIT(2)
+#define RCC_MC_APB2LPENCLRR_TIM16LPEN		BIT(3)
+#define RCC_MC_APB2LPENCLRR_TIM17LPEN		BIT(4)
+#define RCC_MC_APB2LPENCLRR_SPI1LPEN		BIT(8)
+#define RCC_MC_APB2LPENCLRR_SPI4LPEN		BIT(9)
+#define RCC_MC_APB2LPENCLRR_SPI5LPEN		BIT(10)
+#define RCC_MC_APB2LPENCLRR_USART6LPEN		BIT(13)
+#define RCC_MC_APB2LPENCLRR_SAI1LPEN		BIT(16)
+#define RCC_MC_APB2LPENCLRR_SAI2LPEN		BIT(17)
+#define RCC_MC_APB2LPENCLRR_SAI3LPEN		BIT(18)
+#define RCC_MC_APB2LPENCLRR_DFSDMLPEN		BIT(20)
+#define RCC_MC_APB2LPENCLRR_ADFSDMLPEN		BIT(21)
+#define RCC_MC_APB2LPENCLRR_FDCANLPEN		BIT(24)
+
+/* RCC_MC_APB3LPENSETR register fields */
+#define RCC_MC_APB3LPENSETR_LPTIM2LPEN		BIT(0)
+#define RCC_MC_APB3LPENSETR_LPTIM3LPEN		BIT(1)
+#define RCC_MC_APB3LPENSETR_LPTIM4LPEN		BIT(2)
+#define RCC_MC_APB3LPENSETR_LPTIM5LPEN		BIT(3)
+#define RCC_MC_APB3LPENSETR_SAI4LPEN		BIT(8)
+#define RCC_MC_APB3LPENSETR_SYSCFGLPEN		BIT(11)
+#define RCC_MC_APB3LPENSETR_VREFLPEN		BIT(13)
+#define RCC_MC_APB3LPENSETR_TMPSENSLPEN		BIT(16)
+#define RCC_MC_APB3LPENSETR_PMBCTRLLPEN		BIT(17)
+
+/* RCC_MC_APB3LPENCLRR register fields */
+#define RCC_MC_APB3LPENCLRR_LPTIM2LPEN		BIT(0)
+#define RCC_MC_APB3LPENCLRR_LPTIM3LPEN		BIT(1)
+#define RCC_MC_APB3LPENCLRR_LPTIM4LPEN		BIT(2)
+#define RCC_MC_APB3LPENCLRR_LPTIM5LPEN		BIT(3)
+#define RCC_MC_APB3LPENCLRR_SAI4LPEN		BIT(8)
+#define RCC_MC_APB3LPENCLRR_SYSCFGLPEN		BIT(11)
+#define RCC_MC_APB3LPENCLRR_VREFLPEN		BIT(13)
+#define RCC_MC_APB3LPENCLRR_TMPSENSLPEN		BIT(16)
+#define RCC_MC_APB3LPENCLRR_PMBCTRLLPEN		BIT(17)
+
+/* RCC_MC_AHB2LPENSETR register fields */
+#define RCC_MC_AHB2LPENSETR_DMA1LPEN		BIT(0)
+#define RCC_MC_AHB2LPENSETR_DMA2LPEN		BIT(1)
+#define RCC_MC_AHB2LPENSETR_DMAMUXLPEN		BIT(2)
+#define RCC_MC_AHB2LPENSETR_ADC12LPEN		BIT(5)
+#define RCC_MC_AHB2LPENSETR_USBOLPEN		BIT(8)
+#define RCC_MC_AHB2LPENSETR_SDMMC3LPEN		BIT(16)
+
+/* RCC_MC_AHB2LPENCLRR register fields */
+#define RCC_MC_AHB2LPENCLRR_DMA1LPEN		BIT(0)
+#define RCC_MC_AHB2LPENCLRR_DMA2LPEN		BIT(1)
+#define RCC_MC_AHB2LPENCLRR_DMAMUXLPEN		BIT(2)
+#define RCC_MC_AHB2LPENCLRR_ADC12LPEN		BIT(5)
+#define RCC_MC_AHB2LPENCLRR_USBOLPEN		BIT(8)
+#define RCC_MC_AHB2LPENCLRR_SDMMC3LPEN		BIT(16)
+
+/* RCC_MC_AHB3LPENSETR register fields */
+#define RCC_MC_AHB3LPENSETR_DCMILPEN		BIT(0)
+#define RCC_MC_AHB3LPENSETR_CRYP2LPEN		BIT(4)
+#define RCC_MC_AHB3LPENSETR_HASH2LPEN		BIT(5)
+#define RCC_MC_AHB3LPENSETR_RNG2LPEN		BIT(6)
+#define RCC_MC_AHB3LPENSETR_CRC2LPEN		BIT(7)
+#define RCC_MC_AHB3LPENSETR_HSEMLPEN		BIT(11)
+#define RCC_MC_AHB3LPENSETR_IPCCLPEN		BIT(12)
+
+/* RCC_MC_AHB3LPENCLRR register fields */
+#define RCC_MC_AHB3LPENCLRR_DCMILPEN		BIT(0)
+#define RCC_MC_AHB3LPENCLRR_CRYP2LPEN		BIT(4)
+#define RCC_MC_AHB3LPENCLRR_HASH2LPEN		BIT(5)
+#define RCC_MC_AHB3LPENCLRR_RNG2LPEN		BIT(6)
+#define RCC_MC_AHB3LPENCLRR_CRC2LPEN		BIT(7)
+#define RCC_MC_AHB3LPENCLRR_HSEMLPEN		BIT(11)
+#define RCC_MC_AHB3LPENCLRR_IPCCLPEN		BIT(12)
+
+/* RCC_MC_AHB4LPENSETR register fields */
+#define RCC_MC_AHB4LPENSETR_GPIOALPEN		BIT(0)
+#define RCC_MC_AHB4LPENSETR_GPIOBLPEN		BIT(1)
+#define RCC_MC_AHB4LPENSETR_GPIOCLPEN		BIT(2)
+#define RCC_MC_AHB4LPENSETR_GPIODLPEN		BIT(3)
+#define RCC_MC_AHB4LPENSETR_GPIOELPEN		BIT(4)
+#define RCC_MC_AHB4LPENSETR_GPIOFLPEN		BIT(5)
+#define RCC_MC_AHB4LPENSETR_GPIOGLPEN		BIT(6)
+#define RCC_MC_AHB4LPENSETR_GPIOHLPEN		BIT(7)
+#define RCC_MC_AHB4LPENSETR_GPIOILPEN		BIT(8)
+#define RCC_MC_AHB4LPENSETR_GPIOJLPEN		BIT(9)
+#define RCC_MC_AHB4LPENSETR_GPIOKLPEN		BIT(10)
+
+/* RCC_MC_AHB4LPENCLRR register fields */
+#define RCC_MC_AHB4LPENCLRR_GPIOALPEN		BIT(0)
+#define RCC_MC_AHB4LPENCLRR_GPIOBLPEN		BIT(1)
+#define RCC_MC_AHB4LPENCLRR_GPIOCLPEN		BIT(2)
+#define RCC_MC_AHB4LPENCLRR_GPIODLPEN		BIT(3)
+#define RCC_MC_AHB4LPENCLRR_GPIOELPEN		BIT(4)
+#define RCC_MC_AHB4LPENCLRR_GPIOFLPEN		BIT(5)
+#define RCC_MC_AHB4LPENCLRR_GPIOGLPEN		BIT(6)
+#define RCC_MC_AHB4LPENCLRR_GPIOHLPEN		BIT(7)
+#define RCC_MC_AHB4LPENCLRR_GPIOILPEN		BIT(8)
+#define RCC_MC_AHB4LPENCLRR_GPIOJLPEN		BIT(9)
+#define RCC_MC_AHB4LPENCLRR_GPIOKLPEN		BIT(10)
+
+/* RCC_MC_AXIMLPENSETR register fields */
+#define RCC_MC_AXIMLPENSETR_SYSRAMLPEN		BIT(0)
+
+/* RCC_MC_AXIMLPENCLRR register fields */
+#define RCC_MC_AXIMLPENCLRR_SYSRAMLPEN		BIT(0)
+
+/* RCC_MC_MLAHBLPENSETR register fields */
+#define RCC_MC_MLAHBLPENSETR_SRAM1LPEN		BIT(0)
+#define RCC_MC_MLAHBLPENSETR_SRAM2LPEN		BIT(1)
+#define RCC_MC_MLAHBLPENSETR_SRAM34LPEN		BIT(2)
+#define RCC_MC_MLAHBLPENSETR_RETRAMLPEN		BIT(4)
+
+/* RCC_MC_MLAHBLPENCLRR register fields */
+#define RCC_MC_MLAHBLPENCLRR_SRAM1LPEN		BIT(0)
+#define RCC_MC_MLAHBLPENCLRR_SRAM2LPEN		BIT(1)
+#define RCC_MC_MLAHBLPENCLRR_SRAM34LPEN		BIT(2)
+#define RCC_MC_MLAHBLPENCLRR_RETRAMLPEN		BIT(4)
+
+/* RCC_MC_RSTSCLRR register fields */
+#define RCC_MC_RSTSCLRR_PORRSTF			BIT(0)
+#define RCC_MC_RSTSCLRR_BORRSTF			BIT(1)
+#define RCC_MC_RSTSCLRR_PADRSTF			BIT(2)
+#define RCC_MC_RSTSCLRR_HCSSRSTF		BIT(3)
+#define RCC_MC_RSTSCLRR_VCORERSTF		BIT(4)
+#define RCC_MC_RSTSCLRR_MCURSTF			BIT(5)
+#define RCC_MC_RSTSCLRR_MPSYSRSTF		BIT(6)
+#define RCC_MC_RSTSCLRR_MCSYSRSTF		BIT(7)
+#define RCC_MC_RSTSCLRR_IWDG1RSTF		BIT(8)
+#define RCC_MC_RSTSCLRR_IWDG2RSTF		BIT(9)
+#define RCC_MC_RSTSCLRR_WWDG1RSTF		BIT(10)
+
+/* RCC_MC_CIER register fields */
+#define RCC_MC_CIER_LSIRDYIE			BIT(0)
+#define RCC_MC_CIER_LSERDYIE			BIT(1)
+#define RCC_MC_CIER_HSIRDYIE			BIT(2)
+#define RCC_MC_CIER_HSERDYIE			BIT(3)
+#define RCC_MC_CIER_CSIRDYIE			BIT(4)
+#define RCC_MC_CIER_PLL1DYIE			BIT(8)
+#define RCC_MC_CIER_PLL2DYIE			BIT(9)
+#define RCC_MC_CIER_PLL3DYIE			BIT(10)
+#define RCC_MC_CIER_PLL4DYIE			BIT(11)
+#define RCC_MC_CIER_LSECSSIE			BIT(16)
+#define RCC_MC_CIER_WKUPIE			BIT(20)
+
+/* RCC_MC_CIFR register fields */
+#define RCC_MC_CIFR_LSIRDYF			BIT(0)
+#define RCC_MC_CIFR_LSERDYF			BIT(1)
+#define RCC_MC_CIFR_HSIRDYF			BIT(2)
+#define RCC_MC_CIFR_HSERDYF			BIT(3)
+#define RCC_MC_CIFR_CSIRDYF			BIT(4)
+#define RCC_MC_CIFR_PLL1DYF			BIT(8)
+#define RCC_MC_CIFR_PLL2DYF			BIT(9)
+#define RCC_MC_CIFR_PLL3DYF			BIT(10)
+#define RCC_MC_CIFR_PLL4DYF			BIT(11)
+#define RCC_MC_CIFR_LSECSSF			BIT(16)
+#define RCC_MC_CIFR_WKUPF			BIT(20)
+
+/* RCC_VERR register fields */
+#define RCC_VERR_MINREV_MASK			GENMASK(3, 0)
+#define RCC_VERR_MINREV_SHIFT			0
+#define RCC_VERR_MAJREV_MASK			GENMASK(7, 4)
+#define RCC_VERR_MAJREV_SHIFT			4
+
+/* Used for RCC_OCENSETR and RCC_OCENCLRR registers */
+#define RCC_OCENR_HSION				BIT(0)
+#define RCC_OCENR_HSIKERON			BIT(1)
+#define RCC_OCENR_CSION				BIT(4)
+#define RCC_OCENR_CSIKERON			BIT(5)
+#define RCC_OCENR_DIGBYP			BIT(7)
+#define RCC_OCENR_HSEON				BIT(8)
+#define RCC_OCENR_HSEKERON			BIT(9)
+#define RCC_OCENR_HSEBYP			BIT(10)
+#define RCC_OCENR_HSECSSON			BIT(11)
+
+/* Offset between RCC_MP_xxxENSETR and RCC_MP_xxxENCLRR registers */
+#define RCC_MP_ENCLRR_OFFSET			U(4)
+
+/* Offset between RCC_xxxRSTSETR and RCC_xxxRSTCLRR registers */
+#define RCC_RSTCLRR_OFFSET			U(4)
+
+/* Used for most of DIVR register: max div for RTC */
+#define RCC_DIVR_DIV_MASK			GENMASK(5, 0)
+#define RCC_DIVR_DIVRDY				BIT(31)
+
+/* Masks for specific DIVR registers */
+#define RCC_APBXDIV_MASK			GENMASK(2, 0)
+#define RCC_MPUDIV_MASK				GENMASK(2, 0)
+#define RCC_AXIDIV_MASK				GENMASK(2, 0)
+#define RCC_MCUDIV_MASK				GENMASK(3, 0)
+
+/* Used for most of RCC_<x>SELR registers */
+#define RCC_SELR_SRC_MASK			GENMASK(2, 0)
+#define RCC_SELR_REFCLK_SRC_MASK		GENMASK(1, 0)
+#define RCC_SELR_SRCRDY				BIT(31)
+
+/* Used for all RCC_PLL<n>CR registers */
+#define RCC_PLLNCR_PLLON			BIT(0)
+#define RCC_PLLNCR_PLLRDY			BIT(1)
+#define RCC_PLLNCR_SSCG_CTRL			BIT(2)
+#define RCC_PLLNCR_DIVPEN			BIT(4)
+#define RCC_PLLNCR_DIVQEN			BIT(5)
+#define RCC_PLLNCR_DIVREN			BIT(6)
+#define RCC_PLLNCR_DIVEN_SHIFT			4
+
+/* Used for all RCC_PLL<n>CFGR1 registers */
+#define RCC_PLLNCFGR1_DIVM_MASK			GENMASK(21, 16)
+#define RCC_PLLNCFGR1_DIVM_SHIFT		16
+#define RCC_PLLNCFGR1_DIVN_MASK			GENMASK(8, 0)
+#define RCC_PLLNCFGR1_DIVN_SHIFT		0
+
+/* Only for PLL3 and PLL4 */
+#define RCC_PLLNCFGR1_IFRGE_MASK		GENMASK(25, 24)
+#define RCC_PLLNCFGR1_IFRGE_SHIFT		24
+
+/* Used for all RCC_PLL<n>CFGR2 registers */
+#define RCC_PLLNCFGR2_DIVX_MASK			GENMASK(6, 0)
+#define RCC_PLLNCFGR2_DIVP_MASK			GENMASK(6, 0)
+#define RCC_PLLNCFGR2_DIVP_SHIFT		0
+#define RCC_PLLNCFGR2_DIVQ_MASK			GENMASK(14, 8)
+#define RCC_PLLNCFGR2_DIVQ_SHIFT		8
+#define RCC_PLLNCFGR2_DIVR_MASK			GENMASK(22, 16)
+#define RCC_PLLNCFGR2_DIVR_SHIFT		16
+
+/* Used for all RCC_PLL<n>FRACR registers */
+#define RCC_PLLNFRACR_FRACV_SHIFT		3
+#define RCC_PLLNFRACR_FRACV_MASK		GENMASK(15, 3)
+#define RCC_PLLNFRACR_FRACLE			BIT(16)
+
+/* Used for all RCC_PLL<n>CSGR registers */
+#define RCC_PLLNCSGR_INC_STEP_SHIFT		16
+#define RCC_PLLNCSGR_INC_STEP_MASK		GENMASK(30, 16)
+#define RCC_PLLNCSGR_MOD_PER_SHIFT		0
+#define RCC_PLLNCSGR_MOD_PER_MASK		GENMASK(12, 0)
+#define RCC_PLLNCSGR_SSCG_MODE_SHIFT		15
+#define RCC_PLLNCSGR_SSCG_MODE_MASK		BIT(15)
+
+/* Used for TIMER Prescaler */
+#define RCC_TIMGXPRER_TIMGXPRE			BIT(0)
+
+/* Used for RCC_MCO related operations */
+#define RCC_MCOCFG_MCOON			BIT(12)
+#define RCC_MCOCFG_MCODIV_MASK			GENMASK(7, 4)
+#define RCC_MCOCFG_MCODIV_SHIFT			4
+#define RCC_MCOCFG_MCOSRC_MASK			GENMASK(2, 0)
+
 #endif /* STM32MP1_RCC_H */
diff --git a/include/drivers/st/stm32mp1_usb.h b/include/drivers/st/stm32mp1_usb.h
new file mode 100644
index 0000000..06a34cb
--- /dev/null
+++ b/include/drivers/st/stm32mp1_usb.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef STM32MP1_USB_H
+#define STM32MP1_USB_H
+
+#include <drivers/usb_device.h>
+
+void stm32mp1_usb_init_driver(struct usb_handle *usb_core_handle,
+			      struct pcd_handle *pcd_handle,
+			      void *base_register);
+
+#endif /* STM32MP1_USB_H */
diff --git a/include/drivers/st/stm32mp_clkfunc.h b/include/drivers/st/stm32mp_clkfunc.h
index c7e0b6e..c3329cc 100644
--- a/include/drivers/st/stm32mp_clkfunc.h
+++ b/include/drivers/st/stm32mp_clkfunc.h
@@ -19,7 +19,6 @@
 				     const char *prop_name,
 				     uint32_t dflt_value);
 
-int fdt_get_rcc_node(void *fdt);
 int fdt_rcc_read_uint32_array(const char *prop_name, uint32_t count,
 			      uint32_t *array);
 int fdt_rcc_subnode_offset(const char *name);
diff --git a/include/drivers/st/stpmic1.h b/include/drivers/st/stpmic1.h
index f7e293b..dc096cd 100644
--- a/include/drivers/st/stpmic1.h
+++ b/include/drivers/st/stpmic1.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2016-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -86,15 +86,15 @@
 #define ITSOURCE4_REG			0xB3U
 
 /* Registers masks */
-#define LDO_VOLTAGE_MASK		0x7CU
-#define BUCK_VOLTAGE_MASK		0xFCU
+#define LDO_VOLTAGE_MASK		GENMASK(6, 2)
+#define BUCK_VOLTAGE_MASK		GENMASK(7, 2)
 #define LDO_BUCK_VOLTAGE_SHIFT		2
-#define LDO_BUCK_ENABLE_MASK		0x01U
-#define LDO_BUCK_HPLP_ENABLE_MASK	0x02U
+#define LDO_BUCK_ENABLE_MASK		BIT(0)
+#define LDO_BUCK_HPLP_ENABLE_MASK	BIT(1)
 #define LDO_BUCK_HPLP_SHIFT		1
-#define LDO_BUCK_RANK_MASK		0x01U
-#define LDO_BUCK_RESET_MASK		0x01U
-#define LDO_BUCK_PULL_DOWN_MASK		0x03U
+#define LDO_BUCK_RANK_MASK		BIT(0)
+#define LDO_BUCK_RESET_MASK		BIT(0)
+#define LDO_BUCK_PULL_DOWN_MASK		GENMASK(1, 0)
 
 /* Pull down register */
 #define BUCK1_PULL_DOWN_SHIFT		0
@@ -135,12 +135,12 @@
 /* Main PMIC VINLOW Control Register (VIN_CONTROL_REGC DMSC) */
 #define SWIN_DETECTOR_ENABLED		BIT(7)
 #define SWOUT_DETECTOR_ENABLED          BIT(6)
-#define VINLOW_HYST_MASK		0x3
+#define VINLOW_HYST_MASK		GENMASK(1, 0)
 #define VINLOW_HYST_SHIFT		4
-#define VINLOW_THRESHOLD_MASK		0x7
+#define VINLOW_THRESHOLD_MASK		GENMASK(2, 0)
 #define VINLOW_THRESHOLD_SHIFT		1
-#define VINLOW_ENABLED			0x01
-#define VINLOW_CTRL_REG_MASK		0xFF
+#define VINLOW_ENABLED			BIT(0)
+#define VINLOW_CTRL_REG_MASK		GENMASK(7, 0)
 
 /* USB Control Register */
 #define BOOST_OVP_DISABLED		BIT(7)
diff --git a/include/drivers/ufs.h b/include/drivers/ufs.h
index 574c4ea..c074e85 100644
--- a/include/drivers/ufs.h
+++ b/include/drivers/ufs.h
@@ -254,6 +254,17 @@
 #define UFS_VENDOR_SKHYNIX		U(0x1AD)
 
 #define MAX_MODEL_LEN 16
+
+/* maximum number of retries for a general UIC command  */
+#define UFS_UIC_COMMAND_RETRIES		3
+
+/* maximum number of link-startup retries */
+#define DME_LINKSTARTUP_RETRIES		10
+
+#define HCE_ENABLE_OUTER_RETRIES	3
+#define HCE_ENABLE_INNER_RETRIES	50
+#define HCE_ENABLE_TIMEOUT_US		100
+
 /**
  * ufs_dev_desc - ufs device details from the device descriptor
  * @wmanufacturerid: card details
diff --git a/include/drivers/usb_device.h b/include/drivers/usb_device.h
new file mode 100644
index 0000000..8fdb6ae
--- /dev/null
+++ b/include/drivers/usb_device.h
@@ -0,0 +1,278 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef USB_DEVICE_H
+#define USB_DEVICE_H
+
+#include <stdint.h>
+
+#include <lib/utils_def.h>
+
+#define USBD_MAX_NUM_INTERFACES			1U
+#define USBD_MAX_NUM_CONFIGURATION		1U
+
+#define USB_LEN_DEV_QUALIFIER_DESC		0x0AU
+#define USB_LEN_DEV_DESC			0x12U
+#define USB_LEN_CFG_DESC			0x09U
+#define USB_LEN_IF_DESC				0x09U
+#define USB_LEN_EP_DESC				0x07U
+#define USB_LEN_OTG_DESC			0x03U
+#define USB_LEN_LANGID_STR_DESC			0x04U
+#define USB_LEN_OTHER_SPEED_DESC_SIZ		0x09U
+
+#define USBD_IDX_LANGID_STR			0x00U
+#define USBD_IDX_MFC_STR			0x01U
+#define USBD_IDX_PRODUCT_STR			0x02U
+#define USBD_IDX_SERIAL_STR			0x03U
+#define USBD_IDX_CONFIG_STR			0x04U
+#define USBD_IDX_INTERFACE_STR			0x05U
+#define USBD_IDX_USER0_STR			0x06U
+
+#define USB_REQ_TYPE_STANDARD			0x00U
+#define USB_REQ_TYPE_CLASS			0x20U
+#define USB_REQ_TYPE_VENDOR			0x40U
+#define USB_REQ_TYPE_MASK			0x60U
+
+#define USB_REQ_RECIPIENT_DEVICE		0x00U
+#define USB_REQ_RECIPIENT_INTERFACE		0x01U
+#define USB_REQ_RECIPIENT_ENDPOINT		0x02U
+#define USB_REQ_RECIPIENT_MASK			0x1FU
+
+#define USB_REQ_DIRECTION			0x80U
+
+#define USB_REQ_GET_STATUS			0x00U
+#define USB_REQ_CLEAR_FEATURE			0x01U
+#define USB_REQ_SET_FEATURE			0x03U
+#define USB_REQ_SET_ADDRESS			0x05U
+#define USB_REQ_GET_DESCRIPTOR			0x06U
+#define USB_REQ_SET_DESCRIPTOR			0x07U
+#define USB_REQ_GET_CONFIGURATION		0x08U
+#define USB_REQ_SET_CONFIGURATION		0x09U
+#define USB_REQ_GET_INTERFACE			0x0AU
+#define USB_REQ_SET_INTERFACE			0x0BU
+#define USB_REQ_SYNCH_FRAME			0x0CU
+
+#define USB_DESC_TYPE_DEVICE			0x01U
+#define USB_DESC_TYPE_CONFIGURATION		0x02U
+#define USB_DESC_TYPE_STRING			0x03U
+#define USB_DESC_TYPE_INTERFACE			0x04U
+#define USB_DESC_TYPE_ENDPOINT			0x05U
+#define USB_DESC_TYPE_DEVICE_QUALIFIER		0x06U
+#define USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION	0x07U
+#define USB_DESC_TYPE_BOS			0x0FU
+
+#define USB_CONFIG_REMOTE_WAKEUP		2U
+#define USB_CONFIG_SELF_POWERED			1U
+
+#define USB_MAX_EP0_SIZE			64U
+
+/* Device Status */
+#define USBD_STATE_DEFAULT			1U
+#define USBD_STATE_ADDRESSED			2U
+#define USBD_STATE_CONFIGURED			3U
+#define USBD_STATE_SUSPENDED			4U
+
+/* EP0 State */
+#define USBD_EP0_IDLE				0U
+#define USBD_EP0_SETUP				1U
+#define USBD_EP0_DATA_IN			2U
+#define USBD_EP0_DATA_OUT			3U
+#define USBD_EP0_STATUS_IN			4U
+#define USBD_EP0_STATUS_OUT			5U
+#define USBD_EP0_STALL				6U
+
+#define USBD_EP_TYPE_CTRL			0U
+#define USBD_EP_TYPE_ISOC			1U
+#define USBD_EP_TYPE_BULK			2U
+#define USBD_EP_TYPE_INTR			3U
+
+#define  USBD_OUT_EPNUM_MASK			GENMASK(15, 0)
+#define  USBD_OUT_COUNT_MASK			GENMASK(31, 16)
+#define  USBD_OUT_COUNT_SHIFT			16U
+
+/* Number of EP supported, allow to reduce footprint: default max = 15 */
+#ifndef CONFIG_USBD_EP_NB
+#define  USBD_EP_NB				15U
+#else
+#define  USBD_EP_NB				CONFIG_USBD_EP_NB
+#endif
+
+#define LOBYTE(x)	((uint8_t)((x) & 0x00FF))
+#define HIBYTE(x)	((uint8_t)(((x) & 0xFF00) >> 8))
+
+struct usb_setup_req {
+	uint8_t bm_request;
+	uint8_t b_request;
+	uint16_t value;
+	uint16_t index;
+	uint16_t length;
+};
+
+struct usb_handle;
+
+struct usb_class {
+	uint8_t (*init)(struct usb_handle *pdev, uint8_t cfgidx);
+	uint8_t (*de_init)(struct usb_handle *pdev, uint8_t cfgidx);
+	/* Control Endpoints */
+	uint8_t (*setup)(struct usb_handle *pdev, struct usb_setup_req *req);
+	uint8_t (*ep0_tx_sent)(struct usb_handle *pdev);
+	uint8_t (*ep0_rx_ready)(struct usb_handle *pdev);
+	/* Class Specific Endpoints */
+	uint8_t (*data_in)(struct usb_handle *pdev, uint8_t epnum);
+	uint8_t (*data_out)(struct usb_handle *pdev, uint8_t epnum);
+	uint8_t (*sof)(struct usb_handle *pdev);
+	uint8_t (*iso_in_incomplete)(struct usb_handle *pdev, uint8_t epnum);
+	uint8_t (*iso_out_incomplete)(struct usb_handle *pdev, uint8_t epnum);
+};
+
+/* Following USB Device status */
+enum usb_status {
+	USBD_OK = 0U,
+	USBD_BUSY,
+	USBD_FAIL,
+	USBD_TIMEOUT
+};
+
+/* Action to do after IT handling */
+enum usb_action {
+	USB_NOTHING = 0U,
+	USB_DATA_OUT,
+	USB_DATA_IN,
+	USB_SETUP,
+	USB_ENUM_DONE,
+	USB_READ_DATA_PACKET,
+	USB_READ_SETUP_PACKET,
+	USB_RESET,
+	USB_RESUME,
+	USB_SUSPEND,
+	USB_LPM,
+	USB_SOF,
+	USB_DISCONNECT,
+	USB_WRITE_EMPTY
+};
+
+/* USB Device descriptors structure */
+struct usb_desc {
+	uint8_t *(*get_device_desc)(uint16_t *length);
+	uint8_t *(*get_lang_id_desc)(uint16_t *length);
+	uint8_t *(*get_manufacturer_desc)(uint16_t *length);
+	uint8_t *(*get_product_desc)(uint16_t *length);
+	uint8_t *(*get_serial_desc)(uint16_t *length);
+	uint8_t *(*get_configuration_desc)(uint16_t *length);
+	uint8_t *(*get_interface_desc)(uint16_t *length);
+	uint8_t *(*get_usr_desc)(uint8_t index, uint16_t *length);
+	uint8_t *(*get_config_desc)(uint16_t *length);
+	uint8_t *(*get_device_qualifier_desc)(uint16_t *length);
+	/* optional: high speed capable device operating at its other speed */
+	uint8_t *(*get_other_speed_config_desc)(uint16_t *length);
+};
+
+/* USB Device handle structure */
+struct usb_endpoint {
+	uint32_t status;
+	uint32_t total_length;
+	uint32_t rem_length;
+	uint32_t maxpacket;
+};
+
+/*
+ * EndPoint descriptor
+ * num : Endpoint number, between 0 and 15 (limited by USBD_EP_NB)
+ * is_in: Endpoint direction
+ * type : Endpoint type
+ * maxpacket:  Endpoint Max packet size: between 0 and 64KB
+ * xfer_buff: Pointer to transfer buffer
+ * xfer_len: Current transfer lengt
+ * hxfer_count: Partial transfer length in case of multi packet transfer
+ */
+struct usbd_ep {
+	uint8_t num;
+	bool is_in;
+	uint8_t type;
+	uint32_t maxpacket;
+	uint8_t *xfer_buff;
+	uint32_t xfer_len;
+	uint32_t xfer_count;
+};
+
+enum pcd_lpm_state {
+	LPM_L0 = 0x00U, /* on */
+	LPM_L1 = 0x01U, /* LPM L1 sleep */
+	LPM_L2 = 0x02U, /* suspend */
+	LPM_L3 = 0x03U, /* off */
+};
+
+/* USB Device descriptors structure */
+struct usb_driver {
+	enum usb_status (*ep0_out_start)(void *handle);
+	enum usb_status (*ep_start_xfer)(void *handle, struct usbd_ep *ep);
+	enum usb_status (*ep0_start_xfer)(void *handle, struct usbd_ep *ep);
+	enum usb_status (*write_packet)(void *handle, uint8_t *src,
+				     uint8_t ch_ep_num, uint16_t len);
+	void *(*read_packet)(void *handle, uint8_t *dest, uint16_t len);
+	enum usb_status (*ep_set_stall)(void *handle, struct usbd_ep *ep);
+	enum usb_status (*start_device)(void *handle);
+	enum usb_status (*stop_device)(void *handle);
+	enum usb_status (*set_address)(void *handle, uint8_t address);
+	enum usb_status (*write_empty_tx_fifo)(void *handle,
+					    uint32_t epnum, uint32_t xfer_len,
+					    uint32_t *xfer_count,
+					    uint32_t maxpacket,
+					    uint8_t **xfer_buff);
+	enum usb_action (*it_handler)(void *handle, uint32_t *param);
+};
+
+/* USB Peripheral Controller Drivers */
+struct pcd_handle {
+	void *instance; /* Register base address */
+	struct usbd_ep in_ep[USBD_EP_NB]; /* IN endpoint parameters */
+	struct usbd_ep out_ep[USBD_EP_NB]; /* OUT endpoint parameters */
+	uint32_t setup[12]; /* Setup packet buffer */
+	enum pcd_lpm_state lpm_state; /* LPM State */
+};
+
+/* USB Device handle structure */
+struct usb_handle {
+	uint8_t id;
+	uint32_t dev_config;
+	uint32_t dev_config_status;
+	struct usb_endpoint ep_in[USBD_EP_NB];
+	struct usb_endpoint ep_out[USBD_EP_NB];
+	uint32_t ep0_state;
+	uint32_t ep0_data_len;
+	uint8_t dev_state;
+	uint8_t dev_old_state;
+	uint8_t dev_address;
+	uint32_t dev_remote_wakeup;
+	struct usb_setup_req request;
+	const struct usb_desc *desc;
+	struct usb_class *class;
+	void *class_data;
+	void *user_data;
+	struct pcd_handle *data;
+	const struct usb_driver *driver;
+};
+
+enum usb_status usb_core_handle_it(struct usb_handle *pdev);
+enum usb_status usb_core_receive(struct usb_handle *pdev, uint8_t ep_addr,
+				 uint8_t *p_buf, uint32_t len);
+enum usb_status usb_core_transmit(struct usb_handle *pdev, uint8_t ep_addr,
+				  uint8_t *p_buf, uint32_t len);
+enum usb_status usb_core_receive_ep0(struct usb_handle *pdev, uint8_t *p_buf,
+				     uint32_t len);
+enum usb_status usb_core_transmit_ep0(struct usb_handle *pdev, uint8_t *p_buf,
+				      uint32_t len);
+void usb_core_ctl_error(struct usb_handle *pdev);
+enum usb_status usb_core_start(struct usb_handle *pdev);
+enum usb_status usb_core_stop(struct usb_handle *pdev);
+enum usb_status register_usb_driver(struct usb_handle *pdev,
+				    struct pcd_handle *pcd_handle,
+				    const struct usb_driver *driver,
+				    void *driver_handle);
+enum usb_status register_platform(struct usb_handle *pdev,
+				  const struct usb_desc *plat_call_back);
+
+#endif /* USB_DEVICE_H */
diff --git a/include/dt-bindings/interrupt-controller/arm-gic.h b/include/dt-bindings/interrupt-controller/arm-gic.h
index aa9158c..803cd9c 100644
--- a/include/dt-bindings/interrupt-controller/arm-gic.h
+++ b/include/dt-bindings/interrupt-controller/arm-gic.h
@@ -1,21 +1,26 @@
-/* SPDX-License-Identifier: GPL-2.0 or BSD-3-Clause */
 /*
+ * Copyright (c) 2019-2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: MIT
+ *
  * This header provides constants for the ARM GIC.
  */
 
 #ifndef _DT_BINDINGS_INTERRUPT_CONTROLLER_ARM_GIC_H
 #define _DT_BINDINGS_INTERRUPT_CONTROLLER_ARM_GIC_H
 
+#include <dt-bindings/interrupt-controller/irq.h>
+
 /* interrupt specifier cell 0 */
 
 #define GIC_SPI 0
 #define GIC_PPI 1
 
-#define IRQ_TYPE_NONE		0
-#define IRQ_TYPE_EDGE_RISING	1
-#define IRQ_TYPE_EDGE_FALLING	2
-#define IRQ_TYPE_EDGE_BOTH	(IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)
-#define IRQ_TYPE_LEVEL_HIGH	4
-#define IRQ_TYPE_LEVEL_LOW	8
+/*
+ * Interrupt specifier cell 2.
+ * The flags in irq.h are valid, plus those below.
+ */
+#define GIC_CPU_MASK_RAW(x) ((x) << 8)
+#define GIC_CPU_MASK_SIMPLE(num) GIC_CPU_MASK_RAW((1 << (num)) - 1)
 
 #endif
diff --git a/include/dt-bindings/interrupt-controller/irq.h b/include/dt-bindings/interrupt-controller/irq.h
new file mode 100644
index 0000000..94e7f95
--- /dev/null
+++ b/include/dt-bindings/interrupt-controller/irq.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * This header provides constants for most IRQ bindings.
+ *
+ * Most IRQ bindings include a flags cell as part of the IRQ specifier.
+ * In most cases, the format of the flags cell uses the standard values
+ * defined in this header.
+ */
+
+#ifndef _DT_BINDINGS_INTERRUPT_CONTROLLER_IRQ_H
+#define _DT_BINDINGS_INTERRUPT_CONTROLLER_IRQ_H
+
+#define IRQ_TYPE_NONE		0
+#define IRQ_TYPE_EDGE_RISING	1
+#define IRQ_TYPE_EDGE_FALLING	2
+#define IRQ_TYPE_EDGE_BOTH	(IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)
+#define IRQ_TYPE_LEVEL_HIGH	4
+#define IRQ_TYPE_LEVEL_LOW	8
+
+#endif
diff --git a/include/dt-bindings/soc/stm32mp15-tzc400.h b/include/dt-bindings/soc/stm32mp15-tzc400.h
new file mode 100644
index 0000000..54cd902
--- /dev/null
+++ b/include/dt-bindings/soc/stm32mp15-tzc400.h
@@ -0,0 +1,36 @@
+/* SPDX-License-Identifier: GPL-2.0+ OR BSD-3-Clause */
+/*
+ * Copyright (C) 2021, STMicroelectronics - All Rights Reserved
+ */
+
+#ifndef _DT_BINDINGS_STM32MP15_TZC400_H
+#define _DT_BINDINGS_STM32MP15_TZC400_H
+
+#include <drivers/arm/tzc_common.h>
+
+#define STM32MP1_TZC_A7_ID		U(0)
+#define STM32MP1_TZC_M4_ID		U(1)
+#define STM32MP1_TZC_LCD_ID		U(3)
+#define STM32MP1_TZC_GPU_ID		U(4)
+#define STM32MP1_TZC_MDMA_ID		U(5)
+#define STM32MP1_TZC_DMA_ID		U(6)
+#define STM32MP1_TZC_USB_HOST_ID	U(7)
+#define STM32MP1_TZC_USB_OTG_ID		U(8)
+#define STM32MP1_TZC_SDMMC_ID		U(9)
+#define STM32MP1_TZC_ETH_ID		U(10)
+#define STM32MP1_TZC_DAP_ID		U(15)
+
+#define TZC_REGION_NSEC_ALL_ACCESS_RDWR \
+	(TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_A7_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_GPU_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_LCD_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_MDMA_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_M4_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DMA_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_HOST_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_OTG_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_SDMMC_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_ETH_ID) | \
+	 TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DAP_ID))
+
+#endif /* _DT_BINDINGS_STM32MP15_TZC400_H */
diff --git a/include/export/common/ep_info_exp.h b/include/export/common/ep_info_exp.h
index 9d2969f..a5bd10a 100644
--- a/include/export/common/ep_info_exp.h
+++ b/include/export/common/ep_info_exp.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -24,11 +24,23 @@
 #define ENTRY_POINT_INFO_ARGS_OFFSET	U(0x14)
 #endif
 
-/* Security state of the image. */
-#define EP_SECURITY_MASK	UL(0x1)
+/*
+ * Security state of the image. Bit 0 and
+ * bit 5 are used to determine the security
+ * state of the image as follows:
+ *
+ * ---------------------------------
+ *  Bit 5 | Bit 0 | Security state
+ * ---------------------------------
+ *   0        0      EP_SECURE
+ *   0        1      EP_NON_SECURE
+ *   1        1      EP_REALM
+ */
+#define EP_SECURITY_MASK	UL(0x21)
 #define EP_SECURITY_SHIFT	UL(0)
 #define EP_SECURE		UL(0x0)
 #define EP_NON_SECURE		UL(0x1)
+#define EP_REALM		UL(0x21)
 
 /* Endianness of the image. */
 #define EP_EE_MASK		U(0x2)
diff --git a/include/export/common/tbbr/tbbr_img_def_exp.h b/include/export/common/tbbr/tbbr_img_def_exp.h
index 18f0125..98544c0 100644
--- a/include/export/common/tbbr/tbbr_img_def_exp.h
+++ b/include/export/common/tbbr/tbbr_img_def_exp.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -91,7 +91,20 @@
 /* FW_CONFIG */
 #define FW_CONFIG_ID			U(31)
 
+/*
+ * Primary FWU metadata image ID
+ */
+#define FWU_METADATA_IMAGE_ID		U(32)
+
+/*
+ * Backup FWU metadata image ID
+ */
+#define BKUP_FWU_METADATA_IMAGE_ID	U(33)
+
+/* Realm Monitor Manager (RMM) */
+#define RMM_IMAGE_ID			U(34)
+
 /* Max Images */
-#define MAX_IMAGE_IDS			U(32)
+#define MAX_IMAGE_IDS			U(35)
 
 #endif /* ARM_TRUSTED_FIRMWARE_EXPORT_COMMON_TBBR_TBBR_IMG_DEF_EXP_H */
diff --git a/include/lib/cpus/aarch64/cortex_a510.h b/include/lib/cpus/aarch64/cortex_a510.h
new file mode 100644
index 0000000..6a4cfdf
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_a510.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_A510_H
+#define CORTEX_A510_H
+
+#define CORTEX_A510_MIDR					U(0x410FD460)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_A510_CPUECTLR_EL1				S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_A510_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_A510_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
+
+#endif /* CORTEX_A510_H */
diff --git a/include/lib/cpus/aarch64/cortex_a710.h b/include/lib/cpus/aarch64/cortex_a710.h
new file mode 100644
index 0000000..d2bc146
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_a710.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_A710_H
+#define CORTEX_A710_H
+
+#define CORTEX_A710_MIDR					U(0x410FD470)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_A710_CPUECTLR_EL1				S3_0_C15_C1_4
+#define CORTEX_A710_CPUECTLR_EL1_PFSTIDIS_BIT			(ULL(1) << 8)
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_A710_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_A710_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A710_CPUACTLR_EL1 				S3_0_C15_C1_0
+#define CORTEX_A710_CPUACTLR_EL1_BIT_46				(ULL(1) << 46)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A710_CPUACTLR5_EL1				S3_0_C15_C8_0
+#define CORTEX_A710_CPUACTLR5_EL1_BIT_13			(ULL(1) << 13)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A710_CPUECTLR2_EL1				S3_0_C15_C1_5
+#define CORTEX_A710_CPUECTLR2_EL1_PF_MODE_CNSRV			ULL(9)
+#define CPUECTLR2_EL1_PF_MODE_LSB				U(11)
+#define CPUECTLR2_EL1_PF_MODE_WIDTH				U(4)
+
+#endif /* CORTEX_A710_H */
diff --git a/include/lib/cpus/aarch64/cortex_a76.h b/include/lib/cpus/aarch64/cortex_a76.h
index b522e8e..a61825f 100644
--- a/include/lib/cpus/aarch64/cortex_a76.h
+++ b/include/lib/cpus/aarch64/cortex_a76.h
@@ -20,7 +20,6 @@
 
 #define CORTEX_A76_CPUECTLR_EL1_WS_THR_L2	(ULL(3) << 24)
 #define CORTEX_A76_CPUECTLR_EL1_BIT_51		(ULL(1) << 51)
-#define CORTEX_A76_CPUECTLR_EL1_BIT_53		(ULL(1) << 53)
 
 /*******************************************************************************
  * CPU Auxiliary Control register specific definitions.
diff --git a/include/lib/cpus/aarch64/cortex_a77.h b/include/lib/cpus/aarch64/cortex_a77.h
index ed84c0f..5753e90 100644
--- a/include/lib/cpus/aarch64/cortex_a77.h
+++ b/include/lib/cpus/aarch64/cortex_a77.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -17,7 +17,6 @@
  ******************************************************************************/
 #define CORTEX_A77_CPUECTLR_EL1				S3_0_C15_C1_4
 #define CORTEX_A77_CPUECTLR_EL1_BIT_8			(ULL(1) << 8)
-#define CORTEX_A77_CPUECTLR_EL1_BIT_53			(ULL(1) << 53)
 
 /*******************************************************************************
  * CPU Power Control register specific definitions.
@@ -25,6 +24,12 @@
 #define CORTEX_A77_CPUPWRCTLR_EL1			S3_0_C15_C2_7
 #define CORTEX_A77_CPUPWRCTLR_EL1_CORE_PWRDN_BIT	(U(1) << 0)
 
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A77_ACTLR2_EL1				S3_0_C15_C1_1
+#define CORTEX_A77_ACTLR2_EL1_BIT_2			(ULL(1) << 2)
+
 #define CORTEX_A77_CPUPSELR_EL3				S3_6_C15_C8_0
 #define CORTEX_A77_CPUPCR_EL3				S3_6_C15_C8_1
 #define CORTEX_A77_CPUPOR_EL3				S3_6_C15_C8_2
diff --git a/include/lib/cpus/aarch64/cortex_a78.h b/include/lib/cpus/aarch64/cortex_a78.h
index 0d4712b..42b0833 100644
--- a/include/lib/cpus/aarch64/cortex_a78.h
+++ b/include/lib/cpus/aarch64/cortex_a78.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,30 +15,35 @@
  * CPU Extended Control register specific definitions.
  ******************************************************************************/
 #define CORTEX_A78_CPUECTLR_EL1				S3_0_C15_C1_4
+#define CORTEX_A78_CPUECTLR_EL1_BIT_8			(ULL(1) << 8)
+#define CORTEX_A78_CPUECTLR_EL1_PF_MODE_CNSRV		ULL(3)
+#define CPUECTLR_EL1_PF_MODE_LSB				U(6)
+#define CPUECTLR_EL1_PF_MODE_WIDTH				U(2)
 
 /*******************************************************************************
  * CPU Power Control register specific definitions
  ******************************************************************************/
-#define CORTEX_A78_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_A78_CPUPWRCTLR_EL1			S3_0_C15_C2_7
 #define CORTEX_A78_CPUPWRCTLR_EL1_CORE_PWRDN_EN_BIT	U(1)
 
 /*******************************************************************************
  * CPU Auxiliary Control register specific definitions.
  ******************************************************************************/
-#define CORTEX_A78_ACTLR_TAM_BIT				(ULL(1) << 30)
+#define CORTEX_A78_ACTLR_TAM_BIT			(ULL(1) << 30)
 
 #define CORTEX_A78_ACTLR2_EL1				S3_0_C15_C1_1
 #define CORTEX_A78_ACTLR2_EL1_BIT_1			(ULL(1) << 1)
+#define CORTEX_A78_ACTLR2_EL1_BIT_2			(ULL(1) << 2)
 
 /*******************************************************************************
  * CPU Activity Monitor Unit register specific definitions.
  ******************************************************************************/
-#define CPUAMCNTENCLR0_EL0					S3_3_C15_C2_4
-#define CPUAMCNTENSET0_EL0					S3_3_C15_C2_5
-#define CPUAMCNTENCLR1_EL0					S3_3_C15_C3_0
-#define CPUAMCNTENSET1_EL0					S3_3_C15_C3_1
+#define CPUAMCNTENCLR0_EL0				S3_3_C15_C2_4
+#define CPUAMCNTENSET0_EL0				S3_3_C15_C2_5
+#define CPUAMCNTENCLR1_EL0				S3_3_C15_C3_0
+#define CPUAMCNTENSET1_EL0				S3_3_C15_C3_1
 
-#define CORTEX_A78_AMU_GROUP0_MASK				U(0xF)
-#define CORTEX_A78_AMU_GROUP1_MASK				U(0x7)
+#define CORTEX_A78_AMU_GROUP0_MASK			U(0xF)
+#define CORTEX_A78_AMU_GROUP1_MASK			U(0x7)
 
 #endif /* CORTEX_A78_H */
diff --git a/include/lib/cpus/aarch64/cortex_a78_ae.h b/include/lib/cpus/aarch64/cortex_a78_ae.h
index 24ae7ee..0c8adcf 100644
--- a/include/lib/cpus/aarch64/cortex_a78_ae.h
+++ b/include/lib/cpus/aarch64/cortex_a78_ae.h
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,4 +12,10 @@
 
 #define CORTEX_A78_AE_MIDR U(0x410FD420)
 
+/*******************************************************************************
+ * CPU Extended Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A78_AE_CPUECTLR_EL1			CORTEX_A78_CPUECTLR_EL1
+#define CORTEX_A78_AE_CPUECTLR_EL1_BIT_8		CORTEX_A78_CPUECTLR_EL1_BIT_8
+
 #endif /* CORTEX_A78_AE_H */
diff --git a/include/lib/cpus/aarch64/cortex_a78c.h b/include/lib/cpus/aarch64/cortex_a78c.h
new file mode 100644
index 0000000..adb13bc
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_a78c.h
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_A78C_H
+#define CORTEX_A78C_H
+
+
+#define CORTEX_A78C_MIDR			        U(0x410FD4B1)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A78C_CPUECTLR_EL1		        S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_A78C_CPUPWRCTLR_EL1			S3_0_C15_C2_7
+#define CORTEX_A78C_CPUPWRCTLR_EL1_CORE_PWRDN_EN_BIT	U(1)
+
+#endif /* CORTEX_A78C_H */
diff --git a/include/lib/cpus/aarch64/cortex_hayes.h b/include/lib/cpus/aarch64/cortex_hayes.h
new file mode 100644
index 0000000..82022e9
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_hayes.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_HAYES_H
+#define CORTEX_HAYES_H
+
+#define CORTEX_HAYES_MIDR					U(0x410FD800)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_HAYES_CPUECTLR_EL1				S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_HAYES_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_HAYES_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
+
+#endif /* CORTEX_HAYES_H */
diff --git a/include/lib/cpus/aarch64/cortex_hunter.h b/include/lib/cpus/aarch64/cortex_hunter.h
new file mode 100644
index 0000000..8b59fd9
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_hunter.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_HUNTER_H
+#define CORTEX_HUNTER_H
+
+#define CORTEX_HUNTER_MIDR					U(0x410FD810)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_HUNTER_CPUECTLR_EL1				S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_HUNTER_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_HUNTER_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
+
+#endif /* CORTEX_HUNTER_H */
diff --git a/include/lib/cpus/aarch64/cortex_klein.h b/include/lib/cpus/aarch64/cortex_klein.h
deleted file mode 100644
index 729b3bf..0000000
--- a/include/lib/cpus/aarch64/cortex_klein.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef CORTEX_KLEIN_H
-#define CORTEX_KLEIN_H
-
-#define CORTEX_KLEIN_MIDR					U(0x410FD460)
-
-/*******************************************************************************
- * CPU Extended Control register specific definitions
- ******************************************************************************/
-#define CORTEX_KLEIN_CPUECTLR_EL1				S3_0_C15_C1_4
-
-/*******************************************************************************
- * CPU Power Control register specific definitions
- ******************************************************************************/
-#define CORTEX_KLEIN_CPUPWRCTLR_EL1				S3_0_C15_C2_7
-#define CORTEX_KLEIN_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
-
-#endif /* CORTEX_KLEIN_H */
diff --git a/include/lib/cpus/aarch64/cortex_makalu.h b/include/lib/cpus/aarch64/cortex_makalu.h
new file mode 100644
index 0000000..4e0dc86
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_makalu.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_MAKALU_H
+#define CORTEX_MAKALU_H
+
+#define CORTEX_MAKALU_MIDR					U(0x410FD4D0)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_MAKALU_CPUECTLR_EL1				S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_MAKALU_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_MAKALU_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
+
+#endif /* CORTEX_MAKALU_H */
diff --git a/include/lib/cpus/aarch64/cortex_makalu_elp_arm.h b/include/lib/cpus/aarch64/cortex_makalu_elp_arm.h
new file mode 100644
index 0000000..a0d788e
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_makalu_elp_arm.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_MAKALU_ELP_ARM_H
+#define CORTEX_MAKALU_ELP_ARM_H
+
+#define CORTEX_MAKALU_ELP_ARM_MIDR				U(0x410FD4E0)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_MAKALU_ELP_ARM_CPUECTLR_EL1			S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_MAKALU_ELP_ARM_CPUPWRCTLR_EL1			S3_0_C15_C2_7
+#define CORTEX_MAKALU_ELP_ARM_CPUPWRCTLR_EL1_CORE_PWRDN_BIT	U(1)
+
+#endif /* CORTEX_MAKALU_ELP_ARM_H */
diff --git a/include/lib/cpus/aarch64/cortex_matterhorn.h b/include/lib/cpus/aarch64/cortex_matterhorn.h
deleted file mode 100644
index 0185533..0000000
--- a/include/lib/cpus/aarch64/cortex_matterhorn.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef CORTEX_MATTERHORN_H
-#define CORTEX_MATTERHORN_H
-
-#define CORTEX_MATTERHORN_MIDR					U(0x410FD470)
-
-/*******************************************************************************
- * CPU Extended Control register specific definitions
- ******************************************************************************/
-#define CORTEX_MATTERHORN_CPUECTLR_EL1				S3_0_C15_C1_4
-
-/*******************************************************************************
- * CPU Power Control register specific definitions
- ******************************************************************************/
-#define CORTEX_MATTERHORN_CPUPWRCTLR_EL1			S3_0_C15_C2_7
-#define CORTEX_MATTERHORN_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
-
-#endif /* CORTEX_MATTERHORN_H */
diff --git a/include/lib/cpus/aarch64/cortex_x2.h b/include/lib/cpus/aarch64/cortex_x2.h
new file mode 100644
index 0000000..9ce1223
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_x2.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CORTEX_X2_H
+#define CORTEX_X2_H
+
+#define CORTEX_X2_MIDR						U(0x410FD480)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_X2_CPUECTLR_EL1					S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define CORTEX_X2_CPUPWRCTLR_EL1				S3_0_C15_C2_7
+#define CORTEX_X2_CPUPWRCTLR_EL1_CORE_PWRDN_BIT			U(1)
+
+#endif /* CORTEX_X2_H */
diff --git a/include/lib/cpus/aarch64/neoverse_demeter.h b/include/lib/cpus/aarch64/neoverse_demeter.h
new file mode 100644
index 0000000..230ed66
--- /dev/null
+++ b/include/lib/cpus/aarch64/neoverse_demeter.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef NEOVERSE_DEMETER_H
+#define NEOVERSE_DEMETER_H
+
+#define NEOVERSE_DEMETER_MIDR				U(0x410FD4F0)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions
+ ******************************************************************************/
+#define NEOVERSE_DEMETER_CPUECTLR_EL1			S3_0_C15_C1_4
+
+/*******************************************************************************
+ * CPU Power Control register specific definitions
+ ******************************************************************************/
+#define NEOVERSE_DEMETER_CPUPWRCTLR_EL1			S3_0_C15_C2_7
+#define NEOVERSE_DEMETER_CPUPWRCTLR_EL1_CORE_PWRDN_BIT	U(1)
+
+#endif /* NEOVERSE_DEMETER_H */
diff --git a/include/lib/cpus/aarch64/neoverse_n1.h b/include/lib/cpus/aarch64/neoverse_n1.h
index 9998b93..b50befa 100644
--- a/include/lib/cpus/aarch64/neoverse_n1.h
+++ b/include/lib/cpus/aarch64/neoverse_n1.h
@@ -64,12 +64,4 @@
 #define CPUPOR_EL3	S3_6_C15_C8_2
 #define CPUPMR_EL3	S3_6_C15_C8_3
 
-/******************************************************************************
- * CPU Configuration register definitions.
- *****************************************************************************/
-#define CPUCFR_EL1	S3_0_C15_C0_0
-
-/* SCU bit of CPU Configuration Register, EL1 */
-#define SCU_SHIFT	U(2)
-
 #endif /* NEOVERSE_N1_H */
diff --git a/include/lib/cpus/aarch64/neoverse_n2.h b/include/lib/cpus/aarch64/neoverse_n2.h
new file mode 100644
index 0000000..a1e676e
--- /dev/null
+++ b/include/lib/cpus/aarch64/neoverse_n2.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef NEOVERSE_N2_H
+#define NEOVERSE_N2_H
+
+/* Neoverse N2 ID register for revision r0p0 */
+#define NEOVERSE_N2_MIDR				U(0x410FD490)
+
+/*******************************************************************************
+ * CPU Power control register
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUPWRCTLR_EL1			S3_0_C15_C2_7
+#define NEOVERSE_N2_CORE_PWRDN_EN_BIT			(ULL(1) << 0)
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUECTLR_EL1			S3_0_C15_C1_4
+#define NEOVERSE_N2_CPUECTLR_EL1_EXTLLC_BIT		(ULL(1) << 0)
+#define NEOVERSE_N2_CPUECTLR_EL1_PFSTIDIS_BIT		(ULL(1) << 8)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUACTLR_EL1			S3_0_C15_C1_0
+#define NEOVERSE_N2_CPUACTLR_EL1_BIT_46			(ULL(1) << 46)
+#define NEOVERSE_N2_CPUACTLR_EL1_BIT_22			(ULL(1) << 22)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register 2 specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUACTLR2_EL1			S3_0_C15_C1_1
+#define NEOVERSE_N2_CPUACTLR2_EL1_BIT_2			(ULL(1) << 2)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register 5 specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUACTLR5_EL1			S3_0_C15_C8_0
+#define NEOVERSE_N2_CPUACTLR5_EL1_BIT_44		(ULL(1) << 44)
+#define NEOVERSE_N2_CPUACTLR5_EL1_BIT_13		(ULL(1) << 13)
+#define NEOVERSE_N2_CPUACTLR5_EL1_BIT_17		(ULL(1) << 17)
+
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_N2_CPUECTLR2_EL1			S3_0_C15_C1_5
+#define NEOVERSE_N2_CPUECTLR2_EL1_PF_MODE_CNSRV		ULL(9)
+#define CPUECTLR2_EL1_PF_MODE_LSB			U(11)
+#define CPUECTLR2_EL1_PF_MODE_WIDTH			U(4)
+
+#endif /* NEOVERSE_N2_H */
diff --git a/include/lib/cpus/aarch64/neoverse_n_common.h b/include/lib/cpus/aarch64/neoverse_n_common.h
new file mode 100644
index 0000000..7cb91cd
--- /dev/null
+++ b/include/lib/cpus/aarch64/neoverse_n_common.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef NEOVERSE_N_COMMON_H
+#define NEOVERSE_N_COMMON_H
+
+/******************************************************************************
+ * Neoverse Nx CPU Configuration register definitions
+ *****************************************************************************/
+#define CPUCFR_EL1		S3_0_C15_C0_0
+
+/* SCU bit of CPU Configuration Register, EL1 */
+#define SCU_SHIFT		U(2)
+
+#endif /* NEOVERSE_N_COMMON_H */
diff --git a/include/lib/cpus/aarch64/neoverse_v1.h b/include/lib/cpus/aarch64/neoverse_v1.h
index 650eb4d..e43c907 100644
--- a/include/lib/cpus/aarch64/neoverse_v1.h
+++ b/include/lib/cpus/aarch64/neoverse_v1.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,6 +13,11 @@
  * CPU Extended Control register specific definitions.
  ******************************************************************************/
 #define NEOVERSE_V1_CPUECTLR_EL1				S3_0_C15_C1_4
+#define NEOVERSE_V1_CPUECTLR_EL1_BIT_8				(ULL(1) << 8)
+#define NEOVERSE_V1_CPUECTLR_EL1_BIT_53				(ULL(1) << 53)
+#define NEOVERSE_V1_CPUECTLR_EL1_PF_MODE_CNSRV			ULL(3)
+#define CPUECTLR_EL1_PF_MODE_LSB				U(6)
+#define CPUECTLR_EL1_PF_MODE_WIDTH				U(2)
 
 /*******************************************************************************
  * CPU Power Control register specific definitions
@@ -20,4 +25,11 @@
 #define NEOVERSE_V1_CPUPWRCTLR_EL1				S3_0_C15_C2_7
 #define NEOVERSE_V1_CPUPWRCTLR_EL1_CORE_PWRDN_BIT		U(1)
 
+/*******************************************************************************
+ * CPU Auxiliary Control register specific definitions.
+ ******************************************************************************/
+#define NEOVERSE_V1_ACTLR2_EL1					S3_0_C15_C1_1
+#define NEOVERSE_V1_ACTLR2_EL1_BIT_2				(ULL(1) << 2)
+#define NEOVERSE_V1_ACTLR2_EL1_BIT_28				(ULL(1) << 28)
+
 #endif /* NEOVERSE_V1_H */
diff --git a/include/lib/cpus/aarch64/qemu_max.h b/include/lib/cpus/aarch64/qemu_max.h
new file mode 100644
index 0000000..14da170
--- /dev/null
+++ b/include/lib/cpus/aarch64/qemu_max.h
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef QEMU_MAX_H
+#define QEMU_MAX_H
+
+#include <lib/utils_def.h>
+
+/*
+ *  QEMU MAX midr for revision 0
+ *  00   - Reserved for software use
+ *  0    - Variant
+ *  F    - Architectural features identified in ID_* registers
+ *  051  - 'Q', in a 12-bit field.
+ *  0    - Revision
+ */
+#define QEMU_MAX_MIDR		U(0x000F0510)
+
+#endif /* QEMU_MAX_H */
diff --git a/include/lib/cpus/errata_report.h b/include/lib/cpus/errata_report.h
index 7cac77e..efdedf0 100644
--- a/include/lib/cpus/errata_report.h
+++ b/include/lib/cpus/errata_report.h
@@ -30,4 +30,7 @@
 #define ERRATA_APPLIES		1
 #define ERRATA_MISSING		2
 
+/* Macro to get CPU revision code for checking errata version compatibility. */
+#define CPU_REV(r, p)		((r << 4) | p)
+
 #endif /* ERRATA_REPORT_H */
diff --git a/include/lib/el3_runtime/aarch64/context.h b/include/lib/el3_runtime/aarch64/context.h
index 3490414..698e208 100644
--- a/include/lib/el3_runtime/aarch64/context.h
+++ b/include/lib/el3_runtime/aarch64/context.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -60,7 +60,10 @@
 #define CTX_SPSR_EL3		U(0x18)
 #define CTX_ELR_EL3		U(0x20)
 #define CTX_PMCR_EL0		U(0x28)
-#define CTX_EL3STATE_END	U(0x30)
+#define CTX_IS_IN_EL3		U(0x30)
+#define CTX_CPTR_EL3		U(0x38)
+#define CTX_ZCR_EL3		U(0x40)
+#define CTX_EL3STATE_END	U(0x50) /* Align to the next 16 byte boundary */
 
 /*******************************************************************************
  * Constants that allow assembler code to access members of and the
@@ -159,86 +162,78 @@
 #define CTX_AFSR1_EL2		U(0x10)
 #define CTX_AMAIR_EL2		U(0x18)
 #define CTX_CNTHCTL_EL2		U(0x20)
-#define CTX_CNTHP_CTL_EL2	U(0x28)
-#define CTX_CNTHP_CVAL_EL2	U(0x30)
-#define CTX_CNTHP_TVAL_EL2	U(0x38)
-#define CTX_CNTVOFF_EL2		U(0x40)
-#define CTX_CPTR_EL2		U(0x48)
-#define CTX_DBGVCR32_EL2	U(0x50)
-#define CTX_ELR_EL2		U(0x58)
-#define CTX_ESR_EL2		U(0x60)
-#define CTX_FAR_EL2		U(0x68)
-#define CTX_HACR_EL2		U(0x70)
-#define CTX_HCR_EL2		U(0x78)
-#define CTX_HPFAR_EL2		U(0x80)
-#define CTX_HSTR_EL2		U(0x88)
-#define CTX_ICC_SRE_EL2		U(0x90)
-#define CTX_ICH_HCR_EL2		U(0x98)
-#define CTX_ICH_VMCR_EL2	U(0xa0)
-#define CTX_MAIR_EL2		U(0xa8)
-#define CTX_MDCR_EL2		U(0xb0)
-#define CTX_PMSCR_EL2		U(0xb8)
-#define CTX_SCTLR_EL2		U(0xc0)
-#define CTX_SPSR_EL2		U(0xc8)
-#define CTX_SP_EL2		U(0xd0)
-#define CTX_TCR_EL2		U(0xd8)
-#define CTX_TPIDR_EL2		U(0xe0)
-#define CTX_TTBR0_EL2		U(0xe8)
-#define CTX_VBAR_EL2		U(0xf0)
-#define CTX_VMPIDR_EL2		U(0xf8)
-#define CTX_VPIDR_EL2		U(0x100)
-#define CTX_VTCR_EL2		U(0x108)
-#define CTX_VTTBR_EL2		U(0x110)
+#define CTX_CNTVOFF_EL2		U(0x28)
+#define CTX_CPTR_EL2		U(0x30)
+#define CTX_DBGVCR32_EL2	U(0x38)
+#define CTX_ELR_EL2		U(0x40)
+#define CTX_ESR_EL2		U(0x48)
+#define CTX_FAR_EL2		U(0x50)
+#define CTX_HACR_EL2		U(0x58)
+#define CTX_HCR_EL2		U(0x60)
+#define CTX_HPFAR_EL2		U(0x68)
+#define CTX_HSTR_EL2		U(0x70)
+#define CTX_ICC_SRE_EL2		U(0x78)
+#define CTX_ICH_HCR_EL2		U(0x80)
+#define CTX_ICH_VMCR_EL2	U(0x88)
+#define CTX_MAIR_EL2		U(0x90)
+#define CTX_MDCR_EL2		U(0x98)
+#define CTX_PMSCR_EL2		U(0xa0)
+#define CTX_SCTLR_EL2		U(0xa8)
+#define CTX_SPSR_EL2		U(0xb0)
+#define CTX_SP_EL2		U(0xb8)
+#define CTX_TCR_EL2		U(0xc0)
+#define CTX_TPIDR_EL2		U(0xc8)
+#define CTX_TTBR0_EL2		U(0xd0)
+#define CTX_VBAR_EL2		U(0xd8)
+#define CTX_VMPIDR_EL2		U(0xe0)
+#define CTX_VPIDR_EL2		U(0xe8)
+#define CTX_VTCR_EL2		U(0xf0)
+#define CTX_VTTBR_EL2		U(0xf8)
 
 // Only if MTE registers in use
-#define CTX_TFSR_EL2		U(0x118)
+#define CTX_TFSR_EL2		U(0x100)
 
 // Only if ENABLE_MPAM_FOR_LOWER_ELS==1
-#define CTX_MPAM2_EL2		U(0x120)
-#define CTX_MPAMHCR_EL2		U(0x128)
-#define CTX_MPAMVPM0_EL2	U(0x130)
-#define CTX_MPAMVPM1_EL2	U(0x138)
-#define CTX_MPAMVPM2_EL2	U(0x140)
-#define CTX_MPAMVPM3_EL2	U(0x148)
-#define CTX_MPAMVPM4_EL2	U(0x150)
-#define CTX_MPAMVPM5_EL2	U(0x158)
-#define CTX_MPAMVPM6_EL2	U(0x160)
-#define CTX_MPAMVPM7_EL2	U(0x168)
-#define CTX_MPAMVPMV_EL2	U(0x170)
+#define CTX_MPAM2_EL2		U(0x108)
+#define CTX_MPAMHCR_EL2		U(0x110)
+#define CTX_MPAMVPM0_EL2	U(0x118)
+#define CTX_MPAMVPM1_EL2	U(0x120)
+#define CTX_MPAMVPM2_EL2	U(0x128)
+#define CTX_MPAMVPM3_EL2	U(0x130)
+#define CTX_MPAMVPM4_EL2	U(0x138)
+#define CTX_MPAMVPM5_EL2	U(0x140)
+#define CTX_MPAMVPM6_EL2	U(0x148)
+#define CTX_MPAMVPM7_EL2	U(0x150)
+#define CTX_MPAMVPMV_EL2	U(0x158)
 
 // Starting with Armv8.6
-#define CTX_HAFGRTR_EL2		U(0x178)
-#define CTX_HDFGRTR_EL2		U(0x180)
-#define CTX_HDFGWTR_EL2		U(0x188)
-#define CTX_HFGITR_EL2		U(0x190)
-#define CTX_HFGRTR_EL2		U(0x198)
-#define CTX_HFGWTR_EL2		U(0x1a0)
-#define CTX_CNTPOFF_EL2		U(0x1a8)
+#define CTX_HAFGRTR_EL2		U(0x160)
+#define CTX_HDFGRTR_EL2		U(0x168)
+#define CTX_HDFGWTR_EL2		U(0x170)
+#define CTX_HFGITR_EL2		U(0x178)
+#define CTX_HFGRTR_EL2		U(0x180)
+#define CTX_HFGWTR_EL2		U(0x188)
+#define CTX_CNTPOFF_EL2		U(0x190)
 
 // Starting with Armv8.4
-#define CTX_CNTHPS_CTL_EL2	U(0x1b0)
-#define CTX_CNTHPS_CVAL_EL2	U(0x1b8)
-#define CTX_CNTHPS_TVAL_EL2	U(0x1c0)
-#define CTX_CNTHVS_CTL_EL2	U(0x1c8)
-#define CTX_CNTHVS_CVAL_EL2	U(0x1d0)
-#define CTX_CNTHVS_TVAL_EL2	U(0x1d8)
-#define CTX_CNTHV_CTL_EL2	U(0x1e0)
-#define CTX_CNTHV_CVAL_EL2	U(0x1e8)
-#define CTX_CNTHV_TVAL_EL2	U(0x1f0)
-#define CTX_CONTEXTIDR_EL2	U(0x1f8)
-#define CTX_SDER32_EL2		U(0x200)
-#define CTX_TTBR1_EL2		U(0x208)
-#define CTX_VDISR_EL2		U(0x210)
-#define CTX_VNCR_EL2		U(0x218)
-#define CTX_VSESR_EL2		U(0x220)
-#define CTX_VSTCR_EL2		U(0x228)
-#define CTX_VSTTBR_EL2		U(0x230)
-#define CTX_TRFCR_EL2		U(0x238)
+#define CTX_CONTEXTIDR_EL2	U(0x198)
+#define CTX_SDER32_EL2		U(0x1a0)
+#define CTX_TTBR1_EL2		U(0x1a8)
+#define CTX_VDISR_EL2		U(0x1b0)
+#define CTX_VNCR_EL2		U(0x1b8)
+#define CTX_VSESR_EL2		U(0x1c0)
+#define CTX_VSTCR_EL2		U(0x1c8)
+#define CTX_VSTTBR_EL2		U(0x1d0)
+#define CTX_TRFCR_EL2		U(0x1d8)
 
 // Starting with Armv8.5
-#define CTX_SCXTNUM_EL2		U(0x240)
+#define CTX_SCXTNUM_EL2		U(0x1e0)
+
+// Register for FEAT_HCX
+#define CTX_HCRX_EL2            U(0x1e8)
+
 /* Align to the next 16 byte boundary */
-#define CTX_EL2_SYSREGS_END	U(0x250)
+#define CTX_EL2_SYSREGS_END	U(0x1f0)
 
 #endif /* CTX_INCLUDE_EL2_REGS */
 
@@ -410,13 +405,12 @@
 					 = (uint64_t) (val))
 
 /*
- * Top-level context structure which is used by EL3 firmware to
- * preserve the state of a core at EL1 in one of the two security
- * states and save enough EL3 meta data to be able to return to that
- * EL and security state. The context management library will be used
- * to ensure that SP_EL3 always points to an instance of this
- * structure at exception entry and exit. Each instance will
- * correspond to either the secure or the non-secure state.
+ * Top-level context structure which is used by EL3 firmware to preserve
+ * the state of a core at the next lower EL in a given security state and
+ * save enough EL3 meta data to be able to return to that EL and security
+ * state. The context management library will be used to ensure that
+ * SP_EL3 always points to an instance of this structure at exception
+ * entry and exit.
  */
 typedef struct cpu_context {
 	gp_regs_t gpregs_ctx;
diff --git a/include/lib/el3_runtime/cpu_data.h b/include/lib/el3_runtime/cpu_data.h
index 5426135..2c7b619 100644
--- a/include/lib/el3_runtime/cpu_data.h
+++ b/include/lib/el3_runtime/cpu_data.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -19,16 +19,25 @@
 /* 8-bytes aligned size of psci_cpu_data structure */
 #define PSCI_CPU_DATA_SIZE_ALIGNED	((PSCI_CPU_DATA_SIZE + 7) & ~7)
 
+#if ENABLE_RME
+/* Size of cpu_context array */
+#define CPU_DATA_CONTEXT_NUM		3
 /* Offset of cpu_ops_ptr, size 8 bytes */
+#define CPU_DATA_CPU_OPS_PTR		0x18
+#else /* ENABLE_RME */
+#define CPU_DATA_CONTEXT_NUM		2
 #define CPU_DATA_CPU_OPS_PTR		0x10
+#endif /* ENABLE_RME */
 
 #if ENABLE_PAUTH
 /* 8-bytes aligned offset of apiakey[2], size 16 bytes */
-#define	CPU_DATA_APIAKEY_OFFSET		(0x18 + PSCI_CPU_DATA_SIZE_ALIGNED)
-#define CPU_DATA_CRASH_BUF_OFFSET	(CPU_DATA_APIAKEY_OFFSET + 0x10)
-#else
-#define CPU_DATA_CRASH_BUF_OFFSET	(0x18 + PSCI_CPU_DATA_SIZE_ALIGNED)
-#endif	/* ENABLE_PAUTH */
+#define	CPU_DATA_APIAKEY_OFFSET		(0x8 + PSCI_CPU_DATA_SIZE_ALIGNED \
+					     + CPU_DATA_CPU_OPS_PTR)
+#define CPU_DATA_CRASH_BUF_OFFSET	(0x10 + CPU_DATA_APIAKEY_OFFSET)
+#else /* ENABLE_PAUTH */
+#define CPU_DATA_CRASH_BUF_OFFSET	(0x8 + PSCI_CPU_DATA_SIZE_ALIGNED \
+					     + CPU_DATA_CPU_OPS_PTR)
+#endif /* ENABLE_PAUTH */
 
 /* need enough space in crash buffer to save 8 registers */
 #define CPU_DATA_CRASH_BUF_SIZE		64
@@ -65,11 +74,14 @@
 
 #ifndef __ASSEMBLER__
 
+#include <assert.h>
+#include <stdint.h>
+
 #include <arch_helpers.h>
 #include <lib/cassert.h>
 #include <lib/psci/psci.h>
+
 #include <platform_def.h>
-#include <stdint.h>
 
 /* Offsets for the cpu_data structure */
 #define CPU_DATA_PSCI_LOCK_OFFSET	__builtin_offsetof\
@@ -80,27 +92,34 @@
 		(cpu_data_t, platform_cpu_data)
 #endif
 
+typedef enum context_pas {
+	CPU_CONTEXT_SECURE = 0,
+	CPU_CONTEXT_NS,
+#if ENABLE_RME
+	CPU_CONTEXT_REALM,
+#endif
+	CPU_CONTEXT_NUM
+} context_pas_t;
+
 /*******************************************************************************
  * Function & variable prototypes
  ******************************************************************************/
 
 /*******************************************************************************
  * Cache of frequently used per-cpu data:
- *   Pointers to non-secure and secure security state contexts
+ *   Pointers to non-secure, realm, and secure security state contexts
  *   Address of the crash stack
  * It is aligned to the cache line boundary to allow efficient concurrent
  * manipulation of these pointers on different cpus
  *
- * TODO: Add other commonly used variables to this (tf_issues#90)
- *
  * The data structure and the _cpu_data accessors should not be used directly
  * by components that have per-cpu members. The member access macros should be
  * used for this.
  ******************************************************************************/
 typedef struct cpu_data {
 #ifdef __aarch64__
-	void *cpu_context[2];
-#endif
+	void *cpu_context[CPU_DATA_CONTEXT_NUM];
+#endif /* __aarch64__ */
 	uintptr_t cpu_ops_ptr;
 	struct psci_cpu_data psci_svc_cpu_data;
 #if ENABLE_PAUTH
@@ -122,10 +141,15 @@
 
 extern cpu_data_t percpu_data[PLATFORM_CORE_COUNT];
 
+#ifdef __aarch64__
+CASSERT(CPU_DATA_CONTEXT_NUM == CPU_CONTEXT_NUM,
+		assert_cpu_data_context_num_mismatch);
+#endif
+
 #if ENABLE_PAUTH
 CASSERT(CPU_DATA_APIAKEY_OFFSET == __builtin_offsetof
 	(cpu_data_t, apiakey),
-	assert_cpu_data_crash_stack_offset_mismatch);
+	assert_cpu_data_pauth_stack_offset_mismatch);
 #endif
 
 #if CRASH_REPORTING
@@ -160,6 +184,31 @@
 struct cpu_data *_cpu_data(void);
 #endif
 
+/*
+ * Returns the index of the cpu_context array for the given security state.
+ * All accesses to cpu_context should be through this helper to make sure
+ * an access is not out-of-bounds. The function assumes security_state is
+ * valid.
+ */
+static inline context_pas_t get_cpu_context_index(uint32_t security_state)
+{
+	if (security_state == SECURE) {
+		return CPU_CONTEXT_SECURE;
+	} else {
+#if ENABLE_RME
+		if (security_state == NON_SECURE) {
+			return CPU_CONTEXT_NS;
+		} else {
+			assert(security_state == REALM);
+			return CPU_CONTEXT_REALM;
+		}
+#else
+		assert(security_state == NON_SECURE);
+		return CPU_CONTEXT_NS;
+#endif
+	}
+}
+
 /**************************************************************************
  * APIs for initialising and accessing per-cpu data
  *************************************************************************/
diff --git a/include/lib/extensions/amu.h b/include/lib/extensions/amu.h
index dcbdd5a..6452f7e 100644
--- a/include/lib/extensions/amu.h
+++ b/include/lib/extensions/amu.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,82 +10,38 @@
 #include <stdbool.h>
 #include <stdint.h>
 
-#include <lib/cassert.h>
-#include <lib/utils_def.h>
+#include <context.h>
 
 #include <platform_def.h>
 
-/* All group 0 counters */
-#define AMU_GROUP0_COUNTERS_MASK	U(0xf)
-#define AMU_GROUP0_NR_COUNTERS		U(4)
-
-#ifdef PLAT_AMU_GROUP1_COUNTERS_MASK
-#define AMU_GROUP1_COUNTERS_MASK	PLAT_AMU_GROUP1_COUNTERS_MASK
+#if __aarch64__
+void amu_enable(bool el2_unused, cpu_context_t *ctx);
 #else
-#define AMU_GROUP1_COUNTERS_MASK	U(0)
+void amu_enable(bool el2_unused);
 #endif
 
-/* Calculate number of group 1 counters */
-#if (AMU_GROUP1_COUNTERS_MASK	& (1 << 15))
-#define	AMU_GROUP1_NR_COUNTERS		16U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 14))
-#define	AMU_GROUP1_NR_COUNTERS		15U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 13))
-#define	AMU_GROUP1_NR_COUNTERS		14U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 12))
-#define	AMU_GROUP1_NR_COUNTERS		13U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 11))
-#define	AMU_GROUP1_NR_COUNTERS		12U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 10))
-#define	AMU_GROUP1_NR_COUNTERS		11U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 9))
-#define	AMU_GROUP1_NR_COUNTERS		10U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 8))
-#define	AMU_GROUP1_NR_COUNTERS		9U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 7))
-#define	AMU_GROUP1_NR_COUNTERS		8U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 6))
-#define	AMU_GROUP1_NR_COUNTERS		7U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 5))
-#define	AMU_GROUP1_NR_COUNTERS		6U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 4))
-#define	AMU_GROUP1_NR_COUNTERS		5U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 3))
-#define	AMU_GROUP1_NR_COUNTERS		4U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 2))
-#define	AMU_GROUP1_NR_COUNTERS		3U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 1))
-#define	AMU_GROUP1_NR_COUNTERS		2U
-#elif (AMU_GROUP1_COUNTERS_MASK	& (1 << 0))
-#define	AMU_GROUP1_NR_COUNTERS		1U
-#else
-#define	AMU_GROUP1_NR_COUNTERS		0U
-#endif
-
-CASSERT(AMU_GROUP1_COUNTERS_MASK <= 0xffff, invalid_amu_group1_counters_mask);
-
-struct amu_ctx {
-	uint64_t group0_cnts[AMU_GROUP0_NR_COUNTERS];
-
-#if AMU_GROUP1_NR_COUNTERS
-	uint64_t group1_cnts[AMU_GROUP1_NR_COUNTERS];
-#endif
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+/*
+ * AMU data for a single core.
+ */
+struct amu_core {
+	uint16_t enable; /* Mask of auxiliary counters to enable */
 };
 
-bool amu_supported(void);
-void amu_enable(bool el2_unused);
+/*
+ * Topological platform data specific to the AMU.
+ */
+struct amu_topology {
+	struct amu_core cores[PLATFORM_CORE_COUNT]; /* Per-core data */
+};
 
-/* Group 0 configuration helpers */
-uint64_t amu_group0_cnt_read(unsigned int idx);
-void amu_group0_cnt_write(unsigned int idx, uint64_t val);
-
-#if AMU_GROUP1_NR_COUNTERS
-bool amu_group1_supported(void);
-
-/* Group 1 configuration helpers */
-uint64_t amu_group1_cnt_read(unsigned int idx);
-void amu_group1_cnt_write(unsigned int idx, uint64_t val);
-void amu_group1_set_evtype(unsigned int idx, unsigned int val);
-#endif
+#if !ENABLE_AMU_FCONF
+/*
+ * Retrieve the platform's AMU topology. A `NULL` return value is treated as a
+ * non-fatal error, in which case no auxiliary counters will be enabled.
+ */
+const struct amu_topology *plat_amu_topology(void);
+#endif /* ENABLE_AMU_FCONF */
+#endif /* ENABLE_AMU_AUXILIARY_COUNTERS */
 
 #endif /* AMU_H */
diff --git a/include/lib/extensions/amu_private.h b/include/lib/extensions/amu_private.h
deleted file mode 100644
index 30ce59d..0000000
--- a/include/lib/extensions/amu_private.h
+++ /dev/null
@@ -1,19 +0,0 @@
-/*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef AMU_PRIVATE_H
-#define AMU_PRIVATE_H
-
-#include <stdint.h>
-
-uint64_t amu_group0_cnt_read_internal(unsigned int idx);
-void amu_group0_cnt_write_internal(unsigned int idx, uint64_t val);
-
-uint64_t amu_group1_cnt_read_internal(unsigned int idx);
-void amu_group1_cnt_write_internal(unsigned int idx, uint64_t val);
-void amu_group1_set_evtype_internal(unsigned int idx, unsigned int val);
-
-#endif /* AMU_PRIVATE_H */
diff --git a/include/lib/extensions/mpam.h b/include/lib/extensions/mpam.h
index ac8c00a..414adcb 100644
--- a/include/lib/extensions/mpam.h
+++ b/include/lib/extensions/mpam.h
@@ -9,7 +9,6 @@
 
 #include <stdbool.h>
 
-bool mpam_supported(void);
 void mpam_enable(bool el2_unused);
 
 #endif /* MPAM_H */
diff --git a/include/lib/extensions/sme.h b/include/lib/extensions/sme.h
new file mode 100644
index 0000000..893f9f2
--- /dev/null
+++ b/include/lib/extensions/sme.h
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SME_H
+#define SME_H
+
+#include <stdbool.h>
+
+#include <context.h>
+
+/*
+ * Maximum value of LEN field in SMCR_ELx. This is different than the maximum
+ * supported value which is platform dependent. In the first version of SME the
+ * LEN field is limited to 4 bits but will be expanded in future iterations.
+ * To support different versions, the code that discovers the supported vector
+ * lengths will write the max value into SMCR_ELx then read it back to see how
+ * many bits are implemented.
+ */
+#define SME_SMCR_LEN_MAX	U(0x1FF)
+
+void sme_enable(cpu_context_t *context);
+void sme_disable(cpu_context_t *context);
+
+#endif /* SME_H */
diff --git a/include/lib/extensions/sve.h b/include/lib/extensions/sve.h
index 83df177..4b66cdb 100644
--- a/include/lib/extensions/sve.h
+++ b/include/lib/extensions/sve.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,9 +7,9 @@
 #ifndef SVE_H
 #define SVE_H
 
-#include <stdbool.h>
+#include <context.h>
 
-bool sve_supported(void);
-void sve_enable(bool el2_unused);
+void sve_enable(cpu_context_t *context);
+void sve_disable(cpu_context_t *context);
 
 #endif /* SVE_H */
diff --git a/include/lib/extensions/sys_reg_trace.h b/include/lib/extensions/sys_reg_trace.h
new file mode 100644
index 0000000..74470fe
--- /dev/null
+++ b/include/lib/extensions/sys_reg_trace.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SYS_REG_TRACE_H
+#define SYS_REG_TRACE_H
+
+#include <context.h>
+
+#if __aarch64__
+void sys_reg_trace_enable(cpu_context_t *context);
+#else
+void sys_reg_trace_enable(void);
+#endif /* __aarch64__ */
+
+#endif /* SYS_REG_TRACE_H */
diff --git a/include/lib/extensions/trbe.h b/include/lib/extensions/trbe.h
new file mode 100644
index 0000000..1753ab6
--- /dev/null
+++ b/include/lib/extensions/trbe.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TRBE_H
+#define TRBE_H
+
+void trbe_enable(void);
+
+#endif /* TRBE_H */
diff --git a/include/lib/extensions/trf.h b/include/lib/extensions/trf.h
new file mode 100644
index 0000000..18f17f3
--- /dev/null
+++ b/include/lib/extensions/trf.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TRF_H
+#define TRF_H
+
+void trf_enable(void);
+
+#endif /* TRF_H */
diff --git a/include/lib/fconf/fconf_amu_getter.h b/include/lib/fconf/fconf_amu_getter.h
new file mode 100644
index 0000000..2faee73
--- /dev/null
+++ b/include/lib/fconf/fconf_amu_getter.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FCONF_AMU_GETTER_H
+#define FCONF_AMU_GETTER_H
+
+#include <lib/extensions/amu.h>
+
+#define amu__config_getter(id)	fconf_amu_config.id
+
+struct fconf_amu_config {
+	const struct amu_topology *topology;
+};
+
+extern struct fconf_amu_config fconf_amu_config;
+
+#endif /* FCONF_AMU_GETTER_H */
diff --git a/include/lib/fconf/fconf_mpmm_getter.h b/include/lib/fconf/fconf_mpmm_getter.h
new file mode 100644
index 0000000..50d991a
--- /dev/null
+++ b/include/lib/fconf/fconf_mpmm_getter.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FCONF_MPMM_GETTER_H
+#define FCONF_MPMM_GETTER_H
+
+#include <lib/mpmm/mpmm.h>
+
+#define mpmm__config_getter(id)	fconf_mpmm_config.id
+
+struct fconf_mpmm_config {
+	const struct mpmm_topology *topology;
+};
+
+extern struct fconf_mpmm_config fconf_mpmm_config;
+
+#endif /* FCONF_MPMM_GETTER_H */
diff --git a/include/lib/fconf/fconf_tbbr_getter.h b/include/lib/fconf/fconf_tbbr_getter.h
index 6066af6..db98b68 100644
--- a/include/lib/fconf/fconf_tbbr_getter.h
+++ b/include/lib/fconf/fconf_tbbr_getter.h
@@ -23,9 +23,6 @@
 	uint32_t disable_auth;
 	void *mbedtls_heap_addr;
 	size_t mbedtls_heap_size;
-#if MEASURED_BOOT
-	uint8_t bl2_hash_data[TCG_DIGEST_SIZE];
-#endif
 };
 
 extern struct tbbr_dyn_config_t tbbr_dyn_config;
diff --git a/include/lib/gpt_rme/gpt_rme.h b/include/lib/gpt_rme/gpt_rme.h
new file mode 100644
index 0000000..379b915
--- /dev/null
+++ b/include/lib/gpt_rme/gpt_rme.h
@@ -0,0 +1,276 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef GPT_RME_H
+#define GPT_RME_H
+
+#include <stdint.h>
+
+#include <arch.h>
+
+/******************************************************************************/
+/* GPT helper macros and definitions                                          */
+/******************************************************************************/
+
+/*
+ * Structure for specifying a mapping range and it's properties. This should not
+ * be manually initialized, using the MAP_GPT_REGION_x macros is recommended as
+ * to avoid potential incompatibilities in the future.
+ */
+typedef struct pas_region {
+	uintptr_t	base_pa;	/* Base address for PAS. */
+	size_t		size;		/* Size of the PAS. */
+	unsigned int	attrs;		/* PAS GPI and entry type. */
+} pas_region_t;
+
+/* GPT GPI definitions */
+#define GPT_GPI_NO_ACCESS		U(0x0)
+#define GPT_GPI_SECURE			U(0x8)
+#define GPT_GPI_NS			U(0x9)
+#define GPT_GPI_ROOT			U(0xA)
+#define GPT_GPI_REALM			U(0xB)
+#define GPT_GPI_ANY			U(0xF)
+#define GPT_GPI_VAL_MASK		UL(0xF)
+
+/* PAS attribute GPI definitions. */
+#define GPT_PAS_ATTR_GPI_SHIFT		U(0)
+#define GPT_PAS_ATTR_GPI_MASK		U(0xF)
+#define GPT_PAS_ATTR_GPI(_attrs)	(((_attrs)			\
+					>> GPT_PAS_ATTR_GPI_SHIFT)	\
+					& GPT_PAS_ATTR_GPI_MASK)
+
+/* PAS attribute mapping type definitions */
+#define GPT_PAS_ATTR_MAP_TYPE_BLOCK	U(0x0)
+#define GPT_PAS_ATTR_MAP_TYPE_GRANULE	U(0x1)
+#define GPT_PAS_ATTR_MAP_TYPE_SHIFT	U(4)
+#define GPT_PAS_ATTR_MAP_TYPE_MASK	U(0x1)
+#define GPT_PAS_ATTR_MAP_TYPE(_attrs)	(((_attrs)			\
+					>> GPT_PAS_ATTR_MAP_TYPE_SHIFT)	\
+					& GPT_PAS_ATTR_MAP_TYPE_MASK)
+
+/*
+ * Macro to initialize the attributes field in the pas_region_t structure.
+ * [31:5] Reserved
+ * [4]    Mapping type (GPT_PAS_ATTR_MAP_TYPE_x definitions)
+ * [3:0]  PAS GPI type (GPT_GPI_x definitions)
+ */
+#define GPT_PAS_ATTR(_type, _gpi)					\
+	((((_type) & GPT_PAS_ATTR_MAP_TYPE_MASK)			\
+	  << GPT_PAS_ATTR_MAP_TYPE_SHIFT) |				\
+	(((_gpi) & GPT_PAS_ATTR_GPI_MASK)				\
+	 << GPT_PAS_ATTR_GPI_SHIFT))
+
+/*
+ * Macro to create a GPT entry for this PAS range as a block descriptor. If this
+ * region does not fit the requirements for a block descriptor then GPT
+ * initialization will fail.
+ */
+#define GPT_MAP_REGION_BLOCK(_pa, _sz, _gpi)				\
+	{								\
+		.base_pa = (_pa),					\
+		.size = (_sz),						\
+		.attrs = GPT_PAS_ATTR(GPT_PAS_ATTR_MAP_TYPE_BLOCK, (_gpi)), \
+	}
+
+/*
+ * Macro to create a GPT entry for this PAS range as a table descriptor. If this
+ * region does not fit the requirements for a table descriptor then GPT
+ * initialization will fail.
+ */
+#define GPT_MAP_REGION_GRANULE(_pa, _sz, _gpi)				\
+	{								\
+		.base_pa = (_pa),					\
+		.size = (_sz),						\
+		.attrs = GPT_PAS_ATTR(GPT_PAS_ATTR_MAP_TYPE_GRANULE, (_gpi)), \
+	}
+
+/******************************************************************************/
+/* GPT register field definitions                                             */
+/******************************************************************************/
+
+/*
+ * Least significant address bits protected by each entry in level 0 GPT. This
+ * field is read-only.
+ */
+#define GPCCR_L0GPTSZ_SHIFT	U(20)
+#define GPCCR_L0GPTSZ_MASK	U(0xF)
+
+typedef enum {
+	GPCCR_L0GPTSZ_30BITS	= U(0x0),
+	GPCCR_L0GPTSZ_34BITS	= U(0x4),
+	GPCCR_L0GPTSZ_36BITS	= U(0x6),
+	GPCCR_L0GPTSZ_39BITS	= U(0x9)
+} gpccr_l0gptsz_e;
+
+/* Granule protection check priority bit definitions */
+#define GPCCR_GPCP_SHIFT	U(17)
+#define GPCCR_GPCP_BIT		(ULL(1) << GPCCR_EL3_GPCP_SHIFT)
+
+/* Granule protection check bit definitions */
+#define GPCCR_GPC_SHIFT		U(16)
+#define GPCCR_GPC_BIT		(ULL(1) << GPCCR_GPC_SHIFT)
+
+/* Physical granule size bit definitions */
+#define GPCCR_PGS_SHIFT		U(14)
+#define GPCCR_PGS_MASK		U(0x3)
+#define SET_GPCCR_PGS(x)	(((x) & GPCCR_PGS_MASK) << GPCCR_PGS_SHIFT)
+
+typedef enum {
+	GPCCR_PGS_4K		= U(0x0),
+	GPCCR_PGS_64K		= U(0x1),
+	GPCCR_PGS_16K		= U(0x2)
+} gpccr_pgs_e;
+
+/* GPT fetch shareability attribute bit definitions */
+#define GPCCR_SH_SHIFT		U(12)
+#define GPCCR_SH_MASK		U(0x3)
+#define SET_GPCCR_SH(x)		(((x) & GPCCR_SH_MASK) << GPCCR_SH_SHIFT)
+
+typedef enum {
+	GPCCR_SH_NS		= U(0x0),
+	GPCCR_SH_OS		= U(0x2),
+	GPCCR_SH_IS		= U(0x3)
+} gpccr_sh_e;
+
+/* GPT fetch outer cacheability attribute bit definitions */
+#define GPCCR_ORGN_SHIFT	U(10)
+#define GPCCR_ORGN_MASK		U(0x3)
+#define SET_GPCCR_ORGN(x)	(((x) & GPCCR_ORGN_MASK) << GPCCR_ORGN_SHIFT)
+
+typedef enum {
+	GPCCR_ORGN_NC		= U(0x0),
+	GPCCR_ORGN_WB_RA_WA	= U(0x1),
+	GPCCR_ORGN_WT_RA_NWA	= U(0x2),
+	GPCCR_ORGN_WB_RA_NWA	= U(0x3)
+} gpccr_orgn_e;
+
+/* GPT fetch inner cacheability attribute bit definitions */
+#define GPCCR_IRGN_SHIFT	U(8)
+#define GPCCR_IRGN_MASK		U(0x3)
+#define SET_GPCCR_IRGN(x)	(((x) & GPCCR_IRGN_MASK) << GPCCR_IRGN_SHIFT)
+
+typedef enum {
+	GPCCR_IRGN_NC		= U(0x0),
+	GPCCR_IRGN_WB_RA_WA	= U(0x1),
+	GPCCR_IRGN_WT_RA_NWA	= U(0x2),
+	GPCCR_IRGN_WB_RA_NWA	= U(0x3)
+} gpccr_irgn_e;
+
+/* Protected physical address size bit definitions */
+#define GPCCR_PPS_SHIFT		U(0)
+#define GPCCR_PPS_MASK		U(0x7)
+#define SET_GPCCR_PPS(x)	(((x) & GPCCR_PPS_MASK) << GPCCR_PPS_SHIFT)
+
+typedef enum {
+	GPCCR_PPS_4GB		= U(0x0),
+	GPCCR_PPS_64GB		= U(0x1),
+	GPCCR_PPS_1TB		= U(0x2),
+	GPCCR_PPS_4TB		= U(0x3),
+	GPCCR_PPS_16TB		= U(0x4),
+	GPCCR_PPS_256TB		= U(0x5),
+	GPCCR_PPS_4PB		= U(0x6)
+} gpccr_pps_e;
+
+/* Base Address for the GPT bit definitions */
+#define GPTBR_BADDR_SHIFT	U(0)
+#define GPTBR_BADDR_VAL_SHIFT	U(12)
+#define GPTBR_BADDR_MASK	ULL(0xffffffffff)
+
+/******************************************************************************/
+/* GPT public APIs                                                            */
+/******************************************************************************/
+
+/*
+ * Public API that initializes the entire protected space to GPT_GPI_ANY using
+ * the L0 tables (block descriptors).  Ideally, this function is invoked prior
+ * to DDR discovery and initialization.  The MMU must be initialized before
+ * calling this function.
+ *
+ * Parameters
+ *   pps		PPS value to use for table generation
+ *   l0_mem_base	Base address of L0 tables in memory.
+ *   l0_mem_size	Total size of memory available for L0 tables.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_init_l0_tables(gpccr_pps_e pps,
+		       uintptr_t l0_mem_base,
+		       size_t l0_mem_size);
+
+/*
+ * Public API that carves out PAS regions from the L0 tables and builds any L1
+ * tables that are needed.  This function ideally is run after DDR discovery and
+ * initialization.  The L0 tables must have already been initialized to GPI_ANY
+ * when this function is called.
+ *
+ * Parameters
+ *   pgs		PGS value to use for table generation.
+ *   l1_mem_base	Base address of memory used for L1 tables.
+ *   l1_mem_size	Total size of memory available for L1 tables.
+ *   *pas_regions	Pointer to PAS regions structure array.
+ *   pas_count		Total number of PAS regions.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_init_pas_l1_tables(gpccr_pgs_e pgs,
+			   uintptr_t l1_mem_base,
+			   size_t l1_mem_size,
+			   pas_region_t *pas_regions,
+			   unsigned int pas_count);
+
+/*
+ * Public API to initialize the runtime gpt_config structure based on the values
+ * present in the GPTBR_EL3 and GPCCR_EL3 registers. GPT initialization
+ * typically happens in a bootloader stage prior to setting up the EL3 runtime
+ * environment for the granule transition service so this function detects the
+ * initialization from a previous stage. Granule protection checks must be
+ * enabled already or this function will return an error.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_runtime_init(void);
+
+/*
+ * Public API to enable granule protection checks once the tables have all been
+ * initialized.  This function is called at first initialization and then again
+ * later during warm boots of CPU cores.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_enable(void);
+
+/*
+ * Public API to disable granule protection checks.
+ */
+void gpt_disable(void);
+
+/*
+ * This function is the core of the granule transition service. When a granule
+ * transition request occurs it is routed to this function where the request is
+ * validated then fulfilled if possible.
+ *
+ * TODO: implement support for transitioning multiple granules at once.
+ *
+ * Parameters
+ *   base: Base address of the region to transition, must be aligned to granule
+ *         size.
+ *   size: Size of region to transition, must be aligned to granule size.
+ *   src_sec_state: Security state of the caller.
+ *   target_pas: Target PAS of the specified memory region.
+ *
+ * Return
+ *    Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_transition_pas(uint64_t base,
+		       size_t size,
+		       unsigned int src_sec_state,
+		       unsigned int target_pas);
+
+#endif /* GPT_RME_H */
diff --git a/include/lib/libc/aarch32/inttypes_.h b/include/lib/libc/aarch32/inttypes_.h
new file mode 100644
index 0000000..11d2d35
--- /dev/null
+++ b/include/lib/libc/aarch32/inttypes_.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright 2020 Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/*
+ * Portions copyright (c) 2020, ARM Limited and Contributors.
+ * All rights reserved.
+ */
+
+#ifndef INTTYPES__H
+#define INTTYPES__H
+
+#define PRId64		"lld"	/* int64_t */
+#define PRIi64		"lli"	/* int64_t */
+#define PRIo64		"llo"	/* int64_t */
+#define PRIu64		"llu"	/* uint64_t */
+#define PRIx64		"llx"	/* uint64_t */
+#define PRIX64		"llX"	/* uint64_t */
+
+#endif /* INTTYPES__H */
diff --git a/include/lib/libc/aarch32/stdint_.h b/include/lib/libc/aarch32/stdint_.h
new file mode 100644
index 0000000..dafe142
--- /dev/null
+++ b/include/lib/libc/aarch32/stdint_.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2020 Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/*
+ * Portions copyright (c) 2020, ARM Limited and Contributors.
+ * All rights reserved.
+ */
+
+#ifndef STDINT__H
+#define STDINT__H
+
+#define INT64_MAX  LLONG_MAX
+#define INT64_MIN  LLONG_MIN
+#define UINT64_MAX ULLONG_MAX
+
+#define INT64_C(x) x ## LL
+#define UINT64_C(x) x ## ULL
+
+typedef long long int64_t;
+typedef unsigned long long uint64_t;
+typedef long long int64_least_t;
+typedef unsigned long long uint64_least_t;
+typedef long long int64_fast_t;
+typedef unsigned long long uint64_fast_t;
+
+#endif
diff --git a/include/lib/libc/aarch64/inttypes_.h b/include/lib/libc/aarch64/inttypes_.h
new file mode 100644
index 0000000..197d627
--- /dev/null
+++ b/include/lib/libc/aarch64/inttypes_.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright 2020 Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/*
+ * Portions copyright (c) 2020, ARM Limited and Contributors.
+ * All rights reserved.
+ */
+
+#ifndef INTTYPES__H
+#define INTTYPES__H
+
+#define PRId64		"ld"	/* int64_t */
+#define PRIi64		"li"	/* int64_t */
+#define PRIo64		"lo"	/* int64_t */
+#define PRIu64		"lu"	/* uint64_t */
+#define PRIx64		"lx"	/* uint64_t */
+#define PRIX64		"lX"	/* uint64_t */
+
+#endif /* INTTYPES__H */
diff --git a/include/lib/libc/aarch64/stdint_.h b/include/lib/libc/aarch64/stdint_.h
new file mode 100644
index 0000000..56e9f1b
--- /dev/null
+++ b/include/lib/libc/aarch64/stdint_.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright 2020 Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/*
+ * Portions copyright (c) 2020, ARM Limited and Contributors.
+ * All rights reserved.
+ */
+
+#ifndef STDINT__H
+#define STDINT__H
+
+#define INT64_MAX  LONG_MAX
+#define INT64_MIN  LONG_MIN
+#define UINT64_MAX ULONG_MAX
+
+#define INT64_C(x) x ## L
+#define UINT64_C(x) x ## UL
+
+typedef long int64_t;
+typedef unsigned long uint64_t;
+typedef long int64_least_t;
+typedef unsigned long uint64_least_t;
+typedef long int64_fast_t;
+typedef unsigned long uint64_fast_t;
+
+typedef __int128 int128_t;
+typedef unsigned __int128 uint128_t;
+
+#endif
diff --git a/include/lib/libc/arm_acle.h b/include/lib/libc/arm_acle.h
new file mode 100644
index 0000000..eb08552
--- /dev/null
+++ b/include/lib/libc/arm_acle.h
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2021 ARM Limited
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * The definitions below are a subset of what we would normally get by using
+ * the compiler's version of arm_acle.h. We can't use that directly because
+ * we specify -nostdinc in the Makefiles.
+ *
+ * We just define the functions we need so far.
+ */
+
+#ifndef ARM_ACLE_H
+#define ARM_ACLE_H
+
+#if !defined(__aarch64__) || defined(__clang__)
+#	define __crc32b __builtin_arm_crc32b
+#	define __crc32w __builtin_arm_crc32w
+#else
+#	define __crc32b __builtin_aarch64_crc32b
+#	define __crc32w __builtin_aarch64_crc32w
+#endif
+
+#endif	/* ARM_ACLE_H */
diff --git a/include/lib/libc/inttypes.h b/include/lib/libc/inttypes.h
new file mode 100644
index 0000000..0f9e8c6
--- /dev/null
+++ b/include/lib/libc/inttypes.h
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2020 Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/*
+ * Portions copyright (c) 2020, ARM Limited and Contributors.
+ * All rights reserved.
+ */
+
+#ifndef INTTYPES_H
+#define INTTYPES_H
+
+#include <inttypes_.h>
+#include <stdint.h>
+
+#define PRId8		"d"	/* int8_t */
+#define PRId16		"d"	/* int16_t */
+#define PRId32		"d"	/* int32_t */
+#define PRIdPTR		"d"	/* intptr_t */
+
+#define PRIi8		"i"	/* int8_t */
+#define PRIi16		"i"	/* int16_t */
+#define PRIi32		"i"	/* int32_t */
+#define PRIiPTR		"i"	/* intptr_t */
+
+#define PRIo8		"o"	/* int8_t */
+#define PRIo16		"o"	/* int16_t */
+#define PRIo32		"o"	/* int32_t */
+#define PRIoPTR		"o"	/* intptr_t */
+
+#define PRIu8		"u"	/* uint8_t */
+#define PRIu16		"u"	/* uint16_t */
+#define PRIu32		"u"	/* uint32_t */
+#define PRIuPTR		"u"	/* uintptr_t */
+
+#define PRIx8		"x"	/* uint8_t */
+#define PRIx16		"x"	/* uint16_t */
+#define PRIx32		"x"	/* uint32_t */
+#define PRIxPTR		"x"	/* uintptr_t */
+
+#define PRIX8		"X"	/* uint8_t */
+#define PRIX16		"X"	/* uint16_t */
+#define PRIX32		"X"	/* uint32_t */
+#define PRIXPTR		"X"	/* uintptr_t */
+
+#endif
diff --git a/include/lib/libc/stdint.h b/include/lib/libc/stdint.h
index 818870e..e96a25c 100644
--- a/include/lib/libc/stdint.h
+++ b/include/lib/libc/stdint.h
@@ -12,6 +12,7 @@
 #define STDINT_H
 
 #include <limits.h>
+#include <stdint_.h>
 
 #define INT8_MAX  CHAR_MAX
 #define INT8_MIN  CHAR_MIN
@@ -25,10 +26,6 @@
 #define INT32_MIN  INT_MIN
 #define UINT32_MAX UINT_MAX
 
-#define INT64_MAX  LLONG_MAX
-#define INT64_MIN  LLONG_MIN
-#define UINT64_MAX ULLONG_MAX
-
 #define INT_LEAST8_MIN  INT8_MIN
 #define INT_LEAST8_MAX  INT8_MAX
 #define UINT_LEAST8_MAX UINT8_MAX
@@ -77,12 +74,10 @@
 #define INT8_C(x)  x
 #define INT16_C(x) x
 #define INT32_C(x) x
-#define INT64_C(x) x ## LL
 
 #define UINT8_C(x)  x
 #define UINT16_C(x) x
 #define UINT32_C(x) x ## U
-#define UINT64_C(x) x ## ULL
 
 #define INTMAX_C(x)  x ## LL
 #define UINTMAX_C(x) x ## ULL
@@ -90,32 +85,26 @@
 typedef signed char int8_t;
 typedef short int16_t;
 typedef int int32_t;
-typedef long long int64_t;
 
 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_least_t;
 typedef short int16_least_t;
 typedef int int32_least_t;
-typedef long long int64_least_t;
 
 typedef unsigned char uint8_least_t;
 typedef unsigned short uint16_least_t;
 typedef unsigned int uint32_least_t;
-typedef unsigned long long uint64_least_t;
 
 typedef int int8_fast_t;
 typedef int int16_fast_t;
 typedef int int32_fast_t;
-typedef long long int64_fast_t;
 
 typedef unsigned int uint8_fast_t;
 typedef unsigned int uint16_fast_t;
 typedef unsigned int uint32_fast_t;
-typedef unsigned long long uint64_fast_t;
 
 typedef long intptr_t;
 typedef unsigned long uintptr_t;
@@ -130,9 +119,4 @@
 typedef long register_t;
 typedef unsigned long u_register_t;
 
-#ifdef __aarch64__
-typedef __int128 int128_t;
-typedef unsigned __int128 uint128_t;
-#endif /* __aarch64__ */
-
 #endif /* STDINT_H */
diff --git a/include/lib/libc/stdlib.h b/include/lib/libc/stdlib.h
index 24e7bae..4641e56 100644
--- a/include/lib/libc/stdlib.h
+++ b/include/lib/libc/stdlib.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012-2017 Roberto E. Vargas Caballero
+ * Copyright (c) 2012-2021 Roberto E. Vargas Caballero
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -18,8 +18,15 @@
 
 #define _ATEXIT_MAX 1
 
+#define isspace(x)    (((x) == ' ') || ((x) == '\r') || ((x) == '\n') || \
+			((x) == '\t') || ((x) == '\b'))
+
 extern void abort(void);
 extern int atexit(void (*func)(void));
 extern void exit(int status);
 
+long strtol(const char *nptr, char **endptr, int base);
+unsigned long strtoul(const char *nptr, char **endptr, int base);
+long long strtoll(const char *nptr, char **endptr, int base);
+unsigned long long strtoull(const char *nptr, char **endptr, int base);
 #endif /* STDLIB_H */
diff --git a/include/lib/mpmm/mpmm.h b/include/lib/mpmm/mpmm.h
new file mode 100644
index 0000000..955c530
--- /dev/null
+++ b/include/lib/mpmm/mpmm.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MPMM_H
+#define MPMM_H
+
+#include <stdbool.h>
+
+#include <platform_def.h>
+
+/*
+ * Enable the Maximum Power Mitigation Mechanism.
+ *
+ * This function will enable MPMM for the current core. The AMU counters
+ * representing the MPMM gears must have been configured and enabled prior to
+ * calling this function.
+ */
+void mpmm_enable(void);
+
+/*
+ * MPMM core data.
+ *
+ * This structure represents per-core data retrieved from the hardware
+ * configuration device tree.
+ */
+struct mpmm_core {
+	/*
+	 * Whether MPMM is supported.
+	 *
+	 * Cores with support for MPMM offer one or more auxiliary AMU counters
+	 * representing MPMM gears.
+	 */
+	bool supported;
+};
+
+/*
+ * MPMM topology.
+ *
+ * This topology structure describes the system-wide representation of the
+ * information retrieved from the hardware configuration device tree.
+ */
+struct mpmm_topology {
+	struct mpmm_core cores[PLATFORM_CORE_COUNT]; /* Per-core data */
+};
+
+#if !ENABLE_MPMM_FCONF
+/*
+ * Retrieve the platform's MPMM topology. A `NULL` return value is treated as a
+ * non-fatal error, in which case MPMM will not be enabled for any core.
+ */
+const struct mpmm_topology *plat_mpmm_topology(void);
+#endif /* ENABLE_MPMM_FCONF */
+
+#endif /* MPMM_H */
diff --git a/include/lib/optee_utils.h b/include/lib/optee_utils.h
index 6067caf..06378eb 100644
--- a/include/lib/optee_utils.h
+++ b/include/lib/optee_utils.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,8 +7,12 @@
 #ifndef OPTEE_UTILS_H
 #define OPTEE_UTILS_H
 
+#include <stdbool.h>
+
 #include <common/bl_common.h>
 
+bool optee_header_is_valid(uintptr_t header_base);
+
 int parse_optee_header(entry_point_info_t *header_ep,
 	image_info_t *pager_image_info,
 	image_info_t *paged_image_info);
diff --git a/include/lib/smccc.h b/include/lib/smccc.h
index 470317d..1a39f24 100644
--- a/include/lib/smccc.h
+++ b/include/lib/smccc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -51,6 +51,23 @@
 					 FUNCID_OEN_MASK)
 
 /*******************************************************************************
+ * SMCCC_ARCH_SOC_ID SoC version & revision bit definition
+ ******************************************************************************/
+#define SOC_ID_JEP_106_BANK_IDX_MASK	GENMASK_32(30, 24)
+#define SOC_ID_JEP_106_BANK_IDX_SHIFT	U(24)
+#define SOC_ID_JEP_106_ID_CODE_MASK	GENMASK_32(23, 16)
+#define SOC_ID_JEP_106_ID_CODE_SHIFT	U(16)
+#define SOC_ID_IMPL_DEF_MASK		GENMASK_32(15, 0)
+#define SOC_ID_IMPL_DEF_SHIFT		U(0)
+#define SOC_ID_SET_JEP_106(bkid, mfid)	((((bkid) << SOC_ID_JEP_106_BANK_IDX_SHIFT) & \
+					  SOC_ID_JEP_106_BANK_IDX_MASK) | \
+					 (((mfid) << SOC_ID_JEP_106_ID_CODE_SHIFT) & \
+					  SOC_ID_JEP_106_ID_CODE_MASK))
+
+#define SOC_ID_REV_MASK			GENMASK_32(30, 0)
+#define SOC_ID_REV_SHIFT		U(0)
+
+/*******************************************************************************
  * Owning entity number definitions inside the function id as per the SMC
  * calling convention
  ******************************************************************************/
@@ -91,9 +108,24 @@
 #define SMC_ARCH_CALL_NOT_REQUIRED	-2
 #define SMC_ARCH_CALL_INVAL_PARAM	-3
 
-/* Various flags passed to SMC handlers */
+/*
+ * Various flags passed to SMC handlers
+ *
+ * Bit 5 and bit 0 of the flag are used to
+ * determine the source security state as
+ * follows:
+ * ---------------------------------
+ *  Bit 5 | Bit 0 | Security state
+ * ---------------------------------
+ *   0        0      SMC_FROM_SECURE
+ *   0        1      SMC_FROM_NON_SECURE
+ *   1        1      SMC_FROM_REALM
+ */
+
 #define SMC_FROM_SECURE		(U(0) << 0)
 #define SMC_FROM_NON_SECURE	(U(1) << 0)
+#define SMC_FROM_REALM		U(0x21)
+#define SMC_FROM_MASK		U(0x21)
 
 #ifndef __ASSEMBLER__
 
@@ -101,8 +133,18 @@
 
 #include <lib/cassert.h>
 
+#if ENABLE_RME
+#define is_caller_non_secure(_f)	(((_f) & SMC_FROM_MASK) \
+					  == SMC_FROM_NON_SECURE)
+#define is_caller_secure(_f)		(((_f) & SMC_FROM_MASK) \
+					  == SMC_FROM_SECURE)
+#define is_caller_realm(_f)		(((_f) & SMC_FROM_MASK) \
+					  == SMC_FROM_REALM)
+#define caller_sec_state(_f)		((_f) & SMC_FROM_MASK)
+#else /* ENABLE_RME */
 #define is_caller_non_secure(_f)	(((_f) & SMC_FROM_NON_SECURE) != U(0))
 #define is_caller_secure(_f)		(!is_caller_non_secure(_f))
+#endif /* ENABLE_RME */
 
 /* The macro below is used to identify a Standard Service SMC call */
 #define is_std_svc_call(_fid)		(GET_SMC_OEN(_fid) == OEN_STD_START)
diff --git a/include/lib/utils_def.h b/include/lib/utils_def.h
index 2d0e9c0..7a7012d 100644
--- a/include/lib/utils_def.h
+++ b/include/lib/utils_def.h
@@ -163,4 +163,9 @@
  */
 #define MHZ_TICKS_PER_SEC	U(1000000)
 
+/*
+ * Ticks elapsed in one second with a signal of 1 KHz
+ */
+#define KHZ_TICKS_PER_SEC U(1000)
+
 #endif /* UTILS_DEF_H */
diff --git a/include/lib/xlat_mpu/xlat_mpu.h b/include/lib/xlat_mpu/xlat_mpu.h
new file mode 100644
index 0000000..252b92c
--- /dev/null
+++ b/include/lib/xlat_mpu/xlat_mpu.h
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef XLAT_MPU_H
+#define XLAT_MPU_H
+
+#ifndef __ASSEMBLER__
+
+#include <lib/cassert.h>
+
+#define XLAT_TABLES_LIB_V2	1
+
+void enable_mpu_el2(unsigned int flags);
+void enable_mpu_direct_el2(unsigned int flags);
+
+/*
+ * Function to wipe clean and disable all MPU regions.  This function expects
+ * that the MPU has already been turned off, and caching concerns addressed,
+ * but it nevertheless also explicitly turns off the MPU.
+ */
+void clear_all_mpu_regions(void);
+
+#endif /* __ASSEMBLER__ */
+#endif /* XLAT_MPU_H */
diff --git a/include/lib/xlat_tables/xlat_tables.h b/include/lib/xlat_tables/xlat_tables.h
index 082bb5e..a156969 100644
--- a/include/lib/xlat_tables/xlat_tables.h
+++ b/include/lib/xlat_tables/xlat_tables.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -72,6 +72,13 @@
 #define MT_CODE			(MT_MEMORY | MT_RO | MT_EXECUTE)
 #define MT_RO_DATA		(MT_MEMORY | MT_RO | MT_EXECUTE_NEVER)
 
+/* Memory type for EL3 regions */
+#if ENABLE_RME
+#error FEAT_RME requires version 2 of the Translation Tables Library
+#else
+#define EL3_PAS			MT_SECURE
+#endif
+
 /*
  * Structure for specifying a single region of memory.
  */
diff --git a/include/lib/xlat_tables/xlat_tables_defs.h b/include/lib/xlat_tables/xlat_tables_defs.h
index 579d8d8..2d0949b 100644
--- a/include/lib/xlat_tables/xlat_tables_defs.h
+++ b/include/lib/xlat_tables/xlat_tables_defs.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -142,6 +142,7 @@
 #define AP_NO_ACCESS_UNPRIVILEGED	(AP1_NO_ACCESS_UNPRIVILEGED << 4)
 #define AP_ONE_VA_RANGE_RES1		(AP1_RES1 << 4)
 #define NS				(U(0x1) << 3)
+#define EL3_S1_NSE			(U(0x1) << 9)
 #define ATTR_NON_CACHEABLE_INDEX	ULL(0x2)
 #define ATTR_DEVICE_INDEX		ULL(0x1)
 #define ATTR_IWBWA_OWBWA_NTR_INDEX	ULL(0x0)
diff --git a/include/lib/xlat_tables/xlat_tables_v2.h b/include/lib/xlat_tables/xlat_tables_v2.h
index 359b983..69ad027 100644
--- a/include/lib/xlat_tables/xlat_tables_v2.h
+++ b/include/lib/xlat_tables/xlat_tables_v2.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -60,17 +60,22 @@
 #define MT_TYPE(_attr)		((_attr) & MT_TYPE_MASK)
 /* Access permissions (RO/RW) */
 #define MT_PERM_SHIFT		U(3)
-/* Security state (SECURE/NS) */
-#define MT_SEC_SHIFT		U(4)
+
+/* Physical address space (SECURE/NS/Root/Realm) */
+#define	MT_PAS_SHIFT		U(4)
+#define MT_PAS_MASK		(U(3) << MT_PAS_SHIFT)
+#define MT_PAS(_attr)		((_attr) & MT_PAS_MASK)
+
 /* Access permissions for instruction execution (EXECUTE/EXECUTE_NEVER) */
-#define MT_EXECUTE_SHIFT	U(5)
+#define MT_EXECUTE_SHIFT	U(6)
 /* In the EL1&0 translation regime, User (EL0) or Privileged (EL1). */
-#define MT_USER_SHIFT		U(6)
+#define MT_USER_SHIFT		U(7)
 
 /* Shareability attribute for the memory region */
-#define MT_SHAREABILITY_SHIFT	U(7)
+#define MT_SHAREABILITY_SHIFT	U(8)
 #define MT_SHAREABILITY_MASK	(U(3) << MT_SHAREABILITY_SHIFT)
 #define MT_SHAREABILITY(_attr)	((_attr) & MT_SHAREABILITY_MASK)
+
 /* All other bits are reserved */
 
 /*
@@ -91,8 +96,10 @@
 #define MT_RO			(U(0) << MT_PERM_SHIFT)
 #define MT_RW			(U(1) << MT_PERM_SHIFT)
 
-#define MT_SECURE		(U(0) << MT_SEC_SHIFT)
-#define MT_NS			(U(1) << MT_SEC_SHIFT)
+#define MT_SECURE		(U(0) << MT_PAS_SHIFT)
+#define MT_NS			(U(1) << MT_PAS_SHIFT)
+#define MT_ROOT			(U(2) << MT_PAS_SHIFT)
+#define MT_REALM		(U(3) << MT_PAS_SHIFT)
 
 /*
  * Access permissions for instruction execution are only relevant for normal
@@ -149,6 +156,13 @@
 #define EL3_REGIME		3
 #define EL_REGIME_INVALID	-1
 
+/* Memory type for EL3 regions. With RME, EL3 is in ROOT PAS */
+#if ENABLE_RME
+#define EL3_PAS			MT_ROOT
+#else
+#define EL3_PAS			MT_SECURE
+#endif /* ENABLE_RME */
+
 /*
  * Declare the translation context type.
  * Its definition is private.
diff --git a/include/plat/arm/board/common/board_css_def.h b/include/plat/arm/board/common/board_css_def.h
index b79e0d5..1963bf0 100644
--- a/include/plat/arm/board/common/board_css_def.h
+++ b/include/plat/arm/board/common/board_css_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -44,8 +44,18 @@
 #define MAX_IO_HANDLES			4
 
 /* Reserve the last block of flash for PSCI MEM PROTECT flag */
-#define PLAT_ARM_FIP_BASE		V2M_FLASH0_BASE
-#define PLAT_ARM_FIP_MAX_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+#define PLAT_ARM_FLASH_IMAGE_BASE	V2M_FLASH0_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+#if ARM_GPT_SUPPORT
+/*
+ * Offset of the FIP in the GPT image. BL1 component uses this option
+ * as it does not load the partition table to get the FIP base
+ * address. At sector 34 by default (i.e. after reserved sectors 0-33)
+ * Offset = 34 * 512(sector size) = 17408 i.e. 0x4400
+ */
+#define PLAT_ARM_FIP_OFFSET_IN_GPT		0x4400
+#endif /* ARM_GPT_SUPPORT */
 
 #define PLAT_ARM_NVM_BASE		V2M_FLASH0_BASE
 #define PLAT_ARM_NVM_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
diff --git a/include/plat/arm/board/common/v2m_def.h b/include/plat/arm/board/common/v2m_def.h
index 6a6979c..cb11dac 100644
--- a/include/plat/arm/board/common/v2m_def.h
+++ b/include/plat/arm/board/common/v2m_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -8,6 +8,13 @@
 
 #include <lib/utils_def.h>
 
+/* Base address of all V2M */
+#ifdef PLAT_V2M_OFFSET
+#define V2M_OFFSET			PLAT_V2M_OFFSET
+#else
+#define V2M_OFFSET			UL(0)
+#endif
+
 /* V2M motherboard system registers & offsets */
 #define V2M_SYSREGS_BASE		UL(0x1c010000)
 #define V2M_SYS_ID			UL(0x0)
@@ -69,18 +76,18 @@
 
 
 /* NOR Flash */
-#define V2M_FLASH0_BASE			UL(0x08000000)
+#define V2M_FLASH0_BASE			(V2M_OFFSET + UL(0x08000000))
 #define V2M_FLASH0_SIZE			UL(0x04000000)
-#define V2M_FLASH_BLOCK_SIZE		UL(0x00040000)	/* 256 KB */
+#define V2M_FLASH_BLOCK_SIZE		UL(0x00040000) /* 256 KB */
 
-#define V2M_IOFPGA_BASE			UL(0x1c000000)
+#define V2M_IOFPGA_BASE			(V2M_OFFSET + UL(0x1c000000))
 #define V2M_IOFPGA_SIZE			UL(0x03000000)
 
 /* PL011 UART related constants */
-#define V2M_IOFPGA_UART0_BASE		UL(0x1c090000)
-#define V2M_IOFPGA_UART1_BASE		UL(0x1c0a0000)
-#define V2M_IOFPGA_UART2_BASE		UL(0x1c0b0000)
-#define V2M_IOFPGA_UART3_BASE		UL(0x1c0c0000)
+#define V2M_IOFPGA_UART0_BASE		(V2M_OFFSET + UL(0x1c090000))
+#define V2M_IOFPGA_UART1_BASE		(V2M_OFFSET + UL(0x1c0a0000))
+#define V2M_IOFPGA_UART2_BASE		(V2M_OFFSET + UL(0x1c0b0000))
+#define V2M_IOFPGA_UART3_BASE		(V2M_OFFSET + UL(0x1c0c0000))
 
 #define V2M_IOFPGA_UART0_CLK_IN_HZ	24000000
 #define V2M_IOFPGA_UART1_CLK_IN_HZ	24000000
@@ -88,11 +95,11 @@
 #define V2M_IOFPGA_UART3_CLK_IN_HZ	24000000
 
 /* SP804 timer related constants */
-#define V2M_SP804_TIMER0_BASE		UL(0x1C110000)
-#define V2M_SP804_TIMER1_BASE		UL(0x1C120000)
+#define V2M_SP804_TIMER0_BASE		(V2M_OFFSET + UL(0x1C110000))
+#define V2M_SP804_TIMER1_BASE		(V2M_OFFSET + UL(0x1C120000))
 
 /* SP810 controller */
-#define V2M_SP810_BASE			UL(0x1c020000)
+#define V2M_SP810_BASE			(V2M_OFFSET + UL(0x1c020000))
 #define V2M_SP810_CTRL_TIM0_SEL		BIT_32(15)
 #define V2M_SP810_CTRL_TIM1_SEL		BIT_32(17)
 #define V2M_SP810_CTRL_TIM2_SEL		BIT_32(19)
diff --git a/include/plat/arm/board/fvp_r/fvp_r_bl1.h b/include/plat/arm/board/fvp_r/fvp_r_bl1.h
new file mode 100644
index 0000000..0b41e67
--- /dev/null
+++ b/include/plat/arm/board/fvp_r/fvp_r_bl1.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FVP_R_BL1_H
+#define FVP_R_BL1_H
+
+void bl1_load_bl33(void);
+void bl1_transfer_bl33(void);
+
+#endif /* FVP_R_BL1_H */
diff --git a/include/plat/arm/common/arm_def.h b/include/plat/arm/common/arm_def.h
index 00746c6..1993cb4 100644
--- a/include/plat/arm/common/arm_def.h
+++ b/include/plat/arm/common/arm_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -58,8 +58,12 @@
 #define ARM_TRUSTED_DRAM_ID		1
 #define ARM_DRAM_ID			2
 
-/* The first 4KB of Trusted SRAM are used as shared memory */
+#ifdef PLAT_ARM_TRUSTED_SRAM_BASE
+#define ARM_TRUSTED_SRAM_BASE		PLAT_ARM_TRUSTED_SRAM_BASE
+#else
 #define ARM_TRUSTED_SRAM_BASE		UL(0x04000000)
+#endif /* PLAT_ARM_TRUSTED_SRAM_BASE */
+
 #define ARM_SHARED_RAM_BASE		ARM_TRUSTED_SRAM_BASE
 #define ARM_SHARED_RAM_SIZE		UL(0x00001000)	/* 4 KB */
 
@@ -70,38 +74,84 @@
 					 ARM_SHARED_RAM_SIZE)
 
 /*
- * The top 16MB of DRAM1 is configured as secure access only using the TZC
+ * The top 16MB (or 64MB if RME is enabled) of DRAM1 is configured as
+ * follows:
  *   - SCP TZC DRAM: If present, DRAM reserved for SCP use
+ *   - L1 GPT DRAM: Reserved for L1 GPT if RME is enabled
+ *   - REALM DRAM: Reserved for Realm world if RME is enabled
  *   - AP TZC DRAM: The remaining TZC secured DRAM reserved for AP use
+ *
+ *              RME enabled(64MB)                RME not enabled(16MB)
+ *              --------------------             -------------------
+ *              |                  |             |                 |
+ *              |  AP TZC (~28MB)  |             |  AP TZC (~14MB) |
+ *              --------------------             -------------------
+ *              |                  |             |                 |
+ *              |  REALM (32MB)    |             |  EL3 TZC (2MB)  |
+ *              --------------------             -------------------
+ *              |                  |             |                 |
+ *              |  EL3 TZC (3MB)   |             |    SCP TZC      |
+ *              --------------------  0xFFFF_FFFF-------------------
+ *              | L1 GPT + SCP TZC |
+ *              |       (~1MB)     |
+ *  0xFFFF_FFFF --------------------
  */
-#define ARM_TZC_DRAM1_SIZE		UL(0x01000000)
-
-#define ARM_SCP_TZC_DRAM1_BASE		(ARM_DRAM1_BASE +		\
-					 ARM_DRAM1_SIZE -		\
-					 ARM_SCP_TZC_DRAM1_SIZE)
-#define ARM_SCP_TZC_DRAM1_SIZE		PLAT_ARM_SCP_TZC_DRAM1_SIZE
-#define ARM_SCP_TZC_DRAM1_END		(ARM_SCP_TZC_DRAM1_BASE +	\
-					 ARM_SCP_TZC_DRAM1_SIZE - 1U)
-
+#if ENABLE_RME
+#define ARM_TZC_DRAM1_SIZE              UL(0x04000000) /* 64MB */
 /*
- * Define a 2MB region within the TZC secured DRAM for use by EL3 runtime
+ * Define a region within the TZC secured DRAM for use by EL3 runtime
  * firmware. This region is meant to be NOLOAD and will not be zero
  * initialized. Data sections with the attribute `arm_el3_tzc_dram` will be
- * placed here.
+ * placed here. 3MB region is reserved if RME is enabled, 2MB otherwise.
  */
-#define ARM_EL3_TZC_DRAM1_BASE		(ARM_SCP_TZC_DRAM1_BASE - ARM_EL3_TZC_DRAM1_SIZE)
-#define ARM_EL3_TZC_DRAM1_SIZE		UL(0x00200000) /* 2 MB */
+#define ARM_EL3_TZC_DRAM1_SIZE		UL(0x00300000) /* 3MB */
+#define ARM_L1_GPT_SIZE			UL(0x00100000) /* 1MB */
+#define ARM_REALM_SIZE			UL(0x02000000) /* 32MB */
+#else
+#define ARM_TZC_DRAM1_SIZE		UL(0x01000000) /* 16MB */
+#define ARM_EL3_TZC_DRAM1_SIZE		UL(0x00200000) /* 2MB */
+#define ARM_L1_GPT_SIZE			UL(0)
+#define ARM_REALM_SIZE			UL(0)
+#endif /* ENABLE_RME */
+
+#define ARM_SCP_TZC_DRAM1_BASE		(ARM_DRAM1_BASE +		\
+					ARM_DRAM1_SIZE -		\
+					(ARM_SCP_TZC_DRAM1_SIZE +	\
+					ARM_L1_GPT_SIZE))
+#define ARM_SCP_TZC_DRAM1_SIZE		PLAT_ARM_SCP_TZC_DRAM1_SIZE
+#define ARM_SCP_TZC_DRAM1_END		(ARM_SCP_TZC_DRAM1_BASE +	\
+					ARM_SCP_TZC_DRAM1_SIZE - 1U)
+#if ENABLE_RME
+#define ARM_L1_GPT_ADDR_BASE		(ARM_DRAM1_BASE +		\
+					ARM_DRAM1_SIZE -		\
+					ARM_L1_GPT_SIZE)
+#define ARM_L1_GPT_END			(ARM_L1_GPT_ADDR_BASE +		\
+					ARM_L1_GPT_SIZE - 1U)
+
+#define ARM_REALM_BASE			(ARM_DRAM1_BASE +		\
+					ARM_DRAM1_SIZE -		\
+					(ARM_SCP_TZC_DRAM1_SIZE +	\
+					ARM_EL3_TZC_DRAM1_SIZE +	\
+					ARM_REALM_SIZE +		\
+					ARM_L1_GPT_SIZE))
+#define ARM_REALM_END                   (ARM_REALM_BASE + ARM_REALM_SIZE - 1U)
+#endif /* ENABLE_RME */
+
+#define ARM_EL3_TZC_DRAM1_BASE		(ARM_SCP_TZC_DRAM1_BASE -	\
+					ARM_EL3_TZC_DRAM1_SIZE)
 #define ARM_EL3_TZC_DRAM1_END		(ARM_EL3_TZC_DRAM1_BASE +	\
 					ARM_EL3_TZC_DRAM1_SIZE - 1U)
 
 #define ARM_AP_TZC_DRAM1_BASE		(ARM_DRAM1_BASE +		\
-					 ARM_DRAM1_SIZE -		\
-					 ARM_TZC_DRAM1_SIZE)
+					ARM_DRAM1_SIZE -		\
+					ARM_TZC_DRAM1_SIZE)
 #define ARM_AP_TZC_DRAM1_SIZE		(ARM_TZC_DRAM1_SIZE -		\
-					 (ARM_SCP_TZC_DRAM1_SIZE +	\
-					 ARM_EL3_TZC_DRAM1_SIZE))
+					(ARM_SCP_TZC_DRAM1_SIZE +	\
+					ARM_EL3_TZC_DRAM1_SIZE +	\
+					ARM_REALM_SIZE +		\
+					ARM_L1_GPT_SIZE))
 #define ARM_AP_TZC_DRAM1_END		(ARM_AP_TZC_DRAM1_BASE +	\
-					 ARM_AP_TZC_DRAM1_SIZE - 1U)
+					ARM_AP_TZC_DRAM1_SIZE - 1U)
 
 /* Define the Access permissions for Secure peripherals to NS_DRAM */
 #if ARM_CRYPTOCELL_INTEG
@@ -149,8 +199,12 @@
 					 ARM_TZC_DRAM1_SIZE)
 #define ARM_NS_DRAM1_END		(ARM_NS_DRAM1_BASE +		\
 					 ARM_NS_DRAM1_SIZE - 1U)
-
+#ifdef PLAT_ARM_DRAM1_BASE
+#define ARM_DRAM1_BASE			PLAT_ARM_DRAM1_BASE
+#else
 #define ARM_DRAM1_BASE			ULL(0x80000000)
+#endif /* PLAT_ARM_DRAM1_BASE */
+
 #define ARM_DRAM1_SIZE			ULL(0x80000000)
 #define ARM_DRAM1_END			(ARM_DRAM1_BASE +		\
 					 ARM_DRAM1_SIZE - 1U)
@@ -198,45 +252,58 @@
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_6, GIC_HIGHEST_SEC_PRIORITY, (grp), \
 			GIC_INTR_CFG_EDGE)
 
-#define ARM_MAP_SHARED_RAM		MAP_REGION_FLAT(		\
-						ARM_SHARED_RAM_BASE,	\
-						ARM_SHARED_RAM_SIZE,	\
-						MT_DEVICE | MT_RW | MT_SECURE)
+#define ARM_MAP_SHARED_RAM	MAP_REGION_FLAT(			\
+					ARM_SHARED_RAM_BASE,		\
+					ARM_SHARED_RAM_SIZE,		\
+					MT_DEVICE | MT_RW | EL3_PAS)
 
-#define ARM_MAP_NS_DRAM1		MAP_REGION_FLAT(		\
-						ARM_NS_DRAM1_BASE,	\
-						ARM_NS_DRAM1_SIZE,	\
-						MT_MEMORY | MT_RW | MT_NS)
+#define ARM_MAP_NS_DRAM1	MAP_REGION_FLAT(			\
+					ARM_NS_DRAM1_BASE,		\
+					ARM_NS_DRAM1_SIZE,		\
+					MT_MEMORY | MT_RW | MT_NS)
 
-#define ARM_MAP_DRAM2			MAP_REGION_FLAT(		\
-						ARM_DRAM2_BASE,		\
-						ARM_DRAM2_SIZE,		\
-						MT_MEMORY | MT_RW | MT_NS)
+#define ARM_MAP_DRAM2		MAP_REGION_FLAT(			\
+					ARM_DRAM2_BASE,			\
+					ARM_DRAM2_SIZE,			\
+					MT_MEMORY | MT_RW | MT_NS)
 
-#define ARM_MAP_TSP_SEC_MEM		MAP_REGION_FLAT(		\
-						TSP_SEC_MEM_BASE,	\
-						TSP_SEC_MEM_SIZE,	\
-						MT_MEMORY | MT_RW | MT_SECURE)
+#define ARM_MAP_TSP_SEC_MEM	MAP_REGION_FLAT(			\
+					TSP_SEC_MEM_BASE,		\
+					TSP_SEC_MEM_SIZE,		\
+					MT_MEMORY | MT_RW | MT_SECURE)
 
 #if ARM_BL31_IN_DRAM
-#define ARM_MAP_BL31_SEC_DRAM		MAP_REGION_FLAT(		\
-						BL31_BASE,		\
-						PLAT_ARM_MAX_BL31_SIZE,	\
-						MT_MEMORY | MT_RW | MT_SECURE)
+#define ARM_MAP_BL31_SEC_DRAM	MAP_REGION_FLAT(			\
+					BL31_BASE,			\
+					PLAT_ARM_MAX_BL31_SIZE,		\
+					MT_MEMORY | MT_RW | MT_SECURE)
 #endif
 
-#define ARM_MAP_EL3_TZC_DRAM		MAP_REGION_FLAT(			\
-						ARM_EL3_TZC_DRAM1_BASE,	\
-						ARM_EL3_TZC_DRAM1_SIZE,	\
-						MT_MEMORY | MT_RW | MT_SECURE)
+#define ARM_MAP_EL3_TZC_DRAM	MAP_REGION_FLAT(			\
+					ARM_EL3_TZC_DRAM1_BASE,		\
+					ARM_EL3_TZC_DRAM1_SIZE,		\
+					MT_MEMORY | MT_RW | EL3_PAS)
 
 #if defined(SPD_spmd)
-#define ARM_MAP_TRUSTED_DRAM		MAP_REGION_FLAT(		    \
-						PLAT_ARM_TRUSTED_DRAM_BASE, \
-						PLAT_ARM_TRUSTED_DRAM_SIZE, \
-						MT_MEMORY | MT_RW | MT_SECURE)
+#define ARM_MAP_TRUSTED_DRAM	MAP_REGION_FLAT(			\
+					PLAT_ARM_TRUSTED_DRAM_BASE,	\
+					PLAT_ARM_TRUSTED_DRAM_SIZE,	\
+					MT_MEMORY | MT_RW | MT_SECURE)
 #endif
 
+#if ENABLE_RME
+#define ARM_MAP_RMM_DRAM	MAP_REGION_FLAT(			\
+					PLAT_ARM_RMM_BASE,		\
+					PLAT_ARM_RMM_SIZE,		\
+					MT_MEMORY | MT_RW | MT_REALM)
+
+
+#define ARM_MAP_GPT_L1_DRAM	MAP_REGION_FLAT(			\
+					ARM_L1_GPT_ADDR_BASE,		\
+					ARM_L1_GPT_SIZE,		\
+					MT_MEMORY | MT_RW | EL3_PAS)
+
+#endif /* ENABLE_RME */
 
 /*
  * Mapping for the BL1 RW region. This mapping is needed by BL2 in order to
@@ -247,7 +314,7 @@
 #define ARM_MAP_BL1_RW		MAP_REGION_FLAT(	\
 					BL1_RW_BASE,	\
 					BL1_RW_LIMIT - BL1_RW_BASE, \
-					MT_MEMORY | MT_RW | MT_SECURE)
+					MT_MEMORY | MT_RW | EL3_PAS)
 
 /*
  * If SEPARATE_CODE_AND_RODATA=1 we define a region for each section
@@ -257,35 +324,35 @@
 #define ARM_MAP_BL_RO			MAP_REGION_FLAT(			\
 						BL_CODE_BASE,			\
 						BL_CODE_END - BL_CODE_BASE,	\
-						MT_CODE | MT_SECURE),		\
+						MT_CODE | EL3_PAS),		\
 					MAP_REGION_FLAT(			\
 						BL_RO_DATA_BASE,		\
 						BL_RO_DATA_END			\
 							- BL_RO_DATA_BASE,	\
-						MT_RO_DATA | MT_SECURE)
+						MT_RO_DATA | EL3_PAS)
 #else
 #define ARM_MAP_BL_RO			MAP_REGION_FLAT(			\
 						BL_CODE_BASE,			\
 						BL_CODE_END - BL_CODE_BASE,	\
-						MT_CODE | MT_SECURE)
+						MT_CODE | EL3_PAS)
 #endif
 #if USE_COHERENT_MEM
 #define ARM_MAP_BL_COHERENT_RAM		MAP_REGION_FLAT(			\
 						BL_COHERENT_RAM_BASE,		\
 						BL_COHERENT_RAM_END		\
 							- BL_COHERENT_RAM_BASE, \
-						MT_DEVICE | MT_RW | MT_SECURE)
+						MT_DEVICE | MT_RW | EL3_PAS)
 #endif
 #if USE_ROMLIB
 #define ARM_MAP_ROMLIB_CODE		MAP_REGION_FLAT(			\
 						ROMLIB_RO_BASE,			\
 						ROMLIB_RO_LIMIT	- ROMLIB_RO_BASE,\
-						MT_CODE | MT_SECURE)
+						MT_CODE | EL3_PAS)
 
 #define ARM_MAP_ROMLIB_DATA		MAP_REGION_FLAT(			\
 						ROMLIB_RW_BASE,			\
 						ROMLIB_RW_END	- ROMLIB_RW_BASE,\
-						MT_MEMORY | MT_RW | MT_SECURE)
+						MT_MEMORY | MT_RW | EL3_PAS)
 #endif
 
 /*
@@ -300,7 +367,15 @@
 #define ARM_MAP_BL_CONFIG_REGION	MAP_REGION_FLAT(ARM_BL_RAM_BASE,	\
 						(ARM_FW_CONFIGS_LIMIT		\
 							- ARM_BL_RAM_BASE),	\
-						MT_MEMORY | MT_RW | MT_SECURE)
+						MT_MEMORY | MT_RW | EL3_PAS)
+/*
+ * Map L0_GPT with read and write permissions
+ */
+#if ENABLE_RME
+#define ARM_MAP_L0_GPT_REGION		MAP_REGION_FLAT(ARM_L0_GPT_ADDR_BASE,	\
+						ARM_L0_GPT_SIZE,		\
+						MT_MEMORY | MT_RW | MT_ROOT)
+#endif
 
 /*
  * The max number of regions like RO(code), coherent and data required by
@@ -312,16 +387,44 @@
 					 ARM_BL_REGIONS)
 
 /* Memory mapped Generic timer interfaces  */
+#ifdef PLAT_ARM_SYS_CNTCTL_BASE
+#define ARM_SYS_CNTCTL_BASE		PLAT_ARM_SYS_CNTCTL_BASE
+#else
 #define ARM_SYS_CNTCTL_BASE		UL(0x2a430000)
+#endif
+
+#ifdef PLAT_ARM_SYS_CNTREAD_BASE
+#define ARM_SYS_CNTREAD_BASE		PLAT_ARM_SYS_CNTREAD_BASE
+#else
 #define ARM_SYS_CNTREAD_BASE		UL(0x2a800000)
+#endif
+
+#ifdef PLAT_ARM_SYS_TIMCTL_BASE
+#define ARM_SYS_TIMCTL_BASE		PLAT_ARM_SYS_TIMCTL_BASE
+#else
 #define ARM_SYS_TIMCTL_BASE		UL(0x2a810000)
+#endif
+
+#ifdef PLAT_ARM_SYS_CNT_BASE_S
+#define ARM_SYS_CNT_BASE_S		PLAT_ARM_SYS_CNT_BASE_S
+#else
 #define ARM_SYS_CNT_BASE_S		UL(0x2a820000)
+#endif
+
+#ifdef PLAT_ARM_SYS_CNT_BASE_NS
+#define ARM_SYS_CNT_BASE_NS		PLAT_ARM_SYS_CNT_BASE_NS
+#else
 #define ARM_SYS_CNT_BASE_NS		UL(0x2a830000)
+#endif
 
 #define ARM_CONSOLE_BAUDRATE		115200
 
 /* Trusted Watchdog constants */
+#ifdef PLAT_ARM_SP805_TWDG_BASE
+#define ARM_SP805_TWDG_BASE		PLAT_ARM_SP805_TWDG_BASE
+#else
 #define ARM_SP805_TWDG_BASE		UL(0x2a490000)
+#endif
 #define ARM_SP805_TWDG_CLK_HZ		32768
 /* The TBBR document specifies a watchdog timeout of 256 seconds. SP805
  * asserts reset after two consecutive countdowns (2 x 128 = 256 sec) */
@@ -373,15 +476,32 @@
  */
 #define ARM_FW_CONFIGS_LIMIT		(ARM_BL_RAM_BASE + (PAGE_SIZE * 2))
 
+#if ENABLE_RME
+/*
+ * Store the L0 GPT on Trusted SRAM next to firmware
+ * configuration memory, 4KB aligned.
+ */
+#define ARM_L0_GPT_SIZE			(PAGE_SIZE)
+#define ARM_L0_GPT_ADDR_BASE		(ARM_FW_CONFIGS_LIMIT)
+#define ARM_L0_GPT_LIMIT		(ARM_L0_GPT_ADDR_BASE + ARM_L0_GPT_SIZE)
+#else
+#define ARM_L0_GPT_SIZE			U(0)
+#endif
+
 /*******************************************************************************
  * BL1 specific defines.
  * BL1 RW data is relocated from ROM to RAM at runtime so we need 2 sets of
  * addresses.
  ******************************************************************************/
 #define BL1_RO_BASE			PLAT_ARM_TRUSTED_ROM_BASE
+#ifdef PLAT_BL1_RO_LIMIT
+#define BL1_RO_LIMIT			PLAT_BL1_RO_LIMIT
+#else
 #define BL1_RO_LIMIT			(PLAT_ARM_TRUSTED_ROM_BASE	\
 					 + (PLAT_ARM_TRUSTED_ROM_SIZE - \
 					    PLAT_ARM_MAX_ROMLIB_RO_SIZE))
+#endif
+
 /*
  * Put BL1 RW at the top of the Trusted SRAM.
  */
@@ -460,17 +580,29 @@
 #endif
 #endif
 
+/******************************************************************************
+ * RMM specific defines
+ *****************************************************************************/
+#if ENABLE_RME
+#define RMM_BASE			(ARM_REALM_BASE)
+#define RMM_LIMIT			(RMM_BASE + ARM_REALM_SIZE)
+#endif
+
 #if !defined(__aarch64__) || JUNO_AARCH32_EL3_RUNTIME
 /*******************************************************************************
  * BL32 specific defines for EL3 runtime in AArch32 mode
  ******************************************************************************/
 # if RESET_TO_SP_MIN && !JUNO_AARCH32_EL3_RUNTIME
+/* Ensure Position Independent support (PIE) is enabled for this config.*/
+# if !ENABLE_PIE
+#  error "BL32 must be a PIE if RESET_TO_SP_MIN=1."
+#endif
 /*
- * SP_MIN is the only BL image in SRAM. Allocate the whole of SRAM (excluding
- * the page reserved for fw_configs) to BL32
+ * Since this is PIE, we can define BL32_BASE to 0x0 since this macro is solely
+ * used for building BL32 and not used for loading BL32.
  */
-#  define BL32_BASE			ARM_FW_CONFIGS_LIMIT
-#  define BL32_LIMIT			(ARM_BL_RAM_BASE + ARM_BL_RAM_SIZE)
+#  define BL32_BASE			0x0
+#  define BL32_LIMIT			PLAT_ARM_MAX_BL32_SIZE
 # else
 /* Put BL32 below BL2 in the Trusted SRAM.*/
 #  define BL32_BASE			((ARM_BL_RAM_BASE + ARM_BL_RAM_SIZE)\
diff --git a/include/plat/arm/common/arm_dyn_cfg_helpers.h b/include/plat/arm/common/arm_dyn_cfg_helpers.h
index 34bf07c..ff00fe7 100644
--- a/include/plat/arm/common/arm_dyn_cfg_helpers.h
+++ b/include/plat/arm/common/arm_dyn_cfg_helpers.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,8 +14,4 @@
 int arm_set_dtb_mbedtls_heap_info(void *dtb, void *heap_addr,
 	size_t heap_size);
 
-#if MEASURED_BOOT
-int arm_set_bl2_hash_info(void *dtb, void *data);
-#endif
-
 #endif /* ARM_DYN_CFG_HELPERS_H */
diff --git a/include/plat/arm/common/arm_pas_def.h b/include/plat/arm/common/arm_pas_def.h
new file mode 100644
index 0000000..4fee41b
--- /dev/null
+++ b/include/plat/arm/common/arm_pas_def.h
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef ARM_PAS_DEF_H
+#define ARM_PAS_DEF_H
+
+#include <lib/gpt_rme/gpt_rme.h>
+#include <plat/arm/common/arm_def.h>
+
+/*****************************************************************************
+ * PAS regions used to initialize the Granule Protection Table (GPT)
+ ****************************************************************************/
+
+/*
+ * The PA space is initially mapped in the GPT as follows:
+ *
+ * ============================================================================
+ * Base Addr| Size        |L? GPT|PAS   |Content                 |Comment
+ * ============================================================================
+ * 0GB      | 1GB         |L0 GPT|ANY   |TBROM (EL3 code)        |Fixed mapping
+ *          |             |      |      |TSRAM (EL3 data)        |
+ *          |             |      |      |IO (incl.UARTs & GIC)   |
+ * ----------------------------------------------------------------------------
+ * 1GB      | 1GB         |L0 GPT|ANY   |IO                      |Fixed mapping
+ * ----------------------------------------------------------------------------
+ * 2GB      | 1GB         |L1 GPT|NS    |DRAM (NS Kernel)        |Use T.Descrip
+ * ----------------------------------------------------------------------------
+ * 3GB      |1GB-64MB     |L1 GPT|NS    |DRAM (NS Kernel)        |Use T.Descrip
+ * ----------------------------------------------------------------------------
+ * 4GB-64MB |64MB-32MB    |      |      |                        |
+ *          | -4MB        |L1 GPT|SECURE|DRAM TZC                |Use T.Descrip
+ * ----------------------------------------------------------------------------
+ * 4GB-32MB |             |      |      |                        |
+ * -3MB-1MB |32MB         |L1 GPT|REALM |RMM                     |Use T.Descrip
+ * ----------------------------------------------------------------------------
+ * 4GB-3MB  |             |      |      |                        |
+ * -1MB     |3MB          |L1 GPT|ROOT  |EL3 DRAM data           |Use T.Descrip
+ * ----------------------------------------------------------------------------
+ * 4GB-1MB  |1MB          |L1 GPT|ROOT  |DRAM (L1 GPTs, SCP TZC) |Fixed mapping
+ * ============================================================================
+ *
+ * - 4KB of L0 GPT reside in TSRAM, on top of the CONFIG section.
+ * - ~1MB of L1 GPTs reside at the top of DRAM1 (TZC area).
+ * - The first 1GB region has GPT_GPI_ANY and, therefore, is not protected by
+ *   the GPT.
+ * - The DRAM TZC area is split into three regions: the L1 GPT region and
+ *   3MB of region below that are defined as GPT_GPI_ROOT, 32MB Realm region
+ *   below that is defined as GPT_GPI_REALM and the rest of it is defined as
+ *   GPT_GPI_SECURE.
+ */
+
+/* TODO: This might not be the best way to map the PAS */
+
+/* Device memory 0 to 2GB */
+#define ARM_PAS_1_BASE			(U(0))
+#define ARM_PAS_1_SIZE			((ULL(1)<<31)) /* 2GB */
+
+/* NS memory 2GB to (end - 64MB) */
+#define ARM_PAS_2_BASE			(ARM_PAS_1_BASE + ARM_PAS_1_SIZE)
+#define ARM_PAS_2_SIZE			(ARM_NS_DRAM1_SIZE)
+
+/* Secure TZC region */
+#define ARM_PAS_3_BASE			(ARM_AP_TZC_DRAM1_BASE)
+#define ARM_PAS_3_SIZE			(ARM_AP_TZC_DRAM1_SIZE)
+
+#define ARM_PAS_GPI_ANY			MAP_GPT_REGION(ARM_PAS_1_BASE, \
+						       ARM_PAS_1_SIZE, \
+						       GPT_GPI_ANY)
+#define	ARM_PAS_KERNEL			GPT_MAP_REGION_GRANULE(ARM_PAS_2_BASE, \
+							       ARM_PAS_2_SIZE, \
+							       GPT_GPI_NS)
+
+#define ARM_PAS_SECURE			GPT_MAP_REGION_GRANULE(ARM_PAS_3_BASE, \
+							       ARM_PAS_3_SIZE, \
+							       GPT_GPI_SECURE)
+
+#define ARM_PAS_REALM			GPT_MAP_REGION_GRANULE(ARM_REALM_BASE, \
+							       ARM_REALM_SIZE, \
+							       GPT_GPI_REALM)
+
+#define ARM_PAS_EL3_DRAM		GPT_MAP_REGION_GRANULE(ARM_EL3_TZC_DRAM1_BASE, \
+							       ARM_EL3_TZC_DRAM1_SIZE, \
+							       GPT_GPI_ROOT)
+
+#define	ARM_PAS_GPTS			GPT_MAP_REGION_GRANULE(ARM_L1_GPT_ADDR_BASE, \
+							       ARM_L1_GPT_SIZE, \
+							       GPT_GPI_ROOT)
+
+/* GPT Configuration options */
+#define PLATFORM_L0GPTSZ		GPCCR_L0GPTSZ_30BITS
+
+#endif /* ARM_PAS_DEF_H */
diff --git a/include/plat/arm/common/arm_sip_svc.h b/include/plat/arm/common/arm_sip_svc.h
index 85fdb28..2eeed95 100644
--- a/include/plat/arm/common/arm_sip_svc.h
+++ b/include/plat/arm/common/arm_sip_svc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2019,2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -25,6 +25,12 @@
 /* DEBUGFS_SMC_32			0x82000030U */
 /* DEBUGFS_SMC_64			0xC2000030U */
 
+/*
+ * Arm Ethos-N NPU SiP SMC function IDs
+ * 0xC2000050-0xC200005F
+ * 0x82000050-0x8200005F
+ */
+
 /* ARM SiP Service Calls version numbers */
 #define ARM_SIP_SVC_VERSION_MAJOR		U(0x0)
 #define ARM_SIP_SVC_VERSION_MINOR		U(0x2)
diff --git a/include/plat/arm/common/fconf_arm_sp_getter.h b/include/plat/arm/common/fconf_arm_sp_getter.h
index c6315be..aa628df 100644
--- a/include/plat/arm/common/fconf_arm_sp_getter.h
+++ b/include/plat/arm/common/fconf_arm_sp_getter.h
@@ -13,7 +13,7 @@
 /* arm_sp getter */
 #define arm__sp_getter(prop)	arm_sp.prop
 
-#define ARM_SP_MAX_SIZE		U(0x80000)
+#define ARM_SP_MAX_SIZE		U(0xb0000)
 #define ARM_SP_OWNER_NAME_LEN	U(8)
 
 struct arm_sp_t {
diff --git a/include/plat/arm/common/fconf_ethosn_getter.h b/include/plat/arm/common/fconf_ethosn_getter.h
new file mode 100644
index 0000000..fcdc31f
--- /dev/null
+++ b/include/plat/arm/common/fconf_ethosn_getter.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FCONF_ETHOSN_GETTER_H
+#define FCONF_ETHOSN_GETTER_H
+
+#include <assert.h>
+
+#include <lib/fconf/fconf.h>
+
+#define hw_config__ethosn_config_getter(prop) ethosn_config.prop
+#define hw_config__ethosn_core_addr_getter(idx) __extension__ ({	\
+	assert(idx < ethosn_config.num_cores);				\
+	ethosn_config.core[idx].addr;					\
+})
+
+#define ETHOSN_STATUS_DISABLED U(0)
+#define ETHOSN_STATUS_ENABLED  U(1)
+
+#define ETHOSN_CORE_NUM_MAX U(64)
+
+struct ethosn_core_t {
+	uint64_t addr;
+};
+
+struct ethosn_config_t {
+	uint32_t num_cores;
+	struct ethosn_core_t core[ETHOSN_CORE_NUM_MAX];
+};
+
+int fconf_populate_arm_ethosn(uintptr_t config);
+
+extern struct ethosn_config_t ethosn_config;
+
+#endif /* FCONF_ETHOSN_GETTER_H */
diff --git a/include/plat/arm/common/plat_arm.h b/include/plat/arm/common/plat_arm.h
index 95fc18e..9618700 100644
--- a/include/plat/arm/common/plat_arm.h
+++ b/include/plat/arm/common/plat_arm.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -41,7 +41,7 @@
  ******************************************************************************/
 #if SPM_MM
 #define ARM_TZC_REGIONS_DEF						\
-	{ARM_AP_TZC_DRAM1_BASE, ARM_EL3_TZC_DRAM1_END,			\
+	{ARM_AP_TZC_DRAM1_BASE, ARM_EL3_TZC_DRAM1_END + ARM_L1_GPT_SIZE,\
 		TZC_REGION_S_RDWR, 0},					\
 	{ARM_NS_DRAM1_BASE, ARM_NS_DRAM1_END, ARM_TZC_NS_DRAM_S_ACCESS, \
 		PLAT_ARM_TZC_NS_DEV_ACCESS}, 				\
@@ -51,9 +51,20 @@
 		PLAT_SP_IMAGE_NS_BUF_SIZE) - 1, TZC_REGION_S_NONE,	\
 		PLAT_ARM_TZC_NS_DEV_ACCESS}
 
+#elif ENABLE_RME
+#define ARM_TZC_REGIONS_DEF						    \
+	{ARM_AP_TZC_DRAM1_BASE, ARM_AP_TZC_DRAM1_END, TZC_REGION_S_RDWR, 0},\
+	{ARM_EL3_TZC_DRAM1_BASE, ARM_L1_GPT_END, TZC_REGION_S_RDWR, 0},	    \
+	{ARM_NS_DRAM1_BASE, ARM_NS_DRAM1_END, ARM_TZC_NS_DRAM_S_ACCESS,	    \
+		PLAT_ARM_TZC_NS_DEV_ACCESS},				    \
+	{ARM_REALM_BASE, ARM_REALM_END, ARM_TZC_NS_DRAM_S_ACCESS,	    \
+		PLAT_ARM_TZC_NS_DEV_ACCESS},				    \
+	{ARM_DRAM2_BASE, ARM_DRAM2_END, ARM_TZC_NS_DRAM_S_ACCESS,	    \
+		PLAT_ARM_TZC_NS_DEV_ACCESS}
+
 #else
 #define ARM_TZC_REGIONS_DEF						\
-	{ARM_AP_TZC_DRAM1_BASE, ARM_EL3_TZC_DRAM1_END,			\
+	{ARM_AP_TZC_DRAM1_BASE, ARM_EL3_TZC_DRAM1_END + ARM_L1_GPT_SIZE,\
 		TZC_REGION_S_RDWR, 0},					\
 	{ARM_NS_DRAM1_BASE, ARM_NS_DRAM1_END, ARM_TZC_NS_DRAM_S_ACCESS, \
 		PLAT_ARM_TZC_NS_DEV_ACCESS},	 			\
@@ -152,6 +163,11 @@
 /* IO storage utility functions */
 int arm_io_setup(void);
 
+/* Set image specification in IO block policy */
+int arm_set_image_source(unsigned int image_id, const char *part_name,
+			 uintptr_t *dev_handle, uintptr_t *image_spec);
+void arm_set_fip_addr(uint32_t active_fw_bank_idx);
+
 /* Security utility functions */
 void arm_tzc400_setup(uintptr_t tzc_base,
 			const arm_tzc_regions_info_t *tzc_regions);
@@ -234,12 +250,8 @@
 int arm_get_mbedtls_heap(void **heap_addr, size_t *heap_size);
 
 #if MEASURED_BOOT
-/* Measured boot related functions */
-void arm_bl1_set_bl2_hash(const image_desc_t *image_desc);
-void arm_bl2_get_hash(void *data);
-int arm_set_tos_fw_info(uintptr_t config_base, uintptr_t log_addr,
-			size_t log_size);
-int arm_set_nt_fw_info(uintptr_t config_base,
+int arm_set_tos_fw_info(uintptr_t log_addr, size_t log_size);
+int arm_set_nt_fw_info(
 /*
  * Currently OP-TEE does not support reading DTBs from Secure memory
  * and this option should be removed when feature is supported.
@@ -248,6 +260,8 @@
 			uintptr_t log_addr,
 #endif
 			size_t log_size, uintptr_t *ns_log_addr);
+int arm_set_tb_fw_info(uintptr_t log_addr, size_t log_size);
+int arm_get_tb_fw_info(uint64_t *log_addr, size_t *log_size);
 #endif /* MEASURED_BOOT */
 
 /*
diff --git a/include/plat/arm/common/smccc_def.h b/include/plat/arm/common/smccc_def.h
index 6e698e5..0f4e573 100644
--- a/include/plat/arm/common/smccc_def.h
+++ b/include/plat/arm/common/smccc_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,7 +9,5 @@
 /* Defines used to retrieve ARM SOC revision */
 #define ARM_SOC_CONTINUATION_CODE	U(0x4)
 #define ARM_SOC_IDENTIFICATION_CODE	U(0x3B)
-#define ARM_SOC_CONTINUATION_SHIFT	U(24)
-#define ARM_SOC_IDENTIFICATION_SHIFT	U(16)
 
 #endif /* SMCCC_DEF_H */
diff --git a/include/plat/arm/css/common/css_def.h b/include/plat/arm/css/common/css_def.h
index d599352..dde174c 100644
--- a/include/plat/arm/css/common/css_def.h
+++ b/include/plat/arm/css/common/css_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -137,6 +137,8 @@
 #define SSC_DBGCFG_SET		0x14
 #define SSC_DBGCFG_CLR		0x18
 
+#define SPNIDEN_INT_CLR_SHIFT	4
+#define SPNIDEN_SEL_SET_SHIFT	5
 #define SPIDEN_INT_CLR_SHIFT	6
 #define SPIDEN_SEL_SET_SHIFT	7
 
diff --git a/include/plat/common/plat_trng.h b/include/plat/common/plat_trng.h
new file mode 100644
index 0000000..a9f73b6
--- /dev/null
+++ b/include/plat/common/plat_trng.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_TRNG_H
+#define PLAT_TRNG_H
+
+#include <tools_share/uuid.h>
+
+/* TRNG platform functions */
+
+extern uuid_t plat_trng_uuid;
+void plat_entropy_setup(void);
+bool plat_get_entropy(uint64_t *out);
+
+#endif /* PLAT_TRNG_H */
diff --git a/include/plat/common/platform.h b/include/plat/common/platform.h
index ebcc855..3fa63f5 100644
--- a/include/plat/common/platform.h
+++ b/include/plat/common/platform.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,6 +13,10 @@
 #if defined(SPD_spmd)
  #include <services/spm_core_manifest.h>
 #endif
+#if TRNG_SUPPORT
+#include "plat_trng.h"
+#endif
+#include <drivers/fwu/fwu_metadata.h>
 
 /*******************************************************************************
  * Forward declarations
@@ -118,6 +122,16 @@
 void bl2_plat_preload_setup(void);
 int plat_try_next_boot_source(void);
 
+#if MEASURED_BOOT
+int plat_mboot_measure_image(unsigned int image_id, image_info_t *image_data);
+#else
+static inline int plat_mboot_measure_image(unsigned int image_id __unused,
+					   image_info_t *image_data __unused)
+{
+	return 0;
+}
+#endif /* MEASURED_BOOT */
+
 /*******************************************************************************
  * Mandatory BL1 functions
  ******************************************************************************/
@@ -137,6 +151,8 @@
 void plat_sdei_handle_masked_trigger(uint64_t mpidr, unsigned int intr);
 #endif
 
+void plat_default_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
+		void *handle, uint64_t flags);
 void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
 		void *handle, uint64_t flags);
 
@@ -176,12 +192,16 @@
 int bl1_plat_handle_post_image_load(unsigned int image_id);
 
 #if MEASURED_BOOT
-/*
- * Calculates and writes BL2 hash data to the platform's defined location.
- * For ARM platforms the data are written to TB_FW_CONFIG DTB.
- */
-void bl1_plat_set_bl2_hash(const image_desc_t *image_desc);
-#endif
+void bl1_plat_mboot_init(void);
+void bl1_plat_mboot_finish(void);
+#else
+static inline void bl1_plat_mboot_init(void)
+{
+}
+static inline void bl1_plat_mboot_finish(void)
+{
+}
+#endif /* MEASURED_BOOT */
 
 /*******************************************************************************
  * Mandatory BL2 functions
@@ -202,9 +222,16 @@
  * Optional BL2 functions (may be overridden)
  ******************************************************************************/
 #if MEASURED_BOOT
-/* Read TCG_DIGEST_SIZE bytes of BL2 hash data */
-void bl2_plat_get_hash(void *data);
-#endif
+void bl2_plat_mboot_init(void);
+void bl2_plat_mboot_finish(void);
+#else
+static inline void bl2_plat_mboot_init(void)
+{
+}
+static inline void bl2_plat_mboot_finish(void)
+{
+}
+#endif /* MEASURED_BOOT */
 
 /*******************************************************************************
  * Mandatory BL2 at EL3 functions: Must be implemented if BL2_AT_EL3 image is
@@ -346,4 +373,12 @@
  */
 int32_t plat_is_smccc_feature_available(u_register_t fid);
 
+/*******************************************************************************
+ * FWU platform specific functions
+ ******************************************************************************/
+int plat_fwu_set_metadata_image_source(unsigned int image_id,
+				       uintptr_t *dev_handle,
+				       uintptr_t *image_spec);
+void plat_fwu_set_images_source(struct fwu_metadata *metadata);
+
 #endif /* PLATFORM_H */
diff --git a/include/plat/marvell/armada/a3k/common/plat_marvell.h b/include/plat/marvell/armada/a3k/common/plat_marvell.h
index ea7cdcd..cb31481 100644
--- a/include/plat/marvell/armada/a3k/common/plat_marvell.h
+++ b/include/plat/marvell/armada/a3k/common/plat_marvell.h
@@ -100,4 +100,6 @@
 
 const mmap_region_t *plat_marvell_get_mmap(void);
 
+uint32_t get_ref_clk(void);
+
 #endif /* PLAT_MARVELL_H */
diff --git a/include/plat/marvell/armada/a8k/common/efuse_def.h b/include/plat/marvell/armada/a8k/common/efuse_def.h
new file mode 100644
index 0000000..ff1d4a3
--- /dev/null
+++ b/include/plat/marvell/armada/a8k/common/efuse_def.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#ifndef EFUSE_DEF_H
+#define EFUSE_DEF_H
+
+#include <platform_def.h>
+
+#define MVEBU_AP_EFUSE_SRV_CTRL_REG	(MVEBU_AP_GEN_MGMT_BASE + 0x8)
+#define EFUSE_SRV_CTRL_LD_SELECT_OFFS	6
+#define EFUSE_SRV_CTRL_LD_SELECT_MASK	(1 << EFUSE_SRV_CTRL_LD_SELECT_OFFS)
+
+#define MVEBU_AP_LD_EFUSE_BASE		(MVEBU_AP_GEN_MGMT_BASE + 0xF00)
+/* Bits [31:0] - 32 data bits total */
+#define MVEBU_AP_LDX_31_0_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE)
+/* Bits [62:32] - 31 data bits total 32nd bit is parity for bits [62:0]*/
+#define MVEBU_AP_LDX_62_32_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x4)
+/* Bits [94:63] - 32 data bits total */
+#define MVEBU_AP_LDX_94_63_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x8)
+/* Bits [125:95] - 31 data bits total, 32nd bit is parity for bits [125:63] */
+#define MVEBU_AP_LDX_125_95_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0xC)
+/* Bits [157:126] - 32 data bits total */
+#define MVEBU_AP_LDX_126_157_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x10)
+/* Bits [188:158] - 31 data bits total, 32nd bit is parity for bits [188:126] */
+#define MVEBU_AP_LDX_188_158_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x14)
+/* Bits [220:189] - 32 data bits total */
+#define MVEBU_AP_LDX_220_189_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x18)
+
+#endif /* EFUSE_DEF_H */
diff --git a/include/services/ffa_svc.h b/include/services/ffa_svc.h
index 0513eab..4c049c5 100644
--- a/include/services/ffa_svc.h
+++ b/include/services/ffa_svc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -22,7 +22,7 @@
 
 /* The macros below are used to identify FFA calls from the SMC function ID */
 #define FFA_FNUM_MIN_VALUE	U(0x60)
-#define FFA_FNUM_MAX_VALUE	U(0x7f)
+#define FFA_FNUM_MAX_VALUE	U(0x87)
 #define is_ffa_fid(fid) __extension__ ({		\
 	__typeof__(fid) _fid = (fid);			\
 	((GET_SMC_NUM(_fid) >= FFA_FNUM_MIN_VALUE) &&	\
@@ -32,7 +32,7 @@
 #define FFA_VERSION_MAJOR		U(1)
 #define FFA_VERSION_MAJOR_SHIFT		16
 #define FFA_VERSION_MAJOR_MASK		U(0x7FFF)
-#define FFA_VERSION_MINOR		U(0)
+#define FFA_VERSION_MINOR		U(1)
 #define FFA_VERSION_MINOR_SHIFT		0
 #define FFA_VERSION_MINOR_MASK		U(0xFFFF)
 #define FFA_VERSION_BIT31_MASK 		U(0x1u << 31)
@@ -61,30 +61,44 @@
 		 ((func_num) << FUNCID_NUM_SHIFT))
 
 /* FFA function numbers */
-#define FFA_FNUM_ERROR			U(0x60)
-#define FFA_FNUM_SUCCESS		U(0x61)
-#define FFA_FNUM_INTERRUPT		U(0x62)
-#define FFA_FNUM_VERSION		U(0x63)
-#define FFA_FNUM_FEATURES		U(0x64)
-#define FFA_FNUM_RX_RELEASE		U(0x65)
-#define FFA_FNUM_RXTX_MAP		U(0x66)
-#define FFA_FNUM_RXTX_UNMAP		U(0x67)
-#define FFA_FNUM_PARTITION_INFO_GET	U(0x68)
-#define FFA_FNUM_ID_GET		U(0x69)
-#define FFA_FNUM_MSG_POLL		U(0x6A)
-#define FFA_FNUM_MSG_WAIT		U(0x6B)
-#define FFA_FNUM_MSG_YIELD		U(0x6C)
-#define FFA_FNUM_MSG_RUN		U(0x6D)
-#define FFA_FNUM_MSG_SEND		U(0x6E)
-#define FFA_FNUM_MSG_SEND_DIRECT_REQ	U(0x6F)
-#define FFA_FNUM_MSG_SEND_DIRECT_RESP	U(0x70)
-#define FFA_FNUM_MEM_DONATE		U(0x71)
-#define FFA_FNUM_MEM_LEND		U(0x72)
-#define FFA_FNUM_MEM_SHARE		U(0x73)
-#define FFA_FNUM_MEM_RETRIEVE_REQ	U(0x74)
-#define FFA_FNUM_MEM_RETRIEVE_RESP	U(0x75)
-#define FFA_FNUM_MEM_RELINQUISH	U(0x76)
-#define FFA_FNUM_MEM_RECLAIM		U(0x77)
+#define FFA_FNUM_ERROR				U(0x60)
+#define FFA_FNUM_SUCCESS			U(0x61)
+#define FFA_FNUM_INTERRUPT			U(0x62)
+#define FFA_FNUM_VERSION			U(0x63)
+#define FFA_FNUM_FEATURES			U(0x64)
+#define FFA_FNUM_RX_RELEASE			U(0x65)
+#define FFA_FNUM_RXTX_MAP			U(0x66)
+#define FFA_FNUM_RXTX_UNMAP			U(0x67)
+#define FFA_FNUM_PARTITION_INFO_GET		U(0x68)
+#define FFA_FNUM_ID_GET				U(0x69)
+#define FFA_FNUM_MSG_POLL			U(0x6A) /* Legacy FF-A v1.0 */
+#define FFA_FNUM_MSG_WAIT			U(0x6B)
+#define FFA_FNUM_MSG_YIELD			U(0x6C)
+#define FFA_FNUM_MSG_RUN			U(0x6D)
+#define FFA_FNUM_MSG_SEND			U(0x6E) /* Legacy FF-A v1.0 */
+#define FFA_FNUM_MSG_SEND_DIRECT_REQ		U(0x6F)
+#define FFA_FNUM_MSG_SEND_DIRECT_RESP		U(0x70)
+#define FFA_FNUM_MEM_DONATE			U(0x71)
+#define FFA_FNUM_MEM_LEND			U(0x72)
+#define FFA_FNUM_MEM_SHARE			U(0x73)
+#define FFA_FNUM_MEM_RETRIEVE_REQ		U(0x74)
+#define FFA_FNUM_MEM_RETRIEVE_RESP		U(0x75)
+#define FFA_FNUM_MEM_RELINQUISH			U(0x76)
+#define FFA_FNUM_MEM_RECLAIM			U(0x77)
+#define FFA_FNUM_NORMAL_WORLD_RESUME		U(0x7C)
+
+/* FF-A v1.1 */
+#define FFA_FNUM_NOTIFICATION_BITMAP_CREATE	U(0x7D)
+#define FFA_FNUM_NOTIFICATION_BITMAP_DESTROY	U(0x7E)
+#define FFA_FNUM_NOTIFICATION_BIND		U(0x7F)
+#define FFA_FNUM_NOTIFICATION_UNBIND		U(0x80)
+#define FFA_FNUM_NOTIFICATION_SET		U(0x81)
+#define FFA_FNUM_NOTIFICATION_GET		U(0x82)
+#define FFA_FNUM_NOTIFICATION_INFO_GET		U(0x83)
+#define FFA_FNUM_RX_ACQUIRE			U(0x84)
+#define FFA_FNUM_SPM_ID_GET			U(0x85)
+#define FFA_FNUM_MSG_SEND2			U(0x86)
+#define FFA_FNUM_SECONDARY_EP_REGISTER		U(0x87)
 
 /* FFA SMC32 FIDs */
 #define FFA_ERROR		FFA_FID(SMC_32, FFA_FNUM_ERROR)
@@ -114,8 +128,21 @@
 #define FFA_MEM_RETRIEVE_RESP	FFA_FID(SMC_32, FFA_FNUM_MEM_RETRIEVE_RESP)
 #define FFA_MEM_RELINQUISH	FFA_FID(SMC_32, FFA_FNUM_MEM_RELINQUISH)
 #define FFA_MEM_RECLAIM	FFA_FID(SMC_32, FFA_FNUM_MEM_RECLAIM)
+#define FFA_NOTIFICATION_BITMAP_CREATE	\
+	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_BITMAP_CREATE)
+#define FFA_NOTIFICATION_BITMAP_DESTROY	\
+	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_BITMAP_DESTROY)
+#define FFA_NOTIFICATION_BIND	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_BIND)
+#define FFA_NOTIFICATION_UNBIND FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_UNBIND)
+#define FFA_NOTIFICATION_SET 	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_SET)
+#define FFA_NOTIFICATION_GET 	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_GET)
+#define FFA_NOTIFICATION_INFO_GET \
+	FFA_FID(SMC_32, FFA_FNUM_NOTIFICATION_INFO_GET)
+#define FFA_SPM_ID_GET		FFA_FID(SMC_32, FFA_FNUM_SPM_ID_GET)
+#define FFA_NORMAL_WORLD_RESUME	FFA_FID(SMC_32, FFA_FNUM_NORMAL_WORLD_RESUME)
 
 /* FFA SMC64 FIDs */
+#define FFA_ERROR_SMC64		FFA_FID(SMC_64, FFA_FNUM_ERROR)
 #define FFA_SUCCESS_SMC64	FFA_FID(SMC_64, FFA_FNUM_SUCCESS)
 #define FFA_RXTX_MAP_SMC64	FFA_FID(SMC_64, FFA_FNUM_RXTX_MAP)
 #define FFA_MSG_SEND_DIRECT_REQ_SMC64 \
@@ -127,6 +154,10 @@
 #define FFA_MEM_SHARE_SMC64	FFA_FID(SMC_64, FFA_FNUM_MEM_SHARE)
 #define FFA_MEM_RETRIEVE_REQ_SMC64 \
 	FFA_FID(SMC_64, FFA_FNUM_MEM_RETRIEVE_REQ)
+#define FFA_SECONDARY_EP_REGISTER_SMC64 \
+	FFA_FID(SMC_64, FFA_FNUM_SECONDARY_EP_REGISTER)
+#define FFA_NOTIFICATION_INFO_GET_SMC64 \
+	FFA_FID(SMC_64, FFA_FNUM_NOTIFICATION_INFO_GET)
 
 /*
  * Reserve a special value for traffic targeted to the Hypervisor or SPM.
diff --git a/include/services/gtsi_svc.h b/include/services/gtsi_svc.h
new file mode 100644
index 0000000..cb942ed
--- /dev/null
+++ b/include/services/gtsi_svc.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef GTSI_SVC_H
+#define GTSI_SVC_H
+
+/* GTSI error codes. */
+#define GTSI_SUCCESS			0
+#define GTSI_ERROR_NOT_SUPPORTED	-1
+#define GTSI_ERROR_INVALID_ADDRESS	-2
+#define GTSI_ERROR_INVALID_PAS		-3
+
+/* The macros below are used to identify GTSI calls from the SMC function ID */
+#define GTSI_FNUM_MIN_VALUE	U(0x100)
+#define GTSI_FNUM_MAX_VALUE	U(0x101)
+#define is_gtsi_fid(fid) __extension__ ({		\
+	__typeof__(fid) _fid = (fid);			\
+	((GET_SMC_NUM(_fid) >= GTSI_FNUM_MIN_VALUE) &&	\
+	 (GET_SMC_NUM(_fid) <= GTSI_FNUM_MAX_VALUE)); })
+
+/* Get GTSI fastcall std FID from function number */
+#define GTSI_FID(smc_cc, func_num)			\
+	((SMC_TYPE_FAST << FUNCID_TYPE_SHIFT)	|	\
+	 ((smc_cc) << FUNCID_CC_SHIFT)		|	\
+	 (OEN_STD_START << FUNCID_OEN_SHIFT)	|	\
+	 ((func_num) << FUNCID_NUM_SHIFT))
+
+#define GRAN_TRANS_TO_REALM_FNUM	U(0x100)
+#define GRAN_TRANS_TO_NS_FNUM		U(0x101)
+
+#define SMC_ASC_MARK_REALM	GTSI_FID(SMC_64, GRAN_TRANS_TO_REALM_FNUM)
+#define SMC_ASC_MARK_NONSECURE	GTSI_FID(SMC_64, GRAN_TRANS_TO_NS_FNUM)
+
+#define GRAN_TRANS_RET_BAD_ADDR		-2
+#define GRAN_TRANS_RET_BAD_PAS		-3
+
+#endif /* GTSI_SVC_H */
diff --git a/include/services/pci_svc.h b/include/services/pci_svc.h
new file mode 100644
index 0000000..664a742
--- /dev/null
+++ b/include/services/pci_svc.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PCI_SVC_H
+#define PCI_SVC_H
+
+#include <lib/utils_def.h>
+
+/* SMCCC PCI platform functions */
+#define SMC_PCI_VERSION			U(0x84000130)
+#define SMC_PCI_FEATURES		U(0x84000131)
+#define SMC_PCI_READ			U(0x84000132)
+#define SMC_PCI_WRITE			U(0x84000133)
+#define SMC_PCI_SEG_INFO		U(0x84000134)
+
+#define is_pci_fid(_fid) (((_fid) >= SMC_PCI_VERSION) &&  \
+			  ((_fid) <= SMC_PCI_SEG_INFO))
+
+uint64_t pci_smc_handler(uint32_t smc_fid, u_register_t x1, u_register_t x2,
+			 u_register_t x3,  u_register_t x4, void *cookie,
+			 void *handle, u_register_t flags);
+
+#define PCI_ADDR_FUN(dev) ((dev) & U(0x7))
+#define PCI_ADDR_DEV(dev) (((dev) >> U(3))  & U(0x001F))
+#define PCI_ADDR_BUS(dev) (((dev) >> U(8))  & U(0x00FF))
+#define PCI_ADDR_SEG(dev) (((dev) >> U(16)) & U(0xFFFF))
+#define PCI_OFFSET_MASK   U(0xFFF)
+typedef union {
+	struct {
+		uint16_t minor;
+		uint16_t major;
+	} __packed;
+	uint32_t val;
+} pcie_version;
+
+/*
+ * platforms are responsible for providing implementations of these
+ * three functions in a manner which conforms to the Arm PCI Configuration
+ * Space Access Firmware Interface (DEN0115) and the PCIe specification's
+ * sections on PCI configuration access. See the rpi4_pci_svc.c example.
+ */
+uint32_t pci_read_config(uint32_t addr, uint32_t off, uint32_t sz, uint32_t *val);
+uint32_t pci_write_config(uint32_t addr, uint32_t off, uint32_t sz, uint32_t val);
+uint32_t pci_get_bus_for_seg(uint32_t seg, uint32_t *bus_range, uint32_t *nseg);
+
+/* Return codes for Arm PCI Config Space Access Firmware SMC calls */
+#define SMC_PCI_CALL_SUCCESS	       U(0)
+#define SMC_PCI_CALL_NOT_SUPPORTED	-1
+#define SMC_PCI_CALL_INVAL_PARAM	-2
+#define SMC_PCI_CALL_NOT_IMPL		-3
+
+#define SMC_PCI_SZ_8BIT			U(1)
+#define SMC_PCI_SZ_16BIT		U(2)
+#define SMC_PCI_SZ_32BIT		U(4)
+
+#endif /* PCI_SVC_H */
diff --git a/include/services/rmi_svc.h b/include/services/rmi_svc.h
new file mode 100644
index 0000000..22f635b
--- /dev/null
+++ b/include/services/rmi_svc.h
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RMI_SVC_H
+#define RMI_SVC_H
+
+#include <lib/smccc.h>
+#include <lib/utils_def.h>
+
+/* RMI error codes. */
+#define RMI_SUCCESS			0
+#define RMI_ERROR_NOT_SUPPORTED		-1
+#define RMI_ERROR_INVALID_ADDRESS	-2
+#define RMI_ERROR_INVALID_PAS		-3
+
+/* The macros below are used to identify RMI calls from the SMC function ID */
+#define RMI_FNUM_MIN_VALUE	U(0x00)
+#define RMI_FNUM_MAX_VALUE	U(0x20)
+#define is_rmi_fid(fid) __extension__ ({		\
+	__typeof__(fid) _fid = (fid);			\
+	((GET_SMC_NUM(_fid) >= RMI_FNUM_MIN_VALUE) &&	\
+	 (GET_SMC_NUM(_fid) <= RMI_FNUM_MAX_VALUE) &&	\
+	 (GET_SMC_TYPE(_fid) == SMC_TYPE_FAST)	   &&	\
+	 (GET_SMC_CC(_fid) == SMC_64)              &&	\
+	 (GET_SMC_OEN(_fid) == OEN_ARM_START)      &&	\
+	 ((_fid & 0x00FE0000) == 0U)); })
+
+/* Get RMI fastcall std FID from function number */
+#define RMI_FID(smc_cc, func_num)			\
+	((SMC_TYPE_FAST << FUNCID_TYPE_SHIFT)	|	\
+	((smc_cc) << FUNCID_CC_SHIFT)		|	\
+	(OEN_ARM_START << FUNCID_OEN_SHIFT)	|	\
+	((func_num) << FUNCID_NUM_SHIFT))
+
+/*
+ * SMC_RMM_INIT_COMPLETE is the only function in the RMI that originates from
+ * the Realm world and is handled by the RMMD. The remaining functions are
+ * always invoked by the Normal world, forwarded by RMMD and handled by the
+ * RMM
+ */
+#define RMI_FNUM_REQ_COMPLETE		U(0x10)
+#define RMI_FNUM_VERSION_REQ		U(0x00)
+
+#define RMI_FNUM_GRAN_NS_REALM		U(0x01)
+#define RMI_FNUM_GRAN_REALM_NS		U(0x02)
+
+/* RMI SMC64 FIDs handled by the RMMD */
+#define RMI_RMM_REQ_COMPLETE		RMI_FID(SMC_64, RMI_FNUM_REQ_COMPLETE)
+#define RMI_RMM_REQ_VERSION		RMI_FID(SMC_64, RMI_FNUM_VERSION_REQ)
+
+#define RMI_RMM_GRANULE_DELEGATE	RMI_FID(SMC_64, RMI_FNUM_GRAN_NS_REALM)
+#define RMI_RMM_GRANULE_UNDELEGATE	RMI_FID(SMC_64, RMI_FNUM_GRAN_REALM_NS)
+
+
+#define RMI_ABI_VERSION_GET_MAJOR(_version) ((_version) >> 16)
+#define RMI_ABI_VERSION_GET_MINOR(_version) ((_version) & 0xFFFF)
+
+/* Reserve a special value for MBZ parameters. */
+#define RMI_PARAM_MBZ			U(0x0)
+
+#endif /* RMI_SVC_H */
diff --git a/include/services/rmmd_svc.h b/include/services/rmmd_svc.h
new file mode 100644
index 0000000..132973b
--- /dev/null
+++ b/include/services/rmmd_svc.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RMMD_SVC_H
+#define RMMD_SVC_H
+
+#ifndef __ASSEMBLER__
+#include <stdint.h>
+
+int rmmd_setup(void);
+uint64_t rmmd_rmi_handler(uint32_t smc_fid,
+		uint64_t x1,
+		uint64_t x2,
+		uint64_t x3,
+		uint64_t x4,
+		void *cookie,
+		void *handle,
+		uint64_t flags);
+
+uint64_t rmmd_gtsi_handler(uint32_t smc_fid,
+		uint64_t x1,
+		uint64_t x2,
+		uint64_t x3,
+		uint64_t x4,
+		void *cookie,
+		void *handle,
+		uint64_t flags);
+
+#endif /* __ASSEMBLER__ */
+
+#endif /* RMMD_SVC_H */
diff --git a/include/services/trng_svc.h b/include/services/trng_svc.h
new file mode 100644
index 0000000..ed4d557
--- /dev/null
+++ b/include/services/trng_svc.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TRNG_SVC_H
+#define TRNG_SVC_H
+
+#include <stdbool.h>
+#include <stdint.h>
+
+#include <lib/smccc.h>
+
+/* SMC function IDs for TRNG queries */
+#define ARM_TRNG_VERSION	U(0x84000050)
+#define ARM_TRNG_FEATURES	U(0x84000051)
+#define ARM_TRNG_GET_UUID	U(0x84000052)
+#define ARM_TRNG_RND32		U(0x84000053)
+#define ARM_TRNG_RND64		U(0xc4000053)
+
+/* TRNG version numbers */
+#define TRNG_VERSION_MAJOR	(0x1)
+#define TRNG_VERSION_MINOR	(0x0)
+
+/* TRNG Error Numbers */
+#define TRNG_E_SUCCESS		(0)
+#define TRNG_E_NOT_SUPPORTED	(-1)
+#define TRNG_E_INVALID_PARAMS	(-2)
+#define TRNG_E_NO_ENTROPY	(-3)
+#define TRNG_E_NOT_IMPLEMENTED	(-4)
+
+#if TRNG_SUPPORT
+void trng_setup(void);
+bool is_trng_fid(uint32_t smc_fid);
+#else
+static inline void trng_setup(void)
+{
+}
+
+static inline bool is_trng_fid(uint32_t smc_fid)
+{
+	return false;
+}
+#endif
+uintptr_t trng_smc_handler(
+	uint32_t smc_fid,
+	u_register_t x1,
+	u_register_t x2,
+	u_register_t x3,
+	u_register_t x4,
+	void *cookie,
+	void *handle,
+	u_register_t flags
+);
+
+#endif /* TRNG_SVC_H */
diff --git a/include/services/trp/platform_trp.h b/include/services/trp/platform_trp.h
new file mode 100644
index 0000000..b34da85
--- /dev/null
+++ b/include/services/trp/platform_trp.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_TRP_H
+#define PLATFORM_TRP_H
+
+/*******************************************************************************
+ * Mandatory TRP functions (only if platform contains a TRP)
+ ******************************************************************************/
+void trp_early_platform_setup(void);
+
+#endif /* PLATFORM_TRP_H */
diff --git a/include/tools_share/firmware_image_package.h b/include/tools_share/firmware_image_package.h
index bcde04f..bd5b14b 100644
--- a/include/tools_share/firmware_image_package.h
+++ b/include/tools_share/firmware_image_package.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -38,6 +38,8 @@
 	{{0x8e,  0xa8, 0x7b, 0xb1}, {0xcf, 0xa2}, {0x3f, 0x4d}, 0x85, 0xfd, {0xe7, 0xbb, 0xa5, 0x02, 0x20, 0xd9} }
 #define UUID_NON_TRUSTED_FIRMWARE_BL33 \
 	{{0xd6,  0xd0, 0xee, 0xa7}, {0xfc, 0xea}, {0xd5, 0x4b}, 0x97, 0x82, {0x99, 0x34, 0xf2, 0x34, 0xb6, 0xe4} }
+#define UUID_REALM_MONITOR_MGMT_FIRMWARE \
+	{{0x6c,  0x07, 0x62, 0xa6}, {0x12, 0xf2}, {0x4b, 0x56}, 0x92, 0xcb, {0xba, 0x8f, 0x63, 0x36, 0x06, 0xd9} }
 /* Key certificates */
 #define UUID_ROT_KEY_CERT \
 	{{0x86,  0x2d, 0x1d, 0x72}, {0xf8, 0x60}, {0xe4, 0x11}, 0x92, 0x0b, {0x8b, 0xe7, 0x62, 0x16, 0x0f, 0x24} }
@@ -82,6 +84,10 @@
 #define UUID_FW_CONFIG \
 	{{0x58,  0x07, 0xe1, 0x6a}, {0x84, 0x59}, {0x47, 0xbe}, 0x8e, 0xd5, {0x64, 0x8e, 0x8d, 0xdd, 0xab, 0x0e} }
 
+#ifdef PLAT_DEF_FIP_UUID
+#include <plat_def_fip_uuid.h>
+#endif
+
 typedef struct fip_toc_header {
 	uint32_t	name;
 	uint32_t	serial_number;
diff --git a/include/tools_share/tbbr_oid.h b/include/tools_share/tbbr_oid.h
index c789f79..52b43ab 100644
--- a/include/tools_share/tbbr_oid.h
+++ b/include/tools_share/tbbr_oid.h
@@ -160,4 +160,7 @@
 #define SP_PKG7_HASH_OID			"1.3.6.1.4.1.4128.2100.1307"
 #define SP_PKG8_HASH_OID			"1.3.6.1.4.1.4128.2100.1308"
 
+#ifdef PLAT_DEF_OID
+#include <platform_oid.h>
+#endif
 #endif /* TBBR_OID_H */
diff --git a/include/tools_share/uuid.h b/include/tools_share/uuid.h
index 36be9ed..2ced3a3 100644
--- a/include/tools_share/uuid.h
+++ b/include/tools_share/uuid.h
@@ -56,9 +56,16 @@
 	uint8_t		node[_UUID_NODE_LEN];
 };
 
+struct efi_guid {
+	uint32_t time_low;
+	uint16_t time_mid;
+	uint16_t time_hi_and_version;
+	uint8_t clock_seq_and_node[8];
+};
+
 union uuid_helper_t {
 	struct uuid uuid_struct;
-	uint32_t word[4];
+	struct efi_guid efi_guid;
 };
 
 /* XXX namespace pollution? */
diff --git a/lib/aarch32/misc_helpers.S b/lib/aarch32/misc_helpers.S
index e9734ac..8b16f93 100644
--- a/lib/aarch32/misc_helpers.S
+++ b/lib/aarch32/misc_helpers.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,6 +7,8 @@
 #include <arch.h>
 #include <asm_macros.S>
 #include <assert_macros.S>
+#include <common/bl_common.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
 
 	.globl	smc
 	.globl	zeromem
@@ -14,6 +16,9 @@
 	.globl	memcpy4
 	.globl	disable_mmu_icache_secure
 	.globl	disable_mmu_secure
+	.globl	fixup_gdt_reloc
+
+#define PAGE_START_MASK		~(PAGE_SIZE_MASK)
 
 func smc
 	/*
@@ -187,3 +192,124 @@
 	ldr	r1, =(SCTLR_M_BIT | SCTLR_C_BIT | SCTLR_I_BIT)
 	b	do_disable_mmu
 endfunc disable_mmu_icache_secure
+
+/* ---------------------------------------------------------------------------
+ * Helper to fixup Global Descriptor table (GDT) and dynamic relocations
+ * (.rel.dyn) at runtime.
+ *
+ * This function is meant to be used when the firmware is compiled with -fpie
+ * and linked with -pie options. We rely on the linker script exporting
+ * appropriate markers for start and end of the section. For GOT, we
+ * expect __GOT_START__ and __GOT_END__. Similarly for .rela.dyn, we expect
+ * __RELA_START__ and __RELA_END__.
+ *
+ * The function takes the limits of the memory to apply fixups to as
+ * arguments (which is usually the limits of the relocable BL image).
+ *   r0 -  the start of the fixup region
+ *   r1 -  the limit of the fixup region
+ * These addresses have to be 4KB page aligned.
+ * ---------------------------------------------------------------------------
+ */
+
+/* Relocation codes */
+#define R_ARM_RELATIVE 	23
+
+func fixup_gdt_reloc
+	mov	r6, r0
+	mov	r7, r1
+
+#if ENABLE_ASSERTIONS
+	/* Test if the limits are 4K aligned */
+	orr	r0, r0, r1
+	mov	r1, #(PAGE_SIZE_MASK)
+	tst	r0, r1
+	ASM_ASSERT(eq)
+#endif
+	/*
+	 * Calculate the offset based on return address in lr.
+	 * Assume that this function is called within a page at the start of
+	 * fixup region.
+	 */
+	ldr	r1, =PAGE_START_MASK
+	and	r2, lr, r1
+	subs	r0, r2, r6	/* Diff(S) = Current Address - Compiled Address */
+	beq	3f		/* Diff(S) = 0. No relocation needed */
+
+	ldr	r1, =__GOT_START__
+	add	r1, r1, r0
+	ldr	r2, =__GOT_END__
+	add	r2, r2, r0
+
+	/*
+	 * GOT is an array of 32_bit addresses which must be fixed up as
+	 * new_addr = old_addr + Diff(S).
+	 * The new_addr is the address currently the binary is executing from
+	 * and old_addr is the address at compile time.
+	 */
+1:	ldr	r3, [r1]
+
+	/* Skip adding offset if address is < lower limit */
+	cmp	r3, r6
+	blo	2f
+
+	/* Skip adding offset if address is > upper limit */
+	cmp	r3, r7
+	bhi	2f
+	add	r3, r3, r0
+	str	r3, [r1]
+
+2:	add	r1, r1, #4
+	cmp	r1, r2
+	blo	1b
+
+	/* Starting dynamic relocations. Use ldr to get RELA_START and END */
+3:	ldr	r1, =__RELA_START__
+	add	r1, r1, r0
+	ldr	r2, =__RELA_END__
+	add	r2, r2, r0
+
+	/*
+	 * According to ELF-32 specification, the RELA data structure is as
+	 * follows:
+	 *	typedef struct {
+	 *		Elf32_Addr r_offset;
+	 *		Elf32_Xword r_info;
+	 *	} Elf32_Rela;
+	 *
+	 * r_offset is address of reference
+	 * r_info is symbol index and type of relocation (in this case
+	 * code 23  which corresponds to R_ARM_RELATIVE).
+	 *
+	 * Size of Elf32_Rela structure is 8 bytes.
+	 */
+
+	/* Skip R_ARM_NONE entry with code 0 */
+1:	ldr	r3, [r1, #4]
+	ands	r3, r3, #0xff
+	beq	2f
+
+#if ENABLE_ASSERTIONS
+	/* Assert that the relocation type is R_ARM_RELATIVE */
+	cmp	r3, #R_ARM_RELATIVE
+	ASM_ASSERT(eq)
+#endif
+	ldr	r3, [r1]	/* r_offset */
+	add	r3, r0, r3	/* Diff(S) + r_offset */
+	ldr 	r4, [r3]
+
+	/* Skip adding offset if address is < lower limit */
+	cmp	r4, r6
+	blo	2f
+
+	/* Skip adding offset if address is >= upper limit */
+	cmp	r4, r7
+	bhs	2f
+
+	add 	r4, r0, r4
+	str	r4, [r3]
+
+2:	add	r1, r1, #8
+	cmp	r1, r2
+	blo	1b
+	bx	lr
+endfunc fixup_gdt_reloc
diff --git a/lib/aarch64/misc_helpers.S b/lib/aarch64/misc_helpers.S
index 0528916..6e4d1fc 100644
--- a/lib/aarch64/misc_helpers.S
+++ b/lib/aarch64/misc_helpers.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,6 +15,7 @@
 	.globl	zero_normalmem
 	.globl	zeromem
 	.globl	memcpy16
+	.globl	gpt_tlbi_by_pa
 
 	.globl	disable_mmu_el1
 	.globl	disable_mmu_el3
@@ -162,7 +163,8 @@
 	 * Check for M bit (MMU enabled) of the current SCTLR_EL(1|3)
 	 * register value and panic if the MMU is disabled.
 	 */
-#if defined(IMAGE_BL1) || defined(IMAGE_BL31) || (defined(IMAGE_BL2) && BL2_AT_EL3)
+#if defined(IMAGE_BL1) || defined(IMAGE_BL31) || (defined(IMAGE_BL2) && \
+	(BL2_AT_EL3 || ENABLE_RME))
 	mrs	tmp1, sctlr_el3
 #else
 	mrs	tmp1, sctlr_el1
@@ -486,15 +488,20 @@
  * arguments (which is usually the limits of the relocable BL image).
  *   x0 -  the start of the fixup region
  *   x1 -  the limit of the fixup region
- * These addresses have to be page (4KB aligned).
+ * These addresses have to be 4KB page aligned.
  * ---------------------------------------------------------------------------
  */
+
+/* Relocation codes */
+#define	R_AARCH64_NONE		0
+#define	R_AARCH64_RELATIVE	1027
+
 func fixup_gdt_reloc
 	mov	x6, x0
 	mov	x7, x1
 
-	/* Test if the limits are 4K aligned */
 #if ENABLE_ASSERTIONS
+	/* Test if the limits are 4KB aligned */
 	orr	x0, x0, x1
 	tst	x0, #(PAGE_SIZE_MASK)
 	ASM_ASSERT(eq)
@@ -505,7 +512,8 @@
 	 * fixup region.
 	 */
 	and	x2, x30, #~(PAGE_SIZE_MASK)
-	sub	x0, x2, x6	/* Diff(S) = Current Address - Compiled Address */
+	subs	x0, x2, x6	/* Diff(S) = Current Address - Compiled Address */
+	b.eq	3f		/* Diff(S) = 0. No relocation needed */
 
 	adrp	x1, __GOT_START__
 	add	x1, x1, :lo12:__GOT_START__
@@ -518,31 +526,32 @@
 	 * The new_addr is the address currently the binary is executing from
 	 * and old_addr is the address at compile time.
 	 */
-1:
-	ldr	x3, [x1]
+1:	ldr	x3, [x1]
+
 	/* Skip adding offset if address is < lower limit */
 	cmp	x3, x6
 	b.lo	2f
+
 	/* Skip adding offset if address is >= upper limit */
 	cmp	x3, x7
-	b.ge	2f
+	b.hs	2f
 	add	x3, x3, x0
 	str	x3, [x1]
-2:
-	add	x1, x1, #8
+
+2:	add	x1, x1, #8
 	cmp	x1, x2
 	b.lo	1b
 
 	/* Starting dynamic relocations. Use adrp/adr to get RELA_START and END */
-	adrp	x1, __RELA_START__
+3:	adrp	x1, __RELA_START__
 	add	x1, x1, :lo12:__RELA_START__
 	adrp	x2, __RELA_END__
 	add	x2, x2, :lo12:__RELA_END__
+
 	/*
 	 * According to ELF-64 specification, the RELA data structure is as
 	 * follows:
-	 *	typedef struct
-	 * 	{
+	 *	typedef struct {
 	 *		Elf64_Addr r_offset;
 	 *		Elf64_Xword r_info;
 	 *		Elf64_Sxword r_addend;
@@ -550,16 +559,19 @@
 	 *
 	 * r_offset is address of reference
 	 * r_info is symbol index and type of relocation (in this case
-	 * 0x403 which corresponds to R_AARCH64_RELATIVE).
+	 * code 1027 which corresponds to R_AARCH64_RELATIVE).
 	 * r_addend is constant part of expression.
 	 *
 	 * Size of Elf64_Rela structure is 24 bytes.
 	 */
-1:
-	/* Assert that the relocation type is R_AARCH64_RELATIVE */
+
+	/* Skip R_AARCH64_NONE entry with code 0 */
+1:	ldr	x3, [x1, #8]
+	cbz	x3, 2f
+
 #if ENABLE_ASSERTIONS
-	ldr	x3, [x1, #8]
-	cmp	x3, #0x403
+	/* Assert that the relocation type is R_AARCH64_RELATIVE */
+	cmp	x3, #R_AARCH64_RELATIVE
 	ASM_ASSERT(eq)
 #endif
 	ldr	x3, [x1]	/* r_offset */
@@ -569,9 +581,10 @@
 	/* Skip adding offset if r_addend is < lower limit */
 	cmp	x4, x6
 	b.lo	2f
+
 	/* Skip adding offset if r_addend entry is >= upper limit */
 	cmp	x4, x7
-	b.ge	2f
+	b.hs	2f
 
 	add	x4, x0, x4	/* Diff(S) + r_addend */
 	str	x4, [x3]
@@ -579,6 +592,22 @@
 2:	add	x1, x1, #24
 	cmp	x1, x2
 	b.lo	1b
-
 	ret
 endfunc fixup_gdt_reloc
+
+/*
+ * TODO: Currently only supports size of 4KB,
+ * support other sizes as well.
+ */
+func gpt_tlbi_by_pa
+#if ENABLE_ASSERTIONS
+	cmp	x1, #PAGE_SIZE_4KB
+	ASM_ASSERT(eq)
+	tst	x0, #(PAGE_SIZE_MASK)
+	ASM_ASSERT(eq)
+#endif
+	lsr	x0, x0, #FOUR_KB_SHIFT	/* 4KB size encoding is zero */
+	sys	#6, c8, c4, #3, x0 	/* TLBI RPAOS, <Xt> */
+	dsb	sy
+	ret
+endfunc gpt_tlbi_by_pa
diff --git a/lib/bl_aux_params/bl_aux_params.c b/lib/bl_aux_params/bl_aux_params.c
index 7a8115c..7f357b7 100644
--- a/lib/bl_aux_params/bl_aux_params.c
+++ b/lib/bl_aux_params/bl_aux_params.c
@@ -3,6 +3,8 @@
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <common/debug.h>
 #include <lib/coreboot.h>
@@ -25,7 +27,7 @@
 			break;
 #endif
 		default:
-			ERROR("Ignoring unknown BL aux parameter: 0x%llx",
+			ERROR("Ignoring unknown BL aux parameter: 0x%" PRIx64,
 			      p->type);
 			break;
 		}
diff --git a/lib/cpus/aarch32/cpu_helpers.S b/lib/cpus/aarch32/cpu_helpers.S
index 9b5d787..6ed800c 100644
--- a/lib/cpus/aarch32/cpu_helpers.S
+++ b/lib/cpus/aarch32/cpu_helpers.S
@@ -78,6 +78,10 @@
 	mov	r1, #CPU_PWR_DWN_OPS
 	add	r1, r1, r2, lsl #2
 	ldr	r1, [r0, r1]
+#if ENABLE_ASSERTIONS
+	cmp	r1, #0
+	ASM_ASSERT(ne)
+#endif
 	bx	r1
 endfunc prepare_cpu_pwr_dwn
 
@@ -146,6 +150,10 @@
 
 	/* Subtract the increment and offset to get the cpu-ops pointer */
 	sub	r0, r4, #(CPU_OPS_SIZE + CPU_MIDR)
+#if ENABLE_ASSERTIONS
+	cmp	r0, #0
+	ASM_ASSERT(ne)
+#endif
 error_exit:
 	bx	lr
 endfunc get_cpu_ops_ptr
@@ -224,7 +232,15 @@
 	 * function. If it's non-NULL, jump to the function in turn.
 	 */
 	bl	_cpu_data
+#if ENABLE_ASSERTIONS
+	cmp	r0, #0
+	ASM_ASSERT(ne)
+#endif
 	ldr	r1, [r0, #CPU_DATA_CPU_OPS_PTR]
+#if ENABLE_ASSERTIONS
+	cmp	r1, #0
+	ASM_ASSERT(ne)
+#endif
 	ldr	r0, [r1, #CPU_ERRATA_FUNC]
 	cmp	r0, #0
 	beq	1f
diff --git a/lib/cpus/aarch64/cortex_a510.S b/lib/cpus/aarch64/cortex_a510.S
new file mode 100644
index 0000000..3310322
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_a510.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_a510.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex A510 must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex A510 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_a510_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_A510_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_A510_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_A510_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_a510_core_pwr_dwn
+
+	/*
+	 * Errata printing function for Cortex A510. Must follow AAPCS.
+	 */
+#if REPORT_ERRATA
+func cortex_a510_errata_report
+	ret
+endfunc cortex_a510_errata_report
+#endif
+
+func cortex_a510_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_a510_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Cortex-A510 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_a510_regs, "aS"
+cortex_a510_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_a510_cpu_reg_dump
+	adr	x6, cortex_a510_regs
+	mrs	x8, CORTEX_A510_CPUECTLR_EL1
+	ret
+endfunc cortex_a510_cpu_reg_dump
+
+declare_cpu_ops cortex_a510, CORTEX_A510_MIDR, \
+	cortex_a510_reset_func, \
+	cortex_a510_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_a710.S b/lib/cpus/aarch64/cortex_a710.S
new file mode 100644
index 0000000..7d7fbd8
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_a710.S
@@ -0,0 +1,324 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_a710.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex A710 must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex A710 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+/* --------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 1987031.
+ * This applies to revision r0p0, r1p0 and r2p0 of Cortex-A710. It is still
+ * open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a710_1987031_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_1987031
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	ldr x0,=0x6
+	msr S3_6_c15_c8_0,x0
+	ldr x0,=0xF3A08002
+	msr S3_6_c15_c8_2,x0
+	ldr x0,=0xFFF0F7FE
+	msr S3_6_c15_c8_3,x0
+	ldr x0,=0x40000001003ff
+	msr S3_6_c15_c8_1,x0
+	ldr x0,=0x7
+	msr S3_6_c15_c8_0,x0
+	ldr x0,=0xBF200000
+	msr S3_6_c15_c8_2,x0
+	ldr x0,=0xFFEF0000
+	msr S3_6_c15_c8_3,x0
+	ldr x0,=0x40000001003f3
+	msr S3_6_c15_c8_1,x0
+	isb
+1:
+	ret	x17
+endfunc errata_a710_1987031_wa
+
+func check_errata_1987031
+	/* Applies to r0p0, r1p0 and r2p0 */
+	mov	x1, #0x20
+	b	cpu_rev_var_ls
+endfunc check_errata_1987031
+
+/* --------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 2081180.
+ * This applies to revision r0p0, r1p0 and r2p0 of Cortex-A710.
+ * It is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a710_2081180_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2081180
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	ldr	x0,=0x3
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xF3A08002
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFF0F7FE
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x10002001003FF
+	msr	S3_6_c15_c8_1,x0
+	ldr	x0,=0x4
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xBF200000
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFEF0000
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x10002001003F3
+	msr	S3_6_c15_c8_1,x0
+	isb
+1:
+	ret	x17
+endfunc errata_a710_2081180_wa
+
+func check_errata_2081180
+	/* Applies to r0p0, r1p0 and r2p0 */
+	mov	x1, #0x20
+	b	cpu_rev_var_ls
+endfunc check_errata_2081180
+
+/* ---------------------------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 2055002.
+ * This applies to revision r1p0, r2p0 of Cortex-A710 and is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------------
+ */
+func errata_a710_2055002_wa
+	/* Compare x0 against revision r2p0 */
+	mov	x17, x30
+	bl	check_errata_2055002
+	cbz	x0, 1f
+	mrs	x1, CORTEX_A710_CPUACTLR_EL1
+	orr	x1, x1, CORTEX_A710_CPUACTLR_EL1_BIT_46
+	msr	CORTEX_A710_CPUACTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_a710_2055002_wa
+
+func check_errata_2055002
+	/* Applies to r1p0, r2p0 */
+	mov	x1, #0x20
+	b	cpu_rev_var_ls
+endfunc check_errata_2055002
+
+/* -------------------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 2017096.
+ * This applies to revisions r0p0, r1p0 and r2p0 of Cortex-A710.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * -------------------------------------------------------------
+ */
+func errata_a710_2017096_wa
+	/* Compare x0 against revision r0p0 to r2p0 */
+	mov     x17, x30
+	bl      check_errata_2017096
+	cbz     x0, 1f
+	mrs     x1, CORTEX_A710_CPUECTLR_EL1
+	orr     x1, x1, CORTEX_A710_CPUECTLR_EL1_PFSTIDIS_BIT
+	msr     CORTEX_A710_CPUECTLR_EL1, x1
+
+1:
+	ret     x17
+endfunc errata_a710_2017096_wa
+
+func check_errata_2017096
+	/* Applies to r0p0, r1p0, r2p0 */
+	mov     x1, #0x20
+	b       cpu_rev_var_ls
+endfunc check_errata_2017096
+
+
+/* ---------------------------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 2083908.
+ * This applies to revision r2p0 of Cortex-A710 and is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------------
+ */
+func errata_a710_2083908_wa
+	/* Compare x0 against revision r2p0 */
+	mov	x17, x30
+	bl	check_errata_2083908
+	cbz	x0, 1f
+	mrs	x1, CORTEX_A710_CPUACTLR5_EL1
+	orr	x1, x1, CORTEX_A710_CPUACTLR5_EL1_BIT_13
+	msr	CORTEX_A710_CPUACTLR5_EL1, x1
+1:
+	ret	x17
+endfunc errata_a710_2083908_wa
+
+func check_errata_2083908
+	/* Applies to r2p0 */
+	mov	x1, #CPU_REV(2, 0)
+	mov	x2, #CPU_REV(2, 0)
+	b	cpu_rev_var_range
+endfunc check_errata_2083908
+
+/* ---------------------------------------------------------------------
+ * Errata Workaround for Cortex-A710 Erratum 2058056.
+ * This applies to revisions r0p0, r1p0 and r2p0 of Cortex-A710 and is still
+ * open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------------
+ */
+func errata_a710_2058056_wa
+	/* Compare x0 against revision r2p0 */
+	mov	x17, x30
+	bl	check_errata_2058056
+	cbz	x0, 1f
+	mrs	x1, CORTEX_A710_CPUECTLR2_EL1
+	mov	x0, #CORTEX_A710_CPUECTLR2_EL1_PF_MODE_CNSRV
+	bfi	x1, x0, #CPUECTLR2_EL1_PF_MODE_LSB, #CPUECTLR2_EL1_PF_MODE_WIDTH
+	msr	CORTEX_A710_CPUECTLR2_EL1, x1
+1:
+	ret	x17
+endfunc errata_a710_2058056_wa
+
+func check_errata_2058056
+	/* Applies to r0p0, r1p0 and r2p0 */
+	mov	x1, #0x20
+	b	cpu_rev_var_ls
+endfunc check_errata_2058056
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_a710_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_A710_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_A710_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_A710_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_a710_core_pwr_dwn
+
+#if REPORT_ERRATA
+	/*
+	 * Errata printing function for Cortex-A710. Must follow AAPCS.
+	 */
+func cortex_a710_errata_report
+	stp	x8, x30, [sp, #-16]!
+
+	bl	cpu_get_rev_var
+	mov	x8, x0
+
+	/*
+	 * Report all errata. The revision-variant information is passed to
+	 * checking functions of each errata.
+	 */
+	report_errata ERRATA_A710_1987031, cortex_a710, 1987031
+	report_errata ERRATA_A710_2081180, cortex_a710, 2081180
+	report_errata ERRATA_A710_2055002, cortex_a710, 2055002
+	report_errata ERRATA_A710_2017096, cortex_a710, 2017096
+	report_errata ERRATA_A710_2083908, cortex_a710, 2083908
+	report_errata ERRATA_A710_2058056, cortex_a710, 2058056
+
+	ldp	x8, x30, [sp], #16
+	ret
+endfunc cortex_a710_errata_report
+#endif
+
+func cortex_a710_reset_func
+	mov	x19, x30
+
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+
+	bl	cpu_get_rev_var
+	mov	x18, x0
+
+#if ERRATA_A710_1987031
+	mov	x0, x18
+	bl	errata_a710_1987031_wa
+#endif
+
+#if ERRATA_A710_2081180
+	mov	x0, x18
+	bl	errata_a710_2081180_wa
+#endif
+
+#if ERRATA_A710_2055002
+	mov	x0, x18
+	bl	errata_a710_2055002_wa
+#endif
+
+#if ERRATA_A710_2017096
+	mov	x0, x18
+	bl	errata_a710_2017096_wa
+#endif
+
+#if ERRATA_A710_2083908
+	mov	x0, x18
+	bl	errata_a710_2083908_wa
+#endif
+
+#if ERRATA_A710_2058056
+	mov	x0, x18
+	bl	errata_a710_2058056_wa
+#endif
+	isb
+	ret	x19
+endfunc cortex_a710_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Cortex-A710 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_a710_regs, "aS"
+cortex_a710_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_a710_cpu_reg_dump
+	adr	x6, cortex_a710_regs
+	mrs	x8, CORTEX_A710_CPUECTLR_EL1
+	ret
+endfunc cortex_a710_cpu_reg_dump
+
+declare_cpu_ops cortex_a710, CORTEX_A710_MIDR, \
+	cortex_a710_reset_func, \
+	cortex_a710_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_a76.S b/lib/cpus/aarch64/cortex_a76.S
index 98a1183..4f7f4bb 100644
--- a/lib/cpus/aarch64/cortex_a76.S
+++ b/lib/cpus/aarch64/cortex_a76.S
@@ -382,35 +382,6 @@
 endfunc check_errata_1791580
 
 	/* --------------------------------------------------
-	 * Errata Workaround for Cortex A76 Errata #1800710.
-	 * This applies to revision <= r4p0 of Cortex A76.
-	 * Inputs:
-	 * x0: variant[4:7] and revision[0:3] of current cpu.
-	 * Shall clobber: x0-x17
-	 * --------------------------------------------------
-	 */
-func errata_a76_1800710_wa
-	/* Compare x0 against revision <= r4p0 */
-	mov	x17, x30
-	bl	check_errata_1800710
-	cbz	x0, 1f
-
-	/* Disable allocation of splintered pages in the L2 TLB */
-	mrs	x1, CORTEX_A76_CPUECTLR_EL1
-	orr	x1, x1, CORTEX_A76_CPUECTLR_EL1_BIT_53
-	msr	CORTEX_A76_CPUECTLR_EL1, x1
-	isb
-1:
-	ret	x17
-endfunc errata_a76_1800710_wa
-
-func check_errata_1800710
-	/* Applies to everything <= r4p0 */
-	mov	x1, #0x40
-	b	cpu_rev_var_ls
-endfunc check_errata_1800710
-
-	/* --------------------------------------------------
 	 * Errata Workaround for Cortex A76 Errata #1262606,
 	 * #1275112, and #1868343.  #1262606 and #1275112
 	 * apply to revisions <= r3p0 and #1868343 applies to
@@ -459,6 +430,61 @@
 	b	cpu_rev_var_ls
 endfunc check_errata_1868343
 
+/* --------------------------------------------------
+ * Errata Workaround for A76 Erratum 1946160.
+ * This applies to revisions r3p0 - r4p1 of A76.
+ * It also exists in r0p0 - r2p0 but there is no fix
+ * in those revisions.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a76_1946160_wa
+	/* Compare x0 against revisions r3p0 - r4p1 */
+	mov	x17, x30
+	bl	check_errata_1946160
+	cbz	x0, 1f
+
+	mov	x0, #3
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3900002
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #4
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800082
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #5
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800200
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF003E0
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_a76_1946160_wa
+
+func check_errata_1946160
+	/* Applies to revisions r3p0 - r4p1. */
+	mov	x1, #0x30
+	mov	x2, #0x41
+	b	cpu_rev_var_range
+endfunc check_errata_1946160
+
 func check_errata_cve_2018_3639
 #if WORKAROUND_CVE_2018_3639
 	mov	x0, #ERRATA_APPLIES
@@ -538,9 +564,9 @@
 	bl	errata_a76_1791580_wa
 #endif
 
-#if ERRATA_A76_1800710
+#if ERRATA_A76_1946160
 	mov	x0, x18
-	bl	errata_a76_1800710_wa
+	bl	errata_a76_1946160_wa
 #endif
 
 #if WORKAROUND_CVE_2018_3639
@@ -624,9 +650,9 @@
 	report_errata ERRATA_A76_1275112, cortex_a76, 1275112
 	report_errata ERRATA_A76_1286807, cortex_a76, 1286807
 	report_errata ERRATA_A76_1791580, cortex_a76, 1791580
-	report_errata ERRATA_A76_1800710, cortex_a76, 1800710
 	report_errata ERRATA_A76_1165522, cortex_a76, 1165522
 	report_errata ERRATA_A76_1868343, cortex_a76, 1868343
+	report_errata ERRATA_A76_1946160, cortex_a76, 1946160
 	report_errata WORKAROUND_CVE_2018_3639, cortex_a76, cve_2018_3639
 	report_errata ERRATA_DSU_798953, cortex_a76, dsu_798953
 	report_errata ERRATA_DSU_936184, cortex_a76, dsu_936184
diff --git a/lib/cpus/aarch64/cortex_a77.S b/lib/cpus/aarch64/cortex_a77.S
index 04a610e..8c8f4d3 100644
--- a/lib/cpus/aarch64/cortex_a77.S
+++ b/lib/cpus/aarch64/cortex_a77.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -86,35 +86,6 @@
 endfunc check_errata_1508412_0
 
 	/* --------------------------------------------------
-	 * Errata Workaround for Cortex A77 Errata #1800714.
-	 * This applies to revision <= r1p1 of Cortex A77.
-	 * Inputs:
-	 * x0: variant[4:7] and revision[0:3] of current cpu.
-	 * Shall clobber: x0-x17
-	 * --------------------------------------------------
-	 */
-func errata_a77_1800714_wa
-	/* Compare x0 against revision <= r1p1 */
-	mov	x17, x30
-	bl	check_errata_1800714
-	cbz	x0, 1f
-
-	/* Disable allocation of splintered pages in the L2 TLB */
-	mrs	x1, CORTEX_A77_CPUECTLR_EL1
-	orr	x1, x1, CORTEX_A77_CPUECTLR_EL1_BIT_53
-	msr	CORTEX_A77_CPUECTLR_EL1, x1
-	isb
-1:
-	ret	x17
-endfunc errata_a77_1800714_wa
-
-func check_errata_1800714
-	/* Applies to everything <= r1p1 */
-	mov	x1, #0x11
-	b	cpu_rev_var_ls
-endfunc check_errata_1800714
-
-	/* --------------------------------------------------
 	 * Errata Workaround for Cortex A77 Errata #1925769.
 	 * This applies to revision <= r1p1 of Cortex A77.
 	 * Inputs:
@@ -143,6 +114,86 @@
 	b	cpu_rev_var_ls
 endfunc check_errata_1925769
 
+	/* --------------------------------------------------
+	 * Errata Workaround for Cortex A77 Errata #1946167.
+	 * This applies to revision <= r1p1 of Cortex A77.
+	 * Inputs:
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_a77_1946167_wa
+	/* Compare x0 against revision <= r1p1 */
+	mov	x17, x30
+	bl	check_errata_1946167
+	cbz	x0, 1f
+
+	ldr	x0,=0x4
+	msr	CORTEX_A77_CPUPSELR_EL3,x0
+	ldr	x0,=0x10E3900002
+	msr	CORTEX_A77_CPUPOR_EL3,x0
+	ldr	x0,=0x10FFF00083
+	msr	CORTEX_A77_CPUPMR_EL3,x0
+	ldr	x0,=0x2001003FF
+	msr	CORTEX_A77_CPUPCR_EL3,x0
+
+	ldr	x0,=0x5
+	msr	CORTEX_A77_CPUPSELR_EL3,x0
+	ldr	x0,=0x10E3800082
+	msr	CORTEX_A77_CPUPOR_EL3,x0
+	ldr	x0,=0x10FFF00083
+	msr	CORTEX_A77_CPUPMR_EL3,x0
+	ldr	x0,=0x2001003FF
+	msr	CORTEX_A77_CPUPCR_EL3,x0
+
+	ldr	x0,=0x6
+	msr	CORTEX_A77_CPUPSELR_EL3,x0
+	ldr	x0,=0x10E3800200
+	msr	CORTEX_A77_CPUPOR_EL3,x0
+	ldr	x0,=0x10FFF003E0
+	msr	CORTEX_A77_CPUPMR_EL3,x0
+	ldr	x0,=0x2001003FF
+	msr	CORTEX_A77_CPUPCR_EL3,x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_a77_1946167_wa
+
+func check_errata_1946167
+	/* Applies to everything <= r1p1 */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_1946167
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Cortex A77 Errata #1791578.
+	 * This applies to revisions r0p0, r1p0, and r1p1 and is still open.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_a77_1791578_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1791578
+	cbz	x0, 1f
+
+	/* Set bit 2 in ACTLR2_EL1 */
+	mrs     x1, CORTEX_A77_ACTLR2_EL1
+	orr	x1, x1, #CORTEX_A77_ACTLR2_EL1_BIT_2
+	msr     CORTEX_A77_ACTLR2_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_a77_1791578_wa
+
+func check_errata_1791578
+	/* Applies to r0p0, r1p0, and r1p1 right now */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_1791578
+
 	/* -------------------------------------------------
 	 * The CPU Ops reset function for Cortex-A77.
 	 * Shall clobber: x0-x19
@@ -158,16 +209,21 @@
 	bl	errata_a77_1508412_wa
 #endif
 
-#if ERRATA_A77_1800714
-	mov	x0, x18
-	bl	errata_a77_1800714_wa
-#endif
-
 #if ERRATA_A77_1925769
 	mov	x0, x18
 	bl	errata_a77_1925769_wa
 #endif
 
+#if ERRATA_A77_1946167
+	mov	x0, x18
+	bl	errata_a77_1946167_wa
+#endif
+
+#if ERRATA_A77_1791578
+	mov	x0, x18
+	bl	errata_a77_1791578_wa
+#endif
+
 	ret	x19
 endfunc cortex_a77_reset_func
 
@@ -202,8 +258,9 @@
 	 * checking functions of each errata.
 	 */
 	report_errata ERRATA_A77_1508412, cortex_a77, 1508412
-	report_errata ERRATA_A77_1800714, cortex_a77, 1800714
 	report_errata ERRATA_A77_1925769, cortex_a77, 1925769
+	report_errata ERRATA_A77_1946167, cortex_a77, 1946167
+	report_errata ERRATA_A77_1791578, cortex_a77, 1791578
 
 	ldp	x8, x30, [sp], #16
 	ret
diff --git a/lib/cpus/aarch64/cortex_a78.S b/lib/cpus/aarch64/cortex_a78.S
index 9914f12..a1288ba 100644
--- a/lib/cpus/aarch64/cortex_a78.S
+++ b/lib/cpus/aarch64/cortex_a78.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -31,7 +31,7 @@
 	bl	check_errata_1688305
 	cbz	x0, 1f
 	mrs     x1, CORTEX_A78_ACTLR2_EL1
-	orr	x1, x1, CORTEX_A78_ACTLR2_EL1_BIT_1
+	orr	x1, x1, #CORTEX_A78_ACTLR2_EL1_BIT_1
 	msr     CORTEX_A78_ACTLR2_EL1, x1
 	isb
 1:
@@ -44,6 +44,225 @@
 	b	cpu_rev_var_ls
 endfunc check_errata_1688305
 
+/* --------------------------------------------------
+ * Errata Workaround for Cortex A78 Errata #1941498.
+ * This applies to revisions r0p0, r1p0, and r1p1.
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_1941498_wa
+	/* Compare x0 against revision <= r1p1 */
+	mov	x17, x30
+	bl	check_errata_1941498
+	cbz	x0, 1f
+
+	/* Set bit 8 in ECTLR_EL1 */
+	mrs	x1, CORTEX_A78_CPUECTLR_EL1
+	orr	x1, x1, #CORTEX_A78_CPUECTLR_EL1_BIT_8
+	msr	CORTEX_A78_CPUECTLR_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_a78_1941498_wa
+
+func check_errata_1941498
+	/* Check for revision <= r1p1, might need to be updated later. */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_1941498
+
+/* --------------------------------------------------
+ * Errata Workaround for A78 Erratum 1951500.
+ * This applies to revisions r1p0 and r1p1 of A78.
+ * The issue also exists in r0p0 but there is no fix
+ * in that revision.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_1951500_wa
+	/* Compare x0 against revisions r1p0 - r1p1 */
+	mov	x17, x30
+	bl	check_errata_1951500
+	cbz	x0, 1f
+
+	msr	S3_6_c15_c8_0, xzr
+	ldr	x0, =0x10E3900002
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	mov	x0, #1
+	msr	S3_6_c15_c8_0, x0
+	ldr	x0, =0x10E3800082
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	mov	x0, #2
+	msr	S3_6_c15_c8_0, x0
+	ldr	x0, =0x10E3800200
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF003E0
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_a78_1951500_wa
+
+func check_errata_1951500
+	/* Applies to revisions r1p0 and r1p1. */
+	mov	x1, #CPU_REV(1, 0)
+	mov	x2, #CPU_REV(1, 1)
+	b	cpu_rev_var_range
+endfunc check_errata_1951500
+
+/* --------------------------------------------------
+ * Errata Workaround for Cortex A78 Errata #1821534.
+ * This applies to revisions r0p0 and r1p0.
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_1821534_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_1821534
+	cbz	x0, 1f
+
+	/* Set bit 2 in ACTLR2_EL1 */
+	mrs     x1, CORTEX_A78_ACTLR2_EL1
+	orr	x1, x1, #CORTEX_A78_ACTLR2_EL1_BIT_2
+	msr     CORTEX_A78_ACTLR2_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_a78_1821534_wa
+
+func check_errata_1821534
+	/* Applies to r0p0 and r1p0 */
+	mov	x1, #0x10
+	b	cpu_rev_var_ls
+endfunc check_errata_1821534
+
+/* --------------------------------------------------
+ * Errata Workaround for Cortex A78 Errata 1952683.
+ * This applies to revision r0p0.
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_1952683_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_1952683
+	cbz	x0, 1f
+
+	ldr	x0,=0x5
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xEEE10A10
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFEF0FFF
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x0010F000
+	msr	S3_6_c15_c8_4,x0
+	ldr	x0,=0x0010F000
+	msr	S3_6_c15_c8_5,x0
+	ldr	x0,=0x40000080023ff
+	msr	S3_6_c15_c8_1,x0
+	ldr	x0,=0x6
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xEE640F34
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFEF0FFF
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x40000080023ff
+	msr	S3_6_c15_c8_1,x0
+	isb
+1:
+	ret	x17
+endfunc errata_a78_1952683_wa
+
+func check_errata_1952683
+	/* Applies to r0p0 only */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_1952683
+
+/* --------------------------------------------------
+ * Errata Workaround for Cortex A78 Errata 2132060.
+ * This applies to revisions r0p0, r1p0, r1p1, and r1p2.
+ * It is still open.
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_a78_2132060_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2132060
+	cbz	x0, 1f
+
+	/* Apply the workaround. */
+	mrs	x1, CORTEX_A78_CPUECTLR_EL1
+	mov	x0, #CORTEX_A78_CPUECTLR_EL1_PF_MODE_CNSRV
+	bfi	x1, x0, #CPUECTLR_EL1_PF_MODE_LSB, #CPUECTLR_EL1_PF_MODE_WIDTH
+	msr	CORTEX_A78_CPUECTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_a78_2132060_wa
+
+func check_errata_2132060
+	/* Applies to r0p0, r0p1, r1p1, and r1p2 */
+	mov	x1, #0x12
+	b	cpu_rev_var_ls
+endfunc check_errata_2132060
+
+/* --------------------------------------------------------------------
+ * Errata Workaround for A78 Erratum 2242635.
+ * This applies to revisions r1p0, r1p1, and r1p2 of the Cortex A78
+ * processor and is still open.
+ * The issue also exists in r0p0 but there is no fix in that revision.
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------------------------
+ */
+func errata_a78_2242635_wa
+	/* Compare x0 against revisions r1p0 - r1p2 */
+	mov	x17, x30
+	bl	check_errata_2242635
+	cbz	x0, 1f
+
+	ldr	x0, =0x5
+	msr	S3_6_c15_c8_0, x0 /* CPUPSELR_EL3 */
+	ldr	x0, =0x10F600E000
+	msr	S3_6_c15_c8_2, x0 /* CPUPOR_EL3 */
+	ldr	x0, =0x10FF80E000
+	msr	S3_6_c15_c8_3, x0 /* CPUPMR_EL3 */
+	ldr	x0, =0x80000000003FF
+	msr	S3_6_c15_c8_1, x0 /* CPUPCR_EL3 */
+
+	isb
+1:
+	ret	x17
+endfunc errata_a78_2242635_wa
+
+func check_errata_2242635
+	/* Applies to revisions r1p0 through r1p2. */
+	mov	x1, #CPU_REV(1, 0)
+	mov	x2, #CPU_REV(1, 2)
+	b	cpu_rev_var_range
+endfunc check_errata_2242635
+
 	/* -------------------------------------------------
 	 * The CPU Ops reset function for Cortex-A78
 	 * -------------------------------------------------
@@ -58,6 +277,36 @@
 	bl	errata_a78_1688305_wa
 #endif
 
+#if ERRATA_A78_1941498
+	mov     x0, x18
+	bl	errata_a78_1941498_wa
+#endif
+
+#if ERRATA_A78_1951500
+	mov	x0, x18
+	bl	errata_a78_1951500_wa
+#endif
+
+#if ERRATA_A78_1821534
+	mov	x0, x18
+	bl	errata_a78_1821534_wa
+#endif
+
+#if ERRATA_A78_1952683
+	mov	x0, x18
+	bl	errata_a78_1952683_wa
+#endif
+
+#if ERRATA_A78_2132060
+	mov	x0, x18
+	bl	errata_a78_2132060_wa
+#endif
+
+#if ERRATA_A78_2242635
+	mov	x0, x18
+	bl	errata_a78_2242635_wa
+#endif
+
 #if ENABLE_AMU
 	/* Make sure accesses from EL0/EL1 and EL2 are not trapped to EL3 */
 	mrs	x0, actlr_el3
@@ -113,6 +362,12 @@
 	 * checking functions of each errata.
 	 */
 	report_errata ERRATA_A78_1688305, cortex_a78, 1688305
+	report_errata ERRATA_A78_1941498, cortex_a78, 1941498
+	report_errata ERRATA_A78_1951500, cortex_a78, 1951500
+	report_errata ERRATA_A78_1821534, cortex_a78, 1821534
+	report_errata ERRATA_A78_1952683, cortex_a78, 1952683
+	report_errata ERRATA_A78_2132060, cortex_a78, 2132060
+	report_errata ERRATA_A78_2242635, cortex_a78, 2242635
 
 	ldp	x8, x30, [sp], #16
 	ret
diff --git a/lib/cpus/aarch64/cortex_a78_ae.S b/lib/cpus/aarch64/cortex_a78_ae.S
index 9aff9ac..421c174 100644
--- a/lib/cpus/aarch64/cortex_a78_ae.S
+++ b/lib/cpus/aarch64/cortex_a78_ae.S
@@ -1,5 +1,6 @@
 /*
  * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,12 +17,108 @@
 #error "cortex_a78_ae must be compiled with HW_ASSISTED_COHERENCY enabled"
 #endif
 
+/* --------------------------------------------------
+ * Errata Workaround for A78 AE Erratum 1941500.
+ * This applies to revisions r0p0 and r0p1 of A78 AE.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_ae_1941500_wa
+	/* Compare x0 against revisions r0p0 - r0p1 */
+	mov	x17, x30
+	bl	check_errata_1941500
+	cbz	x0, 1f
+
+	/* Set bit 8 in ECTLR_EL1 */
+	mrs	x0, CORTEX_A78_AE_CPUECTLR_EL1
+	bic	x0, x0, #CORTEX_A78_AE_CPUECTLR_EL1_BIT_8
+	msr	CORTEX_A78_AE_CPUECTLR_EL1, x0
+	isb
+1:
+	ret	x17
+endfunc errata_a78_ae_1941500_wa
+
+func check_errata_1941500
+	/* Applies to revisions r0p0 and r0p1. */
+	mov	x1, #CPU_REV(0, 0)
+	mov	x2, #CPU_REV(0, 1)
+	b	cpu_rev_var_range
+endfunc check_errata_1941500
+
+/* --------------------------------------------------
+ * Errata Workaround for A78 AE Erratum 1951502.
+ * This applies to revisions r0p0 and r0p1 of A78 AE.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_a78_ae_1951502_wa
+	/* Compare x0 against revisions r0p0 - r0p1 */
+	mov	x17, x30
+	bl	check_errata_1951502
+	cbz	x0, 1f
+
+	msr	S3_6_c15_c8_0, xzr
+	ldr	x0, =0x10E3900002
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	mov	x0, #1
+	msr	S3_6_c15_c8_0, x0
+	ldr	x0, =0x10E3800082
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	mov	x0, #2
+	msr	S3_6_c15_c8_0, x0
+	ldr	x0, =0x10E3800200
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FFF003E0
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_c15_c8_1, x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_a78_ae_1951502_wa
+
+func check_errata_1951502
+	/* Applies to revisions r0p0 and r0p1. */
+	mov	x1, #CPU_REV(0, 0)
+	mov	x2, #CPU_REV(0, 1)
+	b	cpu_rev_var_range
+endfunc check_errata_1951502
+
 	/* -------------------------------------------------
 	 * The CPU Ops reset function for Cortex-A78-AE
 	 * -------------------------------------------------
 	 */
-#if ENABLE_AMU
 func cortex_a78_ae_reset_func
+	mov	x19, x30
+	bl	cpu_get_rev_var
+	mov	x18, x0
+
+#if ERRATA_A78_AE_1941500
+	mov	x0, x18
+	bl	errata_a78_ae_1941500_wa
+#endif
+
+#if ERRATA_A78_AE_1951502
+	mov	x0, x18
+	bl	errata_a78_ae_1951502_wa
+#endif
+
+#if ENABLE_AMU
 	/* Make sure accesses from EL0/EL1 and EL2 are not trapped to EL3 */
 	mrs	x0, actlr_el3
 	bic	x0, x0, #CORTEX_A78_ACTLR_TAM_BIT
@@ -39,11 +136,12 @@
 	/* Enable group1 counters */
 	mov	x0, #CORTEX_A78_AMU_GROUP1_MASK
 	msr	CPUAMCNTENSET1_EL0, x0
+#endif
+
 	isb
 
-	ret
+	ret	x19
 endfunc cortex_a78_ae_reset_func
-#endif
 
 	/* -------------------------------------------------------
 	 * HW will do the cache maintenance while powering down
@@ -66,6 +164,19 @@
 	 */
 #if REPORT_ERRATA
 func cortex_a78_ae_errata_report
+	stp	x8, x30, [sp, #-16]!
+
+	bl	cpu_get_rev_var
+	mov	x8, x0
+
+	/*
+	 * Report all errata. The revision-variant information is passed to
+	 * checking functions of each errata.
+	 */
+	report_errata ERRATA_A78_AE_1941500, cortex_a78_ae, 1941500
+	report_errata ERRATA_A78_AE_1951502, cortex_a78_ae, 1951502
+
+	ldp	x8, x30, [sp], #16
 	ret
 endfunc cortex_a78_ae_errata_report
 #endif
@@ -89,12 +200,6 @@
 	ret
 endfunc cortex_a78_ae_cpu_reg_dump
 
-#if ENABLE_AMU
-#define A78_AE_RESET_FUNC cortex_a78_ae_reset_func
-#else
-#define A78_AE_RESET_FUNC CPU_NO_RESET_FUNC
-#endif
-
 declare_cpu_ops cortex_a78_ae, CORTEX_A78_AE_MIDR, \
-	A78_AE_RESET_FUNC, \
+	cortex_a78_ae_reset_func, \
 	cortex_a78_ae_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_a78c.S b/lib/cpus/aarch64/cortex_a78c.S
new file mode 100644
index 0000000..1b170fe
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_a78c.S
@@ -0,0 +1,65 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_a78c.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "cortex_a78c must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_a78c_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_A78C_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_A78C_CPUPWRCTLR_EL1_CORE_PWRDN_EN_BIT
+	msr	CORTEX_A78C_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_a78c_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Cortex A78C. Must follow AAPCS.
+ */
+func cortex_a78c_errata_report
+        ret
+endfunc cortex_a78c_errata_report
+#endif
+
+	/* ---------------------------------------------
+	 * This function provides cortex_a78c 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_a78c_regs, "aS"
+cortex_a78c_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_a78c_cpu_reg_dump
+	adr	x6, cortex_a78c_regs
+	mrs	x8, CORTEX_A78C_CPUECTLR_EL1
+	ret
+endfunc cortex_a78c_cpu_reg_dump
+
+declare_cpu_ops cortex_a78c, CORTEX_A78C_MIDR, \
+	CPU_NO_RESET_FUNC, \
+	cortex_a78c_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_hayes.S b/lib/cpus/aarch64/cortex_hayes.S
new file mode 100644
index 0000000..445a691
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_hayes.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_hayes.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex Hayes must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex Hayes supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_hayes_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_HAYES_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_HAYES_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_HAYES_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_hayes_core_pwr_dwn
+
+	/*
+	 * Errata printing function for Cortex Hayes. Must follow AAPCS.
+	 */
+#if REPORT_ERRATA
+func cortex_hayes_errata_report
+	ret
+endfunc cortex_hayes_errata_report
+#endif
+
+func cortex_hayes_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_hayes_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Cortex Hayes 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_hayes_regs, "aS"
+cortex_hayes_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_hayes_cpu_reg_dump
+	adr	x6, cortex_hayes_regs
+	mrs	x8, CORTEX_HAYES_CPUECTLR_EL1
+	ret
+endfunc cortex_hayes_cpu_reg_dump
+
+declare_cpu_ops cortex_hayes, CORTEX_HAYES_MIDR, \
+	cortex_hayes_reset_func, \
+	cortex_hayes_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_hunter.S b/lib/cpus/aarch64/cortex_hunter.S
new file mode 100644
index 0000000..2ab4296
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_hunter.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_hunter.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex Hunter must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex Hunter supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+func cortex_hunter_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_hunter_reset_func
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_hunter_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_HUNTER_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_HUNTER_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_HUNTER_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_hunter_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Cortex Hunter. Must follow AAPCS.
+ */
+func cortex_hunter_errata_report
+	ret
+endfunc cortex_hunter_errata_report
+#endif
+
+	/* ---------------------------------------------
+	 * This function provides Cortex Hunter-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_hunter_regs, "aS"
+cortex_hunter_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_hunter_cpu_reg_dump
+	adr	x6, cortex_hunter_regs
+	mrs	x8, CORTEX_HUNTER_CPUECTLR_EL1
+	ret
+endfunc cortex_hunter_cpu_reg_dump
+
+declare_cpu_ops cortex_hunter, CORTEX_HUNTER_MIDR, \
+	cortex_hunter_reset_func, \
+	cortex_hunter_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_klein.S b/lib/cpus/aarch64/cortex_klein.S
deleted file mode 100644
index d3a8ab4..0000000
--- a/lib/cpus/aarch64/cortex_klein.S
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <common/bl_common.h>
-#include <cortex_klein.h>
-#include <cpu_macros.S>
-#include <plat_macros.S>
-
-/* Hardware handled coherency */
-#if HW_ASSISTED_COHERENCY == 0
-#error "Cortex Klein must be compiled with HW_ASSISTED_COHERENCY enabled"
-#endif
-
-/* 64-bit only core */
-#if CTX_INCLUDE_AARCH32_REGS == 1
-#error "Cortex Klein supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
-#endif
-
-	/* ----------------------------------------------------
-	 * HW will do the cache maintenance while powering down
-	 * ----------------------------------------------------
-	 */
-func cortex_klein_core_pwr_dwn
-	/* ---------------------------------------------------
-	 * Enable CPU power down bit in power control register
-	 * ---------------------------------------------------
-	 */
-	mrs	x0, CORTEX_KLEIN_CPUPWRCTLR_EL1
-	orr	x0, x0, #CORTEX_KLEIN_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
-	msr	CORTEX_KLEIN_CPUPWRCTLR_EL1, x0
-	isb
-	ret
-endfunc cortex_klein_core_pwr_dwn
-
-	/*
-	 * Errata printing function for Cortex Klein. Must follow AAPCS.
-	 */
-#if REPORT_ERRATA
-func cortex_klein_errata_report
-	ret
-endfunc cortex_klein_errata_report
-#endif
-
-func cortex_klein_reset_func
-	/* Disable speculative loads */
-	msr	SSBS, xzr
-	isb
-	ret
-endfunc cortex_klein_reset_func
-
-	/* ---------------------------------------------
-	 * This function provides Cortex-Klein 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_klein_regs, "aS"
-cortex_klein_regs:  /* The ascii list of register names to be reported */
-	.asciz	"cpuectlr_el1", ""
-
-func cortex_klein_cpu_reg_dump
-	adr	x6, cortex_klein_regs
-	mrs	x8, CORTEX_KLEIN_CPUECTLR_EL1
-	ret
-endfunc cortex_klein_cpu_reg_dump
-
-declare_cpu_ops cortex_klein, CORTEX_KLEIN_MIDR, \
-	cortex_klein_reset_func, \
-	cortex_klein_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_makalu.S b/lib/cpus/aarch64/cortex_makalu.S
new file mode 100644
index 0000000..98c7d6d
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_makalu.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_makalu.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex Makalu must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex Makalu supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+func cortex_makalu_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_makalu_reset_func
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_makalu_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_MAKALU_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_MAKALU_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_MAKALU_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_makalu_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Cortex Makalu. Must follow AAPCS.
+ */
+func cortex_makalu_errata_report
+	ret
+endfunc cortex_makalu_errata_report
+#endif
+
+	/* ---------------------------------------------
+	 * This function provides Cortex Makalu-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_makalu_regs, "aS"
+cortex_makalu_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_makalu_cpu_reg_dump
+	adr	x6, cortex_makalu_regs
+	mrs	x8, CORTEX_MAKALU_CPUECTLR_EL1
+	ret
+endfunc cortex_makalu_cpu_reg_dump
+
+declare_cpu_ops cortex_makalu, CORTEX_MAKALU_MIDR, \
+	cortex_makalu_reset_func, \
+	cortex_makalu_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_makalu_elp_arm.S b/lib/cpus/aarch64/cortex_makalu_elp_arm.S
new file mode 100644
index 0000000..fbbf205
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_makalu_elp_arm.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_makalu_elp_arm.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex Makalu ELP must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex Makalu ELP supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_makalu_elp_arm_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_MAKALU_ELP_ARM_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_MAKALU_ELP_ARM_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_MAKALU_ELP_ARM_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_makalu_elp_arm_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Cortex Makalu ELP. Must follow AAPCS.
+ */
+func cortex_makalu_elp_arm_errata_report
+	ret
+endfunc cortex_makalu_elp_arm_errata_report
+#endif
+
+func cortex_makalu_elp_arm_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_makalu_elp_arm_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Cortex Makalu ELP-
+	 * 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_makalu_elp_arm_regs, "aS"
+cortex_makalu_elp_arm_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_makalu_elp_arm_cpu_reg_dump
+	adr	x6, cortex_makalu_elp_arm_regs
+	mrs	x8, CORTEX_MAKALU_ELP_ARM_CPUECTLR_EL1
+	ret
+endfunc cortex_makalu_elp_arm_cpu_reg_dump
+
+declare_cpu_ops cortex_makalu_elp_arm, CORTEX_MAKALU_ELP_ARM_MIDR, \
+	cortex_makalu_elp_arm_reset_func, \
+	cortex_makalu_elp_arm_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_matterhorn.S b/lib/cpus/aarch64/cortex_matterhorn.S
deleted file mode 100644
index 4156f3c..0000000
--- a/lib/cpus/aarch64/cortex_matterhorn.S
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <common/bl_common.h>
-#include <cortex_matterhorn.h>
-#include <cpu_macros.S>
-#include <plat_macros.S>
-
-/* Hardware handled coherency */
-#if HW_ASSISTED_COHERENCY == 0
-#error "Cortex Matterhorn must be compiled with HW_ASSISTED_COHERENCY enabled"
-#endif
-
-/* 64-bit only core */
-#if CTX_INCLUDE_AARCH32_REGS == 1
-#error "Cortex Matterhorn supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
-#endif
-
-	/* ----------------------------------------------------
-	 * HW will do the cache maintenance while powering down
-	 * ----------------------------------------------------
-	 */
-func cortex_matterhorn_core_pwr_dwn
-	/* ---------------------------------------------------
-	 * Enable CPU power down bit in power control register
-	 * ---------------------------------------------------
-	 */
-	mrs	x0, CORTEX_MATTERHORN_CPUPWRCTLR_EL1
-	orr	x0, x0, #CORTEX_MATTERHORN_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
-	msr	CORTEX_MATTERHORN_CPUPWRCTLR_EL1, x0
-	isb
-	ret
-endfunc cortex_matterhorn_core_pwr_dwn
-
-	/*
-	 * Errata printing function for Cortex Matterhorn. Must follow AAPCS.
-	 */
-#if REPORT_ERRATA
-func cortex_matterhorn_errata_report
-	ret
-endfunc cortex_matterhorn_errata_report
-#endif
-
-func cortex_matterhorn_reset_func
-	/* Disable speculative loads */
-	msr	SSBS, xzr
-	isb
-	ret
-endfunc cortex_matterhorn_reset_func
-
-	/* ---------------------------------------------
-	 * This function provides Cortex-Matterhorn 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_matterhorn_regs, "aS"
-cortex_matterhorn_regs:  /* The ascii list of register names to be reported */
-	.asciz	"cpuectlr_el1", ""
-
-func cortex_matterhorn_cpu_reg_dump
-	adr	x6, cortex_matterhorn_regs
-	mrs	x8, CORTEX_MATTERHORN_CPUECTLR_EL1
-	ret
-endfunc cortex_matterhorn_cpu_reg_dump
-
-declare_cpu_ops cortex_matterhorn, CORTEX_MATTERHORN_MIDR, \
-	cortex_matterhorn_reset_func, \
-	cortex_matterhorn_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cortex_x2.S b/lib/cpus/aarch64/cortex_x2.S
new file mode 100644
index 0000000..87a9bdf
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_x2.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <cortex_x2.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Cortex X2 must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Cortex X2 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func cortex_x2_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, CORTEX_X2_CPUPWRCTLR_EL1
+	orr	x0, x0, #CORTEX_X2_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	CORTEX_X2_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_x2_core_pwr_dwn
+
+	/*
+	 * Errata printing function for Cortex X2. Must follow AAPCS.
+	 */
+#if REPORT_ERRATA
+func cortex_x2_errata_report
+	ret
+endfunc cortex_x2_errata_report
+#endif
+
+func cortex_x2_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc cortex_x2_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Cortex X2 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_x2_regs, "aS"
+cortex_x2_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_x2_cpu_reg_dump
+	adr	x6, cortex_x2_regs
+	mrs	x8, CORTEX_X2_CPUECTLR_EL1
+	ret
+endfunc cortex_x2_cpu_reg_dump
+
+declare_cpu_ops cortex_x2, CORTEX_X2_MIDR, \
+	cortex_x2_reset_func, \
+	cortex_x2_core_pwr_dwn
diff --git a/lib/cpus/aarch64/cpu_helpers.S b/lib/cpus/aarch64/cpu_helpers.S
index 730b09b..bd8f85f 100644
--- a/lib/cpus/aarch64/cpu_helpers.S
+++ b/lib/cpus/aarch64/cpu_helpers.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -144,7 +144,7 @@
 	 * If cpu_ops for the MIDR_EL1 cannot be found and
 	 * SUPPORT_UNKNOWN_MPID is enabled, it will try to look for a
 	 * default cpu_ops with an MIDR value of 0.
-	 * (Implementation number 0x0 should be reseverd for software use
+	 * (Implementation number 0x0 should be reserved for software use
 	 * and therefore no clashes should happen with that default value).
 	 *
 	 * Return :
diff --git a/lib/cpus/aarch64/neoverse_demeter.S b/lib/cpus/aarch64/neoverse_demeter.S
new file mode 100644
index 0000000..f43c18b
--- /dev/null
+++ b/lib/cpus/aarch64/neoverse_demeter.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <neoverse_demeter.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Neoverse Demeter must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Neoverse Demeter supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+	/* ----------------------------------------------------
+	 * HW will do the cache maintenance while powering down
+	 * ----------------------------------------------------
+	 */
+func neoverse_demeter_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, NEOVERSE_DEMETER_CPUPWRCTLR_EL1
+	orr	x0, x0, #NEOVERSE_DEMETER_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	NEOVERSE_DEMETER_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc neoverse_demeter_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Neoverse Demeter. Must follow AAPCS.
+ */
+func neoverse_demeter_errata_report
+	ret
+endfunc neoverse_demeter_errata_report
+#endif
+
+func neoverse_demeter_reset_func
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+	isb
+	ret
+endfunc neoverse_demeter_reset_func
+
+	/* ---------------------------------------------
+	 * This function provides Neoverse Demeter-
+	 * 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.neoverse_demeter_regs, "aS"
+neoverse_demeter_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func neoverse_demeter_cpu_reg_dump
+	adr	x6, neoverse_demeter_regs
+	mrs	x8, NEOVERSE_DEMETER_CPUECTLR_EL1
+	ret
+endfunc neoverse_demeter_cpu_reg_dump
+
+declare_cpu_ops neoverse_demeter, NEOVERSE_DEMETER_MIDR, \
+	neoverse_demeter_reset_func, \
+	neoverse_demeter_core_pwr_dwn
diff --git a/lib/cpus/aarch64/neoverse_n1.S b/lib/cpus/aarch64/neoverse_n1.S
index 03ee472..9c97cf6 100644
--- a/lib/cpus/aarch64/neoverse_n1.S
+++ b/lib/cpus/aarch64/neoverse_n1.S
@@ -1,15 +1,15 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <arch.h>
 #include <asm_macros.S>
-#include <neoverse_n1.h>
 #include <cpuamu.h>
 #include <cpu_macros.S>
 #include <context.h>
+#include <neoverse_n1.h>
 
 /* Hardware handled coherency */
 #if HW_ASSISTED_COHERENCY == 0
@@ -22,19 +22,6 @@
 #endif
 
 	.global neoverse_n1_errata_ic_trap_handler
-	.global is_scu_present_in_dsu
-
-/*
- * Check DSU is configured with SCU and L3 unit
- * 1-> SCU present
- * 0-> SCU not present
- */
-func is_scu_present_in_dsu
-	mrs	x0, CPUCFR_EL1
-	ubfx	x0, x0, #SCU_SHIFT, #1
-	eor	x0, x0, #1
-	ret
-endfunc is_scu_present_in_dsu
 
 /* --------------------------------------------------
  * Errata Workaround for Neoverse N1 Erratum 1043202.
@@ -420,6 +407,63 @@
 	b	cpu_rev_var_ls
 endfunc check_errata_1868343
 
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse N1 Errata #1946160.
+	 * This applies to revisions r3p0, r3p1, r4p0, and
+	 * r4p1 of Neoverse N1. It also exists in r0p0, r1p0,
+	 * and r2p0 but there is no fix in these revisions.
+	 * Inputs:
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_n1_1946160_wa
+	/*
+	 * Compare x0 against r3p0 - r4p1
+	 */
+	mov	x17, x30
+	bl	check_errata_1946160
+	cbz	x0, 1f
+
+	mov	x0, #3
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3900002
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #4
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800082
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #5
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800200
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF003E0
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_n1_1946160_wa
+
+func check_errata_1946160
+	/* Applies to r3p0 - r4p1. */
+	mov	x1, #0x30
+	mov	x2, #0x41
+	b	cpu_rev_var_range
+endfunc check_errata_1946160
+
 func neoverse_n1_reset_func
 	mov	x19, x30
 
@@ -499,6 +543,11 @@
 	bl	errata_n1_1868343_wa
 #endif
 
+#if ERRATA_N1_1946160
+	mov	x0, x18
+	bl	errata_n1_1946160_wa
+#endif
+
 #if ENABLE_AMU
 	/* Make sure accesses from EL0/EL1 and EL2 are not trapped to EL3 */
 	mrs	x0, actlr_el3
@@ -515,7 +564,7 @@
 	msr	CPUAMCNTENSET_EL0, x0
 #endif
 
-#if NEOVERSE_N1_EXTERNAL_LLC
+#if NEOVERSE_Nx_EXTERNAL_LLC
 	/* Some system may have External LLC, core needs to be made aware */
 	mrs     x0, NEOVERSE_N1_CPUECTLR_EL1
 	orr     x0, x0, NEOVERSE_N1_CPUECTLR_EL1_EXTLLC_BIT
@@ -573,6 +622,7 @@
 	report_errata ERRATA_N1_1315703, neoverse_n1, 1315703
 	report_errata ERRATA_N1_1542419, neoverse_n1, 1542419
 	report_errata ERRATA_N1_1868343, neoverse_n1, 1868343
+	report_errata ERRATA_N1_1946160, neoverse_n1, 1946160
 	report_errata ERRATA_DSU_936184, neoverse_n1, dsu_936184
 
 	ldp	x8, x30, [sp], #16
diff --git a/lib/cpus/aarch64/neoverse_n2.S b/lib/cpus/aarch64/neoverse_n2.S
new file mode 100644
index 0000000..621aded
--- /dev/null
+++ b/lib/cpus/aarch64/neoverse_n2.S
@@ -0,0 +1,499 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <cpu_macros.S>
+#include <neoverse_n2.h>
+
+/* Hardware handled coherency */
+#if HW_ASSISTED_COHERENCY == 0
+#error "Neoverse N2 must be compiled with HW_ASSISTED_COHERENCY enabled"
+#endif
+
+/* 64-bit only core */
+#if CTX_INCLUDE_AARCH32_REGS == 1
+#error "Neoverse-N2 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
+#endif
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2002655.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_n2_2002655_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2002655
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	ldr x0,=0x6
+	msr S3_6_c15_c8_0,x0
+	ldr x0,=0xF3A08002
+	msr S3_6_c15_c8_2,x0
+	ldr x0,=0xFFF0F7FE
+	msr S3_6_c15_c8_3,x0
+	ldr x0,=0x40000001003ff
+	msr S3_6_c15_c8_1,x0
+	ldr x0,=0x7
+	msr S3_6_c15_c8_0,x0
+	ldr x0,=0xBF200000
+	msr S3_6_c15_c8_2,x0
+	ldr x0,=0xFFEF0000
+	msr S3_6_c15_c8_3,x0
+	ldr x0,=0x40000001003f3
+	msr S3_6_c15_c8_1,x0
+	isb
+1:
+	ret	x17
+endfunc errata_n2_2002655_wa
+
+func check_errata_2002655
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2002655
+
+/* ---------------------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2067956.
+ * This applies to revision r0p0 of Neoverse N2 and is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------
+ */
+func errata_n2_2067956_wa
+	/* Compare x0 against revision r0p0 */
+	mov	x17, x30
+	bl	check_errata_2067956
+	cbz	x0, 1f
+	mrs	x1, NEOVERSE_N2_CPUACTLR_EL1
+	orr	x1, x1, NEOVERSE_N2_CPUACTLR_EL1_BIT_46
+	msr	NEOVERSE_N2_CPUACTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_n2_2067956_wa
+
+func check_errata_2067956
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2067956
+
+/* ---------------------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2025414.
+ * This applies to revision r0p0 of Neoverse N2 and is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------
+ */
+func errata_n2_2025414_wa
+	/* Compare x0 against revision r0p0 */
+	mov     x17, x30
+	bl      check_errata_2025414
+	cbz     x0, 1f
+	mrs     x1, NEOVERSE_N2_CPUECTLR_EL1
+	orr     x1, x1, NEOVERSE_N2_CPUECTLR_EL1_PFSTIDIS_BIT
+	msr     NEOVERSE_N2_CPUECTLR_EL1, x1
+
+1:
+	ret     x17
+endfunc errata_n2_2025414_wa
+
+func check_errata_2025414
+	/* Applies to r0p0 */
+	mov     x1, #0x00
+	b       cpu_rev_var_ls
+endfunc check_errata_2025414
+
+/* ---------------------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2189731.
+ * This applies to revision r0p0 of Neoverse N2 and is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * ---------------------------------------------------------------
+ */
+func errata_n2_2189731_wa
+	/* Compare x0 against revision r0p0 */
+	mov     x17, x30
+	bl      check_errata_2189731
+	cbz     x0, 1f
+	mrs     x1, NEOVERSE_N2_CPUACTLR5_EL1
+	orr     x1, x1, NEOVERSE_N2_CPUACTLR5_EL1_BIT_44
+	msr     NEOVERSE_N2_CPUACTLR5_EL1, x1
+
+1:
+	ret     x17
+endfunc errata_n2_2189731_wa
+
+func check_errata_2189731
+	/* Applies to r0p0 */
+	mov     x1, #0x00
+	b       cpu_rev_var_ls
+endfunc check_errata_2189731
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2138956.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x17
+ * --------------------------------------------------
+ */
+func errata_n2_2138956_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2138956
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	ldr	x0,=0x3
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xF3A08002
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFF0F7FE
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x10002001003FF
+	msr	S3_6_c15_c8_1,x0
+	ldr	x0,=0x4
+	msr	S3_6_c15_c8_0,x0
+	ldr	x0,=0xBF200000
+	msr	S3_6_c15_c8_2,x0
+	ldr	x0,=0xFFEF0000
+	msr	S3_6_c15_c8_3,x0
+	ldr	x0,=0x10002001003F3
+	msr	S3_6_c15_c8_1,x0
+	isb
+1:
+	ret	x17
+endfunc errata_n2_2138956_wa
+
+func check_errata_2138956
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2138956
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2242415.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_n2_2242415_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2242415
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	mrs	x1, NEOVERSE_N2_CPUACTLR_EL1
+	orr	x1, x1, NEOVERSE_N2_CPUACTLR_EL1_BIT_22
+	msr	NEOVERSE_N2_CPUACTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_n2_2242415_wa
+
+func check_errata_2242415
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2242415
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2138953.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_n2_2138953_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2138953
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	mrs	x1, NEOVERSE_N2_CPUECTLR2_EL1
+	mov	x0, #NEOVERSE_N2_CPUECTLR2_EL1_PF_MODE_CNSRV
+	bfi	x1, x0, #CPUECTLR2_EL1_PF_MODE_LSB, #CPUECTLR2_EL1_PF_MODE_WIDTH
+	msr	NEOVERSE_N2_CPUECTLR2_EL1, x1
+1:
+	ret	x17
+endfunc errata_n2_2138953_wa
+
+func check_errata_2138953
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2138953
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2138958.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_n2_2138958_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2138958
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	mrs	x1, NEOVERSE_N2_CPUACTLR5_EL1
+	orr	x1, x1, NEOVERSE_N2_CPUACTLR5_EL1_BIT_13
+	msr	NEOVERSE_N2_CPUACTLR5_EL1, x1
+1:
+	ret	x17
+endfunc errata_n2_2138958_wa
+
+func check_errata_2138958
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2138958
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2242400.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_n2_2242400_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2242400
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	mrs	x1, NEOVERSE_N2_CPUACTLR5_EL1
+	orr	x1, x1, NEOVERSE_N2_CPUACTLR5_EL1_BIT_17
+	msr	NEOVERSE_N2_CPUACTLR5_EL1, x1
+	ldr	x0, =0x2
+	msr	S3_6_c15_c8_0, x0
+	ldr	x0, =0x10F600E000
+	msr	S3_6_c15_c8_2, x0
+	ldr	x0, =0x10FF80E000
+	msr	S3_6_c15_c8_3, x0
+	ldr	x0, =0x80000000003FF
+	msr	S3_6_c15_c8_1, x0
+	isb
+1:
+	ret	x17
+endfunc errata_n2_2242400_wa
+
+func check_errata_2242400
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2242400
+
+/* --------------------------------------------------
+ * Errata Workaround for Neoverse N2 Erratum 2280757.
+ * This applies to revision r0p0 of Neoverse N2. it is still open.
+ * Inputs:
+ * x0: variant[4:7] and revision[0:3] of current cpu.
+ * Shall clobber: x0-x1, x17
+ * --------------------------------------------------
+ */
+func errata_n2_2280757_wa
+	/* Check revision. */
+	mov	x17, x30
+	bl	check_errata_2280757
+	cbz	x0, 1f
+
+	/* Apply instruction patching sequence */
+	mrs	x1, NEOVERSE_N2_CPUACTLR_EL1
+	orr	x1, x1, NEOVERSE_N2_CPUACTLR_EL1_BIT_22
+	msr	NEOVERSE_N2_CPUACTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_n2_2280757_wa
+
+func check_errata_2280757
+	/* Applies to r0p0 */
+	mov	x1, #0x00
+	b	cpu_rev_var_ls
+endfunc check_errata_2280757
+
+	/* -------------------------------------------
+	 * The CPU Ops reset function for Neoverse N2.
+	 * -------------------------------------------
+	 */
+func neoverse_n2_reset_func
+	mov	x19, x30
+
+	/* Check if the PE implements SSBS */
+	mrs	x0, id_aa64pfr1_el1
+	tst	x0, #(ID_AA64PFR1_EL1_SSBS_MASK << ID_AA64PFR1_EL1_SSBS_SHIFT)
+	b.eq	1f
+
+	/* Disable speculative loads */
+	msr	SSBS, xzr
+1:
+	/* Force all cacheable atomic instructions to be near */
+	mrs	x0, NEOVERSE_N2_CPUACTLR2_EL1
+	orr	x0, x0, #NEOVERSE_N2_CPUACTLR2_EL1_BIT_2
+	msr	NEOVERSE_N2_CPUACTLR2_EL1, x0
+
+#if ERRATA_N2_2067956
+	mov	x0, x18
+	bl	errata_n2_2067956_wa
+#endif
+
+#if ERRATA_N2_2025414
+	mov	x0, x18
+	bl	errata_n2_2025414_wa
+#endif
+
+#if ERRATA_N2_2189731
+	mov	x0, x18
+	bl	errata_n2_2189731_wa
+#endif
+
+
+#if ERRATA_N2_2138956
+	mov	x0, x18
+	bl	errata_n2_2138956_wa
+#endif
+
+#if ERRATA_N2_2138953
+	mov	x0, x18
+	bl	errata_n2_2138953_wa
+#endif
+
+#if ERRATA_N2_2242415
+	mov	x0, x18
+	bl	errata_n2_2242415_wa
+#endif
+
+#if ERRATA_N2_2138958
+	mov	x0, x18
+	bl	errata_n2_2138958_wa
+#endif
+
+#if ERRATA_N2_2242400
+	mov	x0, x18
+	bl	errata_n2_2242400_wa
+#endif
+
+#if ERRATA_N2_2280757
+	mov	x0, x18
+	bl	errata_n2_2280757_wa
+#endif
+
+#if ENABLE_AMU
+	/* Make sure accesses from EL0/EL1 and EL2 are not trapped to EL3 */
+	mrs	x0, cptr_el3
+	orr	x0, x0, #TAM_BIT
+	msr	cptr_el3, x0
+
+	/* Make sure accesses from EL0/EL1 are not trapped to EL2 */
+	mrs	x0, cptr_el2
+	orr	x0, x0, #TAM_BIT
+	msr	cptr_el2, x0
+
+	/* No need to enable the counters as this would be done at el3 exit */
+#endif
+
+#if NEOVERSE_Nx_EXTERNAL_LLC
+	/* Some systems may have External LLC, core needs to be made aware */
+	mrs	x0, NEOVERSE_N2_CPUECTLR_EL1
+	orr	x0, x0, NEOVERSE_N2_CPUECTLR_EL1_EXTLLC_BIT
+	msr	NEOVERSE_N2_CPUECTLR_EL1, x0
+#endif
+
+	bl	cpu_get_rev_var
+	mov	x18, x0
+
+#if ERRATA_N2_2002655
+	mov	x0, x18
+	bl	errata_n2_2002655_wa
+#endif
+
+	isb
+	ret	x19
+endfunc neoverse_n2_reset_func
+
+func neoverse_n2_core_pwr_dwn
+	/* ---------------------------------------------------
+	 * Enable CPU power down bit in power control register
+	 * No need to do cache maintenance here.
+	 * ---------------------------------------------------
+	 */
+	mrs	x0, NEOVERSE_N2_CPUPWRCTLR_EL1
+	orr	x0, x0, #NEOVERSE_N2_CORE_PWRDN_EN_BIT
+	msr	NEOVERSE_N2_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+endfunc neoverse_n2_core_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Neoverse N2 cores. Must follow AAPCS.
+ */
+func neoverse_n2_errata_report
+	stp	x8, x30, [sp, #-16]!
+
+	bl	cpu_get_rev_var
+	mov	x8, x0
+
+	/*
+	 * Report all errata. The revision-variant information is passed to
+	 * checking functions of each errata.
+	 */
+	report_errata ERRATA_N2_2002655, neoverse_n2, 2002655
+	report_errata ERRATA_N2_2067956, neoverse_n2, 2067956
+	report_errata ERRATA_N2_2025414, neoverse_n2, 2025414
+	report_errata ERRATA_N2_2189731, neoverse_n2, 2189731
+	report_errata ERRATA_N2_2138956, neoverse_n2, 2138956
+	report_errata ERRATA_N2_2138953, neoverse_n2, 2138953
+	report_errata ERRATA_N2_2242415, neoverse_n2, 2242415
+	report_errata ERRATA_N2_2138958, neoverse_n2, 2138958
+	report_errata ERRATA_N2_2242400, neoverse_n2, 2242400
+	report_errata ERRATA_N2_2280757, neoverse_n2, 2280757
+
+	ldp	x8, x30, [sp], #16
+	ret
+endfunc neoverse_n2_errata_report
+#endif
+
+	/* ---------------------------------------------
+	 * This function provides Neoverse N2 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.neoverse_n2_regs, "aS"
+neoverse_n2_regs:  /* The ASCII list of register names to be reported */
+	.asciz	"cpupwrctlr_el1", ""
+
+func neoverse_n2_cpu_reg_dump
+	adr	x6, neoverse_n2_regs
+	mrs	x8, NEOVERSE_N2_CPUPWRCTLR_EL1
+	ret
+endfunc neoverse_n2_cpu_reg_dump
+
+declare_cpu_ops neoverse_n2, NEOVERSE_N2_MIDR, \
+	neoverse_n2_reset_func, \
+	neoverse_n2_core_pwr_dwn
diff --git a/lib/cpus/aarch64/neoverse_n_common.S b/lib/cpus/aarch64/neoverse_n_common.S
new file mode 100644
index 0000000..b816342
--- /dev/null
+++ b/lib/cpus/aarch64/neoverse_n_common.S
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <asm_macros.S>
+#include <neoverse_n_common.h>
+
+	.global is_scu_present_in_dsu
+
+/*
+ * Check if the SCU L3 Unit is present on the DSU
+ * 1-> SCU present
+ * 0-> SCU not present
+ *
+ * This function is implemented as weak on dsu_helpers.S and must be
+ * overwritten for Neoverse Nx cores.
+ */
+
+func is_scu_present_in_dsu
+	mrs	x0, CPUCFR_EL1
+	ubfx	x0, x0, #SCU_SHIFT, #1
+	eor	x0, x0, #1
+	ret
+endfunc is_scu_present_in_dsu
diff --git a/lib/cpus/aarch64/neoverse_v1.S b/lib/cpus/aarch64/neoverse_v1.S
index 7336294..62a7a30 100644
--- a/lib/cpus/aarch64/neoverse_v1.S
+++ b/lib/cpus/aarch64/neoverse_v1.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -21,6 +21,310 @@
 #error "Neoverse-V1 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
 #endif
 
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #1774420.
+	 * This applies to revisions r0p0 and r1p0, fixed in r1p1.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1774420_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1774420
+	cbz	x0, 1f
+
+	/* Set bit 53 in CPUECTLR_EL1 */
+	mrs     x1, NEOVERSE_V1_CPUECTLR_EL1
+	orr	x1, x1, #NEOVERSE_V1_CPUECTLR_EL1_BIT_53
+	msr     NEOVERSE_V1_CPUECTLR_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1774420_wa
+
+func check_errata_1774420
+	/* Applies to r0p0 and r1p0. */
+	mov	x1, #0x10
+	b	cpu_rev_var_ls
+endfunc check_errata_1774420
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #1791573.
+	 * This applies to revisions r0p0 and r1p0, fixed in r1p1.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1791573_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1791573
+	cbz	x0, 1f
+
+	/* Set bit 2 in ACTLR2_EL1 */
+	mrs	x1, NEOVERSE_V1_ACTLR2_EL1
+	orr	x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_2
+	msr	NEOVERSE_V1_ACTLR2_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1791573_wa
+
+func check_errata_1791573
+	/* Applies to r0p0 and r1p0. */
+	mov	x1, #0x10
+	b	cpu_rev_var_ls
+endfunc check_errata_1791573
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #1852267.
+	 * This applies to revisions r0p0 and r1p0, fixed in r1p1.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1852267_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1852267
+	cbz	x0, 1f
+
+	/* Set bit 28 in ACTLR2_EL1 */
+	mrs	x1, NEOVERSE_V1_ACTLR2_EL1
+	orr	x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_28
+	msr	NEOVERSE_V1_ACTLR2_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1852267_wa
+
+func check_errata_1852267
+	/* Applies to r0p0 and r1p0. */
+	mov	x1, #0x10
+	b	cpu_rev_var_ls
+endfunc check_errata_1852267
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #1925756.
+	 * This applies to revisions <= r1p1.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1925756_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1925756
+	cbz	x0, 1f
+
+	/* Set bit 8 in CPUECTLR_EL1 */
+	mrs	x1, NEOVERSE_V1_CPUECTLR_EL1
+	orr	x1, x1, #NEOVERSE_V1_CPUECTLR_EL1_BIT_8
+	msr	NEOVERSE_V1_CPUECTLR_EL1, x1
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1925756_wa
+
+func check_errata_1925756
+	/* Applies to <= r1p1. */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_1925756
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Erratum #1940577
+	 * This applies to revisions r1p0 - r1p1 and is open.
+	 * It also exists in r0p0 but there is no fix in that
+	 * revision.
+	 * Inputs:
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1940577_wa
+	/* Compare x0 against revisions r1p0 - r1p1 */
+	mov	x17, x30
+	bl	check_errata_1940577
+	cbz	x0, 1f
+
+	mov	x0, #0
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3900002
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #1
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800082
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF00083
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	mov	x0, #2
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0x10E3800200
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0x10FFF003E0
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x2001003FF
+	msr	S3_6_C15_C8_1, x0
+
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1940577_wa
+
+func check_errata_1940577
+	/* Applies to revisions r1p0 - r1p1. */
+	mov	x1, #0x10
+	mov	x2, #0x11
+	b	cpu_rev_var_range
+endfunc check_errata_1940577
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #1966096
+	 * This applies to revisions r1p0 - r1p1 and is open.
+	 * It also exists in r0p0 but there is no workaround
+	 * for that revision.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_1966096_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_1966096
+	cbz	x0, 1f
+
+	/* Apply the workaround. */
+	mov	x0, #0x3
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0xEE010F12
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0xFFFF0FFF
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x80000000003FF
+	msr	S3_6_C15_C8_1, x0
+	isb
+
+1:
+	ret	x17
+endfunc errata_neoverse_v1_1966096_wa
+
+func check_errata_1966096
+	mov	x1, #0x10
+	mov	x2, #0x11
+	b	cpu_rev_var_range
+endfunc check_errata_1966096
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #2139242.
+	 * This applies to revisions r0p0, r1p0, and r1p1, it
+	 * is still open.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_2139242_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_2139242
+	cbz	x0, 1f
+
+	/* Apply the workaround. */
+	mov	x0, #0x3
+	msr	S3_6_C15_C8_0, x0
+	ldr	x0, =0xEE720F14
+	msr	S3_6_C15_C8_2, x0
+	ldr	x0, =0xFFFF0FDF
+	msr	S3_6_C15_C8_3, x0
+	ldr	x0, =0x40000005003FF
+	msr	S3_6_C15_C8_1, x0
+	isb
+
+1:
+	ret	x17
+endfunc errata_neoverse_v1_2139242_wa
+
+func check_errata_2139242
+	/* Applies to r0p0, r1p0, r1p1 */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_2139242
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #2108267.
+	 * This applies to revisions r0p0, r1p0, and r1p1, it
+	 * is still open.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x1, x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_2108267_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_2108267
+	cbz	x0, 1f
+
+	/* Apply the workaround. */
+	mrs	x1, NEOVERSE_V1_CPUECTLR_EL1
+	mov	x0, #NEOVERSE_V1_CPUECTLR_EL1_PF_MODE_CNSRV
+	bfi	x1, x0, #CPUECTLR_EL1_PF_MODE_LSB, #CPUECTLR_EL1_PF_MODE_WIDTH
+	msr	NEOVERSE_V1_CPUECTLR_EL1, x1
+1:
+	ret	x17
+endfunc errata_neoverse_v1_2108267_wa
+
+func check_errata_2108267
+	/* Applies to r0p0, r1p0, r1p1 */
+	mov	x1, #0x11
+	b	cpu_rev_var_ls
+endfunc check_errata_2108267
+
+	/* --------------------------------------------------
+	 * Errata Workaround for Neoverse V1 Errata #2216392.
+	 * This applies to revisions r1p0 and r1p1 and is
+	 * still open.
+	 * This issue is also present in r0p0 but there is no
+	 * workaround in that revision.
+	 * x0: variant[4:7] and revision[0:3] of current cpu.
+	 * Shall clobber: x0-x17
+	 * --------------------------------------------------
+	 */
+func errata_neoverse_v1_2216392_wa
+	/* Check workaround compatibility. */
+	mov	x17, x30
+	bl	check_errata_2216392
+	cbz	x0, 1f
+
+	ldr	x0, =0x5
+	msr	S3_6_c15_c8_0, x0 /* CPUPSELR_EL3 */
+	ldr	x0, =0x10F600E000
+	msr	S3_6_c15_c8_2, x0 /* CPUPOR_EL3 */
+	ldr	x0, =0x10FF80E000
+	msr	S3_6_c15_c8_3, x0 /* CPUPMR_EL3 */
+	ldr	x0, =0x80000000003FF
+	msr	S3_6_c15_c8_1, x0 /* CPUPCR_EL3 */
+
+	isb
+1:
+	ret	x17
+endfunc errata_neoverse_v1_2216392_wa
+
+func check_errata_2216392
+	/* Applies to revisions r1p0 and r1p1. */
+	mov	x1, #CPU_REV(1, 0)
+	mov	x2, #CPU_REV(1, 1)
+	b	cpu_rev_var_range
+endfunc check_errata_2216392
+
 	/* ---------------------------------------------
 	 * HW will do the cache maintenance while powering down
 	 * ---------------------------------------------
@@ -42,6 +346,26 @@
 	 */
 #if REPORT_ERRATA
 func neoverse_v1_errata_report
+	stp	x8, x30, [sp, #-16]!
+
+	bl	cpu_get_rev_var
+	mov	x8, x0
+
+	/*
+	 * Report all errata. The revision-variant information is passed to
+	 * checking functions of each errata.
+	 */
+	report_errata ERRATA_V1_1774420, neoverse_v1, 1774420
+	report_errata ERRATA_V1_1791573, neoverse_v1, 1791573
+	report_errata ERRATA_V1_1852267, neoverse_v1, 1852267
+	report_errata ERRATA_V1_1925756, neoverse_v1, 1925756
+	report_errata ERRATA_V1_1940577, neoverse_v1, 1940577
+	report_errata ERRATA_V1_1966096, neoverse_v1, 1966096
+	report_errata ERRATA_V1_2139242, neoverse_v1, 2139242
+	report_errata ERRATA_V1_2108267, neoverse_v1, 2108267
+	report_errata ERRATA_V1_2216392, neoverse_v1, 2216392
+
+	ldp	x8, x30, [sp], #16
 	ret
 endfunc neoverse_v1_errata_report
 #endif
@@ -51,8 +375,53 @@
 
 	/* Disable speculative loads */
 	msr	SSBS, xzr
-
 	isb
+
+#if ERRATA_V1_1774420
+	mov	x0, x18
+	bl	errata_neoverse_v1_1774420_wa
+#endif
+
+#if ERRATA_V1_1791573
+	mov	x0, x18
+	bl	errata_neoverse_v1_1791573_wa
+#endif
+
+#if ERRATA_V1_1852267
+	mov	x0, x18
+	bl	errata_neoverse_v1_1852267_wa
+#endif
+
+#if ERRATA_V1_1925756
+	mov	x0, x18
+	bl	errata_neoverse_v1_1925756_wa
+#endif
+
+#if ERRATA_V1_1940577
+	mov	x0, x18
+	bl	errata_neoverse_v1_1940577_wa
+#endif
+
+#if ERRATA_V1_1966096
+	mov	x0, x18
+	bl	errata_neoverse_v1_1966096_wa
+#endif
+
+#if ERRATA_V1_2139242
+	mov	x0, x18
+	bl	errata_neoverse_v1_2139242_wa
+#endif
+
+#if ERRATA_V1_2108267
+	mov	x0, x18
+	bl	errata_neoverse_v1_2108267_wa
+#endif
+
+#if ERRATA_V1_2216392
+	mov	x0, x18
+	bl	errata_neoverse_v1_2216392_wa
+#endif
+
 	ret	x19
 endfunc neoverse_v1_reset_func
 
diff --git a/lib/cpus/aarch64/qemu_max.S b/lib/cpus/aarch64/qemu_max.S
new file mode 100644
index 0000000..8948fda
--- /dev/null
+++ b/lib/cpus/aarch64/qemu_max.S
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <arch.h>
+#include <asm_macros.S>
+#include <cpu_macros.S>
+#include <qemu_max.h>
+
+func qemu_max_core_pwr_dwn
+	/* ---------------------------------------------
+	 * Disable the Data Cache.
+	 * ---------------------------------------------
+	 */
+	mrs	x1, sctlr_el3
+	bic	x1, x1, #SCTLR_C_BIT
+	msr	sctlr_el3, x1
+	isb
+
+	/* ---------------------------------------------
+	 * Flush L1 cache to L2.
+	 * ---------------------------------------------
+	 */
+	mov	x18, lr
+	mov	x0, #DCCISW
+	bl	dcsw_op_level1
+	mov	lr, x18
+	ret
+endfunc qemu_max_core_pwr_dwn
+
+func qemu_max_cluster_pwr_dwn
+	/* ---------------------------------------------
+	 * Disable the Data Cache.
+	 * ---------------------------------------------
+	 */
+	mrs	x1, sctlr_el3
+	bic	x1, x1, #SCTLR_C_BIT
+	msr	sctlr_el3, x1
+	isb
+
+	/* ---------------------------------------------
+	 * Flush all caches to PoC.
+	 * ---------------------------------------------
+	 */
+	mov	x0, #DCCISW
+	b	dcsw_op_all
+endfunc qemu_max_cluster_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for QEMU "max". Must follow AAPCS.
+ */
+func qemu_max_errata_report
+	ret
+endfunc qemu_max_errata_report
+#endif
+
+	/* ---------------------------------------------
+	 * This function provides cpu 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.qemu_max_regs, "aS"
+qemu_max_regs:  /* The ascii list of register names to be reported */
+	.asciz	"" /* no registers to report */
+
+func qemu_max_cpu_reg_dump
+	adr	x6, qemu_max_regs
+	ret
+endfunc qemu_max_cpu_reg_dump
+
+
+/* cpu_ops for QEMU MAX */
+declare_cpu_ops qemu_max, QEMU_MAX_MIDR, CPU_NO_RESET_FUNC, \
+	qemu_max_core_pwr_dwn, \
+	qemu_max_cluster_pwr_dwn
diff --git a/lib/cpus/aarch64/rainier.S b/lib/cpus/aarch64/rainier.S
index f7afd0b..3017a50 100644
--- a/lib/cpus/aarch64/rainier.S
+++ b/lib/cpus/aarch64/rainier.S
@@ -21,10 +21,6 @@
 #error "Rainier CPU supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0"
 #endif
 
-#if ERRATA_RAINIER_IC_TRAP
-	.global rainier_errata_ic_trap_handler
-#endif
-
 /* --------------------------------------------------
  * Disable speculative loads if Rainier supports
  * SSBS.
@@ -45,42 +41,6 @@
 	ret
 endfunc rainier_disable_speculative_loads
 
-/* --------------------------------------------------
- * Errata Workaround for Neoverse N1 Erratum 1542419.
- * This applies to revisions r3p0 - r4p0 of Neoverse N1
- * Since Rainier core is based on Neoverse N1 r4p0, this
- * errata applies to Rainier core r0p0
- * Inputs:
- * x0: variant[4:7] and revision[0:3] of current cpu.
- * Shall clobber: x0-x17
- * --------------------------------------------------
- */
-func errata_n1_1542419_wa
-	/* Compare x0 against revision r3p0 and r4p0 */
-	mov	x17, x30
-	bl	check_errata_1542419
-	cbz	x0, 1f
-
-        /* Apply instruction patching sequence */
-	mov	x0, xzr
-	msr	CPUPSELR_EL3, x0
-	ldr	x0, =0xEE670D35
-	msr	CPUPOR_EL3, x0
-	ldr	x0, =0xFFFF0FFF
-	msr	CPUPMR_EL3, x0
-	ldr	x0, =0x08000020007D
-	msr	CPUPCR_EL3, x0
-	isb
-1:
-	ret	x17
-endfunc errata_n1_1542419_wa
-
-func check_errata_1542419
-	/* Applies to Rainier core r0p0. */
-	mov	x1, #0x00
-	b	cpu_rev_var_ls
-endfunc check_errata_1542419
-
 func rainier_reset_func
 	mov	x19, x30
 
@@ -95,11 +55,6 @@
 	bl	cpu_get_rev_var
 	mov	x18, x0
 
-#if ERRATA_N1_1542419
-	mov	x0, x18
-	bl	errata_n1_1542419_wa
-#endif
-
 #if ENABLE_AMU
 	/* Make sure accesses from EL0/EL1 and EL2 are not trapped to EL3 */
 	mrs	x0, actlr_el3
@@ -146,53 +101,11 @@
 	bl	cpu_get_rev_var
 	mov	x8, x0
 
-	/*
-	 * Report all errata. The revision-variant information is passed to
-	 * checking functions of each errata.
-	 */
-	report_errata ERRATA_N1_1542419, rainier, 1542419
-
 	ldp	x8, x30, [sp], #16
 	ret
 endfunc rainier_errata_report
 #endif
 
-/*
- * Handle trap of EL0 IC IVAU instructions to EL3 by executing a TLB
- * inner-shareable invalidation to an arbitrary address followed by a DSB.
- *
- * x1: Exception Syndrome
- */
-func rainier_errata_ic_trap_handler
-	cmp	x1, #RAINIER_EC_IC_TRAP
-	b.ne	1f
-	tlbi	vae3is, xzr
-	dsb	sy
-
-        # Skip the IC instruction itself
-        mrs     x3, elr_el3
-        add     x3, x3, #4
-        msr     elr_el3, x3
-
-	ldp	x0, x1, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X0]
-	ldp	x2, x3, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X2]
-	ldp	x4, x5, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X4]
-	ldr	x30, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
-
-#if IMAGE_BL31 && RAS_EXTENSION
-	/*
-	 * Issue Error Synchronization Barrier to synchronize SErrors before
-	 * exiting EL3. We're running with EAs unmasked, so any synchronized
-	 * errors would be taken immediately; therefore no need to inspect
-	 * DISR_EL1 register.
-	 */
-	esb
-#endif
-	eret
-1:
-	ret
-endfunc rainier_errata_ic_trap_handler
-
 	/* ---------------------------------------------
 	 * This function provides Rainier specific
 	 * register information for crash reporting.
@@ -212,7 +125,6 @@
 	ret
 endfunc rainier_cpu_reg_dump
 
-declare_cpu_ops_eh rainier, RAINIER_MIDR, \
+declare_cpu_ops rainier, RAINIER_MIDR, \
 	rainier_reset_func, \
-	rainier_errata_ic_trap_handler, \
 	rainier_core_pwr_dwn
diff --git a/lib/cpus/cpu-ops.mk b/lib/cpus/cpu-ops.mk
index 1210538..a5b8aae 100644
--- a/lib/cpus/cpu-ops.mk
+++ b/lib/cpus/cpu-ops.mk
@@ -1,6 +1,6 @@
 #
-# Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
-# Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
+# Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2020-2021, NVIDIA Corporation. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -25,9 +25,9 @@
 WORKAROUND_CVE_2018_3639	?=1
 DYNAMIC_WORKAROUND_CVE_2018_3639	?=0
 
-# Flag to indicate internal or external Last level cache
+# Flags to indicate internal or external Last level cache
 # By default internal
-NEOVERSE_N1_EXTERNAL_LLC	?=0
+NEOVERSE_Nx_EXTERNAL_LLC	?=0
 
 # Process A57_ENABLE_NONCACHEABLE_LOAD_FWD flag
 $(eval $(call assert_boolean,A57_ENABLE_NONCACHEABLE_LOAD_FWD))
@@ -56,8 +56,8 @@
 $(eval $(call assert_boolean,DYNAMIC_WORKAROUND_CVE_2018_3639))
 $(eval $(call add_define,DYNAMIC_WORKAROUND_CVE_2018_3639))
 
-$(eval $(call assert_boolean,NEOVERSE_N1_EXTERNAL_LLC))
-$(eval $(call add_define,NEOVERSE_N1_EXTERNAL_LLC))
+$(eval $(call assert_boolean,NEOVERSE_Nx_EXTERNAL_LLC))
+$(eval $(call add_define,NEOVERSE_Nx_EXTERNAL_LLC))
 
 ifneq (${DYNAMIC_WORKAROUND_CVE_2018_3639},0)
     ifeq (${WORKAROUND_CVE_2018_3639},0)
@@ -270,10 +270,6 @@
 # only to revision <= r4p0 of the Cortex A76 cpu.
 ERRATA_A76_1791580	?=0
 
-# Flag to apply erratum 1800710 workaround during reset. This erratum applies
-# only to revision <= r4p0 of the Cortex A76 cpu.
-ERRATA_A76_1800710	?=0
-
 # Flag to apply erratum 1165522 workaround during reset. This erratum applies
 # to all revisions of Cortex A76 cpu.
 ERRATA_A76_1165522	?=0
@@ -282,22 +278,64 @@
 # only to revision <= r4p0 of the Cortex A76 cpu.
 ERRATA_A76_1868343	?=0
 
+# Flag to apply erratum 1946160 workaround during reset. This erratum applies
+# only to revisions r3p0 - r4p1 of the Cortex A76 cpu.
+ERRATA_A76_1946160	?=0
+
 # Flag to apply erratum 1508412 workaround during reset. This erratum applies
 # only to revision <= r1p0 of the Cortex A77 cpu.
 ERRATA_A77_1508412	?=0
 
-# Flag to apply erratum 1800714 workaround during reset. This erratum applies
-# only to revision <= r1p1 of the Cortex A77 cpu.
-ERRATA_A77_1800714	?=0
-
 # Flag to apply erratum 1925769 workaround during reset. This erratum applies
 # only to revision <= r1p1 of the Cortex A77 cpu.
 ERRATA_A77_1925769	?=0
 
+# Flag to apply erratum 1946167 workaround during reset. This erratum applies
+# only to revision <= r1p1 of the Cortex A77 cpu.
+ERRATA_A77_1946167	?=0
+
+# Flag to apply erratum 1791578 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0, and r1p1, it is still open.
+ERRATA_A77_1791578	?=0
+
 # Flag to apply erratum 1688305 workaround during reset. This erratum applies
 # to revisions r0p0 - r1p0 of the A78 cpu.
 ERRATA_A78_1688305	?=0
 
+# Flag to apply erratum 1941498 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0, and r1p1 of the A78 cpu.
+ERRATA_A78_1941498	?=0
+
+# Flag to apply erratum 1951500 workaround during reset. This erratum applies
+# to revisions r1p0 and r1p1 of the A78 cpu.  The issue is present in r0p0 as
+# well but there is no workaround for that revision.
+ERRATA_A78_1951500	?=0
+
+# Flag to apply erratum 1821534 workaround during reset. This erratum applies
+# to revisions r0p0 and r1p0 of the A78 cpu.
+ERRATA_A78_1821534	?=0
+
+# Flag to apply erratum 1952683 workaround during reset. This erratum applies
+# to revision r0p0 of the A78 cpu and was fixed in the revision r1p0.
+ERRATA_A78_1952683  ?=0
+
+# Flag to apply erratum 2132060 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0, r1p1, and r1p2 of the A78 cpu. It is still open.
+ERRATA_A78_2132060  ?=0
+
+# Flag to apply erratum 2242635 workaround during reset. This erratum applies
+# to revisions r1p0, r1p1, and r1p2 of the A78 cpu and is open. The issue is
+# present in r0p0 as well but there is no workaround for that revision.
+ERRATA_A78_2242635	?=0
+
+# Flag to apply erratum 1941500 workaround during reset. This erratum applies
+# to revisions r0p0 and r0p1 of the A78 AE cpu. It is still open.
+ERRATA_A78_AE_1941500	?=0
+
+# Flag to apply erratum 1951502 workaround during reset. This erratum applies
+# to revisions r0p0 and r0p1 of the A78 AE cpu. It is still open.
+ERRATA_A78_AE_1951502	?=0
+
 # Flag to apply T32 CLREX workaround during reset. This erratum applies
 # only to r0p0 and r1p0 of the Neoverse N1 cpu.
 ERRATA_N1_1043202	?=0
@@ -350,6 +388,113 @@
 # to revision <= r4p0 of the Neoverse N1 cpu.
 ERRATA_N1_1868343	?=0
 
+# Flag to apply erratum 1946160 workaround during reset. This erratum applies
+# to revisions r3p0, r3p1, r4p0, and r4p1 of the Neoverse N1 cpu.  The issue
+# exists in revisions r0p0, r1p0, and r2p0 as well but there is no workaround.
+ERRATA_N1_1946160	?=0
+
+# Flag to apply erratum 2002655 workaround during reset. This erratum applies
+# to revisions r0p0 of the Neoverse-N2 cpu, it is still open.
+ERRATA_N2_2002655	?=0
+
+# Flag to apply erratum 1774420 workaround during reset.  This erratum applies
+# to revisions r0p0 and r1p0 of the Neoverse V1 core, and was fixed in r1p1.
+ERRATA_V1_1774420	?=0
+
+# Flag to apply erratum 1791573 workaround during reset.  This erratum applies
+# to revisions r0p0 and r1p0 of the Neoverse V1 core, and was fixed in r1p1.
+ERRATA_V1_1791573	?=0
+
+# Flag to apply erratum 1852267 workaround during reset.  This erratum applies
+# to revisions r0p0 and r1p0 of the Neoverse V1 core, and was fixed in r1p1.
+ERRATA_V1_1852267	?=0
+
+# Flag to apply erratum 1925756 workaround during reset.  This needs to be
+# enabled for r0p0, r1p0, and r1p1 of the Neoverse V1 core, it is still open.
+ERRATA_V1_1925756	?=0
+
+# Flag to apply erratum 1940577 workaround during reset. This erratum applies
+# to revisions r1p0 and r1p1 of the Neoverse V1 cpu.
+ERRATA_V1_1940577	?=0
+
+# Flag to apply erratum 1966096 workaround during reset. This erratum applies
+# to revisions r1p0 and r1p1 of the Neoverse V1 CPU and is open.  This issue
+# exists in r0p0 as well but there is no workaround for that revision.
+ERRATA_V1_1966096	?=0
+
+# Flag to apply erratum 2139242 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0, and r1p1 of the Neoverse V1 cpu and is still open.
+ERRATA_V1_2139242	?=0
+
+# Flag to apply erratum 2108267 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0, and r1p1 of the Neoverse V1 cpu and is still open.
+ERRATA_V1_2108267	?=0
+
+# Flag to apply erratum 2216392 workaround during reset. This erratum applies
+# to revisions r1p0 and r1p1 of the Neoverse V1 cpu and is still open. This
+# issue exists in r0p0 as well but there is no workaround for that revision.
+ERRATA_V1_2216392	?=0
+
+# Flag to apply erratum 1987031 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0 and r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_1987031	?=0
+
+# Flag to apply erratum 2081180 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0 and r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_2081180	?=0
+
+# Flag to apply erratum 2083908 workaround during reset. This erratum applies
+# to revision r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_2083908	?=0
+
+# Flag to apply erratum 2058056 workaround during reset. This erratum applies
+# to revisions r0p0, r1p0 and r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_2058056	?=0
+
+# Flag to apply erratum 2067956 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2067956	?=0
+
+# Flag to apply erratum 2025414 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2025414	?=0
+
+# Flag to apply erratum 2189731 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2189731	?=0
+
+# Flag to apply erratum 2138956 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2138956	?=0
+
+# Flag to apply erratum 2138953 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2138953	?=0
+
+# Flag to apply erratum 2242415 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2242415	?=0
+
+# Flag to apply erratum 2138958 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2138958	?=0
+
+# Flag to apply erratum 2242400 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2242400	?=0
+
+# Flag to apply erratum 2280757 workaround during reset. This erratum applies
+# to revision r0p0 of the Neoverse N2 cpu and is still open.
+ERRATA_N2_2280757	?=0
+
+# Flag to apply erratum 2055002 workaround during reset. This erratum applies
+# to revision r1p0, r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_2055002	?=0
+
+# Flag to apply erratum 2017096 workaround during reset. This erratum applies
+# to revision r0p0, r1p0 and r2p0 of the Cortex-A710 cpu and is still open.
+ERRATA_A710_2017096	?=0
+
 # Flag to apply DSU erratum 798953. This erratum applies to DSUs revision r0p0.
 # Applying the workaround results in higher DSU power consumption on idle.
 ERRATA_DSU_798953	?=0
@@ -555,10 +700,6 @@
 $(eval $(call assert_boolean,ERRATA_A76_1791580))
 $(eval $(call add_define,ERRATA_A76_1791580))
 
-# Process ERRATA_A76_1800710 flag
-$(eval $(call assert_boolean,ERRATA_A76_1800710))
-$(eval $(call add_define,ERRATA_A76_1800710))
-
 # Process ERRATA_A76_1165522 flag
 $(eval $(call assert_boolean,ERRATA_A76_1165522))
 $(eval $(call add_define,ERRATA_A76_1165522))
@@ -567,22 +708,62 @@
 $(eval $(call assert_boolean,ERRATA_A76_1868343))
 $(eval $(call add_define,ERRATA_A76_1868343))
 
+# Process ERRATA_A76_1946160 flag
+$(eval $(call assert_boolean,ERRATA_A76_1946160))
+$(eval $(call add_define,ERRATA_A76_1946160))
+
 # Process ERRATA_A77_1508412 flag
 $(eval $(call assert_boolean,ERRATA_A77_1508412))
 $(eval $(call add_define,ERRATA_A77_1508412))
 
-# Process ERRATA_A77_1800714 flag
-$(eval $(call assert_boolean,ERRATA_A77_1800714))
-$(eval $(call add_define,ERRATA_A77_1800714))
-
 # Process ERRATA_A77_1925769 flag
 $(eval $(call assert_boolean,ERRATA_A77_1925769))
 $(eval $(call add_define,ERRATA_A77_1925769))
 
+# Process ERRATA_A77_1946167 flag
+$(eval $(call assert_boolean,ERRATA_A77_1946167))
+$(eval $(call add_define,ERRATA_A77_1946167))
+
+# Process ERRATA_A77_1791578 flag
+$(eval $(call assert_boolean,ERRATA_A77_1791578))
+$(eval $(call add_define,ERRATA_A77_1791578))
+
 # Process ERRATA_A78_1688305 flag
 $(eval $(call assert_boolean,ERRATA_A78_1688305))
 $(eval $(call add_define,ERRATA_A78_1688305))
 
+# Process ERRATA_A78_1941498 flag
+$(eval $(call assert_boolean,ERRATA_A78_1941498))
+$(eval $(call add_define,ERRATA_A78_1941498))
+
+# Process ERRATA_A78_1951500 flag
+$(eval $(call assert_boolean,ERRATA_A78_1951500))
+$(eval $(call add_define,ERRATA_A78_1951500))
+
+# Process ERRATA_A78_1821534 flag
+$(eval $(call assert_boolean,ERRATA_A78_1821534))
+$(eval $(call add_define,ERRATA_A78_1821534))
+
+# Process ERRATA_A78_1952683 flag
+$(eval $(call assert_boolean,ERRATA_A78_1952683))
+$(eval $(call add_define,ERRATA_A78_1952683))
+
+# Process ERRATA_A78_2132060 flag
+$(eval $(call assert_boolean,ERRATA_A78_2132060))
+$(eval $(call add_define,ERRATA_A78_2132060))
+
+# Process ERRATA_A78_2242635 flag
+$(eval $(call assert_boolean,ERRATA_A78_2242635))
+$(eval $(call add_define,ERRATA_A78_2242635))
+
+# Process ERRATA_A78_AE_1941500 flag
+$(eval $(call assert_boolean,ERRATA_A78_AE_1941500))
+$(eval $(call add_define,ERRATA_A78_AE_1941500))
+
+# Process ERRATA_A78_AE_1951502 flag
+$(eval $(call assert_boolean,ERRATA_A78_AE_1951502))
+$(eval $(call add_define,ERRATA_A78_AE_1951502))
+
 # Process ERRATA_N1_1043202 flag
 $(eval $(call assert_boolean,ERRATA_N1_1043202))
 $(eval $(call add_define,ERRATA_N1_1043202))
@@ -635,6 +816,110 @@
 $(eval $(call assert_boolean,ERRATA_N1_1868343))
 $(eval $(call add_define,ERRATA_N1_1868343))
 
+# Process ERRATA_N1_1946160 flag
+$(eval $(call assert_boolean,ERRATA_N1_1946160))
+$(eval $(call add_define,ERRATA_N1_1946160))
+
+# Process ERRATA_N2_2002655 flag
+$(eval $(call assert_boolean,ERRATA_N2_2002655))
+$(eval $(call add_define,ERRATA_N2_2002655))
+
+# Process ERRATA_V1_1774420 flag
+$(eval $(call assert_boolean,ERRATA_V1_1774420))
+$(eval $(call add_define,ERRATA_V1_1774420))
+
+# Process ERRATA_V1_1791573 flag
+$(eval $(call assert_boolean,ERRATA_V1_1791573))
+$(eval $(call add_define,ERRATA_V1_1791573))
+
+# Process ERRATA_V1_1852267 flag
+$(eval $(call assert_boolean,ERRATA_V1_1852267))
+$(eval $(call add_define,ERRATA_V1_1852267))
+
+# Process ERRATA_V1_1925756 flag
+$(eval $(call assert_boolean,ERRATA_V1_1925756))
+$(eval $(call add_define,ERRATA_V1_1925756))
+
+# Process ERRATA_V1_1940577 flag
+$(eval $(call assert_boolean,ERRATA_V1_1940577))
+$(eval $(call add_define,ERRATA_V1_1940577))
+
+# Process ERRATA_V1_1966096 flag
+$(eval $(call assert_boolean,ERRATA_V1_1966096))
+$(eval $(call add_define,ERRATA_V1_1966096))
+
+# Process ERRATA_V1_2139242 flag
+$(eval $(call assert_boolean,ERRATA_V1_2139242))
+$(eval $(call add_define,ERRATA_V1_2139242))
+
+# Process ERRATA_V1_2108267 flag
+$(eval $(call assert_boolean,ERRATA_V1_2108267))
+$(eval $(call add_define,ERRATA_V1_2108267))
+
+# Process ERRATA_V1_2216392 flag
+$(eval $(call assert_boolean,ERRATA_V1_2216392))
+$(eval $(call add_define,ERRATA_V1_2216392))
+
+# Process ERRATA_A710_1987031 flag
+$(eval $(call assert_boolean,ERRATA_A710_1987031))
+$(eval $(call add_define,ERRATA_A710_1987031))
+
+# Process ERRATA_A710_2081180 flag
+$(eval $(call assert_boolean,ERRATA_A710_2081180))
+$(eval $(call add_define,ERRATA_A710_2081180))
+
+# Process ERRATA_A710_2083908 flag
+$(eval $(call assert_boolean,ERRATA_A710_2083908))
+$(eval $(call add_define,ERRATA_A710_2083908))
+
+# Process ERRATA_A710_2058056 flag
+$(eval $(call assert_boolean,ERRATA_A710_2058056))
+$(eval $(call add_define,ERRATA_A710_2058056))
+
+# Process ERRATA_N2_2067956 flag
+$(eval $(call assert_boolean,ERRATA_N2_2067956))
+$(eval $(call add_define,ERRATA_N2_2067956))
+
+# Process ERRATA_N2_2025414 flag
+$(eval $(call assert_boolean,ERRATA_N2_2025414))
+$(eval $(call add_define,ERRATA_N2_2025414))
+
+# Process ERRATA_N2_2189731 flag
+$(eval $(call assert_boolean,ERRATA_N2_2189731))
+$(eval $(call add_define,ERRATA_N2_2189731))
+
+# Process ERRATA_N2_2138956 flag
+$(eval $(call assert_boolean,ERRATA_N2_2138956))
+$(eval $(call add_define,ERRATA_N2_2138956))
+
+# Process ERRATA_N2_2138953 flag
+$(eval $(call assert_boolean,ERRATA_N2_2138953))
+$(eval $(call add_define,ERRATA_N2_2138953))
+
+# Process ERRATA_N2_2242415 flag
+$(eval $(call assert_boolean,ERRATA_N2_2242415))
+$(eval $(call add_define,ERRATA_N2_2242415))
+
+# Process ERRATA_N2_2138958 flag
+$(eval $(call assert_boolean,ERRATA_N2_2138958))
+$(eval $(call add_define,ERRATA_N2_2138958))
+
+# Process ERRATA_N2_2242400 flag
+$(eval $(call assert_boolean,ERRATA_N2_2242400))
+$(eval $(call add_define,ERRATA_N2_2242400))
+
+# Process ERRATA_N2_2280757 flag
+$(eval $(call assert_boolean,ERRATA_N2_2280757))
+$(eval $(call add_define,ERRATA_N2_2280757))
+
+# Process ERRATA_A710_2055002 flag
+$(eval $(call assert_boolean,ERRATA_A710_2055002))
+$(eval $(call add_define,ERRATA_A710_2055002))
+
+# Process ERRATA_A710_2017096 flag
+$(eval $(call assert_boolean,ERRATA_A710_2017096))
+$(eval $(call add_define,ERRATA_A710_2017096))
+
 # Process ERRATA_DSU_798953 flag
 $(eval $(call assert_boolean,ERRATA_DSU_798953))
 $(eval $(call add_define,ERRATA_DSU_798953))
diff --git a/lib/cpus/errata_report.c b/lib/cpus/errata_report.c
index 5d1e3c5..93b2744 100644
--- a/lib/cpus/errata_report.c
+++ b/lib/cpus/errata_report.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -19,7 +19,7 @@
 # define BL_STRING	"BL1"
 #elif defined(__aarch64__) && defined(IMAGE_BL31)
 # define BL_STRING	"BL31"
-#elif !defined(__arch64__) && defined(IMAGE_BL32)
+#elif !defined(__aarch64__) && defined(IMAGE_BL32)
 # define BL_STRING	"BL32"
 #elif defined(IMAGE_BL2) && BL2_AT_EL3
 # define BL_STRING "BL2"
diff --git a/lib/debugfs/dev.c b/lib/debugfs/dev.c
index 0361437..2fc1d40 100644
--- a/lib/debugfs/dev.c
+++ b/lib/debugfs/dev.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Arm Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -333,6 +333,10 @@
  ******************************************************************************/
 chan_t *clone(chan_t *c, chan_t *nc)
 {
+	if (c->index == NODEV) {
+		return NULL;
+	}
+
 	return devtab[c->index]->clone(c, nc);
 }
 
diff --git a/lib/debugfs/devfip.c b/lib/debugfs/devfip.c
index d8b83b7..85e6403 100644
--- a/lib/debugfs/devfip.c
+++ b/lib/debugfs/devfip.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -129,7 +129,10 @@
 		panic();
 	}
 
-	clone(archives[c->dev].c, &nc);
+	if (clone(archives[c->dev].c, &nc) == NULL) {
+		panic();
+	}
+
 	fip = &archives[nc.dev];
 
 	off = STOC_HEADER;
@@ -202,7 +205,9 @@
 		panic();
 	}
 
-	clone(fip->c, &cs);
+	if (clone(fip->c, &cs) == NULL) {
+		panic();
+	}
 
 	size = fip->size[c->qid];
 	if (c->offset >= size) {
diff --git a/lib/el3_runtime/aarch32/context_mgmt.c b/lib/el3_runtime/aarch32/context_mgmt.c
index 2443001..3ef378c 100644
--- a/lib/el3_runtime/aarch32/context_mgmt.c
+++ b/lib/el3_runtime/aarch32/context_mgmt.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,6 +16,8 @@
 #include <context.h>
 #include <lib/el3_runtime/context_mgmt.h>
 #include <lib/extensions/amu.h>
+#include <lib/extensions/sys_reg_trace.h>
+#include <lib/extensions/trf.h>
 #include <lib/utils.h>
 
 /*******************************************************************************
@@ -49,7 +51,7 @@
  *
  * To prepare the register state for entry call cm_prepare_el3_exit() and
  * el3_exit(). For Secure-EL1 cm_prepare_el3_exit() is equivalent to
- * cm_e1_sysreg_context_restore().
+ * cm_el1_sysregs_context_restore().
  ******************************************************************************/
 void cm_setup_context(cpu_context_t *ctx, const entry_point_info_t *ep)
 {
@@ -136,6 +138,14 @@
 #if ENABLE_AMU
 	amu_enable(el2_unused);
 #endif
+
+#if ENABLE_SYS_REG_TRACE_FOR_NS
+	sys_reg_trace_enable();
+#endif /* ENABLE_SYS_REG_TRACE_FOR_NS */
+
+#if ENABLE_TRF_FOR_NS
+	trf_enable();
+#endif /* ENABLE_TRF_FOR_NS */
 #endif
 }
 
diff --git a/lib/el3_runtime/aarch64/context.S b/lib/el3_runtime/aarch64/context.S
index 773082a..e270ad0 100644
--- a/lib/el3_runtime/aarch64/context.S
+++ b/lib/el3_runtime/aarch64/context.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -30,7 +30,7 @@
 
 /* -----------------------------------------------------
  * The following function strictly follows the AArch64
- * PCS to use x9-x17 (temporary caller-saved registers)
+ * PCS to use x9-x16 (temporary caller-saved registers)
  * to save EL2 system register context. It assumes that
  * 'x0' is pointing to a 'el2_sys_regs' structure where
  * the register context will be saved.
@@ -43,7 +43,6 @@
  * ICH_LR<n>_EL2
  * -----------------------------------------------------
  */
-
 func el2_sysregs_context_save
 	mrs	x9, actlr_el2
 	mrs	x10, afsr0_el2
@@ -54,185 +53,158 @@
 	stp	x11, x12, [x0, #CTX_AFSR1_EL2]
 
 	mrs	x13, cnthctl_el2
-	mrs	x14, cnthp_ctl_el2
+	mrs	x14, cntvoff_el2
 	stp	x13, x14, [x0, #CTX_CNTHCTL_EL2]
 
-	mrs	x15, cnthp_cval_el2
-	mrs	x16, cnthp_tval_el2
-	stp	x15, x16, [x0, #CTX_CNTHP_CVAL_EL2]
+	mrs	x15, cptr_el2
+	str	x15, [x0, #CTX_CPTR_EL2]
 
-	mrs	x17, cntvoff_el2
-	mrs	x9, cptr_el2
-	stp	x17, x9, [x0, #CTX_CNTVOFF_EL2]
-
-	mrs	x11, elr_el2
 #if CTX_INCLUDE_AARCH32_REGS
-	mrs	x10, dbgvcr32_el2
-	stp	x10, x11, [x0, #CTX_DBGVCR32_EL2]
-#else
-	str	x11, [x0, #CTX_ELR_EL2]
+	mrs	x16, dbgvcr32_el2
+	str	x16, [x0, #CTX_DBGVCR32_EL2]
 #endif
 
-	mrs	x14, esr_el2
-	mrs	x15, far_el2
-	stp	x14, x15, [x0, #CTX_ESR_EL2]
+	mrs	x9, elr_el2
+	mrs	x10, esr_el2
+	stp	x9, x10, [x0, #CTX_ELR_EL2]
 
-	mrs	x16, hacr_el2
-	mrs	x17, hcr_el2
-	stp	x16, x17, [x0, #CTX_HACR_EL2]
+	mrs	x11, far_el2
+	mrs	x12, hacr_el2
+	stp	x11, x12, [x0, #CTX_FAR_EL2]
 
-	mrs	x9, hpfar_el2
-	mrs	x10, hstr_el2
-	stp	x9, x10, [x0, #CTX_HPFAR_EL2]
+	mrs	x13, hcr_el2
+	mrs	x14, hpfar_el2
+	stp	x13, x14, [x0, #CTX_HCR_EL2]
 
-	mrs	x11, ICC_SRE_EL2
-	mrs	x12, ICH_HCR_EL2
-	stp	x11, x12, [x0, #CTX_ICC_SRE_EL2]
+	mrs	x15, hstr_el2
+	mrs	x16, ICC_SRE_EL2
+	stp	x15, x16, [x0, #CTX_HSTR_EL2]
 
-	mrs	x13, ICH_VMCR_EL2
-	mrs	x14, mair_el2
-	stp	x13, x14, [x0, #CTX_ICH_VMCR_EL2]
+	mrs	x9, ICH_HCR_EL2
+	mrs	x10, ICH_VMCR_EL2
+	stp	x9, x10, [x0, #CTX_ICH_HCR_EL2]
 
-	mrs	x15, mdcr_el2
+	mrs	x11, mair_el2
+	mrs	x12, mdcr_el2
+	stp	x11, x12, [x0, #CTX_MAIR_EL2]
+
 #if ENABLE_SPE_FOR_LOWER_ELS
-	mrs	x16, PMSCR_EL2
-	stp	x15, x16, [x0, #CTX_MDCR_EL2]
-#else
-	str	x15, [x0, #CTX_MDCR_EL2]
+	mrs	x13, PMSCR_EL2
+	str	x13, [x0, #CTX_PMSCR_EL2]
 #endif
+	mrs	x14, sctlr_el2
+	str	x14, [x0, #CTX_SCTLR_EL2]
 
-	mrs	x17, sctlr_el2
-	mrs	x9, spsr_el2
-	stp	x17, x9, [x0, #CTX_SCTLR_EL2]
+	mrs	x15, spsr_el2
+	mrs	x16, sp_el2
+	stp	x15, x16, [x0, #CTX_SPSR_EL2]
 
-	mrs	x10, sp_el2
-	mrs	x11, tcr_el2
-	stp	x10, x11, [x0, #CTX_SP_EL2]
+	mrs	x9, tcr_el2
+	mrs	x10, tpidr_el2
+	stp	x9, x10, [x0, #CTX_TCR_EL2]
 
-	mrs	x12, tpidr_el2
-	mrs	x13, ttbr0_el2
-	stp	x12, x13, [x0, #CTX_TPIDR_EL2]
+	mrs	x11, ttbr0_el2
+	mrs	x12, vbar_el2
+	stp	x11, x12, [x0, #CTX_TTBR0_EL2]
 
-	mrs	x14, vbar_el2
-	mrs	x15, vmpidr_el2
-	stp	x14, x15, [x0, #CTX_VBAR_EL2]
+	mrs	x13, vmpidr_el2
+	mrs	x14, vpidr_el2
+	stp	x13, x14, [x0, #CTX_VMPIDR_EL2]
 
-	mrs	x16, vpidr_el2
-	mrs	x17, vtcr_el2
-	stp	x16, x17, [x0, #CTX_VPIDR_EL2]
-
-	mrs	x9, vttbr_el2
-	str	x9, [x0, #CTX_VTTBR_EL2]
+	mrs	x15, vtcr_el2
+	mrs	x16, vttbr_el2
+	stp	x15, x16, [x0, #CTX_VTCR_EL2]
 
 #if CTX_INCLUDE_MTE_REGS
-	mrs	x10, TFSR_EL2
-	str	x10, [x0, #CTX_TFSR_EL2]
+	mrs	x9, TFSR_EL2
+	str	x9, [x0, #CTX_TFSR_EL2]
 #endif
 
 #if ENABLE_MPAM_FOR_LOWER_ELS
-	mrs	x9, MPAM2_EL2
-	mrs	x10, MPAMHCR_EL2
-	stp	x9, x10, [x0, #CTX_MPAM2_EL2]
+	mrs	x10, MPAM2_EL2
+	str	x10, [x0, #CTX_MPAM2_EL2]
 
-	mrs	x11, MPAMVPM0_EL2
-	mrs	x12, MPAMVPM1_EL2
-	stp	x11, x12, [x0, #CTX_MPAMVPM0_EL2]
+	mrs	x11, MPAMHCR_EL2
+	mrs	x12, MPAMVPM0_EL2
+	stp	x11, x12, [x0, #CTX_MPAMHCR_EL2]
 
-	mrs	x13, MPAMVPM2_EL2
-	mrs	x14, MPAMVPM3_EL2
-	stp	x13, x14, [x0, #CTX_MPAMVPM2_EL2]
+	mrs	x13, MPAMVPM1_EL2
+	mrs	x14, MPAMVPM2_EL2
+	stp	x13, x14, [x0, #CTX_MPAMVPM1_EL2]
 
-	mrs	x15, MPAMVPM4_EL2
-	mrs	x16, MPAMVPM5_EL2
-	stp	x15, x16, [x0, #CTX_MPAMVPM4_EL2]
+	mrs	x15, MPAMVPM3_EL2
+	mrs	x16, MPAMVPM4_EL2
+	stp	x15, x16, [x0, #CTX_MPAMVPM3_EL2]
 
-	mrs	x17, MPAMVPM6_EL2
-	mrs	x9, MPAMVPM7_EL2
-	stp	x17, x9, [x0, #CTX_MPAMVPM6_EL2]
+	mrs	x9, MPAMVPM5_EL2
+	mrs	x10, MPAMVPM6_EL2
+	stp	x9, x10, [x0, #CTX_MPAMVPM5_EL2]
 
-	mrs	x10, MPAMVPMV_EL2
-	str	x10, [x0, #CTX_MPAMVPMV_EL2]
+	mrs	x11, MPAMVPM7_EL2
+	mrs	x12, MPAMVPMV_EL2
+	stp	x11, x12, [x0, #CTX_MPAMVPM7_EL2]
 #endif
 
-
 #if ARM_ARCH_AT_LEAST(8, 6)
-	mrs	x11, HAFGRTR_EL2
-	mrs	x12, HDFGRTR_EL2
-	stp	x11, x12, [x0, #CTX_HAFGRTR_EL2]
+	mrs	x13, HAFGRTR_EL2
+	mrs	x14, HDFGRTR_EL2
+	stp	x13, x14, [x0, #CTX_HAFGRTR_EL2]
 
-	mrs	x13, HDFGWTR_EL2
-	mrs	x14, HFGITR_EL2
-	stp	x13, x14, [x0, #CTX_HDFGWTR_EL2]
+	mrs	x15, HDFGWTR_EL2
+	mrs	x16, HFGITR_EL2
+	stp	x15, x16, [x0, #CTX_HDFGWTR_EL2]
 
-	mrs	x15, HFGRTR_EL2
-	mrs	x16, HFGWTR_EL2
-	stp	x15, x16, [x0, #CTX_HFGRTR_EL2]
+	mrs	x9, HFGRTR_EL2
+	mrs	x10, HFGWTR_EL2
+	stp	x9, x10, [x0, #CTX_HFGRTR_EL2]
 
-	mrs	x17, CNTPOFF_EL2
-	str	x17, [x0, #CTX_CNTPOFF_EL2]
+	mrs	x11, CNTPOFF_EL2
+	str	x11, [x0, #CTX_CNTPOFF_EL2]
 #endif
 
 #if ARM_ARCH_AT_LEAST(8, 4)
-	mrs	x9, cnthps_ctl_el2
-	mrs	x10, cnthps_cval_el2
-	stp	x9, x10, [x0, #CTX_CNTHPS_CTL_EL2]
-
-	mrs	x11, cnthps_tval_el2
-	mrs	x12, cnthvs_ctl_el2
-	stp	x11, x12, [x0, #CTX_CNTHPS_TVAL_EL2]
-
-	mrs	x13, cnthvs_cval_el2
-	mrs	x14, cnthvs_tval_el2
-	stp	x13, x14, [x0, #CTX_CNTHVS_CVAL_EL2]
-
-	mrs	x15, cnthv_ctl_el2
-	mrs	x16, cnthv_cval_el2
-	stp	x15, x16, [x0, #CTX_CNTHV_CTL_EL2]
-
-	mrs	x17, cnthv_tval_el2
-	mrs	x9, contextidr_el2
-	stp	x17, x9, [x0, #CTX_CNTHV_TVAL_EL2]
+	mrs	x12, contextidr_el2
+	str	x12, [x0, #CTX_CONTEXTIDR_EL2]
 
 #if CTX_INCLUDE_AARCH32_REGS
-	mrs	x10, sder32_el2
-	str	x10, [x0, #CTX_SDER32_EL2]
+	mrs	x13, sder32_el2
+	str	x13, [x0, #CTX_SDER32_EL2]
 #endif
-
-	mrs	x11, ttbr1_el2
-	str	x11, [x0, #CTX_TTBR1_EL2]
-
-	mrs	x12, vdisr_el2
-	str	x12, [x0, #CTX_VDISR_EL2]
+	mrs	x14, ttbr1_el2
+	mrs	x15, vdisr_el2
+	stp	x14, x15, [x0, #CTX_TTBR1_EL2]
 
 #if CTX_INCLUDE_NEVE_REGS
-	mrs	x13, vncr_el2
-	str	x13, [x0, #CTX_VNCR_EL2]
+	mrs	x16, vncr_el2
+	str	x16, [x0, #CTX_VNCR_EL2]
 #endif
 
-	mrs	x14, vsesr_el2
-	str	x14, [x0, #CTX_VSESR_EL2]
+	mrs	x9, vsesr_el2
+	mrs	x10, vstcr_el2
+	stp	x9, x10, [x0, #CTX_VSESR_EL2]
 
-	mrs	x15, vstcr_el2
-	str	x15, [x0, #CTX_VSTCR_EL2]
-
-	mrs	x16, vsttbr_el2
-	str	x16, [x0, #CTX_VSTTBR_EL2]
-
-	mrs	x17, TRFCR_EL2
-	str	x17, [x0, #CTX_TRFCR_EL2]
+	mrs	x11, vsttbr_el2
+	mrs	x12, TRFCR_EL2
+	stp	x11, x12, [x0, #CTX_VSTTBR_EL2]
 #endif
 
 #if ARM_ARCH_AT_LEAST(8, 5)
-	mrs	x9, scxtnum_el2
-	str	x9, [x0, #CTX_SCXTNUM_EL2]
+	mrs	x13, scxtnum_el2
+	str	x13, [x0, #CTX_SCXTNUM_EL2]
+#endif
+
+#if ENABLE_FEAT_HCX
+	mrs	x14, hcrx_el2
+	str	x14, [x0, #CTX_HCRX_EL2]
 #endif
 
 	ret
 endfunc el2_sysregs_context_save
 
+
 /* -----------------------------------------------------
  * The following function strictly follows the AArch64
- * PCS to use x9-x17 (temporary caller-saved registers)
+ * PCS to use x9-x16 (temporary caller-saved registers)
  * to restore EL2 system register context.  It assumes
  * that 'x0' is pointing to a 'el2_sys_regs' structure
  * from where the register context will be restored
@@ -246,7 +218,6 @@
  * -----------------------------------------------------
  */
 func el2_sysregs_context_restore
-
 	ldp	x9, x10, [x0, #CTX_ACTLR_EL2]
 	msr	actlr_el2, x9
 	msr	afsr0_el2, x10
@@ -257,74 +228,66 @@
 
 	ldp	x13, x14, [x0, #CTX_CNTHCTL_EL2]
 	msr	cnthctl_el2, x13
-	msr	cnthp_ctl_el2, x14
+	msr	cntvoff_el2, x14
 
-	ldp	x15, x16, [x0, #CTX_CNTHP_CVAL_EL2]
-	msr	cnthp_cval_el2, x15
-	msr	cnthp_tval_el2, x16
-
-	ldp	x17, x9, [x0, #CTX_CNTVOFF_EL2]
-	msr	cntvoff_el2, x17
-	msr	cptr_el2, x9
+	ldr	x15, [x0, #CTX_CPTR_EL2]
+	msr	cptr_el2, x15
 
 #if CTX_INCLUDE_AARCH32_REGS
-	ldp	x10, x11, [x0, #CTX_DBGVCR32_EL2]
-	msr	dbgvcr32_el2, x10
-#else
-	ldr	x11, [x0, #CTX_ELR_EL2]
+	ldr	x16, [x0, #CTX_DBGVCR32_EL2]
+	msr	dbgvcr32_el2, x16
 #endif
-	msr	elr_el2, x11
 
-	ldp	x14, x15, [x0, #CTX_ESR_EL2]
-	msr	esr_el2, x14
-	msr	far_el2, x15
+	ldp	x9, x10, [x0, #CTX_ELR_EL2]
+	msr	elr_el2, x9
+	msr	esr_el2, x10
 
-	ldp	x16, x17, [x0, #CTX_HACR_EL2]
-	msr	hacr_el2, x16
-	msr	hcr_el2, x17
+	ldp	x11, x12, [x0, #CTX_FAR_EL2]
+	msr	far_el2, x11
+	msr	hacr_el2, x12
 
-	ldp	x9, x10, [x0, #CTX_HPFAR_EL2]
-	msr	hpfar_el2, x9
-	msr	hstr_el2, x10
+	ldp	x13, x14, [x0, #CTX_HCR_EL2]
+	msr	hcr_el2, x13
+	msr	hpfar_el2, x14
 
-	ldp	x11, x12, [x0, #CTX_ICC_SRE_EL2]
-	msr	ICC_SRE_EL2, x11
-	msr	ICH_HCR_EL2, x12
+	ldp	x15, x16, [x0, #CTX_HSTR_EL2]
+	msr	hstr_el2, x15
+	msr	ICC_SRE_EL2, x16
 
-	ldp	x13, x14, [x0, #CTX_ICH_VMCR_EL2]
-	msr	ICH_VMCR_EL2, x13
-	msr	mair_el2, x14
+	ldp	x9, x10, [x0, #CTX_ICH_HCR_EL2]
+	msr	ICH_HCR_EL2, x9
+	msr	ICH_VMCR_EL2, x10
+
+	ldp	x11, x12, [x0, #CTX_MAIR_EL2]
+	msr	mair_el2, x11
+	msr	mdcr_el2, x12
 
 #if ENABLE_SPE_FOR_LOWER_ELS
-	ldp	x15, x16, [x0, #CTX_MDCR_EL2]
-	msr	PMSCR_EL2, x16
-#else
-	ldr	x15, [x0, #CTX_MDCR_EL2]
+	ldr	x13, [x0, #CTX_PMSCR_EL2]
+	msr	PMSCR_EL2, x13
 #endif
-	msr	mdcr_el2, x15
+	ldr	x14, [x0, #CTX_SCTLR_EL2]
+	msr	sctlr_el2, x14
 
-	ldp	x17, x9, [x0, #CTX_SCTLR_EL2]
-	msr	sctlr_el2, x17
-	msr	spsr_el2, x9
+	ldp	x15, x16, [x0, #CTX_SPSR_EL2]
+	msr	spsr_el2, x15
+	msr	sp_el2, x16
 
-	ldp	x10, x11, [x0, #CTX_SP_EL2]
-	msr	sp_el2, x10
-	msr	tcr_el2, x11
+	ldp	x9, x10, [x0, #CTX_TCR_EL2]
+	msr	tcr_el2, x9
+	msr	tpidr_el2, x10
 
-	ldp	x12, x13, [x0, #CTX_TPIDR_EL2]
-	msr	tpidr_el2, x12
-	msr	ttbr0_el2, x13
+	ldp	x11, x12, [x0, #CTX_TTBR0_EL2]
+	msr	ttbr0_el2, x11
+	msr	vbar_el2, x12
 
-	ldp	x13, x14, [x0, #CTX_VBAR_EL2]
-	msr	vbar_el2, x13
-	msr	vmpidr_el2, x14
+	ldp	x13, x14, [x0, #CTX_VMPIDR_EL2]
+	msr	vmpidr_el2, x13
+	msr	vpidr_el2, x14
 
-	ldp	x15, x16, [x0, #CTX_VPIDR_EL2]
-	msr	vpidr_el2, x15
-	msr	vtcr_el2, x16
-
-	ldr	x17, [x0, #CTX_VTTBR_EL2]
-	msr	vttbr_el2, x17
+	ldp	x15, x16, [x0, #CTX_VTCR_EL2]
+	msr	vtcr_el2, x15
+	msr	vttbr_el2, x16
 
 #if CTX_INCLUDE_MTE_REGS
 	ldr	x9, [x0, #CTX_TFSR_EL2]
@@ -332,100 +295,81 @@
 #endif
 
 #if ENABLE_MPAM_FOR_LOWER_ELS
-	ldp	x10, x11, [x0, #CTX_MPAM2_EL2]
+	ldr	x10, [x0, #CTX_MPAM2_EL2]
 	msr	MPAM2_EL2, x10
+
+	ldp	x11, x12, [x0, #CTX_MPAMHCR_EL2]
 	msr	MPAMHCR_EL2, x11
-
-	ldp	x12, x13, [x0, #CTX_MPAMVPM0_EL2]
 	msr	MPAMVPM0_EL2, x12
+
+	ldp	x13, x14, [x0, #CTX_MPAMVPM1_EL2]
 	msr	MPAMVPM1_EL2, x13
-
-	ldp	x14, x15, [x0, #CTX_MPAMVPM2_EL2]
 	msr	MPAMVPM2_EL2, x14
+
+	ldp	x15, x16, [x0, #CTX_MPAMVPM3_EL2]
 	msr	MPAMVPM3_EL2, x15
-
-	ldp	x16, x17, [x0, #CTX_MPAMVPM4_EL2]
 	msr	MPAMVPM4_EL2, x16
-	msr	MPAMVPM5_EL2, x17
 
-	ldp	x9, x10, [x0, #CTX_MPAMVPM6_EL2]
-	msr	MPAMVPM6_EL2, x9
-	msr	MPAMVPM7_EL2, x10
+	ldp	x9, x10, [x0, #CTX_MPAMVPM5_EL2]
+	msr	MPAMVPM5_EL2, x9
+	msr	MPAMVPM6_EL2, x10
 
-	ldr	x11, [x0, #CTX_MPAMVPMV_EL2]
-	msr	MPAMVPMV_EL2, x11
+	ldp	x11, x12, [x0, #CTX_MPAMVPM7_EL2]
+	msr	MPAMVPM7_EL2, x11
+	msr	MPAMVPMV_EL2, x12
 #endif
 
 #if ARM_ARCH_AT_LEAST(8, 6)
-	ldp	x12, x13, [x0, #CTX_HAFGRTR_EL2]
-	msr	HAFGRTR_EL2, x12
-	msr	HDFGRTR_EL2, x13
+	ldp	x13, x14, [x0, #CTX_HAFGRTR_EL2]
+	msr	HAFGRTR_EL2, x13
+	msr	HDFGRTR_EL2, x14
 
-	ldp	x14, x15, [x0, #CTX_HDFGWTR_EL2]
-	msr	HDFGWTR_EL2, x14
-	msr	HFGITR_EL2, x15
+	ldp	x15, x16, [x0, #CTX_HDFGWTR_EL2]
+	msr	HDFGWTR_EL2, x15
+	msr	HFGITR_EL2, x16
 
-	ldp	x16, x17, [x0, #CTX_HFGRTR_EL2]
-	msr	HFGRTR_EL2, x16
-	msr	HFGWTR_EL2, x17
+	ldp	x9, x10, [x0, #CTX_HFGRTR_EL2]
+	msr	HFGRTR_EL2, x9
+	msr	HFGWTR_EL2, x10
 
-	ldr	x9, [x0, #CTX_CNTPOFF_EL2]
-	msr	CNTPOFF_EL2, x9
+	ldr	x11, [x0, #CTX_CNTPOFF_EL2]
+	msr	CNTPOFF_EL2, x11
 #endif
 
 #if ARM_ARCH_AT_LEAST(8, 4)
-	ldp	x10, x11, [x0, #CTX_CNTHPS_CTL_EL2]
-	msr	cnthps_ctl_el2, x10
-	msr	cnthps_cval_el2, x11
-
-	ldp	x12, x13, [x0, #CTX_CNTHPS_TVAL_EL2]
-	msr	cnthps_tval_el2, x12
-	msr	cnthvs_ctl_el2, x13
-
-	ldp	x14, x15, [x0, #CTX_CNTHVS_CVAL_EL2]
-	msr	cnthvs_cval_el2, x14
-	msr	cnthvs_tval_el2, x15
-
-	ldp	x16, x17, [x0, #CTX_CNTHV_CTL_EL2]
-	msr	cnthv_ctl_el2, x16
-	msr	cnthv_cval_el2, x17
-
-	ldp	x9, x10, [x0, #CTX_CNTHV_TVAL_EL2]
-	msr	cnthv_tval_el2, x9
-	msr	contextidr_el2, x10
+	ldr	x12, [x0, #CTX_CONTEXTIDR_EL2]
+	msr	contextidr_el2, x12
 
 #if CTX_INCLUDE_AARCH32_REGS
-	ldr	x11, [x0, #CTX_SDER32_EL2]
-	msr	sder32_el2, x11
+	ldr	x13, [x0, #CTX_SDER32_EL2]
+	msr	sder32_el2, x13
 #endif
-
-	ldr	x12, [x0, #CTX_TTBR1_EL2]
-	msr	ttbr1_el2, x12
-
-	ldr	x13, [x0, #CTX_VDISR_EL2]
-	msr	vdisr_el2, x13
+	ldp	x14, x15, [x0, #CTX_TTBR1_EL2]
+	msr	ttbr1_el2, x14
+	msr	vdisr_el2, x15
 
 #if CTX_INCLUDE_NEVE_REGS
-	ldr	x14, [x0, #CTX_VNCR_EL2]
-	msr	vncr_el2, x14
+	ldr	x16, [x0, #CTX_VNCR_EL2]
+	msr	vncr_el2, x16
 #endif
 
-	ldr	x15, [x0, #CTX_VSESR_EL2]
-	msr	vsesr_el2, x15
+	ldp	x9, x10, [x0, #CTX_VSESR_EL2]
+	msr	vsesr_el2, x9
+	msr	vstcr_el2, x10
 
-	ldr	x16, [x0, #CTX_VSTCR_EL2]
-	msr	vstcr_el2, x16
-
-	ldr	x17, [x0, #CTX_VSTTBR_EL2]
-	msr	vsttbr_el2, x17
-
-	ldr	x9, [x0, #CTX_TRFCR_EL2]
-	msr	TRFCR_EL2, x9
+	ldp	x11, x12, [x0, #CTX_VSTTBR_EL2]
+	msr	vsttbr_el2, x11
+	msr	TRFCR_EL2, x12
 #endif
 
 #if ARM_ARCH_AT_LEAST(8, 5)
-	ldr	x10, [x0, #CTX_SCXTNUM_EL2]
-	msr	scxtnum_el2, x10
+	ldr	x13, [x0, #CTX_SCXTNUM_EL2]
+	msr	scxtnum_el2, x13
+#endif
+
+#if ENABLE_FEAT_HCX
+	ldr	x14, [x0, #CTX_HCRX_EL2]
+	msr	hcrx_el2, x14
 #endif
 
 	ret
@@ -763,13 +707,14 @@
 	str	x18, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_SP_EL0]
 
 	/* ----------------------------------------------------------
-	 * Check if earlier initialization MDCR_EL3.SCCD to 1 failed,
-	 * meaning that ARMv8-PMU is not implemented and PMCR_EL0
-	 * should be saved in non-secure context.
+	 * Check if earlier initialization MDCR_EL3.SCCD/MCCD to 1
+	 * failed, meaning that FEAT_PMUv3p5/7 is not implemented and
+	 * PMCR_EL0 should be saved in non-secure context.
 	 * ----------------------------------------------------------
 	 */
+	mov_imm	x10, (MDCR_SCCD_BIT | MDCR_MCCD_BIT)
 	mrs	x9, mdcr_el3
-	tst	x9, #MDCR_SCCD_BIT
+	tst	x9, x10
 	bne	1f
 
 	/* Secure Cycle Counter is not disabled */
@@ -858,13 +803,14 @@
 
 	/* ----------------------------------------------------------
 	 * Back to Non-secure state.
-	 * Check if earlier initialization MDCR_EL3.SCCD to 1 failed,
-	 * meaning that ARMv8-PMU is not implemented and PMCR_EL0
-	 * should be restored from non-secure context.
+	 * Check if earlier initialization MDCR_EL3.SCCD/MCCD to 1
+	 * failed, meaning that FEAT_PMUv3p5/7 is not implemented and
+	 * PMCR_EL0 should be restored from non-secure context.
 	 * ----------------------------------------------------------
 	 */
+	mov_imm	x1, (MDCR_SCCD_BIT | MDCR_MCCD_BIT)
 	mrs	x0, mdcr_el3
-	tst	x0, #MDCR_SCCD_BIT
+	tst	x0, x1
 	bne	2f
 	ldr	x0, [sp, #CTX_EL3STATE_OFFSET + CTX_PMCR_EL0]
 	msr	pmcr_el0, x0
@@ -965,6 +911,24 @@
 	msr	spsr_el3, x16
 	msr	elr_el3, x17
 
+#if IMAGE_BL31
+	/* ----------------------------------------------------------
+	 * Restore CPTR_EL3.
+	 * ZCR is only restored if SVE is supported and enabled.
+	 * Synchronization is required before zcr_el3 is addressed.
+	 * ----------------------------------------------------------
+	 */
+	ldp	x19, x20, [sp, #CTX_EL3STATE_OFFSET + CTX_CPTR_EL3]
+	msr	cptr_el3, x19
+
+	ands	x19, x19, #CPTR_EZ_BIT
+	beq	sve_not_enabled
+
+	isb
+	msr	S3_6_C1_C2_0, x20 /* zcr_el3 */
+sve_not_enabled:
+#endif
+
 #if IMAGE_BL31 && DYNAMIC_WORKAROUND_CVE_2018_3639
 	/* ----------------------------------------------------------
 	 * Restore mitigation state as it was on entry to EL3
@@ -995,6 +959,11 @@
  	 * ----------------------------------------------------------
 	 */
 	esb
+#else
+	dsb	sy
+#endif
+#ifdef IMAGE_BL31
+	str	xzr, [sp, #CTX_EL3STATE_OFFSET + CTX_IS_IN_EL3]
 #endif
 	exception_return
 
diff --git a/lib/el3_runtime/aarch64/context_mgmt.c b/lib/el3_runtime/aarch64/context_mgmt.c
index b460731..c69dc95 100644
--- a/lib/el3_runtime/aarch64/context_mgmt.c
+++ b/lib/el3_runtime/aarch64/context_mgmt.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -20,11 +20,16 @@
 #include <lib/el3_runtime/pubsub_events.h>
 #include <lib/extensions/amu.h>
 #include <lib/extensions/mpam.h>
+#include <lib/extensions/sme.h>
 #include <lib/extensions/spe.h>
 #include <lib/extensions/sve.h>
+#include <lib/extensions/sys_reg_trace.h>
+#include <lib/extensions/trbe.h>
+#include <lib/extensions/trf.h>
 #include <lib/extensions/twed.h>
 #include <lib/utils.h>
 
+static void manage_extensions_secure(cpu_context_t *ctx);
 
 /*******************************************************************************
  * Context management library initialisation routine. This library is used by
@@ -60,7 +65,7 @@
  *
  * To prepare the register state for entry call cm_prepare_el3_exit() and
  * el3_exit(). For Secure-EL1 cm_prepare_el3_exit() is equivalent to
- * cm_e1_sysreg_context_restore().
+ * cm_el1_sysregs_context_restore().
  ******************************************************************************/
 void cm_setup_context(cpu_context_t *ctx, const entry_point_info_t *ep)
 {
@@ -89,24 +94,49 @@
 	scr_el3 = read_scr();
 	scr_el3 &= ~(SCR_NS_BIT | SCR_RW_BIT | SCR_FIQ_BIT | SCR_IRQ_BIT |
 			SCR_ST_BIT | SCR_HCE_BIT);
+
+#if ENABLE_RME
+	/* When RME support is enabled, clear the NSE bit as well. */
+	scr_el3 &= ~SCR_NSE_BIT;
+#endif /* ENABLE_RME */
+
 	/*
 	 * SCR_NS: Set the security state of the next EL.
 	 */
-	if (security_state != SECURE)
+	if (security_state == NON_SECURE) {
 		scr_el3 |= SCR_NS_BIT;
+	}
+
+#if ENABLE_RME
+	/* Check for realm state if RME support enabled. */
+	if (security_state == REALM) {
+		scr_el3 |= SCR_NS_BIT | SCR_NSE_BIT | SCR_EnSCXT_BIT;
+	}
+#endif /* ENABLE_RME */
+
 	/*
 	 * SCR_EL3.RW: Set the execution state, AArch32 or AArch64, for next
 	 *  Exception level as specified by SPSR.
 	 */
-	if (GET_RW(ep->spsr) == MODE_RW_64)
+	if (GET_RW(ep->spsr) == MODE_RW_64) {
 		scr_el3 |= SCR_RW_BIT;
+	}
 	/*
 	 * SCR_EL3.ST: Traps Secure EL1 accesses to the Counter-timer Physical
 	 *  Secure timer registers to EL3, from AArch64 state only, if specified
 	 *  by the entrypoint attributes.
 	 */
-	if (EP_GET_ST(ep->h.attr) != 0U)
+	if (EP_GET_ST(ep->h.attr) != 0U) {
 		scr_el3 |= SCR_ST_BIT;
+	}
+
+	/*
+	 * If FEAT_HCX is enabled, enable access to HCRX_EL2 by setting
+	 * SCR_EL3.HXEn.
+	 */
+#if ENABLE_FEAT_HCX
+	scr_el3 |= SCR_HXEn_BIT;
+#endif
 
 #if RAS_TRAP_LOWER_EL_ERR_ACCESS
 	/*
@@ -140,43 +170,59 @@
 	 * If the Secure world wants to use pointer authentication,
 	 * CTX_INCLUDE_PAUTH_REGS must be set to 1.
 	 */
-	if (security_state == NON_SECURE)
+	if (security_state == NON_SECURE) {
 		scr_el3 |= SCR_API_BIT | SCR_APK_BIT;
+	}
 #endif /* !CTX_INCLUDE_PAUTH_REGS */
 
+#if !CTX_INCLUDE_MTE_REGS || ENABLE_ASSERTIONS
+	/* Get Memory Tagging Extension support level */
+	unsigned int mte = get_armv8_5_mte_support();
+#endif
 	/*
 	 * Enable MTE support. Support is enabled unilaterally for the normal
 	 * world, and only for the secure world when CTX_INCLUDE_MTE_REGS is
 	 * set.
 	 */
 #if CTX_INCLUDE_MTE_REGS
-	assert(get_armv8_5_mte_support() == MTE_IMPLEMENTED_ELX);
+	assert((mte == MTE_IMPLEMENTED_ELX) || (mte == MTE_IMPLEMENTED_ASY));
 	scr_el3 |= SCR_ATA_BIT;
 #else
-	unsigned int mte = get_armv8_5_mte_support();
-	if (mte == MTE_IMPLEMENTED_EL0) {
-		/*
-		 * Can enable MTE across both worlds as no MTE registers are
-		 * used
-		 */
-		scr_el3 |= SCR_ATA_BIT;
-	} else if (mte == MTE_IMPLEMENTED_ELX && security_state == NON_SECURE) {
-		/*
-		 * Can only enable MTE in Non-Secure world without register
-		 * saving
-		 */
+	/*
+	 * When MTE is only implemented at EL0, it can be enabled
+	 * across both worlds as no MTE registers are used.
+	 */
+	if ((mte == MTE_IMPLEMENTED_EL0) ||
+	/*
+	 * When MTE is implemented at all ELs, it can be only enabled
+	 * in Non-Secure world without register saving.
+	 */
+	  (((mte == MTE_IMPLEMENTED_ELX) || (mte == MTE_IMPLEMENTED_ASY)) &&
+	    (security_state == NON_SECURE))) {
 		scr_el3 |= SCR_ATA_BIT;
 	}
-#endif
+#endif	/* CTX_INCLUDE_MTE_REGS */
 
 #ifdef IMAGE_BL31
 	/*
 	 * SCR_EL3.IRQ, SCR_EL3.FIQ: Enable the physical FIQ and IRQ routing as
 	 *  indicated by the interrupt routing model for BL31.
+	 *
+	 * TODO: The interrupt routing model code is not updated for REALM
+	 * state. Use the default values of IRQ = FIQ = 0 for REALM security
+	 * state for now.
 	 */
-	scr_el3 |= get_scr_el3_from_routing_model(security_state);
+	if (security_state != REALM) {
+		scr_el3 |= get_scr_el3_from_routing_model(security_state);
+	}
 #endif
 
+	/* Save the initialized value of CPTR_EL3 register */
+	write_ctx_reg(get_el3state_ctx(ctx), CTX_CPTR_EL3, read_cptr_el3());
+	if (security_state == SECURE) {
+		manage_extensions_secure(ctx);
+	}
+
 	/*
 	 * SCR_EL3.HCE: Enable HVC instructions if next execution state is
 	 * AArch64 and next EL is EL2, or if next execution state is AArch32 and
@@ -214,6 +260,16 @@
 	}
 
 	/*
+	 * FEAT_AMUv1p1 virtual offset registers are only accessible from EL3
+	 * and EL2, when clear, this bit traps accesses from EL2 so we set it
+	 * to 1 when EL2 is present.
+	 */
+	if (is_armv8_6_feat_amuv1p1_present() &&
+		(el_implemented(2) != EL_IMPL_NONE)) {
+		scr_el3 |= SCR_AMVOFFEN_BIT;
+	}
+
+	/*
 	 * Initialise SCTLR_EL1 to the reset value corresponding to the target
 	 * execution state setting all fields rather than relying of the hw.
 	 * Some fields have architecturally UNKNOWN reset values and these are
@@ -225,9 +281,9 @@
 	 *  required by PSCI specification)
 	 */
 	sctlr_elx = (EP_GET_EE(ep->h.attr) != 0U) ? SCTLR_EE_BIT : 0U;
-	if (GET_RW(ep->spsr) == MODE_RW_64)
+	if (GET_RW(ep->spsr) == MODE_RW_64) {
 		sctlr_elx |= SCTLR_EL1_RES1;
-	else {
+	} else {
 		/*
 		 * If the target execution state is AArch32 then the following
 		 * fields need to be set.
@@ -273,7 +329,7 @@
 
 	/*
 	 * Store the initialised SCTLR_EL1 value in the cpu_context - SCTLR_EL2
-	 * and other EL2 registers are set up by cm_prepare_ns_entry() as they
+	 * and other EL2 registers are set up by cm_prepare_el3_exit() as they
 	 * are not part of the stored cpu_context.
 	 */
 	write_ctx_reg(get_el1_sysregs_ctx(ctx), CTX_SCTLR_EL1, sctlr_elx);
@@ -310,7 +366,7 @@
  * When EL2 is implemented but unused `el2_unused` is non-zero, otherwise
  * it is zero.
  ******************************************************************************/
-static void enable_extensions_nonsecure(bool el2_unused)
+static void manage_extensions_nonsecure(bool el2_unused, cpu_context_t *ctx)
 {
 #if IMAGE_BL31
 #if ENABLE_SPE_FOR_LOWER_ELS
@@ -318,20 +374,74 @@
 #endif
 
 #if ENABLE_AMU
-	amu_enable(el2_unused);
+	amu_enable(el2_unused, ctx);
 #endif
 
-#if ENABLE_SVE_FOR_NS
-	sve_enable(el2_unused);
+#if ENABLE_SME_FOR_NS
+	/* Enable SME, SVE, and FPU/SIMD for non-secure world. */
+	sme_enable(ctx);
+#elif ENABLE_SVE_FOR_NS
+	/* Enable SVE and FPU/SIMD for non-secure world. */
+	sve_enable(ctx);
 #endif
 
 #if ENABLE_MPAM_FOR_LOWER_ELS
 	mpam_enable(el2_unused);
 #endif
+
+#if ENABLE_TRBE_FOR_NS
+	trbe_enable();
+#endif /* ENABLE_TRBE_FOR_NS */
+
+#if ENABLE_SYS_REG_TRACE_FOR_NS
+	sys_reg_trace_enable(ctx);
+#endif /* ENABLE_SYS_REG_TRACE_FOR_NS */
+
+#if ENABLE_TRF_FOR_NS
+	trf_enable();
+#endif /* ENABLE_TRF_FOR_NS */
 #endif
 }
 
 /*******************************************************************************
+ * Enable architecture extensions on first entry to Secure world.
+ ******************************************************************************/
+static void manage_extensions_secure(cpu_context_t *ctx)
+{
+#if IMAGE_BL31
+ #if ENABLE_SME_FOR_NS
+  #if ENABLE_SME_FOR_SWD
+	/*
+	 * Enable SME, SVE, FPU/SIMD in secure context, secure manager must
+	 * ensure SME, SVE, and FPU/SIMD context properly managed.
+	 */
+	sme_enable(ctx);
+  #else /* ENABLE_SME_FOR_SWD */
+	/*
+	 * Disable SME, SVE, FPU/SIMD in secure context so non-secure world can
+	 * safely use the associated registers.
+	 */
+	sme_disable(ctx);
+  #endif /* ENABLE_SME_FOR_SWD */
+ #elif ENABLE_SVE_FOR_NS
+  #if ENABLE_SVE_FOR_SWD
+	/*
+	 * Enable SVE and FPU in secure context, secure manager must ensure that
+	 * the SVE and FPU register contexts are properly managed.
+	 */
+	sve_enable(ctx);
+ #else /* ENABLE_SVE_FOR_SWD */
+	/*
+	 * Disable SVE and FPU in secure context so non-secure world can safely
+	 * use them.
+	 */
+	sve_disable(ctx);
+  #endif /* ENABLE_SVE_FOR_SWD */
+ #endif /* ENABLE_SVE_FOR_NS */
+#endif /* IMAGE_BL31 */
+}
+
+/*******************************************************************************
  * The following function initializes the cpu_context for a CPU specified by
  * its `cpu_idx` for first use, and sets the initial entrypoint state as
  * specified by the entry_point_info structure.
@@ -357,7 +467,8 @@
 }
 
 /*******************************************************************************
- * Prepare the CPU system registers for first entry into secure or normal world
+ * Prepare the CPU system registers for first entry into realm, secure, or
+ * normal world.
  *
  * If execution is requested to EL2 or hyp mode, SCTLR_EL2 is initialized
  * If execution is requested to non-secure EL1 or svc mode, and the CPU supports
@@ -425,6 +536,8 @@
 			 * CPTR_EL2.TTA: Set to zero so that Non-secure System
 			 *  register accesses to the trace registers from both
 			 *  Execution states do not trap to EL2.
+			 *  If PE trace unit System registers are not implemented
+			 *  then this bit is reserved, and must be set to zero.
 			 *
 			 * CPTR_EL2.TFP: Set to zero so that Non-secure accesses
 			 *  to SIMD and floating-point functionality from both
@@ -439,7 +552,7 @@
 			 * architecturally UNKNOWN on reset and are set to zero
 			 * except for field(s) listed below.
 			 *
-			 * CNTHCTL_EL2.EL1PCEN: Set to one to disable traps to
+			 * CNTHCTL_EL2.EL1PTEN: Set to one to disable traps to
 			 *  Hyp mode of Non-secure EL0 and EL1 accesses to the
 			 *  physical timer registers.
 			 *
@@ -533,6 +646,11 @@
 			 *
 			 * MDCR_EL2.HPMN: Set to value of PMCR_EL0.N which is the
 			 *  architecturally-defined reset value.
+			 *
+			 * MDCR_EL2.E2TB: Set to zero so that the trace Buffer
+			 *  owning exception level is NS-EL1 and, tracing is
+			 *  prohibited at NS-EL2. These bits are RES0 when
+			 *  FEAT_TRBE is not implemented.
 			 */
 			mdcr_el2 = ((MDCR_EL2_RESET_VAL | MDCR_EL2_HLP |
 				     MDCR_EL2_HPMD) |
@@ -542,7 +660,8 @@
 				     MDCR_EL2_TDRA_BIT | MDCR_EL2_TDOSA_BIT |
 				     MDCR_EL2_TDA_BIT | MDCR_EL2_TDE_BIT |
 				     MDCR_EL2_HPME_BIT | MDCR_EL2_TPM_BIT |
-				     MDCR_EL2_TPMCR_BIT);
+				     MDCR_EL2_TPMCR_BIT |
+				     MDCR_EL2_E2TB(MDCR_EL2_E2TB_EL1));
 
 			write_mdcr_el2(mdcr_el2);
 
@@ -565,7 +684,7 @@
 			write_cnthp_ctl_el2(CNTHP_CTL_RESET_VAL &
 						~(CNTHP_CTL_ENABLE_BIT));
 		}
-		enable_extensions_nonsecure(el2_unused);
+		manage_extensions_nonsecure(el2_unused, ctx);
 	}
 
 	cm_el1_sysregs_context_restore(security_state);
@@ -581,10 +700,10 @@
 	u_register_t scr_el3 = read_scr();
 
 	/*
-	 * Always save the non-secure EL2 context, only save the
+	 * Always save the non-secure and realm EL2 context, only save the
 	 * S-EL2 context if S-EL2 is enabled.
 	 */
-	if ((security_state == NON_SECURE) ||
+	if ((security_state != SECURE) ||
 	    ((security_state == SECURE) && ((scr_el3 & SCR_EEL2_BIT) != 0U))) {
 		cpu_context_t *ctx;
 
@@ -603,10 +722,10 @@
 	u_register_t scr_el3 = read_scr();
 
 	/*
-	 * Always restore the non-secure EL2 context, only restore the
+	 * Always restore the non-secure and realm EL2 context, only restore the
 	 * S-EL2 context if S-EL2 is enabled.
 	 */
-	if ((security_state == NON_SECURE) ||
+	if ((security_state != SECURE) ||
 	    ((security_state == SECURE) && ((scr_el3 & SCR_EEL2_BIT) != 0U))) {
 		cpu_context_t *ctx;
 
diff --git a/lib/extensions/amu/aarch32/amu.c b/lib/extensions/amu/aarch32/amu.c
index 0f75f07..57b1158 100644
--- a/lib/extensions/amu/aarch32/amu.c
+++ b/lib/extensions/amu/aarch32/amu.c
@@ -1,236 +1,417 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <cdefs.h>
 #include <stdbool.h>
 
+#include "../amu_private.h"
 #include <arch.h>
 #include <arch_helpers.h>
-
+#include <common/debug.h>
 #include <lib/el3_runtime/pubsub_events.h>
 #include <lib/extensions/amu.h>
-#include <lib/extensions/amu_private.h>
 
 #include <plat/common/platform.h>
 
-static struct amu_ctx amu_ctxs[PLATFORM_CORE_COUNT];
+struct amu_ctx {
+	uint64_t group0_cnts[AMU_GROUP0_MAX_COUNTERS];
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint64_t group1_cnts[AMU_GROUP1_MAX_COUNTERS];
+#endif
 
-/* Check if AMUv1 for Armv8.4 or 8.6 is implemented */
-bool amu_supported(void)
+	uint16_t group0_enable;
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint16_t group1_enable;
+#endif
+};
+
+static struct amu_ctx amu_ctxs_[PLATFORM_CORE_COUNT];
+
+CASSERT((sizeof(amu_ctxs_[0].group0_enable) * CHAR_BIT) <= AMU_GROUP0_MAX_COUNTERS,
+	amu_ctx_group0_enable_cannot_represent_all_group0_counters);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+CASSERT((sizeof(amu_ctxs_[0].group1_enable) * CHAR_BIT) <= AMU_GROUP1_MAX_COUNTERS,
+	amu_ctx_group1_enable_cannot_represent_all_group1_counters);
+#endif
+
+static inline __unused uint32_t read_id_pfr0_amu(void)
 {
-	uint32_t features = read_id_pfr0() >> ID_PFR0_AMU_SHIFT;
-
-	features &= ID_PFR0_AMU_MASK;
-	return ((features == 1U) || (features == 2U));
+	return (read_id_pfr0() >> ID_PFR0_AMU_SHIFT) &
+		ID_PFR0_AMU_MASK;
 }
 
-#if AMU_GROUP1_NR_COUNTERS
-/* Check if group 1 counters is implemented */
-bool amu_group1_supported(void)
+static inline __unused void write_hcptr_tam(uint32_t value)
 {
-	uint32_t features = read_amcfgr() >> AMCFGR_NCG_SHIFT;
+	write_hcptr((read_hcptr() & ~TAM_BIT) |
+		((value << TAM_SHIFT) & TAM_BIT));
+}
 
-	return (features & AMCFGR_NCG_MASK) == 1U;
+static inline __unused void write_amcr_cg1rz(uint32_t value)
+{
+	write_amcr((read_amcr() & ~AMCR_CG1RZ_BIT) |
+		((value << AMCR_CG1RZ_SHIFT) & AMCR_CG1RZ_BIT));
+}
+
+static inline __unused uint32_t read_amcfgr_ncg(void)
+{
+	return (read_amcfgr() >> AMCFGR_NCG_SHIFT) &
+		AMCFGR_NCG_MASK;
+}
+
+static inline __unused uint32_t read_amcgcr_cg0nc(void)
+{
+	return (read_amcgcr() >> AMCGCR_CG0NC_SHIFT) &
+		AMCGCR_CG0NC_MASK;
+}
+
+static inline __unused uint32_t read_amcgcr_cg1nc(void)
+{
+	return (read_amcgcr() >> AMCGCR_CG1NC_SHIFT) &
+		AMCGCR_CG1NC_MASK;
+}
+
+static inline __unused uint32_t read_amcntenset0_px(void)
+{
+	return (read_amcntenset0() >> AMCNTENSET0_Pn_SHIFT) &
+		AMCNTENSET0_Pn_MASK;
+}
+
+static inline __unused uint32_t read_amcntenset1_px(void)
+{
+	return (read_amcntenset1() >> AMCNTENSET1_Pn_SHIFT) &
+		AMCNTENSET1_Pn_MASK;
+}
+
+static inline __unused void write_amcntenset0_px(uint32_t px)
+{
+	uint32_t value = read_amcntenset0();
+
+	value &= ~AMCNTENSET0_Pn_MASK;
+	value |= (px << AMCNTENSET0_Pn_SHIFT) &
+		AMCNTENSET0_Pn_MASK;
+
+	write_amcntenset0(value);
+}
+
+static inline __unused void write_amcntenset1_px(uint32_t px)
+{
+	uint32_t value = read_amcntenset1();
+
+	value &= ~AMCNTENSET1_Pn_MASK;
+	value |= (px << AMCNTENSET1_Pn_SHIFT) &
+		AMCNTENSET1_Pn_MASK;
+
+	write_amcntenset1(value);
+}
+
+static inline __unused void write_amcntenclr0_px(uint32_t px)
+{
+	uint32_t value = read_amcntenclr0();
+
+	value &= ~AMCNTENCLR0_Pn_MASK;
+	value |= (px << AMCNTENCLR0_Pn_SHIFT) & AMCNTENCLR0_Pn_MASK;
+
+	write_amcntenclr0(value);
+}
+
+static inline __unused void write_amcntenclr1_px(uint32_t px)
+{
+	uint32_t value = read_amcntenclr1();
+
+	value &= ~AMCNTENCLR1_Pn_MASK;
+	value |= (px << AMCNTENCLR1_Pn_SHIFT) & AMCNTENCLR1_Pn_MASK;
+
+	write_amcntenclr1(value);
+}
+
+static __unused bool amu_supported(void)
+{
+	return read_id_pfr0_amu() >= ID_PFR0_AMU_V1;
+}
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+static __unused bool amu_group1_supported(void)
+{
+	return read_amcfgr_ncg() > 0U;
 }
 #endif
 
 /*
- * Enable counters. This function is meant to be invoked
- * by the context management library before exiting from EL3.
+ * Enable counters. This function is meant to be invoked by the context
+ * management library before exiting from EL3.
  */
 void amu_enable(bool el2_unused)
 {
-	if (!amu_supported()) {
+	uint32_t id_pfr0_amu;		/* AMU version */
+
+	uint32_t amcfgr_ncg;		/* Number of counter groups */
+	uint32_t amcgcr_cg0nc;		/* Number of group 0 counters */
+
+	uint32_t amcntenset0_px = 0x0;	/* Group 0 enable mask */
+	uint32_t amcntenset1_px = 0x0;	/* Group 1 enable mask */
+
+	id_pfr0_amu = read_id_pfr0_amu();
+	if (id_pfr0_amu == ID_PFR0_AMU_NOT_SUPPORTED) {
+		/*
+		 * If the AMU is unsupported, nothing needs to be done.
+		 */
+
 		return;
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Check and set presence of group 1 counters */
-	if (!amu_group1_supported()) {
-		ERROR("AMU Counter Group 1 is not implemented\n");
-		panic();
-	}
-
-	/* Check number of group 1 counters */
-	uint32_t cnt_num = (read_amcgcr() >> AMCGCR_CG1NC_SHIFT) &
-				AMCGCR_CG1NC_MASK;
-	VERBOSE("%s%u. %s%u\n",
-		"Number of AMU Group 1 Counters ", cnt_num,
-		"Requested number ", AMU_GROUP1_NR_COUNTERS);
-
-	if (cnt_num < AMU_GROUP1_NR_COUNTERS) {
-		ERROR("%s%u is less than %s%u\n",
-		"Number of AMU Group 1 Counters ", cnt_num,
-		"Requested number ", AMU_GROUP1_NR_COUNTERS);
-		panic();
-	}
-#endif
-
 	if (el2_unused) {
-		uint64_t v;
 		/*
-		 * Non-secure access from EL0 or EL1 to the Activity Monitor
-		 * registers do not trap to EL2.
+		 * HCPTR.TAM: Set to zero so any accesses to the Activity
+		 * Monitor registers do not trap to EL2.
 		 */
-		v = read_hcptr();
-		v &= ~TAM_BIT;
-		write_hcptr(v);
+		write_hcptr_tam(0U);
 	}
 
-	/* Enable group 0 counters */
-	write_amcntenset0(AMU_GROUP0_COUNTERS_MASK);
+	/*
+	 * Retrieve the number of architected counters. All of these counters
+	 * are enabled by default.
+	 */
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Enable group 1 counters */
-	write_amcntenset1(AMU_GROUP1_COUNTERS_MASK);
+	amcgcr_cg0nc = read_amcgcr_cg0nc();
+	amcntenset0_px = (UINT32_C(1) << (amcgcr_cg0nc)) - 1U;
+
+	assert(amcgcr_cg0nc <= AMU_AMCGCR_CG0NC_MAX);
+
+	/*
+	 * The platform may opt to enable specific auxiliary counters. This can
+	 * be done via the common FCONF getter, or via the platform-implemented
+	 * function.
+	 */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	const struct amu_topology *topology;
+
+#if ENABLE_AMU_FCONF
+	topology = FCONF_GET_PROPERTY(amu, config, topology);
+#else
+	topology = plat_amu_topology();
+#endif /* ENABLE_AMU_FCONF */
+
+	if (topology != NULL) {
+		unsigned int core_pos = plat_my_core_pos();
+
+		amcntenset1_el0_px = topology->cores[core_pos].enable;
+	} else {
+		ERROR("AMU: failed to generate AMU topology\n");
+	}
+#endif /* ENABLE_AMU_AUXILIARY_COUNTERS */
+
+	/*
+	 * Enable the requested counters.
+	 */
+
+	write_amcntenset0_px(amcntenset0_px);
+
+	amcfgr_ncg = read_amcfgr_ncg();
+	if (amcfgr_ncg > 0U) {
+		write_amcntenset1_px(amcntenset1_px);
+
+#if !ENABLE_AMU_AUXILIARY_COUNTERS
+		VERBOSE("AMU: auxiliary counters detected but support is disabled\n");
+#endif
+	}
+
+	/* Initialize FEAT_AMUv1p1 features if present. */
+	if (id_pfr0_amu < ID_PFR0_AMU_V1P1) {
+		return;
+	}
+
+#if AMU_RESTRICT_COUNTERS
+	/*
+	 * FEAT_AMUv1p1 adds a register field to restrict access to group 1
+	 * counters at all but the highest implemented EL.  This is controlled
+	 * with the AMU_RESTRICT_COUNTERS compile time flag, when set, system
+	 * register reads at lower ELs return zero.  Reads from the memory
+	 * mapped view are unaffected.
+	 */
+	VERBOSE("AMU group 1 counter access restricted.\n");
+	write_amcr_cg1rz(1U);
+#else
+	write_amcr_cg1rz(0U);
 #endif
 }
 
 /* Read the group 0 counter identified by the given `idx`. */
-uint64_t amu_group0_cnt_read(unsigned int idx)
+static uint64_t amu_group0_cnt_read(unsigned int idx)
 {
 	assert(amu_supported());
-	assert(idx < AMU_GROUP0_NR_COUNTERS);
+	assert(idx < read_amcgcr_cg0nc());
 
 	return amu_group0_cnt_read_internal(idx);
 }
 
 /* Write the group 0 counter identified by the given `idx` with `val` */
-void amu_group0_cnt_write(unsigned  int idx, uint64_t val)
+static void amu_group0_cnt_write(unsigned  int idx, uint64_t val)
 {
 	assert(amu_supported());
-	assert(idx < AMU_GROUP0_NR_COUNTERS);
+	assert(idx < read_amcgcr_cg0nc());
 
 	amu_group0_cnt_write_internal(idx, val);
 	isb();
 }
 
-#if AMU_GROUP1_NR_COUNTERS
+#if ENABLE_AMU_AUXILIARY_COUNTERS
 /* Read the group 1 counter identified by the given `idx` */
-uint64_t amu_group1_cnt_read(unsigned  int idx)
+static uint64_t amu_group1_cnt_read(unsigned  int idx)
 {
 	assert(amu_supported());
 	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
+	assert(idx < read_amcgcr_cg1nc());
 
 	return amu_group1_cnt_read_internal(idx);
 }
 
 /* Write the group 1 counter identified by the given `idx` with `val` */
-void amu_group1_cnt_write(unsigned  int idx, uint64_t val)
+static void amu_group1_cnt_write(unsigned  int idx, uint64_t val)
 {
 	assert(amu_supported());
 	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
+	assert(idx < read_amcgcr_cg1nc());
 
 	amu_group1_cnt_write_internal(idx, val);
 	isb();
 }
-
-/*
- * Program the event type register for the given `idx` with
- * the event number `val`
- */
-void amu_group1_set_evtype(unsigned int idx, unsigned int val)
-{
-	assert(amu_supported());
-	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
-
-	amu_group1_set_evtype_internal(idx, val);
-	isb();
-}
-#endif	/* AMU_GROUP1_NR_COUNTERS */
+#endif
 
 static void *amu_context_save(const void *arg)
 {
-	struct amu_ctx *ctx = &amu_ctxs[plat_my_core_pos()];
-	unsigned int i;
+	uint32_t i;
 
-	if (!amu_supported()) {
-		return (void *)-1;
+	unsigned int core_pos;
+	struct amu_ctx *ctx;
+
+	uint32_t id_pfr0_amu;	/* AMU version */
+	uint32_t amcgcr_cg0nc;	/* Number of group 0 counters */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint32_t amcfgr_ncg;	/* Number of counter groups */
+	uint32_t amcgcr_cg1nc;	/* Number of group 1 counters */
+#endif
+
+	id_pfr0_amu = read_id_pfr0_amu();
+	if (id_pfr0_amu == ID_PFR0_AMU_NOT_SUPPORTED) {
+		return (void *)0;
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	if (!amu_group1_supported()) {
-		return (void *)-1;
-	}
-#endif
-	/* Assert that group 0/1 counter configuration is what we expect */
-	assert(read_amcntenset0_el0() == AMU_GROUP0_COUNTERS_MASK);
+	core_pos = plat_my_core_pos();
+	ctx = &amu_ctxs_[core_pos];
 
-#if AMU_GROUP1_NR_COUNTERS
-	assert(read_amcntenset1_el0() == AMU_GROUP1_COUNTERS_MASK);
+	amcgcr_cg0nc = read_amcgcr_cg0nc();
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	amcfgr_ncg = read_amcfgr_ncg();
+	amcgcr_cg1nc = (amcfgr_ncg > 0U) ? read_amcgcr_cg1nc() : 0U;
 #endif
+
 	/*
-	 * Disable group 0/1 counters to avoid other observers like SCP sampling
-	 * counter values from the future via the memory mapped view.
+	 * Disable all AMU counters.
 	 */
-	write_amcntenclr0(AMU_GROUP0_COUNTERS_MASK);
 
-#if AMU_GROUP1_NR_COUNTERS
-	write_amcntenclr1(AMU_GROUP1_COUNTERS_MASK);
+	ctx->group0_enable = read_amcntenset0_px();
+	write_amcntenclr0_px(ctx->group0_enable);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	if (amcfgr_ncg > 0U) {
+		ctx->group1_enable = read_amcntenset1_px();
+		write_amcntenclr1_px(ctx->group1_enable);
+	}
 #endif
-	isb();
 
-	/* Save all group 0 counters */
-	for (i = 0U; i < AMU_GROUP0_NR_COUNTERS; i++) {
+	/*
+	 * Save the counters to the local context.
+	 */
+
+	isb(); /* Ensure counters have been stopped */
+
+	for (i = 0U; i < amcgcr_cg0nc; i++) {
 		ctx->group0_cnts[i] = amu_group0_cnt_read(i);
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Save group 1 counters */
-	for (i = 0U; i < AMU_GROUP1_NR_COUNTERS; i++) {
-		if ((AMU_GROUP1_COUNTERS_MASK & (1U << i)) != 0U) {
-			ctx->group1_cnts[i] = amu_group1_cnt_read(i);
-		}
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	for (i = 0U; i < amcgcr_cg1nc; i++) {
+		ctx->group1_cnts[i] = amu_group1_cnt_read(i);
 	}
 #endif
+
 	return (void *)0;
 }
 
 static void *amu_context_restore(const void *arg)
 {
-	struct amu_ctx *ctx = &amu_ctxs[plat_my_core_pos()];
-	unsigned int i;
+	uint32_t i;
 
-	if (!amu_supported()) {
-		return (void *)-1;
-	}
+	unsigned int core_pos;
+	struct amu_ctx *ctx;
 
-#if AMU_GROUP1_NR_COUNTERS
-	if (!amu_group1_supported()) {
-		return (void *)-1;
-	}
-#endif
-	/* Counters were disabled in `amu_context_save()` */
-	assert(read_amcntenset0_el0() == 0U);
+	uint32_t id_pfr0_amu;	/* AMU version */
 
-#if AMU_GROUP1_NR_COUNTERS
-	assert(read_amcntenset1_el0() == 0U);
+	uint32_t amcfgr_ncg;	/* Number of counter groups */
+	uint32_t amcgcr_cg0nc;	/* Number of group 0 counters */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint32_t amcgcr_cg1nc;	/* Number of group 1 counters */
 #endif
 
-	/* Restore all group 0 counters */
-	for (i = 0U; i < AMU_GROUP0_NR_COUNTERS; i++) {
+	id_pfr0_amu = read_id_pfr0_amu();
+	if (id_pfr0_amu == ID_PFR0_AMU_NOT_SUPPORTED) {
+		return (void *)0;
+	}
+
+	core_pos = plat_my_core_pos();
+	ctx = &amu_ctxs_[core_pos];
+
+	amcfgr_ncg = read_amcfgr_ncg();
+	amcgcr_cg0nc = read_amcgcr_cg0nc();
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	amcgcr_cg1nc = (amcfgr_ncg > 0U) ? read_amcgcr_cg1nc() : 0U;
+#endif
+
+	/*
+	 * Sanity check that all counters were disabled when the context was
+	 * previously saved.
+	 */
+
+	assert(read_amcntenset0_px() == 0U);
+
+	if (amcfgr_ncg > 0U) {
+		assert(read_amcntenset1_px() == 0U);
+	}
+
+	/*
+	 * Restore the counter values from the local context.
+	 */
+
+	for (i = 0U; i < amcgcr_cg0nc; i++) {
 		amu_group0_cnt_write(i, ctx->group0_cnts[i]);
 	}
 
-	/* Restore group 0 counter configuration */
-	write_amcntenset0(AMU_GROUP0_COUNTERS_MASK);
-
-#if AMU_GROUP1_NR_COUNTERS
-	/* Restore group 1 counters */
-	for (i = 0U; i < AMU_GROUP1_NR_COUNTERS; i++) {
-		if ((AMU_GROUP1_COUNTERS_MASK & (1U << i)) != 0U) {
-			amu_group1_cnt_write(i, ctx->group1_cnts[i]);
-		}
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	for (i = 0U; i < amcgcr_cg1nc; i++) {
+		amu_group1_cnt_write(i, ctx->group1_cnts[i]);
 	}
+#endif
 
-	/* Restore group 1 counter configuration */
-	write_amcntenset1(AMU_GROUP1_COUNTERS_MASK);
+	/*
+	 * Re-enable counters that were disabled during context save.
+	 */
+
+	write_amcntenset0_px(ctx->group0_enable);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	if (amcfgr_ncg > 0U) {
+		write_amcntenset1_px(ctx->group1_enable);
+	}
 #endif
 
 	return (void *)0;
diff --git a/lib/extensions/amu/aarch32/amu_helpers.S b/lib/extensions/amu/aarch32/amu_helpers.S
index effb8e5..8ac7678 100644
--- a/lib/extensions/amu/aarch32/amu_helpers.S
+++ b/lib/extensions/amu/aarch32/amu_helpers.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -75,15 +75,16 @@
 
 1:
 	stcopr16	r2, r3, AMEVCNTR00	/* index 0 */
-	bx 		lr
+	bx		lr
 	stcopr16	r2, r3, AMEVCNTR01	/* index 1 */
-	bx 		lr
+	bx		lr
 	stcopr16	r2, r3, AMEVCNTR02	/* index 2 */
-	bx 		lr
+	bx		lr
 	stcopr16	r2, r3, AMEVCNTR03	/* index 3 */
-	bx 		lr
+	bx		lr
 endfunc amu_group0_cnt_write_internal
 
+#if ENABLE_AMU_AUXILIARY_COUNTERS
 /*
  * uint64_t amu_group1_cnt_read_internal(int idx);
  *
@@ -169,37 +170,37 @@
 	bx	r1
 
 1:
-	stcopr16	r2, r3,	AMEVCNTR10	/* index 0 */
+	stcopr16	r2, r3, AMEVCNTR10	/* index 0 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR11	/* index 1 */
+	stcopr16	r2, r3, AMEVCNTR11	/* index 1 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR12	/* index 2 */
+	stcopr16	r2, r3, AMEVCNTR12	/* index 2 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR13	/* index 3 */
+	stcopr16	r2, r3, AMEVCNTR13	/* index 3 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR14	/* index 4 */
+	stcopr16	r2, r3, AMEVCNTR14	/* index 4 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR15	/* index 5 */
+	stcopr16	r2, r3, AMEVCNTR15	/* index 5 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR16	/* index 6 */
+	stcopr16	r2, r3, AMEVCNTR16	/* index 6 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR17	/* index 7 */
+	stcopr16	r2, r3, AMEVCNTR17	/* index 7 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR18	/* index 8 */
+	stcopr16	r2, r3, AMEVCNTR18	/* index 8 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR19	/* index 9 */
+	stcopr16	r2, r3, AMEVCNTR19	/* index 9 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1A	/* index 10 */
+	stcopr16	r2, r3, AMEVCNTR1A	/* index 10 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1B	/* index 11 */
+	stcopr16	r2, r3, AMEVCNTR1B	/* index 11 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1C	/* index 12 */
+	stcopr16	r2, r3, AMEVCNTR1C	/* index 12 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1D	/* index 13 */
+	stcopr16	r2, r3, AMEVCNTR1D	/* index 13 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1E	/* index 14 */
+	stcopr16	r2, r3, AMEVCNTR1E	/* index 14 */
 	bx		lr
-	stcopr16	r2, r3,	AMEVCNTR1F	/* index 15 */
+	stcopr16	r2, r3, AMEVCNTR1F	/* index 15 */
 	bx		lr
 endfunc amu_group1_cnt_write_internal
 
@@ -234,36 +235,37 @@
 	bx	r2
 
 1:
-	stcopr	r1,	AMEVTYPER10 /* index 0 */
+	stcopr	r1, AMEVTYPER10 /* index 0 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER11 /* index 1 */
+	stcopr	r1, AMEVTYPER11 /* index 1 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER12 /* index 2 */
+	stcopr	r1, AMEVTYPER12 /* index 2 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER13 /* index 3 */
+	stcopr	r1, AMEVTYPER13 /* index 3 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER14 /* index 4 */
+	stcopr	r1, AMEVTYPER14 /* index 4 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER15 /* index 5 */
+	stcopr	r1, AMEVTYPER15 /* index 5 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER16 /* index 6 */
+	stcopr	r1, AMEVTYPER16 /* index 6 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER17 /* index 7 */
+	stcopr	r1, AMEVTYPER17 /* index 7 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER18 /* index 8 */
+	stcopr	r1, AMEVTYPER18 /* index 8 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER19 /* index 9 */
+	stcopr	r1, AMEVTYPER19 /* index 9 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1A /* index 10 */
+	stcopr	r1, AMEVTYPER1A /* index 10 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1B /* index 11 */
+	stcopr	r1, AMEVTYPER1B /* index 11 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1C /* index 12 */
+	stcopr	r1, AMEVTYPER1C /* index 12 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1D /* index 13 */
+	stcopr	r1, AMEVTYPER1D /* index 13 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1E /* index 14 */
+	stcopr	r1, AMEVTYPER1E /* index 14 */
 	bx	lr
-	stcopr	r1,	AMEVTYPER1F /* index 15 */
+	stcopr	r1, AMEVTYPER1F /* index 15 */
 	bx	lr
 endfunc amu_group1_set_evtype_internal
+#endif
diff --git a/lib/extensions/amu/aarch64/amu.c b/lib/extensions/amu/aarch64/amu.c
index 4997363..d329c3d 100644
--- a/lib/extensions/amu/aarch64/amu.c
+++ b/lib/extensions/amu/aarch64/amu.c
@@ -1,245 +1,634 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <cdefs.h>
+#include <inttypes.h>
 #include <stdbool.h>
+#include <stdint.h>
 
+#include "../amu_private.h"
 #include <arch.h>
+#include <arch_features.h>
 #include <arch_helpers.h>
-
+#include <common/debug.h>
 #include <lib/el3_runtime/pubsub_events.h>
 #include <lib/extensions/amu.h>
-#include <lib/extensions/amu_private.h>
 
 #include <plat/common/platform.h>
 
-static struct amu_ctx amu_ctxs[PLATFORM_CORE_COUNT];
+#if ENABLE_AMU_FCONF
+#	include <lib/fconf/fconf.h>
+#	include <lib/fconf/fconf_amu_getter.h>
+#endif
 
-/* Check if AMUv1 for Armv8.4 or 8.6 is implemented */
-bool amu_supported(void)
+#if ENABLE_MPMM
+#	include <lib/mpmm/mpmm.h>
+#endif
+
+struct amu_ctx {
+	uint64_t group0_cnts[AMU_GROUP0_MAX_COUNTERS];
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint64_t group1_cnts[AMU_GROUP1_MAX_COUNTERS];
+#endif
+
+	/* Architected event counter 1 does not have an offset register */
+	uint64_t group0_voffsets[AMU_GROUP0_MAX_COUNTERS - 1U];
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint64_t group1_voffsets[AMU_GROUP1_MAX_COUNTERS];
+#endif
+
+	uint16_t group0_enable;
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint16_t group1_enable;
+#endif
+};
+
+static struct amu_ctx amu_ctxs_[PLATFORM_CORE_COUNT];
+
+CASSERT((sizeof(amu_ctxs_[0].group0_enable) * CHAR_BIT) <= AMU_GROUP0_MAX_COUNTERS,
+	amu_ctx_group0_enable_cannot_represent_all_group0_counters);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+CASSERT((sizeof(amu_ctxs_[0].group1_enable) * CHAR_BIT) <= AMU_GROUP1_MAX_COUNTERS,
+	amu_ctx_group1_enable_cannot_represent_all_group1_counters);
+#endif
+
+static inline __unused uint64_t read_id_aa64pfr0_el1_amu(void)
 {
-	uint64_t features = read_id_aa64pfr0_el1() >> ID_AA64PFR0_AMU_SHIFT;
-
-	features &= ID_AA64PFR0_AMU_MASK;
-	return ((features == 1U) || (features == 2U));
+	return (read_id_aa64pfr0_el1() >> ID_AA64PFR0_AMU_SHIFT) &
+		ID_AA64PFR0_AMU_MASK;
 }
 
-#if AMU_GROUP1_NR_COUNTERS
-/* Check if group 1 counters is implemented */
-bool amu_group1_supported(void)
+static inline __unused uint64_t read_hcr_el2_amvoffen(void)
 {
-	uint64_t features = read_amcfgr_el0() >> AMCFGR_EL0_NCG_SHIFT;
+	return (read_hcr_el2() & HCR_AMVOFFEN_BIT) >>
+		HCR_AMVOFFEN_SHIFT;
+}
 
-	return (features & AMCFGR_EL0_NCG_MASK) == 1U;
+static inline __unused void write_cptr_el2_tam(uint64_t value)
+{
+	write_cptr_el2((read_cptr_el2() & ~CPTR_EL2_TAM_BIT) |
+		((value << CPTR_EL2_TAM_SHIFT) & CPTR_EL2_TAM_BIT));
+}
+
+static inline __unused void write_cptr_el3_tam(cpu_context_t *ctx, uint64_t tam)
+{
+	uint64_t value = read_ctx_reg(get_el3state_ctx(ctx), CTX_CPTR_EL3);
+
+	value &= ~TAM_BIT;
+	value |= (tam << TAM_SHIFT) & TAM_BIT;
+
+	write_ctx_reg(get_el3state_ctx(ctx), CTX_CPTR_EL3, value);
+}
+
+static inline __unused void write_hcr_el2_amvoffen(uint64_t value)
+{
+	write_hcr_el2((read_hcr_el2() & ~HCR_AMVOFFEN_BIT) |
+		((value << HCR_AMVOFFEN_SHIFT) & HCR_AMVOFFEN_BIT));
+}
+
+static inline __unused void write_amcr_el0_cg1rz(uint64_t value)
+{
+	write_amcr_el0((read_amcr_el0() & ~AMCR_CG1RZ_BIT) |
+		((value << AMCR_CG1RZ_SHIFT) & AMCR_CG1RZ_BIT));
+}
+
+static inline __unused uint64_t read_amcfgr_el0_ncg(void)
+{
+	return (read_amcfgr_el0() >> AMCFGR_EL0_NCG_SHIFT) &
+		AMCFGR_EL0_NCG_MASK;
+}
+
+static inline __unused uint64_t read_amcgcr_el0_cg0nc(void)
+{
+	return (read_amcgcr_el0() >> AMCGCR_EL0_CG0NC_SHIFT) &
+		AMCGCR_EL0_CG0NC_MASK;
+}
+
+static inline __unused uint64_t read_amcg1idr_el0_voff(void)
+{
+	return (read_amcg1idr_el0() >> AMCG1IDR_VOFF_SHIFT) &
+		AMCG1IDR_VOFF_MASK;
+}
+
+static inline __unused uint64_t read_amcgcr_el0_cg1nc(void)
+{
+	return (read_amcgcr_el0() >> AMCGCR_EL0_CG1NC_SHIFT) &
+		AMCGCR_EL0_CG1NC_MASK;
+}
+
+static inline __unused uint64_t read_amcntenset0_el0_px(void)
+{
+	return (read_amcntenset0_el0() >> AMCNTENSET0_EL0_Pn_SHIFT) &
+		AMCNTENSET0_EL0_Pn_MASK;
+}
+
+static inline __unused uint64_t read_amcntenset1_el0_px(void)
+{
+	return (read_amcntenset1_el0() >> AMCNTENSET1_EL0_Pn_SHIFT) &
+		AMCNTENSET1_EL0_Pn_MASK;
+}
+
+static inline __unused void write_amcntenset0_el0_px(uint64_t px)
+{
+	uint64_t value = read_amcntenset0_el0();
+
+	value &= ~AMCNTENSET0_EL0_Pn_MASK;
+	value |= (px << AMCNTENSET0_EL0_Pn_SHIFT) & AMCNTENSET0_EL0_Pn_MASK;
+
+	write_amcntenset0_el0(value);
+}
+
+static inline __unused void write_amcntenset1_el0_px(uint64_t px)
+{
+	uint64_t value = read_amcntenset1_el0();
+
+	value &= ~AMCNTENSET1_EL0_Pn_MASK;
+	value |= (px << AMCNTENSET1_EL0_Pn_SHIFT) & AMCNTENSET1_EL0_Pn_MASK;
+
+	write_amcntenset1_el0(value);
+}
+
+static inline __unused void write_amcntenclr0_el0_px(uint64_t px)
+{
+	uint64_t value = read_amcntenclr0_el0();
+
+	value &= ~AMCNTENCLR0_EL0_Pn_MASK;
+	value |= (px << AMCNTENCLR0_EL0_Pn_SHIFT) & AMCNTENCLR0_EL0_Pn_MASK;
+
+	write_amcntenclr0_el0(value);
+}
+
+static inline __unused void write_amcntenclr1_el0_px(uint64_t px)
+{
+	uint64_t value = read_amcntenclr1_el0();
+
+	value &= ~AMCNTENCLR1_EL0_Pn_MASK;
+	value |= (px << AMCNTENCLR1_EL0_Pn_SHIFT) & AMCNTENCLR1_EL0_Pn_MASK;
+
+	write_amcntenclr1_el0(value);
+}
+
+static __unused bool amu_supported(void)
+{
+	return read_id_aa64pfr0_el1_amu() >= ID_AA64PFR0_AMU_V1;
+}
+
+static __unused bool amu_v1p1_supported(void)
+{
+	return read_id_aa64pfr0_el1_amu() >= ID_AA64PFR0_AMU_V1P1;
+}
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+static __unused bool amu_group1_supported(void)
+{
+	return read_amcfgr_el0_ncg() > 0U;
 }
 #endif
 
 /*
- * Enable counters. This function is meant to be invoked
- * by the context management library before exiting from EL3.
+ * Enable counters. This function is meant to be invoked by the context
+ * management library before exiting from EL3.
  */
-void amu_enable(bool el2_unused)
+void amu_enable(bool el2_unused, cpu_context_t *ctx)
 {
-	uint64_t v;
+	uint64_t id_aa64pfr0_el1_amu;		/* AMU version */
 
-	if (!amu_supported()) {
+	uint64_t amcfgr_el0_ncg;		/* Number of counter groups */
+	uint64_t amcgcr_el0_cg0nc;		/* Number of group 0 counters */
+
+	uint64_t amcntenset0_el0_px = 0x0;	/* Group 0 enable mask */
+	uint64_t amcntenset1_el0_px = 0x0;	/* Group 1 enable mask */
+
+	id_aa64pfr0_el1_amu = read_id_aa64pfr0_el1_amu();
+	if (id_aa64pfr0_el1_amu == ID_AA64PFR0_AMU_NOT_SUPPORTED) {
+		/*
+		 * If the AMU is unsupported, nothing needs to be done.
+		 */
+
 		return;
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Check and set presence of group 1 counters */
-	if (!amu_group1_supported()) {
-		ERROR("AMU Counter Group 1 is not implemented\n");
-		panic();
-	}
-
-	/* Check number of group 1 counters */
-	uint64_t cnt_num = (read_amcgcr_el0() >> AMCGCR_EL0_CG1NC_SHIFT) &
-				AMCGCR_EL0_CG1NC_MASK;
-	VERBOSE("%s%llu. %s%u\n",
-		"Number of AMU Group 1 Counters ", cnt_num,
-		"Requested number ", AMU_GROUP1_NR_COUNTERS);
-
-	if (cnt_num < AMU_GROUP1_NR_COUNTERS) {
-		ERROR("%s%llu is less than %s%u\n",
-		"Number of AMU Group 1 Counters ", cnt_num,
-		"Requested number ", AMU_GROUP1_NR_COUNTERS);
-		panic();
-	}
-#endif
-
 	if (el2_unused) {
 		/*
-		 * CPTR_EL2.TAM: Set to zero so any accesses to
-		 * the Activity Monitor registers do not trap to EL2.
+		 * CPTR_EL2.TAM: Set to zero so any accesses to the Activity
+		 * Monitor registers do not trap to EL2.
 		 */
-		v = read_cptr_el2();
-		v &= ~CPTR_EL2_TAM_BIT;
-		write_cptr_el2(v);
+		write_cptr_el2_tam(0U);
 	}
 
 	/*
-	 * CPTR_EL3.TAM: Set to zero so that any accesses to
+	 * Retrieve and update the CPTR_EL3 value from the context mentioned
+	 * in 'ctx'. Set CPTR_EL3.TAM to zero so that any accesses to
 	 * the Activity Monitor registers do not trap to EL3.
 	 */
-	v = read_cptr_el3();
-	v &= ~TAM_BIT;
-	write_cptr_el3(v);
+	write_cptr_el3_tam(ctx, 0U);
 
-	/* Enable group 0 counters */
-	write_amcntenset0_el0(AMU_GROUP0_COUNTERS_MASK);
+	/*
+	 * Retrieve the number of architected counters. All of these counters
+	 * are enabled by default.
+	 */
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Enable group 1 counters */
-	write_amcntenset1_el0(AMU_GROUP1_COUNTERS_MASK);
+	amcgcr_el0_cg0nc = read_amcgcr_el0_cg0nc();
+	amcntenset0_el0_px = (UINT64_C(1) << (amcgcr_el0_cg0nc)) - 1U;
+
+	assert(amcgcr_el0_cg0nc <= AMU_AMCGCR_CG0NC_MAX);
+
+	/*
+	 * The platform may opt to enable specific auxiliary counters. This can
+	 * be done via the common FCONF getter, or via the platform-implemented
+	 * function.
+	 */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	const struct amu_topology *topology;
+
+#if ENABLE_AMU_FCONF
+	topology = FCONF_GET_PROPERTY(amu, config, topology);
+#else
+	topology = plat_amu_topology();
+#endif /* ENABLE_AMU_FCONF */
+
+	if (topology != NULL) {
+		unsigned int core_pos = plat_my_core_pos();
+
+		amcntenset1_el0_px = topology->cores[core_pos].enable;
+	} else {
+		ERROR("AMU: failed to generate AMU topology\n");
+	}
+#endif /* ENABLE_AMU_AUXILIARY_COUNTERS */
+
+	/*
+	 * Enable the requested counters.
+	 */
+
+	write_amcntenset0_el0_px(amcntenset0_el0_px);
+
+	amcfgr_el0_ncg = read_amcfgr_el0_ncg();
+	if (amcfgr_el0_ncg > 0U) {
+		write_amcntenset1_el0_px(amcntenset1_el0_px);
+
+#if !ENABLE_AMU_AUXILIARY_COUNTERS
+		VERBOSE("AMU: auxiliary counters detected but support is disabled\n");
+#endif
+	}
+
+	/* Initialize FEAT_AMUv1p1 features if present. */
+	if (id_aa64pfr0_el1_amu >= ID_AA64PFR0_AMU_V1P1) {
+		if (el2_unused) {
+			/*
+			 * Make sure virtual offsets are disabled if EL2 not
+			 * used.
+			 */
+			write_hcr_el2_amvoffen(0U);
+		}
+
+#if AMU_RESTRICT_COUNTERS
+		/*
+		 * FEAT_AMUv1p1 adds a register field to restrict access to
+		 * group 1 counters at all but the highest implemented EL. This
+		 * is controlled with the `AMU_RESTRICT_COUNTERS` compile time
+		 * flag, when set, system register reads at lower ELs return
+		 * zero. Reads from the memory mapped view are unaffected.
+		 */
+		VERBOSE("AMU group 1 counter access restricted.\n");
+		write_amcr_el0_cg1rz(1U);
+#else
+		write_amcr_el0_cg1rz(0U);
+#endif
+	}
+
+#if ENABLE_MPMM
+	mpmm_enable();
 #endif
 }
 
 /* Read the group 0 counter identified by the given `idx`. */
-uint64_t amu_group0_cnt_read(unsigned int idx)
+static uint64_t amu_group0_cnt_read(unsigned int idx)
 {
 	assert(amu_supported());
-	assert(idx < AMU_GROUP0_NR_COUNTERS);
+	assert(idx < read_amcgcr_el0_cg0nc());
 
 	return amu_group0_cnt_read_internal(idx);
 }
 
 /* Write the group 0 counter identified by the given `idx` with `val` */
-void amu_group0_cnt_write(unsigned  int idx, uint64_t val)
+static void amu_group0_cnt_write(unsigned  int idx, uint64_t val)
 {
 	assert(amu_supported());
-	assert(idx < AMU_GROUP0_NR_COUNTERS);
+	assert(idx < read_amcgcr_el0_cg0nc());
 
 	amu_group0_cnt_write_internal(idx, val);
 	isb();
 }
 
-#if AMU_GROUP1_NR_COUNTERS
+/*
+ * Unlike with auxiliary counters, we cannot detect at runtime whether an
+ * architected counter supports a virtual offset. These are instead fixed
+ * according to FEAT_AMUv1p1, but this switch will need to be updated if later
+ * revisions of FEAT_AMU add additional architected counters.
+ */
+static bool amu_group0_voffset_supported(uint64_t idx)
+{
+	switch (idx) {
+	case 0U:
+	case 2U:
+	case 3U:
+		return true;
+
+	case 1U:
+		return false;
+
+	default:
+		ERROR("AMU: can't set up virtual offset for unknown "
+		      "architected counter %" PRIu64 "!\n", idx);
+
+		panic();
+	}
+}
+
+/*
+ * Read the group 0 offset register for a given index. Index must be 0, 2,
+ * or 3, the register for 1 does not exist.
+ *
+ * Using this function requires FEAT_AMUv1p1 support.
+ */
+static uint64_t amu_group0_voffset_read(unsigned int idx)
+{
+	assert(amu_v1p1_supported());
+	assert(idx < read_amcgcr_el0_cg0nc());
+	assert(idx != 1U);
+
+	return amu_group0_voffset_read_internal(idx);
+}
+
+/*
+ * Write the group 0 offset register for a given index. Index must be 0, 2, or
+ * 3, the register for 1 does not exist.
+ *
+ * Using this function requires FEAT_AMUv1p1 support.
+ */
+static void amu_group0_voffset_write(unsigned int idx, uint64_t val)
+{
+	assert(amu_v1p1_supported());
+	assert(idx < read_amcgcr_el0_cg0nc());
+	assert(idx != 1U);
+
+	amu_group0_voffset_write_internal(idx, val);
+	isb();
+}
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
 /* Read the group 1 counter identified by the given `idx` */
-uint64_t amu_group1_cnt_read(unsigned  int idx)
+static uint64_t amu_group1_cnt_read(unsigned int idx)
 {
 	assert(amu_supported());
 	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
+	assert(idx < read_amcgcr_el0_cg1nc());
 
 	return amu_group1_cnt_read_internal(idx);
 }
 
 /* Write the group 1 counter identified by the given `idx` with `val` */
-void amu_group1_cnt_write(unsigned  int idx, uint64_t val)
+static void amu_group1_cnt_write(unsigned int idx, uint64_t val)
 {
 	assert(amu_supported());
 	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
+	assert(idx < read_amcgcr_el0_cg1nc());
 
 	amu_group1_cnt_write_internal(idx, val);
 	isb();
 }
 
 /*
- * Program the event type register for the given `idx` with
- * the event number `val`
+ * Read the group 1 offset register for a given index.
+ *
+ * Using this function requires FEAT_AMUv1p1 support.
  */
-void amu_group1_set_evtype(unsigned int idx, unsigned int val)
+static uint64_t amu_group1_voffset_read(unsigned int idx)
 {
-	assert(amu_supported());
+	assert(amu_v1p1_supported());
 	assert(amu_group1_supported());
-	assert(idx < AMU_GROUP1_NR_COUNTERS);
+	assert(idx < read_amcgcr_el0_cg1nc());
+	assert((read_amcg1idr_el0_voff() & (UINT64_C(1) << idx)) != 0U);
 
-	amu_group1_set_evtype_internal(idx, val);
+	return amu_group1_voffset_read_internal(idx);
+}
+
+/*
+ * Write the group 1 offset register for a given index.
+ *
+ * Using this function requires FEAT_AMUv1p1 support.
+ */
+static void amu_group1_voffset_write(unsigned int idx, uint64_t val)
+{
+	assert(amu_v1p1_supported());
+	assert(amu_group1_supported());
+	assert(idx < read_amcgcr_el0_cg1nc());
+	assert((read_amcg1idr_el0_voff() & (UINT64_C(1) << idx)) != 0U);
+
+	amu_group1_voffset_write_internal(idx, val);
 	isb();
 }
-#endif	/* AMU_GROUP1_NR_COUNTERS */
+#endif
 
 static void *amu_context_save(const void *arg)
 {
-	struct amu_ctx *ctx = &amu_ctxs[plat_my_core_pos()];
-	unsigned int i;
+	uint64_t i, j;
 
-	if (!amu_supported()) {
-		return (void *)-1;
+	unsigned int core_pos;
+	struct amu_ctx *ctx;
+
+	uint64_t id_aa64pfr0_el1_amu;	/* AMU version */
+	uint64_t hcr_el2_amvoffen;	/* AMU virtual offsets enabled */
+	uint64_t amcgcr_el0_cg0nc;	/* Number of group 0 counters */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint64_t amcg1idr_el0_voff;	/* Auxiliary counters with virtual offsets */
+	uint64_t amcfgr_el0_ncg;	/* Number of counter groups */
+	uint64_t amcgcr_el0_cg1nc;	/* Number of group 1 counters */
+#endif
+
+	id_aa64pfr0_el1_amu = read_id_aa64pfr0_el1_amu();
+	if (id_aa64pfr0_el1_amu == ID_AA64PFR0_AMU_NOT_SUPPORTED) {
+		return (void *)0;
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	if (!amu_group1_supported()) {
-		return (void *)-1;
-	}
-#endif
-	/* Assert that group 0/1 counter configuration is what we expect */
-	assert(read_amcntenset0_el0() == AMU_GROUP0_COUNTERS_MASK);
+	core_pos = plat_my_core_pos();
+	ctx = &amu_ctxs_[core_pos];
 
-#if AMU_GROUP1_NR_COUNTERS
-	assert(read_amcntenset1_el0() == AMU_GROUP1_COUNTERS_MASK);
+	amcgcr_el0_cg0nc = read_amcgcr_el0_cg0nc();
+	hcr_el2_amvoffen = (id_aa64pfr0_el1_amu >= ID_AA64PFR0_AMU_V1P1) ?
+		read_hcr_el2_amvoffen() : 0U;
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	amcfgr_el0_ncg = read_amcfgr_el0_ncg();
+	amcgcr_el0_cg1nc = (amcfgr_el0_ncg > 0U) ? read_amcgcr_el0_cg1nc() : 0U;
+	amcg1idr_el0_voff = (hcr_el2_amvoffen != 0U) ? read_amcg1idr_el0_voff() : 0U;
 #endif
+
 	/*
-	 * Disable group 0/1 counters to avoid other observers like SCP sampling
-	 * counter values from the future via the memory mapped view.
+	 * Disable all AMU counters.
 	 */
-	write_amcntenclr0_el0(AMU_GROUP0_COUNTERS_MASK);
 
-#if AMU_GROUP1_NR_COUNTERS
-	write_amcntenclr1_el0(AMU_GROUP1_COUNTERS_MASK);
+	ctx->group0_enable = read_amcntenset0_el0_px();
+	write_amcntenclr0_el0_px(ctx->group0_enable);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	if (amcfgr_el0_ncg > 0U) {
+		ctx->group1_enable = read_amcntenset1_el0_px();
+		write_amcntenclr1_el0_px(ctx->group1_enable);
+	}
 #endif
-	isb();
 
-	/* Save all group 0 counters */
-	for (i = 0U; i < AMU_GROUP0_NR_COUNTERS; i++) {
+	/*
+	 * Save the counters to the local context.
+	 */
+
+	isb(); /* Ensure counters have been stopped */
+
+	for (i = 0U; i < amcgcr_el0_cg0nc; i++) {
 		ctx->group0_cnts[i] = amu_group0_cnt_read(i);
 	}
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Save group 1 counters */
-	for (i = 0U; i < AMU_GROUP1_NR_COUNTERS; i++) {
-		if ((AMU_GROUP1_COUNTERS_MASK & (1U << i)) != 0U) {
-			ctx->group1_cnts[i] = amu_group1_cnt_read(i);
-		}
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	for (i = 0U; i < amcgcr_el0_cg1nc; i++) {
+		ctx->group1_cnts[i] = amu_group1_cnt_read(i);
 	}
 #endif
+
+	/*
+	 * Save virtual offsets for counters that offer them.
+	 */
+
+	if (hcr_el2_amvoffen != 0U) {
+		for (i = 0U, j = 0U; i < amcgcr_el0_cg0nc; i++) {
+			if (!amu_group0_voffset_supported(i)) {
+				continue; /* No virtual offset */
+			}
+
+			ctx->group0_voffsets[j++] = amu_group0_voffset_read(i);
+		}
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+		for (i = 0U, j = 0U; i < amcgcr_el0_cg1nc; i++) {
+			if ((amcg1idr_el0_voff >> i) & 1U) {
+				continue; /* No virtual offset */
+			}
+
+			ctx->group1_voffsets[j++] = amu_group1_voffset_read(i);
+		}
+#endif
+	}
+
 	return (void *)0;
 }
 
 static void *amu_context_restore(const void *arg)
 {
-	struct amu_ctx *ctx = &amu_ctxs[plat_my_core_pos()];
-	unsigned int i;
+	uint64_t i, j;
 
-	if (!amu_supported()) {
-		return (void *)-1;
-	}
+	unsigned int core_pos;
+	struct amu_ctx *ctx;
 
-#if AMU_GROUP1_NR_COUNTERS
-	if (!amu_group1_supported()) {
-		return (void *)-1;
-	}
-#endif
-	/* Counters were disabled in `amu_context_save()` */
-	assert(read_amcntenset0_el0() == 0U);
+	uint64_t id_aa64pfr0_el1_amu;	/* AMU version */
 
-#if AMU_GROUP1_NR_COUNTERS
-	assert(read_amcntenset1_el0() == 0U);
+	uint64_t hcr_el2_amvoffen;	/* AMU virtual offsets enabled */
+
+	uint64_t amcfgr_el0_ncg;	/* Number of counter groups */
+	uint64_t amcgcr_el0_cg0nc;	/* Number of group 0 counters */
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	uint64_t amcgcr_el0_cg1nc;	/* Number of group 1 counters */
+	uint64_t amcg1idr_el0_voff;	/* Auxiliary counters with virtual offsets */
 #endif
 
-	/* Restore all group 0 counters */
-	for (i = 0U; i < AMU_GROUP0_NR_COUNTERS; i++) {
+	id_aa64pfr0_el1_amu = read_id_aa64pfr0_el1_amu();
+	if (id_aa64pfr0_el1_amu == ID_AA64PFR0_AMU_NOT_SUPPORTED) {
+		return (void *)0;
+	}
+
+	core_pos = plat_my_core_pos();
+	ctx = &amu_ctxs_[core_pos];
+
+	amcfgr_el0_ncg = read_amcfgr_el0_ncg();
+	amcgcr_el0_cg0nc = read_amcgcr_el0_cg0nc();
+
+	hcr_el2_amvoffen = (id_aa64pfr0_el1_amu >= ID_AA64PFR0_AMU_V1P1) ?
+		read_hcr_el2_amvoffen() : 0U;
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	amcgcr_el0_cg1nc = (amcfgr_el0_ncg > 0U) ? read_amcgcr_el0_cg1nc() : 0U;
+	amcg1idr_el0_voff = (hcr_el2_amvoffen != 0U) ? read_amcg1idr_el0_voff() : 0U;
+#endif
+
+	/*
+	 * Sanity check that all counters were disabled when the context was
+	 * previously saved.
+	 */
+
+	assert(read_amcntenset0_el0_px() == 0U);
+
+	if (amcfgr_el0_ncg > 0U) {
+		assert(read_amcntenset1_el0_px() == 0U);
+	}
+
+	/*
+	 * Restore the counter values from the local context.
+	 */
+
+	for (i = 0U; i < amcgcr_el0_cg0nc; i++) {
 		amu_group0_cnt_write(i, ctx->group0_cnts[i]);
 	}
 
-	/* Restore group 0 counter configuration */
-	write_amcntenset0_el0(AMU_GROUP0_COUNTERS_MASK);
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	for (i = 0U; i < amcgcr_el0_cg1nc; i++) {
+		amu_group1_cnt_write(i, ctx->group1_cnts[i]);
+	}
+#endif
 
-#if AMU_GROUP1_NR_COUNTERS
-	/* Restore group 1 counters */
-	for (i = 0U; i < AMU_GROUP1_NR_COUNTERS; i++) {
-		if ((AMU_GROUP1_COUNTERS_MASK & (1U << i)) != 0U) {
-			amu_group1_cnt_write(i, ctx->group1_cnts[i]);
+	/*
+	 * Restore virtual offsets for counters that offer them.
+	 */
+
+	if (hcr_el2_amvoffen != 0U) {
+		for (i = 0U, j = 0U; i < amcgcr_el0_cg0nc; i++) {
+			if (!amu_group0_voffset_supported(i)) {
+				continue; /* No virtual offset */
+			}
+
+			amu_group0_voffset_write(i, ctx->group0_voffsets[j++]);
 		}
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+		for (i = 0U, j = 0U; i < amcgcr_el0_cg1nc; i++) {
+			if ((amcg1idr_el0_voff >> i) & 1U) {
+				continue; /* No virtual offset */
+			}
+
+			amu_group1_voffset_write(i, ctx->group1_voffsets[j++]);
+		}
+#endif
 	}
 
-	/* Restore group 1 counter configuration */
-	write_amcntenset1_el0(AMU_GROUP1_COUNTERS_MASK);
+	/*
+	 * Re-enable counters that were disabled during context save.
+	 */
+
+	write_amcntenset0_el0_px(ctx->group0_enable);
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+	if (amcfgr_el0_ncg > 0) {
+		write_amcntenset1_el0_px(ctx->group1_enable);
+	}
+#endif
+
+#if ENABLE_MPMM
+	mpmm_enable();
 #endif
 
 	return (void *)0;
diff --git a/lib/extensions/amu/aarch64/amu_helpers.S b/lib/extensions/amu/aarch64/amu_helpers.S
index 89007a3..0f6d799 100644
--- a/lib/extensions/amu/aarch64/amu_helpers.S
+++ b/lib/extensions/amu/aarch64/amu_helpers.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,6 +14,12 @@
 	.globl	amu_group1_cnt_write_internal
 	.globl	amu_group1_set_evtype_internal
 
+	/* FEAT_AMUv1p1 virtualisation offset register functions */
+	.globl	amu_group0_voffset_read_internal
+	.globl	amu_group0_voffset_write_internal
+	.globl	amu_group1_voffset_read_internal
+	.globl	amu_group1_voffset_write_internal
+
 /*
  * uint64_t amu_group0_cnt_read_internal(int idx);
  *
@@ -77,6 +83,7 @@
 	write	AMEVCNTR03_EL0		/* index 3 */
 endfunc amu_group0_cnt_write_internal
 
+#if ENABLE_AMU_AUXILIARY_COUNTERS
 /*
  * uint64_t amu_group1_cnt_read_internal(int idx);
  *
@@ -211,3 +218,172 @@
 	write	AMEVTYPER1E_EL0		/* index 14 */
 	write	AMEVTYPER1F_EL0		/* index 15 */
 endfunc amu_group1_set_evtype_internal
+#endif
+
+/*
+ * Accessor functions for virtual offset registers added with FEAT_AMUv1p1
+ */
+
+/*
+ * uint64_t amu_group0_voffset_read_internal(int idx);
+ *
+ * Given `idx`, read the corresponding AMU virtual offset register
+ * and return it in `x0`.
+ */
+func amu_group0_voffset_read_internal
+	adr	x1, 1f
+#if ENABLE_ASSERTIONS
+	/*
+	 * It can be dangerous to call this function with an
+	 * out of bounds index.  Ensure `idx` is valid.
+	 */
+	tst	x0, #~3
+	ASM_ASSERT(eq)
+	/* Make sure idx != 1 since AMEVCNTVOFF01_EL2 does not exist */
+	cmp	x0, #1
+	ASM_ASSERT(ne)
+#endif
+	/*
+	 * Given `idx` calculate address of mrs/ret instruction pair
+	 * in the table below.
+	 */
+	add	x1, x1, x0, lsl #3	/* each mrs/ret sequence is 8 bytes */
+#if ENABLE_BTI
+	add	x1, x1, x0, lsl #2	/* + "bti j" instruction */
+#endif
+	br	x1
+
+1:	read	AMEVCNTVOFF00_EL2	/* index 0 */
+	.skip	8			/* AMEVCNTVOFF01_EL2 does not exist */
+#if ENABLE_BTI
+	.skip	4
+#endif
+	read	AMEVCNTVOFF02_EL2	/* index 2 */
+	read	AMEVCNTVOFF03_EL2	/* index 3 */
+endfunc amu_group0_voffset_read_internal
+
+/*
+ * void amu_group0_voffset_write_internal(int idx, uint64_t val);
+ *
+ * Given `idx`, write `val` to the corresponding AMU virtual offset register.
+ */
+func amu_group0_voffset_write_internal
+	adr	x2, 1f
+#if ENABLE_ASSERTIONS
+	/*
+	 * It can be dangerous to call this function with an
+	 * out of bounds index.  Ensure `idx` is valid.
+	 */
+	tst	x0, #~3
+	ASM_ASSERT(eq)
+	/* Make sure idx != 1 since AMEVCNTVOFF01_EL2 does not exist */
+	cmp	x0, #1
+	ASM_ASSERT(ne)
+#endif
+	/*
+	 * Given `idx` calculate address of mrs/ret instruction pair
+	 * in the table below.
+	 */
+	add	x2, x2, x0, lsl #3	/* each msr/ret sequence is 8 bytes */
+#if ENABLE_BTI
+	add	x2, x2, x0, lsl #2	/* + "bti j" instruction */
+#endif
+	br	x2
+
+1:	write	AMEVCNTVOFF00_EL2	/* index 0 */
+	.skip	8			/* AMEVCNTVOFF01_EL2 does not exist */
+#if ENABLE_BTI
+	.skip	4
+#endif
+	write	AMEVCNTVOFF02_EL2	/* index 2 */
+	write	AMEVCNTVOFF03_EL2	/* index 3 */
+endfunc amu_group0_voffset_write_internal
+
+#if ENABLE_AMU_AUXILIARY_COUNTERS
+/*
+ * uint64_t amu_group1_voffset_read_internal(int idx);
+ *
+ * Given `idx`, read the corresponding AMU virtual offset register
+ * and return it in `x0`.
+ */
+func amu_group1_voffset_read_internal
+	adr	x1, 1f
+#if ENABLE_ASSERTIONS
+	/*
+	 * It can be dangerous to call this function with an
+	 * out of bounds index.  Ensure `idx` is valid.
+	 */
+	tst	x0, #~0xF
+	ASM_ASSERT(eq)
+#endif
+	/*
+	 * Given `idx` calculate address of mrs/ret instruction pair
+	 * in the table below.
+	 */
+	add	x1, x1, x0, lsl #3	/* each mrs/ret sequence is 8 bytes */
+#if ENABLE_BTI
+	add	x1, x1, x0, lsl #2	/* + "bti j" instruction */
+#endif
+	br	x1
+
+1:	read	AMEVCNTVOFF10_EL2	/* index 0 */
+	read	AMEVCNTVOFF11_EL2	/* index 1 */
+	read	AMEVCNTVOFF12_EL2	/* index 2 */
+	read	AMEVCNTVOFF13_EL2	/* index 3 */
+	read	AMEVCNTVOFF14_EL2	/* index 4 */
+	read	AMEVCNTVOFF15_EL2	/* index 5 */
+	read	AMEVCNTVOFF16_EL2	/* index 6 */
+	read	AMEVCNTVOFF17_EL2	/* index 7 */
+	read	AMEVCNTVOFF18_EL2	/* index 8 */
+	read	AMEVCNTVOFF19_EL2	/* index 9 */
+	read	AMEVCNTVOFF1A_EL2	/* index 10 */
+	read	AMEVCNTVOFF1B_EL2	/* index 11 */
+	read	AMEVCNTVOFF1C_EL2	/* index 12 */
+	read	AMEVCNTVOFF1D_EL2	/* index 13 */
+	read	AMEVCNTVOFF1E_EL2	/* index 14 */
+	read	AMEVCNTVOFF1F_EL2	/* index 15 */
+endfunc amu_group1_voffset_read_internal
+
+/*
+ * void amu_group1_voffset_write_internal(int idx, uint64_t val);
+ *
+ * Given `idx`, write `val` to the corresponding AMU virtual offset register.
+ */
+func amu_group1_voffset_write_internal
+	adr	x2, 1f
+#if ENABLE_ASSERTIONS
+	/*
+	 * It can be dangerous to call this function with an
+	 * out of bounds index.  Ensure `idx` is valid.
+	 */
+	tst	x0, #~0xF
+	ASM_ASSERT(eq)
+#endif
+	/*
+	 * Given `idx` calculate address of mrs/ret instruction pair
+	 * in the table below.
+	 */
+	add	x2, x2, x0, lsl #3	/* each msr/ret sequence is 8 bytes */
+#if ENABLE_BTI
+	add	x2, x2, x0, lsl #2	/* + "bti j" instruction */
+#endif
+	br	x2
+
+1:	write	AMEVCNTVOFF10_EL2	/* index 0 */
+	write	AMEVCNTVOFF11_EL2	/* index 1 */
+	write	AMEVCNTVOFF12_EL2	/* index 2 */
+	write	AMEVCNTVOFF13_EL2	/* index 3 */
+	write	AMEVCNTVOFF14_EL2	/* index 4 */
+	write	AMEVCNTVOFF15_EL2	/* index 5 */
+	write	AMEVCNTVOFF16_EL2	/* index 6 */
+	write	AMEVCNTVOFF17_EL2	/* index 7 */
+	write	AMEVCNTVOFF18_EL2	/* index 8 */
+	write	AMEVCNTVOFF19_EL2	/* index 9 */
+	write	AMEVCNTVOFF1A_EL2	/* index 10 */
+	write	AMEVCNTVOFF1B_EL2	/* index 11 */
+	write	AMEVCNTVOFF1C_EL2	/* index 12 */
+	write	AMEVCNTVOFF1D_EL2	/* index 13 */
+	write	AMEVCNTVOFF1E_EL2	/* index 14 */
+	write	AMEVCNTVOFF1F_EL2	/* index 15 */
+endfunc amu_group1_voffset_write_internal
+#endif
diff --git a/lib/extensions/amu/amu.mk b/lib/extensions/amu/amu.mk
new file mode 100644
index 0000000..0d203cb
--- /dev/null
+++ b/lib/extensions/amu/amu.mk
@@ -0,0 +1,24 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+include lib/fconf/fconf.mk
+
+AMU_SOURCES	:=	lib/extensions/amu/${ARCH}/amu.c \
+			lib/extensions/amu/${ARCH}/amu_helpers.S
+
+ifneq (${ENABLE_AMU_AUXILIARY_COUNTERS},0)
+        ifeq (${ENABLE_AMU},0)
+                $(error AMU auxiliary counter support (`ENABLE_AMU_AUXILIARY_COUNTERS`) requires AMU support (`ENABLE_AMU`))
+        endif
+endif
+
+ifneq (${ENABLE_AMU_FCONF},0)
+        ifeq (${ENABLE_AMU_AUXILIARY_COUNTERS},0)
+                $(error AMU FCONF support (`ENABLE_AMU_FCONF`) is not necessary when auxiliary counter support (`ENABLE_AMU_AUXILIARY_COUNTERS`) is disabled)
+        endif
+
+        AMU_SOURCES	+=	${FCONF_AMU_SOURCES}
+endif
diff --git a/lib/extensions/amu/amu_private.h b/lib/extensions/amu/amu_private.h
new file mode 100644
index 0000000..eb7ff0e
--- /dev/null
+++ b/lib/extensions/amu/amu_private.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef AMU_PRIVATE_H
+#define AMU_PRIVATE_H
+
+#include <stdint.h>
+
+#include <lib/cassert.h>
+#include <lib/extensions/amu.h>
+#include <lib/utils_def.h>
+
+#include <platform_def.h>
+
+#define AMU_GROUP0_MAX_COUNTERS		U(16)
+#define AMU_GROUP1_MAX_COUNTERS		U(16)
+
+#define AMU_AMCGCR_CG0NC_MAX		U(16)
+
+uint64_t amu_group0_cnt_read_internal(unsigned int idx);
+void amu_group0_cnt_write_internal(unsigned int idx, uint64_t val);
+
+uint64_t amu_group1_cnt_read_internal(unsigned int idx);
+void amu_group1_cnt_write_internal(unsigned int idx, uint64_t val);
+void amu_group1_set_evtype_internal(unsigned int idx, unsigned int val);
+
+#if __aarch64__
+uint64_t amu_group0_voffset_read_internal(unsigned int idx);
+void amu_group0_voffset_write_internal(unsigned int idx, uint64_t val);
+
+uint64_t amu_group1_voffset_read_internal(unsigned int idx);
+void amu_group1_voffset_write_internal(unsigned int idx, uint64_t val);
+#endif
+
+#endif /* AMU_PRIVATE_H */
diff --git a/lib/extensions/mtpmu/aarch32/mtpmu.S b/lib/extensions/mtpmu/aarch32/mtpmu.S
new file mode 100644
index 0000000..834cee3
--- /dev/null
+++ b/lib/extensions/mtpmu/aarch32/mtpmu.S
@@ -0,0 +1,105 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+
+	.global	mtpmu_disable
+
+/* -------------------------------------------------------------
+ * The functions in this file are called at entrypoint, before
+ * the CPU has decided whether this is a cold or a warm boot.
+ * Therefore there are no stack yet to rely on for a C function
+ * call.
+ * -------------------------------------------------------------
+ */
+
+/*
+ * bool mtpmu_supported(void)
+ *
+ * Return a boolean indicating whether FEAT_MTPMU is supported or not.
+ *
+ * Trash registers: r0.
+ */
+func mtpmu_supported
+	ldcopr	r0, ID_DFR1
+	and	r0, r0, #(ID_DFR1_MTPMU_MASK >> ID_DFR1_MTPMU_SHIFT)
+	cmp	r0, #ID_DFR1_MTPMU_SUPPORTED
+	mov	r0, #0
+	addeq	r0, r0, #1
+	bx	lr
+endfunc mtpmu_supported
+
+/*
+ * bool el_implemented(unsigned int el)
+ *
+ * Return a boolean indicating if the specified EL (2 or 3) is implemented.
+ *
+ * Trash registers: r0
+ */
+func el_implemented
+	cmp	r0, #3
+	ldcopr	r0, ID_PFR1
+	lsreq	r0, r0, #ID_PFR1_SEC_SHIFT
+	lsrne	r0, r0, #ID_PFR1_VIRTEXT_SHIFT
+	/*
+	 * ID_PFR1_VIRTEXT_MASK is the same as ID_PFR1_SEC_MASK
+	 * so use any one of them
+	 */
+	and	r0, r0, #ID_PFR1_VIRTEXT_MASK
+	cmp	r0, #ID_PFR1_ELx_ENABLED
+	mov	r0, #0
+	addeq	r0, r0, #1
+	bx	lr
+endfunc el_implemented
+
+/*
+ * void mtpmu_disable(void)
+ *
+ * Disable mtpmu feature if supported.
+ *
+ * Trash register: r0, r1, r2
+ */
+func mtpmu_disable
+	mov	r2, lr
+	bl	mtpmu_supported
+	cmp	r0, #0
+	bxeq	r2	/* FEAT_MTPMU not supported */
+
+	/* FEAT_MTMPU Supported */
+	mov	r0, #3
+	bl	el_implemented
+	cmp	r0, #0
+	beq	1f
+
+	/* EL3 implemented */
+	ldcopr	r0, SDCR
+	ldr	r1, =SDCR_MTPME_BIT
+	bic	r0, r0, r1
+	stcopr	r0, SDCR
+
+	/*
+	 * If EL3 is implemented, HDCR.MTPME is implemented as Res0 and
+	 * FEAT_MTPMU is controlled only from EL3, so no need to perform
+	 * any operations for EL2.
+	 */
+	isb
+	bx	r2
+1:
+	/* EL3 not implemented */
+	mov	r0, #2
+	bl	el_implemented
+	cmp	r0, #0
+	bxeq	r2	/* No EL2 or EL3 implemented */
+
+	/* EL2 implemented */
+	ldcopr	r0, HDCR
+	ldr	r1, =HDCR_MTPME_BIT
+	orr	r0, r0, r1
+	stcopr	r0, HDCR
+	isb
+	bx	r2
+endfunc mtpmu_disable
diff --git a/lib/extensions/mtpmu/aarch64/mtpmu.S b/lib/extensions/mtpmu/aarch64/mtpmu.S
new file mode 100644
index 0000000..0a1d57b
--- /dev/null
+++ b/lib/extensions/mtpmu/aarch64/mtpmu.S
@@ -0,0 +1,96 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+
+	.global	mtpmu_disable
+
+/* -------------------------------------------------------------
+ * The functions in this file are called at entrypoint, before
+ * the CPU has decided whether this is a cold or a warm boot.
+ * Therefore there are no stack yet to rely on for a C function
+ * call.
+ * -------------------------------------------------------------
+ */
+
+/*
+ * bool mtpmu_supported(void)
+ *
+ * Return a boolean indicating whether FEAT_MTPMU is supported or not.
+ *
+ * Trash registers: x0, x1
+ */
+func mtpmu_supported
+	mrs	x0, id_aa64dfr0_el1
+	mov_imm	x1, ID_AA64DFR0_MTPMU_MASK
+	and	x0, x1, x0, LSR #ID_AA64DFR0_MTPMU_SHIFT
+	cmp	x0, ID_AA64DFR0_MTPMU_SUPPORTED
+	cset	x0, eq
+	ret
+endfunc mtpmu_supported
+
+/*
+ * bool el_implemented(unsigned int el_shift)
+ *
+ * Return a boolean indicating if the specified EL is implemented.
+ * The EL is represented as the bitmask shift on id_aa64pfr0_el1 register.
+ *
+ * Trash registers: x0, x1
+ */
+func el_implemented
+	mrs	x1, id_aa64pfr0_el1
+	lsr	x1, x1, x0
+	cmp	x1, #ID_AA64PFR0_ELX_MASK
+	cset	x0, eq
+	ret
+endfunc el_implemented
+
+/*
+ * void mtpmu_disable(void)
+ *
+ * Disable mtpmu feature if supported.
+ *
+ * Trash register: x0, x1, x30
+ */
+func mtpmu_disable
+	mov	x10, x30
+	bl	mtpmu_supported
+	cbz	x0, exit_disable
+
+	/* FEAT_MTMPU Supported */
+	mov_imm	x0, ID_AA64PFR0_EL3_SHIFT
+	bl	el_implemented
+	cbz	x0, 1f
+
+	/* EL3 implemented */
+	mrs	x0, mdcr_el3
+	mov_imm x1, MDCR_MTPME_BIT
+	bic	x0, x0, x1
+	msr	mdcr_el3, x0
+
+	/*
+	 * If EL3 is implemented, MDCR_EL2.MTPME is implemented as Res0 and
+	 * FEAT_MTPMU is controlled only from EL3, so no need to perform
+	 * any operations for EL2.
+	 */
+	isb
+exit_disable:
+	ret	x10
+1:
+	/* EL3 not implemented */
+	mov_imm	x0, ID_AA64PFR0_EL2_SHIFT
+	bl	el_implemented
+	cbz	x0, exit_disable
+
+	/* EL2 implemented */
+	mrs	x0, mdcr_el2
+	mov_imm x1, MDCR_EL2_MTPME
+	bic	x0, x0, x1
+	msr	mdcr_el2, x0
+	isb
+	ret	x10
+endfunc mtpmu_disable
diff --git a/lib/extensions/ras/ras_common.c b/lib/extensions/ras/ras_common.c
index 36f9a95..622879e 100644
--- a/lib/extensions/ras/ras_common.c
+++ b/lib/extensions/ras/ras_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
@@ -139,7 +139,7 @@
 	assert(ras_interrupt_mappings.num_intrs > 0UL);
 
 	start = 0;
-	end = (int) ras_interrupt_mappings.num_intrs;
+	end = (int)ras_interrupt_mappings.num_intrs - 1;
 	while (start <= end) {
 		mid = ((end + start) / 2);
 		if (intr_raw == ras_inrs[mid].intr_number) {
diff --git a/lib/extensions/sme/sme.c b/lib/extensions/sme/sme.c
new file mode 100644
index 0000000..1c2b984
--- /dev/null
+++ b/lib/extensions/sme/sme.c
@@ -0,0 +1,103 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/el3_runtime/context_mgmt.h>
+#include <lib/extensions/sme.h>
+#include <lib/extensions/sve.h>
+
+static bool feat_sme_supported(void)
+{
+	uint64_t features;
+
+	features = read_id_aa64pfr1_el1() >> ID_AA64PFR1_EL1_SME_SHIFT;
+	return (features & ID_AA64PFR1_EL1_SME_MASK) != 0U;
+}
+
+static bool feat_sme_fa64_supported(void)
+{
+	uint64_t features;
+
+	features = read_id_aa64smfr0_el1();
+	return (features & ID_AA64SMFR0_EL1_FA64_BIT) != 0U;
+}
+
+void sme_enable(cpu_context_t *context)
+{
+	u_register_t reg;
+	u_register_t cptr_el3;
+	el3_state_t *state;
+
+	/* Make sure SME is implemented in hardware before continuing. */
+	if (!feat_sme_supported()) {
+		return;
+	}
+
+	/* Get the context state. */
+	state = get_el3state_ctx(context);
+
+	/* Enable SME in CPTR_EL3. */
+	reg = read_ctx_reg(state, CTX_CPTR_EL3);
+	reg |= ESM_BIT;
+	write_ctx_reg(state, CTX_CPTR_EL3, reg);
+
+	/* Set the ENTP2 bit in SCR_EL3 to enable access to TPIDR2_EL0. */
+	reg = read_ctx_reg(state, CTX_SCR_EL3);
+	reg |= SCR_ENTP2_BIT;
+	write_ctx_reg(state, CTX_SCR_EL3, reg);
+
+	/* Set CPTR_EL3.ESM bit so we can write SMCR_EL3 without trapping. */
+	cptr_el3 = read_cptr_el3();
+	write_cptr_el3(cptr_el3 | ESM_BIT);
+
+	/*
+	 * Set the max LEN value and FA64 bit. This register is set up globally
+	 * to be the least restrictive, then lower ELs can restrict as needed
+	 * using SMCR_EL2 and SMCR_EL1.
+	 */
+	reg = SMCR_ELX_LEN_MASK;
+	if (feat_sme_fa64_supported()) {
+		VERBOSE("[SME] FA64 enabled\n");
+		reg |= SMCR_ELX_FA64_BIT;
+	}
+	write_smcr_el3(reg);
+
+	/* Reset CPTR_EL3 value. */
+	write_cptr_el3(cptr_el3);
+
+	/* Enable SVE/FPU in addition to SME. */
+	sve_enable(context);
+}
+
+void sme_disable(cpu_context_t *context)
+{
+	u_register_t reg;
+	el3_state_t *state;
+
+	/* Make sure SME is implemented in hardware before continuing. */
+	if (!feat_sme_supported()) {
+		return;
+	}
+
+	/* Get the context state. */
+	state = get_el3state_ctx(context);
+
+	/* Disable SME, SVE, and FPU since they all share registers. */
+	reg = read_ctx_reg(state, CTX_CPTR_EL3);
+	reg &= ~ESM_BIT;	/* Trap SME */
+	reg &= ~CPTR_EZ_BIT;	/* Trap SVE */
+	reg |= TFP_BIT;		/* Trap FPU/SIMD */
+	write_ctx_reg(state, CTX_CPTR_EL3, reg);
+
+	/* Disable access to TPIDR2_EL0. */
+	reg = read_ctx_reg(state, CTX_SCR_EL3);
+	reg &= ~SCR_ENTP2_BIT;
+	write_ctx_reg(state, CTX_SCR_EL3, reg);
+}
diff --git a/lib/extensions/sve/sve.c b/lib/extensions/sve/sve.c
index fa4ac77..aa8904b 100644
--- a/lib/extensions/sve/sve.c
+++ b/lib/extensions/sve/sve.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,7 +11,13 @@
 #include <lib/el3_runtime/pubsub.h>
 #include <lib/extensions/sve.h>
 
-bool sve_supported(void)
+/*
+ * Converts SVE vector size restriction in bytes to LEN according to ZCR_EL3 documentation.
+ * VECTOR_SIZE = (LEN+1) * 128
+ */
+#define CONVERT_SVE_LENGTH(x)	(((x / 128) - 1))
+
+static bool sve_supported(void)
 {
 	uint64_t features;
 
@@ -19,113 +25,41 @@
 	return (features & ID_AA64PFR0_SVE_MASK) == 1U;
 }
 
-static void *disable_sve_hook(const void *arg)
+void sve_enable(cpu_context_t *context)
 {
-	uint64_t cptr;
+	u_register_t cptr_el3;
 
-	if (!sve_supported())
-		return (void *)-1;
-
-	/*
-	 * Disable SVE, SIMD and FP access for the Secure world.
-	 * As the SIMD/FP registers are part of the SVE Z-registers, any
-	 * use of SIMD/FP functionality will corrupt the SVE registers.
-	 * Therefore it is necessary to prevent use of SIMD/FP support
-	 * in the Secure world as well as SVE functionality.
-	 */
-	cptr = read_cptr_el3();
-	cptr = (cptr | TFP_BIT) & ~(CPTR_EZ_BIT);
-	write_cptr_el3(cptr);
-
-	/*
-	 * No explicit ISB required here as ERET to switch to Secure
-	 * world covers it
-	 */
-	return (void *)0;
-}
-
-static void *enable_sve_hook(const void *arg)
-{
-	uint64_t cptr;
-
-	if (!sve_supported())
-		return (void *)-1;
-
-	/*
-	 * Enable SVE, SIMD and FP access for the Non-secure world.
-	 */
-	cptr = read_cptr_el3();
-	cptr = (cptr | CPTR_EZ_BIT) & ~(TFP_BIT);
-	write_cptr_el3(cptr);
-
-	/*
-	 * No explicit ISB required here as ERET to switch to Non-secure
-	 * world covers it
-	 */
-	return (void *)0;
-}
-
-void sve_enable(bool el2_unused)
-{
-	uint64_t cptr;
-
-	if (!sve_supported())
+	if (!sve_supported()) {
 		return;
-
-#if CTX_INCLUDE_FPREGS
-	/*
-	 * CTX_INCLUDE_FPREGS is not supported on SVE enabled systems.
-	 */
-	assert(0);
-#endif
-	/*
-	 * Update CPTR_EL3 to enable access to SVE functionality for the
-	 * Non-secure world.
-	 * NOTE - assumed that CPTR_EL3.TFP is set to allow access to
-	 * the SIMD, floating-point and SVE support.
-	 *
-	 * CPTR_EL3.EZ: Set to 1 to enable access to SVE  functionality
-	 *  in the Non-secure world.
-	 */
-	cptr = read_cptr_el3();
-	cptr |= CPTR_EZ_BIT;
-	write_cptr_el3(cptr);
-
-	/*
-	 * Need explicit ISB here to guarantee that update to ZCR_ELx
-	 * and CPTR_EL2.TZ do not result in trap to EL3.
-	 */
-	isb();
-
-	/*
-	 * Ensure lower ELs have access to full vector length.
-	 */
-	write_zcr_el3(ZCR_EL3_LEN_MASK);
-
-	if (el2_unused) {
-		/*
-		 * Update CPTR_EL2 to enable access to SVE functionality
-		 * for Non-secure world, EL2 and Non-secure EL1 and EL0.
-		 * NOTE - assumed that CPTR_EL2.TFP is set to allow
-		 * access to the SIMD, floating-point and SVE support.
-		 *
-		 * CPTR_EL2.TZ: Set to 0 to enable access to SVE support
-		 *  for EL2 and Non-secure EL1 and EL0.
-		 */
-		cptr = read_cptr_el2();
-		cptr &= ~(CPTR_EL2_TZ_BIT);
-		write_cptr_el2(cptr);
-
-		/*
-		 * Ensure lower ELs have access to full vector length.
-		 */
-		write_zcr_el2(ZCR_EL2_LEN_MASK);
 	}
-	/*
-	 * No explicit ISB required here as ERET to switch to
-	 * Non-secure world covers it.
-	 */
+
+	cptr_el3 = read_ctx_reg(get_el3state_ctx(context), CTX_CPTR_EL3);
+
+	/* Enable access to SVE functionality for all ELs. */
+	cptr_el3 = (cptr_el3 | CPTR_EZ_BIT) & ~(TFP_BIT);
+	write_ctx_reg(get_el3state_ctx(context), CTX_CPTR_EL3, cptr_el3);
+
+	/* Restrict maximum SVE vector length (SVE_VECTOR_LENGTH+1) * 128. */
+	write_ctx_reg(get_el3state_ctx(context), CTX_ZCR_EL3,
+		(ZCR_EL3_LEN_MASK & CONVERT_SVE_LENGTH(512)));
 }
 
-SUBSCRIBE_TO_EVENT(cm_exited_normal_world, disable_sve_hook);
-SUBSCRIBE_TO_EVENT(cm_entering_normal_world, enable_sve_hook);
+void sve_disable(cpu_context_t *context)
+{
+	u_register_t reg;
+	el3_state_t *state;
+
+	/* Make sure SME is implemented in hardware before continuing. */
+	if (!sve_supported()) {
+		return;
+	}
+
+	/* Get the context state. */
+	state = get_el3state_ctx(context);
+
+	/* Disable SVE and FPU since they share registers. */
+	reg = read_ctx_reg(state, CTX_CPTR_EL3);
+	reg &= ~CPTR_EZ_BIT;	/* Trap SVE */
+	reg |= TFP_BIT;		/* Trap FPU/SIMD */
+	write_ctx_reg(state, CTX_CPTR_EL3, reg);
+}
diff --git a/lib/extensions/sys_reg_trace/aarch32/sys_reg_trace.c b/lib/extensions/sys_reg_trace/aarch32/sys_reg_trace.c
new file mode 100644
index 0000000..89b8029
--- /dev/null
+++ b/lib/extensions/sys_reg_trace/aarch32/sys_reg_trace.c
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/extensions/sys_reg_trace.h>
+
+static bool sys_reg_trace_supported(void)
+{
+	uint32_t features;
+
+	features = read_id_dfr0() >> ID_DFR0_COPTRC_SHIFT;
+	return ((features & ID_DFR0_COPTRC_MASK) ==
+		ID_DFR0_COPTRC_SUPPORTED);
+}
+
+void sys_reg_trace_enable(void)
+{
+	uint32_t val;
+
+	if (sys_reg_trace_supported()) {
+		/*
+		 * NSACR.NSTRCDIS = b0
+		 * enable NS system register access to implemented trace
+		 * registers.
+		 */
+		val = read_nsacr();
+		val &= ~NSTRCDIS_BIT;
+		write_nsacr(val);
+	}
+}
diff --git a/lib/extensions/sys_reg_trace/aarch64/sys_reg_trace.c b/lib/extensions/sys_reg_trace/aarch64/sys_reg_trace.c
new file mode 100644
index 0000000..960d698
--- /dev/null
+++ b/lib/extensions/sys_reg_trace/aarch64/sys_reg_trace.c
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/extensions/sys_reg_trace.h>
+
+static bool sys_reg_trace_supported(void)
+{
+	uint64_t features;
+
+	features = read_id_aa64dfr0_el1() >> ID_AA64DFR0_TRACEVER_SHIFT;
+	return ((features & ID_AA64DFR0_TRACEVER_MASK) ==
+		ID_AA64DFR0_TRACEVER_SUPPORTED);
+}
+
+void sys_reg_trace_enable(cpu_context_t *ctx)
+{
+	uint64_t val;
+
+	if (sys_reg_trace_supported()) {
+		/* Retrieve CPTR_EL3 value from the given context 'ctx',
+		 * and update CPTR_EL3.TTA bit to 0.
+		 * This function is called while switching context to NS to
+		 * allow system trace register access to NS-EL2 and NS-EL1
+		 * when NS-EL2 is implemented but not used.
+		 */
+		val = read_ctx_reg(get_el3state_ctx(ctx), CTX_CPTR_EL3);
+		val &= ~TTA_BIT;
+		write_ctx_reg(get_el3state_ctx(ctx), CTX_CPTR_EL3, val);
+	}
+}
diff --git a/lib/extensions/trbe/trbe.c b/lib/extensions/trbe/trbe.c
new file mode 100644
index 0000000..9f754d5
--- /dev/null
+++ b/lib/extensions/trbe/trbe.c
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/el3_runtime/pubsub.h>
+#include <lib/extensions/trbe.h>
+
+static void tsb_csync(void)
+{
+	/*
+	 * The assembler does not yet understand the tsb csync mnemonic
+	 * so use the equivalent hint instruction.
+	 */
+	__asm__ volatile("hint #18");
+}
+
+static bool trbe_supported(void)
+{
+	uint64_t features;
+
+	features = read_id_aa64dfr0_el1() >> ID_AA64DFR0_TRACEBUFFER_SHIFT;
+	return ((features & ID_AA64DFR0_TRACEBUFFER_MASK) ==
+		ID_AA64DFR0_TRACEBUFFER_SUPPORTED);
+}
+
+void trbe_enable(void)
+{
+	uint64_t val;
+
+	if (trbe_supported()) {
+		/*
+		 * MDCR_EL3.NSTB = 0b11
+		 * Allow access of trace buffer control registers from NS-EL1
+		 * and NS-EL2, tracing is prohibited in Secure and Realm state
+		 * (if implemented).
+		 */
+		val = read_mdcr_el3();
+		val |= MDCR_NSTB(MDCR_NSTB_EL1);
+		write_mdcr_el3(val);
+	}
+}
+
+static void *trbe_drain_trace_buffers_hook(const void *arg __unused)
+{
+	if (trbe_supported()) {
+		/*
+		 * Before switching from normal world to secure world
+		 * the trace buffers need to be drained out to memory. This is
+		 * required to avoid an invalid memory access when TTBR is switched
+		 * for entry to S-EL1.
+		 */
+		tsb_csync();
+		dsbnsh();
+	}
+
+	return (void *)0;
+}
+
+SUBSCRIBE_TO_EVENT(cm_entering_secure_world, trbe_drain_trace_buffers_hook);
diff --git a/lib/extensions/trf/aarch32/trf.c b/lib/extensions/trf/aarch32/trf.c
new file mode 100644
index 0000000..834092d
--- /dev/null
+++ b/lib/extensions/trf/aarch32/trf.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/extensions/trf.h>
+
+static bool trf_supported(void)
+{
+	uint32_t features;
+
+	features = read_id_dfr0() >> ID_DFR0_TRACEFILT_SHIFT;
+	return ((features & ID_DFR0_TRACEFILT_MASK) ==
+		ID_DFR0_TRACEFILT_SUPPORTED);
+}
+
+void trf_enable(void)
+{
+	uint32_t val;
+
+	if (trf_supported()) {
+		/*
+		 * Allow access of trace filter control registers from
+		 * non-monitor mode
+		 */
+		val = read_sdcr();
+		val &= ~SDCR_TTRF_BIT;
+		write_sdcr(val);
+	}
+}
diff --git a/lib/extensions/trf/aarch64/trf.c b/lib/extensions/trf/aarch64/trf.c
new file mode 100644
index 0000000..1da5dce
--- /dev/null
+++ b/lib/extensions/trf/aarch64/trf.c
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/extensions/trf.h>
+
+static bool trf_supported(void)
+{
+	uint64_t features;
+
+	features = read_id_aa64dfr0_el1() >> ID_AA64DFR0_TRACEFILT_SHIFT;
+	return ((features & ID_AA64DFR0_TRACEFILT_MASK) ==
+		ID_AA64DFR0_TRACEFILT_SUPPORTED);
+}
+
+void trf_enable(void)
+{
+	uint64_t val;
+
+	if (trf_supported()) {
+		/*
+		 * MDCR_EL3.TTRF = b0
+		 * Allow access of trace filter control registers from NS-EL2
+		 * and NS-EL1 when NS-EL2 is implemented but not used
+		 */
+		val = read_mdcr_el3();
+		val &= ~MDCR_TTRF_BIT;
+		write_mdcr_el3(val);
+	}
+}
diff --git a/lib/fconf/fconf.mk b/lib/fconf/fconf.mk
index b01dc6f..fb88910 100644
--- a/lib/fconf/fconf.mk
+++ b/lib/fconf/fconf.mk
@@ -1,12 +1,19 @@
 #
-# Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+# Copyright (c) 2019-2021, ARM Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
-# Add Firmware Configuration files
-FCONF_SOURCES		:=	lib/fconf/fconf.c
-FCONF_DYN_SOURCES	:=	lib/fconf/fconf_dyn_cfg_getter.c
+include common/fdt_wrappers.mk
 
-BL1_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
-BL2_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+FCONF_SOURCES		:=	lib/fconf/fconf.c
+FCONF_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
+FCONF_DYN_SOURCES	:=	lib/fconf/fconf_dyn_cfg_getter.c
+FCONF_DYN_SOURCES	+=	${FDT_WRAPPERS_SOURCES}
+
+FCONF_AMU_SOURCES	:=	lib/fconf/fconf_amu_getter.c
+FCONF_AMU_SOURCES	+=	${FDT_WRAPPERS_SOURCES}
+
+FCONF_MPMM_SOURCES	:=	lib/fconf/fconf_mpmm_getter.c
+FCONF_MPMM_SOURCES	+=	${FDT_WRAPPERS_SOURCES}
diff --git a/lib/fconf/fconf_amu_getter.c b/lib/fconf/fconf_amu_getter.c
new file mode 100644
index 0000000..eff309c
--- /dev/null
+++ b/lib/fconf/fconf_amu_getter.c
@@ -0,0 +1,142 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <common/fdt_wrappers.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_amu_getter.h>
+#include <libfdt.h>
+
+#include <plat/common/platform.h>
+
+struct fconf_amu_config fconf_amu_config;
+static struct amu_topology fconf_amu_topology_;
+
+/*
+ * Populate the core-specific AMU structure with information retrieved from a
+ * device tree.
+ *
+ * Returns `0` on success, or a negative integer representing an error code.
+ */
+static int fconf_populate_amu_cpu_amu(const void *fdt, int parent,
+				      struct amu_core *amu)
+{
+	int ret = 0;
+	int node = 0;
+
+	fdt_for_each_subnode(node, fdt, parent) {
+		const char *name;
+		const char *value;
+		int len;
+
+		uintptr_t idx = 0U;
+
+		name = fdt_get_name(fdt, node, &len);
+		if (strncmp(name, "counter@", 8) != 0) {
+			continue;
+		}
+
+		ret = fdt_get_reg_props_by_index(fdt, node, 0, &idx, NULL);
+		if (ret < 0) {
+			break;
+		}
+
+		value = fdt_getprop(fdt, node, "enable-at-el3", &len);
+		if ((value == NULL) && (len != -FDT_ERR_NOTFOUND)) {
+			break;
+		}
+
+		if (len != -FDT_ERR_NOTFOUND) {
+			amu->enable |= (1 << idx);
+		}
+	}
+
+	if ((node < 0) && (node != -FDT_ERR_NOTFOUND)) {
+		return node;
+	}
+
+	return ret;
+}
+
+/*
+ * Within a `cpu` node, attempt to dereference the `amu` property, and populate
+ * the AMU information for the core.
+ *
+ * Returns `0` on success, or a negative integer representing an error code.
+ */
+static int fconf_populate_amu_cpu(const void *fdt, int node, uintptr_t mpidr)
+{
+	int ret;
+	int idx;
+
+	uint32_t amu_phandle;
+	struct amu_core *amu;
+
+	ret = fdt_read_uint32(fdt, node, "amu", &amu_phandle);
+	if (ret < 0) {
+		if (ret == -FDT_ERR_NOTFOUND) {
+			ret = 0;
+		}
+
+		return ret;
+	}
+
+	node = fdt_node_offset_by_phandle(fdt, amu_phandle);
+	if (node < 0) {
+		return node;
+	}
+
+	idx = plat_core_pos_by_mpidr(mpidr);
+	if (idx < 0) {
+		return -FDT_ERR_BADVALUE;
+	}
+
+	amu = &fconf_amu_topology_.cores[idx];
+
+	return fconf_populate_amu_cpu_amu(fdt, node, amu);
+}
+
+/*
+ * Populates the global `amu_topology` structure based on what's described by
+ * the hardware configuration device tree blob.
+ *
+ * The device tree is expected to provide an `amu` property for each `cpu` node,
+ * like so:
+ *
+ *     cpu@0 {
+ *         amu = <&cpu0_amu>;
+ *     };
+ *
+ *     amus {
+ *         cpu0_amu: amu-0 {
+ *             counters {
+ *                 #address-cells = <2>;
+ *                 #size-cells = <0>;
+ *
+ *                 counter@x,y {
+ *                     reg = <x y>; // Group x, counter y
+ *                 };
+ *             };
+ *         };
+ *     };
+ */
+static int fconf_populate_amu(uintptr_t config)
+{
+	int ret = fdtw_for_each_cpu(
+		(const void *)config, fconf_populate_amu_cpu);
+	if (ret == 0) {
+		fconf_amu_config.topology = &fconf_amu_topology_;
+	} else {
+		ERROR("FCONF: failed to parse AMU information: %d\n", ret);
+	}
+
+	return ret;
+}
+
+FCONF_REGISTER_POPULATOR(HW_CONFIG, amu, fconf_populate_amu);
diff --git a/lib/fconf/fconf_mpmm_getter.c b/lib/fconf/fconf_mpmm_getter.c
new file mode 100644
index 0000000..02a566d
--- /dev/null
+++ b/lib/fconf/fconf_mpmm_getter.c
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <common/fdt_wrappers.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_mpmm_getter.h>
+#include <libfdt.h>
+
+#include <plat/common/platform.h>
+
+struct fconf_mpmm_config fconf_mpmm_config;
+static struct mpmm_topology fconf_mpmm_topology;
+
+/*
+ * Within a `cpu` node, determine support for MPMM via the `supports-mpmm`
+ * property.
+ *
+ * Returns `0` on success, or a negative integer representing an error code.
+ */
+static int fconf_populate_mpmm_cpu(const void *fdt, int off, uintptr_t mpidr)
+{
+	int ret, len;
+
+	int core_pos;
+	struct mpmm_core *core;
+
+	core_pos = plat_core_pos_by_mpidr(mpidr);
+	if (core_pos < 0) {
+		return -FDT_ERR_BADVALUE;
+	}
+
+	core = &fconf_mpmm_topology.cores[core_pos];
+
+	fdt_getprop(fdt, off, "supports-mpmm", &len);
+	if (len >= 0) {
+		core->supported = true;
+		ret = 0;
+	} else {
+		core->supported = false;
+		ret = len;
+	}
+
+	return ret;
+}
+
+/*
+ * Populates the global `fconf_mpmm_config` structure based on what's described
+ * by the hardware configuration device tree blob.
+ *
+ * The device tree is expected to provide a `supports-mpmm` property for each
+ * `cpu` node, like so:
+ *
+ *     cpu@0 {
+ *       supports-mpmm;
+ *     };
+ *
+ * This property indicates whether the core implements MPMM, as we cannot detect
+ * support for it dynamically.
+ */
+static int fconf_populate_mpmm(uintptr_t config)
+{
+	int ret = fdtw_for_each_cpu(
+		(const void *)config, fconf_populate_mpmm_cpu);
+	if (ret == 0) {
+		fconf_mpmm_config.topology = &fconf_mpmm_topology;
+	} else {
+		ERROR("FCONF: failed to configure MPMM: %d\n", ret);
+	}
+
+	return ret;
+}
+
+FCONF_REGISTER_POPULATOR(HW_CONFIG, mpmm, fconf_populate_mpmm);
diff --git a/lib/fconf/fconf_tbbr_getter.c b/lib/fconf/fconf_tbbr_getter.c
index 9a20ced..6f043e6 100644
--- a/lib/fconf/fconf_tbbr_getter.c
+++ b/lib/fconf/fconf_tbbr_getter.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -71,26 +71,13 @@
 	}
 	tbbr_dyn_config.mbedtls_heap_size = val32;
 
-#if MEASURED_BOOT
-	/* Retrieve BL2 hash data details from the DTB */
-	err = fdtw_read_bytes(dtb, node, "bl2_hash_data", TCG_DIGEST_SIZE,
-				&tbbr_dyn_config.bl2_hash_data);
-	if (err < 0) {
-		ERROR("FCONF: Read %s failed for '%s'\n",
-				"bytes", "bl2_hash_data");
-		return err;
-	}
-#endif
 	VERBOSE("%s%s%s %d\n", "FCONF: `tbbr.", "disable_auth",
 		"` cell found with value =", tbbr_dyn_config.disable_auth);
 	VERBOSE("%s%s%s %p\n", "FCONF: `tbbr.", "mbedtls_heap_addr",
 		"` cell found with value =", tbbr_dyn_config.mbedtls_heap_addr);
 	VERBOSE("%s%s%s %zu\n", "FCONF: `tbbr.", "mbedtls_heap_size",
 		"` cell found with value =", tbbr_dyn_config.mbedtls_heap_size);
-#if MEASURED_BOOT
-	VERBOSE("%s%s%s %p\n", "FCONF: `tbbr.", "bl2_hash_data",
-		"` array found at address =", tbbr_dyn_config.bl2_hash_data);
-#endif
+
 	return 0;
 }
 
diff --git a/lib/gpt_rme/gpt_rme.c b/lib/gpt_rme/gpt_rme.c
new file mode 100644
index 0000000..e424fe2
--- /dev/null
+++ b/lib/gpt_rme/gpt_rme.c
@@ -0,0 +1,1124 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <inttypes.h>
+#include <limits.h>
+#include <stdint.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include "gpt_rme_private.h"
+#include <lib/gpt_rme/gpt_rme.h>
+#include <lib/smccc.h>
+#include <lib/spinlock.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#if !ENABLE_RME
+#error "ENABLE_RME must be enabled to use the GPT library."
+#endif
+
+/*
+ * Lookup T from PPS
+ *
+ *   PPS    Size    T
+ *   0b000  4GB     32
+ *   0b001  64GB    36
+ *   0b010  1TB     40
+ *   0b011  4TB     42
+ *   0b100  16TB    44
+ *   0b101  256TB   48
+ *   0b110  4PB     52
+ *
+ * See section 15.1.27 of the RME specification.
+ */
+static const gpt_t_val_e gpt_t_lookup[] = {PPS_4GB_T, PPS_64GB_T,
+					   PPS_1TB_T, PPS_4TB_T,
+					   PPS_16TB_T, PPS_256TB_T,
+					   PPS_4PB_T};
+
+/*
+ * Lookup P from PGS
+ *
+ *   PGS    Size    P
+ *   0b00   4KB     12
+ *   0b10   16KB    14
+ *   0b01   64KB    16
+ *
+ * Note that pgs=0b10 is 16KB and pgs=0b01 is 64KB, this is not a typo.
+ *
+ * See section 15.1.27 of the RME specification.
+ */
+static const gpt_p_val_e gpt_p_lookup[] = {PGS_4KB_P, PGS_64KB_P, PGS_16KB_P};
+
+/*
+ * This structure contains GPT configuration data.
+ */
+typedef struct {
+	uintptr_t plat_gpt_l0_base;
+	gpccr_pps_e pps;
+	gpt_t_val_e t;
+	gpccr_pgs_e pgs;
+	gpt_p_val_e p;
+} gpt_config_t;
+
+static gpt_config_t gpt_config;
+
+/* These variables are used during initialization of the L1 tables. */
+static unsigned int gpt_next_l1_tbl_idx;
+static uintptr_t gpt_l1_tbl;
+
+/*
+ * This function checks to see if a GPI value is valid.
+ *
+ * These are valid GPI values.
+ *   GPT_GPI_NO_ACCESS   U(0x0)
+ *   GPT_GPI_SECURE      U(0x8)
+ *   GPT_GPI_NS          U(0x9)
+ *   GPT_GPI_ROOT        U(0xA)
+ *   GPT_GPI_REALM       U(0xB)
+ *   GPT_GPI_ANY         U(0xF)
+ *
+ * Parameters
+ *   gpi		GPI to check for validity.
+ *
+ * Return
+ *   true for a valid GPI, false for an invalid one.
+ */
+static bool gpt_is_gpi_valid(unsigned int gpi)
+{
+	if ((gpi == GPT_GPI_NO_ACCESS) || (gpi == GPT_GPI_ANY) ||
+	    ((gpi >= GPT_GPI_SECURE) && (gpi <= GPT_GPI_REALM))) {
+		return true;
+	} else {
+		return false;
+	}
+}
+
+/*
+ * This function checks to see if two PAS regions overlap.
+ *
+ * Parameters
+ *   base_1: base address of first PAS
+ *   size_1: size of first PAS
+ *   base_2: base address of second PAS
+ *   size_2: size of second PAS
+ *
+ * Return
+ *   True if PAS regions overlap, false if they do not.
+ */
+static bool gpt_check_pas_overlap(uintptr_t base_1, size_t size_1,
+				  uintptr_t base_2, size_t size_2)
+{
+	if (((base_1 + size_1) > base_2) && ((base_2 + size_2) > base_1)) {
+		return true;
+	} else {
+		return false;
+	}
+}
+
+/*
+ * This helper function checks to see if a PAS region from index 0 to
+ * (pas_idx - 1) occupies the L0 region at index l0_idx in the L0 table.
+ *
+ * Parameters
+ *   l0_idx:      Index of the L0 entry to check
+ *   pas_regions: PAS region array
+ *   pas_idx:     Upper bound of the PAS array index.
+ *
+ * Return
+ *   True if a PAS region occupies the L0 region in question, false if not.
+ */
+static bool gpt_does_previous_pas_exist_here(unsigned int l0_idx,
+					     pas_region_t *pas_regions,
+					     unsigned int pas_idx)
+{
+	/* Iterate over PAS regions up to pas_idx. */
+	for (unsigned int i = 0U; i < pas_idx; i++) {
+		if (gpt_check_pas_overlap((GPT_L0GPTSZ_ACTUAL_SIZE * l0_idx),
+		    GPT_L0GPTSZ_ACTUAL_SIZE,
+		    pas_regions[i].base_pa, pas_regions[i].size)) {
+			return true;
+		}
+	}
+	return false;
+}
+
+/*
+ * This function iterates over all of the PAS regions and checks them to ensure
+ * proper alignment of base and size, that the GPI is valid, and that no regions
+ * overlap. As a part of the overlap checks, this function checks existing L0
+ * mappings against the new PAS regions in the event that gpt_init_pas_l1_tables
+ * is called multiple times to place L1 tables in different areas of memory. It
+ * also counts the number of L1 tables needed and returns it on success.
+ *
+ * Parameters
+ *   *pas_regions	Pointer to array of PAS region structures.
+ *   pas_region_cnt	Total number of PAS regions in the array.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, number of L1 regions
+ *   required when successful.
+ */
+static int gpt_validate_pas_mappings(pas_region_t *pas_regions,
+				     unsigned int pas_region_cnt)
+{
+	unsigned int idx;
+	unsigned int l1_cnt = 0U;
+	unsigned int pas_l1_cnt;
+	uint64_t *l0_desc = (uint64_t *)gpt_config.plat_gpt_l0_base;
+
+	assert(pas_regions != NULL);
+	assert(pas_region_cnt != 0U);
+
+	for (idx = 0U; idx < pas_region_cnt; idx++) {
+		/* Check for arithmetic overflow in region. */
+		if ((ULONG_MAX - pas_regions[idx].base_pa) <
+		    pas_regions[idx].size) {
+			ERROR("[GPT] Address overflow in PAS[%u]!\n", idx);
+			return -EOVERFLOW;
+		}
+
+		/* Initial checks for PAS validity. */
+		if (((pas_regions[idx].base_pa + pas_regions[idx].size) >
+		    GPT_PPS_ACTUAL_SIZE(gpt_config.t)) ||
+		    !gpt_is_gpi_valid(GPT_PAS_ATTR_GPI(pas_regions[idx].attrs))) {
+			ERROR("[GPT] PAS[%u] is invalid!\n", idx);
+			return -EFAULT;
+		}
+
+		/*
+		 * Make sure this PAS does not overlap with another one. We
+		 * start from idx + 1 instead of 0 since prior PAS mappings will
+		 * have already checked themselves against this one.
+		 */
+		for (unsigned int i = idx + 1; i < pas_region_cnt; i++) {
+			if (gpt_check_pas_overlap(pas_regions[idx].base_pa,
+			    pas_regions[idx].size,
+			    pas_regions[i].base_pa,
+			    pas_regions[i].size)) {
+				ERROR("[GPT] PAS[%u] overlaps with PAS[%u]\n",
+					i, idx);
+				return -EFAULT;
+			}
+		}
+
+		/*
+		 * Since this function can be called multiple times with
+		 * separate L1 tables we need to check the existing L0 mapping
+		 * to see if this PAS would fall into one that has already been
+		 * initialized.
+		 */
+		for (unsigned int i = GPT_L0_IDX(pas_regions[idx].base_pa);
+		     i <= GPT_L0_IDX(pas_regions[idx].base_pa + pas_regions[idx].size - 1);
+		     i++) {
+			if ((GPT_L0_TYPE(l0_desc[i]) == GPT_L0_TYPE_BLK_DESC) &&
+			    (GPT_L0_BLKD_GPI(l0_desc[i]) == GPT_GPI_ANY)) {
+				/* This descriptor is unused so continue. */
+				continue;
+			}
+
+			/*
+			 * This descriptor has been initialized in a previous
+			 * call to this function so cannot be initialized again.
+			 */
+			ERROR("[GPT] PAS[%u] overlaps with previous L0[%d]!\n",
+			      idx, i);
+			return -EFAULT;
+		}
+
+		/* Check for block mapping (L0) type. */
+		if (GPT_PAS_ATTR_MAP_TYPE(pas_regions[idx].attrs) ==
+		    GPT_PAS_ATTR_MAP_TYPE_BLOCK) {
+			/* Make sure base and size are block-aligned. */
+			if (!GPT_IS_L0_ALIGNED(pas_regions[idx].base_pa) ||
+			    !GPT_IS_L0_ALIGNED(pas_regions[idx].size)) {
+				ERROR("[GPT] PAS[%u] is not block-aligned!\n",
+				      idx);
+				return -EFAULT;
+			}
+
+			continue;
+		}
+
+		/* Check for granule mapping (L1) type. */
+		if (GPT_PAS_ATTR_MAP_TYPE(pas_regions[idx].attrs) ==
+		    GPT_PAS_ATTR_MAP_TYPE_GRANULE) {
+			/* Make sure base and size are granule-aligned. */
+			if (!GPT_IS_L1_ALIGNED(gpt_config.p, pas_regions[idx].base_pa) ||
+			    !GPT_IS_L1_ALIGNED(gpt_config.p, pas_regions[idx].size)) {
+				ERROR("[GPT] PAS[%u] is not granule-aligned!\n",
+				      idx);
+				return -EFAULT;
+			}
+
+			/* Find how many L1 tables this PAS occupies. */
+			pas_l1_cnt = (GPT_L0_IDX(pas_regions[idx].base_pa +
+				     pas_regions[idx].size - 1) -
+				     GPT_L0_IDX(pas_regions[idx].base_pa) + 1);
+
+			/*
+			 * This creates a situation where, if multiple PAS
+			 * regions occupy the same table descriptor, we can get
+			 * an artificially high total L1 table count. The way we
+			 * handle this is by checking each PAS against those
+			 * before it in the array, and if they both occupy the
+			 * same PAS we subtract from pas_l1_cnt and only the
+			 * first PAS in the array gets to count it.
+			 */
+
+			/*
+			 * If L1 count is greater than 1 we know the start and
+			 * end PAs are in different L0 regions so we must check
+			 * both for overlap against other PAS.
+			 */
+			if (pas_l1_cnt > 1) {
+				if (gpt_does_previous_pas_exist_here(
+				    GPT_L0_IDX(pas_regions[idx].base_pa +
+				    pas_regions[idx].size - 1),
+				    pas_regions, idx)) {
+					pas_l1_cnt = pas_l1_cnt - 1;
+				}
+			}
+
+			if (gpt_does_previous_pas_exist_here(
+			    GPT_L0_IDX(pas_regions[idx].base_pa),
+			    pas_regions, idx)) {
+				pas_l1_cnt = pas_l1_cnt - 1;
+			}
+
+			l1_cnt += pas_l1_cnt;
+			continue;
+		}
+
+		/* If execution reaches this point, mapping type is invalid. */
+		ERROR("[GPT] PAS[%u] has invalid mapping type 0x%x.\n", idx,
+		      GPT_PAS_ATTR_MAP_TYPE(pas_regions[idx].attrs));
+		return -EINVAL;
+	}
+
+	return l1_cnt;
+}
+
+/*
+ * This function validates L0 initialization parameters.
+ *
+ * Parameters
+ *   l0_mem_base	Base address of memory used for L0 tables.
+ *   l1_mem_size	Size of memory available for L0 tables.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+static int gpt_validate_l0_params(gpccr_pps_e pps, uintptr_t l0_mem_base,
+				  size_t l0_mem_size)
+{
+	size_t l0_alignment;
+
+	/*
+	 * Make sure PPS is valid and then store it since macros need this value
+	 * to work.
+	 */
+	if (pps > GPT_PPS_MAX) {
+		ERROR("[GPT] Invalid PPS: 0x%x\n", pps);
+		return -EINVAL;
+	}
+	gpt_config.pps = pps;
+	gpt_config.t = gpt_t_lookup[pps];
+
+	/* Alignment must be the greater of 4k or l0 table size. */
+	l0_alignment = PAGE_SIZE_4KB;
+	if (l0_alignment < GPT_L0_TABLE_SIZE(gpt_config.t)) {
+		l0_alignment = GPT_L0_TABLE_SIZE(gpt_config.t);
+	}
+
+	/* Check base address. */
+	if ((l0_mem_base == 0U) || ((l0_mem_base & (l0_alignment - 1)) != 0U)) {
+		ERROR("[GPT] Invalid L0 base address: 0x%lx\n", l0_mem_base);
+		return -EFAULT;
+	}
+
+	/* Check size. */
+	if (l0_mem_size < GPT_L0_TABLE_SIZE(gpt_config.t)) {
+		ERROR("[GPT] Inadequate L0 memory: need 0x%lx, have 0x%lx)\n",
+		      GPT_L0_TABLE_SIZE(gpt_config.t),
+		      l0_mem_size);
+		return -ENOMEM;
+	}
+
+	return 0;
+}
+
+/*
+ * In the event that L1 tables are needed, this function validates
+ * the L1 table generation parameters.
+ *
+ * Parameters
+ *   l1_mem_base	Base address of memory used for L1 table allocation.
+ *   l1_mem_size	Total size of memory available for L1 tables.
+ *   l1_gpt_cnt		Number of L1 tables needed.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+static int gpt_validate_l1_params(uintptr_t l1_mem_base, size_t l1_mem_size,
+				  unsigned int l1_gpt_cnt)
+{
+	size_t l1_gpt_mem_sz;
+
+	/* Check if the granularity is supported */
+	if (!xlat_arch_is_granule_size_supported(
+	    GPT_PGS_ACTUAL_SIZE(gpt_config.p))) {
+		return -EPERM;
+	}
+
+	/* Make sure L1 tables are aligned to their size. */
+	if ((l1_mem_base & (GPT_L1_TABLE_SIZE(gpt_config.p) - 1)) != 0U) {
+		ERROR("[GPT] Unaligned L1 GPT base address: 0x%lx\n",
+		      l1_mem_base);
+		return -EFAULT;
+	}
+
+	/* Get total memory needed for L1 tables. */
+	l1_gpt_mem_sz = l1_gpt_cnt * GPT_L1_TABLE_SIZE(gpt_config.p);
+
+	/* Check for overflow. */
+	if ((l1_gpt_mem_sz / GPT_L1_TABLE_SIZE(gpt_config.p)) != l1_gpt_cnt) {
+		ERROR("[GPT] Overflow calculating L1 memory size.\n");
+		return -ENOMEM;
+	}
+
+	/* Make sure enough space was supplied. */
+	if (l1_mem_size < l1_gpt_mem_sz) {
+		ERROR("[GPT] Inadequate memory for L1 GPTs. ");
+		ERROR("      Expected 0x%lx bytes. Got 0x%lx bytes\n",
+		      l1_gpt_mem_sz, l1_mem_size);
+		return -ENOMEM;
+	}
+
+	VERBOSE("[GPT] Requested 0x%lx bytes for L1 GPTs.\n", l1_gpt_mem_sz);
+	return 0;
+}
+
+/*
+ * This function initializes L0 block descriptors (regions that cannot be
+ * transitioned at the granule level) according to the provided PAS.
+ *
+ * Parameters
+ *   *pas		Pointer to the structure defining the PAS region to
+ *			initialize.
+ */
+static void gpt_generate_l0_blk_desc(pas_region_t *pas)
+{
+	uint64_t gpt_desc;
+	unsigned int end_idx;
+	unsigned int idx;
+	uint64_t *l0_gpt_arr;
+
+	assert(gpt_config.plat_gpt_l0_base != 0U);
+	assert(pas != NULL);
+
+	/*
+	 * Checking of PAS parameters has already been done in
+	 * gpt_validate_pas_mappings so no need to check the same things again.
+	 */
+
+	l0_gpt_arr = (uint64_t *)gpt_config.plat_gpt_l0_base;
+
+	/* Create the GPT Block descriptor for this PAS region */
+	gpt_desc = GPT_L0_BLK_DESC(GPT_PAS_ATTR_GPI(pas->attrs));
+
+	/* Start index of this region in L0 GPTs */
+	idx = pas->base_pa >> GPT_L0_IDX_SHIFT;
+
+	/*
+	 * Determine number of L0 GPT descriptors covered by
+	 * this PAS region and use the count to populate these
+	 * descriptors.
+	 */
+	end_idx = (pas->base_pa + pas->size) >> GPT_L0_IDX_SHIFT;
+
+	/* Generate the needed block descriptors. */
+	for (; idx < end_idx; idx++) {
+		l0_gpt_arr[idx] = gpt_desc;
+		VERBOSE("[GPT] L0 entry (BLOCK) index %u [%p]: GPI = 0x%" PRIx64 " (0x%" PRIx64 ")\n",
+			idx, &l0_gpt_arr[idx],
+			(gpt_desc >> GPT_L0_BLK_DESC_GPI_SHIFT) &
+			GPT_L0_BLK_DESC_GPI_MASK, l0_gpt_arr[idx]);
+	}
+}
+
+/*
+ * Helper function to determine if the end physical address lies in the same L0
+ * region as the current physical address. If true, the end physical address is
+ * returned else, the start address of the next region is returned.
+ *
+ * Parameters
+ *   cur_pa		Physical address of the current PA in the loop through
+ *			the range.
+ *   end_pa		Physical address of the end PA in a PAS range.
+ *
+ * Return
+ *   The PA of the end of the current range.
+ */
+static uintptr_t gpt_get_l1_end_pa(uintptr_t cur_pa, uintptr_t end_pa)
+{
+	uintptr_t cur_idx;
+	uintptr_t end_idx;
+
+	cur_idx = cur_pa >> GPT_L0_IDX_SHIFT;
+	end_idx = end_pa >> GPT_L0_IDX_SHIFT;
+
+	assert(cur_idx <= end_idx);
+
+	if (cur_idx == end_idx) {
+		return end_pa;
+	}
+
+	return (cur_idx + 1U) << GPT_L0_IDX_SHIFT;
+}
+
+/*
+ * Helper function to fill out GPI entries in a single L1 table. This function
+ * fills out entire L1 descriptors at a time to save memory writes.
+ *
+ * Parameters
+ *   gpi		GPI to set this range to
+ *   l1			Pointer to L1 table to fill out
+ *   first		Address of first granule in range.
+ *   last		Address of last granule in range (inclusive).
+ */
+static void gpt_fill_l1_tbl(uint64_t gpi, uint64_t *l1, uintptr_t first,
+			    uintptr_t last)
+{
+	uint64_t gpi_field = GPT_BUILD_L1_DESC(gpi);
+	uint64_t gpi_mask = 0xFFFFFFFFFFFFFFFF;
+
+	assert(first <= last);
+	assert((first & (GPT_PGS_ACTUAL_SIZE(gpt_config.p) - 1)) == 0U);
+	assert((last & (GPT_PGS_ACTUAL_SIZE(gpt_config.p) - 1)) == 0U);
+	assert(GPT_L0_IDX(first) == GPT_L0_IDX(last));
+	assert(l1 != NULL);
+
+	/* Shift the mask if we're starting in the middle of an L1 entry. */
+	gpi_mask = gpi_mask << (GPT_L1_GPI_IDX(gpt_config.p, first) << 2);
+
+	/* Fill out each L1 entry for this region. */
+	for (unsigned int i = GPT_L1_IDX(gpt_config.p, first);
+	     i <= GPT_L1_IDX(gpt_config.p, last); i++) {
+		/* Account for stopping in the middle of an L1 entry. */
+		if (i == GPT_L1_IDX(gpt_config.p, last)) {
+			gpi_mask &= (gpi_mask >> ((15 -
+				    GPT_L1_GPI_IDX(gpt_config.p, last)) << 2));
+		}
+
+		/* Write GPI values. */
+		assert((l1[i] & gpi_mask) ==
+		       (GPT_BUILD_L1_DESC(GPT_GPI_ANY) & gpi_mask));
+		l1[i] = (l1[i] & ~gpi_mask) | (gpi_mask & gpi_field);
+
+		/* Reset mask. */
+		gpi_mask = 0xFFFFFFFFFFFFFFFF;
+	}
+}
+
+/*
+ * This function finds the next available unused L1 table and initializes all
+ * granules descriptor entries to GPI_ANY. This ensures that there are no chunks
+ * of GPI_NO_ACCESS (0b0000) memory floating around in the system in the
+ * event that a PAS region stops midway through an L1 table, thus guaranteeing
+ * that all memory not explicitly assigned is GPI_ANY. This function does not
+ * check for overflow conditions, that should be done by the caller.
+ *
+ * Return
+ *   Pointer to the next available L1 table.
+ */
+static uint64_t *gpt_get_new_l1_tbl(void)
+{
+	/* Retrieve the next L1 table. */
+	uint64_t *l1 = (uint64_t *)((uint64_t)(gpt_l1_tbl) +
+		       (GPT_L1_TABLE_SIZE(gpt_config.p) *
+		       gpt_next_l1_tbl_idx));
+
+	/* Increment L1 counter. */
+	gpt_next_l1_tbl_idx++;
+
+	/* Initialize all GPIs to GPT_GPI_ANY */
+	for (unsigned int i = 0U; i < GPT_L1_ENTRY_COUNT(gpt_config.p); i++) {
+		l1[i] = GPT_BUILD_L1_DESC(GPT_GPI_ANY);
+	}
+
+	return l1;
+}
+
+/*
+ * When L1 tables are needed, this function creates the necessary L0 table
+ * descriptors and fills out the L1 table entries according to the supplied
+ * PAS range.
+ *
+ * Parameters
+ *   *pas		Pointer to the structure defining the PAS region.
+ */
+static void gpt_generate_l0_tbl_desc(pas_region_t *pas)
+{
+	uintptr_t end_pa;
+	uintptr_t cur_pa;
+	uintptr_t last_gran_pa;
+	uint64_t *l0_gpt_base;
+	uint64_t *l1_gpt_arr;
+	unsigned int l0_idx;
+
+	assert(gpt_config.plat_gpt_l0_base != 0U);
+	assert(pas != NULL);
+
+	/*
+	 * Checking of PAS parameters has already been done in
+	 * gpt_validate_pas_mappings so no need to check the same things again.
+	 */
+
+	end_pa = pas->base_pa + pas->size;
+	l0_gpt_base = (uint64_t *)gpt_config.plat_gpt_l0_base;
+
+	/* We start working from the granule at base PA */
+	cur_pa = pas->base_pa;
+
+	/* Iterate over each L0 region in this memory range. */
+	for (l0_idx = GPT_L0_IDX(pas->base_pa);
+	     l0_idx <= GPT_L0_IDX(end_pa - 1U);
+	     l0_idx++) {
+
+		/*
+		 * See if the L0 entry is already a table descriptor or if we
+		 * need to create one.
+		 */
+		if (GPT_L0_TYPE(l0_gpt_base[l0_idx]) == GPT_L0_TYPE_TBL_DESC) {
+			/* Get the L1 array from the L0 entry. */
+			l1_gpt_arr = GPT_L0_TBLD_ADDR(l0_gpt_base[l0_idx]);
+		} else {
+			/* Get a new L1 table from the L1 memory space. */
+			l1_gpt_arr = gpt_get_new_l1_tbl();
+
+			/* Fill out the L0 descriptor and flush it. */
+			l0_gpt_base[l0_idx] = GPT_L0_TBL_DESC(l1_gpt_arr);
+		}
+
+		VERBOSE("[GPT] L0 entry (TABLE) index %u [%p] ==> L1 Addr 0x%llx (0x%" PRIx64 ")\n",
+			l0_idx, &l0_gpt_base[l0_idx],
+			(unsigned long long)(l1_gpt_arr),
+			l0_gpt_base[l0_idx]);
+
+		/*
+		 * Determine the PA of the last granule in this L0 descriptor.
+		 */
+		last_gran_pa = gpt_get_l1_end_pa(cur_pa, end_pa) -
+			       GPT_PGS_ACTUAL_SIZE(gpt_config.p);
+
+		/*
+		 * Fill up L1 GPT entries between these two addresses. This
+		 * function needs the addresses of the first granule and last
+		 * granule in the range.
+		 */
+		gpt_fill_l1_tbl(GPT_PAS_ATTR_GPI(pas->attrs), l1_gpt_arr,
+				cur_pa, last_gran_pa);
+
+		/* Advance cur_pa to first granule in next L0 region. */
+		cur_pa = gpt_get_l1_end_pa(cur_pa, end_pa);
+	}
+}
+
+/*
+ * This function flushes a range of L0 descriptors used by a given PAS region
+ * array. There is a chance that some unmodified L0 descriptors would be flushed
+ * in the case that there are "holes" in an array of PAS regions but overall
+ * this should be faster than individually flushing each modified L0 descriptor
+ * as they are created.
+ *
+ * Parameters
+ *   *pas		Pointer to an array of PAS regions.
+ *   pas_count		Number of entries in the PAS array.
+ */
+static void flush_l0_for_pas_array(pas_region_t *pas, unsigned int pas_count)
+{
+	unsigned int idx;
+	unsigned int start_idx;
+	unsigned int end_idx;
+	uint64_t *l0 = (uint64_t *)gpt_config.plat_gpt_l0_base;
+
+	assert(pas != NULL);
+	assert(pas_count > 0);
+
+	/* Initial start and end values. */
+	start_idx = GPT_L0_IDX(pas[0].base_pa);
+	end_idx = GPT_L0_IDX(pas[0].base_pa + pas[0].size - 1);
+
+	/* Find lowest and highest L0 indices used in this PAS array. */
+	for (idx = 1; idx < pas_count; idx++) {
+		if (GPT_L0_IDX(pas[idx].base_pa) < start_idx) {
+			start_idx = GPT_L0_IDX(pas[idx].base_pa);
+		}
+		if (GPT_L0_IDX(pas[idx].base_pa + pas[idx].size - 1) > end_idx) {
+			end_idx = GPT_L0_IDX(pas[idx].base_pa + pas[idx].size - 1);
+		}
+	}
+
+	/*
+	 * Flush all covered L0 descriptors, add 1 because we need to include
+	 * the end index value.
+	 */
+	flush_dcache_range((uintptr_t)&l0[start_idx],
+			   ((end_idx + 1) - start_idx) * sizeof(uint64_t));
+}
+
+/*
+ * Public API to enable granule protection checks once the tables have all been
+ * initialized. This function is called at first initialization and then again
+ * later during warm boots of CPU cores.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_enable(void)
+{
+	u_register_t gpccr_el3;
+
+	/*
+	 * Granule tables must be initialised before enabling
+	 * granule protection.
+	 */
+	if (gpt_config.plat_gpt_l0_base == 0U) {
+		ERROR("[GPT] Tables have not been initialized!\n");
+		return -EPERM;
+	}
+
+	/* Invalidate any stale TLB entries */
+	tlbipaallos();
+	dsb();
+
+	/* Write the base address of the L0 tables into GPTBR */
+	write_gptbr_el3(((gpt_config.plat_gpt_l0_base >> GPTBR_BADDR_VAL_SHIFT)
+			>> GPTBR_BADDR_SHIFT) & GPTBR_BADDR_MASK);
+
+	/* GPCCR_EL3.PPS */
+	gpccr_el3 = SET_GPCCR_PPS(gpt_config.pps);
+
+	/* GPCCR_EL3.PGS */
+	gpccr_el3 |= SET_GPCCR_PGS(gpt_config.pgs);
+
+	/*
+	 * Since EL3 maps the L1 region as Inner shareable, use the same
+	 * shareability attribute for GPC as well so that
+	 * GPC fetches are visible to PEs
+	 */
+	gpccr_el3 |= SET_GPCCR_SH(GPCCR_SH_IS);
+
+	/* Outer and Inner cacheability set to Normal memory, WB, RA, WA. */
+	gpccr_el3 |= SET_GPCCR_ORGN(GPCCR_ORGN_WB_RA_WA);
+	gpccr_el3 |= SET_GPCCR_IRGN(GPCCR_IRGN_WB_RA_WA);
+
+	/* Enable GPT */
+	gpccr_el3 |= GPCCR_GPC_BIT;
+
+	/* TODO: Configure GPCCR_EL3_GPCP for Fault control. */
+	write_gpccr_el3(gpccr_el3);
+	isb();
+	tlbipaallos();
+	dsb();
+	isb();
+
+	return 0;
+}
+
+/*
+ * Public API to disable granule protection checks.
+ */
+void gpt_disable(void)
+{
+	u_register_t gpccr_el3 = read_gpccr_el3();
+
+	write_gpccr_el3(gpccr_el3 & ~GPCCR_GPC_BIT);
+	dsbsy();
+	isb();
+}
+
+/*
+ * Public API that initializes the entire protected space to GPT_GPI_ANY using
+ * the L0 tables (block descriptors). Ideally, this function is invoked prior
+ * to DDR discovery and initialization. The MMU must be initialized before
+ * calling this function.
+ *
+ * Parameters
+ *   pps		PPS value to use for table generation
+ *   l0_mem_base	Base address of L0 tables in memory.
+ *   l0_mem_size	Total size of memory available for L0 tables.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_init_l0_tables(unsigned int pps, uintptr_t l0_mem_base,
+		       size_t l0_mem_size)
+{
+	int ret;
+	uint64_t gpt_desc;
+
+	/* Ensure that MMU and Data caches are enabled. */
+	assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
+
+	/* Validate other parameters. */
+	ret = gpt_validate_l0_params(pps, l0_mem_base, l0_mem_size);
+	if (ret < 0) {
+		return ret;
+	}
+
+	/* Create the descriptor to initialize L0 entries with. */
+	gpt_desc = GPT_L0_BLK_DESC(GPT_GPI_ANY);
+
+	/* Iterate through all L0 entries */
+	for (unsigned int i = 0U; i < GPT_L0_REGION_COUNT(gpt_config.t); i++) {
+		((uint64_t *)l0_mem_base)[i] = gpt_desc;
+	}
+
+	/* Flush updated L0 tables to memory. */
+	flush_dcache_range((uintptr_t)l0_mem_base,
+			   (size_t)GPT_L0_TABLE_SIZE(gpt_config.t));
+
+	/* Stash the L0 base address once initial setup is complete. */
+	gpt_config.plat_gpt_l0_base = l0_mem_base;
+
+	return 0;
+}
+
+/*
+ * Public API that carves out PAS regions from the L0 tables and builds any L1
+ * tables that are needed. This function ideally is run after DDR discovery and
+ * initialization. The L0 tables must have already been initialized to GPI_ANY
+ * when this function is called.
+ *
+ * This function can be called multiple times with different L1 memory ranges
+ * and PAS regions if it is desirable to place L1 tables in different locations
+ * in memory. (ex: you have multiple DDR banks and want to place the L1 tables
+ * in the DDR bank that they control)
+ *
+ * Parameters
+ *   pgs		PGS value to use for table generation.
+ *   l1_mem_base	Base address of memory used for L1 tables.
+ *   l1_mem_size	Total size of memory available for L1 tables.
+ *   *pas_regions	Pointer to PAS regions structure array.
+ *   pas_count		Total number of PAS regions.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_init_pas_l1_tables(gpccr_pgs_e pgs, uintptr_t l1_mem_base,
+			   size_t l1_mem_size, pas_region_t *pas_regions,
+			   unsigned int pas_count)
+{
+	int ret;
+	int l1_gpt_cnt;
+
+	/* Ensure that MMU and Data caches are enabled. */
+	assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
+
+	/* PGS is needed for gpt_validate_pas_mappings so check it now. */
+	if (pgs > GPT_PGS_MAX) {
+		ERROR("[GPT] Invalid PGS: 0x%x\n", pgs);
+		return -EINVAL;
+	}
+	gpt_config.pgs = pgs;
+	gpt_config.p = gpt_p_lookup[pgs];
+
+	/* Make sure L0 tables have been initialized. */
+	if (gpt_config.plat_gpt_l0_base == 0U) {
+		ERROR("[GPT] L0 tables must be initialized first!\n");
+		return -EPERM;
+	}
+
+	/* Check if L1 GPTs are required and how many. */
+	l1_gpt_cnt = gpt_validate_pas_mappings(pas_regions, pas_count);
+	if (l1_gpt_cnt < 0) {
+		return l1_gpt_cnt;
+	}
+
+	VERBOSE("[GPT] %u L1 GPTs requested.\n", l1_gpt_cnt);
+
+	/* If L1 tables are needed then validate the L1 parameters. */
+	if (l1_gpt_cnt > 0) {
+		ret = gpt_validate_l1_params(l1_mem_base, l1_mem_size,
+		      l1_gpt_cnt);
+		if (ret < 0) {
+			return ret;
+		}
+
+		/* Set up parameters for L1 table generation. */
+		gpt_l1_tbl = l1_mem_base;
+		gpt_next_l1_tbl_idx = 0U;
+	}
+
+	INFO("[GPT] Boot Configuration\n");
+	INFO("  PPS/T:     0x%x/%u\n", gpt_config.pps, gpt_config.t);
+	INFO("  PGS/P:     0x%x/%u\n", gpt_config.pgs, gpt_config.p);
+	INFO("  L0GPTSZ/S: 0x%x/%u\n", GPT_L0GPTSZ, GPT_S_VAL);
+	INFO("  PAS count: 0x%x\n", pas_count);
+	INFO("  L0 base:   0x%lx\n", gpt_config.plat_gpt_l0_base);
+
+	/* Generate the tables in memory. */
+	for (unsigned int idx = 0U; idx < pas_count; idx++) {
+		INFO("[GPT] PAS[%u]: base 0x%lx, size 0x%lx, GPI 0x%x, type 0x%x\n",
+		     idx, pas_regions[idx].base_pa, pas_regions[idx].size,
+		     GPT_PAS_ATTR_GPI(pas_regions[idx].attrs),
+		     GPT_PAS_ATTR_MAP_TYPE(pas_regions[idx].attrs));
+
+		/* Check if a block or table descriptor is required */
+		if (GPT_PAS_ATTR_MAP_TYPE(pas_regions[idx].attrs) ==
+		    GPT_PAS_ATTR_MAP_TYPE_BLOCK) {
+			gpt_generate_l0_blk_desc(&pas_regions[idx]);
+
+		} else {
+			gpt_generate_l0_tbl_desc(&pas_regions[idx]);
+		}
+	}
+
+	/* Flush modified L0 tables. */
+	flush_l0_for_pas_array(pas_regions, pas_count);
+
+	/* Flush L1 tables if needed. */
+	if (l1_gpt_cnt > 0) {
+		flush_dcache_range(l1_mem_base,
+				   GPT_L1_TABLE_SIZE(gpt_config.p) *
+				   l1_gpt_cnt);
+	}
+
+	/* Make sure that all the entries are written to the memory. */
+	dsbishst();
+	tlbipaallos();
+	dsb();
+	isb();
+
+	return 0;
+}
+
+/*
+ * Public API to initialize the runtime gpt_config structure based on the values
+ * present in the GPTBR_EL3 and GPCCR_EL3 registers. GPT initialization
+ * typically happens in a bootloader stage prior to setting up the EL3 runtime
+ * environment for the granule transition service so this function detects the
+ * initialization from a previous stage. Granule protection checks must be
+ * enabled already or this function will return an error.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_runtime_init(void)
+{
+	u_register_t reg;
+
+	/* Ensure that MMU and Data caches are enabled. */
+	assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
+
+	/* Ensure GPC are already enabled. */
+	if ((read_gpccr_el3() & GPCCR_GPC_BIT) == 0U) {
+		ERROR("[GPT] Granule protection checks are not enabled!\n");
+		return -EPERM;
+	}
+
+	/*
+	 * Read the L0 table address from GPTBR, we don't need the L1 base
+	 * address since those are included in the L0 tables as needed.
+	 */
+	reg = read_gptbr_el3();
+	gpt_config.plat_gpt_l0_base = ((reg >> GPTBR_BADDR_SHIFT) &
+				      GPTBR_BADDR_MASK) <<
+				      GPTBR_BADDR_VAL_SHIFT;
+
+	/* Read GPCCR to get PGS and PPS values. */
+	reg = read_gpccr_el3();
+	gpt_config.pps = (reg >> GPCCR_PPS_SHIFT) & GPCCR_PPS_MASK;
+	gpt_config.t = gpt_t_lookup[gpt_config.pps];
+	gpt_config.pgs = (reg >> GPCCR_PGS_SHIFT) & GPCCR_PGS_MASK;
+	gpt_config.p = gpt_p_lookup[gpt_config.pgs];
+
+	VERBOSE("[GPT] Runtime Configuration\n");
+	VERBOSE("  PPS/T:     0x%x/%u\n", gpt_config.pps, gpt_config.t);
+	VERBOSE("  PGS/P:     0x%x/%u\n", gpt_config.pgs, gpt_config.p);
+	VERBOSE("  L0GPTSZ/S: 0x%x/%u\n", GPT_L0GPTSZ, GPT_S_VAL);
+	VERBOSE("  L0 base:   0x%lx\n", gpt_config.plat_gpt_l0_base);
+
+	return 0;
+}
+
+/*
+ * The L1 descriptors are protected by a spinlock to ensure that multiple
+ * CPUs do not attempt to change the descriptors at once. In the future it
+ * would be better to have separate spinlocks for each L1 descriptor.
+ */
+static spinlock_t gpt_lock;
+
+/*
+ * Check if caller is allowed to transition a PAS.
+ *
+ * - Secure world caller can only request S <-> NS transitions on a
+ *   granule that is already in either S or NS PAS.
+ *
+ * - Realm world caller can only request R <-> NS transitions on a
+ *   granule that is already in either R or NS PAS.
+ *
+ * Parameters
+ *   src_sec_state	Security state of the caller.
+ *   current_gpi	Current GPI of the granule.
+ *   target_gpi		Requested new GPI for the granule.
+ *
+ * Return
+ *   Negative Linux error code in the event of a failure, 0 for success.
+ */
+static int gpt_check_transition_gpi(unsigned int src_sec_state,
+				    unsigned int current_gpi,
+				    unsigned int target_gpi)
+{
+	unsigned int check_gpi;
+
+	/* Cannot transition a granule to the state it is already in. */
+	if (current_gpi == target_gpi) {
+		return -EINVAL;
+	}
+
+	/* Check security state, only secure and realm can transition. */
+	if (src_sec_state == SMC_FROM_REALM) {
+		check_gpi = GPT_GPI_REALM;
+	} else if (src_sec_state == SMC_FROM_SECURE) {
+		check_gpi = GPT_GPI_SECURE;
+	} else {
+		return -EINVAL;
+	}
+
+	/* Make sure security state is allowed to make the transition. */
+	if ((target_gpi != check_gpi) && (target_gpi != GPT_GPI_NS)) {
+		return -EINVAL;
+	}
+	if ((current_gpi != check_gpi) && (current_gpi != GPT_GPI_NS)) {
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+/*
+ * This function is the core of the granule transition service. When a granule
+ * transition request occurs it is routed to this function where the request is
+ * validated then fulfilled if possible.
+ *
+ * TODO: implement support for transitioning multiple granules at once.
+ *
+ * Parameters
+ *   base		Base address of the region to transition, must be
+ *			aligned to granule size.
+ *   size		Size of region to transition, must be aligned to granule
+ *			size.
+ *   src_sec_state	Security state of the caller.
+ *   target_pas		Target PAS of the specified memory region.
+ *
+ * Return
+ *    Negative Linux error code in the event of a failure, 0 for success.
+ */
+int gpt_transition_pas(uint64_t base, size_t size, unsigned int src_sec_state,
+	unsigned int target_pas)
+{
+	int idx;
+	unsigned int gpi_shift;
+	unsigned int gpi;
+	uint64_t gpt_l0_desc;
+	uint64_t gpt_l1_desc;
+	uint64_t *gpt_l1_addr;
+	uint64_t *gpt_l0_base;
+
+	/* Ensure that the tables have been set up before taking requests. */
+	assert(gpt_config.plat_gpt_l0_base != 0U);
+
+	/* Ensure that MMU and data caches are enabled. */
+	assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
+
+	/* Check for address range overflow. */
+	if ((ULONG_MAX - base) < size) {
+		VERBOSE("[GPT] Transition request address overflow!\n");
+		VERBOSE("      Base=0x%" PRIx64 "\n", base);
+		VERBOSE("      Size=0x%lx\n", size);
+		return -EINVAL;
+	}
+
+	/* Make sure base and size are valid. */
+	if (((base & (GPT_PGS_ACTUAL_SIZE(gpt_config.p) - 1)) != 0U) ||
+	    ((size & (GPT_PGS_ACTUAL_SIZE(gpt_config.p) - 1)) != 0U) ||
+	    (size == 0U) ||
+	    ((base + size) >= GPT_PPS_ACTUAL_SIZE(gpt_config.t))) {
+		VERBOSE("[GPT] Invalid granule transition address range!\n");
+		VERBOSE("      Base=0x%" PRIx64 "\n", base);
+		VERBOSE("      Size=0x%lx\n", size);
+		return -EINVAL;
+	}
+
+	/* See if this is a single granule transition or a range of granules. */
+	if (size != GPT_PGS_ACTUAL_SIZE(gpt_config.p)) {
+		/*
+		 * TODO: Add support for transitioning multiple granules with a
+		 * single call to this function.
+		 */
+		panic();
+	}
+
+	/* Get the L0 descriptor and make sure it is for a table. */
+	gpt_l0_base = (uint64_t *)gpt_config.plat_gpt_l0_base;
+	gpt_l0_desc = gpt_l0_base[GPT_L0_IDX(base)];
+	if (GPT_L0_TYPE(gpt_l0_desc) != GPT_L0_TYPE_TBL_DESC) {
+		VERBOSE("[GPT] Granule is not covered by a table descriptor!\n");
+		VERBOSE("      Base=0x%" PRIx64 "\n", base);
+		return -EINVAL;
+	}
+
+	/* Get the table index and GPI shift from PA. */
+	gpt_l1_addr = GPT_L0_TBLD_ADDR(gpt_l0_desc);
+	idx = GPT_L1_IDX(gpt_config.p, base);
+	gpi_shift = GPT_L1_GPI_IDX(gpt_config.p, base) << 2;
+
+	/*
+	 * Access to L1 tables is controlled by a global lock to ensure
+	 * that no more than one CPU is allowed to make changes at any
+	 * given time.
+	 */
+	spin_lock(&gpt_lock);
+	gpt_l1_desc = gpt_l1_addr[idx];
+	gpi = (gpt_l1_desc >> gpi_shift) & GPT_L1_GRAN_DESC_GPI_MASK;
+
+	/* Make sure caller state and source/target PAS are allowed. */
+	if (gpt_check_transition_gpi(src_sec_state, gpi, target_pas) < 0) {
+		spin_unlock(&gpt_lock);
+			VERBOSE("[GPT] Invalid caller state and PAS combo!\n");
+		VERBOSE("      Caller: %u, Current GPI: %u, Target GPI: %u\n",
+			src_sec_state, gpi, target_pas);
+		return -EPERM;
+	}
+
+	/* Clear existing GPI encoding and transition granule. */
+	gpt_l1_desc &= ~(GPT_L1_GRAN_DESC_GPI_MASK << gpi_shift);
+	gpt_l1_desc |= ((uint64_t)target_pas << gpi_shift);
+	gpt_l1_addr[idx] = gpt_l1_desc;
+
+	/* Ensure that the write operation will be observed by GPC */
+	dsbishst();
+
+	/* Unlock access to the L1 tables. */
+	spin_unlock(&gpt_lock);
+
+	gpt_tlbi_by_pa(base, GPT_PGS_ACTUAL_SIZE(gpt_config.p));
+	dsbishst();
+	/*
+	 * The isb() will be done as part of context
+	 * synchronization when returning to lower EL
+	 */
+	VERBOSE("[GPT] Granule 0x%" PRIx64 ", GPI 0x%x->0x%x\n", base, gpi,
+		target_pas);
+
+	return 0;
+}
diff --git a/lib/gpt_rme/gpt_rme.mk b/lib/gpt_rme/gpt_rme.mk
new file mode 100644
index 0000000..60176f4
--- /dev/null
+++ b/lib/gpt_rme/gpt_rme.mk
@@ -0,0 +1,8 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+GPT_LIB_SRCS	:=	$(addprefix lib/gpt_rme/,        \
+			gpt_rme.c)
diff --git a/lib/gpt_rme/gpt_rme_private.h b/lib/gpt_rme/gpt_rme_private.h
new file mode 100644
index 0000000..5770bf7
--- /dev/null
+++ b/lib/gpt_rme/gpt_rme_private.h
@@ -0,0 +1,228 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef GPT_RME_PRIVATE_H
+#define GPT_RME_PRIVATE_H
+
+#include <arch.h>
+#include <lib/gpt_rme/gpt_rme.h>
+#include <lib/utils_def.h>
+
+/******************************************************************************/
+/* GPT descriptor definitions                                                 */
+/******************************************************************************/
+
+/* GPT level 0 descriptor bit definitions. */
+#define GPT_L0_TYPE_MASK		UL(0xF)
+#define GPT_L0_TYPE_SHIFT		U(0)
+
+/* For now, we don't support contiguous descriptors, only table and block. */
+#define GPT_L0_TYPE_TBL_DESC		UL(0x3)
+#define GPT_L0_TYPE_BLK_DESC		UL(0x1)
+
+#define GPT_L0_TBL_DESC_L1ADDR_MASK	UL(0xFFFFFFFFFF)
+#define GPT_L0_TBL_DESC_L1ADDR_SHIFT	U(12)
+
+#define GPT_L0_BLK_DESC_GPI_MASK	UL(0xF)
+#define GPT_L0_BLK_DESC_GPI_SHIFT	U(4)
+
+/* GPT level 1 descriptor bit definitions */
+#define GPT_L1_GRAN_DESC_GPI_MASK	UL(0xF)
+
+/*
+ * This macro fills out every GPI entry in a granules descriptor to the same
+ * value.
+ */
+#define GPT_BUILD_L1_DESC(_gpi)		(((uint64_t)(_gpi) << 4*0) | \
+					 ((uint64_t)(_gpi) << 4*1) | \
+					 ((uint64_t)(_gpi) << 4*2) | \
+					 ((uint64_t)(_gpi) << 4*3) | \
+					 ((uint64_t)(_gpi) << 4*4) | \
+					 ((uint64_t)(_gpi) << 4*5) | \
+					 ((uint64_t)(_gpi) << 4*6) | \
+					 ((uint64_t)(_gpi) << 4*7) | \
+					 ((uint64_t)(_gpi) << 4*8) | \
+					 ((uint64_t)(_gpi) << 4*9) | \
+					 ((uint64_t)(_gpi) << 4*10) | \
+					 ((uint64_t)(_gpi) << 4*11) | \
+					 ((uint64_t)(_gpi) << 4*12) | \
+					 ((uint64_t)(_gpi) << 4*13) | \
+					 ((uint64_t)(_gpi) << 4*14) | \
+					 ((uint64_t)(_gpi) << 4*15))
+
+/******************************************************************************/
+/* GPT platform configuration                                                 */
+/******************************************************************************/
+
+/* This value comes from GPCCR_EL3 so no externally supplied definition. */
+#define GPT_L0GPTSZ		((unsigned int)((read_gpccr_el3() >> \
+				GPCCR_L0GPTSZ_SHIFT) & GPCCR_L0GPTSZ_MASK))
+
+/* The "S" value is directly related to L0GPTSZ */
+#define GPT_S_VAL		(GPT_L0GPTSZ + 30U)
+
+/*
+ * Map PPS values to T values.
+ *
+ *   PPS    Size    T
+ *   0b000  4GB     32
+ *   0b001  64GB    36
+ *   0b010  1TB     40
+ *   0b011  4TB     42
+ *   0b100  16TB    44
+ *   0b101  256TB   48
+ *   0b110  4PB     52
+ *
+ * See section 15.1.27 of the RME specification.
+ */
+typedef enum {
+	PPS_4GB_T =	32U,
+	PPS_64GB_T =	36U,
+	PPS_1TB_T =	40U,
+	PPS_4TB_T =	42U,
+	PPS_16TB_T =	44U,
+	PPS_256TB_T =	48U,
+	PPS_4PB_T =	52U
+} gpt_t_val_e;
+
+/*
+ * Map PGS values to P values.
+ *
+ *   PGS    Size    P
+ *   0b00   4KB     12
+ *   0b10   16KB    14
+ *   0b01   64KB    16
+ *
+ * Note that pgs=0b10 is 16KB and pgs=0b01 is 64KB, this is not a typo.
+ *
+ * See section 15.1.27 of the RME specification.
+ */
+typedef enum {
+	PGS_4KB_P =	12U,
+	PGS_16KB_P =	14U,
+	PGS_64KB_P =	16U
+} gpt_p_val_e;
+
+/* Max valid value for PGS. */
+#define GPT_PGS_MAX			(2U)
+
+/* Max valid value for PPS. */
+#define GPT_PPS_MAX			(6U)
+
+/******************************************************************************/
+/* L0 address attribute macros                                                */
+/******************************************************************************/
+
+/*
+ * If S is greater than or equal to T then there is a single L0 region covering
+ * the entire protected space so there is no L0 index, so the width (and the
+ * derivative mask value) are both zero.  If we don't specifically handle this
+ * special case we'll get a negative width value which does not make sense and
+ * could cause a lot of problems.
+ */
+#define GPT_L0_IDX_WIDTH(_t)		(((_t) > GPT_S_VAL) ? \
+					((_t) - GPT_S_VAL) : (0U))
+
+/* Bit shift for the L0 index field in a PA. */
+#define GPT_L0_IDX_SHIFT		(GPT_S_VAL)
+
+/* Mask for the L0 index field, must be shifted. */
+#define GPT_L0_IDX_MASK(_t)		(0xFFFFFFFFFFFFFFFFUL >> \
+					(64U - (GPT_L0_IDX_WIDTH(_t))))
+
+/* Total number of L0 regions. */
+#define GPT_L0_REGION_COUNT(_t)		((GPT_L0_IDX_MASK(_t)) + 1U)
+
+/* Total size of each GPT L0 region in bytes. */
+#define GPT_L0_REGION_SIZE		(1UL << (GPT_L0_IDX_SHIFT))
+
+/* Total size in bytes of the whole L0 table. */
+#define GPT_L0_TABLE_SIZE(_t)		((GPT_L0_REGION_COUNT(_t)) << 3U)
+
+/******************************************************************************/
+/* L1 address attribute macros                                                */
+/******************************************************************************/
+
+/* Width of the L1 index field. */
+#define GPT_L1_IDX_WIDTH(_p)		((GPT_S_VAL - 1U) - ((_p) + 3U))
+
+/* Bit shift for the L1 index field. */
+#define GPT_L1_IDX_SHIFT(_p)		((_p) + 4U)
+
+/* Mask for the L1 index field, must be shifted. */
+#define GPT_L1_IDX_MASK(_p)		(0xFFFFFFFFFFFFFFFFUL >> \
+					(64U - (GPT_L1_IDX_WIDTH(_p))))
+
+/* Bit shift for the index of the L1 GPI in a PA. */
+#define GPT_L1_GPI_IDX_SHIFT(_p)	(_p)
+
+/* Mask for the index of the L1 GPI in a PA. */
+#define GPT_L1_GPI_IDX_MASK		(0xF)
+
+/* Total number of entries in each L1 table. */
+#define GPT_L1_ENTRY_COUNT(_p)		((GPT_L1_IDX_MASK(_p)) + 1U)
+
+/* Total size in bytes of each L1 table. */
+#define GPT_L1_TABLE_SIZE(_p)		((GPT_L1_ENTRY_COUNT(_p)) << 3U)
+
+/******************************************************************************/
+/* General helper macros                                                      */
+/******************************************************************************/
+
+/* Protected space actual size in bytes. */
+#define GPT_PPS_ACTUAL_SIZE(_t)	(1UL << (_t))
+
+/* Granule actual size in bytes. */
+#define GPT_PGS_ACTUAL_SIZE(_p)	(1UL << (_p))
+
+/* L0 GPT region size in bytes. */
+#define GPT_L0GPTSZ_ACTUAL_SIZE	(1UL << GPT_S_VAL)
+
+/* Get the index of the L0 entry from a physical address. */
+#define GPT_L0_IDX(_pa)		((_pa) >> GPT_L0_IDX_SHIFT)
+
+/*
+ * This definition is used to determine if a physical address lies on an L0
+ * region boundary.
+ */
+#define GPT_IS_L0_ALIGNED(_pa)	(((_pa) & (GPT_L0_REGION_SIZE - U(1))) == U(0))
+
+/* Get the type field from an L0 descriptor. */
+#define GPT_L0_TYPE(_desc)	(((_desc) >> GPT_L0_TYPE_SHIFT) & \
+				GPT_L0_TYPE_MASK)
+
+/* Create an L0 block descriptor. */
+#define GPT_L0_BLK_DESC(_gpi)	(GPT_L0_TYPE_BLK_DESC | \
+				(((_gpi) & GPT_L0_BLK_DESC_GPI_MASK) << \
+				GPT_L0_BLK_DESC_GPI_SHIFT))
+
+/* Create an L0 table descriptor with an L1 table address. */
+#define GPT_L0_TBL_DESC(_pa)	(GPT_L0_TYPE_TBL_DESC | ((uint64_t)(_pa) & \
+				(GPT_L0_TBL_DESC_L1ADDR_MASK << \
+				GPT_L0_TBL_DESC_L1ADDR_SHIFT)))
+
+/* Get the GPI from an L0 block descriptor. */
+#define GPT_L0_BLKD_GPI(_desc)	(((_desc) >> GPT_L0_BLK_DESC_GPI_SHIFT) & \
+				GPT_L0_BLK_DESC_GPI_MASK)
+
+/* Get the L1 address from an L0 table descriptor. */
+#define GPT_L0_TBLD_ADDR(_desc)	((uint64_t *)(((_desc) & \
+				(GPT_L0_TBL_DESC_L1ADDR_MASK << \
+				GPT_L0_TBL_DESC_L1ADDR_SHIFT))))
+
+/* Get the index into the L1 table from a physical address. */
+#define GPT_L1_IDX(_p, _pa)	(((_pa) >> GPT_L1_IDX_SHIFT(_p)) & \
+				GPT_L1_IDX_MASK(_p))
+
+/* Get the index of the GPI within an L1 table entry from a physical address. */
+#define GPT_L1_GPI_IDX(_p, _pa)	(((_pa) >> GPT_L1_GPI_IDX_SHIFT(_p)) & \
+				GPT_L1_GPI_IDX_MASK)
+
+/* Determine if an address is granule-aligned. */
+#define GPT_IS_L1_ALIGNED(_p, _pa) (((_pa) & (GPT_PGS_ACTUAL_SIZE(_p) - U(1))) \
+				   == U(0))
+
+#endif /* GPT_RME_PRIVATE_H */
diff --git a/lib/libc/libc.mk b/lib/libc/libc.mk
index 93d30d0..b75d09c 100644
--- a/lib/libc/libc.mk
+++ b/lib/libc/libc.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -20,11 +20,17 @@
 			snprintf.c			\
 			strchr.c			\
 			strcmp.c			\
+			strlcat.c			\
 			strlcpy.c			\
 			strlen.c			\
 			strncmp.c			\
 			strnlen.c			\
-			strrchr.c)
+			strrchr.c			\
+			strtok.c			\
+			strtoul.c			\
+			strtoll.c			\
+			strtoull.c			\
+			strtol.c)
 
 ifeq (${ARCH},aarch64)
 LIBC_SRCS	+=	$(addprefix lib/libc/aarch64/,	\
diff --git a/lib/libc/libc_asm.mk b/lib/libc/libc_asm.mk
index 6416a3c..2f27265 100644
--- a/lib/libc/libc_asm.mk
+++ b/lib/libc/libc_asm.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2020, Arm Limited. All rights reserved.
+# Copyright (c) 2020-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -19,11 +19,17 @@
 			snprintf.c			\
 			strchr.c			\
 			strcmp.c			\
+			strlcat.c			\
 			strlcpy.c			\
 			strlen.c			\
 			strncmp.c			\
 			strnlen.c			\
-			strrchr.c)
+			strrchr.c			\
+			strtok.c			\
+			strtoul.c			\
+			strtoll.c			\
+			strtoull.c			\
+			strtol.c)
 
 ifeq (${ARCH},aarch64)
 LIBC_SRCS	+=	$(addprefix lib/libc/aarch64/,	\
diff --git a/lib/libc/memset.c b/lib/libc/memset.c
index f9dd4c5..17f798c 100644
--- a/lib/libc/memset.c
+++ b/lib/libc/memset.c
@@ -10,19 +10,20 @@
 
 void *memset(void *dst, int val, size_t count)
 {
-	char *ptr = dst;
+	uint8_t *ptr = dst;
 	uint64_t *ptr64;
 	uint64_t fill = (unsigned char)val;
 
 	/* Simplify code below by making sure we write at least one byte. */
-	if (count == 0) {
+	if (count == 0U) {
 		return dst;
 	}
 
 	/* Handle the first part, until the pointer becomes 64-bit aligned. */
-	while (((uintptr_t)ptr & 7)) {
-		*ptr++ = val;
-		if (--count == 0) {
+	while (((uintptr_t)ptr & 7U) != 0U) {
+		*ptr = (uint8_t)val;
+		ptr++;
+		if (--count == 0U) {
 			return dst;
 		}
 	}
@@ -33,15 +34,17 @@
 	fill |= fill << 32;
 
 	/* Use 64-bit writes for as long as possible. */
-	ptr64 = (void *)ptr;
-	for (; count >= 8; count -= 8) {
-		*ptr64++ = fill;
+	ptr64 = (uint64_t *)ptr;
+	for (; count >= 8U; count -= 8) {
+		*ptr64 = fill;
+		ptr64++;
 	}
 
 	/* Handle the remaining part byte-per-byte. */
-	ptr = (void *)ptr64;
-	while (count--) {
-		*ptr++ = val;
+	ptr = (uint8_t *)ptr64;
+	while (count-- > 0U)  {
+		*ptr = (uint8_t)val;
+		ptr++;
 	}
 
 	return dst;
diff --git a/lib/libc/printf.c b/lib/libc/printf.c
index 2715a72..45e153e 100644
--- a/lib/libc/printf.c
+++ b/lib/libc/printf.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -108,6 +108,9 @@
 			/* Check the format specifier */
 loop:
 			switch (*fmt) {
+			case '%':
+				(void)putchar('%');
+				break;
 			case 'i': /* Fall through to next one */
 			case 'd':
 				num = get_num_va_args(args, l_count);
diff --git a/lib/libc/snprintf.c b/lib/libc/snprintf.c
index 6e80d8c..3b175ed 100644
--- a/lib/libc/snprintf.c
+++ b/lib/libc/snprintf.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,16 +10,20 @@
 #include <common/debug.h>
 #include <plat/common/platform.h>
 
+#define CHECK_AND_PUT_CHAR(buf, size, chars_printed, ch)	\
+	do {						\
+		if ((chars_printed) < (size)) {		\
+			*(buf) = (ch);			\
+			(buf)++;			\
+		}					\
+		(chars_printed)++;			\
+	} while (false)
+
 static void string_print(char **s, size_t n, size_t *chars_printed,
 			 const char *str)
 {
 	while (*str != '\0') {
-		if (*chars_printed < n) {
-			*(*s) = *str;
-			(*s)++;
-		}
-
-		(*chars_printed)++;
+		CHECK_AND_PUT_CHAR(*s, n, *chars_printed, *str);
 		str++;
 	}
 }
@@ -130,6 +134,9 @@
 			/* Check the format specifier. */
 loop:
 			switch (*fmt) {
+			case '%':
+				CHECK_AND_PUT_CHAR(s, n, chars_printed, '%');
+				break;
 			case '0':
 			case '1':
 			case '2':
@@ -158,12 +165,8 @@
 				num = va_arg(args, int);
 
 				if (num < 0) {
-					if (chars_printed < n) {
-						*s = '-';
-						s++;
-					}
-					chars_printed++;
-
+					CHECK_AND_PUT_CHAR(s, n, chars_printed,
+						'-');
 					unum = (unsigned int)-num;
 				} else {
 					unum = (unsigned int)num;
@@ -210,13 +213,9 @@
 			continue;
 		}
 
-		if (chars_printed < n) {
-			*s = *fmt;
-			s++;
-		}
+		CHECK_AND_PUT_CHAR(s, n, chars_printed, *fmt);
 
 		fmt++;
-		chars_printed++;
 	}
 
 	if (n > 0U) {
diff --git a/lib/libc/strtol.c b/lib/libc/strtol.c
new file mode 100644
index 0000000..deb862c
--- /dev/null
+++ b/lib/libc/strtol.c
@@ -0,0 +1,133 @@
+/*-
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * Copyright (c) 1990, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Copyright (c) 2011 The FreeBSD Foundation
+ * All rights reserved.
+ * Portions of this software were developed by David Chisnall
+ * under sponsorship from the FreeBSD Foundation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. 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.
+ * 3. Neither the name of the University 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 REGENTS 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 REGENTS 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 <errno.h>
+#include <limits.h>
+#include <stddef.h>
+#include <stdlib.h>
+
+/*
+ * Convert a string to a long integer.
+ *
+ * Assumes that the upper and lower case
+ * alphabets and digits are each contiguous.
+ */
+long strtol(const char *nptr, char **endptr, int base)
+{
+	const char *s;
+	unsigned long acc;
+	char c;
+	unsigned long cutoff;
+	int neg, any, cutlim;
+
+	/*
+	 * Skip white space and pick up leading +/- sign if any.
+	 * If base is 0, allow 0x for hex and 0 for octal, else
+	 * assume decimal; if base is already 16, allow 0x.
+	 */
+	s = nptr;
+	do {
+		c = *s++;
+	} while (isspace((unsigned char)c));
+	if (c == '-') {
+		neg = 1;
+		c = *s++;
+	} else {
+		neg = 0;
+		if (c == '+')
+			c = *s++;
+	}
+	if ((base == 0 || base == 16) &&
+	    c == '0' && (*s == 'x' || *s == 'X') &&
+	    ((s[1] >= '0' && s[1] <= '9') ||
+	    (s[1] >= 'A' && s[1] <= 'F') ||
+	    (s[1] >= 'a' && s[1] <= 'f'))) {
+		c = s[1];
+		s += 2;
+		base = 16;
+	}
+	if (base == 0)
+		base = c == '0' ? 8 : 10;
+	acc = any = 0;
+
+	/*
+	 * Compute the cutoff value between legal numbers and illegal
+	 * numbers.  That is the largest legal value, divided by the
+	 * base.  An input number that is greater than this value, if
+	 * followed by a legal input character, is too big.  One that
+	 * is equal to this value may be valid or not; the limit
+	 * between valid and invalid numbers is then based on the last
+	 * digit.  For instance, if the range for longs is
+	 * [-2147483648..2147483647] and the input base is 10,
+	 * cutoff will be set to 214748364 and cutlim to either
+	 * 7 (neg==0) or 8 (neg==1), meaning that if we have accumulated
+	 * a value > 214748364, or equal but the next digit is > 7 (or 8),
+	 * the number is too big, and we will return a range error.
+	 *
+	 * Set 'any' if any `digits' consumed; make it negative to indicate
+	 * overflow.
+	 */
+	cutoff = neg ? (unsigned long)-(LONG_MIN + LONG_MAX) + LONG_MAX
+	    : LONG_MAX;
+	cutlim = cutoff % base;
+	cutoff /= base;
+	for ( ; ; c = *s++) {
+		if (c >= '0' && c <= '9')
+			c -= '0';
+		else if (c >= 'A' && c <= 'Z')
+			c -= 'A' - 10;
+		else if (c >= 'a' && c <= 'z')
+			c -= 'a' - 10;
+		else
+			break;
+		if (c >= base)
+			break;
+		if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
+			any = -1;
+		else {
+			any = 1;
+			acc *= base;
+			acc += c;
+		}
+	}
+	if (any < 0) {
+		acc = neg ? LONG_MIN : LONG_MAX;
+	} else if (neg)
+		acc = -acc;
+	if (endptr != NULL)
+		*endptr = (char *)(any ? s - 1 : nptr);
+	return (acc);
+}
diff --git a/lib/libc/strtoll.c b/lib/libc/strtoll.c
new file mode 100644
index 0000000..4e101e8
--- /dev/null
+++ b/lib/libc/strtoll.c
@@ -0,0 +1,134 @@
+/*-
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * Copyright (c) 1992, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Copyright (c) 2011 The FreeBSD Foundation
+ * All rights reserved.
+ * Portions of this software were developed by David Chisnall
+ * under sponsorship from the FreeBSD Foundation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. 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.
+ * 3. Neither the name of the University 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 REGENTS 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 REGENTS 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 <errno.h>
+#include <limits.h>
+#include <stddef.h>
+#include <stdlib.h>
+
+/*
+ * Convert a string to a long long integer.
+ *
+ * Assumes that the upper and lower case
+ * alphabets and digits are each contiguous.
+ */
+long long strtoll(const char *nptr, char **endptr, int base)
+{
+	const char *s;
+	unsigned long long acc;
+	char c;
+	unsigned long long cutoff;
+	int neg, any, cutlim;
+
+	/*
+	 * Skip white space and pick up leading +/- sign if any.
+	 * If base is 0, allow 0x for hex and 0 for octal, else
+	 * assume decimal; if base is already 16, allow 0x.
+	 */
+	s = nptr;
+	do {
+		c = *s++;
+	} while (isspace((unsigned char)c));
+	if (c == '-') {
+		neg = 1;
+		c = *s++;
+	} else {
+		neg = 0;
+		if (c == '+')
+			c = *s++;
+	}
+	if ((base == 0 || base == 16) &&
+	    c == '0' && (*s == 'x' || *s == 'X') &&
+	    ((s[1] >= '0' && s[1] <= '9') ||
+	    (s[1] >= 'A' && s[1] <= 'F') ||
+	    (s[1] >= 'a' && s[1] <= 'f'))) {
+		c = s[1];
+		s += 2;
+		base = 16;
+	}
+	if (base == 0)
+		base = c == '0' ? 8 : 10;
+	acc = any = 0;
+
+	/*
+	 * Compute the cutoff value between legal numbers and illegal
+	 * numbers.  That is the largest legal value, divided by the
+	 * base.  An input number that is greater than this value, if
+	 * followed by a legal input character, is too big.  One that
+	 * is equal to this value may be valid or not; the limit
+	 * between valid and invalid numbers is then based on the last
+	 * digit.  For instance, if the range for quads is
+	 * [-9223372036854775808..9223372036854775807] and the input base
+	 * is 10, cutoff will be set to 922337203685477580 and cutlim to
+	 * either 7 (neg==0) or 8 (neg==1), meaning that if we have
+	 * accumulated a value > 922337203685477580, or equal but the
+	 * next digit is > 7 (or 8), the number is too big, and we will
+	 * return a range error.
+	 *
+	 * Set 'any' if any `digits' consumed; make it negative to indicate
+	 * overflow.
+	 */
+	cutoff = neg ? (unsigned long long)-(LLONG_MIN + LLONG_MAX) + LLONG_MAX
+	    : LLONG_MAX;
+	cutlim = cutoff % base;
+	cutoff /= base;
+	for ( ; ; c = *s++) {
+		if (c >= '0' && c <= '9')
+			c -= '0';
+		else if (c >= 'A' && c <= 'Z')
+			c -= 'A' - 10;
+		else if (c >= 'a' && c <= 'z')
+			c -= 'a' - 10;
+		else
+			break;
+		if (c >= base)
+			break;
+		if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
+			any = -1;
+		else {
+			any = 1;
+			acc *= base;
+			acc += c;
+		}
+	}
+	if (any < 0) {
+		acc = neg ? LLONG_MIN : LLONG_MAX;
+	} else if (neg)
+		acc = -acc;
+	if (endptr != NULL)
+		*endptr = (char *)(any ? s - 1 : nptr);
+	return (acc);
+}
diff --git a/lib/libc/strtoul.c b/lib/libc/strtoul.c
new file mode 100644
index 0000000..b42fb14
--- /dev/null
+++ b/lib/libc/strtoul.c
@@ -0,0 +1,112 @@
+/*-
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * Copyright (c) 1990, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Copyright (c) 2011 The FreeBSD Foundation
+ * All rights reserved.
+ * Portions of this software were developed by David Chisnall
+ * under sponsorship from the FreeBSD Foundation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. 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.
+ * 3. Neither the name of the University 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 REGENTS 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 REGENTS 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 <errno.h>
+#include <limits.h>
+#include <stddef.h>
+#include <stdlib.h>
+
+/*
+ * Convert a string to an unsigned long integer.
+ *
+ * Assumes that the upper and lower case
+ * alphabets and digits are each contiguous.
+ */
+unsigned long strtoul(const char *nptr, char **endptr, int base)
+{
+	const char *s;
+	unsigned long acc;
+	char c;
+	unsigned long cutoff;
+	int neg, any, cutlim;
+
+	/*
+	 * See strtol for comments as to the logic used.
+	 */
+	s = nptr;
+	do {
+		c = *s++;
+	} while (isspace((unsigned char)c));
+	if (c == '-') {
+		neg = 1;
+		c = *s++;
+	} else {
+		neg = 0;
+		if (c == '+')
+			c = *s++;
+	}
+	if ((base == 0 || base == 16) &&
+	    c == '0' && (*s == 'x' || *s == 'X') &&
+	    ((s[1] >= '0' && s[1] <= '9') ||
+	    (s[1] >= 'A' && s[1] <= 'F') ||
+	    (s[1] >= 'a' && s[1] <= 'f'))) {
+		c = s[1];
+		s += 2;
+		base = 16;
+	}
+	if (base == 0)
+		base = c == '0' ? 8 : 10;
+	acc = any = 0;
+
+	cutoff = ULONG_MAX / base;
+	cutlim = ULONG_MAX % base;
+	for ( ; ; c = *s++) {
+		if (c >= '0' && c <= '9')
+			c -= '0';
+		else if (c >= 'A' && c <= 'Z')
+			c -= 'A' - 10;
+		else if (c >= 'a' && c <= 'z')
+			c -= 'a' - 10;
+		else
+			break;
+		if (c >= base)
+			break;
+		if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
+			any = -1;
+		else {
+			any = 1;
+			acc *= base;
+			acc += c;
+		}
+	}
+	if (any < 0) {
+		acc = ULONG_MAX;
+	} else if (neg)
+		acc = -acc;
+	if (endptr != NULL)
+		*endptr = (char *)(any ? s - 1 : nptr);
+	return (acc);
+}
diff --git a/lib/libc/strtoull.c b/lib/libc/strtoull.c
new file mode 100644
index 0000000..2e65a43
--- /dev/null
+++ b/lib/libc/strtoull.c
@@ -0,0 +1,112 @@
+/*-
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * Copyright (c) 1992, 1993
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * Copyright (c) 2011 The FreeBSD Foundation
+ * All rights reserved.
+ * Portions of this software were developed by David Chisnall
+ * under sponsorship from the FreeBSD Foundation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. 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.
+ * 3. Neither the name of the University 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 REGENTS 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 REGENTS 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 <errno.h>
+#include <limits.h>
+#include <stddef.h>
+#include <stdlib.h>
+
+/*
+ * Convert a string to an unsigned long long integer.
+ *
+ * Assumes that the upper and lower case
+ * alphabets and digits are each contiguous.
+ */
+unsigned long long strtoull(const char *nptr, char **endptr, int base)
+{
+	const char *s;
+	unsigned long long acc;
+	char c;
+	unsigned long long cutoff;
+	int neg, any, cutlim;
+
+	/*
+	 * See strtoq for comments as to the logic used.
+	 */
+	s = nptr;
+	do {
+		c = *s++;
+	} while (isspace((unsigned char)c));
+	if (c == '-') {
+		neg = 1;
+		c = *s++;
+	} else {
+		neg = 0;
+		if (c == '+')
+			c = *s++;
+	}
+	if ((base == 0 || base == 16) &&
+	    c == '0' && (*s == 'x' || *s == 'X') &&
+	    ((s[1] >= '0' && s[1] <= '9') ||
+	    (s[1] >= 'A' && s[1] <= 'F') ||
+	    (s[1] >= 'a' && s[1] <= 'f'))) {
+		c = s[1];
+		s += 2;
+		base = 16;
+	}
+	if (base == 0)
+		base = c == '0' ? 8 : 10;
+	acc = any = 0;
+
+	cutoff = ULLONG_MAX / base;
+	cutlim = ULLONG_MAX % base;
+	for ( ; ; c = *s++) {
+		if (c >= '0' && c <= '9')
+			c -= '0';
+		else if (c >= 'A' && c <= 'Z')
+			c -= 'A' - 10;
+		else if (c >= 'a' && c <= 'z')
+			c -= 'a' - 10;
+		else
+			break;
+		if (c >= base)
+			break;
+		if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
+			any = -1;
+		else {
+			any = 1;
+			acc *= base;
+			acc += c;
+		}
+	}
+	if (any < 0) {
+		acc = ULLONG_MAX;
+	} else if (neg)
+		acc = -acc;
+	if (endptr != NULL)
+		*endptr = (char *)(any ? s - 1 : nptr);
+	return (acc);
+}
diff --git a/lib/mpmm/mpmm.c b/lib/mpmm/mpmm.c
new file mode 100644
index 0000000..a66f2aa
--- /dev/null
+++ b/lib/mpmm/mpmm.c
@@ -0,0 +1,72 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <common/debug.h>
+#include <lib/mpmm/mpmm.h>
+
+#include <plat/common/platform.h>
+
+#if ENABLE_MPMM_FCONF
+#	include <lib/fconf/fconf.h>
+#	include <lib/fconf/fconf_mpmm_getter.h>
+#endif
+
+static uint64_t read_cpuppmcr_el3_mpmmpinctl(void)
+{
+	return (read_cpuppmcr_el3() >> CPUPPMCR_EL3_MPMMPINCTL_SHIFT) &
+		CPUPPMCR_EL3_MPMMPINCTL_MASK;
+}
+
+static void write_cpumpmmcr_el3_mpmm_en(uint64_t mpmm_en)
+{
+	uint64_t value = read_cpumpmmcr_el3();
+
+	value &= ~(CPUMPMMCR_EL3_MPMM_EN_MASK << CPUMPMMCR_EL3_MPMM_EN_SHIFT);
+	value |= (mpmm_en & CPUMPMMCR_EL3_MPMM_EN_MASK) <<
+		CPUMPMMCR_EL3_MPMM_EN_SHIFT;
+
+	write_cpumpmmcr_el3(value);
+}
+
+static bool mpmm_supported(void)
+{
+	bool supported = false;
+	const struct mpmm_topology *topology;
+
+#if ENABLE_MPMM_FCONF
+	topology = FCONF_GET_PROPERTY(mpmm, config, topology);
+#else
+	topology = plat_mpmm_topology();
+#endif /* ENABLE_MPMM_FCONF */
+
+	/*
+	 * For the current core firstly try to find out if the platform
+	 * configuration has claimed support for MPMM, then make sure that MPMM
+	 * is controllable through the system registers.
+	 */
+
+	if (topology != NULL) {
+		unsigned int core_pos = plat_my_core_pos();
+
+		supported = topology->cores[core_pos].supported &&
+			(read_cpuppmcr_el3_mpmmpinctl() == 0U);
+	} else {
+		ERROR("MPMM: failed to generate MPMM topology\n");
+	}
+
+	return supported;
+}
+
+void mpmm_enable(void)
+{
+	bool supported = mpmm_supported();
+
+	if (supported) {
+		write_cpumpmmcr_el3_mpmm_en(1U);
+	}
+}
diff --git a/lib/mpmm/mpmm.mk b/lib/mpmm/mpmm.mk
new file mode 100644
index 0000000..826f925
--- /dev/null
+++ b/lib/mpmm/mpmm.mk
@@ -0,0 +1,29 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+include lib/extensions/amu/amu.mk
+include lib/fconf/fconf.mk
+
+ifneq (${ENABLE_MPMM},0)
+        ifneq ($(ARCH),aarch64)
+                $(error MPMM support (`ENABLE_MPMM`) can only be enabled in AArch64 images (`ARCH`))
+        endif
+
+        ifeq (${ENABLE_AMU_AUXILIARY_COUNTERS},0) # For MPMM gear AMU counters
+                $(error MPMM support (`ENABLE_MPM`) requires auxiliary AMU counter support (`ENABLE_AMU_AUXILIARY_COUNTERS`))
+        endif
+endif
+
+MPMM_SOURCES	:=	lib/mpmm/mpmm.c
+MPMM_SOURCES	+=	${AMU_SOURCES}
+
+ifneq (${ENABLE_MPMM_FCONF},0)
+        ifeq (${ENABLE_MPMM},0)
+                $(error MPMM FCONF support (`ENABLE_MPMM_FCONF`) requires MPMM support (`ENABLE_MPMM`))
+        endif
+
+        MPMM_SOURCES	+= ${FCONF_MPMM_SOURCES}
+endif
diff --git a/lib/optee/optee_utils.c b/lib/optee/optee_utils.c
index 0ad1082..72979cd 100644
--- a/lib/optee/optee_utils.c
+++ b/lib/optee/optee_utils.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -47,25 +47,24 @@
 
 /*******************************************************************************
  * Check if it is a valid tee header
- * Return 1 if valid
- * Return 0 if invalid
+ * Return true if valid
+ * Return false if invalid
  ******************************************************************************/
-static inline int tee_validate_header(optee_header_t *header)
+static bool tee_validate_header(optee_header_t *header)
 {
-	int valid = 0;
-
 	if ((header->magic == TEE_MAGIC_NUM_OPTEE) &&
 		(header->version == 2u) &&
 		(header->nb_images > 0u) &&
 		(header->nb_images <= OPTEE_MAX_NUM_IMAGES)) {
-		valid = 1;
+		return true;
 	}
 
-	else {
-		WARN("Not a known TEE, use default loading options.\n");
-	}
+	return false;
+}
 
-	return valid;
+bool optee_header_is_valid(uintptr_t header_base)
+{
+	return tee_validate_header((optee_header_t *)header_base);
 }
 
 /*******************************************************************************
@@ -83,11 +82,14 @@
 	init_size = image->size;
 
 	/*
-	 * -1 indicates loader decided address; take our pre-mapped area
-	 * for current image since arm-tf could not allocate memory dynamically
+	 * image->load_addr_hi & image->load_addr_lo set to UINT32_MAX indicate
+	 * loader decided address; take our pre-mapped area for current image
+	 * since arm-tf could not allocate memory dynamically
 	 */
-	if (init_load_addr == -1)
+	if ((image->load_addr_hi == UINT32_MAX) &&
+	    (image->load_addr_lo == UINT32_MAX)) {
 		init_load_addr = image_info->image_base;
+	}
 
 	/* Check that the default end address doesn't overflow */
 	if (check_uptr_overflow(image_info->image_base,
@@ -139,7 +141,8 @@
 
 {
 	optee_header_t *header;
-	int num, ret;
+	uint32_t num;
+	int ret;
 
 	assert(header_ep);
 	header = (optee_header_t *)header_ep->pc;
@@ -182,7 +185,7 @@
 	}
 
 	/* Parse OPTEE image */
-	for (num = 0; num < header->nb_images; num++) {
+	for (num = 0U; num < header->nb_images; num++) {
 		if (header->optee_image_list[num].image_id ==
 				OPTEE_PAGER_IMAGE_ID) {
 			ret = parse_optee_image(pager_image_info,
diff --git a/lib/psci/psci_private.h b/lib/psci/psci_private.h
index e2dcfa8..72bd6bd 100644
--- a/lib/psci/psci_private.h
+++ b/lib/psci/psci_private.h
@@ -42,6 +42,11 @@
 			define_psci_cap(PSCI_SYSTEM_RESET2_AARCH64) |	\
 			define_psci_cap(PSCI_MEM_CHK_RANGE_AARCH64))
 
+/* Internally PSCI uses a uint16_t for various cpu indexes so
+ * define a limit to number of CPUs that can be initialised.
+ */
+#define PSCI_MAX_CPUS_INDEX	0xFFFFU
+
 /*
  * Helper functions to get/set the fields of PSCI per-cpu data.
  */
@@ -134,7 +139,7 @@
 	unsigned char level;
 
 	/* For indexing the psci_lock array*/
-	unsigned char lock_index;
+	uint16_t lock_index;
 } non_cpu_pd_node_t;
 
 typedef struct cpu_pwr_domain_node {
@@ -239,7 +244,7 @@
 #endif /* HW_ASSISTED_COHERENCY */
 
 static inline void psci_lock_init(non_cpu_pd_node_t *non_cpu_pd_node,
-				  unsigned char idx)
+				  uint16_t idx)
 {
 	non_cpu_pd_node[idx].lock_index = idx;
 }
diff --git a/lib/psci/psci_setup.c b/lib/psci/psci_setup.c
index d1ec998..3cb4f7e 100644
--- a/lib/psci/psci_setup.c
+++ b/lib/psci/psci_setup.c
@@ -17,6 +17,12 @@
 
 #include "psci_private.h"
 
+/*
+ * Check that PLATFORM_CORE_COUNT fits into the number of cores
+ * that can be represented by PSCI_MAX_CPUS_INDEX.
+ */
+CASSERT(PLATFORM_CORE_COUNT <= (PSCI_MAX_CPUS_INDEX + 1U), assert_psci_cores_overflow);
+
 /*******************************************************************************
  * Per cpu non-secure contexts used to program the architectural state prior
  * return to the normal world.
@@ -34,11 +40,13 @@
  * Function which initializes the 'psci_non_cpu_pd_nodes' or the
  * 'psci_cpu_pd_nodes' corresponding to the power level.
  ******************************************************************************/
-static void __init psci_init_pwr_domain_node(unsigned char node_idx,
+static void __init psci_init_pwr_domain_node(uint16_t node_idx,
 					unsigned int parent_idx,
 					unsigned char level)
 {
 	if (level > PSCI_CPU_PWR_LVL) {
+		assert(node_idx < PSCI_NUM_NON_CPU_PWR_DOMAINS);
+
 		psci_non_cpu_pd_nodes[node_idx].level = level;
 		psci_lock_init(psci_non_cpu_pd_nodes, node_idx);
 		psci_non_cpu_pd_nodes[node_idx].parent_node = parent_idx;
@@ -47,6 +55,8 @@
 	} else {
 		psci_cpu_data_t *svc_cpu_data;
 
+		assert(node_idx < PLATFORM_CORE_COUNT);
+
 		psci_cpu_pd_nodes[node_idx].parent_node = parent_idx;
 
 		/* Initialize with an invalid mpidr */
@@ -144,7 +154,7 @@
 
 			for (j = node_index;
 				j < (node_index + num_children); j++)
-				psci_init_pwr_domain_node((unsigned char)j,
+				psci_init_pwr_domain_node((uint16_t)j,
 						  parent_node_index - 1U,
 						  (unsigned char)level);
 
@@ -240,7 +250,8 @@
 		psci_caps |=  define_psci_cap(PSCI_CPU_ON_AARCH64);
 	if ((psci_plat_pm_ops->pwr_domain_suspend != NULL) &&
 	    (psci_plat_pm_ops->pwr_domain_suspend_finish != NULL)) {
-		psci_caps |=  define_psci_cap(PSCI_CPU_SUSPEND_AARCH64);
+		if (psci_plat_pm_ops->validate_power_state != NULL)
+			psci_caps |=  define_psci_cap(PSCI_CPU_SUSPEND_AARCH64);
 		if (psci_plat_pm_ops->get_sys_suspend_power_state != NULL)
 			psci_caps |=  define_psci_cap(PSCI_SYSTEM_SUSPEND_AARCH64);
 	}
diff --git a/lib/xlat_mpu/aarch64/enable_mpu.S b/lib/xlat_mpu/aarch64/enable_mpu.S
new file mode 100644
index 0000000..3791f2d
--- /dev/null
+++ b/lib/xlat_mpu/aarch64/enable_mpu.S
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <asm_macros.S>
+#include <assert_macros.S>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <platform_def.h>
+
+	.global	enable_mpu_direct_el2
+
+	/* void enable_mmu_direct_el2(unsigned int flags) */
+func enable_mpu_direct_el2
+#if ENABLE_ASSERTIONS
+	mrs	x1, sctlr_el2
+	tst	x1, #SCTLR_M_BIT
+	ASM_ASSERT(eq)
+#endif
+	mov	x7, x0
+	adrp	x0, mmu_cfg_params
+	add	x0, x0, :lo12:mmu_cfg_params
+
+	/* (MAIRs are already set up) */
+
+	/* TCR */
+	ldr	x2, [x0, #(MMU_CFG_TCR << 3)]
+	msr	tcr_el2, x2
+
+	/*
+	 * Ensure all translation table writes have drained into memory, the TLB
+	 * invalidation is complete, and translation register writes are
+	 * committed before enabling the MMU
+	 */
+	dsb	ish
+	isb
+
+	/* Set and clear required fields of SCTLR */
+	mrs	x4, sctlr_el2
+	mov_imm	x5, SCTLR_WXN_BIT | SCTLR_C_BIT | SCTLR_M_BIT
+	orr	x4, x4, x5
+
+	/* Additionally, amend SCTLR fields based on flags */
+	bic	x5, x4, #SCTLR_C_BIT
+	tst	x7, #DISABLE_DCACHE
+	csel	x4, x5, x4, ne
+
+	msr	sctlr_el2, x4
+	isb
+
+	ret
+endfunc enable_mpu_direct_el2
diff --git a/lib/xlat_mpu/aarch64/xlat_mpu_arch.c b/lib/xlat_mpu/aarch64/xlat_mpu_arch.c
new file mode 100644
index 0000000..5068eb8
--- /dev/null
+++ b/lib/xlat_mpu/aarch64/xlat_mpu_arch.c
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+#include "../xlat_mpu_private.h"
+#include <arch.h>
+#include <arch_features.h>
+#include <lib/cassert.h>
+#include <lib/utils_def.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#include <fvp_r_arch_helpers.h>
+
+#warning "xlat_mpu library is currently experimental and its API may change in future."
+
+#if ENABLE_ASSERTIONS
+/*
+ * Return minimum virtual address space size supported by the architecture
+ */
+uintptr_t xlat_get_min_virt_addr_space_size(void)
+{
+	uintptr_t ret;
+
+	if (is_armv8_4_ttst_present()) {
+		ret = MIN_VIRT_ADDR_SPACE_SIZE_TTST;
+	} else {
+		ret = MIN_VIRT_ADDR_SPACE_SIZE;
+	}
+	return ret;
+}
+#endif /* ENABLE_ASSERTIONS*/
+
+bool is_mpu_enabled_ctx(const xlat_ctx_t *ctx)
+{
+	if (ctx->xlat_regime == EL1_EL0_REGIME) {
+		assert(xlat_arch_current_el() >= 1U);
+		return (read_sctlr_el1() & SCTLR_M_BIT) != 0U;
+	} else {
+		assert(xlat_arch_current_el() >= 2U);
+		return (read_sctlr_el2() & SCTLR_M_BIT) != 0U;
+	}
+}
+
+bool is_dcache_enabled(void)
+{
+	unsigned int el = get_current_el();
+
+	if (el == 1U) {
+		return (read_sctlr_el1() & SCTLR_C_BIT) != 0U;
+	} else {  /* must be EL2 */
+		return (read_sctlr_el2() & SCTLR_C_BIT) != 0U;
+	}
+}
+
+unsigned int xlat_arch_current_el(void)
+{
+	unsigned int el = (unsigned int)GET_EL(read_CurrentEl());
+
+	assert(el > 0U);
+
+	return el;
+}
+
diff --git a/lib/xlat_mpu/ro_xlat_mpu.mk b/lib/xlat_mpu/ro_xlat_mpu.mk
new file mode 100644
index 0000000..23f1d46
--- /dev/null
+++ b/lib/xlat_mpu/ro_xlat_mpu.mk
@@ -0,0 +1,14 @@
+#
+# Copyright (c) 2021, ARM Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifeq (${USE_DEBUGFS}, 1)
+    $(error "Debugfs requires functionality from the dynamic translation \
+             library and is incompatible with ALLOW_RO_XLAT_TABLES.")
+endif
+
+ifeq (${ARCH},aarch32)
+    $(error "The xlat_mpu library does not currently support AArch32.")
+endif
diff --git a/lib/xlat_mpu/xlat_mpu.mk b/lib/xlat_mpu/xlat_mpu.mk
new file mode 100644
index 0000000..041b91c
--- /dev/null
+++ b/lib/xlat_mpu/xlat_mpu.mk
@@ -0,0 +1,19 @@
+#
+# Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+XLAT_MPU_LIB_V1_SRCS	:=	$(addprefix lib/xlat_mpu/,		\
+				${ARCH}/enable_mpu.S			\
+				${ARCH}/xlat_mpu_arch.c			\
+				xlat_mpu_context.c			\
+				xlat_mpu_core.c				\
+				xlat_mpu_utils.c)
+
+XLAT_MPU_LIB_V1	:=	1
+$(eval $(call add_define,XLAT_MPU_LIB_V1))
+
+ifeq (${ALLOW_XLAT_MPU}, 1)
+    include lib/xlat_mpu_v2/ro_xlat_mpu.mk
+endif
diff --git a/lib/xlat_mpu/xlat_mpu_context.c b/lib/xlat_mpu/xlat_mpu_context.c
new file mode 100644
index 0000000..28c463b
--- /dev/null
+++ b/lib/xlat_mpu/xlat_mpu_context.c
@@ -0,0 +1,65 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+
+#include "lib/xlat_mpu/xlat_mpu.h"
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include "xlat_mpu_private.h"
+
+#include <fvp_r_arch_helpers.h>
+#include <platform_def.h>
+
+#warning "xlat_mpu library is currently experimental and its API may change in future."
+
+
+/*
+ * MMU configuration register values for the active translation context. Used
+ * from the MMU assembly helpers.
+ */
+uint64_t mmu_cfg_params[MMU_CFG_PARAM_MAX];
+
+/*
+ * Allocate and initialise the default translation context for the BL image
+ * currently executing.
+ */
+REGISTER_XLAT_CONTEXT(tf, MAX_MMAP_REGIONS, MAX_XLAT_TABLES,
+			PLAT_VIRT_ADDR_SPACE_SIZE, PLAT_PHY_ADDR_SPACE_SIZE);
+
+void mmap_add(const mmap_region_t *mm)
+{
+	mmap_add_ctx(&tf_xlat_ctx, mm);
+}
+
+void __init init_xlat_tables(void)
+{
+	assert(tf_xlat_ctx.xlat_regime == EL_REGIME_INVALID);
+
+	unsigned int current_el = xlat_arch_current_el();
+
+	if (current_el == 1U) {
+		tf_xlat_ctx.xlat_regime = EL1_EL0_REGIME;
+	} else {
+		assert(current_el == 2U);
+		tf_xlat_ctx.xlat_regime = EL2_REGIME;
+	}
+	/* Note:  If EL3 is supported in future v8-R64, add EL3 assignment */
+	init_xlat_tables_ctx(&tf_xlat_ctx);
+}
+
+int xlat_get_mem_attributes(uintptr_t base_va, uint32_t *attr)
+{
+	return xlat_get_mem_attributes_ctx(&tf_xlat_ctx, base_va, attr);
+}
+
+void enable_mpu_el2(unsigned int flags)
+{
+	/* EL2 is strictly MPU on v8-R64, so no need for setup_mpu_cfg() */
+	enable_mpu_direct_el2(flags);
+}
diff --git a/lib/xlat_mpu/xlat_mpu_core.c b/lib/xlat_mpu/xlat_mpu_core.c
new file mode 100644
index 0000000..6b4b0c2
--- /dev/null
+++ b/lib/xlat_mpu/xlat_mpu_core.c
@@ -0,0 +1,408 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_features.h>
+#include <common/debug.h>
+#include <lib/utils_def.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include "xlat_mpu_private.h"
+
+#include <fvp_r_arch_helpers.h>
+#include <platform_def.h>
+
+#warning "xlat_mpu library is currently experimental and its API may change in future."
+
+
+/* Helper function that cleans the data cache only if it is enabled. */
+static inline __attribute__((unused))
+	void xlat_clean_dcache_range(uintptr_t addr, size_t size)
+{
+	if (is_dcache_enabled()) {
+		clean_dcache_range(addr, size);
+	}
+}
+
+
+
+/* Calculate region-attributes byte for PRBAR part of MPU-region descriptor: */
+uint64_t prbar_attr_value(uint32_t attr)
+{
+	uint64_t retValue = UL(0);
+	uint64_t extract;  /* temp var holding bit extracted from attr */
+
+	/* Extract and stuff SH: */
+	extract = (uint64_t) ((attr >> MT_SHAREABILITY_SHIFT)
+				& MT_SHAREABILITY_MASK);
+	retValue |= (extract << PRBAR_SH_SHIFT);
+
+	/* Extract and stuff AP: */
+	extract = (uint64_t) ((attr >> MT_PERM_SHIFT) & MT_PERM_MASK);
+	if (extract == 0U) {
+		retValue |= (UL(2) << PRBAR_AP_SHIFT);
+	} else /* extract == 1 */ {
+		retValue |= (UL(0) << PRBAR_AP_SHIFT);
+	}
+
+	/* Extract and stuff XN: */
+	extract = (uint64_t) ((attr >> MT_EXECUTE_SHIFT) & MT_EXECUTE_MASK);
+	retValue |= (extract << PRBAR_XN_SHIFT);
+	/* However, also don't execute in peripheral space: */
+	extract = (uint64_t) ((attr >> MT_TYPE_SHIFT) & MT_TYPE_MASK);
+	if (extract == 0U) {
+		retValue |= (UL(1) << PRBAR_XN_SHIFT);
+	}
+	return retValue;
+}
+
+/* Calculate region-attributes byte for PRLAR part of MPU-region descriptor: */
+uint64_t prlar_attr_value(uint32_t attr)
+{
+	uint64_t retValue = UL(0);
+	uint64_t extract;  /* temp var holding bit extracted from attr */
+
+	/* Extract and stuff AttrIndx: */
+	extract = (uint64_t) ((attr >> MT_TYPE_SHIFT)
+				& MT_TYPE_MASK);
+	switch (extract) {
+	case UL(0):
+		retValue |= (UL(1) << PRLAR_ATTR_SHIFT);
+		break;
+	case UL(2):
+		/* 0, so OR in nothing */
+		break;
+	case UL(3):
+		retValue |= (UL(2) << PRLAR_ATTR_SHIFT);
+		break;
+	default:
+		retValue |= (extract << PRLAR_ATTR_SHIFT);
+		break;
+	}
+
+	/* Stuff EN: */
+	retValue |= (UL(1) << PRLAR_EN_SHIFT);
+
+	/* Force NS to 0 (Secure);  v8-R64 only supports Secure: */
+	extract = ~(1U << PRLAR_NS_SHIFT);
+	retValue &= extract;
+
+	return retValue;
+}
+
+/*
+ * Function that writes an MPU "translation" into the MPU registers. If not
+ * possible (e.g., if no more MPU regions available) boot is aborted.
+ */
+static void mpu_map_region(mmap_region_t *mm)
+{
+	uint64_t prenr_el2_value = 0UL;
+	uint64_t prbar_attrs = 0UL;
+	uint64_t prlar_attrs = 0UL;
+	int region_to_use = 0;
+
+	/* If all MPU regions in use, then abort boot: */
+	prenr_el2_value = read_prenr_el2();
+	assert(prenr_el2_value != 0xffffffff);
+
+	/* Find and select first-available MPU region (PRENR has an enable bit
+	 * for each MPU region, 1 for in-use or 0 for unused):
+	 */
+	for (region_to_use = 0;  region_to_use < N_MPU_REGIONS;
+	     region_to_use++) {
+		if (((prenr_el2_value >> region_to_use) & 1) == 0) {
+			break;
+		}
+	}
+	write_prselr_el2((uint64_t) (region_to_use));
+	isb();
+
+	/* Set base and limit addresses: */
+	write_prbar_el2(mm->base_pa & PRBAR_PRLAR_ADDR_MASK);
+	write_prlar_el2((mm->base_pa + mm->size - 1UL)
+			& PRBAR_PRLAR_ADDR_MASK);
+	dsbsy();
+	isb();
+
+	/* Set attributes: */
+	prbar_attrs = prbar_attr_value(mm->attr);
+	write_prbar_el2(read_prbar_el2() | prbar_attrs);
+	prlar_attrs = prlar_attr_value(mm->attr);
+	write_prlar_el2(read_prlar_el2() | prlar_attrs);
+	dsbsy();
+	isb();
+
+	/* Mark this MPU region as used: */
+	prenr_el2_value |= (1 << region_to_use);
+	write_prenr_el2(prenr_el2_value);
+	isb();
+}
+
+/*
+ * Function that verifies that a region can be mapped.
+ * Returns:
+ *        0: Success, the mapping is allowed.
+ *   EINVAL: Invalid values were used as arguments.
+ *   ERANGE: The memory limits were surpassed.
+ *   ENOMEM: There is not enough memory in the mmap array.
+ *    EPERM: Region overlaps another one in an invalid way.
+ */
+static int mmap_add_region_check(const xlat_ctx_t *ctx, const mmap_region_t *mm)
+{
+	unsigned long long base_pa = mm->base_pa;
+	uintptr_t base_va = mm->base_va;
+	size_t size = mm->size;
+
+	unsigned long long end_pa = base_pa + size - 1U;
+	uintptr_t end_va = base_va + size - 1U;
+
+	if (base_pa != base_va) {
+		return -EINVAL;  /* MPU does not perform address translation */
+	}
+	if ((base_pa % 64ULL) != 0ULL) {
+		return -EINVAL;  /* MPU requires 64-byte alignment */
+	}
+	/* Check for overflows */
+	if ((base_pa > end_pa) || (base_va > end_va)) {
+		return -ERANGE;
+	}
+	if (end_pa > ctx->pa_max_address) {
+		return -ERANGE;
+	}
+	/* Check that there is space in the ctx->mmap array */
+	if (ctx->mmap[ctx->mmap_num - 1].size != 0U) {
+		return -ENOMEM;
+	}
+	/* Check for PAs and VAs overlaps with all other regions */
+	for (const mmap_region_t *mm_cursor = ctx->mmap;
+	     mm_cursor->size != 0U; ++mm_cursor) {
+
+		uintptr_t mm_cursor_end_va =
+			mm_cursor->base_va + mm_cursor->size - 1U;
+
+		/*
+		 * Check if one of the regions is completely inside the other
+		 * one.
+		 */
+		bool fully_overlapped_va =
+			((base_va >= mm_cursor->base_va) &&
+					(end_va <= mm_cursor_end_va)) ||
+			((mm_cursor->base_va >= base_va) &&
+						(mm_cursor_end_va <= end_va));
+
+		/*
+		 * Full VA overlaps are only allowed if both regions are
+		 * identity mapped (zero offset) or have the same VA to PA
+		 * offset. Also, make sure that it's not the exact same area.
+		 * This can only be done with static regions.
+		 */
+		if (fully_overlapped_va) {
+
+#if PLAT_XLAT_TABLES_DYNAMIC
+			if (((mm->attr & MT_DYNAMIC) != 0U) ||
+			    ((mm_cursor->attr & MT_DYNAMIC) != 0U)) {
+				return -EPERM;
+			}
+#endif /* PLAT_XLAT_TABLES_DYNAMIC */
+			if ((mm_cursor->base_va - mm_cursor->base_pa)
+					!= (base_va - base_pa)) {
+				return -EPERM;
+			}
+			if ((base_va == mm_cursor->base_va) &&
+					(size == mm_cursor->size)) {
+				return -EPERM;
+			}
+		} else {
+			/*
+			 * If the regions do not have fully overlapping VAs,
+			 * then they must have fully separated VAs and PAs.
+			 * Partial overlaps are not allowed
+			 */
+
+			unsigned long long mm_cursor_end_pa =
+				     mm_cursor->base_pa + mm_cursor->size - 1U;
+
+			bool separated_pa = (end_pa < mm_cursor->base_pa) ||
+				(base_pa > mm_cursor_end_pa);
+			bool separated_va = (end_va < mm_cursor->base_va) ||
+				(base_va > mm_cursor_end_va);
+
+			if (!separated_va || !separated_pa) {
+				return -EPERM;
+			}
+		}
+	}
+
+	return 0;
+}
+
+void mmap_add_region_ctx(xlat_ctx_t *ctx, const mmap_region_t *mm)
+{
+	mmap_region_t *mm_cursor = ctx->mmap, *mm_destination;
+	const mmap_region_t *mm_end = ctx->mmap + ctx->mmap_num;
+	const mmap_region_t *mm_last;
+	unsigned long long end_pa = mm->base_pa + mm->size - 1U;
+	uintptr_t end_va = mm->base_va + mm->size - 1U;
+	int ret;
+
+	/* Ignore empty regions */
+	if (mm->size == 0U) {
+		return;
+	}
+
+	/* Static regions must be added before initializing the xlat tables. */
+	assert(!ctx->initialized);
+
+	ret = mmap_add_region_check(ctx, mm);
+	if (ret != 0) {
+		ERROR("mmap_add_region_check() failed. error %d\n", ret);
+		assert(false);
+		return;
+	}
+
+	/*
+	 * Find the last entry marker in the mmap
+	 */
+	mm_last = ctx->mmap;
+	while ((mm_last->size != 0U) && (mm_last < mm_end)) {
+		++mm_last;
+	}
+
+	/*
+	 * Check if we have enough space in the memory mapping table.
+	 * This shouldn't happen as we have checked in mmap_add_region_check
+	 * that there is free space.
+	 */
+	assert(mm_last->size == 0U);
+
+	/* Make room for new region by moving other regions up by one place */
+	mm_destination = mm_cursor + 1;
+	(void)memmove(mm_destination, mm_cursor,
+		(uintptr_t)mm_last - (uintptr_t)mm_cursor);
+
+	/*
+	 * Check we haven't lost the empty sentinel from the end of the array.
+	 * This shouldn't happen as we have checked in mmap_add_region_check
+	 * that there is free space.
+	 */
+	assert(mm_end->size == 0U);
+
+	*mm_cursor = *mm;
+
+	if (end_pa > ctx->max_pa) {
+		ctx->max_pa = end_pa;
+	}
+	if (end_va > ctx->max_va) {
+		ctx->max_va = end_va;
+	}
+}
+
+void mmap_add_ctx(xlat_ctx_t *ctx, const mmap_region_t *mm)
+{
+	const mmap_region_t *mm_cursor = mm;
+
+	while (mm_cursor->granularity != 0U) {
+		mmap_add_region_ctx(ctx, mm_cursor);
+		mm_cursor++;
+	}
+}
+
+void __init init_xlat_tables_ctx(xlat_ctx_t *ctx)
+{
+	uint64_t mair = UL(0);
+
+	assert(ctx != NULL);
+	assert(!ctx->initialized);
+	assert((ctx->xlat_regime == EL2_REGIME) ||
+		(ctx->xlat_regime == EL1_EL0_REGIME));
+	/* Note:  Add EL3_REGIME if EL3 is supported in future v8-R64 cores. */
+	assert(!is_mpu_enabled_ctx(ctx));
+
+	mmap_region_t *mm = ctx->mmap;
+
+	assert(ctx->va_max_address >=
+		(xlat_get_min_virt_addr_space_size() - 1U));
+	assert(ctx->va_max_address <= (MAX_VIRT_ADDR_SPACE_SIZE - 1U));
+	assert(IS_POWER_OF_TWO(ctx->va_max_address + 1U));
+
+	xlat_mmap_print(mm);
+
+	/* All tables must be zeroed before mapping any region. */
+
+	for (unsigned int i = 0U; i < ctx->base_table_entries; i++)
+		ctx->base_table[i] = INVALID_DESC;
+
+	/* Also mark all MPU regions as invalid in the MPU hardware itself: */
+	write_prenr_el2(0);
+		/* Sufficient for current, max-32-region implementations. */
+	dsbsy();
+	isb();
+	while (mm->size != 0U) {
+		if (read_prenr_el2() == ALL_MPU_EL2_REGIONS_USED) {
+			ERROR("Not enough MPU regions to map region:\n"
+				" VA:0x%lx  PA:0x%llx  size:0x%zx  attr:0x%x\n",
+				mm->base_va, mm->base_pa, mm->size, mm->attr);
+			panic();
+		} else {
+#if !(HW_ASSISTED_COHERENCY || WARMBOOT_ENABLE_DCACHE_EARLY)
+			xlat_clean_dcache_range((uintptr_t)mm->base_va,
+				mm->size);
+#endif
+			mpu_map_region(mm);
+		}
+		mm++;
+	}
+
+	ctx->initialized = true;
+
+	xlat_tables_print(ctx);
+
+	/* Set attributes in the right indices of the MAIR */
+	mair = MAIR_ATTR_SET(ATTR_DEVICE, ATTR_DEVICE_INDEX);
+	mair |= MAIR_ATTR_SET(ATTR_IWBWA_OWBWA_NTR,
+			ATTR_IWBWA_OWBWA_NTR_INDEX);
+	mair |= MAIR_ATTR_SET(ATTR_NON_CACHEABLE,
+			ATTR_NON_CACHEABLE_INDEX);
+	write_mair_el2(mair);
+	dsbsy();
+	isb();
+}
+
+/*
+ * Function to wipe clean and disable all MPU regions.  This function expects
+ * that the MPU has already been turned off, and caching concerns addressed,
+ * but it nevertheless also explicitly turns off the MPU.
+ */
+void clear_all_mpu_regions(void)
+{
+	uint64_t sctlr_el2_value = 0UL;
+	uint64_t region_n = 0UL;
+
+	/*
+	 * MPU should already be disabled, but explicitly disable it
+	 * nevertheless:
+	 */
+	sctlr_el2_value = read_sctlr_el2() & ~(1UL);
+	write_sctlr_el2(sctlr_el2_value);
+
+	/* Disable all regions: */
+	write_prenr_el2(0UL);
+
+	/* Sequence through all regions, zeroing them out and turning off: */
+	for (region_n = 0UL;  region_n < N_MPU_REGIONS;  region_n++) {
+		write_prselr_el2(region_n);
+		isb();
+		write_prbar_el2((uint64_t) 0);
+		write_prlar_el2((uint64_t) 0);
+		dsbsy();
+		isb();
+	}
+}
diff --git a/lib/xlat_mpu/xlat_mpu_private.h b/lib/xlat_mpu/xlat_mpu_private.h
new file mode 100644
index 0000000..e0e479d
--- /dev/null
+++ b/lib/xlat_mpu/xlat_mpu_private.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef XLAT_MPU_PRIVATE_H
+#define XLAT_MPU_PRIVATE_H
+
+#include <stdbool.h>
+
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#include <platform_def.h>
+
+#if PLAT_XLAT_TABLES_DYNAMIC
+/*
+ * Private shifts and masks to access fields of an mmap attribute
+ */
+/* Dynamic or static */
+#define MT_DYN_SHIFT		U(31)
+
+/*
+ * Memory mapping private attributes
+ *
+ * Private attributes not exposed in the public header.
+ */
+
+#endif /* PLAT_XLAT_TABLES_DYNAMIC */
+
+/* Calculate region-attributes byte for PRBAR part of MPU-region descriptor: */
+uint64_t prbar_attr_value(uint32_t attr);
+/* Calculate region-attributes byte for PRLAR part of MPU-region descriptor: */
+uint64_t prlar_attr_value(uint32_t attr);
+/* Calculates the attr value for a given PRBAR and PRLAR entry value: */
+uint32_t region_attr(uint64_t prbar_attr, uint64_t prlar_attr);
+
+#define PRBAR_PRLAR_ADDR_MASK	UL(0xffffffffffc0)
+	/* mask for PRBAR & PRLAR MPU-region field */
+/* MPU region attribute bit fields: */
+#define PRBAR_SH_SHIFT		UL(4)
+#define PRBAR_SH_MASK		UL(0x3)
+#define PRBAR_AP_SHIFT		UL(2)
+#define PRBAR_AP_MASK		UL(0x3)
+#define PRBAR_XN_SHIFT		UL(1)
+#define PRBAR_XN_MASK		UL(0x3)
+#define PRLAR_NS_SHIFT		UL(4)
+#define PRLAR_NS_MASK		UL(0x3)
+#define PRBAR_ATTR_SHIFT	UL(0)
+#define PRBAR_ATTR_MASK		UL(0x3f)
+#define PRLAR_ATTR_SHIFT	UL(1)
+#define PRLAR_ATTR_MASK		UL(0x7)
+#define PRLAR_EN_SHIFT		UL(0)
+#define PRLAR_EN_MASK		UL(0x1)
+/* Aspects of the source attributes not defined elsewhere: */
+#define MT_PERM_MASK		UL(0x1)
+#define MT_SEC_MASK		UL(0x1)
+#define MT_EXECUTE_MASK		UL(0x3)
+#define MT_TYPE_SHIFT		UL(0)
+
+extern uint64_t mmu_cfg_params[MMU_CFG_PARAM_MAX];
+
+/*
+ * Return the execute-never mask that will prevent instruction fetch at the
+ * given translation regime.
+ */
+uint64_t xlat_arch_regime_get_xn_desc(int xlat_regime);
+
+/* Print VA, PA, size and attributes of all regions in the mmap array. */
+void xlat_mmap_print(const mmap_region_t *mmap);
+
+/*
+ * Print the current state of the translation tables by reading them from
+ * memory.
+ */
+void xlat_tables_print(xlat_ctx_t *ctx);
+
+/*
+ * Returns a block/page table descriptor for the given level and attributes.
+ */
+uint64_t xlat_desc(const xlat_ctx_t *ctx, uint32_t attr,
+		   unsigned long long addr_pa, unsigned int level);
+
+/*
+ * Architecture-specific initialization code.
+ */
+
+/* Returns the current Exception Level. The returned EL must be 1 or higher. */
+unsigned int xlat_arch_current_el(void);
+
+/*
+ * Returns true if the MMU of the translation regime managed by the given
+ * xlat_ctx_t is enabled, false otherwise.
+ */
+bool is_mpu_enabled_ctx(const xlat_ctx_t *ctx);
+
+/*
+ * Returns minimum virtual address space size supported by the architecture
+ */
+uintptr_t xlat_get_min_virt_addr_space_size(void);
+
+#endif /* XLAT_MPU_PRIVATE_H */
diff --git a/lib/xlat_mpu/xlat_mpu_utils.c b/lib/xlat_mpu/xlat_mpu_utils.c
new file mode 100644
index 0000000..5400875
--- /dev/null
+++ b/lib/xlat_mpu/xlat_mpu_utils.c
@@ -0,0 +1,83 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+
+#include <common/debug.h>
+#include <lib/utils_def.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include "xlat_mpu_private.h"
+
+#include <fvp_r_arch_helpers.h>
+#include <platform_def.h>
+
+#warning "xlat_mpu library is currently experimental and its API may change in future."
+
+
+void xlat_mmap_print(__unused const mmap_region_t *mmap)
+{
+	/* Empty */
+}
+
+#if LOG_LEVEL < LOG_LEVEL_VERBOSE
+
+void xlat_tables_print(__unused xlat_ctx_t *ctx)
+{
+	/* Empty */
+}
+
+#else /* if LOG_LEVEL >= LOG_LEVEL_VERBOSE */
+
+static void xlat_tables_print_internal(__unused xlat_ctx_t *ctx)
+{
+	int region_to_use = 0;
+	uintptr_t region_base;
+	size_t region_size;
+	uint64_t prenr_el2_value = 0U;
+
+	/*
+	 * Keep track of how many invalid descriptors are counted in a row.
+	 * Whenever multiple invalid descriptors are found, only the first one
+	 * is printed, and a line is added to inform about how many descriptors
+	 * have been omitted.
+	 */
+
+	/*
+	 * TODO:  Remove this WARN() and comment when these API calls are more
+	 *        completely implemented and tested!
+	 */
+	WARN("%s in this early version of xlat_mpu library may not produce reliable results!",
+	     __func__);
+
+	/*
+	 * Sequence through all regions and print those in-use (PRENR has an
+	 * enable bit for each MPU region, 1 for in-use or 0 for unused):
+	 */
+	prenr_el2_value = read_prenr_el2();
+	for (region_to_use = 0;  region_to_use < N_MPU_REGIONS;
+	     region_to_use++) {
+		if (((prenr_el2_value >> region_to_use) & 1U) == 0U) {
+			continue;
+		}
+		region_base = read_prbar_el2() & PRBAR_PRLAR_ADDR_MASK;
+		region_size = read_prlar_el2() & PRBAR_PRLAR_ADDR_MASK;
+		printf("Address:  0x%llx, size:  0x%llx ",
+			(long long) region_base,
+			(long long) region_size);
+	}
+}
+
+void xlat_tables_print(__unused xlat_ctx_t *ctx)
+{
+	xlat_tables_print_internal(ctx);
+}
+
+#endif /* LOG_LEVEL >= LOG_LEVEL_VERBOSE */
diff --git a/lib/xlat_tables/aarch64/xlat_tables.c b/lib/xlat_tables/aarch64/xlat_tables.c
index c86412c..dc167e3 100644
--- a/lib/xlat_tables/aarch64/xlat_tables.c
+++ b/lib/xlat_tables/aarch64/xlat_tables.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -147,7 +147,7 @@
  *			exception level
  ******************************************************************************/
 #define DEFINE_ENABLE_MMU_EL(_el, _tcr_extra, _tlbi_fct)		\
-	void enable_mmu_el##_el(unsigned int flags)				\
+	void enable_mmu_el##_el(unsigned int flags)			\
 	{								\
 		uint64_t mair, tcr, ttbr;				\
 		uint32_t sctlr;						\
diff --git a/lib/xlat_tables_v2/aarch32/xlat_tables_arch.c b/lib/xlat_tables_v2/aarch32/xlat_tables_arch.c
index b69c670..a1a44af 100644
--- a/lib/xlat_tables_v2/aarch32/xlat_tables_arch.c
+++ b/lib/xlat_tables_v2/aarch32/xlat_tables_arch.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -39,6 +39,23 @@
 	return PAGE_SIZE_4KB;
 }
 
+/*
+ * Determine the physical address space encoded in the 'attr' parameter.
+ *
+ * The physical address will fall into one of two spaces; secure or
+ * nonsecure.
+ */
+uint32_t xlat_arch_get_pas(uint32_t attr)
+{
+	uint32_t pas = MT_PAS(attr);
+
+	if (pas == MT_NS) {
+		return LOWER_ATTRS(NS);
+	} else { /* MT_SECURE */
+		return 0U;
+	}
+}
+
 #if ENABLE_ASSERTIONS
 unsigned long long xlat_arch_get_max_supported_pa(void)
 {
@@ -203,8 +220,6 @@
 
 		assert(virtual_addr_space_size >=
 			xlat_get_min_virt_addr_space_size());
-		assert(virtual_addr_space_size <=
-			MAX_VIRT_ADDR_SPACE_SIZE);
 		assert(IS_POWER_OF_TWO(virtual_addr_space_size));
 
 		/*
diff --git a/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c b/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c
index 3832b07..719110a 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-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -53,6 +53,33 @@
 	}
 }
 
+/*
+ * Determine the physical address space encoded in the 'attr' parameter.
+ *
+ * The physical address will fall into one of four spaces; secure,
+ * nonsecure, root, or realm if RME is enabled, or one of two spaces;
+ * secure and nonsecure otherwise.
+ */
+uint32_t xlat_arch_get_pas(uint32_t attr)
+{
+	uint32_t pas = MT_PAS(attr);
+
+	switch (pas) {
+#if ENABLE_RME
+	/* TTD.NSE = 1 and TTD.NS = 1 for Realm PAS */
+	case MT_REALM:
+		return LOWER_ATTRS(EL3_S1_NSE | NS);
+	/* TTD.NSE = 1 and TTD.NS = 0 for Root PAS */
+	case MT_ROOT:
+		return LOWER_ATTRS(EL3_S1_NSE);
+#endif
+	case MT_NS:
+		return LOWER_ATTRS(NS);
+	default: /* MT_SECURE */
+		return 0U;
+	}
+}
+
 unsigned long long tcr_physical_addr_size_bits(unsigned long long max_addr)
 {
 	/* Physical address can't exceed 48 bits */
diff --git a/lib/xlat_tables_v2/xlat_tables_core.c b/lib/xlat_tables_v2/xlat_tables_core.c
index bb6d184..de57184 100644
--- a/lib/xlat_tables_v2/xlat_tables_core.c
+++ b/lib/xlat_tables_v2/xlat_tables_core.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -125,11 +125,14 @@
 	 * faults aren't managed.
 	 */
 	desc |= LOWER_ATTRS(ACCESS_FLAG);
+
+	/* Determine the physical address space this region belongs to. */
+	desc |= xlat_arch_get_pas(attr);
+
 	/*
-	 * Deduce other fields of the descriptor based on the MT_NS and MT_RW
-	 * memory region attributes.
+	 * Deduce other fields of the descriptor based on the MT_RW memory
+	 * region attributes.
 	 */
-	desc |= ((attr & MT_NS) != 0U) ? LOWER_ATTRS(NS) : 0U;
 	desc |= ((attr & MT_RW) != 0U) ? LOWER_ATTRS(AP_RW) : LOWER_ATTRS(AP_RO);
 
 	/*
diff --git a/lib/xlat_tables_v2/xlat_tables_private.h b/lib/xlat_tables_v2/xlat_tables_private.h
index 863470c..42c9a43 100644
--- a/lib/xlat_tables_v2/xlat_tables_private.h
+++ b/lib/xlat_tables_v2/xlat_tables_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -40,6 +40,9 @@
 
 extern uint64_t mmu_cfg_params[MMU_CFG_PARAM_MAX];
 
+/* Determine the physical address space encoded in the 'attr' parameter. */
+uint32_t xlat_arch_get_pas(uint32_t attr);
+
 /*
  * Return the execute-never mask that will prevent instruction fetch at the
  * given translation regime.
diff --git a/lib/xlat_tables_v2/xlat_tables_utils.c b/lib/xlat_tables_v2/xlat_tables_utils.c
index 9fae7e9..df17386 100644
--- a/lib/xlat_tables_v2/xlat_tables_utils.c
+++ b/lib/xlat_tables_v2/xlat_tables_utils.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -95,7 +95,23 @@
 			  ? "-USER" : "-PRIV");
 	}
 
+#if ENABLE_RME
+	switch (desc & LOWER_ATTRS(EL3_S1_NSE | NS)) {
+	case 0ULL:
+		printf("-S");
+		break;
+	case LOWER_ATTRS(NS):
+		printf("-NS");
+		break;
+	case LOWER_ATTRS(EL3_S1_NSE):
+		printf("-RT");
+		break;
+	default: /* LOWER_ATTRS(EL3_S1_NSE | NS) */
+		printf("-RL");
+	}
+#else
 	printf(((LOWER_ATTRS(NS) & desc) != 0ULL) ? "-NS" : "-S");
+#endif
 
 #ifdef __aarch64__
 	/* Check Guarded Page bit */
diff --git a/lib/zlib/tf_gunzip.c b/lib/zlib/tf_gunzip.c
index fd56dfc..3ac80bc 100644
--- a/lib/zlib/tf_gunzip.c
+++ b/lib/zlib/tf_gunzip.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,6 +9,7 @@
 #include <string.h>
 
 #include <common/debug.h>
+#include <common/tf_crc32.h>
 #include <lib/utils.h>
 #include <tf_gunzip.h>
 
@@ -100,3 +101,15 @@
 
 	return ret;
 }
+
+/* Wrapper function to calculate CRC
+ * @crc: previous accumulated CRC
+ * @buf: buffer base address
+ * @size: size of the buffer
+ *
+ * Return calculated CRC32 value
+ */
+uint32_t tf_crc32(uint32_t crc, const unsigned char *buf, size_t size)
+{
+	return (uint32_t)crc32((unsigned long)crc, buf, size);
+}
diff --git a/licenses/LICENSE.MIT b/licenses/LICENSE.MIT
new file mode 100644
index 0000000..8aa2645
--- /dev/null
+++ b/licenses/LICENSE.MIT
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) [year] [fullname]
+
+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.
diff --git a/make_helpers/build_macros.mk b/make_helpers/build_macros.mk
index 613fca2..12aaee6 100644
--- a/make_helpers/build_macros.mk
+++ b/make_helpers/build_macros.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -98,41 +98,41 @@
 endef
 
 # IMG_LINKERFILE defines the linker script corresponding to a BL stage
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 define IMG_LINKERFILE
-    ${BUILD_DIR}/bl$(1).ld
+    ${BUILD_DIR}/$(1).ld
 endef
 
 # IMG_MAPFILE defines the output file describing the memory map corresponding
 # to a BL stage
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 define IMG_MAPFILE
-    ${BUILD_DIR}/bl$(1).map
+    ${BUILD_DIR}/$(1).map
 endef
 
 # IMG_ELF defines the elf file corresponding to a BL stage
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 define IMG_ELF
-    ${BUILD_DIR}/bl$(1).elf
+    ${BUILD_DIR}/$(1).elf
 endef
 
 # IMG_DUMP defines the symbols dump file corresponding to a BL stage
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 define IMG_DUMP
-    ${BUILD_DIR}/bl$(1).dump
+    ${BUILD_DIR}/$(1).dump
 endef
 
 # IMG_BIN defines the default image file corresponding to a BL stage
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 define IMG_BIN
-    ${BUILD_PLAT}/bl$(1).bin
+    ${BUILD_PLAT}/$(1).bin
 endef
 
 # IMG_ENC_BIN defines the default encrypted image file corresponding to a
 # BL stage
-#   $(1) = BL stage (2, 30, 31, 32, 33)
+#   $(1) = BL stage
 define IMG_ENC_BIN
-    ${BUILD_PLAT}/bl$(1)_enc.bin
+    ${BUILD_PLAT}/$(1)_enc.bin
 endef
 
 # ENCRYPT_FW invokes enctool to encrypt firmware binary
@@ -214,21 +214,28 @@
     # This is the uppercase form of the first parameter
     $(eval _V := $(call uppercase,$(1)))
 
+    # $(check_$(1)_cmd) variable is executed in the check_$(1) target and also
+    # is put into the ${CHECK_$(3)FIP_CMD} variable which is executed by the
+    # target ${BUILD_PLAT}/${$(3)FIP_NAME}.
+    $(eval check_$(1)_cmd := \
+        $(if $(value $(_V)),,$$$$(error "Platform '${PLAT}' requires $(_V). Please set $(_V) to point to the right file")) \
+        $(if $(wildcard $(value $(_V))),,$$$$(error '$(_V)=$(value $(_V))' was specified, but '$(value $(_V))' does not exist)) \
+    )
+
     $(3)CRT_DEPS += check_$(1)
-    $(3)FIP_DEPS += check_$(1)
+    CHECK_$(3)FIP_CMD += $$(check_$(1)_cmd)
 ifeq ($(4),1)
     $(eval ENC_BIN := ${BUILD_PLAT}/$(1)_enc.bin)
     $(call ENCRYPT_FW,$(value $(_V)),$(ENC_BIN))
     $(call TOOL_ADD_IMG_PAYLOAD,$(1),$(value $(_V)),$(2),$(ENC_BIN),$(3), \
 		$(ENC_BIN))
 else
-    $(call TOOL_ADD_IMG_PAYLOAD,$(1),$(value $(_V)),$(2),,$(3))
+    $(call TOOL_ADD_IMG_PAYLOAD,$(1),$(value $(_V)),$(2),$(if $(wildcard $(value $(_V))),$(value $(_V)),FORCE),$(3))
 endif
 
 .PHONY: check_$(1)
 check_$(1):
-	$$(if $(value $(_V)),,$$(error "Platform '${PLAT}' requires $(_V). Please set $(_V) to point to the right file"))
-	$$(if $(wildcard $(value $(_V))),,$$(error '$(_V)=$(value $(_V))' was specified, but '$(value $(_V))' does not exist))
+	$(check_$(1)_cmd)
 endef
 
 ################################################################################
@@ -287,15 +294,15 @@
 # MAKE_C builds a C source file and generates the dependency file
 #   $(1) = output directory
 #   $(2) = source file (%.c)
-#   $(3) = BL stage (1, 2, 2u, 31, 32)
+#   $(3) = BL stage
 define MAKE_C
 
 $(eval OBJ := $(1)/$(patsubst %.c,%.o,$(notdir $(2))))
 $(eval DEP := $(patsubst %.o,%.d,$(OBJ)))
-$(eval BL_CPPFLAGS := $(BL$(call uppercase,$(3))_CPPFLAGS) -DIMAGE_BL$(call uppercase,$(3)))
-$(eval BL_CFLAGS := $(BL$(call uppercase,$(3))_CFLAGS))
+$(eval BL_CPPFLAGS := $($(call uppercase,$(3))_CPPFLAGS) -DIMAGE_$(call uppercase,$(3)))
+$(eval BL_CFLAGS := $($(call uppercase,$(3))_CFLAGS))
 
-$(OBJ): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | bl$(3)_dirs
+$(OBJ): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | $(3)_dirs
 	$$(ECHO) "  CC      $$<"
 	$$(Q)$$(CC) $$(LTO_CFLAGS) $$(TF_CFLAGS) $$(CFLAGS) $(BL_CPPFLAGS) $(BL_CFLAGS) $(MAKE_DEP) -c $$< -o $$@
 
@@ -307,15 +314,15 @@
 # MAKE_S builds an assembly source file and generates the dependency file
 #   $(1) = output directory
 #   $(2) = assembly file (%.S)
-#   $(3) = BL stage (1, 2, 2u, 31, 32)
+#   $(3) = BL stage
 define MAKE_S
 
 $(eval OBJ := $(1)/$(patsubst %.S,%.o,$(notdir $(2))))
 $(eval DEP := $(patsubst %.o,%.d,$(OBJ)))
-$(eval BL_CPPFLAGS := $(BL$(call uppercase,$(3))_CPPFLAGS) -DIMAGE_BL$(call uppercase,$(3)))
-$(eval BL_ASFLAGS := $(BL$(call uppercase,$(3))_ASFLAGS))
+$(eval BL_CPPFLAGS := $($(call uppercase,$(3))_CPPFLAGS) -DIMAGE_$(call uppercase,$(3)))
+$(eval BL_ASFLAGS := $($(call uppercase,$(3))_ASFLAGS))
 
-$(OBJ): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | bl$(3)_dirs
+$(OBJ): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | $(3)_dirs
 	$$(ECHO) "  AS      $$<"
 	$$(Q)$$(AS) $$(ASFLAGS) $(BL_CPPFLAGS) $(BL_ASFLAGS) $(MAKE_DEP) -c $$< -o $$@
 
@@ -327,13 +334,13 @@
 # MAKE_LD generate the linker script using the C preprocessor
 #   $(1) = output linker script
 #   $(2) = input template
-#   $(3) = BL stage (1, 2, 2u, 31, 32)
+#   $(3) = BL stage
 define MAKE_LD
 
 $(eval DEP := $(1).d)
-$(eval BL_CPPFLAGS := $(BL$(call uppercase,$(3))_CPPFLAGS) -DIMAGE_BL$(call uppercase,$(3)))
+$(eval BL_CPPFLAGS := $($(call uppercase,$(3))_CPPFLAGS) -DIMAGE_$(call uppercase,$(3)))
 
-$(1): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | bl$(3)_dirs
+$(1): $(2) $(filter-out %.d,$(MAKEFILE_LIST)) | $(3)_dirs
 	$$(ECHO) "  PP      $$<"
 	$$(Q)$$(CPP) $$(CPPFLAGS) $(BL_CPPFLAGS) $(TF_CFLAGS_$(ARCH)) -P -x assembler-with-cpp -D__LINKER__ $(MAKE_DEP) -o $$@ $$<
 
@@ -361,7 +368,7 @@
 # MAKE_OBJS builds both C and assembly source files
 #   $(1) = output directory
 #   $(2) = list of source files (both C and assembly)
-#   $(3) = BL stage (1, 2, 2u, 31, 32)
+#   $(3) = BL stage
 define MAKE_OBJS
         $(eval C_OBJS := $(filter %.c,$(2)))
         $(eval REMAIN := $(filter-out %.c,$(2)))
@@ -438,13 +445,13 @@
 
 # MAKE_BL macro defines the targets and options to build each BL image.
 # Arguments:
-#   $(1) = BL stage (1, 2, 2u, 31, 32)
+#   $(1) = BL stage
 #   $(2) = FIP command line option (if empty, image will not be included in the FIP)
 #   $(3) = FIP prefix (optional) (if FWU_, target is fwu_fip instead of fip)
 #   $(4) = BL encryption flag (optional) (0, 1)
 define MAKE_BL
-        $(eval BUILD_DIR  := ${BUILD_PLAT}/bl$(1))
-        $(eval BL_SOURCES := $(BL$(call uppercase,$(1))_SOURCES))
+        $(eval BUILD_DIR  := ${BUILD_PLAT}/$(1))
+        $(eval BL_SOURCES := $($(call uppercase,$(1))_SOURCES))
         $(eval SOURCES    := $(BL_SOURCES) $(BL_COMMON_SOURCES) $(PLAT_BL_COMMON_SOURCES))
         $(eval OBJS       := $(addprefix $(BUILD_DIR)/,$(call SOURCES_TO_OBJS,$(SOURCES))))
         $(eval LINKERFILE := $(call IMG_LINKERFILE,$(1)))
@@ -453,8 +460,8 @@
         $(eval DUMP       := $(call IMG_DUMP,$(1)))
         $(eval BIN        := $(call IMG_BIN,$(1)))
         $(eval ENC_BIN    := $(call IMG_ENC_BIN,$(1)))
-        $(eval BL_LINKERFILE := $(BL$(call uppercase,$(1))_LINKERFILE))
-        $(eval BL_LIBS    := $(BL$(call uppercase,$(1))_LIBS))
+        $(eval BL_LINKERFILE := $($(call uppercase,$(1))_LINKERFILE))
+        $(eval BL_LIBS    := $($(call uppercase,$(1))_LIBS))
         # We use sort only to get a list of unique object directory names.
         # ordering is not relevant but sort removes duplicates.
         $(eval TEMP_OBJ_DIRS := $(sort $(dir ${OBJS} ${LINKERFILE})))
@@ -468,21 +475,21 @@
 
 $(eval $(foreach objd,${OBJ_DIRS},$(call MAKE_PREREQ_DIR,${objd},${BUILD_DIR})))
 
-.PHONY : bl${1}_dirs
+.PHONY : ${1}_dirs
 
 # We use order-only prerequisites to ensure that directories are created,
 # but do not cause re-builds every time a file is written.
-bl${1}_dirs: | ${OBJ_DIRS}
+${1}_dirs: | ${OBJ_DIRS}
 
 $(eval $(call MAKE_OBJS,$(BUILD_DIR),$(SOURCES),$(1)))
 $(eval $(call MAKE_LD,$(LINKERFILE),$(BL_LINKERFILE),$(1)))
-$(eval BL_LDFLAGS := $(BL$(call uppercase,$(1))_LDFLAGS))
+$(eval BL_LDFLAGS := $($(call uppercase,$(1))_LDFLAGS))
 
 ifeq ($(USE_ROMLIB),1)
 $(ELF): romlib.bin
 endif
 
-$(ELF): $(OBJS) $(LINKERFILE) | bl$(1)_dirs libraries $(BL_LIBS)
+$(ELF): $(OBJS) $(LINKERFILE) | $(1)_dirs libraries $(BL_LIBS)
 	$$(ECHO) "  LD      $$@"
 ifdef MAKE_BUILD_STRINGS
 	$(call MAKE_BUILD_STRINGS, $(BUILD_DIR)/build_message.o)
@@ -492,10 +499,10 @@
 		$$(CC) $$(TF_CFLAGS) $$(CFLAGS) -xc -c - -o $(BUILD_DIR)/build_message.o
 endif
 ifneq ($(findstring armlink,$(notdir $(LD))),)
-	$$(Q)$$(LD) -o $$@ $$(TF_LDFLAGS) $$(LDFLAGS) $(BL_LDFLAGS) --entry=bl${1}_entrypoint \
+	$$(Q)$$(LD) -o $$@ $$(TF_LDFLAGS) $$(LDFLAGS) $(BL_LDFLAGS) --entry=${1}_entrypoint \
 		--predefine="-D__LINKER__=$(__LINKER__)" \
 		--predefine="-DTF_CFLAGS=$(TF_CFLAGS)" \
-		--map --list="$(MAPFILE)" --scatter=${PLAT_DIR}/scat/bl${1}.scat \
+		--map --list="$(MAPFILE)" --scatter=${PLAT_DIR}/scat/${1}.scat \
 		$(LDPATHS) $(LIBWRAPPER) $(LDLIBS) $(BL_LIBS) \
 		$(BUILD_DIR)/build_message.o $(OBJS)
 else ifneq ($(findstring gcc,$(notdir $(LD))),)
@@ -524,21 +531,21 @@
 	@echo "Built $$@ successfully"
 	@${ECHO_BLANK_LINE}
 
-.PHONY: bl$(1)
+.PHONY: $(1)
 ifeq ($(DISABLE_BIN_GENERATION),1)
-bl$(1): $(ELF) $(DUMP)
+$(1): $(ELF) $(DUMP)
 else
-bl$(1): $(BIN) $(DUMP)
+$(1): $(BIN) $(DUMP)
 endif
 
-all: bl$(1)
+all: $(1)
 
 ifeq ($(4),1)
 $(call ENCRYPT_FW,$(BIN),$(ENC_BIN))
-$(if $(2),$(call TOOL_ADD_IMG_PAYLOAD,bl$(1),$(BIN),--$(2),$(ENC_BIN),$(3), \
+$(if $(2),$(call TOOL_ADD_IMG_PAYLOAD,$(1),$(BIN),--$(2),$(ENC_BIN),$(3), \
 		$(ENC_BIN)))
 else
-$(if $(2),$(call TOOL_ADD_IMG_PAYLOAD,bl$(1),$(BIN),--$(2),$(BIN),$(3)))
+$(if $(2),$(call TOOL_ADD_IMG_PAYLOAD,$(1),$(BIN),--$(2),$(BIN),$(3)))
 endif
 
 endef
diff --git a/make_helpers/defaults.mk b/make_helpers/defaults.mk
index 578bd59..e88148f 100644
--- a/make_helpers/defaults.mk
+++ b/make_helpers/defaults.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2016-2020, ARM Limited. All rights reserved.
+# Copyright (c) 2016-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -19,6 +19,9 @@
 # The Target build architecture. Supported values are: aarch64, aarch32.
 ARCH				:= aarch64
 
+# ARM Architecture feature modifiers: none by default
+ARM_ARCH_FEATURE		:= none
+
 # ARM Architecture major and minor versions: 8.0 by default.
 ARM_ARCH_MAJOR			:= 8
 ARM_ARCH_MINOR			:= 0
@@ -29,6 +32,9 @@
 # Execute BL2 at EL3
 BL2_AT_EL3			:= 0
 
+# Only use SP packages if SP layout JSON is defined
+BL2_ENABLE_SP_LOAD		:= 0
+
 # BL2 image is stored in XIP memory, for now, this option is only supported
 # when BL2_AT_EL3 is 1.
 BL2_IN_XIP_MEM			:= 0
@@ -79,6 +85,10 @@
 # Disable the generation of the binary image (ELF only).
 DISABLE_BIN_GENERATION		:= 0
 
+# Disable MTPMU if FEAT_MTPMU is supported. Default is 0 to keep backwards
+# compatibility.
+DISABLE_MTPMU			:= 0
+
 # Enable capability to disable authentication dynamically. Only meant for
 # development platforms.
 DYN_DISABLE_AUTH		:= 0
@@ -86,6 +96,12 @@
 # Build option to enable MPAM for lower ELs
 ENABLE_MPAM_FOR_LOWER_ELS	:= 0
 
+# Enable the Maximum Power Mitigation Mechanism on supporting cores.
+ENABLE_MPMM			:= 0
+
+# Enable MPMM configuration via FCONF.
+ENABLE_MPMM_FCONF		:= 0
+
 # Flag to Enable Position Independant support (PIE)
 ENABLE_PIE			:= 0
 
@@ -95,6 +111,9 @@
 # Flag to enable PSCI STATs functionality
 ENABLE_PSCI_STAT		:= 0
 
+# Flag to enable Realm Management Extension (FEAT_RME)
+ENABLE_RME			:= 0
+
 # Flag to enable runtime instrumentation using PMF
 ENABLE_RUNTIME_INSTRUMENTATION	:= 0
 
@@ -114,6 +133,9 @@
 # Use BRANCH_PROTECTION to enable PAUTH.
 ENABLE_PAUTH			:= 0
 
+# Flag to enable access to the HCRX_EL2 register by setting SCR_EL3.HXEn.
+ENABLE_FEAT_HCX			:= 0
+
 # By default BL31 encryption disabled
 ENCRYPT_BL31			:= 0
 
@@ -200,7 +222,13 @@
 SAVE_KEYS			:= 0
 
 # Software Delegated Exception support
-SDEI_SUPPORT            	:= 0
+SDEI_SUPPORT			:= 0
+
+# True Random Number firmware Interface
+TRNG_SUPPORT			:= 0
+
+# SMCCC PCI support
+SMC_PCI_SUPPORT			:= 0
 
 # Whether code and read-only data should be put on separate memory pages. The
 # platform Makefile is free to override this value.
@@ -275,23 +303,31 @@
 
 # SPE is only supported on AArch64 so disable it on AArch32.
 ifeq (${ARCH},aarch32)
-    override ENABLE_SPE_FOR_LOWER_ELS := 0
+	override ENABLE_SPE_FOR_LOWER_ELS := 0
 endif
 
 # Include Memory Tagging Extension registers in cpu context. This must be set
 # to 1 if the platform wants to use this feature in the Secure world and MTE is
 # enabled at ELX.
-CTX_INCLUDE_MTE_REGS := 0
+CTX_INCLUDE_MTE_REGS		:= 0
 
 ENABLE_AMU			:= 0
+ENABLE_AMU_AUXILIARY_COUNTERS	:= 0
+ENABLE_AMU_FCONF		:= 0
+AMU_RESTRICT_COUNTERS		:= 0
 
-# By default, enable Scalable Vector Extension if implemented for Non-secure
-# lower ELs
-# Note SVE is only supported on AArch64 - therefore do not enable in AArch32
-ifneq (${ARCH},aarch32)
-    ENABLE_SVE_FOR_NS		:= 1
-else
-    override ENABLE_SVE_FOR_NS	:= 0
+# Enable SVE for non-secure world by default
+ENABLE_SVE_FOR_NS		:= 1
+ENABLE_SVE_FOR_SWD		:= 0
+
+# SME defaults to disabled
+ENABLE_SME_FOR_NS		:= 0
+ENABLE_SME_FOR_SWD		:= 0
+
+# If SME is enabled then force SVE off
+ifeq (${ENABLE_SME_FOR_NS},1)
+	override ENABLE_SVE_FOR_NS	:= 0
+	override ENABLE_SVE_FOR_SWD	:= 0
 endif
 
 SANITIZE_UB := off
@@ -315,7 +351,7 @@
 SUPPORT_STACK_MEMTAG		:= no
 
 # Select workaround for AT speculative behaviour.
-ERRATA_SPECULATIVE_AT           := 0
+ERRATA_SPECULATIVE_AT		:= 0
 
 # Trap RAS error record access from lower EL
 RAS_TRAP_LOWER_EL_ERR_ACCESS	:= 0
@@ -328,3 +364,35 @@
 
 # Build option to use the SP804 timer instead of the generic one
 USE_SP804_TIMER			:= 0
+
+# Build option to define number of firmware banks, used in firmware update
+# metadata structure.
+NR_OF_FW_BANKS			:= 2
+
+# Build option to define number of images in firmware bank, used in firmware
+# update metadata structure.
+NR_OF_IMAGES_IN_FW_BANK		:= 1
+
+# Disable Firmware update support by default
+PSA_FWU_SUPPORT			:= 0
+
+# By default, disable access of trace buffer control registers from NS
+# lower ELs  i.e. NS-EL2, or NS-EL1 if NS-EL2 implemented but unused
+# if FEAT_TRBE is implemented.
+# Note FEAT_TRBE is only supported on AArch64 - therefore do not enable in
+# AArch32.
+ifneq (${ARCH},aarch32)
+	ENABLE_TRBE_FOR_NS		:= 0
+else
+	override ENABLE_TRBE_FOR_NS	:= 0
+endif
+
+# By default, disable access of trace system registers from NS lower
+# ELs  i.e. NS-EL2, or NS-EL1 if NS-EL2 implemented but unused if
+# system register trace is implemented.
+ENABLE_SYS_REG_TRACE_FOR_NS	:= 0
+
+# By default, disable trace filter control registers access to NS
+# lower ELs, i.e. NS-EL2, or NS-EL1 if NS-EL2 implemented but unused
+# if FEAT_TRF is implemented.
+ENABLE_TRF_FOR_NS		:= 0
diff --git a/make_helpers/tbbr/tbbr_tools.mk b/make_helpers/tbbr/tbbr_tools.mk
index 853ad11..0a280b4 100644
--- a/make_helpers/tbbr/tbbr_tools.mk
+++ b/make_helpers/tbbr/tbbr_tools.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -11,6 +11,7 @@
 # Expected environment:
 #
 #   BUILD_PLAT: output directory
+#   NEED_BL2: indicates whether BL2 is needed by the platform
 #   NEED_BL32: indicates whether BL32 is needed by the platform
 #   BL2: image filename (optional). Default is IMG_BIN(2) (see macro IMG_BIN)
 #   SCP_BL2: image filename (optional). Default is IMG_BIN(30)
@@ -33,7 +34,7 @@
 #
 
 # Certificate generation tool default parameters
-TRUSTED_KEY_CERT	:=	${BUILD_PLAT}/trusted_key.crt
+TRUSTED_KEY_CERT	?=	${BUILD_PLAT}/trusted_key.crt
 FWU_CERT		:=	${BUILD_PLAT}/fwu_cert.crt
 
 # Default non-volatile counter values (overridable by the platform)
@@ -67,9 +68,11 @@
 
 
 # Add the BL2 CoT (image cert)
+ifeq (${NEED_BL2},yes)
 ifeq (${BL2_AT_EL3}, 0)
 $(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/tb_fw.crt,--tb-fw-cert))
 endif
+endif
 
 # Add the SCP_BL2 CoT (key cert + img cert)
 ifneq (${SCP_BL2},)
diff --git a/package-lock.json b/package-lock.json
new file mode 100644
index 0000000..61caf57
--- /dev/null
+++ b/package-lock.json
@@ -0,0 +1,2070 @@
+{
+  "requires": true,
+  "lockfileVersion": 1,
+  "dependencies": {
+    "@babel/code-frame": {
+      "version": "7.12.13",
+      "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.12.13.tgz",
+      "integrity": "sha512-HV1Cm0Q3ZrpCR93tkWOYiuYIgLxZXZFVG2VgK+MBWjUqZTundupbfx2aXarXuw5Ko5aMcjtJgbSs4vUGBS5v6g==",
+      "dev": true,
+      "requires": {
+        "@babel/highlight": "^7.12.13"
+      }
+    },
+    "@babel/helper-validator-identifier": {
+      "version": "7.14.0",
+      "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.14.0.tgz",
+      "integrity": "sha512-V3ts7zMSu5lfiwWDVWzRDGIN+lnCEUdaXgtVHJgLb1rGaA6jMrtB9EmE7L18foXJIE8Un/A/h6NJfGQp/e1J4A==",
+      "dev": true
+    },
+    "@babel/highlight": {
+      "version": "7.14.0",
+      "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.14.0.tgz",
+      "integrity": "sha512-YSCOwxvTYEIMSGaBQb5kDDsCopDdiUGsqpatp3fOlI4+2HQSkTmEVWnVuySdAC5EWCqSWWTv0ib63RjR7dTBdg==",
+      "dev": true,
+      "requires": {
+        "@babel/helper-validator-identifier": "^7.14.0",
+        "chalk": "^2.0.0",
+        "js-tokens": "^4.0.0"
+      },
+      "dependencies": {
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "color-convert": {
+          "version": "1.9.3",
+          "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz",
+          "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==",
+          "dev": true,
+          "requires": {
+            "color-name": "1.1.3"
+          }
+        },
+        "color-name": {
+          "version": "1.1.3",
+          "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz",
+          "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=",
+          "dev": true
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
+      }
+    },
+    "@babel/runtime": {
+      "version": "7.14.0",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.14.0.tgz",
+      "integrity": "sha512-JELkvo/DlpNdJ7dlyw/eY7E0suy5i5GQH+Vlxaq1nsNJ+H7f4Vtv3jMeCEgRhZZQFXTjldYfQgv2qmM6M1v5wA==",
+      "dev": true,
+      "requires": {
+        "regenerator-runtime": "^0.13.4"
+      }
+    },
+    "@commitlint/cli": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/cli/-/cli-11.0.0.tgz",
+      "integrity": "sha512-YWZWg1DuqqO5Zjh7vUOeSX76vm0FFyz4y0cpGMFhrhvUi5unc4IVfCXZ6337R9zxuBtmveiRuuhQqnRRer+13g==",
+      "dev": true,
+      "requires": {
+        "@babel/runtime": "^7.11.2",
+        "@commitlint/format": "^11.0.0",
+        "@commitlint/lint": "^11.0.0",
+        "@commitlint/load": "^11.0.0",
+        "@commitlint/read": "^11.0.0",
+        "chalk": "4.1.0",
+        "core-js": "^3.6.1",
+        "get-stdin": "8.0.0",
+        "lodash": "^4.17.19",
+        "resolve-from": "5.0.0",
+        "resolve-global": "1.0.0",
+        "yargs": "^15.1.0"
+      }
+    },
+    "@commitlint/config-conventional": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/config-conventional/-/config-conventional-11.0.0.tgz",
+      "integrity": "sha512-SNDRsb5gLuDd2PL83yCOQX6pE7gevC79UPFx+GLbLfw6jGnnbO9/tlL76MLD8MOViqGbo7ZicjChO9Gn+7tHhA==",
+      "dev": true,
+      "requires": {
+        "conventional-changelog-conventionalcommits": "^4.3.1"
+      }
+    },
+    "@commitlint/ensure": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/ensure/-/ensure-11.0.0.tgz",
+      "integrity": "sha512-/T4tjseSwlirKZdnx4AuICMNNlFvRyPQimbZIOYujp9DSO6XRtOy9NrmvWujwHsq9F5Wb80QWi4WMW6HMaENug==",
+      "dev": true,
+      "requires": {
+        "@commitlint/types": "^11.0.0",
+        "lodash": "^4.17.19"
+      }
+    },
+    "@commitlint/execute-rule": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/execute-rule/-/execute-rule-11.0.0.tgz",
+      "integrity": "sha512-g01p1g4BmYlZ2+tdotCavrMunnPFPhTzG1ZiLKTCYrooHRbmvqo42ZZn4QMStUEIcn+jfLb6BRZX3JzIwA1ezQ==",
+      "dev": true
+    },
+    "@commitlint/format": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/format/-/format-11.0.0.tgz",
+      "integrity": "sha512-bpBLWmG0wfZH/svzqD1hsGTpm79TKJWcf6EXZllh2J/LSSYKxGlv967lpw0hNojme0sZd4a/97R3qA2QHWWSLg==",
+      "dev": true,
+      "requires": {
+        "@commitlint/types": "^11.0.0",
+        "chalk": "^4.0.0"
+      }
+    },
+    "@commitlint/is-ignored": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/is-ignored/-/is-ignored-11.0.0.tgz",
+      "integrity": "sha512-VLHOUBN+sOlkYC4tGuzE41yNPO2w09sQnOpfS+pSPnBFkNUUHawEuA44PLHtDvQgVuYrMAmSWFQpWabMoP5/Xg==",
+      "dev": true,
+      "requires": {
+        "@commitlint/types": "^11.0.0",
+        "semver": "7.3.2"
+      }
+    },
+    "@commitlint/lint": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/lint/-/lint-11.0.0.tgz",
+      "integrity": "sha512-Q8IIqGIHfwKr8ecVZyYh6NtXFmKw4YSEWEr2GJTB/fTZXgaOGtGFZDWOesCZllQ63f1s/oWJYtVv5RAEuwN8BQ==",
+      "dev": true,
+      "requires": {
+        "@commitlint/is-ignored": "^11.0.0",
+        "@commitlint/parse": "^11.0.0",
+        "@commitlint/rules": "^11.0.0",
+        "@commitlint/types": "^11.0.0"
+      }
+    },
+    "@commitlint/load": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/load/-/load-11.0.0.tgz",
+      "integrity": "sha512-t5ZBrtgvgCwPfxmG811FCp39/o3SJ7L+SNsxFL92OR4WQxPcu6c8taD0CG2lzOHGuRyuMxZ7ps3EbngT2WpiCg==",
+      "dev": true,
+      "requires": {
+        "@commitlint/execute-rule": "^11.0.0",
+        "@commitlint/resolve-extends": "^11.0.0",
+        "@commitlint/types": "^11.0.0",
+        "chalk": "4.1.0",
+        "cosmiconfig": "^7.0.0",
+        "lodash": "^4.17.19",
+        "resolve-from": "^5.0.0"
+      }
+    },
+    "@commitlint/message": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/message/-/message-11.0.0.tgz",
+      "integrity": "sha512-01ObK/18JL7PEIE3dBRtoMmU6S3ecPYDTQWWhcO+ErA3Ai0KDYqV5VWWEijdcVafNpdeUNrEMigRkxXHQLbyJA==",
+      "dev": true
+    },
+    "@commitlint/parse": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/parse/-/parse-11.0.0.tgz",
+      "integrity": "sha512-DekKQAIYWAXIcyAZ6/PDBJylWJ1BROTfDIzr9PMVxZRxBPc1gW2TG8fLgjZfBP5mc0cuthPkVi91KQQKGri/7A==",
+      "dev": true,
+      "requires": {
+        "conventional-changelog-angular": "^5.0.0",
+        "conventional-commits-parser": "^3.0.0"
+      }
+    },
+    "@commitlint/read": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/read/-/read-11.0.0.tgz",
+      "integrity": "sha512-37V0V91GSv0aDzMzJioKpCoZw6l0shk7+tRG8RkW1GfZzUIytdg3XqJmM+IaIYpaop0m6BbZtfq+idzUwJnw7g==",
+      "dev": true,
+      "requires": {
+        "@commitlint/top-level": "^11.0.0",
+        "fs-extra": "^9.0.0",
+        "git-raw-commits": "^2.0.0"
+      }
+    },
+    "@commitlint/resolve-extends": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/resolve-extends/-/resolve-extends-11.0.0.tgz",
+      "integrity": "sha512-WinU6Uv6L7HDGLqn/To13KM1CWvZ09VHZqryqxXa1OY+EvJkfU734CwnOEeNlSCK7FVLrB4kmodLJtL1dkEpXw==",
+      "dev": true,
+      "requires": {
+        "import-fresh": "^3.0.0",
+        "lodash": "^4.17.19",
+        "resolve-from": "^5.0.0",
+        "resolve-global": "^1.0.0"
+      }
+    },
+    "@commitlint/rules": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/rules/-/rules-11.0.0.tgz",
+      "integrity": "sha512-2hD9y9Ep5ZfoNxDDPkQadd2jJeocrwC4vJ98I0g8pNYn/W8hS9+/FuNpolREHN8PhmexXbkjrwyQrWbuC0DVaA==",
+      "dev": true,
+      "requires": {
+        "@commitlint/ensure": "^11.0.0",
+        "@commitlint/message": "^11.0.0",
+        "@commitlint/to-lines": "^11.0.0",
+        "@commitlint/types": "^11.0.0"
+      }
+    },
+    "@commitlint/to-lines": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/to-lines/-/to-lines-11.0.0.tgz",
+      "integrity": "sha512-TIDTB0Y23jlCNubDROUVokbJk6860idYB5cZkLWcRS9tlb6YSoeLn1NLafPlrhhkkkZzTYnlKYzCVrBNVes1iw==",
+      "dev": true
+    },
+    "@commitlint/top-level": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/top-level/-/top-level-11.0.0.tgz",
+      "integrity": "sha512-O0nFU8o+Ws+py5pfMQIuyxOtfR/kwtr5ybqTvR+C2lUPer2x6lnQU+OnfD7hPM+A+COIUZWx10mYQvkR3MmtAA==",
+      "dev": true,
+      "requires": {
+        "find-up": "^5.0.0"
+      },
+      "dependencies": {
+        "find-up": {
+          "version": "5.0.0",
+          "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz",
+          "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==",
+          "dev": true,
+          "requires": {
+            "locate-path": "^6.0.0",
+            "path-exists": "^4.0.0"
+          }
+        },
+        "locate-path": {
+          "version": "6.0.0",
+          "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz",
+          "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==",
+          "dev": true,
+          "requires": {
+            "p-locate": "^5.0.0"
+          }
+        },
+        "p-limit": {
+          "version": "3.1.0",
+          "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz",
+          "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==",
+          "dev": true,
+          "requires": {
+            "yocto-queue": "^0.1.0"
+          }
+        },
+        "p-locate": {
+          "version": "5.0.0",
+          "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz",
+          "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==",
+          "dev": true,
+          "requires": {
+            "p-limit": "^3.0.2"
+          }
+        }
+      }
+    },
+    "@commitlint/types": {
+      "version": "11.0.0",
+      "resolved": "https://registry.npmjs.org/@commitlint/types/-/types-11.0.0.tgz",
+      "integrity": "sha512-VoNqai1vR5anRF5Tuh/+SWDFk7xi7oMwHrHrbm1BprYXjB2RJsWLhUrStMssDxEl5lW/z3EUdg8RvH/IUBccSQ==",
+      "dev": true
+    },
+    "@types/minimist": {
+      "version": "1.2.1",
+      "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.1.tgz",
+      "integrity": "sha512-fZQQafSREFyuZcdWFAExYjBiCL7AUCdgsk80iO0q4yihYYdcIiH28CcuPTGFgLOCC8RlW49GSQxdHwZP+I7CNg==",
+      "dev": true
+    },
+    "@types/normalize-package-data": {
+      "version": "2.4.0",
+      "resolved": "https://registry.npmjs.org/@types/normalize-package-data/-/normalize-package-data-2.4.0.tgz",
+      "integrity": "sha512-f5j5b/Gf71L+dbqxIpQ4Z2WlmI/mPJ0fOkGGmFgtb6sAu97EPczzbS3/tJKxmcYDj55OX6ssqwDAWOHIYDRDGA==",
+      "dev": true
+    },
+    "@types/parse-json": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.0.tgz",
+      "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==",
+      "dev": true
+    },
+    "JSONStream": {
+      "version": "1.3.5",
+      "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.5.tgz",
+      "integrity": "sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==",
+      "dev": true,
+      "requires": {
+        "jsonparse": "^1.2.0",
+        "through": ">=2.2.7 <3"
+      }
+    },
+    "ansi-escapes": {
+      "version": "3.2.0",
+      "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz",
+      "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==",
+      "dev": true
+    },
+    "ansi-regex": {
+      "version": "5.0.0",
+      "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.0.tgz",
+      "integrity": "sha512-bY6fj56OUQ0hU1KjFNDQuJFezqKdrAyFdIevADiqrWHwSlbmBNMHp5ak2f40Pm8JTFyM2mqxkG6ngkHO11f/lg==",
+      "dev": true
+    },
+    "ansi-styles": {
+      "version": "4.3.0",
+      "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
+      "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
+      "dev": true,
+      "requires": {
+        "color-convert": "^2.0.1"
+      }
+    },
+    "array-ify": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/array-ify/-/array-ify-1.0.0.tgz",
+      "integrity": "sha1-nlKHYrSpBmrRY6aWKjZEGOlibs4=",
+      "dev": true
+    },
+    "arrify": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz",
+      "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=",
+      "dev": true
+    },
+    "at-least-node": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz",
+      "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==",
+      "dev": true
+    },
+    "balanced-match": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz",
+      "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==",
+      "dev": true
+    },
+    "brace-expansion": {
+      "version": "1.1.11",
+      "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
+      "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
+      "dev": true,
+      "requires": {
+        "balanced-match": "^1.0.0",
+        "concat-map": "0.0.1"
+      }
+    },
+    "braces": {
+      "version": "3.0.2",
+      "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz",
+      "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==",
+      "dev": true,
+      "requires": {
+        "fill-range": "^7.0.1"
+      }
+    },
+    "cachedir": {
+      "version": "2.2.0",
+      "resolved": "https://registry.npmjs.org/cachedir/-/cachedir-2.2.0.tgz",
+      "integrity": "sha512-VvxA0xhNqIIfg0V9AmJkDg91DaJwryutH5rVEZAhcNi4iJFj9f+QxmAjgK1LT9I8OgToX27fypX6/MeCXVbBjQ==",
+      "dev": true
+    },
+    "callsites": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz",
+      "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==",
+      "dev": true
+    },
+    "camelcase": {
+      "version": "5.3.1",
+      "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz",
+      "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==",
+      "dev": true
+    },
+    "camelcase-keys": {
+      "version": "6.2.2",
+      "resolved": "https://registry.npmjs.org/camelcase-keys/-/camelcase-keys-6.2.2.tgz",
+      "integrity": "sha512-YrwaA0vEKazPBkn0ipTiMpSajYDSe+KjQfrjhcBMxJt/znbvlHd8Pw/Vamaz5EB4Wfhs3SUR3Z9mwRu/P3s3Yg==",
+      "dev": true,
+      "requires": {
+        "camelcase": "^5.3.1",
+        "map-obj": "^4.0.0",
+        "quick-lru": "^4.0.1"
+      }
+    },
+    "chalk": {
+      "version": "4.1.0",
+      "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz",
+      "integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==",
+      "dev": true,
+      "requires": {
+        "ansi-styles": "^4.1.0",
+        "supports-color": "^7.1.0"
+      }
+    },
+    "chardet": {
+      "version": "0.7.0",
+      "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz",
+      "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==",
+      "dev": true
+    },
+    "cli-cursor": {
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz",
+      "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=",
+      "dev": true,
+      "requires": {
+        "restore-cursor": "^2.0.0"
+      }
+    },
+    "cli-width": {
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.1.tgz",
+      "integrity": "sha512-GRMWDxpOB6Dgk2E5Uo+3eEBvtOOlimMmpbFiKuLFnQzYDavtLFY3K5ona41jgN/WdRZtG7utuVSVTL4HbZHGkw==",
+      "dev": true
+    },
+    "cliui": {
+      "version": "6.0.0",
+      "resolved": "https://registry.npmjs.org/cliui/-/cliui-6.0.0.tgz",
+      "integrity": "sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==",
+      "dev": true,
+      "requires": {
+        "string-width": "^4.2.0",
+        "strip-ansi": "^6.0.0",
+        "wrap-ansi": "^6.2.0"
+      }
+    },
+    "color-convert": {
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz",
+      "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==",
+      "dev": true,
+      "requires": {
+        "color-name": "~1.1.4"
+      }
+    },
+    "color-name": {
+      "version": "1.1.4",
+      "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz",
+      "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
+      "dev": true
+    },
+    "commitizen": {
+      "version": "4.2.4",
+      "resolved": "https://registry.npmjs.org/commitizen/-/commitizen-4.2.4.tgz",
+      "integrity": "sha512-LlZChbDzg3Ir3O2S7jSo/cgWp5/QwylQVr59K4xayVq8S4/RdKzSyJkghAiZZHfhh5t4pxunUoyeg0ml1q/7aw==",
+      "dev": true,
+      "requires": {
+        "cachedir": "2.2.0",
+        "cz-conventional-changelog": "3.2.0",
+        "dedent": "0.7.0",
+        "detect-indent": "6.0.0",
+        "find-node-modules": "^2.1.2",
+        "find-root": "1.1.0",
+        "fs-extra": "8.1.0",
+        "glob": "7.1.4",
+        "inquirer": "6.5.2",
+        "is-utf8": "^0.2.1",
+        "lodash": "^4.17.20",
+        "minimist": "1.2.5",
+        "strip-bom": "4.0.0",
+        "strip-json-comments": "3.0.1"
+      },
+      "dependencies": {
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "color-convert": {
+          "version": "1.9.3",
+          "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz",
+          "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==",
+          "dev": true,
+          "requires": {
+            "color-name": "1.1.3"
+          }
+        },
+        "color-name": {
+          "version": "1.1.3",
+          "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz",
+          "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=",
+          "dev": true
+        },
+        "cz-conventional-changelog": {
+          "version": "3.2.0",
+          "resolved": "https://registry.npmjs.org/cz-conventional-changelog/-/cz-conventional-changelog-3.2.0.tgz",
+          "integrity": "sha512-yAYxeGpVi27hqIilG1nh4A9Bnx4J3Ov+eXy4koL3drrR+IO9GaWPsKjik20ht608Asqi8TQPf0mczhEeyAtMzg==",
+          "dev": true,
+          "requires": {
+            "@commitlint/load": ">6.1.1",
+            "chalk": "^2.4.1",
+            "commitizen": "^4.0.3",
+            "conventional-commit-types": "^3.0.0",
+            "lodash.map": "^4.5.1",
+            "longest": "^2.0.1",
+            "word-wrap": "^1.0.3"
+          }
+        },
+        "fs-extra": {
+          "version": "8.1.0",
+          "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-8.1.0.tgz",
+          "integrity": "sha512-yhlQgA6mnOJUKOsRUFsgJdQCvkKhcz8tlZG5HBQfReYZy46OwLcY+Zia0mtdHsOo9y/hP+CxMN0TU9QxoOtG4g==",
+          "dev": true,
+          "requires": {
+            "graceful-fs": "^4.2.0",
+            "jsonfile": "^4.0.0",
+            "universalify": "^0.1.0"
+          }
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "jsonfile": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz",
+          "integrity": "sha1-h3Gq4HmbZAdrdmQPygWPnBDjPss=",
+          "dev": true,
+          "requires": {
+            "graceful-fs": "^4.1.6"
+          }
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        },
+        "universalify": {
+          "version": "0.1.2",
+          "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.2.tgz",
+          "integrity": "sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==",
+          "dev": true
+        }
+      }
+    },
+    "compare-func": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/compare-func/-/compare-func-2.0.0.tgz",
+      "integrity": "sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==",
+      "dev": true,
+      "requires": {
+        "array-ify": "^1.0.0",
+        "dot-prop": "^5.1.0"
+      }
+    },
+    "concat-map": {
+      "version": "0.0.1",
+      "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
+      "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=",
+      "dev": true
+    },
+    "conventional-changelog-angular": {
+      "version": "5.0.12",
+      "resolved": "https://registry.npmjs.org/conventional-changelog-angular/-/conventional-changelog-angular-5.0.12.tgz",
+      "integrity": "sha512-5GLsbnkR/7A89RyHLvvoExbiGbd9xKdKqDTrArnPbOqBqG/2wIosu0fHwpeIRI8Tl94MhVNBXcLJZl92ZQ5USw==",
+      "dev": true,
+      "requires": {
+        "compare-func": "^2.0.0",
+        "q": "^1.5.1"
+      }
+    },
+    "conventional-changelog-conventionalcommits": {
+      "version": "4.6.0",
+      "resolved": "https://registry.npmjs.org/conventional-changelog-conventionalcommits/-/conventional-changelog-conventionalcommits-4.6.0.tgz",
+      "integrity": "sha512-sj9tj3z5cnHaSJCYObA9nISf7eq/YjscLPoq6nmew4SiOjxqL2KRpK20fjnjVbpNDjJ2HR3MoVcWKXwbVvzS0A==",
+      "dev": true,
+      "requires": {
+        "compare-func": "^2.0.0",
+        "lodash": "^4.17.15",
+        "q": "^1.5.1"
+      }
+    },
+    "conventional-commit-types": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/conventional-commit-types/-/conventional-commit-types-3.0.0.tgz",
+      "integrity": "sha512-SmmCYnOniSsAa9GqWOeLqc179lfr5TRu5b4QFDkbsrJ5TZjPJx85wtOr3zn+1dbeNiXDKGPbZ72IKbPhLXh/Lg==",
+      "dev": true
+    },
+    "conventional-commits-parser": {
+      "version": "3.2.1",
+      "resolved": "https://registry.npmjs.org/conventional-commits-parser/-/conventional-commits-parser-3.2.1.tgz",
+      "integrity": "sha512-OG9kQtmMZBJD/32NEw5IhN5+HnBqVjy03eC+I71I0oQRFA5rOgA4OtPOYG7mz1GkCfCNxn3gKIX8EiHJYuf1cA==",
+      "dev": true,
+      "requires": {
+        "JSONStream": "^1.0.4",
+        "is-text-path": "^1.0.1",
+        "lodash": "^4.17.15",
+        "meow": "^8.0.0",
+        "split2": "^3.0.0",
+        "through2": "^4.0.0",
+        "trim-off-newlines": "^1.0.0"
+      }
+    },
+    "core-js": {
+      "version": "3.12.1",
+      "resolved": "https://registry.npmjs.org/core-js/-/core-js-3.12.1.tgz",
+      "integrity": "sha512-Ne9DKPHTObRuB09Dru5AjwKjY4cJHVGu+y5f7coGn1E9Grkc3p2iBwE9AI/nJzsE29mQF7oq+mhYYRqOMFN1Bw==",
+      "dev": true
+    },
+    "cosmiconfig": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.0.tgz",
+      "integrity": "sha512-pondGvTuVYDk++upghXJabWzL6Kxu6f26ljFw64Swq9v6sQPUL3EUlVDV56diOjpCayKihL6hVe8exIACU4XcA==",
+      "dev": true,
+      "requires": {
+        "@types/parse-json": "^4.0.0",
+        "import-fresh": "^3.2.1",
+        "parse-json": "^5.0.0",
+        "path-type": "^4.0.0",
+        "yaml": "^1.10.0"
+      }
+    },
+    "cz-conventional-changelog": {
+      "version": "3.3.0",
+      "resolved": "https://registry.npmjs.org/cz-conventional-changelog/-/cz-conventional-changelog-3.3.0.tgz",
+      "integrity": "sha512-U466fIzU5U22eES5lTNiNbZ+d8dfcHcssH4o7QsdWaCcRs/feIPCxKYSWkYBNs5mny7MvEfwpTLWjvbm94hecw==",
+      "dev": true,
+      "requires": {
+        "@commitlint/load": ">6.1.1",
+        "chalk": "^2.4.1",
+        "commitizen": "^4.0.3",
+        "conventional-commit-types": "^3.0.0",
+        "lodash.map": "^4.5.1",
+        "longest": "^2.0.1",
+        "word-wrap": "^1.0.3"
+      },
+      "dependencies": {
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "color-convert": {
+          "version": "1.9.3",
+          "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz",
+          "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==",
+          "dev": true,
+          "requires": {
+            "color-name": "1.1.3"
+          }
+        },
+        "color-name": {
+          "version": "1.1.3",
+          "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz",
+          "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=",
+          "dev": true
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
+      }
+    },
+    "dargs": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/dargs/-/dargs-7.0.0.tgz",
+      "integrity": "sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==",
+      "dev": true
+    },
+    "decamelize": {
+      "version": "1.2.0",
+      "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz",
+      "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=",
+      "dev": true
+    },
+    "decamelize-keys": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz",
+      "integrity": "sha1-0XGoeTMlKAfrPLYdwcFEXQeN8tk=",
+      "dev": true,
+      "requires": {
+        "decamelize": "^1.1.0",
+        "map-obj": "^1.0.0"
+      },
+      "dependencies": {
+        "map-obj": {
+          "version": "1.0.1",
+          "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz",
+          "integrity": "sha1-2TPOuSBdgr3PSIb2dCvcK03qFG0=",
+          "dev": true
+        }
+      }
+    },
+    "dedent": {
+      "version": "0.7.0",
+      "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz",
+      "integrity": "sha1-JJXduvbrh0q7Dhvp3yLS5aVEMmw=",
+      "dev": true
+    },
+    "detect-file": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/detect-file/-/detect-file-1.0.0.tgz",
+      "integrity": "sha1-8NZtA2cqglyxtzvbP+YjEMjlUrc=",
+      "dev": true
+    },
+    "detect-indent": {
+      "version": "6.0.0",
+      "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-6.0.0.tgz",
+      "integrity": "sha512-oSyFlqaTHCItVRGK5RmrmjB+CmaMOW7IaNA/kdxqhoa6d17j/5ce9O9eWXmV/KEdRwqpQA+Vqe8a8Bsybu4YnA==",
+      "dev": true
+    },
+    "dot-prop": {
+      "version": "5.3.0",
+      "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz",
+      "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==",
+      "dev": true,
+      "requires": {
+        "is-obj": "^2.0.0"
+      }
+    },
+    "emoji-regex": {
+      "version": "8.0.0",
+      "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz",
+      "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==",
+      "dev": true
+    },
+    "error-ex": {
+      "version": "1.3.2",
+      "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz",
+      "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==",
+      "dev": true,
+      "requires": {
+        "is-arrayish": "^0.2.1"
+      }
+    },
+    "escape-string-regexp": {
+      "version": "1.0.5",
+      "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz",
+      "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=",
+      "dev": true
+    },
+    "expand-tilde": {
+      "version": "2.0.2",
+      "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz",
+      "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=",
+      "dev": true,
+      "requires": {
+        "homedir-polyfill": "^1.0.1"
+      }
+    },
+    "external-editor": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.1.0.tgz",
+      "integrity": "sha512-hMQ4CX1p1izmuLYyZqLMO/qGNw10wSv9QDCPfzXfyFrOaCSSoRfqE1Kf1s5an66J5JZC62NewG+mK49jOCtQew==",
+      "dev": true,
+      "requires": {
+        "chardet": "^0.7.0",
+        "iconv-lite": "^0.4.24",
+        "tmp": "^0.0.33"
+      }
+    },
+    "figures": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz",
+      "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=",
+      "dev": true,
+      "requires": {
+        "escape-string-regexp": "^1.0.5"
+      }
+    },
+    "fill-range": {
+      "version": "7.0.1",
+      "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz",
+      "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==",
+      "dev": true,
+      "requires": {
+        "to-regex-range": "^5.0.1"
+      }
+    },
+    "find-node-modules": {
+      "version": "2.1.2",
+      "resolved": "https://registry.npmjs.org/find-node-modules/-/find-node-modules-2.1.2.tgz",
+      "integrity": "sha512-x+3P4mbtRPlSiVE1Qco0Z4YLU8WFiFcuWTf3m75OV9Uzcfs2Bg+O9N+r/K0AnmINBW06KpfqKwYJbFlFq4qNug==",
+      "dev": true,
+      "requires": {
+        "findup-sync": "^4.0.0",
+        "merge": "^2.1.0"
+      }
+    },
+    "find-root": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/find-root/-/find-root-1.1.0.tgz",
+      "integrity": "sha512-NKfW6bec6GfKc0SGx1e07QZY9PE99u0Bft/0rzSD5k3sO/vwkVUpDUKVm5Gpp5Ue3YfShPFTX2070tDs5kB9Ng==",
+      "dev": true
+    },
+    "find-up": {
+      "version": "4.1.0",
+      "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz",
+      "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==",
+      "dev": true,
+      "requires": {
+        "locate-path": "^5.0.0",
+        "path-exists": "^4.0.0"
+      }
+    },
+    "findup-sync": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/findup-sync/-/findup-sync-4.0.0.tgz",
+      "integrity": "sha512-6jvvn/12IC4quLBL1KNokxC7wWTvYncaVUYSoxWw7YykPLuRrnv4qdHcSOywOI5RpkOVGeQRtWM8/q+G6W6qfQ==",
+      "dev": true,
+      "requires": {
+        "detect-file": "^1.0.0",
+        "is-glob": "^4.0.0",
+        "micromatch": "^4.0.2",
+        "resolve-dir": "^1.0.1"
+      }
+    },
+    "fs-extra": {
+      "version": "9.1.0",
+      "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz",
+      "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==",
+      "dev": true,
+      "requires": {
+        "at-least-node": "^1.0.0",
+        "graceful-fs": "^4.2.0",
+        "jsonfile": "^6.0.1",
+        "universalify": "^2.0.0"
+      }
+    },
+    "fs.realpath": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
+      "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
+      "dev": true
+    },
+    "function-bind": {
+      "version": "1.1.1",
+      "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz",
+      "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==",
+      "dev": true
+    },
+    "get-caller-file": {
+      "version": "2.0.5",
+      "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz",
+      "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==",
+      "dev": true
+    },
+    "get-stdin": {
+      "version": "8.0.0",
+      "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz",
+      "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==",
+      "dev": true
+    },
+    "git-raw-commits": {
+      "version": "2.0.10",
+      "resolved": "https://registry.npmjs.org/git-raw-commits/-/git-raw-commits-2.0.10.tgz",
+      "integrity": "sha512-sHhX5lsbG9SOO6yXdlwgEMQ/ljIn7qMpAbJZCGfXX2fq5T8M5SrDnpYk9/4HswTildcIqatsWa91vty6VhWSaQ==",
+      "dev": true,
+      "requires": {
+        "dargs": "^7.0.0",
+        "lodash": "^4.17.15",
+        "meow": "^8.0.0",
+        "split2": "^3.0.0",
+        "through2": "^4.0.0"
+      }
+    },
+    "glob": {
+      "version": "7.1.4",
+      "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz",
+      "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==",
+      "dev": true,
+      "requires": {
+        "fs.realpath": "^1.0.0",
+        "inflight": "^1.0.4",
+        "inherits": "2",
+        "minimatch": "^3.0.4",
+        "once": "^1.3.0",
+        "path-is-absolute": "^1.0.0"
+      }
+    },
+    "global-dirs": {
+      "version": "0.1.1",
+      "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz",
+      "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=",
+      "dev": true,
+      "requires": {
+        "ini": "^1.3.4"
+      }
+    },
+    "global-modules": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-1.0.0.tgz",
+      "integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==",
+      "dev": true,
+      "requires": {
+        "global-prefix": "^1.0.1",
+        "is-windows": "^1.0.1",
+        "resolve-dir": "^1.0.0"
+      }
+    },
+    "global-prefix": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-1.0.2.tgz",
+      "integrity": "sha1-2/dDxsFJklk8ZVVoy2btMsASLr4=",
+      "dev": true,
+      "requires": {
+        "expand-tilde": "^2.0.2",
+        "homedir-polyfill": "^1.0.1",
+        "ini": "^1.3.4",
+        "is-windows": "^1.0.1",
+        "which": "^1.2.14"
+      }
+    },
+    "graceful-fs": {
+      "version": "4.2.6",
+      "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.6.tgz",
+      "integrity": "sha512-nTnJ528pbqxYanhpDYsi4Rd8MAeaBA67+RZ10CM1m3bTAVFEDcd5AuA4a6W5YkGZ1iNXHzZz8T6TBKLeBuNriQ==",
+      "dev": true
+    },
+    "hard-rejection": {
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/hard-rejection/-/hard-rejection-2.1.0.tgz",
+      "integrity": "sha512-VIZB+ibDhx7ObhAe7OVtoEbuP4h/MuOTHJ+J8h/eBXotJYl0fBgR72xDFCKgIh22OJZIOVNxBMWuhAr10r8HdA==",
+      "dev": true
+    },
+    "has": {
+      "version": "1.0.3",
+      "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz",
+      "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==",
+      "dev": true,
+      "requires": {
+        "function-bind": "^1.1.1"
+      }
+    },
+    "has-flag": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
+      "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
+      "dev": true
+    },
+    "homedir-polyfill": {
+      "version": "1.0.3",
+      "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz",
+      "integrity": "sha512-eSmmWE5bZTK2Nou4g0AI3zZ9rswp7GRKoKXS1BLUkvPviOqs4YTN1djQIqrXy9k5gEtdLPy86JjRwsNM9tnDcA==",
+      "dev": true,
+      "requires": {
+        "parse-passwd": "^1.0.0"
+      }
+    },
+    "hosted-git-info": {
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.0.2.tgz",
+      "integrity": "sha512-c9OGXbZ3guC/xOlCg1Ci/VgWlwsqDv1yMQL1CWqXDL0hDjXuNcq0zuR4xqPSuasI3kqFDhqSyTjREz5gzq0fXg==",
+      "dev": true,
+      "requires": {
+        "lru-cache": "^6.0.0"
+      }
+    },
+    "husky": {
+      "version": "5.2.0",
+      "resolved": "https://registry.npmjs.org/husky/-/husky-5.2.0.tgz",
+      "integrity": "sha512-AM8T/auHXRBxlrfPVLKP6jt49GCM2Zz47m8G3FOMsLmTv8Dj/fKVWE0Rh2d4Qrvmy131xEsdQnb3OXRib67PGg==",
+      "dev": true
+    },
+    "iconv-lite": {
+      "version": "0.4.24",
+      "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz",
+      "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==",
+      "dev": true,
+      "requires": {
+        "safer-buffer": ">= 2.1.2 < 3"
+      }
+    },
+    "import-fresh": {
+      "version": "3.3.0",
+      "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz",
+      "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==",
+      "dev": true,
+      "requires": {
+        "parent-module": "^1.0.0",
+        "resolve-from": "^4.0.0"
+      },
+      "dependencies": {
+        "resolve-from": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz",
+          "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==",
+          "dev": true
+        }
+      }
+    },
+    "indent-string": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-4.0.0.tgz",
+      "integrity": "sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==",
+      "dev": true
+    },
+    "inflight": {
+      "version": "1.0.6",
+      "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
+      "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=",
+      "dev": true,
+      "requires": {
+        "once": "^1.3.0",
+        "wrappy": "1"
+      }
+    },
+    "inherits": {
+      "version": "2.0.4",
+      "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
+      "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==",
+      "dev": true
+    },
+    "ini": {
+      "version": "1.3.8",
+      "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz",
+      "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==",
+      "dev": true
+    },
+    "inquirer": {
+      "version": "6.5.2",
+      "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.5.2.tgz",
+      "integrity": "sha512-cntlB5ghuB0iuO65Ovoi8ogLHiWGs/5yNrtUcKjFhSSiVeAIVpD7koaSU9RM8mpXw5YDi9RdYXGQMaOURB7ycQ==",
+      "dev": true,
+      "requires": {
+        "ansi-escapes": "^3.2.0",
+        "chalk": "^2.4.2",
+        "cli-cursor": "^2.1.0",
+        "cli-width": "^2.0.0",
+        "external-editor": "^3.0.3",
+        "figures": "^2.0.0",
+        "lodash": "^4.17.12",
+        "mute-stream": "0.0.7",
+        "run-async": "^2.2.0",
+        "rxjs": "^6.4.0",
+        "string-width": "^2.1.0",
+        "strip-ansi": "^5.1.0",
+        "through": "^2.3.6"
+      },
+      "dependencies": {
+        "ansi-regex": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
+          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
+          "dev": true
+        },
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "color-convert": {
+          "version": "1.9.3",
+          "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz",
+          "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==",
+          "dev": true,
+          "requires": {
+            "color-name": "1.1.3"
+          }
+        },
+        "color-name": {
+          "version": "1.1.3",
+          "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz",
+          "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=",
+          "dev": true
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "is-fullwidth-code-point": {
+          "version": "2.0.0",
+          "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz",
+          "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=",
+          "dev": true
+        },
+        "string-width": {
+          "version": "2.1.1",
+          "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz",
+          "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==",
+          "dev": true,
+          "requires": {
+            "is-fullwidth-code-point": "^2.0.0",
+            "strip-ansi": "^4.0.0"
+          },
+          "dependencies": {
+            "strip-ansi": {
+              "version": "4.0.0",
+              "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
+              "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
+              "dev": true,
+              "requires": {
+                "ansi-regex": "^3.0.0"
+              }
+            }
+          }
+        },
+        "strip-ansi": {
+          "version": "5.2.0",
+          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz",
+          "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==",
+          "dev": true,
+          "requires": {
+            "ansi-regex": "^4.1.0"
+          },
+          "dependencies": {
+            "ansi-regex": {
+              "version": "4.1.0",
+              "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz",
+              "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==",
+              "dev": true
+            }
+          }
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
+      }
+    },
+    "is-arrayish": {
+      "version": "0.2.1",
+      "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz",
+      "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=",
+      "dev": true
+    },
+    "is-core-module": {
+      "version": "2.4.0",
+      "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.4.0.tgz",
+      "integrity": "sha512-6A2fkfq1rfeQZjxrZJGerpLCTHRNEBiSgnu0+obeJpEPZRUooHgsizvzv0ZjJwOz3iWIHdJtVWJ/tmPr3D21/A==",
+      "dev": true,
+      "requires": {
+        "has": "^1.0.3"
+      }
+    },
+    "is-extglob": {
+      "version": "2.1.1",
+      "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz",
+      "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=",
+      "dev": true
+    },
+    "is-fullwidth-code-point": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz",
+      "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==",
+      "dev": true
+    },
+    "is-glob": {
+      "version": "4.0.1",
+      "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz",
+      "integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==",
+      "dev": true,
+      "requires": {
+        "is-extglob": "^2.1.1"
+      }
+    },
+    "is-number": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz",
+      "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==",
+      "dev": true
+    },
+    "is-obj": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz",
+      "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==",
+      "dev": true
+    },
+    "is-plain-obj": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz",
+      "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=",
+      "dev": true
+    },
+    "is-text-path": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/is-text-path/-/is-text-path-1.0.1.tgz",
+      "integrity": "sha1-Thqg+1G/vLPpJogAE5cgLBd1tm4=",
+      "dev": true,
+      "requires": {
+        "text-extensions": "^1.0.0"
+      }
+    },
+    "is-utf8": {
+      "version": "0.2.1",
+      "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz",
+      "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=",
+      "dev": true
+    },
+    "is-windows": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz",
+      "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==",
+      "dev": true
+    },
+    "isexe": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz",
+      "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=",
+      "dev": true
+    },
+    "js-tokens": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz",
+      "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==",
+      "dev": true
+    },
+    "json-parse-even-better-errors": {
+      "version": "2.3.1",
+      "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz",
+      "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==",
+      "dev": true
+    },
+    "jsonfile": {
+      "version": "6.1.0",
+      "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz",
+      "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==",
+      "dev": true,
+      "requires": {
+        "graceful-fs": "^4.1.6",
+        "universalify": "^2.0.0"
+      }
+    },
+    "jsonparse": {
+      "version": "1.3.1",
+      "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz",
+      "integrity": "sha1-P02uSpH6wxX3EGL4UhzCOfE2YoA=",
+      "dev": true
+    },
+    "kind-of": {
+      "version": "6.0.3",
+      "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz",
+      "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==",
+      "dev": true
+    },
+    "lines-and-columns": {
+      "version": "1.1.6",
+      "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.1.6.tgz",
+      "integrity": "sha1-HADHQ7QzzQpOgHWPe2SldEDZ/wA=",
+      "dev": true
+    },
+    "locate-path": {
+      "version": "5.0.0",
+      "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz",
+      "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==",
+      "dev": true,
+      "requires": {
+        "p-locate": "^4.1.0"
+      }
+    },
+    "lodash": {
+      "version": "4.17.21",
+      "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz",
+      "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==",
+      "dev": true
+    },
+    "lodash.map": {
+      "version": "4.6.0",
+      "resolved": "https://registry.npmjs.org/lodash.map/-/lodash.map-4.6.0.tgz",
+      "integrity": "sha1-dx7Hg540c9nEzeKLGTlMNWL09tM=",
+      "dev": true
+    },
+    "longest": {
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/longest/-/longest-2.0.1.tgz",
+      "integrity": "sha1-eB4YMpaqlPbU2RbcM10NF676I/g=",
+      "dev": true
+    },
+    "lru-cache": {
+      "version": "6.0.0",
+      "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz",
+      "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==",
+      "dev": true,
+      "requires": {
+        "yallist": "^4.0.0"
+      }
+    },
+    "map-obj": {
+      "version": "4.2.1",
+      "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-4.2.1.tgz",
+      "integrity": "sha512-+WA2/1sPmDj1dlvvJmB5G6JKfY9dpn7EVBUL06+y6PoljPkh+6V1QihwxNkbcGxCRjt2b0F9K0taiCuo7MbdFQ==",
+      "dev": true
+    },
+    "meow": {
+      "version": "8.1.2",
+      "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz",
+      "integrity": "sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==",
+      "dev": true,
+      "requires": {
+        "@types/minimist": "^1.2.0",
+        "camelcase-keys": "^6.2.2",
+        "decamelize-keys": "^1.1.0",
+        "hard-rejection": "^2.1.0",
+        "minimist-options": "4.1.0",
+        "normalize-package-data": "^3.0.0",
+        "read-pkg-up": "^7.0.1",
+        "redent": "^3.0.0",
+        "trim-newlines": "^3.0.0",
+        "type-fest": "^0.18.0",
+        "yargs-parser": "^20.2.3"
+      }
+    },
+    "merge": {
+      "version": "2.1.1",
+      "resolved": "https://registry.npmjs.org/merge/-/merge-2.1.1.tgz",
+      "integrity": "sha512-jz+Cfrg9GWOZbQAnDQ4hlVnQky+341Yk5ru8bZSe6sIDTCIg8n9i/u7hSQGSVOF3C7lH6mGtqjkiT9G4wFLL0w==",
+      "dev": true
+    },
+    "micromatch": {
+      "version": "4.0.4",
+      "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz",
+      "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==",
+      "dev": true,
+      "requires": {
+        "braces": "^3.0.1",
+        "picomatch": "^2.2.3"
+      }
+    },
+    "mimic-fn": {
+      "version": "1.2.0",
+      "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz",
+      "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==",
+      "dev": true
+    },
+    "min-indent": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/min-indent/-/min-indent-1.0.1.tgz",
+      "integrity": "sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==",
+      "dev": true
+    },
+    "minimatch": {
+      "version": "3.0.4",
+      "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
+      "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
+      "dev": true,
+      "requires": {
+        "brace-expansion": "^1.1.7"
+      }
+    },
+    "minimist": {
+      "version": "1.2.5",
+      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz",
+      "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==",
+      "dev": true
+    },
+    "minimist-options": {
+      "version": "4.1.0",
+      "resolved": "https://registry.npmjs.org/minimist-options/-/minimist-options-4.1.0.tgz",
+      "integrity": "sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==",
+      "dev": true,
+      "requires": {
+        "arrify": "^1.0.1",
+        "is-plain-obj": "^1.1.0",
+        "kind-of": "^6.0.3"
+      }
+    },
+    "mute-stream": {
+      "version": "0.0.7",
+      "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz",
+      "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=",
+      "dev": true
+    },
+    "normalize-package-data": {
+      "version": "3.0.2",
+      "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-3.0.2.tgz",
+      "integrity": "sha512-6CdZocmfGaKnIHPVFhJJZ3GuR8SsLKvDANFp47Jmy51aKIr8akjAWTSxtpI+MBgBFdSMRyo4hMpDlT6dTffgZg==",
+      "dev": true,
+      "requires": {
+        "hosted-git-info": "^4.0.1",
+        "resolve": "^1.20.0",
+        "semver": "^7.3.4",
+        "validate-npm-package-license": "^3.0.1"
+      },
+      "dependencies": {
+        "semver": {
+          "version": "7.3.5",
+          "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz",
+          "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==",
+          "dev": true,
+          "requires": {
+            "lru-cache": "^6.0.0"
+          }
+        }
+      }
+    },
+    "once": {
+      "version": "1.4.0",
+      "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
+      "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
+      "dev": true,
+      "requires": {
+        "wrappy": "1"
+      }
+    },
+    "onetime": {
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz",
+      "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=",
+      "dev": true,
+      "requires": {
+        "mimic-fn": "^1.0.0"
+      }
+    },
+    "os-tmpdir": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz",
+      "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=",
+      "dev": true
+    },
+    "p-limit": {
+      "version": "2.3.0",
+      "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz",
+      "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==",
+      "dev": true,
+      "requires": {
+        "p-try": "^2.0.0"
+      }
+    },
+    "p-locate": {
+      "version": "4.1.0",
+      "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz",
+      "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==",
+      "dev": true,
+      "requires": {
+        "p-limit": "^2.2.0"
+      }
+    },
+    "p-try": {
+      "version": "2.2.0",
+      "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz",
+      "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==",
+      "dev": true
+    },
+    "parent-module": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz",
+      "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==",
+      "dev": true,
+      "requires": {
+        "callsites": "^3.0.0"
+      }
+    },
+    "parse-json": {
+      "version": "5.2.0",
+      "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz",
+      "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==",
+      "dev": true,
+      "requires": {
+        "@babel/code-frame": "^7.0.0",
+        "error-ex": "^1.3.1",
+        "json-parse-even-better-errors": "^2.3.0",
+        "lines-and-columns": "^1.1.6"
+      }
+    },
+    "parse-passwd": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz",
+      "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=",
+      "dev": true
+    },
+    "path-exists": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz",
+      "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==",
+      "dev": true
+    },
+    "path-is-absolute": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
+      "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=",
+      "dev": true
+    },
+    "path-parse": {
+      "version": "1.0.7",
+      "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz",
+      "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==",
+      "dev": true
+    },
+    "path-type": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz",
+      "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==",
+      "dev": true
+    },
+    "picomatch": {
+      "version": "2.2.3",
+      "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.2.3.tgz",
+      "integrity": "sha512-KpELjfwcCDUb9PeigTs2mBJzXUPzAuP2oPcA989He8Rte0+YUAjw1JVedDhuTKPkHjSYzMN3npC9luThGYEKdg==",
+      "dev": true
+    },
+    "q": {
+      "version": "1.5.1",
+      "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz",
+      "integrity": "sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=",
+      "dev": true
+    },
+    "quick-lru": {
+      "version": "4.0.1",
+      "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-4.0.1.tgz",
+      "integrity": "sha512-ARhCpm70fzdcvNQfPoy49IaanKkTlRWF2JMzqhcJbhSFRZv7nPTvZJdcY7301IPmvW+/p0RgIWnQDLJxifsQ7g==",
+      "dev": true
+    },
+    "read-pkg": {
+      "version": "5.2.0",
+      "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-5.2.0.tgz",
+      "integrity": "sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==",
+      "dev": true,
+      "requires": {
+        "@types/normalize-package-data": "^2.4.0",
+        "normalize-package-data": "^2.5.0",
+        "parse-json": "^5.0.0",
+        "type-fest": "^0.6.0"
+      },
+      "dependencies": {
+        "hosted-git-info": {
+          "version": "2.8.9",
+          "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.9.tgz",
+          "integrity": "sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==",
+          "dev": true
+        },
+        "normalize-package-data": {
+          "version": "2.5.0",
+          "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz",
+          "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==",
+          "dev": true,
+          "requires": {
+            "hosted-git-info": "^2.1.4",
+            "resolve": "^1.10.0",
+            "semver": "2 || 3 || 4 || 5",
+            "validate-npm-package-license": "^3.0.1"
+          }
+        },
+        "semver": {
+          "version": "5.7.1",
+          "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz",
+          "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==",
+          "dev": true
+        },
+        "type-fest": {
+          "version": "0.6.0",
+          "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.6.0.tgz",
+          "integrity": "sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==",
+          "dev": true
+        }
+      }
+    },
+    "read-pkg-up": {
+      "version": "7.0.1",
+      "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-7.0.1.tgz",
+      "integrity": "sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==",
+      "dev": true,
+      "requires": {
+        "find-up": "^4.1.0",
+        "read-pkg": "^5.2.0",
+        "type-fest": "^0.8.1"
+      },
+      "dependencies": {
+        "type-fest": {
+          "version": "0.8.1",
+          "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz",
+          "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==",
+          "dev": true
+        }
+      }
+    },
+    "readable-stream": {
+      "version": "3.6.0",
+      "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz",
+      "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==",
+      "dev": true,
+      "requires": {
+        "inherits": "^2.0.3",
+        "string_decoder": "^1.1.1",
+        "util-deprecate": "^1.0.1"
+      }
+    },
+    "redent": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz",
+      "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==",
+      "dev": true,
+      "requires": {
+        "indent-string": "^4.0.0",
+        "strip-indent": "^3.0.0"
+      }
+    },
+    "regenerator-runtime": {
+      "version": "0.13.7",
+      "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.7.tgz",
+      "integrity": "sha512-a54FxoJDIr27pgf7IgeQGxmqUNYrcV338lf/6gH456HZ/PhX+5BcwHXG9ajESmwe6WRO0tAzRUrRmNONWgkrew==",
+      "dev": true
+    },
+    "require-directory": {
+      "version": "2.1.1",
+      "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz",
+      "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=",
+      "dev": true
+    },
+    "require-main-filename": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz",
+      "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==",
+      "dev": true
+    },
+    "resolve": {
+      "version": "1.20.0",
+      "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.20.0.tgz",
+      "integrity": "sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==",
+      "dev": true,
+      "requires": {
+        "is-core-module": "^2.2.0",
+        "path-parse": "^1.0.6"
+      }
+    },
+    "resolve-dir": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-1.0.1.tgz",
+      "integrity": "sha1-eaQGRMNivoLybv/nOcm7U4IEb0M=",
+      "dev": true,
+      "requires": {
+        "expand-tilde": "^2.0.0",
+        "global-modules": "^1.0.0"
+      }
+    },
+    "resolve-from": {
+      "version": "5.0.0",
+      "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz",
+      "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==",
+      "dev": true
+    },
+    "resolve-global": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/resolve-global/-/resolve-global-1.0.0.tgz",
+      "integrity": "sha512-zFa12V4OLtT5XUX/Q4VLvTfBf+Ok0SPc1FNGM/z9ctUdiU618qwKpWnd0CHs3+RqROfyEg/DhuHbMWYqcgljEw==",
+      "dev": true,
+      "requires": {
+        "global-dirs": "^0.1.1"
+      }
+    },
+    "restore-cursor": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz",
+      "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=",
+      "dev": true,
+      "requires": {
+        "onetime": "^2.0.0",
+        "signal-exit": "^3.0.2"
+      }
+    },
+    "run-async": {
+      "version": "2.4.1",
+      "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.4.1.tgz",
+      "integrity": "sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==",
+      "dev": true
+    },
+    "rxjs": {
+      "version": "6.6.7",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz",
+      "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==",
+      "dev": true,
+      "requires": {
+        "tslib": "^1.9.0"
+      }
+    },
+    "safe-buffer": {
+      "version": "5.2.1",
+      "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
+      "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==",
+      "dev": true
+    },
+    "safer-buffer": {
+      "version": "2.1.2",
+      "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
+      "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
+      "dev": true
+    },
+    "semver": {
+      "version": "7.3.2",
+      "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.2.tgz",
+      "integrity": "sha512-OrOb32TeeambH6UrhtShmF7CRDqhL6/5XpPNp2DuRH6+9QLw/orhp72j87v8Qa1ScDkvrrBNpZcDejAirJmfXQ==",
+      "dev": true
+    },
+    "set-blocking": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz",
+      "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=",
+      "dev": true
+    },
+    "signal-exit": {
+      "version": "3.0.3",
+      "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.3.tgz",
+      "integrity": "sha512-VUJ49FC8U1OxwZLxIbTTrDvLnf/6TDgxZcK8wxR8zs13xpx7xbG60ndBlhNrFi2EMuFRoeDoJO7wthSLq42EjA==",
+      "dev": true
+    },
+    "spdx-correct": {
+      "version": "3.1.1",
+      "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz",
+      "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==",
+      "dev": true,
+      "requires": {
+        "spdx-expression-parse": "^3.0.0",
+        "spdx-license-ids": "^3.0.0"
+      }
+    },
+    "spdx-exceptions": {
+      "version": "2.3.0",
+      "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.3.0.tgz",
+      "integrity": "sha512-/tTrYOC7PPI1nUAgx34hUpqXuyJG+DTHJTnIULG4rDygi4xu/tfgmq1e1cIRwRzwZgo4NLySi+ricLkZkw4i5A==",
+      "dev": true
+    },
+    "spdx-expression-parse": {
+      "version": "3.0.1",
+      "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.1.tgz",
+      "integrity": "sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==",
+      "dev": true,
+      "requires": {
+        "spdx-exceptions": "^2.1.0",
+        "spdx-license-ids": "^3.0.0"
+      }
+    },
+    "spdx-license-ids": {
+      "version": "3.0.8",
+      "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.8.tgz",
+      "integrity": "sha512-NDgA96EnaLSvtbM7trJj+t1LUR3pirkDCcz9nOUlPb5DMBGsH7oES6C3hs3j7R9oHEa1EMvReS/BUAIT5Tcr0g==",
+      "dev": true
+    },
+    "split2": {
+      "version": "3.2.2",
+      "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz",
+      "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==",
+      "dev": true,
+      "requires": {
+        "readable-stream": "^3.0.0"
+      }
+    },
+    "string-width": {
+      "version": "4.2.2",
+      "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.2.tgz",
+      "integrity": "sha512-XBJbT3N4JhVumXE0eoLU9DCjcaF92KLNqTmFCnG1pf8duUxFGwtP6AD6nkjw9a3IdiRtL3E2w3JDiE/xi3vOeA==",
+      "dev": true,
+      "requires": {
+        "emoji-regex": "^8.0.0",
+        "is-fullwidth-code-point": "^3.0.0",
+        "strip-ansi": "^6.0.0"
+      }
+    },
+    "string_decoder": {
+      "version": "1.3.0",
+      "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz",
+      "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==",
+      "dev": true,
+      "requires": {
+        "safe-buffer": "~5.2.0"
+      }
+    },
+    "strip-ansi": {
+      "version": "6.0.0",
+      "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.0.tgz",
+      "integrity": "sha512-AuvKTrTfQNYNIctbR1K/YGTR1756GycPsg7b9bdV9Duqur4gv6aKqHXah67Z8ImS7WEz5QVcOtlfW2rZEugt6w==",
+      "dev": true,
+      "requires": {
+        "ansi-regex": "^5.0.0"
+      }
+    },
+    "strip-bom": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-4.0.0.tgz",
+      "integrity": "sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w==",
+      "dev": true
+    },
+    "strip-indent": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/strip-indent/-/strip-indent-3.0.0.tgz",
+      "integrity": "sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ==",
+      "dev": true,
+      "requires": {
+        "min-indent": "^1.0.0"
+      }
+    },
+    "strip-json-comments": {
+      "version": "3.0.1",
+      "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.0.1.tgz",
+      "integrity": "sha512-VTyMAUfdm047mwKl+u79WIdrZxtFtn+nBxHeb844XBQ9uMNTuTHdx2hc5RiAJYqwTj3wc/xe5HLSdJSkJ+WfZw==",
+      "dev": true
+    },
+    "supports-color": {
+      "version": "7.2.0",
+      "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
+      "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
+      "dev": true,
+      "requires": {
+        "has-flag": "^4.0.0"
+      }
+    },
+    "text-extensions": {
+      "version": "1.9.0",
+      "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-1.9.0.tgz",
+      "integrity": "sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==",
+      "dev": true
+    },
+    "through": {
+      "version": "2.3.8",
+      "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz",
+      "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=",
+      "dev": true
+    },
+    "through2": {
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/through2/-/through2-4.0.2.tgz",
+      "integrity": "sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==",
+      "dev": true,
+      "requires": {
+        "readable-stream": "3"
+      }
+    },
+    "tmp": {
+      "version": "0.0.33",
+      "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz",
+      "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==",
+      "dev": true,
+      "requires": {
+        "os-tmpdir": "~1.0.2"
+      }
+    },
+    "to-regex-range": {
+      "version": "5.0.1",
+      "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz",
+      "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==",
+      "dev": true,
+      "requires": {
+        "is-number": "^7.0.0"
+      }
+    },
+    "trim-newlines": {
+      "version": "3.0.1",
+      "resolved": "https://registry.npmjs.org/trim-newlines/-/trim-newlines-3.0.1.tgz",
+      "integrity": "sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==",
+      "dev": true
+    },
+    "trim-off-newlines": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/trim-off-newlines/-/trim-off-newlines-1.0.1.tgz",
+      "integrity": "sha1-n5up2e+odkw4dpi8v+sshI8RrbM=",
+      "dev": true
+    },
+    "tslib": {
+      "version": "1.14.1",
+      "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
+      "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==",
+      "dev": true
+    },
+    "type-fest": {
+      "version": "0.18.1",
+      "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.18.1.tgz",
+      "integrity": "sha512-OIAYXk8+ISY+qTOwkHtKqzAuxchoMiD9Udx+FSGQDuiRR+PJKJHc2NJAXlbhkGwTt/4/nKZxELY1w3ReWOL8mw==",
+      "dev": true
+    },
+    "universalify": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz",
+      "integrity": "sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==",
+      "dev": true
+    },
+    "util-deprecate": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
+      "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=",
+      "dev": true
+    },
+    "validate-npm-package-license": {
+      "version": "3.0.4",
+      "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz",
+      "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==",
+      "dev": true,
+      "requires": {
+        "spdx-correct": "^3.0.0",
+        "spdx-expression-parse": "^3.0.0"
+      }
+    },
+    "which": {
+      "version": "1.3.1",
+      "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz",
+      "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==",
+      "dev": true,
+      "requires": {
+        "isexe": "^2.0.0"
+      }
+    },
+    "which-module": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz",
+      "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=",
+      "dev": true
+    },
+    "word-wrap": {
+      "version": "1.2.3",
+      "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz",
+      "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==",
+      "dev": true
+    },
+    "wrap-ansi": {
+      "version": "6.2.0",
+      "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz",
+      "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==",
+      "dev": true,
+      "requires": {
+        "ansi-styles": "^4.0.0",
+        "string-width": "^4.1.0",
+        "strip-ansi": "^6.0.0"
+      }
+    },
+    "wrappy": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
+      "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=",
+      "dev": true
+    },
+    "y18n": {
+      "version": "4.0.3",
+      "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.3.tgz",
+      "integrity": "sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==",
+      "dev": true
+    },
+    "yallist": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz",
+      "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==",
+      "dev": true
+    },
+    "yaml": {
+      "version": "1.10.2",
+      "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz",
+      "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==",
+      "dev": true
+    },
+    "yargs": {
+      "version": "15.4.1",
+      "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.4.1.tgz",
+      "integrity": "sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==",
+      "dev": true,
+      "requires": {
+        "cliui": "^6.0.0",
+        "decamelize": "^1.2.0",
+        "find-up": "^4.1.0",
+        "get-caller-file": "^2.0.1",
+        "require-directory": "^2.1.1",
+        "require-main-filename": "^2.0.0",
+        "set-blocking": "^2.0.0",
+        "string-width": "^4.2.0",
+        "which-module": "^2.0.0",
+        "y18n": "^4.0.0",
+        "yargs-parser": "^18.1.2"
+      },
+      "dependencies": {
+        "yargs-parser": {
+          "version": "18.1.3",
+          "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.3.tgz",
+          "integrity": "sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==",
+          "dev": true,
+          "requires": {
+            "camelcase": "^5.0.0",
+            "decamelize": "^1.2.0"
+          }
+        }
+      }
+    },
+    "yargs-parser": {
+      "version": "20.2.7",
+      "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.7.tgz",
+      "integrity": "sha512-FiNkvbeHzB/syOjIUxFDCnhSfzAL8R5vs40MgLFBorXACCOAEaWu0gRZl14vG8MR9AOJIZbmkjhusqBYZ3HTHw==",
+      "dev": true
+    },
+    "yocto-queue": {
+      "version": "0.1.0",
+      "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz",
+      "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==",
+      "dev": true
+    }
+  }
+}
diff --git a/package.json b/package.json
new file mode 100644
index 0000000..ebd5d55
--- /dev/null
+++ b/package.json
@@ -0,0 +1,13 @@
+{
+  "private": true,
+  "scripts": {
+    "postinstall": "husky install"
+  },
+  "devDependencies": {
+    "@commitlint/cli": "^11.0.0",
+    "@commitlint/config-conventional": "^11.0.0",
+    "commitizen": "^4.2.4",
+    "cz-conventional-changelog": "^3.3.0",
+    "husky": "^5.0.4"
+  }
+}
diff --git a/plat/allwinner/common/allwinner-common.mk b/plat/allwinner/common/allwinner-common.mk
index 997aaa6..61ae9b6 100644
--- a/plat/allwinner/common/allwinner-common.mk
+++ b/plat/allwinner/common/allwinner-common.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -20,8 +20,6 @@
 				${AW_PLAT}/common/sunxi_common.c
 
 BL31_SOURCES		+=	drivers/allwinner/axp/common.c		\
-				drivers/allwinner/sunxi_msgbox.c	\
-				drivers/arm/css/scpi/css_scpi.c		\
 				${GICV2_SOURCES}			\
 				drivers/delay_timer/delay_timer.c	\
 				drivers/delay_timer/generic_delay_timer.c \
@@ -29,12 +27,40 @@
 				plat/common/plat_gicv2.c		\
 				plat/common/plat_psci_common.c		\
 				${AW_PLAT}/common/sunxi_bl31_setup.c	\
-				${AW_PLAT}/common/sunxi_cpu_ops.c	\
 				${AW_PLAT}/common/sunxi_pm.c		\
 				${AW_PLAT}/${PLAT}/sunxi_power.c	\
 				${AW_PLAT}/common/sunxi_security.c	\
 				${AW_PLAT}/common/sunxi_topology.c
 
+# By default, attempt to use SCPI to the ARISC management processor. If SCPI
+# is not enabled or SCP firmware is not loaded, fall back to a simpler native
+# implementation that does not support CPU or system suspend.
+#
+# If SCP firmware will always be present (or absent), the unused implementation
+# can be compiled out.
+SUNXI_PSCI_USE_NATIVE	?=	1
+SUNXI_PSCI_USE_SCPI	?=	1
+
+$(eval $(call assert_boolean,SUNXI_PSCI_USE_NATIVE))
+$(eval $(call assert_boolean,SUNXI_PSCI_USE_SCPI))
+$(eval $(call add_define,SUNXI_PSCI_USE_NATIVE))
+$(eval $(call add_define,SUNXI_PSCI_USE_SCPI))
+
+ifeq (${SUNXI_PSCI_USE_NATIVE}${SUNXI_PSCI_USE_SCPI},00)
+$(error "At least one of SCPI or native PSCI ops must be enabled")
+endif
+
+ifeq (${SUNXI_PSCI_USE_NATIVE},1)
+BL31_SOURCES		+=	${AW_PLAT}/common/sunxi_cpu_ops.c	\
+				${AW_PLAT}/common/sunxi_native_pm.c
+endif
+
+ifeq (${SUNXI_PSCI_USE_SCPI},1)
+BL31_SOURCES		+=	drivers/allwinner/sunxi_msgbox.c	\
+				drivers/arm/css/scpi/css_scpi.c		\
+				${AW_PLAT}/common/sunxi_scpi_pm.c
+endif
+
 # The bootloader is guaranteed to only run on CPU 0 by the boot ROM.
 COLD_BOOT_SINGLE_CPU		:=	1
 
@@ -48,6 +74,10 @@
 ERRATA_A53_835769		:=	1
 ERRATA_A53_843419		:=	1
 ERRATA_A53_855873		:=	1
+ERRATA_A53_1530924		:=	1
+
+# The traditional U-Boot load address is 160MB into DRAM.
+PRELOADED_BL33_BASE		?=	0x4a000000
 
 # The reset vector can be changed for each CPU.
 PROGRAMMABLE_RESET_ADDRESS	:=	1
@@ -55,9 +85,6 @@
 # Allow mapping read-only data as execute-never.
 SEPARATE_CODE_AND_RODATA	:=	1
 
-# Put NOBITS memory in SRAM A1, overwriting U-Boot's SPL.
-SEPARATE_NOBITS_REGION		:=	1
-
 # BL31 gets loaded alongside BL33 (U-Boot) by U-Boot's SPL
 RESET_TO_BL31			:=	1
 
diff --git a/plat/allwinner/common/include/platform_def.h b/plat/allwinner/common/include/platform_def.h
index 975cc48..49951e0 100644
--- a/plat/allwinner/common/include/platform_def.h
+++ b/plat/allwinner/common/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,23 +13,37 @@
 
 #include <sunxi_mmap.h>
 
-#define BL31_BASE			(SUNXI_SRAM_A2_BASE + 0x4000)
+#ifdef SUNXI_BL31_IN_DRAM
+
+#define BL31_BASE			SUNXI_DRAM_BASE
+#define BL31_LIMIT			(SUNXI_DRAM_BASE + 0x40000)
+
+#define MAX_XLAT_TABLES			4
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
+
+#define SUNXI_BL33_VIRT_BASE		PRELOADED_BL33_BASE
+
+#else	/* !SUNXI_BL31_IN_DRAM */
+
+#define BL31_BASE			(SUNXI_SRAM_A2_BASE + \
+					 SUNXI_SRAM_A2_BL31_OFFSET)
 #define BL31_LIMIT			(SUNXI_SRAM_A2_BASE + \
 					 SUNXI_SRAM_A2_SIZE - SUNXI_SCP_SIZE)
 
-/* The SCP firmware is allocated the last 16KiB of SRAM A2. */
-#define SUNXI_SCP_BASE			BL31_LIMIT
-#define SUNXI_SCP_SIZE			0x4000
-
 /* Overwrite U-Boot SPL, but reserve the first page for the SPL header. */
 #define BL31_NOBITS_BASE		(SUNXI_SRAM_A1_BASE + 0x1000)
 #define BL31_NOBITS_LIMIT		(SUNXI_SRAM_A1_BASE + SUNXI_SRAM_A1_SIZE)
 
-/* The traditional U-Boot load address is 160MB into DRAM, so at 0x4a000000 */
-#define PLAT_SUNXI_NS_IMAGE_OFFSET	(SUNXI_DRAM_BASE + (160U << 20))
+#define MAX_XLAT_TABLES			1
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 28)
 
-/* How much memory to reserve as secure for BL32, if configured */
-#define SUNXI_DRAM_SEC_SIZE		(32U << 20)
+#define SUNXI_BL33_VIRT_BASE		SUNXI_DRAM_VIRT_BASE
+
+/* The SCP firmware is allocated the last 16KiB of SRAM A2. */
+#define SUNXI_SCP_BASE			BL31_LIMIT
+#define SUNXI_SCP_SIZE			0x4000
+
+#endif /* SUNXI_BL31_IN_DRAM */
 
 /* How much DRAM to map (to map BL33, for fetching the DTB from U-Boot) */
 #define SUNXI_DRAM_MAP_SIZE		(64U << 20)
@@ -37,8 +51,8 @@
 #define CACHE_WRITEBACK_SHIFT		6
 #define CACHE_WRITEBACK_GRANULE		(1 << CACHE_WRITEBACK_SHIFT)
 
-#define MAX_MMAP_REGIONS		(3 + PLATFORM_MMAP_REGIONS)
-#define MAX_XLAT_TABLES			1
+#define MAX_STATIC_MMAP_REGIONS		3
+#define MAX_MMAP_REGIONS		(5 + MAX_STATIC_MMAP_REGIONS)
 
 #define PLAT_CSS_SCP_COM_SHARED_MEM_BASE \
 	(SUNXI_SRAM_A2_BASE + SUNXI_SRAM_A2_SIZE - 0x200)
@@ -53,13 +67,11 @@
 					 PLATFORM_CORE_COUNT)
 
 #define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 28)
 
 #define PLATFORM_CLUSTER_COUNT		U(1)
 #define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER_COUNT * \
 					 PLATFORM_MAX_CPUS_PER_CLUSTER)
 #define PLATFORM_MAX_CPUS_PER_CLUSTER	U(4)
-#define PLATFORM_MMAP_REGIONS		5
 #define PLATFORM_STACK_SIZE		(0x1000 / PLATFORM_CORE_COUNT)
 
 #ifndef SPD_none
diff --git a/plat/allwinner/common/include/sunxi_def.h b/plat/allwinner/common/include/sunxi_def.h
index 73c4453..ec50887 100644
--- a/plat/allwinner/common/include/sunxi_def.h
+++ b/plat/allwinner/common/include/sunxi_def.h
@@ -17,5 +17,7 @@
 #define SUNXI_SOC_A64			0x1689
 #define SUNXI_SOC_H5			0x1718
 #define SUNXI_SOC_H6			0x1728
+#define SUNXI_SOC_H616			0x1823
+#define SUNXI_SOC_R329			0x1851
 
 #endif /* SUNXI_DEF_H */
diff --git a/plat/allwinner/common/include/sunxi_private.h b/plat/allwinner/common/include/sunxi_private.h
index dcf3dc9..6cf4670 100644
--- a/plat/allwinner/common/include/sunxi_private.h
+++ b/plat/allwinner/common/include/sunxi_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,13 +7,32 @@
 #ifndef SUNXI_PRIVATE_H
 #define SUNXI_PRIVATE_H
 
+#include <lib/psci/psci.h>
+
 void sunxi_configure_mmu_el3(int flags);
 
 void sunxi_cpu_on(u_register_t mpidr);
-void sunxi_cpu_off(u_register_t mpidr);
-void sunxi_disable_secondary_cpus(u_register_t primary_mpidr);
+void sunxi_cpu_power_off_others(void);
+void sunxi_cpu_power_off_self(void);
 void sunxi_power_down(void);
 
+#if SUNXI_PSCI_USE_NATIVE
+void sunxi_set_native_psci_ops(const plat_psci_ops_t **psci_ops);
+#else
+static inline void sunxi_set_native_psci_ops(const plat_psci_ops_t **psci_ops)
+{
+}
+#endif
+#if SUNXI_PSCI_USE_SCPI
+int sunxi_set_scpi_psci_ops(const plat_psci_ops_t **psci_ops);
+#else
+static inline int sunxi_set_scpi_psci_ops(const plat_psci_ops_t **psci_ops)
+{
+	return -1;
+}
+#endif
+int sunxi_validate_ns_entrypoint(uintptr_t ns_entrypoint);
+
 int sunxi_pmic_setup(uint16_t socid, const void *fdt);
 void sunxi_security_setup(void);
 
@@ -22,4 +41,12 @@
 int sunxi_init_platform_r_twi(uint16_t socid, bool use_rsb);
 void sunxi_execute_arisc_code(uint32_t *code, size_t size, uint16_t param);
 
+#ifdef SUNXI_BL31_IN_DRAM
+void sunxi_prepare_dtb(void *fdt);
+#else
+static inline void sunxi_prepare_dtb(void *fdt)
+{
+}
+#endif
+
 #endif /* SUNXI_PRIVATE_H */
diff --git a/plat/allwinner/common/sunxi_bl31_setup.c b/plat/allwinner/common/sunxi_bl31_setup.c
index e836a34..14049e8 100644
--- a/plat/allwinner/common/sunxi_bl31_setup.c
+++ b/plat/allwinner/common/sunxi_bl31_setup.c
@@ -13,6 +13,8 @@
 #include <arch.h>
 #include <arch_helpers.h>
 #include <common/debug.h>
+#include <common/fdt_fixup.h>
+#include <common/fdt_wrappers.h>
 #include <drivers/arm/gicv2.h>
 #include <drivers/console.h>
 #include <drivers/generic_delay_timer.h>
@@ -52,12 +54,12 @@
 	uint64_t *u_boot_base;
 	int i;
 
-	u_boot_base = (void *)(SUNXI_DRAM_VIRT_BASE + SUNXI_DRAM_SEC_SIZE);
+	u_boot_base = (void *)SUNXI_BL33_VIRT_BASE;
 
 	for (i = 0; i < 2048 / sizeof(uint64_t); i++) {
 		uint32_t *dtb_base;
 
-		if (u_boot_base[i] != PLAT_SUNXI_NS_IMAGE_OFFSET)
+		if (u_boot_base[i] != PRELOADED_BL33_BASE)
 			continue;
 
 		/* Does the suspected U-Boot size look anyhow reasonable? */
@@ -96,13 +98,10 @@
 	 * Tell BL31 where the non-trusted software image
 	 * is located and the entry state information
 	 */
-	bl33_image_ep_info.pc = plat_get_ns_image_entrypoint();
+	bl33_image_ep_info.pc = PRELOADED_BL33_BASE;
 	bl33_image_ep_info.spsr = SPSR_64(MODE_EL2, MODE_SP_ELX,
 					  DISABLE_ALL_EXCEPTIONS);
 	SET_SECURITY_STATE(bl33_image_ep_info.h.attr, NON_SECURE);
-
-	/* Turn off all secondary CPUs */
-	sunxi_disable_secondary_cpus(read_mpidr());
 }
 
 void bl31_plat_arch_setup(void)
@@ -126,6 +125,12 @@
 	case SUNXI_SOC_H6:
 		soc_name = "H6";
 		break;
+	case SUNXI_SOC_H616:
+		soc_name = "H616";
+		break;
+	case SUNXI_SOC_R329:
+		soc_name = "R329";
+		break;
 	default:
 		soc_name = "unknown";
 		break;
@@ -175,6 +180,8 @@
 
 	sunxi_pmic_setup(soc_id, fdt);
 
+	sunxi_prepare_dtb(fdt);
+
 	INFO("BL31: Platform setup done\n");
 }
 
diff --git a/plat/allwinner/common/sunxi_common.c b/plat/allwinner/common/sunxi_common.c
index 0ca18ad..82410b1 100644
--- a/plat/allwinner/common/sunxi_common.c
+++ b/plat/allwinner/common/sunxi_common.c
@@ -1,36 +1,26 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <errno.h>
 
-#include <platform_def.h>
-
-#include <arch_helpers.h>
 #include <common/debug.h>
 #include <lib/mmio.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
-#include <plat/common/platform.h>
 
 #include <sunxi_def.h>
 #include <sunxi_mmap.h>
 #include <sunxi_private.h>
 
-static const mmap_region_t sunxi_mmap[PLATFORM_MMAP_REGIONS + 1] = {
+static const mmap_region_t sunxi_mmap[MAX_STATIC_MMAP_REGIONS + 1] = {
 	MAP_REGION_FLAT(SUNXI_SRAM_BASE, SUNXI_SRAM_SIZE,
-			MT_RW_DATA | MT_SECURE),
-	MAP_REGION_FLAT(SUNXI_SCP_BASE, SUNXI_SCP_SIZE,
 			MT_DEVICE | MT_RW | MT_SECURE | MT_EXECUTE_NEVER),
 	MAP_REGION_FLAT(SUNXI_DEV_BASE, SUNXI_DEV_SIZE,
 			MT_DEVICE | MT_RW | MT_SECURE | MT_EXECUTE_NEVER),
-	MAP_REGION(SUNXI_DRAM_BASE, SUNXI_DRAM_VIRT_BASE, SUNXI_DRAM_SEC_SIZE,
-		   MT_RW_DATA | MT_SECURE),
-	MAP_REGION(PLAT_SUNXI_NS_IMAGE_OFFSET,
-		   SUNXI_DRAM_VIRT_BASE + SUNXI_DRAM_SEC_SIZE,
-		   SUNXI_DRAM_MAP_SIZE,
-		   MT_RO_DATA | MT_NS),
+	MAP_REGION(PRELOADED_BL33_BASE, SUNXI_BL33_VIRT_BASE,
+		   SUNXI_DRAM_MAP_SIZE, MT_RW_DATA | MT_NS),
 	{},
 };
 
@@ -39,26 +29,29 @@
 	return SUNXI_OSC24M_CLK_IN_HZ;
 }
 
-uintptr_t plat_get_ns_image_entrypoint(void)
-{
-#ifdef PRELOADED_BL33_BASE
-	return PRELOADED_BL33_BASE;
-#else
-	return PLAT_SUNXI_NS_IMAGE_OFFSET;
-#endif
-}
-
 void sunxi_configure_mmu_el3(int flags)
 {
 	mmap_add_region(BL_CODE_BASE, BL_CODE_BASE,
 			BL_CODE_END - BL_CODE_BASE,
 			MT_CODE | MT_SECURE);
+	mmap_add_region(BL_CODE_END, BL_CODE_END,
+			BL_END - BL_CODE_END,
+			MT_RW_DATA | MT_SECURE);
+#if SEPARATE_CODE_AND_RODATA
 	mmap_add_region(BL_RO_DATA_BASE, BL_RO_DATA_BASE,
 			BL_RO_DATA_END - BL_RO_DATA_BASE,
 			MT_RO_DATA | MT_SECURE);
+#endif
+#if SEPARATE_NOBITS_REGION
+	mmap_add_region(BL_NOBITS_BASE, BL_NOBITS_BASE,
+			BL_NOBITS_END - BL_NOBITS_BASE,
+			MT_RW_DATA | MT_SECURE);
+#endif
+#if USE_COHERENT_MEM
 	mmap_add_region(BL_COHERENT_RAM_BASE, BL_COHERENT_RAM_BASE,
 			BL_COHERENT_RAM_END - BL_COHERENT_RAM_BASE,
 			MT_DEVICE | MT_RW | MT_SECURE | MT_EXECUTE_NEVER);
+#endif
 
 	mmap_add(sunxi_mmap);
 	init_xlat_tables();
@@ -125,11 +118,10 @@
 		device_bit = BIT(6);
 		break;
 	case SUNXI_SOC_H6:
-		if (use_rsb)
-			return -ENODEV;
-		pin_func = 0x33;
+	case SUNXI_SOC_H616:
+		pin_func = use_rsb ? 0x22 : 0x33;
 		device_bit = BIT(16);
-		reset_offset = 0x19c;
+		reset_offset = use_rsb ? 0x1bc : 0x19c;
 		break;
 	case SUNXI_SOC_A64:
 		pin_func = use_rsb ? 0x22 : 0x33;
@@ -141,7 +133,7 @@
 	}
 
 	/* un-gate R_PIO clock */
-	if (socid != SUNXI_SOC_H6)
+	if (socid != SUNXI_SOC_H6 && socid != SUNXI_SOC_H616)
 		mmio_setbits_32(SUNXI_R_PRCM_BASE + 0x28, BIT(0));
 
 	/* switch pins PL0 and PL1 to the desired function */
@@ -154,10 +146,10 @@
 	mmio_clrsetbits_32(SUNXI_R_PIO_BASE + 0x1c, 0x0fU, 0x5U);
 
 	/* un-gate clock */
-	if (socid != SUNXI_SOC_H6)
+	if (socid != SUNXI_SOC_H6 && socid != SUNXI_SOC_H616)
 		mmio_setbits_32(SUNXI_R_PRCM_BASE + 0x28, device_bit);
 	else
-		mmio_setbits_32(SUNXI_R_PRCM_BASE + 0x19c, device_bit | BIT(0));
+		mmio_setbits_32(SUNXI_R_PRCM_BASE + reset_offset, BIT(0));
 
 	/* assert, then de-assert reset of I2C/RSB controller */
 	mmio_clrbits_32(SUNXI_R_PRCM_BASE + reset_offset, device_bit);
@@ -165,50 +157,3 @@
 
 	return 0;
 }
-
-/* This lock synchronises access to the arisc management processor. */
-DEFINE_BAKERY_LOCK(arisc_lock);
-
-/*
- * Tell the "arisc" SCP core (an OpenRISC core) to execute some code.
- * We don't have any service running there, so we place some OpenRISC code
- * in SRAM, put the address of that into the reset vector and release the
- * arisc reset line. The SCP will execute that code and pull the line up again.
- */
-void sunxi_execute_arisc_code(uint32_t *code, size_t size, uint16_t param)
-{
-	uintptr_t arisc_reset_vec = SUNXI_SRAM_A2_BASE + 0x100;
-
-	do {
-		bakery_lock_get(&arisc_lock);
-		/* Wait until the arisc is in reset state. */
-		if (!(mmio_read_32(SUNXI_R_CPUCFG_BASE) & BIT(0)))
-			break;
-
-		bakery_lock_release(&arisc_lock);
-	} while (1);
-
-	/* Patch up the code to feed in an input parameter. */
-	code[0] = (code[0] & ~0xffff) | param;
-	clean_dcache_range((uintptr_t)code, size);
-
-	/*
-	 * The OpenRISC unconditional branch has opcode 0, the branch offset
-	 * is in the lower 26 bits, containing the distance to the target,
-	 * in instruction granularity (32 bits).
-	 */
-	mmio_write_32(arisc_reset_vec, ((uintptr_t)code - arisc_reset_vec) / 4);
-	clean_dcache_range(arisc_reset_vec, 4);
-
-	/* De-assert the arisc reset line to let it run. */
-	mmio_setbits_32(SUNXI_R_CPUCFG_BASE, BIT(0));
-
-	/*
-	 * We release the lock here, although the arisc is still busy.
-	 * But as long as it runs, the reset line is high, so other users
-	 * won't leave the loop above.
-	 * Once it has finished, the code is supposed to clear the reset line,
-	 * to signal this to other users.
-	 */
-	bakery_lock_release(&arisc_lock);
-}
diff --git a/plat/allwinner/common/sunxi_cpu_ops.c b/plat/allwinner/common/sunxi_cpu_ops.c
index 6e29b69..46e7090 100644
--- a/plat/allwinner/common/sunxi_cpu_ops.c
+++ b/plat/allwinner/common/sunxi_cpu_ops.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,7 +15,6 @@
 #include <lib/utils_def.h>
 #include <plat/common/platform.h>
 
-#include <core_off_arisc.h>
 #include <sunxi_cpucfg.h>
 #include <sunxi_mmap.h>
 #include <sunxi_private.h>
@@ -43,9 +42,11 @@
 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xe0);
 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0x80);
 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0x00);
+	udelay(1);
 }
 
-void sunxi_cpu_off(u_register_t mpidr)
+/* We can't turn ourself off like this, but it works for other cores. */
+static void sunxi_cpu_off(u_register_t mpidr)
 {
 	unsigned int cluster = MPIDR_AFFLVL1_VAL(mpidr);
 	unsigned int core    = MPIDR_AFFLVL0_VAL(mpidr);
@@ -54,31 +55,13 @@
 
 	/* Deassert DBGPWRDUP */
 	mmio_clrbits_32(SUNXI_CPUCFG_DBG_REG0, BIT(core));
-
-	/* We can't turn ourself off like this, but it works for other cores. */
-	if (read_mpidr() != mpidr) {
-		/* Activate the core output clamps, but not for core 0. */
-		if (core != 0)
-			mmio_setbits_32(SUNXI_POWEROFF_GATING_REG(cluster),
-					BIT(core));
-		/* Assert CPU power-on reset */
-		mmio_clrbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
-		/* Remove power from the CPU */
-		sunxi_cpu_disable_power(cluster, core);
-
-		return;
-	}
-
-	/* Simplifies assembly, all SoCs so far are single cluster anyway. */
-	assert(cluster == 0);
-
-	/*
-	 * If we are supposed to turn ourself off, tell the arisc SCP
-	 * to do that work for us. The code expects the core mask to be
-	 * patched into the first instruction.
-	 */
-	sunxi_execute_arisc_code(arisc_core_off, sizeof(arisc_core_off),
-				 BIT_32(core));
+	/* Activate the core output clamps, but not for core 0. */
+	if (core != 0)
+		mmio_setbits_32(SUNXI_POWEROFF_GATING_REG(cluster), BIT(core));
+	/* Assert CPU power-on reset */
+	mmio_clrbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
+	/* Remove power from the CPU */
+	sunxi_cpu_disable_power(cluster, core);
 }
 
 void sunxi_cpu_on(u_register_t mpidr)
@@ -93,7 +76,8 @@
 	/* Assert CPU power-on reset */
 	mmio_clrbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
 	/* Set CPU to start in AArch64 mode */
-	mmio_setbits_32(SUNXI_CPUCFG_CLS_CTRL_REG0(cluster), BIT(24 + core));
+	mmio_setbits_32(SUNXI_AA64nAA32_REG(cluster),
+			BIT(SUNXI_AA64nAA32_OFFSET + core));
 	/* Apply power to the CPU */
 	sunxi_cpu_enable_power(cluster, core);
 	/* Release the core output clamps */
@@ -106,8 +90,9 @@
 	mmio_setbits_32(SUNXI_CPUCFG_DBG_REG0, BIT(core));
 }
 
-void sunxi_disable_secondary_cpus(u_register_t primary_mpidr)
+void sunxi_cpu_power_off_others(void)
 {
+	u_register_t self = read_mpidr();
 	unsigned int cluster;
 	unsigned int core;
 
@@ -116,7 +101,7 @@
 			u_register_t mpidr = (cluster << MPIDR_AFF1_SHIFT) |
 					     (core    << MPIDR_AFF0_SHIFT) |
 					     BIT(31);
-			if (mpidr != primary_mpidr)
+			if (mpidr != self)
 				sunxi_cpu_off(mpidr);
 		}
 	}
diff --git a/plat/allwinner/common/sunxi_native_pm.c b/plat/allwinner/common/sunxi_native_pm.c
new file mode 100644
index 0000000..148f50e
--- /dev/null
+++ b/plat/allwinner/common/sunxi_native_pm.c
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/arm/gicv2.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+#include <lib/psci/psci.h>
+
+#include <sunxi_mmap.h>
+#include <sunxi_private.h>
+
+#define SUNXI_WDOG0_CTRL_REG		(SUNXI_R_WDOG_BASE + 0x0010)
+#define SUNXI_WDOG0_CFG_REG		(SUNXI_R_WDOG_BASE + 0x0014)
+#define SUNXI_WDOG0_MODE_REG		(SUNXI_R_WDOG_BASE + 0x0018)
+
+static int sunxi_pwr_domain_on(u_register_t mpidr)
+{
+	sunxi_cpu_on(mpidr);
+
+	return PSCI_E_SUCCESS;
+}
+
+static void sunxi_pwr_domain_off(const psci_power_state_t *target_state)
+{
+	gicv2_cpuif_disable();
+
+	sunxi_cpu_power_off_self();
+}
+
+static void sunxi_pwr_domain_on_finish(const psci_power_state_t *target_state)
+{
+	gicv2_pcpu_distif_init();
+	gicv2_cpuif_enable();
+}
+
+static void __dead2 sunxi_system_off(void)
+{
+	gicv2_cpuif_disable();
+
+	/* Attempt to power down the board (may not return) */
+	sunxi_power_down();
+
+	/* Turn off all CPUs */
+	sunxi_cpu_power_off_others();
+	sunxi_cpu_power_off_self();
+	psci_power_down_wfi();
+}
+
+static void __dead2 sunxi_system_reset(void)
+{
+	gicv2_cpuif_disable();
+
+	/* Reset the whole system when the watchdog times out */
+	mmio_write_32(SUNXI_WDOG0_CFG_REG, 1);
+	/* Enable the watchdog with the shortest timeout (0.5 seconds) */
+	mmio_write_32(SUNXI_WDOG0_MODE_REG, (0 << 4) | 1);
+	/* Wait for twice the watchdog timeout before panicking */
+	mdelay(1000);
+
+	ERROR("PSCI: System reset failed\n");
+	panic();
+}
+
+static const plat_psci_ops_t sunxi_native_psci_ops = {
+	.pwr_domain_on			= sunxi_pwr_domain_on,
+	.pwr_domain_off			= sunxi_pwr_domain_off,
+	.pwr_domain_on_finish		= sunxi_pwr_domain_on_finish,
+	.system_off			= sunxi_system_off,
+	.system_reset			= sunxi_system_reset,
+	.validate_ns_entrypoint		= sunxi_validate_ns_entrypoint,
+};
+
+void sunxi_set_native_psci_ops(const plat_psci_ops_t **psci_ops)
+{
+	*psci_ops = &sunxi_native_psci_ops;
+}
diff --git a/plat/allwinner/common/sunxi_pm.c b/plat/allwinner/common/sunxi_pm.c
index e0fa5b3..eb1b7e7 100644
--- a/plat/allwinner/common/sunxi_pm.c
+++ b/plat/allwinner/common/sunxi_pm.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -8,257 +8,22 @@
 
 #include <platform_def.h>
 
-#include <arch_helpers.h>
 #include <common/debug.h>
-#include <drivers/arm/css/css_scpi.h>
-#include <drivers/arm/gicv2.h>
-#include <drivers/delay_timer.h>
 #include <lib/mmio.h>
 #include <lib/psci/psci.h>
-#include <plat/common/platform.h>
 
 #include <sunxi_cpucfg.h>
-#include <sunxi_def.h>
-#include <sunxi_mmap.h>
 #include <sunxi_private.h>
 
-#define SUNXI_WDOG0_CTRL_REG		(SUNXI_R_WDOG_BASE + 0x0010)
-#define SUNXI_WDOG0_CFG_REG		(SUNXI_R_WDOG_BASE + 0x0014)
-#define SUNXI_WDOG0_MODE_REG		(SUNXI_R_WDOG_BASE + 0x0018)
-
-#define CPU_PWR_LVL			MPIDR_AFFLVL0
-#define CLUSTER_PWR_LVL			MPIDR_AFFLVL1
-#define SYSTEM_PWR_LVL			MPIDR_AFFLVL2
-
-#define CPU_PWR_STATE(state) \
-	((state)->pwr_domain_state[CPU_PWR_LVL])
-#define CLUSTER_PWR_STATE(state) \
-	((state)->pwr_domain_state[CLUSTER_PWR_LVL])
-#define SYSTEM_PWR_STATE(state) \
-	((state)->pwr_domain_state[SYSTEM_PWR_LVL])
-
-#define mpidr_is_valid(mpidr) (plat_core_pos_by_mpidr(mpidr) >= 0)
-
-/*
- * The addresses for the SCP exception vectors are defined in the or1k
- * architecture specification.
- */
-#define OR1K_VEC_FIRST			0x01
-#define OR1K_VEC_LAST			0x0e
-#define OR1K_VEC_ADDR(n)		(0x100 * (n))
-
-/*
- * This magic value is the little-endian representation of the or1k
- * instruction "l.mfspr r2, r0, 0x12", which is guaranteed to be the
- * first instruction in the SCP firmware.
- */
-#define SCP_FIRMWARE_MAGIC		0xb4400012
-
-static bool scpi_available;
-
-static inline scpi_power_state_t scpi_map_state(plat_local_state_t psci_state)
-{
-	if (is_local_state_run(psci_state))
-		return scpi_power_on;
-	if (is_local_state_retn(psci_state))
-		return scpi_power_retention;
-	return scpi_power_off;
-}
-
-static void sunxi_cpu_standby(plat_local_state_t cpu_state)
-{
-	u_register_t scr = read_scr_el3();
-
-	assert(is_local_state_retn(cpu_state));
-
-	write_scr_el3(scr | SCR_IRQ_BIT);
-	wfi();
-	write_scr_el3(scr);
-}
-
-static int sunxi_pwr_domain_on(u_register_t mpidr)
-{
-	if (mpidr_is_valid(mpidr) == 0)
-		return PSCI_E_INTERN_FAIL;
-
-	if (scpi_available) {
-		scpi_set_css_power_state(mpidr,
-					 scpi_power_on,
-					 scpi_power_on,
-					 scpi_power_on);
-	} else {
-		sunxi_cpu_on(mpidr);
-	}
-
-	return PSCI_E_SUCCESS;
-}
-
-static void sunxi_pwr_domain_off(const psci_power_state_t *target_state)
-{
-	plat_local_state_t cpu_pwr_state     = CPU_PWR_STATE(target_state);
-	plat_local_state_t cluster_pwr_state = CLUSTER_PWR_STATE(target_state);
-	plat_local_state_t system_pwr_state  = SYSTEM_PWR_STATE(target_state);
-
-	if (is_local_state_off(cpu_pwr_state))
-		gicv2_cpuif_disable();
-
-	if (scpi_available) {
-		scpi_set_css_power_state(read_mpidr(),
-					 scpi_map_state(cpu_pwr_state),
-					 scpi_map_state(cluster_pwr_state),
-					 scpi_map_state(system_pwr_state));
-	}
-}
-
-static void __dead2 sunxi_pwr_down_wfi(const psci_power_state_t *target_state)
-{
-	sunxi_cpu_off(read_mpidr());
-
-	while (1)
-		wfi();
-}
-
-static void sunxi_pwr_domain_on_finish(const psci_power_state_t *target_state)
-{
-	if (is_local_state_off(SYSTEM_PWR_STATE(target_state)))
-		gicv2_distif_init();
-	if (is_local_state_off(CPU_PWR_STATE(target_state))) {
-		gicv2_pcpu_distif_init();
-		gicv2_cpuif_enable();
-	}
-}
-
-static void __dead2 sunxi_system_off(void)
-{
-	gicv2_cpuif_disable();
-
-	if (scpi_available) {
-		/* Send the power down request to the SCP */
-		uint32_t ret = scpi_sys_power_state(scpi_system_shutdown);
-
-		if (ret != SCP_OK)
-			ERROR("PSCI: SCPI %s failed: %d\n", "shutdown", ret);
-	}
-
-	/* Turn off all secondary CPUs */
-	sunxi_disable_secondary_cpus(read_mpidr());
-
-	sunxi_power_down();
-
-	udelay(1000);
-	ERROR("PSCI: Cannot turn off system, halting\n");
-	wfi();
-	panic();
-}
-
-static void __dead2 sunxi_system_reset(void)
-{
-	gicv2_cpuif_disable();
-
-	if (scpi_available) {
-		/* Send the system reset request to the SCP */
-		uint32_t ret = scpi_sys_power_state(scpi_system_reboot);
-
-		if (ret != SCP_OK)
-			ERROR("PSCI: SCPI %s failed: %d\n", "reboot", ret);
-	}
-
-	/* Reset the whole system when the watchdog times out */
-	mmio_write_32(SUNXI_WDOG0_CFG_REG, 1);
-	/* Enable the watchdog with the shortest timeout (0.5 seconds) */
-	mmio_write_32(SUNXI_WDOG0_MODE_REG, (0 << 4) | 1);
-	/* Wait for twice the watchdog timeout before panicking */
-	mdelay(1000);
-
-	ERROR("PSCI: System reset failed\n");
-	wfi();
-	panic();
-}
-
-static int sunxi_validate_power_state(unsigned int power_state,
-				      psci_power_state_t *req_state)
-{
-	unsigned int power_level = psci_get_pstate_pwrlvl(power_state);
-	unsigned int type = psci_get_pstate_type(power_state);
-
-	assert(req_state != NULL);
-
-	if (power_level > PLAT_MAX_PWR_LVL)
-		return PSCI_E_INVALID_PARAMS;
-
-	if (type == PSTATE_TYPE_STANDBY) {
-		/* Only one retention power state is supported. */
-		if (psci_get_pstate_id(power_state) > 0)
-			return PSCI_E_INVALID_PARAMS;
-		/* The SoC cannot be suspended without losing state */
-		if (power_level == SYSTEM_PWR_LVL)
-			return PSCI_E_INVALID_PARAMS;
-		for (unsigned int i = 0; i <= power_level; ++i)
-			req_state->pwr_domain_state[i] = PLAT_MAX_RET_STATE;
-	} else {
-		/* Only one off power state is supported. */
-		if (psci_get_pstate_id(power_state) > 0)
-			return PSCI_E_INVALID_PARAMS;
-		for (unsigned int i = 0; i <= power_level; ++i)
-			req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
-	}
-	/* Higher power domain levels should all remain running */
-	for (unsigned int i = power_level + 1; i <= PLAT_MAX_PWR_LVL; ++i)
-		req_state->pwr_domain_state[i] = PSCI_LOCAL_STATE_RUN;
-
-	return PSCI_E_SUCCESS;
-}
-
-static int sunxi_validate_ns_entrypoint(uintptr_t ns_entrypoint)
+int sunxi_validate_ns_entrypoint(uintptr_t ns_entrypoint)
 {
 	/* The non-secure entry point must be in DRAM */
-	if (ns_entrypoint >= SUNXI_DRAM_BASE)
-		return PSCI_E_SUCCESS;
-
-	return PSCI_E_INVALID_ADDRESS;
-}
-
-static void sunxi_get_sys_suspend_power_state(psci_power_state_t *req_state)
-{
-	assert(req_state);
-
-	for (unsigned int i = 0; i <= PLAT_MAX_PWR_LVL; ++i)
-		req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
-}
-
-static int sunxi_get_node_hw_state(u_register_t mpidr,
-				   unsigned int power_level)
-{
-	unsigned int cluster_state, cpu_state;
-	unsigned int cpu = MPIDR_AFFLVL0_VAL(mpidr);
-
-	/* SoC power level (always on if PSCI works). */
-	if (power_level == SYSTEM_PWR_LVL)
-		return HW_ON;
-	if (scpi_get_css_power_state(mpidr, &cpu_state, &cluster_state))
-		return PSCI_E_NOT_SUPPORTED;
-	/* Cluster power level (full power state available). */
-	if (power_level == CLUSTER_PWR_LVL) {
-		if (cluster_state == scpi_power_on)
-			return HW_ON;
-		if (cluster_state == scpi_power_retention)
-			return HW_STANDBY;
-		return HW_OFF;
+	if (ns_entrypoint < SUNXI_DRAM_BASE) {
+		return PSCI_E_INVALID_ADDRESS;
 	}
-	/* CPU power level (one bit boolean for on or off). */
-	return ((cpu_state & BIT(cpu)) != 0) ? HW_ON : HW_OFF;
-}
 
-static plat_psci_ops_t sunxi_psci_ops = {
-	.cpu_standby			= sunxi_cpu_standby,
-	.pwr_domain_on			= sunxi_pwr_domain_on,
-	.pwr_domain_off			= sunxi_pwr_domain_off,
-	.pwr_domain_on_finish		= sunxi_pwr_domain_on_finish,
-	.system_off			= sunxi_system_off,
-	.system_reset			= sunxi_system_reset,
-	.validate_power_state		= sunxi_validate_power_state,
-	.validate_ns_entrypoint		= sunxi_validate_ns_entrypoint,
-};
+	return PSCI_E_SUCCESS;
+}
 
 int plat_setup_psci_ops(uintptr_t sec_entrypoint,
 			const plat_psci_ops_t **psci_ops)
@@ -273,37 +38,12 @@
 			      sec_entrypoint >> 32);
 	}
 
-	/* Check for a valid SCP firmware, and boot the SCP if found. */
-	if (mmio_read_32(SUNXI_SCP_BASE) == SCP_FIRMWARE_MAGIC) {
-		/* Program SCP exception vectors to the firmware entrypoint. */
-		for (unsigned int i = OR1K_VEC_FIRST; i <= OR1K_VEC_LAST; ++i) {
-			uint32_t vector = SUNXI_SRAM_A2_BASE + OR1K_VEC_ADDR(i);
-			uint32_t offset = SUNXI_SCP_BASE - vector;
-
-			mmio_write_32(vector, offset >> 2);
-			clean_dcache_range(vector, sizeof(uint32_t));
-		}
-		/* Take the SCP out of reset. */
-		mmio_setbits_32(SUNXI_R_CPUCFG_BASE, BIT(0));
-		/* Wait for the SCP firmware to boot. */
-		if (scpi_wait_ready() == 0)
-			scpi_available = true;
-	}
-
-	NOTICE("PSCI: System suspend is %s\n",
-	       scpi_available ? "available via SCPI" : "unavailable");
-	if (scpi_available) {
-		/* Suspend is only available via SCPI. */
-		sunxi_psci_ops.pwr_domain_suspend = sunxi_pwr_domain_off;
-		sunxi_psci_ops.pwr_domain_suspend_finish = sunxi_pwr_domain_on_finish;
-		sunxi_psci_ops.get_sys_suspend_power_state = sunxi_get_sys_suspend_power_state;
-		sunxi_psci_ops.get_node_hw_state = sunxi_get_node_hw_state;
+	if (sunxi_set_scpi_psci_ops(psci_ops) == 0) {
+		INFO("PSCI: Suspend is available via SCPI\n");
 	} else {
-		/* This is only needed when SCPI is unavailable. */
-		sunxi_psci_ops.pwr_domain_pwr_down_wfi = sunxi_pwr_down_wfi;
+		INFO("PSCI: Suspend is unavailable\n");
+		sunxi_set_native_psci_ops(psci_ops);
 	}
 
-	*psci_ops = &sunxi_psci_ops;
-
 	return 0;
 }
diff --git a/plat/allwinner/common/sunxi_scpi_pm.c b/plat/allwinner/common/sunxi_scpi_pm.c
new file mode 100644
index 0000000..eb37daa
--- /dev/null
+++ b/plat/allwinner/common/sunxi_scpi_pm.c
@@ -0,0 +1,222 @@
+/*
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <platform_def.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/arm/css/css_scpi.h>
+#include <drivers/arm/gicv2.h>
+#include <lib/mmio.h>
+#include <lib/psci/psci.h>
+
+#include <sunxi_mmap.h>
+#include <sunxi_private.h>
+
+/*
+ * The addresses for the SCP exception vectors are defined in the or1k
+ * architecture specification.
+ */
+#define OR1K_VEC_FIRST			0x01
+#define OR1K_VEC_LAST			0x0e
+#define OR1K_VEC_ADDR(n)		(0x100 * (n))
+
+/*
+ * This magic value is the little-endian representation of the or1k
+ * instruction "l.mfspr r2, r0, 0x12", which is guaranteed to be the
+ * first instruction in the SCP firmware.
+ */
+#define SCP_FIRMWARE_MAGIC		0xb4400012
+
+#define CPU_PWR_LVL			MPIDR_AFFLVL0
+#define CLUSTER_PWR_LVL			MPIDR_AFFLVL1
+#define SYSTEM_PWR_LVL			MPIDR_AFFLVL2
+
+#define CPU_PWR_STATE(state) \
+	((state)->pwr_domain_state[CPU_PWR_LVL])
+#define CLUSTER_PWR_STATE(state) \
+	((state)->pwr_domain_state[CLUSTER_PWR_LVL])
+#define SYSTEM_PWR_STATE(state) \
+	((state)->pwr_domain_state[SYSTEM_PWR_LVL])
+
+static inline scpi_power_state_t scpi_map_state(plat_local_state_t psci_state)
+{
+	if (is_local_state_run(psci_state)) {
+		return scpi_power_on;
+	}
+	if (is_local_state_retn(psci_state)) {
+		return scpi_power_retention;
+	}
+	return scpi_power_off;
+}
+
+static void sunxi_cpu_standby(plat_local_state_t cpu_state)
+{
+	u_register_t scr = read_scr_el3();
+
+	assert(is_local_state_retn(cpu_state));
+
+	write_scr_el3(scr | SCR_IRQ_BIT);
+	wfi();
+	write_scr_el3(scr);
+}
+
+static int sunxi_pwr_domain_on(u_register_t mpidr)
+{
+	scpi_set_css_power_state(mpidr,
+				 scpi_power_on,
+				 scpi_power_on,
+				 scpi_power_on);
+
+	return PSCI_E_SUCCESS;
+}
+
+static void sunxi_pwr_domain_off(const psci_power_state_t *target_state)
+{
+	plat_local_state_t cpu_pwr_state     = CPU_PWR_STATE(target_state);
+	plat_local_state_t cluster_pwr_state = CLUSTER_PWR_STATE(target_state);
+	plat_local_state_t system_pwr_state  = SYSTEM_PWR_STATE(target_state);
+
+	if (is_local_state_off(cpu_pwr_state)) {
+		gicv2_cpuif_disable();
+	}
+
+	scpi_set_css_power_state(read_mpidr(),
+				 scpi_map_state(cpu_pwr_state),
+				 scpi_map_state(cluster_pwr_state),
+				 scpi_map_state(system_pwr_state));
+}
+
+static void sunxi_pwr_domain_on_finish(const psci_power_state_t *target_state)
+{
+	if (is_local_state_off(SYSTEM_PWR_STATE(target_state))) {
+		gicv2_distif_init();
+	}
+	if (is_local_state_off(CPU_PWR_STATE(target_state))) {
+		gicv2_pcpu_distif_init();
+		gicv2_cpuif_enable();
+	}
+}
+
+static void __dead2 sunxi_system_off(void)
+{
+	uint32_t ret;
+
+	gicv2_cpuif_disable();
+
+	/* Send the power down request to the SCP. */
+	ret = scpi_sys_power_state(scpi_system_shutdown);
+	if (ret != SCP_OK) {
+		ERROR("PSCI: SCPI %s failed: %d\n", "shutdown", ret);
+	}
+
+	psci_power_down_wfi();
+}
+
+static void __dead2 sunxi_system_reset(void)
+{
+	uint32_t ret;
+
+	gicv2_cpuif_disable();
+
+	/* Send the system reset request to the SCP. */
+	ret = scpi_sys_power_state(scpi_system_reboot);
+	if (ret != SCP_OK) {
+		ERROR("PSCI: SCPI %s failed: %d\n", "reboot", ret);
+	}
+
+	psci_power_down_wfi();
+}
+
+static int sunxi_validate_power_state(unsigned int power_state,
+				      psci_power_state_t *req_state)
+{
+	unsigned int power_level = psci_get_pstate_pwrlvl(power_state);
+	unsigned int type = psci_get_pstate_type(power_state);
+
+	assert(req_state != NULL);
+
+	if (power_level > PLAT_MAX_PWR_LVL) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	if (type == PSTATE_TYPE_STANDBY) {
+		/* Only one retention power state is supported. */
+		if (psci_get_pstate_id(power_state) > 0) {
+			return PSCI_E_INVALID_PARAMS;
+		}
+		/* The SoC cannot be suspended without losing state */
+		if (power_level == SYSTEM_PWR_LVL) {
+			return PSCI_E_INVALID_PARAMS;
+		}
+		for (unsigned int i = 0; i <= power_level; ++i) {
+			req_state->pwr_domain_state[i] = PLAT_MAX_RET_STATE;
+		}
+	} else {
+		/* Only one off power state is supported. */
+		if (psci_get_pstate_id(power_state) > 0) {
+			return PSCI_E_INVALID_PARAMS;
+		}
+		for (unsigned int i = 0; i <= power_level; ++i) {
+			req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
+		}
+	}
+	/* Higher power domain levels should all remain running */
+	for (unsigned int i = power_level + 1; i <= PLAT_MAX_PWR_LVL; ++i) {
+		req_state->pwr_domain_state[i] = PSCI_LOCAL_STATE_RUN;
+	}
+
+	return PSCI_E_SUCCESS;
+}
+
+static void sunxi_get_sys_suspend_power_state(psci_power_state_t *req_state)
+{
+	assert(req_state != NULL);
+
+	for (unsigned int i = 0; i <= PLAT_MAX_PWR_LVL; ++i) {
+		req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
+	}
+}
+
+static const plat_psci_ops_t sunxi_scpi_psci_ops = {
+	.cpu_standby			= sunxi_cpu_standby,
+	.pwr_domain_on			= sunxi_pwr_domain_on,
+	.pwr_domain_off			= sunxi_pwr_domain_off,
+	.pwr_domain_suspend		= sunxi_pwr_domain_off,
+	.pwr_domain_on_finish		= sunxi_pwr_domain_on_finish,
+	.pwr_domain_suspend_finish	= sunxi_pwr_domain_on_finish,
+	.system_off			= sunxi_system_off,
+	.system_reset			= sunxi_system_reset,
+	.validate_power_state		= sunxi_validate_power_state,
+	.validate_ns_entrypoint		= sunxi_validate_ns_entrypoint,
+	.get_sys_suspend_power_state	= sunxi_get_sys_suspend_power_state,
+};
+
+int sunxi_set_scpi_psci_ops(const plat_psci_ops_t **psci_ops)
+{
+	*psci_ops = &sunxi_scpi_psci_ops;
+
+	/* Check for a valid SCP firmware. */
+	if (mmio_read_32(SUNXI_SCP_BASE) != SCP_FIRMWARE_MAGIC) {
+		return -1;
+	}
+
+	/* Program SCP exception vectors to the firmware entrypoint. */
+	for (unsigned int i = OR1K_VEC_FIRST; i <= OR1K_VEC_LAST; ++i) {
+		uint32_t vector = SUNXI_SRAM_A2_BASE + OR1K_VEC_ADDR(i);
+		uint32_t offset = SUNXI_SCP_BASE - vector;
+
+		mmio_write_32(vector, offset >> 2);
+	}
+
+	/* Take the SCP out of reset. */
+	mmio_setbits_32(SUNXI_R_CPUCFG_BASE, BIT(0));
+
+	/* Wait for the SCP firmware to boot. */
+	return scpi_wait_ready();
+}
diff --git a/plat/allwinner/common/sunxi_security.c b/plat/allwinner/common/sunxi_security.c
index 92c83b0..98b91c3 100644
--- a/plat/allwinner/common/sunxi_security.c
+++ b/plat/allwinner/common/sunxi_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,16 +7,11 @@
 #include <common/debug.h>
 #include <lib/mmio.h>
 
+#include <sunxi_ccu.h>
 #include <sunxi_mmap.h>
 #include <sunxi_private.h>
+#include <sunxi_spc.h>
 
-#ifdef SUNXI_SPC_BASE
-#define SPC_DECPORT_STA_REG(p)	(SUNXI_SPC_BASE + ((p) * 0x0c) + 0x4)
-#define SPC_DECPORT_SET_REG(p)	(SUNXI_SPC_BASE + ((p) * 0x0c) + 0x8)
-#define SPC_DECPORT_CLR_REG(p)	(SUNXI_SPC_BASE + ((p) * 0x0c) + 0xc)
-#endif
-
-#define R_PRCM_SEC_SWITCH_REG	0x1d0
 #define DMA_SEC_REG		0x20
 
 /*
@@ -27,20 +22,18 @@
  */
 void sunxi_security_setup(void)
 {
-#ifdef SUNXI_SPC_BASE
 	int i;
 
 	INFO("Configuring SPC Controller\n");
 	/* SPC setup: set all devices to non-secure */
-	for (i = 0; i < 6; i++)
-		mmio_write_32(SPC_DECPORT_SET_REG(i), 0xff);
-#endif
+	for (i = 0; i < SUNXI_SPC_NUM_PORTS; i++)
+		mmio_write_32(SUNXI_SPC_DECPORT_SET_REG(i), 0xffffffff);
 
 	/* set MBUS clocks, bus clocks (AXI/AHB/APB) and PLLs to non-secure */
 	mmio_write_32(SUNXI_CCU_SEC_SWITCH_REG, 0x7);
 
 	/* Set R_PRCM bus clocks to non-secure */
-	mmio_write_32(SUNXI_R_PRCM_BASE + R_PRCM_SEC_SWITCH_REG, 0x1);
+	mmio_write_32(SUNXI_R_PRCM_SEC_SWITCH_REG, 0x1);
 
 	/* Set all DMA channels (16 max.) to non-secure */
 	mmio_write_32(SUNXI_DMA_BASE + DMA_SEC_REG, 0xffff);
diff --git a/plat/allwinner/sun50i_a64/include/sunxi_ccu.h b/plat/allwinner/sun50i_a64/include/sunxi_ccu.h
new file mode 100644
index 0000000..2a24886
--- /dev/null
+++ b/plat/allwinner/sun50i_a64/include/sunxi_ccu.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CCU_H
+#define SUNXI_CCU_H
+
+#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0x02f0)
+
+#define SUNXI_R_PRCM_SEC_SWITCH_REG	(SUNXI_R_PRCM_BASE + 0x01d0)
+
+#endif /* SUNXI_CCU_H */
diff --git a/plat/allwinner/sun50i_a64/include/sunxi_cpucfg.h b/plat/allwinner/sun50i_a64/include/sunxi_cpucfg.h
index c3eeadb..aed3585 100644
--- a/plat/allwinner/sun50i_a64/include/sunxi_cpucfg.h
+++ b/plat/allwinner/sun50i_a64/include/sunxi_cpucfg.h
@@ -33,4 +33,7 @@
 #define SUNXI_R_CPUCFG_SS_ENTRY_REG	(SUNXI_R_CPUCFG_BASE + 0x01a8)
 #define SUNXI_R_CPUCFG_HP_FLAG_REG	(SUNXI_R_CPUCFG_BASE + 0x01ac)
 
+#define SUNXI_AA64nAA32_REG		SUNXI_CPUCFG_CLS_CTRL_REG0
+#define SUNXI_AA64nAA32_OFFSET		24
+
 #endif /* SUNXI_CPUCFG_H */
diff --git a/plat/allwinner/sun50i_a64/include/sunxi_mmap.h b/plat/allwinner/sun50i_a64/include/sunxi_mmap.h
index 9d2542f..6d10921 100644
--- a/plat/allwinner/sun50i_a64/include/sunxi_mmap.h
+++ b/plat/allwinner/sun50i_a64/include/sunxi_mmap.h
@@ -15,6 +15,7 @@
 #define SUNXI_SRAM_A1_BASE		0x00010000
 #define SUNXI_SRAM_A1_SIZE		0x00008000
 #define SUNXI_SRAM_A2_BASE		0x00040000
+#define SUNXI_SRAM_A2_BL31_OFFSET	0x00004000
 #define SUNXI_SRAM_A2_SIZE		0x00014000
 #define SUNXI_SRAM_C_BASE		0x00018000
 #define SUNXI_SRAM_C_SIZE		0x0001c000
@@ -36,7 +37,6 @@
 #define SUNXI_MSGBOX_BASE		0x01c17000
 #define SUNXI_SPINLOCK_BASE		0x01c18000
 #define SUNXI_CCU_BASE			0x01c20000
-#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0x2f0)
 #define SUNXI_PIO_BASE			0x01c20800
 #define SUNXI_TIMER_BASE		0x01c20c00
 #define SUNXI_WDOG_BASE			0x01c20ca0
diff --git a/plat/allwinner/sun50i_a64/include/sunxi_spc.h b/plat/allwinner/sun50i_a64/include/sunxi_spc.h
new file mode 100644
index 0000000..5ba7e18
--- /dev/null
+++ b/plat/allwinner/sun50i_a64/include/sunxi_spc.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_SPC_H
+#define SUNXI_SPC_H
+
+#define SUNXI_SPC_NUM_PORTS		6
+
+#define SUNXI_SPC_DECPORT_STA_REG(p)	(SUNXI_SPC_BASE + 0x0004 + 0x0c * (p))
+#define SUNXI_SPC_DECPORT_SET_REG(p)	(SUNXI_SPC_BASE + 0x0008 + 0x0c * (p))
+#define SUNXI_SPC_DECPORT_CLR_REG(p)	(SUNXI_SPC_BASE + 0x000c + 0x0c * (p))
+
+#endif /* SUNXI_SPC_H */
diff --git a/plat/allwinner/sun50i_a64/platform.mk b/plat/allwinner/sun50i_a64/platform.mk
index f6d5aa9..e3c7c52 100644
--- a/plat/allwinner/sun50i_a64/platform.mk
+++ b/plat/allwinner/sun50i_a64/platform.mk
@@ -9,3 +9,9 @@
 
 BL31_SOURCES		+=	drivers/allwinner/axp/axp803.c		\
 				drivers/allwinner/sunxi_rsb.c
+
+FDT_ASSUME_MASK := "(ASSUME_LATEST | ASSUME_NO_ROLLBACK | ASSUME_LIBFDT_ORDER)"
+$(eval $(call add_define,FDT_ASSUME_MASK))
+
+# Put NOBITS memory in SRAM A1, overwriting U-Boot's SPL.
+SEPARATE_NOBITS_REGION	:=	1
diff --git a/plat/allwinner/sun50i_a64/sunxi_power.c b/plat/allwinner/sun50i_a64/sunxi_power.c
index 5b7d76a..a35b9dd 100644
--- a/plat/allwinner/sun50i_a64/sunxi_power.c
+++ b/plat/allwinner/sun50i_a64/sunxi_power.c
@@ -14,6 +14,7 @@
 #include <drivers/allwinner/sunxi_rsb.h>
 #include <lib/mmio.h>
 
+#include <core_off_arisc.h>
 #include <sunxi_def.h>
 #include <sunxi_mmap.h>
 #include <sunxi_private.h>
@@ -92,24 +93,16 @@
 	if (ret)
 		return ret;
 
-	/* Start with 400 KHz to issue the I2C->RSB switch command. */
-	ret = rsb_set_bus_speed(SUNXI_OSC24M_CLK_IN_HZ, 400000);
-	if (ret)
-		return ret;
-
-	/*
-	 * Initiate an I2C transaction to write 0x7c into register 0x3e,
-	 * switching the PMIC to RSB mode.
-	 */
-	ret = rsb_set_device_mode(0x7c3e00);
-	if (ret)
-		return ret;
-
-	/* Now in RSB mode, switch to the recommended 3 MHz. */
+	/* Switch to the recommended 3 MHz bus clock. */
 	ret = rsb_set_bus_speed(SUNXI_OSC24M_CLK_IN_HZ, 3000000);
 	if (ret)
 		return ret;
 
+	/* Initiate an I2C transaction to switch the PMIC to RSB mode. */
+	ret = rsb_set_device_mode(AXP20X_MODE_RSB << 16 | AXP20X_MODE_REG << 8);
+	if (ret)
+		return ret;
+
 	/* Associate the 8-bit runtime address with the 12-bit bus address. */
 	ret = rsb_assign_runtime_address(AXP803_HW_ADDR,
 					 AXP803_RT_ADDR);
@@ -156,6 +149,11 @@
 		pmic = AXP803_RSB;
 		axp_setup_regulators(fdt);
 
+		/* Switch the PMIC back to I2C mode. */
+		ret = axp_write(AXP20X_MODE_REG, AXP20X_MODE_I2C);
+		if (ret)
+			return ret;
+
 		break;
 	default:
 		return -ENODEV;
@@ -208,3 +206,54 @@
 	}
 
 }
+
+/* This lock synchronises access to the arisc management processor. */
+static DEFINE_BAKERY_LOCK(arisc_lock);
+
+/*
+ * If we are supposed to turn ourself off, tell the arisc SCP to do that
+ * work for us. Without any SCPI provider running there, we place some
+ * OpenRISC code into SRAM, put the address of that into the reset vector
+ * and release the arisc reset line. The SCP will wait for the core to enter
+ * WFI, then execute that code and pull the line up again.
+ * The code expects the core mask to be patched into the first instruction.
+ */
+void sunxi_cpu_power_off_self(void)
+{
+	u_register_t mpidr = read_mpidr();
+	unsigned int core  = MPIDR_AFFLVL0_VAL(mpidr);
+	uintptr_t arisc_reset_vec = SUNXI_SRAM_A2_BASE + 0x100;
+	uint32_t *code = arisc_core_off;
+
+	do {
+		bakery_lock_get(&arisc_lock);
+		/* Wait until the arisc is in reset state. */
+		if (!(mmio_read_32(SUNXI_R_CPUCFG_BASE) & BIT(0)))
+			break;
+
+		bakery_lock_release(&arisc_lock);
+	} while (1);
+
+	/* Patch up the code to feed in an input parameter. */
+	code[0] = (code[0] & ~0xffff) | BIT_32(core);
+	clean_dcache_range((uintptr_t)code, sizeof(arisc_core_off));
+
+	/*
+	 * The OpenRISC unconditional branch has opcode 0, the branch offset
+	 * is in the lower 26 bits, containing the distance to the target,
+	 * in instruction granularity (32 bits).
+	 */
+	mmio_write_32(arisc_reset_vec, ((uintptr_t)code - arisc_reset_vec) / 4);
+
+	/* De-assert the arisc reset line to let it run. */
+	mmio_setbits_32(SUNXI_R_CPUCFG_BASE, BIT(0));
+
+	/*
+	 * We release the lock here, although the arisc is still busy.
+	 * But as long as it runs, the reset line is high, so other users
+	 * won't leave the loop above.
+	 * Once it has finished, the code is supposed to clear the reset line,
+	 * to signal this to other users.
+	 */
+	bakery_lock_release(&arisc_lock);
+}
diff --git a/plat/allwinner/sun50i_h6/include/core_off_arisc.h b/plat/allwinner/sun50i_h6/include/core_off_arisc.h
deleted file mode 100644
index 63a5d8d..0000000
--- a/plat/allwinner/sun50i_h6/include/core_off_arisc.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-static uint32_t arisc_core_off[] = {
-	0x18600000, /* l.movhi	r3, <corenr>	*/
-	0x18000000, /* l.movhi	r0, 0x0		*/
-	0x19a00901, /* l.movhi	r13, 0x901	*/
-	0x84ad0080, /* l.lwz	r5, 0x80(r13)	*/
-	0xe0a51803, /* l.and	r5, r5, r3	*/
-	0xe4050000, /* l.sfeq	r5, r0		*/
-	0x13fffffd, /* l.bf	-12		*/
-	0xb8c30050, /* l.srli	r6, r3, 16	*/
-
-	0xbc060001, /* l.sfeqi	r6, 1		*/
-	0x10000005, /* l.bf	+20		*/
-	0x19a00700, /* l.movhi	r13, 0x700	*/
-	0x84ad0444, /* l.lwz	r5, 0x0444(r13)	*/
-	0xe0a53004, /* l.or	r5, r5, r6	*/
-	0xd40d2c44, /* l.sw	0x0444(r13), r5	*/
-
-	0x84ad0440, /* l.lwz	r5, 0x0440(r13)	*/
-	0xacc6ffff, /* l.xori	r6, r6, -1	*/
-	0xe0a53003, /* l.and	r5, r5, r6	*/
-	0xd40d2c40, /* l.sw	0x0440(r13), r5	*/
-
-	0xe0c3000f, /* l.ff1	r6, r3		*/
-	0x9cc6ffef, /* l.addi	r6, r6, -17	*/
-	0xb8c60002, /* l.slli	r6, r6, 2	*/
-	0xe0c66800, /* l.add	r6, r6, r13	*/
-	0xa8a000ff, /* l.ori	r5, r0, 0xff	*/
-	0xd4062c50, /* l.sw	0x0450(r6), r5	*/
-
-	0xd40d0400, /* l.sw	0x0400(r13), r0	*/
-	0x03ffffff, /* l.j	-1		*/
-	0x15000000, /* l.nop			*/
-};
diff --git a/plat/allwinner/sun50i_h6/include/sunxi_ccu.h b/plat/allwinner/sun50i_h6/include/sunxi_ccu.h
new file mode 100644
index 0000000..85fbb90
--- /dev/null
+++ b/plat/allwinner/sun50i_h6/include/sunxi_ccu.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CCU_H
+#define SUNXI_CCU_H
+
+#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0x0f00)
+
+#define SUNXI_R_PRCM_SEC_SWITCH_REG	(SUNXI_R_PRCM_BASE + 0x0290)
+
+#endif /* SUNXI_CCU_H */
diff --git a/plat/allwinner/sun50i_h6/include/sunxi_cpucfg.h b/plat/allwinner/sun50i_h6/include/sunxi_cpucfg.h
index 556fb97..5bfda5d 100644
--- a/plat/allwinner/sun50i_h6/include/sunxi_cpucfg.h
+++ b/plat/allwinner/sun50i_h6/include/sunxi_cpucfg.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -24,4 +24,12 @@
 #define SUNXI_CPU_POWER_CLAMP_REG(c, n)	(SUNXI_R_CPUCFG_BASE + 0x0050 + \
 					(c) * 0x10 + (n) * 4)
 
+#define SUNXI_CPUIDLE_EN_REG		(SUNXI_R_CPUCFG_BASE + 0x0100)
+#define SUNXI_CORE_CLOSE_REG		(SUNXI_R_CPUCFG_BASE + 0x0104)
+#define SUNXI_PWR_SW_DELAY_REG		(SUNXI_R_CPUCFG_BASE + 0x0140)
+#define SUNXI_CONFIG_DELAY_REG		(SUNXI_R_CPUCFG_BASE + 0x0144)
+
+#define SUNXI_AA64nAA32_REG		SUNXI_CPUCFG_CLS_CTRL_REG0
+#define SUNXI_AA64nAA32_OFFSET		24
+
 #endif /* SUNXI_CPUCFG_H */
diff --git a/plat/allwinner/sun50i_h6/include/sunxi_mmap.h b/plat/allwinner/sun50i_h6/include/sunxi_mmap.h
index 702db77..58216d8 100644
--- a/plat/allwinner/sun50i_h6/include/sunxi_mmap.h
+++ b/plat/allwinner/sun50i_h6/include/sunxi_mmap.h
@@ -15,6 +15,7 @@
 #define SUNXI_SRAM_A1_BASE		0x00020000
 #define SUNXI_SRAM_A1_SIZE		0x00008000
 #define SUNXI_SRAM_A2_BASE		0x00100000
+#define SUNXI_SRAM_A2_BL31_OFFSET	0x00004000
 #define SUNXI_SRAM_A2_SIZE		0x00018000
 #define SUNXI_SRAM_C_BASE		0x00028000
 #define SUNXI_SRAM_C_SIZE		0x0001e000
@@ -30,8 +31,8 @@
 #define SUNXI_DMA_BASE			0x03002000
 #define SUNXI_MSGBOX_BASE		0x03003000
 #define SUNXI_CCU_BASE			0x03001000
-#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0xf00)
 #define SUNXI_PIO_BASE			0x0300b000
+#define SUNXI_SPC_BASE			0x03008000
 #define SUNXI_TIMER_BASE		0x03009000
 #define SUNXI_WDOG_BASE			0x030090a0
 #define SUNXI_THS_BASE			0x05070400
@@ -55,6 +56,7 @@
 #define SUNXI_R_TWD_BASE		0x07020800
 #define SUNXI_R_CPUCFG_BASE		0x07000400
 #define SUNXI_R_I2C_BASE		0x07081400
+#define SUNXI_R_RSB_BASE		0x07083000
 #define SUNXI_R_UART_BASE		0x07080000
 #define SUNXI_R_PIO_BASE		0x07022000
 
diff --git a/plat/allwinner/sun50i_h6/include/sunxi_spc.h b/plat/allwinner/sun50i_h6/include/sunxi_spc.h
new file mode 100644
index 0000000..0f5965b
--- /dev/null
+++ b/plat/allwinner/sun50i_h6/include/sunxi_spc.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_SPC_H
+#define SUNXI_SPC_H
+
+#define SUNXI_SPC_NUM_PORTS		14
+
+#define SUNXI_SPC_DECPORT_STA_REG(p)	(SUNXI_SPC_BASE + 0x0000 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_SET_REG(p)	(SUNXI_SPC_BASE + 0x0004 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_CLR_REG(p)	(SUNXI_SPC_BASE + 0x0008 + 0x10 * (p))
+
+#endif /* SUNXI_SPC_H */
diff --git a/plat/allwinner/sun50i_h6/platform.mk b/plat/allwinner/sun50i_h6/platform.mk
index 4ecc57c..e13e8cb 100644
--- a/plat/allwinner/sun50i_h6/platform.mk
+++ b/plat/allwinner/sun50i_h6/platform.mk
@@ -8,4 +8,7 @@
 include plat/allwinner/common/allwinner-common.mk
 
 BL31_SOURCES		+=	drivers/allwinner/axp/axp805.c		\
-				drivers/mentor/i2c/mi2cv.c
+				drivers/allwinner/sunxi_rsb.c
+
+# Put NOBITS memory in SRAM A1, overwriting U-Boot's SPL.
+SEPARATE_NOBITS_REGION	:=	1
diff --git a/plat/allwinner/sun50i_h6/sunxi_power.c b/plat/allwinner/sun50i_h6/sunxi_power.c
index 443015b..d298e6b 100644
--- a/plat/allwinner/sun50i_h6/sunxi_power.c
+++ b/plat/allwinner/sun50i_h6/sunxi_power.c
@@ -6,20 +6,19 @@
  */
 
 #include <errno.h>
-#include <string.h>
 
-#include <arch_helpers.h>
 #include <common/debug.h>
 #include <drivers/allwinner/axp.h>
-#include <drivers/delay_timer.h>
-#include <drivers/mentor/mi2cv.h>
+#include <drivers/allwinner/sunxi_rsb.h>
 #include <lib/mmio.h>
 
+#include <sunxi_cpucfg.h>
 #include <sunxi_def.h>
 #include <sunxi_mmap.h>
 #include <sunxi_private.h>
 
-#define AXP805_ADDR	0x36
+#define AXP805_HW_ADDR	0x745
+#define AXP805_RT_ADDR	0x3a
 
 static enum pmic_type {
 	UNKNOWN,
@@ -28,67 +27,67 @@
 
 int axp_read(uint8_t reg)
 {
-	uint8_t val;
-	int ret;
-
-	ret = i2c_write(AXP805_ADDR, 0, 0, &reg, 1);
-	if (ret == 0)
-		ret = i2c_read(AXP805_ADDR, 0, 0, &val, 1);
-	if (ret) {
-		ERROR("PMIC: Cannot read AXP805 register %02x\n", reg);
-		return ret;
-	}
-
-	return val;
+	return rsb_read(AXP805_RT_ADDR, reg);
 }
 
 int axp_write(uint8_t reg, uint8_t val)
 {
-	int ret;
-
-	ret = i2c_write(AXP805_ADDR, reg, 1, &val, 1);
-	if (ret)
-		ERROR("PMIC: Cannot write AXP805 register %02x\n", reg);
-
-	return ret;
+	return rsb_write(AXP805_RT_ADDR, reg, val);
 }
 
-static int axp805_probe(void)
+static int rsb_init(void)
 {
 	int ret;
 
-	/* Switch the AXP805 to master/single-PMIC mode. */
-	ret = axp_write(0xff, 0x0);
+	ret = rsb_init_controller();
 	if (ret)
 		return ret;
 
-	ret = axp_check_id();
+	/* Switch to the recommended 3 MHz bus clock. */
+	ret = rsb_set_bus_speed(SUNXI_OSC24M_CLK_IN_HZ, 3000000);
 	if (ret)
 		return ret;
 
-	return 0;
+	/* Initiate an I2C transaction to switch the PMIC to RSB mode. */
+	ret = rsb_set_device_mode(AXP20X_MODE_RSB << 16 | AXP20X_MODE_REG << 8);
+	if (ret)
+		return ret;
+
+	/* Associate the 8-bit runtime address with the 12-bit bus address. */
+	ret = rsb_assign_runtime_address(AXP805_HW_ADDR, AXP805_RT_ADDR);
+	if (ret)
+		return ret;
+
+	return axp_check_id();
 }
 
 int sunxi_pmic_setup(uint16_t socid, const void *fdt)
 {
 	int ret;
 
-	INFO("PMIC: Probing AXP805 on I2C\n");
+	INFO("PMIC: Probing AXP805 on RSB\n");
 
-	ret = sunxi_init_platform_r_twi(SUNXI_SOC_H6, false);
+	ret = sunxi_init_platform_r_twi(socid, true);
 	if (ret)
 		return ret;
 
-	/* initialise mi2cv driver */
-	i2c_init((void *)SUNXI_R_I2C_BASE);
+	ret = rsb_init();
+	if (ret)
+		return ret;
 
-	ret = axp805_probe();
+	/* Switch the AXP805 to master/single-PMIC mode. */
+	ret = axp_write(0xff, 0x0);
 	if (ret)
 		return ret;
 
 	pmic = AXP805;
 	axp_setup_regulators(fdt);
 
+	/* Switch the PMIC back to I2C mode. */
+	ret = axp_write(AXP20X_MODE_REG, AXP20X_MODE_I2C);
+	if (ret)
+		return ret;
+
 	return 0;
 }
 
@@ -96,13 +95,25 @@
 {
 	switch (pmic) {
 	case AXP805:
-		/* Re-initialise after rich OS might have used it. */
-		sunxi_init_platform_r_twi(SUNXI_SOC_H6, false);
-		/* initialise mi2cv driver */
-		i2c_init((void *)SUNXI_R_I2C_BASE);
+		/* (Re-)init RSB in case the rich OS has disabled it. */
+		sunxi_init_platform_r_twi(SUNXI_SOC_H6, true);
+		rsb_init();
 		axp_power_off();
 		break;
 	default:
 		break;
 	}
 }
+
+void sunxi_cpu_power_off_self(void)
+{
+	u_register_t mpidr = read_mpidr();
+	unsigned int core  = MPIDR_AFFLVL0_VAL(mpidr);
+
+	/* Enable the CPUIDLE hardware (only really needs to be done once). */
+	mmio_write_32(SUNXI_CPUIDLE_EN_REG, 0x16aa0000);
+	mmio_write_32(SUNXI_CPUIDLE_EN_REG, 0xaa160001);
+
+	/* Trigger power off for this core. */
+	mmio_write_32(SUNXI_CORE_CLOSE_REG, BIT_32(core));
+}
diff --git a/plat/allwinner/sun50i_h616/include/sunxi_ccu.h b/plat/allwinner/sun50i_h616/include/sunxi_ccu.h
new file mode 100644
index 0000000..85fbb90
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/include/sunxi_ccu.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CCU_H
+#define SUNXI_CCU_H
+
+#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0x0f00)
+
+#define SUNXI_R_PRCM_SEC_SWITCH_REG	(SUNXI_R_PRCM_BASE + 0x0290)
+
+#endif /* SUNXI_CCU_H */
diff --git a/plat/allwinner/sun50i_h616/include/sunxi_cpucfg.h b/plat/allwinner/sun50i_h616/include/sunxi_cpucfg.h
new file mode 100644
index 0000000..dab663b
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/include/sunxi_cpucfg.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2017-2020, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CPUCFG_H
+#define SUNXI_CPUCFG_H
+
+#include <sunxi_mmap.h>
+
+/* c = cluster, n = core */
+#define SUNXI_CPUCFG_CLS_CTRL_REG0(c)	(SUNXI_CPUCFG_BASE + 0x0010 + (c) * 0x10)
+#define SUNXI_CPUCFG_CLS_CTRL_REG1(c)	(SUNXI_CPUCFG_BASE + 0x0014 + (c) * 0x10)
+#define SUNXI_CPUCFG_CACHE_CFG_REG	(SUNXI_CPUCFG_BASE + 0x0024)
+#define SUNXI_CPUCFG_DBG_REG0		(SUNXI_CPUCFG_BASE + 0x00c0)
+
+#define SUNXI_CPUCFG_RST_CTRL_REG(c)	(SUNXI_CPUCFG_BASE + 0x0000 + (c) * 4)
+#define SUNXI_CPUCFG_RVBAR_LO_REG(n)	(SUNXI_CPUCFG_BASE + 0x0040 + (n) * 8)
+#define SUNXI_CPUCFG_RVBAR_HI_REG(n)	(SUNXI_CPUCFG_BASE + 0x0044 + (n) * 8)
+
+#define SUNXI_POWERON_RST_REG(c)	(SUNXI_R_CPUCFG_BASE + 0x0040 + (c) * 4)
+#define SUNXI_POWEROFF_GATING_REG(c)	(SUNXI_R_CPUCFG_BASE + 0x0044 + (c) * 4)
+#define SUNXI_CPU_POWER_CLAMP_REG(c, n)	(SUNXI_R_CPUCFG_BASE + 0x0050 + \
+					(c) * 0x10 + (n) * 4)
+
+#define SUNXI_CPUIDLE_EN_REG		(SUNXI_R_CPUCFG_BASE + 0x0100)
+#define SUNXI_CORE_CLOSE_REG		(SUNXI_R_CPUCFG_BASE + 0x0104)
+#define SUNXI_PWR_SW_DELAY_REG		(SUNXI_R_CPUCFG_BASE + 0x0140)
+#define SUNXI_CONFIG_DELAY_REG		(SUNXI_R_CPUCFG_BASE + 0x0144)
+
+#define SUNXI_AA64nAA32_REG		SUNXI_CPUCFG_CLS_CTRL_REG0
+#define SUNXI_AA64nAA32_OFFSET		24
+
+#endif /* SUNXI_CPUCFG_H */
diff --git a/plat/allwinner/sun50i_h616/include/sunxi_mmap.h b/plat/allwinner/sun50i_h616/include/sunxi_mmap.h
new file mode 100644
index 0000000..3b4f4a0
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/include/sunxi_mmap.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_MMAP_H
+#define SUNXI_MMAP_H
+
+/* Memory regions */
+#define SUNXI_ROM_BASE			0x00000000
+#define SUNXI_ROM_SIZE			0x00010000
+#define SUNXI_SRAM_BASE			0x00020000
+#define SUNXI_SRAM_SIZE			0x00038000
+#define SUNXI_SRAM_A1_BASE		0x00020000
+#define SUNXI_SRAM_A1_SIZE		0x00008000
+#define SUNXI_SRAM_C_BASE		0x00028000
+#define SUNXI_SRAM_C_SIZE		0x00030000
+#define SUNXI_DEV_BASE			0x01000000
+#define SUNXI_DEV_SIZE			0x09000000
+#define SUNXI_DRAM_BASE			0x40000000
+#define SUNXI_DRAM_VIRT_BASE		SUNXI_DRAM_BASE
+
+/* Memory-mapped devices */
+#define SUNXI_SYSCON_BASE		0x03000000
+#define SUNXI_CCU_BASE			0x03001000
+#define SUNXI_DMA_BASE			0x03002000
+#define SUNXI_SID_BASE			0x03006000
+#define SUNXI_SPC_BASE			0x03008000
+#define SUNXI_WDOG_BASE			0x030090a0
+#define SUNXI_PIO_BASE			0x0300b000
+#define SUNXI_GICD_BASE			0x03021000
+#define SUNXI_GICC_BASE			0x03022000
+#define SUNXI_UART0_BASE		0x05000000
+#define SUNXI_SPI0_BASE			0x05010000
+#define SUNXI_R_CPUCFG_BASE		0x07000400
+#define SUNXI_R_PRCM_BASE		0x07010000
+//#define SUNXI_R_WDOG_BASE		0x07020400
+#define SUNXI_R_WDOG_BASE		SUNXI_WDOG_BASE
+#define SUNXI_R_PIO_BASE		0x07022000
+#define SUNXI_R_UART_BASE		0x07080000
+#define SUNXI_R_I2C_BASE		0x07081400
+#define SUNXI_R_RSB_BASE		0x07083000
+#define SUNXI_CPUCFG_BASE		0x09010000
+
+#endif /* SUNXI_MMAP_H */
diff --git a/plat/allwinner/sun50i_h616/include/sunxi_spc.h b/plat/allwinner/sun50i_h616/include/sunxi_spc.h
new file mode 100644
index 0000000..0f5965b
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/include/sunxi_spc.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_SPC_H
+#define SUNXI_SPC_H
+
+#define SUNXI_SPC_NUM_PORTS		14
+
+#define SUNXI_SPC_DECPORT_STA_REG(p)	(SUNXI_SPC_BASE + 0x0000 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_SET_REG(p)	(SUNXI_SPC_BASE + 0x0004 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_CLR_REG(p)	(SUNXI_SPC_BASE + 0x0008 + 0x10 * (p))
+
+#endif /* SUNXI_SPC_H */
diff --git a/plat/allwinner/sun50i_h616/platform.mk b/plat/allwinner/sun50i_h616/platform.mk
new file mode 100644
index 0000000..fc09af7
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/platform.mk
@@ -0,0 +1,24 @@
+#
+# Copyright (c) 2017-2020, ARM Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Without a management processor there is no SCPI support.
+SUNXI_PSCI_USE_SCPI	:=	0
+SUNXI_PSCI_USE_NATIVE	:=	1
+
+# The differences between the platforms are covered by the include files.
+include plat/allwinner/common/allwinner-common.mk
+
+# the above could be overwritten on the command line
+ifeq (${SUNXI_PSCI_USE_SCPI}, 1)
+    $(error "H616 does not support SCPI PSCI ops")
+endif
+
+BL31_SOURCES		+=	drivers/allwinner/axp/axp805.c		\
+				drivers/allwinner/sunxi_rsb.c		\
+				common/fdt_fixup.c			\
+				${AW_PLAT}/${PLAT}/prepare_dtb.c
+
+$(eval $(call add_define,SUNXI_BL31_IN_DRAM))
diff --git a/plat/allwinner/sun50i_h616/prepare_dtb.c b/plat/allwinner/sun50i_h616/prepare_dtb.c
new file mode 100644
index 0000000..e94b0b4
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/prepare_dtb.c
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <libfdt.h>
+
+#include <common/debug.h>
+#include <common/fdt_fixup.h>
+#include <common/fdt_wrappers.h>
+
+#include <sunxi_private.h>
+
+void sunxi_prepare_dtb(void *fdt)
+{
+	int ret;
+
+	if (fdt == NULL || fdt_check_header(fdt) != 0) {
+		return;
+	}
+	ret = fdt_open_into(fdt, fdt, 0x100000);
+	if (ret < 0) {
+		ERROR("Preparing devicetree at %p: error %d\n", fdt, ret);
+		return;
+	}
+
+	/* Reserve memory used by Trusted Firmware. */
+	if (fdt_add_reserved_memory(fdt, "tf-a@40000000", BL31_BASE,
+				    BL31_LIMIT - BL31_BASE)) {
+		WARN("Failed to add reserved memory nodes to DT.\n");
+		return;
+	}
+
+	ret = fdt_pack(fdt);
+	if (ret < 0) {
+		ERROR("Failed to pack devicetree at %p: error %d\n",
+		      fdt, ret);
+	} else {
+		clean_dcache_range((uintptr_t)fdt, fdt_blob_size(fdt));
+		INFO("Changed devicetree to reserve BL31 memory.\n");
+	}
+}
diff --git a/plat/allwinner/sun50i_h616/sunxi_power.c b/plat/allwinner/sun50i_h616/sunxi_power.c
new file mode 100644
index 0000000..dd6ebba
--- /dev/null
+++ b/plat/allwinner/sun50i_h616/sunxi_power.c
@@ -0,0 +1,121 @@
+/*
+ * Copyright (c) 2017-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2018, Icenowy Zheng <icenowy@aosc.io>
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/allwinner/axp.h>
+#include <drivers/allwinner/sunxi_rsb.h>
+#include <lib/mmio.h>
+
+#include <sunxi_cpucfg.h>
+#include <sunxi_def.h>
+#include <sunxi_mmap.h>
+#include <sunxi_private.h>
+
+#define AXP305_I2C_ADDR	0x36
+#define AXP305_HW_ADDR	0x745
+#define AXP305_RT_ADDR	0x3a
+
+static enum pmic_type {
+	UNKNOWN,
+	AXP305,
+} pmic;
+
+int axp_read(uint8_t reg)
+{
+	return rsb_read(AXP305_RT_ADDR, reg);
+}
+
+int axp_write(uint8_t reg, uint8_t val)
+{
+	return rsb_write(AXP305_RT_ADDR, reg, val);
+}
+
+static int rsb_init(void)
+{
+	int ret;
+
+	ret = rsb_init_controller();
+	if (ret)
+		return ret;
+
+	/* Switch to the recommended 3 MHz bus clock. */
+	ret = rsb_set_bus_speed(SUNXI_OSC24M_CLK_IN_HZ, 3000000);
+	if (ret)
+		return ret;
+
+	/* Initiate an I2C transaction to switch the PMIC to RSB mode. */
+	ret = rsb_set_device_mode(AXP20X_MODE_RSB << 16 | AXP20X_MODE_REG << 8);
+	if (ret)
+		return ret;
+
+	/* Associate the 8-bit runtime address with the 12-bit bus address. */
+	ret = rsb_assign_runtime_address(AXP305_HW_ADDR, AXP305_RT_ADDR);
+	if (ret)
+		return ret;
+
+	return axp_check_id();
+}
+
+int sunxi_pmic_setup(uint16_t socid, const void *fdt)
+{
+	int ret;
+
+	INFO("PMIC: Probing AXP305 on RSB\n");
+
+	ret = sunxi_init_platform_r_twi(socid, true);
+	if (ret) {
+		INFO("Could not init platform bus: %d\n", ret);
+		return ret;
+	}
+
+	ret = rsb_init();
+	if (ret) {
+		INFO("Could not init RSB: %d\n", ret);
+		return ret;
+	}
+
+	pmic = AXP305;
+	axp_setup_regulators(fdt);
+
+	/* Switch the PMIC back to I2C mode. */
+	ret = axp_write(AXP20X_MODE_REG, AXP20X_MODE_I2C);
+	if (ret)
+		return ret;
+
+	return 0;
+}
+
+void sunxi_power_down(void)
+{
+	switch (pmic) {
+	case AXP305:
+		/* Re-initialise after rich OS might have used it. */
+		sunxi_init_platform_r_twi(SUNXI_SOC_H616, true);
+		rsb_init();
+		axp_power_off();
+		break;
+	default:
+		break;
+	}
+}
+
+void sunxi_cpu_power_off_self(void)
+{
+	u_register_t mpidr = read_mpidr();
+	unsigned int core  = MPIDR_AFFLVL0_VAL(mpidr);
+
+	/* Enable the CPUIDLE hardware (only really needs to be done once). */
+	mmio_write_32(SUNXI_CPUIDLE_EN_REG, 0x16aa0000);
+	mmio_write_32(SUNXI_CPUIDLE_EN_REG, 0xaa160001);
+
+	/* Trigger power off for this core. */
+	mmio_write_32(SUNXI_CORE_CLOSE_REG, BIT_32(core));
+}
diff --git a/plat/allwinner/sun50i_r329/include/sunxi_ccu.h b/plat/allwinner/sun50i_r329/include/sunxi_ccu.h
new file mode 100644
index 0000000..0e6b543
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/include/sunxi_ccu.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2021 Sipeed
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CCU_H
+#define SUNXI_CCU_H
+
+#define SUNXI_CCU_SEC_SWITCH_REG	(SUNXI_CCU_BASE + 0x0f00)
+
+#define SUNXI_R_PRCM_SEC_SWITCH_REG	(SUNXI_R_PRCM_BASE + 0x0290)
+
+#endif /* SUNXI_CCU_H */
diff --git a/plat/allwinner/sun50i_r329/include/sunxi_cpucfg.h b/plat/allwinner/sun50i_r329/include/sunxi_cpucfg.h
new file mode 100644
index 0000000..9478f32
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/include/sunxi_cpucfg.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2021 Sipeed
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_CPUCFG_H
+#define SUNXI_CPUCFG_H
+
+#include <sunxi_mmap.h>
+
+/* c = cluster, n = core */
+#define SUNXI_CPUCFG_CLS_CTRL_REG0(c)	(SUNXI_C0_CPUXCFG_BASE + 0x0010)
+#define SUNXI_CPUCFG_CLS_CTRL_REG1(c)	(SUNXI_C0_CPUXCFG_BASE + 0x0014)
+#define SUNXI_CPUCFG_CACHE_CFG_REG	(SUNXI_C0_CPUXCFG_BASE + 0x0024)
+#define SUNXI_CPUCFG_DBG_REG0		(SUNXI_C0_CPUXCFG_BASE + 0x00c0)
+
+#define SUNXI_CPUCFG_RST_CTRL_REG(c)	(SUNXI_C0_CPUXCFG_BASE + 0x0000)
+#define SUNXI_CPUCFG_GEN_CTRL_REG0(c)	(SUNXI_CPUCFG_BASE + 0x0000)
+#define SUNXI_CPUCFG_RVBAR_LO_REG(n)	(SUNXI_CPUCFG_BASE + 0x0040 + (n) * 8)
+#define SUNXI_CPUCFG_RVBAR_HI_REG(n)	(SUNXI_CPUCFG_BASE + 0x0044 + (n) * 8)
+
+#define SUNXI_POWERON_RST_REG(c)	(SUNXI_R_CPUCFG_BASE + 0x0040 + (c) * 4)
+#define SUNXI_POWEROFF_GATING_REG(c)	(SUNXI_R_CPUCFG_BASE + 0x0044 + (c) * 4)
+#define SUNXI_CPU_POWER_CLAMP_REG(c, n)	(SUNXI_R_CPUCFG_BASE + 0x0050 + \
+					(c) * 0x10 + (n) * 4)
+
+#define SUNXI_AA64nAA32_REG		SUNXI_CPUCFG_GEN_CTRL_REG0
+#define SUNXI_AA64nAA32_OFFSET		4
+
+#endif /* SUNXI_CPUCFG_H */
diff --git a/plat/allwinner/sun50i_r329/include/sunxi_mmap.h b/plat/allwinner/sun50i_r329/include/sunxi_mmap.h
new file mode 100644
index 0000000..a4469b5
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/include/sunxi_mmap.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_MMAP_H
+#define SUNXI_MMAP_H
+
+/* Memory regions */
+#define SUNXI_ROM_BASE			0x00000000
+#define SUNXI_ROM_SIZE			0x00010000
+/*
+ * In fact all SRAM from 0x100000 is SRAM A2. However as it's too big for
+ * firmware, and the user manual gives a tip on a 2*64K/27*64K partition,
+ * only use the first 2*64K for firmwares now, with the SPL using the first
+ * 64K and BL3-1 using the second one.
+ *
+ * Only the used 2*64K SRAM is defined here, to prevent a gaint translation
+ * table to be generated.
+ */
+#define SUNXI_SRAM_BASE			0x00100000
+#define SUNXI_SRAM_SIZE			0x00020000
+#define SUNXI_SRAM_A1_BASE		0x00100000
+#define SUNXI_SRAM_A1_SIZE		0x00010000
+#define SUNXI_SRAM_A2_BASE		0x00110000
+#define SUNXI_SRAM_A2_BL31_OFFSET	0x00000000
+#define SUNXI_SRAM_A2_SIZE		0x00010000
+#define SUNXI_DEV_BASE			0x01000000
+#define SUNXI_DEV_SIZE			0x09000000
+#define SUNXI_DRAM_BASE			0x40000000
+#define SUNXI_DRAM_VIRT_BASE		0x0a000000
+
+/* Memory-mapped devices */
+#define SUNXI_WDOG_BASE			0x020000a0
+#define SUNXI_R_WDOG_BASE		SUNXI_WDOG_BASE
+#define SUNXI_PIO_BASE			0x02000400
+#define SUNXI_SPC_BASE			0x02000800
+#define SUNXI_CCU_BASE			0x02001000
+#define SUNXI_UART0_BASE		0x02500000
+#define SUNXI_SYSCON_BASE		0x03000000
+#define SUNXI_DMA_BASE			0x03002000
+#define SUNXI_SID_BASE			0x03006000
+#define SUNXI_GICD_BASE			0x03021000
+#define SUNXI_GICC_BASE			0x03022000
+#define SUNXI_SPI0_BASE			0x04025000
+#define SUNXI_R_CPUCFG_BASE		0x07000400
+#define SUNXI_R_PRCM_BASE		0x07010000
+#define SUNXI_R_PIO_BASE		0x07022000
+#define SUNXI_R_UART_BASE		0x07080000
+#define SUNXI_R_I2C_BASE		0x07081400
+#define SUNXI_CPUCFG_BASE		0x08100000
+#define SUNXI_C0_CPUXCFG_BASE		0x09010000
+
+#endif /* SUNXI_MMAP_H */
diff --git a/plat/allwinner/sun50i_r329/include/sunxi_spc.h b/plat/allwinner/sun50i_r329/include/sunxi_spc.h
new file mode 100644
index 0000000..2c87bca
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/include/sunxi_spc.h
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2021 Sipeed
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SUNXI_SPC_H
+#define SUNXI_SPC_H
+
+/* Get by REing stock ATF and checking initialization loop boundary */
+#define SUNXI_SPC_NUM_PORTS		11
+
+#define SUNXI_SPC_DECPORT_STA_REG(p)	(SUNXI_SPC_BASE + 0x0000 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_SET_REG(p)	(SUNXI_SPC_BASE + 0x0004 + 0x10 * (p))
+#define SUNXI_SPC_DECPORT_CLR_REG(p)	(SUNXI_SPC_BASE + 0x0008 + 0x10 * (p))
+
+#endif /* SUNXI_SPC_H */
diff --git a/plat/allwinner/sun50i_r329/platform.mk b/plat/allwinner/sun50i_r329/platform.mk
new file mode 100644
index 0000000..05d7cde
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/platform.mk
@@ -0,0 +1,20 @@
+#
+# Copyright (c) 2021 Sipeed
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Without a management processor there is no SCPI support.
+SUNXI_PSCI_USE_SCPI	:=	0
+SUNXI_PSCI_USE_NATIVE	:=	1
+
+# The differences between the platforms are covered by the include files.
+include plat/allwinner/common/allwinner-common.mk
+
+# the above could be overwritten on the command line
+ifeq (${SUNXI_PSCI_USE_SCPI}, 1)
+    $(error "R329 does not support SCPI PSCI ops")
+endif
+
+# Put NOBITS memory in the first 64K of SRAM A2, overwriting U-Boot's SPL.
+SEPARATE_NOBITS_REGION	:=	1
diff --git a/plat/allwinner/sun50i_r329/sunxi_power.c b/plat/allwinner/sun50i_r329/sunxi_power.c
new file mode 100644
index 0000000..96a24d5
--- /dev/null
+++ b/plat/allwinner/sun50i_r329/sunxi_power.c
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2021 Sipeed
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <platform_def.h>
+
+#include <sunxi_mmap.h>
+#include <sunxi_cpucfg.h>
+#include <sunxi_private.h>
+
+int sunxi_pmic_setup(uint16_t socid, const void *fdt)
+{
+	/* Currently known hardware has no PMIC */
+
+	return 0;
+}
+
+void sunxi_power_down(void)
+{
+}
+
+void sunxi_cpu_power_off_self(void)
+{
+	/* TODO: It's still unknown whether CPUIDLE exists on R329 */
+}
diff --git a/plat/amlogic/axg/include/platform_def.h b/plat/amlogic/axg/include/platform_def.h
index a47cf73..c97687e 100644
--- a/plat/amlogic/axg/include/platform_def.h
+++ b/plat/amlogic/axg/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -24,7 +24,7 @@
 
 #define AML_PRIMARY_CPU			U(0)
 
-#define PLAT_MAX_PWR_LVL		MPIDR_AFFLVL1
+#define PLAT_MAX_PWR_LVL		MPIDR_AFFLVL2
 #define PLAT_NUM_PWR_DOMAINS		(PLATFORM_CLUSTER_COUNT + \
 					 PLATFORM_CORE_COUNT)
 
diff --git a/plat/arm/board/a5ds/include/platform_def.h b/plat/arm/board/a5ds/include/platform_def.h
index 792a754..9f3df1e 100644
--- a/plat/arm/board/a5ds/include/platform_def.h
+++ b/plat/arm/board/a5ds/include/platform_def.h
@@ -315,8 +315,8 @@
 #define MAX_IO_HANDLES			4
 
 /* Reserve the last block of flash for PSCI MEM PROTECT flag */
-#define PLAT_ARM_FIP_BASE		BOOT_BASE
-#define PLAT_ARM_FIP_MAX_SIZE		(BOOT_SIZE - V2M_FLASH_BLOCK_SIZE)
+#define PLAT_ARM_FLASH_IMAGE_BASE	BOOT_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(BOOT_SIZE - V2M_FLASH_BLOCK_SIZE)
 
 #define PLAT_ARM_NVM_BASE		BOOT_BASE
 #define PLAT_ARM_NVM_SIZE		(BOOT_SIZE - V2M_FLASH_BLOCK_SIZE)
diff --git a/plat/arm/board/a5ds/platform.mk b/plat/arm/board/a5ds/platform.mk
index 8b0dc5c..4f87306 100644
--- a/plat/arm/board/a5ds/platform.mk
+++ b/plat/arm/board/a5ds/platform.mk
@@ -1,18 +1,23 @@
 #
-# Copyright (c) 2019-2020, Arm Limited. All rights reserved.
+# Copyright (c) 2019-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
 # Firmware Configuration Framework sources
+include common/fdt_wrappers.mk
 include lib/fconf/fconf.mk
 
+BL1_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+BL2_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+
 # Add `libfdt` and Arm common helpers required for Dynamic Config
 include lib/libfdt/libfdt.mk
 
 DYN_CFG_SOURCES		+=	plat/arm/common/arm_dyn_cfg.c		\
-				plat/arm/common/arm_dyn_cfg_helpers.c	\
-				common/fdt_wrappers.c
+				plat/arm/common/arm_dyn_cfg_helpers.c
+
+DYN_CFG_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
 
 # Include GICv2 driver files
 include drivers/arm/gic/v2/gicv2.mk
diff --git a/plat/arm/board/arm_fpga/build_axf.ld.S b/plat/arm/board/arm_fpga/build_axf.ld.S
index d7cd008..d8254e5 100644
--- a/plat/arm/board/arm_fpga/build_axf.ld.S
+++ b/plat/arm/board/arm_fpga/build_axf.ld.S
@@ -15,10 +15,11 @@
 OUTPUT_FORMAT("elf64-littleaarch64")
 OUTPUT_ARCH(aarch64)
 
-INPUT(./bl31/bl31.elf)
 INPUT(./rom_trampoline.o)
+INPUT(./kernel_trampoline.o)
 
 TARGET(binary)
+INPUT(./bl31.bin)
 INPUT(./fdts/arm_fpga.dtb)
 
 ENTRY(_start)
@@ -32,8 +33,7 @@
 
 	.bl31 (BL31_BASE): {
 		ASSERT(. == ALIGN(PAGE_SIZE), "BL31_BASE is not page aligned");
-		*bl31.elf(.text* .data* .rodata* ro* .bss*)
-		*bl31.elf(.stack)
+		*bl31.bin
 	}
 
 	.dtb (FPGA_PRELOADED_DTB_BASE): {
@@ -41,6 +41,12 @@
 		*arm_fpga.dtb
 	}
 
+	.kern_tramp (PRELOADED_BL33_BASE): {
+		*kernel_trampoline.o(.text*)
+		KEEP(*(.kern_tramp))
+	}
+
+	/DISCARD/ : { *(stacks) }
 	/DISCARD/ : { *(.debug_*) }
 	/DISCARD/ : { *(.note*) }
 	/DISCARD/ : { *(.comment*) }
diff --git a/plat/arm/board/arm_fpga/fpga_bl31_setup.c b/plat/arm/board/arm_fpga/fpga_bl31_setup.c
index a5f5ea0..e1b3abb 100644
--- a/plat/arm/board/arm_fpga/fpga_bl31_setup.c
+++ b/plat/arm/board/arm_fpga/fpga_bl31_setup.c
@@ -13,6 +13,7 @@
 #include <drivers/delay_timer.h>
 #include <drivers/generic_delay_timer.h>
 #include <lib/extensions/spe.h>
+#include <lib/mmio.h>
 #include <libfdt.h>
 
 #include "fpga_private.h"
@@ -20,6 +21,7 @@
 #include <platform_def.h>
 
 static entry_point_info_t bl33_image_ep_info;
+static unsigned int system_freq;
 volatile uint32_t secondary_core_spinlock;
 
 uintptr_t plat_get_ns_image_entrypoint(void)
@@ -118,18 +120,187 @@
 	}
 }
 
-unsigned int plat_get_syscnt_freq2(void)
-{
-	const void *fdt = (void *)(uintptr_t)FPGA_PRELOADED_DTB_BASE;
-	int node;
+/*
+ * Even though we sell the FPGA UART as an SBSA variant, it is actually
+ * a full fledged PL011. So the baudrate divider registers exist.
+ */
+#ifndef UARTIBRD
+#define UARTIBRD	0x024
+#define UARTFBRD	0x028
+#endif
 
-	node = fdt_node_offset_by_compatible(fdt, 0, "arm,armv8-timer");
-	if (node < 0) {
-		return FPGA_DEFAULT_TIMER_FREQUENCY;
+/* Round an integer to the closest multiple of a value. */
+static unsigned int round_multiple(unsigned int x, unsigned int multiple)
+{
+	if (multiple < 2) {
+		return x;
 	}
 
-	return fdt_read_uint32_default(fdt, node, "clock-frequency",
-				       FPGA_DEFAULT_TIMER_FREQUENCY);
+	return ((x + (multiple / 2 - 1)) / multiple) * multiple;
+}
+
+#define PL011_FRAC_SHIFT	6
+#define FPGA_DEFAULT_BAUDRATE	38400
+#define PL011_OVERSAMPLING	16
+static unsigned int pl011_freq_from_divider(unsigned int divider)
+{
+	unsigned int freq;
+
+	freq = divider * FPGA_DEFAULT_BAUDRATE * PL011_OVERSAMPLING;
+
+	return freq >> PL011_FRAC_SHIFT;
+}
+
+/*
+ * The FPGAs run most peripherals from one main clock, among them the CPUs,
+ * the arch timer, and the UART baud base clock.
+ * The SCP knows this frequency and programs the UART clock divider for a
+ * 38400 bps baudrate. Recalculate the base input clock from there.
+ */
+static unsigned int fpga_get_system_frequency(void)
+{
+	const void *fdt = (void *)(uintptr_t)FPGA_PRELOADED_DTB_BASE;
+	int node, err;
+
+	/*
+	 * If the arch timer DT node has an explicit clock-frequency property
+	 * set, use that, to allow people overriding auto-detection.
+	 */
+	node = fdt_node_offset_by_compatible(fdt, 0, "arm,armv8-timer");
+	if (node >= 0) {
+		uint32_t freq;
+
+		err = fdt_read_uint32(fdt, node, "clock-frequency", &freq);
+		if (err >= 0) {
+			return freq;
+		}
+	}
+
+	node = fdt_node_offset_by_compatible(fdt, 0, "arm,pl011");
+	if (node >= 0) {
+		uintptr_t pl011_base;
+		unsigned int divider;
+
+		err = fdt_get_reg_props_by_index(fdt, node, 0,
+						 &pl011_base, NULL);
+		if (err >= 0) {
+			divider = mmio_read_32(pl011_base + UARTIBRD);
+			divider <<= PL011_FRAC_SHIFT;
+			divider += mmio_read_32(pl011_base + UARTFBRD);
+
+			/*
+			 * The result won't be exact, due to rounding errors,
+			 * but the input frequency was a multiple of 250 KHz.
+			 */
+			return round_multiple(pl011_freq_from_divider(divider),
+					      250000);
+		} else {
+			WARN("Cannot read PL011 MMIO base\n");
+		}
+	} else {
+		WARN("No PL011 DT node\n");
+	}
+
+	/* No PL011 DT node or calculation failed. */
+	return FPGA_DEFAULT_TIMER_FREQUENCY;
+}
+
+unsigned int plat_get_syscnt_freq2(void)
+{
+	if (system_freq == 0U) {
+		system_freq = fpga_get_system_frequency();
+	}
+
+	return system_freq;
+}
+
+static void fpga_dtb_update_clock(void *fdt, unsigned int freq)
+{
+	uint32_t freq_dtb = fdt32_to_cpu(freq);
+	uint32_t phandle;
+	int node, err;
+
+	node = fdt_node_offset_by_compatible(fdt, 0, "arm,pl011");
+	if (node < 0) {
+		WARN("%s(): No PL011 DT node found\n", __func__);
+
+		return;
+	}
+
+	err = fdt_read_uint32(fdt, node, "clocks", &phandle);
+	if (err != 0) {
+		WARN("Cannot find clocks property\n");
+
+		return;
+	}
+
+	node = fdt_node_offset_by_phandle(fdt, phandle);
+	if (node < 0) {
+		WARN("Cannot get phandle\n");
+
+		return;
+	}
+
+	err = fdt_setprop_inplace(fdt, node,
+				  "clock-frequency",
+				  &freq_dtb,
+				  sizeof(freq_dtb));
+	if (err < 0) {
+		WARN("Could not update DT baud clock frequency\n");
+
+		return;
+	}
+}
+
+#define CMDLINE_SIGNATURE	"CMD:"
+
+static int fpga_dtb_set_commandline(void *fdt, const char *cmdline)
+{
+	int chosen;
+	const char *eol;
+	char nul = 0;
+	int slen, err;
+
+	chosen = fdt_add_subnode(fdt, 0, "chosen");
+	if (chosen == -FDT_ERR_EXISTS) {
+		chosen = fdt_path_offset(fdt, "/chosen");
+	}
+
+	if (chosen < 0) {
+		return chosen;
+	}
+
+	/*
+	 * There is most likely an EOL at the end of the
+	 * command line, make sure we terminate the line there.
+	 * We can't replace the EOL with a NUL byte in the
+	 * source, as this is in read-only memory. So we first
+	 * create the property without any termination, then
+	 * append a single NUL byte.
+	 */
+	eol = strchr(cmdline, '\n');
+	if (eol == NULL) {
+		eol = strchr(cmdline, 0);
+	}
+	/* Skip the signature and omit the EOL/NUL byte. */
+	slen = eol - (cmdline + strlen(CMDLINE_SIGNATURE));
+	/*
+	 * Let's limit the size of the property, just in case
+	 * we find the signature by accident. The Linux kernel
+	 * limits to 4096 characters at most (in fact 2048 for
+	 * arm64), so that sounds like a reasonable number.
+	 */
+	if (slen > 4095) {
+		slen = 4095;
+	}
+
+	err = fdt_setprop(fdt, chosen, "bootargs",
+			  cmdline + strlen(CMDLINE_SIGNATURE), slen);
+	if (err != 0) {
+		return err;
+	}
+
+	return fdt_appendprop(fdt, chosen, "bootargs", &nul, 1);
 }
 
 static void fpga_prepare_dtb(void)
@@ -144,56 +315,20 @@
 		panic();
 	}
 
+	/* Reserve memory used by Trusted Firmware. */
+	if (fdt_add_reserved_memory(fdt, "tf-a@80000000", BL31_BASE,
+				    BL31_LIMIT - BL31_BASE)) {
+		WARN("Failed to add reserved memory node to DT\n");
+	}
+
 	/* Check for the command line signature. */
-	if (!strncmp(cmdline, "CMD:", 4)) {
-		int chosen;
-
-		INFO("using command line at 0x%x\n", FPGA_PRELOADED_CMD_LINE);
-
-		chosen = fdt_add_subnode(fdt, 0, "chosen");
-		if (chosen == -FDT_ERR_EXISTS) {
-			chosen = fdt_path_offset(fdt, "/chosen");
-		}
-		if (chosen < 0) {
-			ERROR("cannot find /chosen node: %d\n", chosen);
+	if (!strncmp(cmdline, CMDLINE_SIGNATURE, strlen(CMDLINE_SIGNATURE))) {
+		err = fpga_dtb_set_commandline(fdt, cmdline);
+		if (err == 0) {
+			INFO("using command line at 0x%x\n",
+			     FPGA_PRELOADED_CMD_LINE);
 		} else {
-			const char *eol;
-			char nul = 0;
-			int slen;
-
-			/*
-			 * There is most likely an EOL at the end of the
-			 * command line, make sure we terminate the line there.
-			 * We can't replace the EOL with a NUL byte in the
-			 * source, as this is in read-only memory. So we first
-			 * create the property without any termination, then
-			 * append a single NUL byte.
-			 */
-			eol = strchr(cmdline, '\n');
-			if (!eol) {
-				eol = strchr(cmdline, 0);
-			}
-			/* Skip the signature and omit the EOL/NUL byte. */
-			slen = eol - (cmdline + 4);
-
-			/*
-			 * Let's limit the size of the property, just in case
-			 * we find the signature by accident. The Linux kernel
-			 * limits to 4096 characters at most (in fact 2048 for
-			 * arm64), so that sounds like a reasonable number.
-			 */
-			if (slen > 4095) {
-				slen = 4095;
-			}
-			err = fdt_setprop(fdt, chosen, "bootargs",
-					  cmdline + 4, slen);
-			if (!err) {
-				err = fdt_appendprop(fdt, chosen, "bootargs",
-						     &nul, 1);
-			}
-			if (err) {
-				ERROR("Could not set command line: %d\n", err);
-			}
+			ERROR("failed to put command line into DTB: %d\n", err);
 		}
 	}
 
@@ -218,13 +353,16 @@
 			INFO("Adjusting GICR DT region to cover %u cores\n",
 			      nr_cores);
 			err = fdt_adjust_gic_redist(fdt, nr_cores,
-						    1U << GICR_PCPUBASE_SHIFT);
+						    fpga_get_redist_base(),
+						    fpga_get_redist_size());
 			if (err < 0) {
 				ERROR("Error %d fixing up GIC DT node\n", err);
 			}
 		}
 	}
 
+	fpga_dtb_update_clock(fdt, system_freq);
+
 	/* Check whether we support the SPE PMU. Remove the DT node if not. */
 	if (!spe_supported()) {
 		int node = fdt_node_offset_by_compatible(fdt, 0,
@@ -235,6 +373,16 @@
 		}
 	}
 
+	/* Check whether we have an ITS. Remove the DT node if not. */
+	if (!fpga_has_its()) {
+		int node = fdt_node_offset_by_compatible(fdt, 0,
+							 "arm,gic-v3-its");
+
+		if (node >= 0) {
+			fdt_del_node(fdt, node);
+		}
+	}
+
 	err = fdt_pack(fdt);
 	if (err < 0) {
 		ERROR("Failed to pack Device Tree at %p: error %d\n", fdt, err);
diff --git a/plat/arm/board/arm_fpga/fpga_gicv3.c b/plat/arm/board/arm_fpga/fpga_gicv3.c
index bfc116b..e06a9da 100644
--- a/plat/arm/board/arm_fpga/fpga_gicv3.c
+++ b/plat/arm/board/arm_fpga/fpga_gicv3.c
@@ -1,13 +1,15 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <common/debug.h>
 #include <common/fdt_wrappers.h>
-#include <drivers/arm/gicv3.h>
+#include <drivers/arm/arm_gicv3_common.h>
 #include <drivers/arm/gic_common.h>
+#include <drivers/arm/gicv3.h>
+#include <lib/mmio.h>
 #include <libfdt.h>
 
 #include <platform_def.h>
@@ -20,6 +22,7 @@
 };
 
 static uintptr_t fpga_rdistif_base_addrs[PLATFORM_CORE_COUNT];
+static int nr_itses;
 
 static unsigned int fpga_mpidr_to_core_pos(unsigned long mpidr)
 {
@@ -37,6 +40,8 @@
 void plat_fpga_gic_init(void)
 {
 	const void *fdt = (void *)(uintptr_t)FPGA_PRELOADED_DTB_BASE;
+	uintptr_t gicr_base = 0U;
+	uint32_t iidr;
 	int node, ret;
 
 	node = fdt_node_offset_by_compatible(fdt, 0, "arm,gic-v3");
@@ -53,11 +58,66 @@
 		return;
 	}
 
-	ret = fdt_get_reg_props_by_index(fdt, node, 1,
-				 &fpga_gicv3_driver_data.gicr_base, NULL);
-	if (ret < 0) {
-		WARN("Could not read GIC redistributor address from DT.\n");
-		return;
+	iidr = mmio_read_32(fpga_gicv3_driver_data.gicd_base + GICD_IIDR);
+	if (((iidr & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_600) ||
+	    ((iidr & IIDR_MODEL_MASK) == IIDR_MODEL_ARM_GIC_700)) {
+		unsigned int frame_id;
+
+		/*
+		 * According to the GIC TRMs, if there are any ITSes, they
+		 * start four 64K pages after the distributor. After all
+		 * the ITSes then follow the redistributors.
+		 */
+		gicr_base = fpga_gicv3_driver_data.gicd_base + (4U << 16);
+
+		do {
+			uint64_t its_typer;
+
+			/* Each GIC component can be identified by its ID. */
+			frame_id = gicv3_get_component_partnum(gicr_base);
+
+			if (frame_id == PIDR_COMPONENT_ARM_REDIST) {
+				INFO("Found %d ITSes, redistributors start at 0x%llx\n",
+				     nr_itses, (unsigned long long)gicr_base);
+				break;
+			}
+
+			if (frame_id != PIDR_COMPONENT_ARM_ITS) {
+				WARN("GICv3: found unexpected frame 0x%x\n",
+					frame_id);
+				gicr_base = 0U;
+				break;
+			}
+
+			/*
+			 * Found an ITS, now work out if it supports virtual
+			 * SGIs (for direct guest injection). If yes, each
+			 * ITS occupies four 64K pages, otherwise just two.
+			 */
+			its_typer = mmio_read_64(gicr_base + GITS_TYPER);
+			if ((its_typer & GITS_TYPER_VSGI) != 0U) {
+				gicr_base += 4U << 16;
+			} else {
+				gicr_base += 2U << 16;
+			}
+			nr_itses++;
+		} while (true);
+	}
+
+	/*
+	 * If this is not a GIC-600 or -700, or the autodetection above failed,
+	 * use the base address from the device tree.
+	 */
+	if (gicr_base == 0U) {
+		ret = fdt_get_reg_props_by_index(fdt, node, 1,
+					&fpga_gicv3_driver_data.gicr_base,
+					NULL);
+		if (ret < 0) {
+			WARN("Could not read GIC redistributor address from DT.\n");
+			return;
+		}
+	} else {
+		fpga_gicv3_driver_data.gicr_base = gicr_base;
 	}
 
 	gicv3_driver_init(&fpga_gicv3_driver_data);
@@ -82,3 +142,21 @@
 {
 	return gicv3_rdistif_get_number_frames(fpga_gicv3_driver_data.gicr_base);
 }
+
+uintptr_t fpga_get_redist_size(void)
+{
+	uint64_t typer_val = mmio_read_64(fpga_gicv3_driver_data.gicr_base +
+					  GICR_TYPER);
+
+	return gicv3_redist_size(typer_val);
+}
+
+uintptr_t fpga_get_redist_base(void)
+{
+	return fpga_gicv3_driver_data.gicr_base;
+}
+
+bool fpga_has_its(void)
+{
+	return nr_itses > 0;
+}
diff --git a/plat/arm/board/arm_fpga/fpga_private.h b/plat/arm/board/arm_fpga/fpga_private.h
index 1ca241f..84d651c 100644
--- a/plat/arm/board/arm_fpga/fpga_private.h
+++ b/plat/arm/board/arm_fpga/fpga_private.h
@@ -25,6 +25,9 @@
 void fpga_pwr_gic_off(void);
 unsigned int plat_fpga_calc_core_pos(uint32_t mpid);
 unsigned int fpga_get_nr_gic_cores(void);
+uintptr_t fpga_get_redist_size(void);
+uintptr_t fpga_get_redist_base(void);
+bool fpga_has_its(void);
 
 #endif /* __ASSEMBLER__ */
 
diff --git a/plat/arm/board/arm_fpga/include/platform_def.h b/plat/arm/board/arm_fpga/include/platform_def.h
index 411b936..2350d87 100644
--- a/plat/arm/board/arm_fpga/include/platform_def.h
+++ b/plat/arm/board/arm_fpga/include/platform_def.h
@@ -30,7 +30,7 @@
 
 #if !ENABLE_PIE
 #define BL31_BASE			UL(0x80000000)
-#define BL31_LIMIT			UL(0x80100000)
+#define BL31_LIMIT			UL(0x80070000)
 #else
 #define BL31_BASE			UL(0x0)
 #define BL31_LIMIT			UL(0x01000000)
diff --git a/plat/arm/board/arm_fpga/kernel_trampoline.S b/plat/arm/board/arm_fpga/kernel_trampoline.S
new file mode 100644
index 0000000..f4c08ef
--- /dev/null
+++ b/plat/arm/board/arm_fpga/kernel_trampoline.S
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * The traditional arm64 Linux kernel load address is 512KiB from the
+ * beginning of DRAM, caused by this having been the default value of the
+ * kernel's CONFIG_TEXT_OFFSET Kconfig value.
+ * However kernel version 5.8 changed the default offset (into a 2MB page)
+ * to 0, so TF-A's default assumption is no longer true. Fortunately the
+ * kernel got more relaxed about this offset at the same time, so it
+ * tolerates the wrong offset, but issues a warning:
+ * [Firmware Bug]: Kernel image misaligned at boot, please fix your bootloader!
+ *
+ * We cannot easily change the load address offset in TF-A to be 2MiB, because
+ * this would break older kernels - and they are not as forgiving in this
+ * respect.
+ *
+ * But we can allow users to load the kernel at the right offset, and
+ * offer this trampoline here to transition to this new load address.
+ * Any older kernels, or newer kernels misloaded, will overwrite this code
+ * here, so it does no harm in this case.
+ */
+
+#include <asm_macros.S>
+#include <common/bl_common.ld.h>
+
+.text
+.global _tramp_start
+
+_tramp_start:
+	adr	x4, _tramp_start
+	orr	x4, x4, #0x1fffff
+	add	x4, x4, #1			/* align up to 2MB */
+	br	x4
diff --git a/plat/arm/board/arm_fpga/platform.mk b/plat/arm/board/arm_fpga/platform.mk
index 4b751fb..084532c 100644
--- a/plat/arm/board/arm_fpga/platform.mk
+++ b/plat/arm/board/arm_fpga/platform.mk
@@ -1,9 +1,10 @@
 #
-# Copyright (c) 2020, Arm Limited. All rights reserved.
+# Copyright (c) 2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
 include lib/libfdt/libfdt.mk
 
 RESET_TO_BL31 := 1
@@ -32,6 +33,8 @@
 FPGA_PRELOADED_CMD_LINE := 0x1000
 $(eval $(call add_define,FPGA_PRELOADED_CMD_LINE))
 
+ENABLE_AMU		:=	1
+
 # Treating this as a memory-constrained port for now
 USE_COHERENT_MEM	:=	0
 
@@ -59,14 +62,19 @@
 				lib/cpus/aarch64/cortex_a76ae.S		\
 				lib/cpus/aarch64/cortex_a77.S		\
 				lib/cpus/aarch64/cortex_a78.S		\
+				lib/cpus/aarch64/neoverse_n_common.S	\
 				lib/cpus/aarch64/neoverse_n1.S		\
+				lib/cpus/aarch64/neoverse_n2.S		\
 				lib/cpus/aarch64/neoverse_e1.S		\
 				lib/cpus/aarch64/neoverse_v1.S		\
 				lib/cpus/aarch64/cortex_a78_ae.S	\
 				lib/cpus/aarch64/cortex_a65.S		\
 				lib/cpus/aarch64/cortex_a65ae.S		\
-				lib/cpus/aarch64/cortex_klein.S		\
-				lib/cpus/aarch64/cortex_matterhorn.S
+				lib/cpus/aarch64/cortex_a510.S		\
+				lib/cpus/aarch64/cortex_a710.S	\
+				lib/cpus/aarch64/cortex_makalu.S	\
+				lib/cpus/aarch64/cortex_makalu_elp_arm.S \
+				lib/cpus/aarch64/cortex_a78c.S
 
 # AArch64/AArch32 cores
 	FPGA_CPU_LIBS	+=	lib/cpus/aarch64/cortex_a55.S	\
@@ -82,6 +90,8 @@
 # Allow detection of GIC-600
 GICV3_SUPPORT_GIC600	:=	1
 
+GIC_ENABLE_V4_EXTN	:=	1
+
 # Include GICv3 driver files
 include drivers/arm/gic/v3/gicv3.mk
 
@@ -95,8 +105,7 @@
 
 PLAT_BL_COMMON_SOURCES	:=	plat/arm/board/arm_fpga/${ARCH}/fpga_helpers.S
 
-BL31_SOURCES		+=	common/fdt_wrappers.c				\
-				common/fdt_fixup.c				\
+BL31_SOURCES		+=	common/fdt_fixup.c				\
 				drivers/delay_timer/delay_timer.c		\
 				drivers/delay_timer/generic_delay_timer.c	\
 				drivers/arm/pl011/${ARCH}/pl011_console.S	\
@@ -108,11 +117,14 @@
 				${FPGA_CPU_LIBS}				\
 				${FPGA_GIC_SOURCES}
 
-$(eval $(call MAKE_S,$(BUILD_PLAT),plat/arm/board/arm_fpga/rom_trampoline.S,31))
-$(eval $(call MAKE_LD,$(BUILD_PLAT)/build_axf.ld,plat/arm/board/arm_fpga/build_axf.ld.S,31))
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
 
-bl31.axf: bl31 dtbs ${BUILD_PLAT}/rom_trampoline.o ${BUILD_PLAT}/build_axf.ld
+$(eval $(call MAKE_S,$(BUILD_PLAT),plat/arm/board/arm_fpga/rom_trampoline.S,bl31))
+$(eval $(call MAKE_S,$(BUILD_PLAT),plat/arm/board/arm_fpga/kernel_trampoline.S,bl31))
+$(eval $(call MAKE_LD,$(BUILD_PLAT)/build_axf.ld,plat/arm/board/arm_fpga/build_axf.ld.S,bl31))
+
+bl31.axf: bl31 dtbs ${BUILD_PLAT}/rom_trampoline.o ${BUILD_PLAT}/kernel_trampoline.o ${BUILD_PLAT}/build_axf.ld
 	$(ECHO) "  LD      $@"
-	$(Q)$(LD) -T ${BUILD_PLAT}/build_axf.ld -L ${BUILD_PLAT} --strip-debug -o ${BUILD_PLAT}/bl31.axf
+	$(Q)$(LD) -T ${BUILD_PLAT}/build_axf.ld -L ${BUILD_PLAT} --strip-debug -s -n -o ${BUILD_PLAT}/bl31.axf
 
 all: bl31.axf
diff --git a/plat/arm/board/common/board_common.mk b/plat/arm/board/common/board_common.mk
index 1885a60..5cdf1bf 100644
--- a/plat/arm/board/common/board_common.mk
+++ b/plat/arm/board/common/board_common.mk
@@ -33,7 +33,7 @@
 $(warning Development keys support for FVP is deprecated. Use `regs` \
 option instead)
 else
-	$(error "Unsupported ARM_ROTPK_LOCATION value")
+$(error "Unsupported ARM_ROTPK_LOCATION value")
 endif
 
 $(eval $(call add_define,ARM_ROTPK_LOCATION_ID))
@@ -41,7 +41,6 @@
 # Force generation of the new hash if ROT_KEY is specified
 ifdef ROT_KEY
 	HASH_PREREQUISITES = $(ROT_KEY) FORCE
-FORCE:
 else
 	HASH_PREREQUISITES = $(ROT_KEY)
 endif
diff --git a/plat/arm/board/common/rotpk/arm_dev_rotpk.S b/plat/arm/board/common/rotpk/arm_dev_rotpk.S
index 80f2192..38f91fe 100644
--- a/plat/arm/board/common/rotpk/arm_dev_rotpk.S
+++ b/plat/arm/board/common/rotpk/arm_dev_rotpk.S
@@ -1,10 +1,17 @@
 /*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+/* diphda platform provides custom values for the macros defined in
+ * arm_def.h , so only platform_def.h needs to be included
+ */
+#if !defined(TARGET_PLATFORM_FVP) && !defined(TARGET_PLATFORM_FPGA)
 #include "plat/arm/common/arm_def.h"
+#else
+#include <platform_def.h>
+#endif
 
 	.global arm_rotpk_header
 	.global arm_rotpk_header_end
diff --git a/plat/arm/board/diphda/common/diphda_bl2_mem_params_desc.c b/plat/arm/board/diphda/common/diphda_bl2_mem_params_desc.c
new file mode 100644
index 0000000..916c868
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_bl2_mem_params_desc.c
@@ -0,0 +1,86 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/desc_image_load.h>
+
+#include <platform_def.h>
+
+/*******************************************************************************
+ * Following descriptor provides BL image/ep information that gets used
+ * by BL2 to load the images and also subset of this information is
+ * passed to next BL image. The image loading sequence is managed by
+ * populating the images in required loading order. The image execution
+ * sequence is managed by populating the `next_handoff_image_id` with
+ * the next executable image id.
+ ******************************************************************************/
+static bl_mem_params_node_t bl2_mem_params_descs[] = {
+
+	/* Fill BL31 related information */
+	{
+		.image_id = BL31_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+			VERSION_2, entry_point_info_t,
+			SECURE | EXECUTABLE | EP_FIRST_EXE),
+		.ep_info.pc = BL31_BASE,
+		.ep_info.spsr = SPSR_64(MODE_EL3, MODE_SP_ELX,
+			DISABLE_ALL_EXCEPTIONS),
+			.ep_info.args.arg3 = ARM_BL31_PLAT_PARAM_VAL,
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+			VERSION_2, image_info_t, IMAGE_ATTRIB_PLAT_SETUP),
+		.image_info.image_base = BL31_BASE,
+		.image_info.image_max_size = BL31_LIMIT - BL31_BASE,
+
+		.next_handoff_image_id = BL32_IMAGE_ID,
+	},
+
+	/* Fill BL32 related information */
+	{
+		.image_id = BL32_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+			VERSION_2, entry_point_info_t, SECURE | EXECUTABLE),
+		.ep_info.pc = BL32_BASE,
+			.ep_info.args.arg0 = DIPHDA_TOS_FW_CONFIG_BASE,
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+			VERSION_2, image_info_t, 0),
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size = BL32_LIMIT - BL32_BASE,
+
+		.next_handoff_image_id = BL33_IMAGE_ID,
+	},
+
+	/* Fill TOS_FW_CONFIG related information */
+	{
+		.image_id = TOS_FW_CONFIG_ID,
+		.image_info.image_base = DIPHDA_TOS_FW_CONFIG_BASE,
+		.image_info.image_max_size = DIPHDA_TOS_FW_CONFIG_LIMIT - \
+			DIPHDA_TOS_FW_CONFIG_BASE,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_IMAGE_BINARY,
+			VERSION_2, entry_point_info_t, SECURE | NON_EXECUTABLE),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_IMAGE_BINARY,
+		VERSION_2, image_info_t, 0),
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+
+	/* Fill BL33 related information */
+	{
+		.image_id = BL33_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+			VERSION_2, entry_point_info_t, NON_SECURE | EXECUTABLE),
+		.ep_info.pc = PLAT_ARM_NS_IMAGE_BASE,
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+			VERSION_2, image_info_t, 0),
+		.image_info.image_base = PLAT_ARM_NS_IMAGE_BASE,
+		.image_info.image_max_size = ARM_DRAM1_BASE + ARM_DRAM1_SIZE
+			- PLAT_ARM_NS_IMAGE_BASE,
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+};
+
+REGISTER_BL_IMAGE_DESCS(bl2_mem_params_descs)
diff --git a/plat/arm/board/diphda/common/diphda_err.c b/plat/arm/board/diphda/common/diphda_err.c
new file mode 100644
index 0000000..89a3b82
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_err.c
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * diphda error handler
+ */
+void __dead2 plat_arm_error_handler(int err)
+{
+	while (1) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/diphda/common/diphda_helpers.S b/plat/arm/board/diphda/common/diphda_helpers.S
new file mode 100644
index 0000000..c9d2a88
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_helpers.S
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <platform_def.h>
+
+	.globl	plat_secondary_cold_boot_setup
+	.globl	plat_get_my_entrypoint
+	.globl	plat_is_my_cpu_primary
+	.globl	plat_arm_calc_core_pos
+
+	/* --------------------------------------------------------------------
+	 * void plat_secondary_cold_boot_setup (void);
+	 *
+	 * For AArch32, cold-booting secondary CPUs is not yet
+	 * implemented and they panic.
+	 * --------------------------------------------------------------------
+	 */
+func plat_secondary_cold_boot_setup
+cb_panic:
+	b	cb_panic
+endfunc plat_secondary_cold_boot_setup
+
+	/* ---------------------------------------------------------------------
+	 * unsigned long plat_get_my_entrypoint (void);
+	 *
+	 * Main job of this routine is to distinguish between a cold and warm
+	 * boot. On diphda, this information can be queried from the power
+	 * controller. The Power Control SYS Status Register (PSYSR) indicates
+	 * the wake-up reason for the CPU.
+	 *
+	 * For a cold boot, return 0.
+	 * For a warm boot, Not yet supported.
+	 *
+	 * TODO: PSYSR is a common register and should be
+	 * 	accessed using locks. Since it is not possible
+	 * 	to use locks immediately after a cold reset
+	 * 	we are relying on the fact that after a cold
+	 * 	reset all cpus will read the same WK field
+	 * ---------------------------------------------------------------------
+	 */
+func plat_get_my_entrypoint
+	/* TODO support warm boot */
+	/* Cold reset */
+	mov	x0, #0
+	ret
+endfunc plat_get_my_entrypoint
+
+	/* -----------------------------------------------------
+	 * unsigned int plat_is_my_cpu_primary (void);
+	 *
+	 * Find out whether the current CPU is the primary
+	 * CPU.
+	 * -----------------------------------------------------
+	 */
+func plat_is_my_cpu_primary
+	mrs	x0, mpidr_el1
+	mov_imm	x1, MPIDR_AFFINITY_MASK
+	and	x0, x0, x1
+	cmp	x0, #DIPHDA_PRIMARY_CPU
+	cset	w0, eq
+	ret
+endfunc plat_is_my_cpu_primary
diff --git a/plat/arm/board/diphda/common/diphda_plat.c b/plat/arm/board/diphda/common/diphda_plat.c
new file mode 100644
index 0000000..28d15a5
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_plat.c
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/bl_common.h>
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+/*
+ * Table of regions to map using the MMU.
+ * Replace or extend the below regions as required
+ */
+
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	ARM_MAP_NS_SHARED_RAM,
+	ARM_MAP_NS_DRAM1,
+	DIPHDA_MAP_DEVICE,
+	DIPHDA_EXTERNAL_FLASH,
+	{0}
+};
+
+/* diphda only has one always-on power domain and there
+ * is no power control present
+ */
+void __init plat_arm_pwrc_setup(void)
+{
+}
+
+unsigned int plat_get_syscnt_freq2(void)
+{
+	/* Returning the Generic Timer Frequency */
+	return SYS_COUNTER_FREQ_IN_TICKS;
+}
+
+
+/*
+ * Helper function to initialize ARM interconnect driver.
+ */
+void plat_arm_interconnect_init(void)
+{
+}
+
+/*
+ * Helper function to place current master into coherency
+ */
+void plat_arm_interconnect_enter_coherency(void)
+{
+}
+
+/*
+ * Helper function to remove current master from coherency
+ */
+void plat_arm_interconnect_exit_coherency(void)
+{
+}
+
+/*
+ * This function is invoked during Mbed TLS library initialisation to get a heap
+ * The function simply returns the default allocated heap.
+ */
+
+#if TRUSTED_BOARD_BOOT
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	assert(heap_addr != NULL);
+	assert(heap_size != NULL);
+
+	return arm_get_mbedtls_heap(heap_addr, heap_size);
+}
+#endif
diff --git a/plat/arm/board/diphda/common/diphda_pm.c b/plat/arm/board/diphda/common/diphda_pm.c
new file mode 100644
index 0000000..12b322e
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_pm.c
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/psci/psci.h>
+#include <plat/arm/common/plat_arm.h>
+
+/*******************************************************************************
+ * Export the platform handlers via plat_arm_psci_pm_ops. The ARM Standard
+ * platform layer will take care of registering the handlers with PSCI.
+ ******************************************************************************/
+plat_psci_ops_t plat_arm_psci_pm_ops = {
+	/* dummy struct */
+	.validate_ns_entrypoint = NULL
+};
+
+const plat_psci_ops_t *plat_arm_psci_override_pm_ops(plat_psci_ops_t *ops)
+{
+	return ops;
+}
diff --git a/plat/arm/board/diphda/common/diphda_security.c b/plat/arm/board/diphda/common/diphda_security.c
new file mode 100644
index 0000000..bf172af
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_security.c
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/*
+ * We assume that all security programming is done by the primary core.
+ */
+void plat_arm_security_setup(void)
+{
+	/*
+	 * If the platform had additional peripheral specific security
+	 * configurations, those would be configured here.
+	 */
+}
diff --git a/plat/arm/board/diphda/common/diphda_stack_protector.c b/plat/arm/board/diphda/common/diphda_stack_protector.c
new file mode 100644
index 0000000..6228b63
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_stack_protector.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <plat/common/platform.h>
+
+static uint32_t plat_generate_random_number(void)
+{
+	uintptr_t return_addr = (uintptr_t)__builtin_return_address(0U);
+	uintptr_t frame_addr = (uintptr_t)__builtin_frame_address(0U);
+	uint64_t cntpct = read_cntpct_el0();
+
+	/* Generate 32-bit pattern: saving the 2 least significant bytes
+	 * in random_lo and random_hi
+	 */
+	uint16_t random_lo = (uint16_t)(
+			(((uint64_t)return_addr) << 13) ^ frame_addr ^ cntpct
+			);
+
+	uint16_t random_hi = (uint16_t)(
+			(((uint64_t)frame_addr) << 15) ^ return_addr ^ cntpct
+			);
+
+	return (((uint32_t)random_hi) << 16) | random_lo;
+}
+
+u_register_t plat_get_stack_protector_canary(void)
+{
+	return  plat_generate_random_number(); /* a 32-bit pattern returned */
+}
diff --git a/plat/arm/board/diphda/common/diphda_topology.c b/plat/arm/board/diphda/common/diphda_topology.c
new file mode 100644
index 0000000..9dfd05d
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_topology.c
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+
+/* The diphda power domain tree descriptor */
+static unsigned char diphda_power_domain_tree_desc[PLAT_ARM_CLUSTER_COUNT
+							+ 2];
+/*******************************************************************************
+ * This function dynamically constructs the topology according to
+ * CLUSTER_COUNT and returns it.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	int i;
+
+	/*
+	 * The highest level is the system level. The next level is constituted
+	 * by clusters and then cores in clusters.
+	 */
+	diphda_power_domain_tree_desc[0] = 1;
+	diphda_power_domain_tree_desc[1] = PLAT_ARM_CLUSTER_COUNT;
+
+	for (i = 0; i < PLAT_ARM_CLUSTER_COUNT; i++)
+		diphda_power_domain_tree_desc[i + 2] = PLATFORM_CORE_COUNT;
+
+	return diphda_power_domain_tree_desc;
+}
+
+/******************************************************************************
+ * This function implements a part of the critical interface between the PSCI
+ * generic layer and the platform that allows the former to query the platform
+ * to convert an MPIDR to a unique linear index. An error code (-1) is
+ * returned in case the MPIDR is invalid.
+ *****************************************************************************/
+int plat_core_pos_by_mpidr(u_register_t mpidr)
+{
+	return plat_arm_calc_core_pos(mpidr);
+}
diff --git a/plat/arm/board/diphda/common/diphda_trusted_boot.c b/plat/arm/board/diphda/common/diphda_trusted_boot.c
new file mode 100644
index 0000000..ddb41fa
--- /dev/null
+++ b/plat/arm/board/diphda/common/diphda_trusted_boot.c
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * Return the ROTPK hash in the following ASN.1 structure in DER format:
+ *
+ * AlgorithmIdentifier  ::=  SEQUENCE  {
+ *     algorithm         OBJECT IDENTIFIER,
+ *     parameters        ANY DEFINED BY algorithm OPTIONAL
+ * }
+ *
+ * DigestInfo ::= SEQUENCE {
+ *     digestAlgorithm   AlgorithmIdentifier,
+ *     digest            OCTET STRING
+ * }
+ *
+ * The function returns 0 on success. Any other value is treated as error by the
+ * Trusted Board Boot. The function also reports extra information related
+ * to the ROTPK in the flags parameter: ROTPK_IS_HASH, ROTPK_NOT_DEPLOYED.
+ *
+ * Refer to the TF-A porting-guide document for more details.
+ */
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	return arm_get_rotpk_info(cookie, key_ptr, key_len, flags);
+}
+
+/*
+ * STUB overriding the non-volatile counter reading.
+ * NV counters are not implemented at this stage of development.
+ * Return: 0 = success
+ */
+int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
+{
+    *nv_ctr = DIPHDA_FW_NVCTR_VAL;
+    return 0;
+}
+
+/*
+ * STUB overriding the non-volatile counter updating.
+ * NV counters are not implemented at this stage of development.
+ * Return: 0 = success
+ */
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+    return 0;
+}
diff --git a/plat/arm/board/diphda/common/fdts/diphda_spmc_manifest.dts b/plat/arm/board/diphda/common/fdts/diphda_spmc_manifest.dts
new file mode 100644
index 0000000..536bdc3
--- /dev/null
+++ b/plat/arm/board/diphda/common/fdts/diphda_spmc_manifest.dts
@@ -0,0 +1,30 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/dts-v1/;
+
+/ {
+	compatible = "arm,ffa-core-manifest-1.0";
+	#address-cells = <2>;
+	#size-cells = <1>;
+
+	/*
+	 * BL32 image details needed by SPMC
+	 *
+	 * Note:
+	 * binary_size: size of BL32 + TOS_FW_CONFIG
+	 */
+
+	attribute {
+		spmc_id = <0x8000>;
+		maj_ver = <0x1>;
+		min_ver = <0x1>;
+		exec_state = <0x0>;
+		load_address = <0x0 0x2002000>;
+		entrypoint = <0x0 0x2002000>;
+		binary_size = <0xae000>;
+	};
+
+};
diff --git a/plat/arm/board/diphda/common/include/platform_def.h b/plat/arm/board/diphda/common/include/platform_def.h
new file mode 100644
index 0000000..37fd71b
--- /dev/null
+++ b/plat/arm/board/diphda/common/include/platform_def.h
@@ -0,0 +1,416 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <common/tbbr/tbbr_img_def.h>
+#include <lib/utils_def.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <plat/arm/board/common/v2m_def.h>
+#include <plat/arm/common/arm_spm_def.h>
+#include <plat/arm/common/smccc_def.h>
+#include <plat/common/common_def.h>
+#include <plat/arm/soc/common/soc_css_def.h>
+
+#define ARM_ROTPK_HEADER_LEN			19
+#define ARM_ROTPK_HASH_LEN			32
+
+/* Special value used to verify platform parameters from BL2 to BL31 */
+#define ARM_BL31_PLAT_PARAM_VAL		ULL(0x0f1e2d3c4b5a6978)
+
+/* PL011 UART related constants */
+#ifdef V2M_IOFPGA_UART0_CLK_IN_HZ
+#undef V2M_IOFPGA_UART0_CLK_IN_HZ
+#endif
+
+#ifdef V2M_IOFPGA_UART1_CLK_IN_HZ
+#undef V2M_IOFPGA_UART1_CLK_IN_HZ
+#endif
+
+#define V2M_IOFPGA_UART0_CLK_IN_HZ		50000000
+#define V2M_IOFPGA_UART1_CLK_IN_HZ		50000000
+
+/* Core/Cluster/Thread counts for diphda */
+#define DIPHDA_CLUSTER_COUNT			U(1)
+#define DIPHDA_MAX_CPUS_PER_CLUSTER		U(4)
+#define DIPHDA_MAX_PE_PER_CPU			U(1)
+#define DIPHDA_PRIMARY_CPU			U(0)
+
+#define PLAT_ARM_CLUSTER_COUNT		DIPHDA_CLUSTER_COUNT
+
+#define PLATFORM_CORE_COUNT			(PLAT_ARM_CLUSTER_COUNT *      \
+						DIPHDA_MAX_CPUS_PER_CLUSTER *  \
+						DIPHDA_MAX_PE_PER_CPU)
+
+/* UART related constants */
+#define PLAT_ARM_BOOT_UART_BASE		0x1a510000
+#define PLAT_ARM_BOOT_UART_CLK_IN_HZ		V2M_IOFPGA_UART0_CLK_IN_HZ
+#define PLAT_ARM_RUN_UART_BASE		0x1a520000
+#define PLAT_ARM_RUN_UART_CLK_IN_HZ		V2M_IOFPGA_UART1_CLK_IN_HZ
+#define ARM_CONSOLE_BAUDRATE			115200
+#define PLAT_ARM_CRASH_UART_BASE		PLAT_ARM_RUN_UART_BASE
+#define PLAT_ARM_CRASH_UART_CLK_IN_HZ		PLAT_ARM_RUN_UART_CLK_IN_HZ
+
+/* Memory related constants */
+
+/* SRAM (CVM) memory layout
+ *
+ * <ARM_TRUSTED_SRAM_BASE>
+ *
+ *         partition size: sizeof(meminfo_t) = 16 bytes
+ *
+ *         content: memory info area used by the next BL
+ *
+ * <ARM_FW_CONFIG_BASE>
+ *
+ *         partition size: 4080 bytes
+ *
+ * <ARM_BL2_MEM_DESC_BASE>
+ *
+ *         partition size: 4 KB
+ *
+ *         content:
+ *
+ *             Area where BL2 copies the images descriptors
+ *
+ * <ARM_BL_RAM_BASE> = <BL32_BASE>
+ *
+ *         partition size: 688 KB
+ *
+ *         content:
+ *
+ *             BL32 (optee-os)
+ *
+ * <DIPHDA_TOS_FW_CONFIG_BASE> = 0x20ae000
+ *
+ *         partition size: 8 KB
+ *
+ *         content:
+ *
+ *             BL32 config (TOS_FW_CONFIG)
+ *
+ * <BL31_BASE>
+ *
+ *         partition size: 140 KB
+ *
+ *         content:
+ *
+ *             BL31
+ *
+ * <BL2_SIGNATURE_BASE>
+ *
+ *     partition size: 4 KB
+ *
+ *     content:
+ *
+ *         MCUBOOT data needed to verify TF-A BL2
+ *
+ * <BL2_BASE>
+ *
+ *     partition size: 176 KB
+ *
+ *         content:
+ *
+ *             BL2
+ *
+ * <ARM_NS_SHARED_RAM_BASE> = <ARM_TRUSTED_SRAM_BASE> + 1 MB
+ *
+ *         partition size: 3 MB
+ *
+ *         content:
+ *
+ *             BL33 (u-boot)
+ */
+
+/* DDR memory */
+#define ARM_DRAM1_BASE			UL(0x80000000)
+#define ARM_DRAM1_SIZE			UL(0x80000000)
+#define ARM_DRAM1_END				(ARM_DRAM1_BASE +	\
+						ARM_DRAM1_SIZE - 1)
+
+/* DRAM1 and DRAM2 are the same for diphda */
+#define ARM_DRAM2_BASE			ARM_DRAM1_BASE
+#define ARM_DRAM2_SIZE			ARM_DRAM1_SIZE
+#define ARM_DRAM2_END				ARM_DRAM1_END
+
+#define ARM_NS_DRAM1_BASE			ARM_DRAM1_BASE
+#define ARM_NS_DRAM1_SIZE			ARM_DRAM1_SIZE
+#define ARM_NS_DRAM1_END			(ARM_NS_DRAM1_BASE +	\
+						ARM_NS_DRAM1_SIZE - 1)
+
+/* The first 8 KB of Trusted SRAM are used as shared memory */
+#define ARM_TRUSTED_SRAM_BASE			UL(0x02000000)
+#define ARM_SHARED_RAM_SIZE			UL(0x00002000)  /* 8 KB */
+#define ARM_SHARED_RAM_BASE			ARM_TRUSTED_SRAM_BASE
+
+/* The remaining Trusted SRAM is used to load the BL images */
+
+#define PLAT_ARM_TRUSTED_SRAM_SIZE		UL(0x00100000)  /* 1 MB */
+
+#define PLAT_ARM_MAX_BL2_SIZE			UL(0x0002d000)  /* 180 KB */
+
+#define PLAT_ARM_MAX_BL31_SIZE		UL(0x00023000)  /* 140 KB */
+
+#define ARM_BL_RAM_BASE			(ARM_SHARED_RAM_BASE +	\
+						ARM_SHARED_RAM_SIZE)
+#define ARM_BL_RAM_SIZE			(PLAT_ARM_TRUSTED_SRAM_SIZE -	\
+						ARM_SHARED_RAM_SIZE)
+
+#define BL2_SIGNATURE_SIZE			UL(0x00001000)  /* 4 KB */
+#define BL2_SIGNATURE_BASE			(BL2_LIMIT - \
+						PLAT_ARM_MAX_BL2_SIZE)
+#define BL2_BASE				(BL2_LIMIT - \
+						PLAT_ARM_MAX_BL2_SIZE + \
+						BL2_SIGNATURE_SIZE)
+#define BL2_LIMIT				(ARM_BL_RAM_BASE + \
+						ARM_BL_RAM_SIZE)
+
+#define BL31_BASE				(BL2_SIGNATURE_BASE - \
+						PLAT_ARM_MAX_BL31_SIZE)
+#define BL31_LIMIT				BL2_SIGNATURE_BASE
+
+#define DIPHDA_TOS_FW_CONFIG_BASE		(BL31_BASE - \
+						DIPHDA_TOS_FW_CONFIG_SIZE)
+#define DIPHDA_TOS_FW_CONFIG_SIZE		UL(0x00002000)  /* 8 KB */
+#define DIPHDA_TOS_FW_CONFIG_LIMIT		BL31_BASE
+
+#define BL32_BASE				ARM_BL_RAM_BASE
+#define PLAT_ARM_MAX_BL32_SIZE		(DIPHDA_TOS_FW_CONFIG_BASE - \
+						BL32_BASE)     /* 688 KB */
+#define BL32_LIMIT				(BL32_BASE + \
+						PLAT_ARM_MAX_BL32_SIZE)
+
+/* SPD_spmd settings */
+
+#define PLAT_ARM_SPMC_BASE			BL32_BASE
+#define PLAT_ARM_SPMC_SIZE			PLAT_ARM_MAX_BL32_SIZE
+
+/* NS memory */
+
+/* The last 3 MB of the SRAM is allocated to the non secure area */
+#define ARM_NS_SHARED_RAM_BASE		(ARM_TRUSTED_SRAM_BASE + \
+						PLAT_ARM_TRUSTED_SRAM_SIZE)
+#define ARM_NS_SHARED_RAM_SIZE		UL(0x00300000)  /* 3 MB */
+
+/* end of the definition of SRAM memory layout */
+
+/* NOR Flash */
+
+#define PLAT_ARM_FIP_BASE			UL(0x08131000)
+#define PLAT_ARM_FIP_MAX_SIZE			UL(0x1ff000)  /* 1.996 MB */
+
+#define PLAT_ARM_NVM_BASE			V2M_FLASH0_BASE
+#define PLAT_ARM_NVM_SIZE			UL(0x02000000)  /* 32 MB */
+
+#define PLAT_ARM_FLASH_IMAGE_BASE		PLAT_ARM_FIP_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE		PLAT_ARM_FIP_MAX_SIZE
+
+/*
+ * Some data must be aligned on the biggest cache line size in the platform.
+ * This is known only to the platform as it might have a combination of
+ * integrated and external caches.
+ */
+#define CACHE_WRITEBACK_GRANULE		(U(1) << ARM_CACHE_WRITEBACK_SHIFT)
+#define ARM_CACHE_WRITEBACK_SHIFT		6
+
+/*
+ * Define FW_CONFIG area base and limit. Leave enough space for BL2 meminfo.
+ * FW_CONFIG is intended to host the device tree. Currently, This area is not
+ * used because diphda platform doesn't use a device tree at TF-A level.
+ */
+#define ARM_FW_CONFIG_BASE			(ARM_SHARED_RAM_BASE \
+						+ sizeof(meminfo_t))
+#define ARM_FW_CONFIG_LIMIT			(ARM_SHARED_RAM_BASE \
+						+ (ARM_SHARED_RAM_SIZE >> 1))
+
+/*
+ * Boot parameters passed from BL2 to BL31/BL32 are stored here
+ */
+#define ARM_BL2_MEM_DESC_BASE			ARM_FW_CONFIG_LIMIT
+#define ARM_BL2_MEM_DESC_LIMIT		ARM_BL_RAM_BASE
+
+/*
+ * The max number of regions like RO(code), coherent and data required by
+ * different BL stages which need to be mapped in the MMU.
+ */
+#define ARM_BL_REGIONS			3
+#define PLAT_ARM_MMAP_ENTRIES			8
+#define MAX_XLAT_TABLES			5
+#define MAX_MMAP_REGIONS			(PLAT_ARM_MMAP_ENTRIES + \
+						ARM_BL_REGIONS)
+#define MAX_IO_DEVICES			2
+#define MAX_IO_HANDLES			3
+#define MAX_IO_BLOCK_DEVICES			1
+
+/* GIC related constants */
+#define PLAT_ARM_GICD_BASE			0x1C010000
+#define PLAT_ARM_GICC_BASE			0x1C02F000
+
+/* MHUv2 Secure Channel receiver and sender */
+#define PLAT_SDK700_MHU0_SEND			0x1B800000
+#define PLAT_SDK700_MHU0_RECV			0x1B810000
+
+/* Timer/watchdog related constants */
+#define ARM_SYS_CNTCTL_BASE			UL(0x1a200000)
+#define ARM_SYS_CNTREAD_BASE			UL(0x1a210000)
+#define ARM_SYS_TIMCTL_BASE			UL(0x1a220000)
+
+#define SYS_COUNTER_FREQ_IN_TICKS	UL(50000000) /* 50MHz */
+
+#define DIPHDA_IRQ_TZ_WDOG			32
+#define DIPHDA_IRQ_SEC_SYS_TIMER		34
+
+#define PLAT_MAX_PWR_LVL			2
+/*
+ * Macros mapping the MPIDR Affinity levels to ARM Platform Power levels. The
+ * power levels have a 1:1 mapping with the MPIDR affinity levels.
+ */
+#define ARM_PWR_LVL0				MPIDR_AFFLVL0
+#define ARM_PWR_LVL1				MPIDR_AFFLVL1
+#define ARM_PWR_LVL2				MPIDR_AFFLVL2
+
+/*
+ *  Macros for local power states in ARM platforms encoded by State-ID field
+ *  within the power-state parameter.
+ */
+/* Local power state for power domains in Run state. */
+#define ARM_LOCAL_STATE_RUN			U(0)
+/* Local power state for retention. Valid only for CPU power domains */
+#define ARM_LOCAL_STATE_RET			U(1)
+/* Local power state for OFF/power-down. Valid for CPU and cluster
+ * power domains
+ */
+#define ARM_LOCAL_STATE_OFF			U(2)
+
+#define PLAT_ARM_TRUSTED_MAILBOX_BASE		ARM_TRUSTED_SRAM_BASE
+#define PLAT_ARM_NSTIMER_FRAME_ID		U(1)
+
+#define PLAT_ARM_NS_IMAGE_BASE		(ARM_NS_SHARED_RAM_BASE)
+
+#define PLAT_PHY_ADDR_SPACE_SIZE		(1ULL << 32)
+#define PLAT_VIRT_ADDR_SPACE_SIZE		(1ULL << 32)
+
+/*
+ * This macro defines the deepest retention state possible. A higher state
+ * ID will represent an invalid or a power down state.
+ */
+#define PLAT_MAX_RET_STATE			1
+
+/*
+ * This macro defines the deepest power down states possible. Any state ID
+ * higher than this is invalid.
+ */
+#define PLAT_MAX_OFF_STATE			2
+
+#define PLATFORM_STACK_SIZE			UL(0x440)
+
+#define DIPHDA_EXTERNAL_FLASH			MAP_REGION_FLAT(	\
+						PLAT_ARM_NVM_BASE,	\
+						PLAT_ARM_NVM_SIZE,	\
+						MT_DEVICE | MT_RO | MT_SECURE)
+
+#define ARM_MAP_SHARED_RAM			MAP_REGION_FLAT(	\
+						ARM_SHARED_RAM_BASE,	\
+						ARM_SHARED_RAM_SIZE,	\
+						MT_MEMORY | MT_RW | MT_SECURE)
+
+#define ARM_MAP_NS_SHARED_RAM			MAP_REGION_FLAT(	\
+						ARM_NS_SHARED_RAM_BASE, \
+						ARM_NS_SHARED_RAM_SIZE, \
+						MT_MEMORY | MT_RW | MT_NS)
+
+#define ARM_MAP_NS_DRAM1			MAP_REGION_FLAT(	\
+						ARM_NS_DRAM1_BASE,	\
+						ARM_NS_DRAM1_SIZE,	\
+						MT_MEMORY | MT_RW | MT_NS)
+
+#define ARM_MAP_BL_RO				MAP_REGION_FLAT(	\
+						BL_CODE_BASE,		\
+						BL_CODE_END		\
+							- BL_CODE_BASE, \
+						MT_CODE | MT_SECURE),	\
+						MAP_REGION_FLAT(	\
+						BL_RO_DATA_BASE,	\
+						BL_RO_DATA_END	\
+						- BL_RO_DATA_BASE,	\
+						MT_RO_DATA | MT_SECURE)
+#if USE_COHERENT_MEM
+#define ARM_MAP_BL_COHERENT_RAM		MAP_REGION_FLAT(	\
+						BL_COHERENT_RAM_BASE,	\
+						BL_COHERENT_RAM_END	\
+						- BL_COHERENT_RAM_BASE, \
+						MT_DEVICE | MT_RW | MT_SECURE)
+#endif
+
+/*
+ * Map the region for the optional device tree configuration with read and
+ * write permissions
+ */
+#define ARM_MAP_BL_CONFIG_REGION		MAP_REGION_FLAT(	\
+						ARM_FW_CONFIG_BASE,	\
+						(ARM_FW_CONFIG_LIMIT-   \
+						ARM_FW_CONFIG_BASE),   \
+						MT_MEMORY | MT_RW | MT_SECURE)
+
+#define DIPHDA_DEVICE_BASE			(0x1A000000)
+#define DIPHDA_DEVICE_SIZE			(0x26000000)
+#define DIPHDA_MAP_DEVICE			MAP_REGION_FLAT(	\
+						DIPHDA_DEVICE_BASE,	\
+						DIPHDA_DEVICE_SIZE,	\
+						MT_DEVICE | MT_RW | MT_SECURE)
+
+#define ARM_IRQ_SEC_PHY_TIMER			29
+
+#define ARM_IRQ_SEC_SGI_0			8
+#define ARM_IRQ_SEC_SGI_1			9
+#define ARM_IRQ_SEC_SGI_2			10
+#define ARM_IRQ_SEC_SGI_3			11
+#define ARM_IRQ_SEC_SGI_4			12
+#define ARM_IRQ_SEC_SGI_5			13
+#define ARM_IRQ_SEC_SGI_6			14
+#define ARM_IRQ_SEC_SGI_7			15
+
+/*
+ * Define a list of Group 1 Secure and Group 0 interrupt properties as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define ARM_G1S_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(ARM_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, \
+		(grp), GIC_INTR_CFG_LEVEL), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_1, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_2, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_3, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_4, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_5, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_7, GIC_HIGHEST_SEC_PRIORITY,	\
+		(grp), GIC_INTR_CFG_EDGE)
+
+#define ARM_G0_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_6, GIC_HIGHEST_SEC_PRIORITY, (grp), \
+		GIC_INTR_CFG_EDGE)
+
+/*
+ * Define a list of Group 1 Secure and Group 0 interrupts as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define PLAT_ARM_G1S_IRQ_PROPS(grp)	\
+	ARM_G1S_IRQ_PROPS(grp), \
+	INTR_PROP_DESC(DIPHDA_IRQ_TZ_WDOG, GIC_HIGHEST_SEC_PRIORITY, \
+		(grp), GIC_INTR_CFG_LEVEL), \
+	INTR_PROP_DESC(DIPHDA_IRQ_SEC_SYS_TIMER, \
+		GIC_HIGHEST_SEC_PRIORITY, (grp), GIC_INTR_CFG_LEVEL)
+
+#define PLAT_ARM_G0_IRQ_PROPS(grp)	ARM_G0_IRQ_PROPS(grp)
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/diphda/include/plat_macros.S b/plat/arm/board/diphda/include/plat_macros.S
new file mode 100644
index 0000000..4de8f95
--- /dev/null
+++ b/plat/arm/board/diphda/include/plat_macros.S
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef PLAT_MACROS_S
+#define PLAT_MACROS_S
+
+#include <css_macros.S>
+
+/* ---------------------------------------------
+ * The below required platform porting macro
+ * prints out relevant platform registers
+ * whenever an unhandled exception is taken in
+ * BL31.
+ * ---------------------------------------------
+ */
+	.macro plat_crash_print_regs
+	css_print_gic_regs
+	.endm
+
+#endif /* PLAT_MACROS_S */
diff --git a/plat/arm/board/diphda/platform.mk b/plat/arm/board/diphda/platform.mk
new file mode 100644
index 0000000..8b89cee
--- /dev/null
+++ b/plat/arm/board/diphda/platform.mk
@@ -0,0 +1,83 @@
+#
+# Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Making sure the diphda platform type is specified
+ifeq ($(filter ${TARGET_PLATFORM}, fpga fvp),)
+	$(error TARGET_PLATFORM must be fpga or fvp)
+endif
+
+DIPHDA_CPU_LIBS	+=lib/cpus/aarch64/cortex_a35.S
+
+PLAT_INCLUDES		:=	-Iplat/arm/board/diphda/common/include	\
+				-Iplat/arm/board/diphda/include		\
+				-Iinclude/plat/arm/common			\
+				-Iinclude/plat/arm/css/common/aarch64
+
+
+DIPHDA_FW_NVCTR_VAL	:=	255
+TFW_NVCTR_VAL		:=	${DIPHDA_FW_NVCTR_VAL}
+NTFW_NVCTR_VAL		:=	${DIPHDA_FW_NVCTR_VAL}
+
+override NEED_BL1	:=	no
+
+override NEED_BL2	:=	yes
+FIP_BL2_ARGS := tb-fw
+
+override NEED_BL2U	:=	no
+override NEED_BL31	:=	yes
+NEED_BL32		:=	yes
+override NEED_BL33	:=	yes
+
+# Include GICv2 driver files
+include drivers/arm/gic/v2/gicv2.mk
+
+DIPHDA_GIC_SOURCES	:=	${GICV2_SOURCES}			\
+				plat/common/plat_gicv2.c		\
+				plat/arm/common/arm_gicv2.c
+
+
+BL2_SOURCES		+=	plat/arm/board/diphda/common/diphda_security.c		\
+				plat/arm/board/diphda/common/diphda_err.c		\
+				plat/arm/board/diphda/common/diphda_trusted_boot.c	\
+				lib/utils/mem_region.c					\
+				plat/arm/board/diphda/common/diphda_helpers.S		\
+				plat/arm/board/diphda/common/diphda_plat.c		\
+				plat/arm/board/diphda/common/diphda_bl2_mem_params_desc.c \
+				${DIPHDA_CPU_LIBS}					\
+
+
+BL31_SOURCES	+=	drivers/cfi/v2m/v2m_flash.c				\
+			lib/utils/mem_region.c					\
+			plat/arm/board/diphda/common/diphda_helpers.S		\
+			plat/arm/board/diphda/common/diphda_topology.c		\
+			plat/arm/board/diphda/common/diphda_security.c		\
+			plat/arm/board/diphda/common/diphda_plat.c		\
+			plat/arm/board/diphda/common/diphda_pm.c		\
+			${DIPHDA_CPU_LIBS}					\
+			${DIPHDA_GIC_SOURCES}
+
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+	ifneq (${ENABLE_STACK_PROTECTOR},none)
+		DIPHDA_SECURITY_SOURCES := plat/arm/board/diphda/common/diphda_stack_protector.c
+		BL2_SOURCES += ${DIPHDA_SECURITY_SOURCES}
+		BL31_SOURCES += ${DIPHDA_SECURITY_SOURCES}
+	endif
+endif
+
+FDT_SOURCES		+=	plat/arm/board/diphda/common/fdts/diphda_spmc_manifest.dts
+DIPHDA_TOS_FW_CONFIG	:=	${BUILD_PLAT}/fdts/diphda_spmc_manifest.dtb
+
+# Add the SPMC manifest to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${DIPHDA_TOS_FW_CONFIG},--tos-fw-config,${DIPHDA_TOS_FW_CONFIG}))
+
+# Adding TARGET_PLATFORM as a GCC define (-D option)
+$(eval $(call add_define,TARGET_PLATFORM_$(call uppercase,${TARGET_PLATFORM})))
+
+# Adding DIPHDA_FW_NVCTR_VAL as a GCC define (-D option)
+$(eval $(call add_define,DIPHDA_FW_NVCTR_VAL))
+
+include plat/arm/common/arm_common.mk
+include plat/arm/board/common/board_common.mk
diff --git a/plat/arm/board/fvp/fconf/fconf_hw_config_getter.c b/plat/arm/board/fvp/fconf/fconf_hw_config_getter.c
index 35a777b..45e3b7e 100644
--- a/plat/arm/board/fvp/fconf/fconf_hw_config_getter.c
+++ b/plat/arm/board/fvp/fconf/fconf_hw_config_getter.c
@@ -5,6 +5,9 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/debug.h>
 #include <common/fdt_wrappers.h>
 #include <fconf_hw_config_getter.h>
@@ -229,7 +232,7 @@
 
 	uart_serial_config.uart_base = translated_addr;
 
-	VERBOSE("FCONF: UART serial device base address: %llx\n",
+	VERBOSE("FCONF: UART serial device base address: %" PRIx64 "\n",
 		uart_serial_config.uart_base);
 
 	/*
diff --git a/plat/arm/board/fvp/fdts/fvp_fw_config.dts b/plat/arm/board/fvp/fdts/fvp_fw_config.dts
index 9fb566b..c26b519 100644
--- a/plat/arm/board/fvp/fdts/fvp_fw_config.dts
+++ b/plat/arm/board/fvp/fdts/fvp_fw_config.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -36,11 +36,14 @@
 			id = <SOC_FW_CONFIG_ID>;
 		};
 
+/* If required, SPD should enable loading of trusted OS fw config */
+#if defined(SPD_tspd) || defined(SPD_spmd)
 		tos_fw-config {
 			load-address = <0x0 0x04001500>;
 			max-size = <0xB00>;
 			id = <TOS_FW_CONFIG_ID>;
 		};
+#endif
 
 		nt_fw-config {
 			load-address = <0x0 0x80000000>;
diff --git a/plat/arm/board/fvp/fdts/fvp_spmc_manifest.dts b/plat/arm/board/fvp/fdts/fvp_spmc_manifest.dts
index 8b9c281..21a6073 100644
--- a/plat/arm/board/fvp/fdts/fvp_spmc_manifest.dts
+++ b/plat/arm/board/fvp/fdts/fvp_spmc_manifest.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -20,24 +20,21 @@
 	attribute {
 		spmc_id = <0x8000>;
 		maj_ver = <0x1>;
-		min_ver = <0x0>;
+		min_ver = <0x1>;
 		exec_state = <0x0>;
 		load_address = <0x0 0x6000000>;
 		entrypoint = <0x0 0x6000000>;
 		binary_size = <0x80000>;
 	};
 
-	chosen {
-		linux,initrd-start = <0>;
-		linux,initrd-end = <0>;
-	};
-
 	hypervisor {
 		compatible = "hafnium,hafnium";
 		vm1 {
 			is_ffa_partition;
 			debug_name = "cactus-primary";
 			load_address = <0x7000000>;
+			vcpu_count = <8>;
+			mem_size = <1048576>;
 		};
 		vm2 {
 			is_ffa_partition;
@@ -50,7 +47,14 @@
 			is_ffa_partition;
 			debug_name = "cactus-tertiary";
 			load_address = <0x7200000>;
-			vcpu_count = <8>;
+			vcpu_count = <1>;
+			mem_size = <1048576>;
+		};
+		vm4 {
+			is_ffa_partition;
+			debug_name = "ivy";
+			load_address = <0x7600000>;
+			vcpu_count = <1>;
 			mem_size = <1048576>;
 		};
 	};
@@ -74,11 +78,6 @@
 		CPU_1
 	};
 
-	device-memory@0 {
-		device_type = "device-memory";
-		reg = <0x0 0x0 0x6000000 0x0 0x8000000 0x78000000>;
-	};
-
 	memory@6000000 {
 		device_type = "memory";
 		reg = <0x0 0x6000000 0x2000000>; /* Trusted DRAM */
diff --git a/plat/arm/board/fvp/fdts/fvp_spmc_optee_sp_manifest.dts b/plat/arm/board/fvp/fdts/fvp_spmc_optee_sp_manifest.dts
index 266adfc..041dade 100644
--- a/plat/arm/board/fvp/fdts/fvp_spmc_optee_sp_manifest.dts
+++ b/plat/arm/board/fvp/fdts/fvp_spmc_optee_sp_manifest.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -20,25 +20,21 @@
 	attribute {
 		spmc_id = <0x8000>;
 		maj_ver = <0x1>;
-		min_ver = <0x0>;
+		min_ver = <0x1>;
 		exec_state = <0x0>;
 		load_address = <0x0 0x6000000>;
 		entrypoint = <0x0 0x6000000>;
 		binary_size = <0x80000>;
 	};
 
-	chosen {
-		linux,initrd-start = <0>;
-		linux,initrd-end = <0>;
-	};
-
 	hypervisor {
 		compatible = "hafnium,hafnium";
 		vm1 {
 			is_ffa_partition;
 			debug_name = "op-tee";
 			load_address = <0x6280000>;
-			smc_whitelist = <0xbe000000>;
+			vcpu_count = <8>;
+			mem_size = <1048576>;
 		};
 	};
 
@@ -61,11 +57,6 @@
 		CPU_1
 	};
 
-	device-memory@0 {
-		device_type = "device-memory";
-		reg = <0x0 0x0 0x6000000 0x0 0x8000000 0x78000000>;
-	};
-
 	memory@6000000 {
 		device_type = "memory";
 		reg = <0x0 0x6000000 0x2000000>; /* Trusted DRAM */
diff --git a/plat/arm/board/fvp/fdts/fvp_tb_fw_config.dts b/plat/arm/board/fvp/fdts/fvp_tb_fw_config.dts
index fe154e9..cf4ef2d 100644
--- a/plat/arm/board/fvp/fdts/fvp_tb_fw_config.dts
+++ b/plat/arm/board/fvp/fdts/fvp_tb_fw_config.dts
@@ -1,9 +1,11 @@
 /*
- * Copyright (c) 2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <lib/libc/cdefs.h>
+
 /dts-v1/;
 
 / {
@@ -24,19 +26,6 @@
 		 */
 		mbedtls_heap_addr = <0x0 0x0>;
 		mbedtls_heap_size = <0x0>;
-
-#if MEASURED_BOOT
-		/* BL2 image hash calculated by BL1 */
-		bl2_hash_data = [
-			00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
-#if BL2_HASH_SIZE > 32
-			00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
-#if BL2_HASH_SIZE > 48
-			00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
-#endif /* > 48 */
-#endif /* > 32 */
-			00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00];
-#endif /* MEASURED_BOOT */
 	};
 
 	/*
@@ -48,61 +37,77 @@
 	arm-io_policies {
 		fip-handles {
 			compatible = "arm,io-fip-handle";
-			scp_bl2_uuid = <0x9766fd3d 0x89bee849 0xae5d78a1 0x40608213>;
-			bl31_uuid = <0x47d4086d 0x4cfe9846 0x9b952950 0xcbbd5a00>;
-			bl32_uuid = <0x05d0e189 0x53dc1347 0x8d2b500a 0x4b7a3e38>;
-			bl32_extra1_uuid = <0x0b70c28b 0x2a5a7840 0x9f650a56 0x82738288>;
-			bl32_extra2_uuid = <0x8ea87bb1 0xcfa23f4d 0x85fde7bb 0xa50220d9>;
-			bl33_uuid = <0xd6d0eea7 0xfcead54b 0x97829934 0xf234b6e4>;
-			hw_cfg_uuid = <0x08b8f1d9 0xc9cf9349 0xa9626fbc 0x6b7265cc>;
-			soc_fw_cfg_uuid = <0x9979814b 0x0376fb46 0x8c8e8d26 0x7f7859e0>;
-			tos_fw_cfg_uuid = <0x26257c1a 0xdbc67f47 0x8d96c4c4 0xb0248021>;
-			nt_fw_cfg_uuid = <0x28da9815 0x93e87e44 0xac661aaf 0x801550f9>;
-			t_key_cert_uuid = <0x827ee890 0xf860e411 0xa1b477a7 0x21b4f94c>;
-			scp_fw_key_uuid = <0x024221a1 0xf860e411 0x8d9bf33c 0x0e15a014>;
-			soc_fw_key_uuid = <0x8ab8becc 0xf960e411 0x9ad0eb48 0x22d8dcf8>;
-			tos_fw_key_cert_uuid = <0x9477d603 0xfb60e411 0x85ddb710 0x5b8cee04>;
-			nt_fw_key_cert_uuid = <0x8ad5832a 0xfb60e411 0x8aafdf30 0xbbc49859>;
-			scp_fw_content_cert_uuid = <0x44be6f04 0x5e63e411 0xb28b73d8 0xeaae9656>;
-			soc_fw_content_cert_uuid = <0xe2b20c20 0x5e63e411 0x9ce8abcc 0xf92bb666>;
-			tos_fw_content_cert_uuid = <0xa49f4411 0x5e63e411 0x87283f05 0x722af33d>;
-			nt_fw_content_cert_uuid = <0x8ec4c1f3 0x5d63e411 0xa7a987ee 0x40b23fa7>;
-			sp_content_cert_uuid = <0x776dfd44 0x86974c3b 0x91ebc13e 0x025a2a6f>;
+			scp_bl2_uuid = "9766fd3d-89be-e849-ae5d-78a140608213";
+			bl31_uuid = "47d4086d-4cfe-9846-9b95-2950cbbd5a00";
+			bl32_uuid = "05d0e189-53dc-1347-8d2b-500a4b7a3e38";
+			bl32_extra1_uuid = "0b70c29b-2a5a-7840-9f65-0a5682738288";
+			bl32_extra2_uuid = "8ea87bb1-cfa2-3f4d-85fd-e7bba50220d9";
+			bl33_uuid = "d6d0eea7-fcea-d54b-9782-9934f234b6e4";
+			hw_cfg_uuid = "08b8f1d9-c9cf-9349-a962-6fbc6b7265cc";
+			soc_fw_cfg_uuid = "9979814b-0376-fb46-8c8e-8d267f7859e0";
+			tos_fw_cfg_uuid = "26257c1a-dbc6-7f47-8d96-c4c4b0248021";
+			nt_fw_cfg_uuid = "28da9815-93e8-7e44-ac66-1aaf801550f9";
+			t_key_cert_uuid = "827ee890-f860-e411-a1b4-777a21b4f94c";
+			scp_fw_key_uuid = "024221a1-f860-e411-8d9b-f33c0e15a014";
+			soc_fw_key_uuid = "8ab8becc-f960-e411-9ad0-eb4822d8dcf8";
+			tos_fw_key_cert_uuid = "9477d603-fb60-e411-85dd-b7105b8cee04";
+			nt_fw_key_cert_uuid = "8ad5832a-fb60-e411-8aaf-df30bbc49859";
+			scp_fw_content_cert_uuid = "44be6f04-5e63-e411-b28b-73d8eaae9656";
+			soc_fw_content_cert_uuid = "e2b20c20-5e63-e411-9ce8-abccf92bb666";
+			tos_fw_content_cert_uuid = "a49f4411-5e63-e411-8728-3f05722af33d";
+			nt_fw_content_cert_uuid = "8ec4c1f3-5d63-e411-a7a9-87ee40b23fa7";
+			sp_content_cert_uuid = "776dfd44-8697-4c3b-91eb-c13e025a2a6f";
 		};
 	};
 #endif /* ARM_IO_IN_DTB */
 
 	secure-partitions {
 		compatible = "arm,sp";
+
+#ifdef ARM_BL2_SP_LIST_DTS
+	#include __XSTRING(ARM_BL2_SP_LIST_DTS)
+#else
 #ifdef OPTEE_SP_FW_CONFIG
 		op-tee {
-			uuid = <0x486178e0 0xe7f811e3 0xbc5e0002 0xa5d5c51b>;
+			uuid = "486178e0-e7f8-11e3-bc5e-0002a5d5c51b";
 			load-address = <0x6280000>;
 		};
 #else
 		cactus-primary {
-			uuid = <0xb4b5671e 0x4a904fe1 0xb81ffb13 0xdae1dacb>;
+			uuid = "b4b5671e-4a90-4fe1-b81f-fb13dae1dacb";
 			load-address = <0x7000000>;
 			owner = "SiP";
 		};
 
 		cactus-secondary {
-			uuid = <0xd1582309 0xf02347b9 0x827c4464 0xf5578fc8>;
+			uuid = "d1582309-f023-47b9-827c-4464f5578fc8";
 			load-address = <0x7100000>;
 			owner = "Plat";
 		};
 
 		cactus-tertiary {
-			uuid = <0x79b55c73 0x1d8c44b9 0x859361e1 0x770ad8d2>;
+			uuid = "79b55c73-1d8c-44b9-8593-61e1770ad8d2";
 			load-address = <0x7200000>;
+			owner = "Plat";
+		};
+
+		ivy {
+			uuid = "eaba83d8-baaf-4eaf-8144-f7fdcbe544a7";
+			load-address = <0x7600000>;
+			owner = "Plat";
 		};
 #endif
+#endif /* ARM_BL2_SP_LIST_DTS */
 	};
 
 #if COT_DESC_IN_DTB
 	#include "cot_descriptors.dtsi"
 #endif
 
+#if MEASURED_BOOT
+	#include "event_log.dtsi"
+#endif
+
 };
 
 #if COT_DESC_IN_DTB
diff --git a/plat/arm/board/fvp/fdts/optee_sp_manifest.dts b/plat/arm/board/fvp/fdts/optee_sp_manifest.dts
new file mode 100644
index 0000000..551efe6
--- /dev/null
+++ b/plat/arm/board/fvp/fdts/optee_sp_manifest.dts
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * This file is a Partition Manifest (PM) for a minimal Secure Partition (SP)
+ * that has additional optional properties defined.
+ *
+ */
+
+/dts-v1/;
+
+/ {
+	compatible = "arm,ffa-manifest-1.0";
+
+	/* Properties */
+	description = "op-tee";
+	ffa-version = <0x00010000>; /* 31:16 - Major, 15:0 - Minor */
+	uuid = <0xe0786148 0xe311f8e7 0x02005ebc 0x1bc5d5a5>;
+	id = <1>;
+	execution-ctx-count = <8>;
+	exception-level = <2>; /* S-EL1 */
+	execution-state = <0>; /* AARCH64 */
+	load-address = <0x6280000>;
+	entrypoint-offset = <0x1000>;
+	xlat-granule = <0>; /* 4KiB */
+	boot-order = <0>;
+	messaging-method = <0x3>; /* Direct request/response supported. */
+	managed-exit;
+	run-time-model = <1>; /* SP pre-emptible. */
+
+	/* Boot protocol */
+	gp-register-num = <0x0>;
+
+	device-regions {
+		compatible = "arm,ffa-manifest-device-regions";
+
+		uart1 {
+			base-address = <0x00000000 0x1c0a0000>;
+			pages-count = <1>;
+			attributes = <0x3>; /* read-write */
+		};
+
+		gicd {
+			base-address = <0x00000000 0x2f000000>;
+			pages-count = <16>;
+			attributes = <0x3>; /* read-write */
+		};
+	};
+};
diff --git a/plat/arm/board/fvp/fvp_bl1_measured_boot.c b/plat/arm/board/fvp/fvp_bl1_measured_boot.c
new file mode 100644
index 0000000..47af1f5
--- /dev/null
+++ b/plat/arm/board/fvp/fvp_bl1_measured_boot.c
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <drivers/measured_boot/event_log/event_log.h>
+#include <plat/arm/common/plat_arm.h>
+
+/* Event Log data */
+static uint8_t event_log[PLAT_ARM_EVENT_LOG_MAX_SIZE];
+
+/* FVP table with platform specific image IDs, names and PCRs */
+const event_log_metadata_t fvp_event_log_metadata[] = {
+	{ FW_CONFIG_ID, EVLOG_FW_CONFIG_STRING, PCR_0 },
+	{ TB_FW_CONFIG_ID, EVLOG_TB_FW_CONFIG_STRING, PCR_0 },
+	{ BL2_IMAGE_ID, EVLOG_BL2_STRING, PCR_0 },
+	{ INVALID_ID, NULL, (unsigned int)(-1) }	/* Terminator */
+};
+
+void bl1_plat_mboot_init(void)
+{
+	event_log_init(event_log, event_log + sizeof(event_log));
+	event_log_write_header();
+}
+
+void bl1_plat_mboot_finish(void)
+{
+	size_t event_log_cur_size;
+
+	event_log_cur_size = event_log_get_cur_size(event_log);
+	int rc = arm_set_tb_fw_info((uintptr_t)event_log,
+				    event_log_cur_size);
+	if (rc != 0) {
+		/*
+		 * It is a fatal error because on FVP platform, BL2 software
+		 * assumes that a valid Event Log buffer exist and it will use
+		 * same Event Log buffer to append image measurements.
+		 */
+		panic();
+	}
+}
diff --git a/plat/arm/board/fvp/fvp_bl1_setup.c b/plat/arm/board/fvp/fvp_bl1_setup.c
index e713bbc..59fc0f3 100644
--- a/plat/arm/board/fvp/fvp_bl1_setup.c
+++ b/plat/arm/board/fvp/fvp_bl1_setup.c
@@ -1,15 +1,17 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <errno.h>
 
 #include <bl1/bl1.h>
 #include <common/tbbr/tbbr_img_def.h>
 #include <drivers/arm/smmu_v3.h>
 #include <drivers/arm/sp805.h>
+#include <lib/mmio.h>
 #include <plat/arm/common/arm_config.h>
 #include <plat/arm/common/plat_arm.h>
 #include <plat/arm/common/arm_def.h>
@@ -61,6 +63,12 @@
 
 __dead2 void bl1_plat_fwu_done(void *client_cookie, void *reserved)
 {
+	uint32_t nv_flags = mmio_read_32(V2M_SYS_NVFLAGS_ADDR);
+
+	/* Clear the NV flags register. */
+	mmio_write_32((V2M_SYSREGS_BASE + V2M_SYS_NVFLAGSCLR),
+		      nv_flags);
+
 	/* Setup the watchdog to reset the system as soon as possible */
 	sp805_refresh(ARM_SP805_TWDG_BASE, 1U);
 
@@ -68,59 +76,14 @@
 		wfi();
 }
 
-#if MEASURED_BOOT
-/*
- * Calculates and writes BL2 hash data to TB_FW_CONFIG DTB.
- */
-void bl1_plat_set_bl2_hash(const image_desc_t *image_desc)
+/*******************************************************************************
+ * The following function checks if Firmware update is needed by checking error
+ * reported in NV flag.
+ ******************************************************************************/
+bool plat_arm_bl1_fwu_needed(void)
 {
-	arm_bl1_set_bl2_hash(image_desc);
+	int32_t nv_flags = (int32_t)mmio_read_32(V2M_SYS_NVFLAGS_ADDR);
+
+	/* if image load/authentication failed */
+	return ((nv_flags == -EAUTH) || (nv_flags == -ENOENT));
 }
-
-/*
- * Implementation for bl1_plat_handle_post_image_load(). This function
- * populates the default arguments to BL2. The BL2 memory layout structure
- * is allocated and the calculated layout is populated in arg1 to BL2.
- */
-int bl1_plat_handle_post_image_load(unsigned int image_id)
-{
-	meminfo_t *bl2_tzram_layout;
-	meminfo_t *bl1_tzram_layout;
-	image_desc_t *image_desc;
-	entry_point_info_t *ep_info;
-
-	if (image_id != BL2_IMAGE_ID) {
-		return 0;
-	}
-
-	/* Get the image descriptor */
-	image_desc = bl1_plat_get_image_desc(BL2_IMAGE_ID);
-	assert(image_desc != NULL);
-
-	/* Calculate BL2 hash and set it in TB_FW_CONFIG */
-	bl1_plat_set_bl2_hash(image_desc);
-
-	/* Get the entry point info */
-	ep_info = &image_desc->ep_info;
-
-	/* Find out how much free trusted ram remains after BL1 load */
-	bl1_tzram_layout = bl1_plat_sec_mem_layout();
-
-	/*
-	 * Create a new layout of memory for BL2 as seen by BL1 i.e.
-	 * tell it the amount of total and free memory available.
-	 * This layout is created at the first free address visible
-	 * to BL2. BL2 will read the memory layout before using its
-	 * memory for other purposes.
-	 */
-	bl2_tzram_layout = (meminfo_t *)bl1_tzram_layout->total_base;
-
-	bl1_calc_bl2_mem_layout(bl1_tzram_layout, bl2_tzram_layout);
-
-	ep_info->args.arg1 = (uintptr_t)bl2_tzram_layout;
-
-	VERBOSE("BL1: BL2 memory layout address = %p\n",
-		(void *)bl2_tzram_layout);
-	return 0;
-}
-#endif /* MEASURED_BOOT */
diff --git a/plat/arm/board/fvp/fvp_bl2_measured_boot.c b/plat/arm/board/fvp/fvp_bl2_measured_boot.c
new file mode 100644
index 0000000..5ebfede
--- /dev/null
+++ b/plat/arm/board/fvp/fvp_bl2_measured_boot.c
@@ -0,0 +1,110 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <drivers/measured_boot/event_log/event_log.h>
+#include <plat/arm/common/plat_arm.h>
+
+/* Event Log data */
+static uint64_t event_log_base;
+
+/* FVP table with platform specific image IDs, names and PCRs */
+const event_log_metadata_t fvp_event_log_metadata[] = {
+	{ BL31_IMAGE_ID, EVLOG_BL31_STRING, PCR_0 },
+	{ BL32_IMAGE_ID, EVLOG_BL32_STRING, PCR_0 },
+	{ BL32_EXTRA1_IMAGE_ID, EVLOG_BL32_EXTRA1_STRING, PCR_0 },
+	{ BL32_EXTRA2_IMAGE_ID, EVLOG_BL32_EXTRA2_STRING, PCR_0 },
+	{ BL33_IMAGE_ID, EVLOG_BL33_STRING, PCR_0 },
+	{ HW_CONFIG_ID, EVLOG_HW_CONFIG_STRING, PCR_0 },
+	{ NT_FW_CONFIG_ID, EVLOG_NT_FW_CONFIG_STRING, PCR_0 },
+	{ SCP_BL2_IMAGE_ID, EVLOG_SCP_BL2_STRING, PCR_0 },
+	{ SOC_FW_CONFIG_ID, EVLOG_SOC_FW_CONFIG_STRING, PCR_0 },
+	{ TOS_FW_CONFIG_ID, EVLOG_TOS_FW_CONFIG_STRING, PCR_0 },
+	{ INVALID_ID, NULL, (unsigned int)(-1) }	/* Terminator */
+};
+
+void bl2_plat_mboot_init(void)
+{
+	uint8_t *event_log_start;
+	uint8_t *event_log_finish;
+	size_t bl1_event_log_size;
+	int rc;
+
+	rc = arm_get_tb_fw_info(&event_log_base, &bl1_event_log_size);
+	if (rc != 0) {
+		ERROR("%s(): Unable to get Event Log info from TB_FW_CONFIG\n",
+		      __func__);
+		/*
+		 * It is a fatal error because on FVP platform, BL2 software
+		 * assumes that a valid Event Log buffer exist and it will use
+		 * same Event Log buffer to append image measurements.
+		 */
+		panic();
+	}
+
+	/*
+	 * BL1 and BL2 share the same Event Log buffer and that BL2 will
+	 * append its measurements after BL1's
+	 */
+	event_log_start = (uint8_t *)((uintptr_t)event_log_base +
+				      bl1_event_log_size);
+	event_log_finish = (uint8_t *)((uintptr_t)event_log_base +
+				       PLAT_ARM_EVENT_LOG_MAX_SIZE);
+
+	event_log_init((uint8_t *)event_log_start, event_log_finish);
+}
+
+void bl2_plat_mboot_finish(void)
+{
+	int rc;
+
+	/* Event Log address in Non-Secure memory */
+	uintptr_t ns_log_addr;
+
+	/* Event Log filled size */
+	size_t event_log_cur_size;
+
+	event_log_cur_size = event_log_get_cur_size((uint8_t *)event_log_base);
+
+	rc = arm_set_nt_fw_info(
+#ifdef SPD_opteed
+			    (uintptr_t)event_log_base,
+#endif
+			    event_log_cur_size, &ns_log_addr);
+	if (rc != 0) {
+		ERROR("%s(): Unable to update %s_FW_CONFIG\n",
+		      __func__, "NT");
+		/*
+		 * It is a fatal error because on FVP secure world software
+		 * assumes that a valid event log exists and will use it to
+		 * record the measurements into the fTPM.
+		 * Note: In FVP platform, OP-TEE uses nt_fw_config to get the
+		 * secure Event Log buffer address.
+		 */
+		panic();
+	}
+
+	/* Copy Event Log to Non-secure memory */
+	(void)memcpy((void *)ns_log_addr, (const void *)event_log_base,
+		     event_log_cur_size);
+
+	/* Ensure that the Event Log is visible in Non-secure memory */
+	flush_dcache_range(ns_log_addr, event_log_cur_size);
+
+#if defined(SPD_tspd) || defined(SPD_spmd)
+	/* Set Event Log data in TOS_FW_CONFIG */
+	rc = arm_set_tos_fw_info((uintptr_t)event_log_base,
+				 event_log_cur_size);
+	if (rc != 0) {
+		ERROR("%s(): Unable to update %s_FW_CONFIG\n",
+		      __func__, "TOS");
+		panic();
+	}
+#endif /* defined(SPD_tspd) || defined(SPD_spmd) */
+
+	dump_event_log((uint8_t *)event_log_base, event_log_cur_size);
+}
diff --git a/plat/arm/board/fvp/fvp_bl2_setup.c b/plat/arm/board/fvp/fvp_bl2_setup.c
index f2f2143..5a17a0d 100644
--- a/plat/arm/board/fvp/fvp_bl2_setup.c
+++ b/plat/arm/board/fvp/fvp_bl2_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,9 +9,6 @@
 #include <common/debug.h>
 #include <common/desc_image_load.h>
 #include <drivers/arm/sp804_delay_timer.h>
-#if MEASURED_BOOT
-#include <drivers/measured_boot/measured_boot.h>
-#endif
 #include <lib/fconf/fconf.h>
 #include <lib/fconf/fconf_dyn_cfg_getter.h>
 
@@ -73,45 +70,3 @@
 
 	return arm_bl_params;
 }
-#if MEASURED_BOOT
-static int fvp_bl2_plat_handle_post_image_load(unsigned int image_id)
-{
-	const bl_mem_params_node_t *bl_mem_params =
-				get_bl_mem_params_node(image_id);
-
-	assert(bl_mem_params != NULL);
-
-	image_info_t info = bl_mem_params->image_info;
-	int err;
-
-	if ((info.h.attr & IMAGE_ATTRIB_SKIP_LOADING) == 0U) {
-		/* Calculate image hash and record data in Event Log */
-		err = tpm_record_measurement(info.image_base,
-					     info.image_size, image_id);
-		if (err != 0) {
-			ERROR("%s%s image id %u (%i)\n",
-				"BL2: Failed to ", "record", image_id, err);
-			return err;
-		}
-	}
-
-	err = arm_bl2_handle_post_image_load(image_id);
-	if (err != 0) {
-		ERROR("%s%s image id %u (%i)\n",
-			"BL2: Failed to ", "handle", image_id, err);
-	}
-
-	return err;
-}
-
-int arm_bl2_plat_handle_post_image_load(unsigned int image_id)
-{
-	int err = fvp_bl2_plat_handle_post_image_load(image_id);
-
-	if (err != 0) {
-		ERROR("%s() returns %i\n", __func__, err);
-	}
-
-	return err;
-}
-#endif	/* MEASURED_BOOT */
diff --git a/plat/arm/board/fvp/fvp_common.c b/plat/arm/board/fvp/fvp_common.c
index 6e479ac..e7a28ac 100644
--- a/plat/arm/board/fvp/fvp_common.c
+++ b/plat/arm/board/fvp/fvp_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -48,6 +48,18 @@
 					DEVICE1_SIZE,			\
 					MT_DEVICE | MT_RW | MT_SECURE)
 
+#if FVP_GICR_REGION_PROTECTION
+#define MAP_GICD_MEM	MAP_REGION_FLAT(BASE_GICD_BASE,			\
+					BASE_GICD_SIZE,			\
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+/* Map all core's redistributor memory as read-only. After boots up,
+ * per-core map its redistributor memory as read-write */
+#define MAP_GICR_MEM	MAP_REGION_FLAT(BASE_GICR_BASE,			\
+					(BASE_GICR_SIZE * PLATFORM_CORE_COUNT),\
+					MT_DEVICE | MT_RO | MT_SECURE)
+#endif /* FVP_GICR_REGION_PROTECTION */
+
 /*
  * Need to be mapped with write permissions in order to set a new non-volatile
  * counter value.
@@ -60,17 +72,16 @@
  * Table of memory regions for various BL stages to map using the MMU.
  * This doesn't include Trusted SRAM as setup_page_tables() already takes care
  * of mapping it.
- *
- * The flash needs to be mapped as writable in order to erase the FIP's Table of
- * Contents in case of unrecoverable error (see plat_error_handler()).
  */
 #ifdef IMAGE_BL1
 const mmap_region_t plat_arm_mmap[] = {
 	ARM_MAP_SHARED_RAM,
-	V2M_MAP_FLASH0_RW,
+	V2M_MAP_FLASH0_RO,
 	V2M_MAP_IOFPGA,
 	MAP_DEVICE0,
+#if FVP_INTERCONNECT_DRIVER == FVP_CCN
 	MAP_DEVICE1,
+#endif
 #if TRUSTED_BOARD_BOOT
 	/* To access the Root of Trust Public Key registers. */
 	MAP_DEVICE2,
@@ -86,7 +97,9 @@
 	V2M_MAP_FLASH0_RW,
 	V2M_MAP_IOFPGA,
 	MAP_DEVICE0,
+#if FVP_INTERCONNECT_DRIVER == FVP_CCN
 	MAP_DEVICE1,
+#endif
 	ARM_MAP_NS_DRAM1,
 #ifdef __aarch64__
 	ARM_MAP_DRAM2,
@@ -94,6 +107,10 @@
 #if defined(SPD_spmd)
 	ARM_MAP_TRUSTED_DRAM,
 #endif
+#if ENABLE_RME
+	ARM_MAP_RMM_DRAM,
+	ARM_MAP_GPT_L1_DRAM,
+#endif /* ENABLE_RME */
 #ifdef SPD_tspd
 	ARM_MAP_TSP_SEC_MEM,
 #endif
@@ -134,13 +151,21 @@
 	ARM_MAP_EL3_TZC_DRAM,
 	V2M_MAP_IOFPGA,
 	MAP_DEVICE0,
+#if FVP_GICR_REGION_PROTECTION
+	MAP_GICD_MEM,
+	MAP_GICR_MEM,
+#else
 	MAP_DEVICE1,
+#endif /* FVP_GICR_REGION_PROTECTION */
 	ARM_V2M_MAP_MEM_PROTECT,
 #if SPM_MM
 	ARM_SPM_BUF_EL3_MMAP,
 #endif
 	/* Required by fconf APIs to read HW_CONFIG dtb loaded into DRAM */
 	ARM_DTB_DRAM_NS,
+#if ENABLE_RME
+	ARM_MAP_GPT_L1_DRAM,
+#endif
 	{0}
 };
 
@@ -173,6 +198,15 @@
 };
 #endif
 
+#ifdef IMAGE_RMM
+const mmap_region_t plat_arm_mmap[] = {
+	V2M_MAP_IOFPGA,
+	MAP_DEVICE0,
+	MAP_DEVICE1,
+	{0}
+};
+#endif
+
 ARM_CASSERT_MMAP
 
 #if FVP_INTERCONNECT_DRIVER != FVP_CCN
@@ -462,9 +496,9 @@
 int32_t plat_get_soc_version(void)
 {
 	return (int32_t)
-		((ARM_SOC_IDENTIFICATION_CODE << ARM_SOC_IDENTIFICATION_SHIFT)
-		 | (ARM_SOC_CONTINUATION_CODE << ARM_SOC_CONTINUATION_SHIFT)
-		 | FVP_SOC_ID);
+		(SOC_ID_SET_JEP_106(ARM_SOC_CONTINUATION_CODE,
+				    ARM_SOC_IDENTIFICATION_CODE) |
+		 (FVP_SOC_ID & SOC_ID_IMPL_DEF_MASK));
 }
 
 /* Get SOC revision */
@@ -473,6 +507,6 @@
 	unsigned int sys_id;
 
 	sys_id = mmio_read_32(V2M_SYSREGS_BASE + V2M_SYS_ID);
-	return (int32_t)((sys_id >> V2M_SYS_ID_REV_SHIFT) &
-			V2M_SYS_ID_REV_MASK);
+	return (int32_t)(((sys_id >> V2M_SYS_ID_REV_SHIFT) &
+			  V2M_SYS_ID_REV_MASK) & SOC_ID_REV_MASK);
 }
diff --git a/plat/arm/board/fvp/fvp_common_measured_boot.c b/plat/arm/board/fvp/fvp_common_measured_boot.c
new file mode 100644
index 0000000..6a403d9
--- /dev/null
+++ b/plat/arm/board/fvp/fvp_common_measured_boot.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <common/desc_image_load.h>
+#include <drivers/measured_boot/event_log/event_log.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+
+extern event_log_metadata_t fvp_event_log_metadata[];
+
+const event_log_metadata_t *plat_event_log_get_metadata(void)
+{
+	return fvp_event_log_metadata;
+}
+
+int plat_mboot_measure_image(unsigned int image_id, image_info_t *image_data)
+{
+	/* Calculate image hash and record data in Event Log */
+	int err = event_log_measure_and_record(image_data->image_base,
+					       image_data->image_size,
+					       image_id);
+	if (err != 0) {
+		ERROR("%s%s image id %u (%i)\n",
+		      "Failed to ", "record", image_id, err);
+		return err;
+	}
+
+	return 0;
+}
diff --git a/plat/arm/board/fvp/fvp_def.h b/plat/arm/board/fvp/fvp_def.h
index 4efe692..831eb35 100644
--- a/plat/arm/board/fvp/fvp_def.h
+++ b/plat/arm/board/fvp/fvp_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -135,7 +135,16 @@
 
 /* Base FVP compatible GIC memory map */
 #define BASE_GICD_BASE			UL(0x2f000000)
+#define BASE_GICD_SIZE			UL(0x10000)
 #define BASE_GICR_BASE			UL(0x2f100000)
+
+#if GIC_ENABLE_V4_EXTN
+/* GICv4 redistributor size: 256KB */
+#define BASE_GICR_SIZE			UL(0x40000)
+#else
+#define BASE_GICR_SIZE			UL(0x20000)
+#endif /* GIC_ENABLE_V4_EXTN */
+
 #define BASE_GICC_BASE			UL(0x2c000000)
 #define BASE_GICH_BASE			UL(0x2c010000)
 #define BASE_GICV_BASE			UL(0x2c02f000)
diff --git a/plat/arm/board/fvp/fvp_err.c b/plat/arm/board/fvp/fvp_err.c
index c9b2090..1f9f0dd 100644
--- a/plat/arm/board/fvp/fvp_err.c
+++ b/plat/arm/board/fvp/fvp_err.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,6 +9,7 @@
 #include <common/debug.h>
 #include <drivers/arm/sp805.h>
 #include <drivers/cfi/v2m_flash.h>
+#include <lib/mmio.h>
 #include <plat/arm/common/plat_arm.h>
 #include <platform_def.h>
 
@@ -17,25 +18,8 @@
  */
 __dead2 void plat_arm_error_handler(int err)
 {
-	int ret;
-
-	switch (err) {
-	case -ENOENT:
-	case -EAUTH:
-		/* Image load or authentication error. Erase the ToC */
-		INFO("Erasing FIP ToC from flash...\n");
-		(void)nor_unlock(PLAT_ARM_FIP_BASE);
-		ret = nor_word_program(PLAT_ARM_FIP_BASE, 0);
-		if (ret != 0) {
-			ERROR("Cannot erase ToC\n");
-		} else {
-			INFO("Done\n");
-		}
-		break;
-	default:
-		/* Unexpected error */
-		break;
-	}
+	/* Propagate the err code in the NV-flags register */
+	mmio_write_32(V2M_SYS_NVFLAGS_ADDR, (uint32_t)err);
 
 	console_flush();
 
diff --git a/plat/arm/board/fvp/fvp_gicv3.c b/plat/arm/board/fvp/fvp_gicv3.c
index 3e04d6b..8f3e7b7 100644
--- a/plat/arm/board/fvp/fvp_gicv3.c
+++ b/plat/arm/board/fvp/fvp_gicv3.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,6 +15,11 @@
 #include <plat/arm/common/fconf_sec_intr_config.h>
 #include <plat/common/platform.h>
 
+#if FVP_GICR_REGION_PROTECTION
+/* To indicate GICR region of the core initialized as Read-Write */
+static bool fvp_gicr_rw_region_init[PLATFORM_CORE_COUNT] = {false};
+#endif /* FVP_GICR_REGION_PROTECTION */
+
 /* The GICv3 driver only needs to be initialized in EL3 */
 static uintptr_t fvp_rdistif_base_addrs[PLATFORM_CORE_COUNT];
 
@@ -61,8 +66,39 @@
 	.mpidr_to_core_pos = fvp_gicv3_mpidr_hash
 };
 
+/******************************************************************************
+ * This function gets called per core to make its redistributor frame rw
+ *****************************************************************************/
+static void fvp_gicv3_make_rdistrif_rw(void)
+{
+#if FVP_GICR_REGION_PROTECTION
+	unsigned int core_pos = plat_my_core_pos();
+
+	/* Make the redistributor frame RW if it is not done previously */
+	if (fvp_gicr_rw_region_init[core_pos] != true) {
+		int ret = xlat_change_mem_attributes(BASE_GICR_BASE +
+						     (core_pos * BASE_GICR_SIZE),
+						     BASE_GICR_SIZE,
+						     MT_EXECUTE_NEVER |
+						     MT_DEVICE | MT_RW |
+						     MT_SECURE);
+
+		if (ret != 0) {
+			ERROR("Failed to make redistributor frame \
+			       read write = %d\n", ret);
+			panic();
+		} else {
+			fvp_gicr_rw_region_init[core_pos] = true;
+		}
+	}
+#else
+	return;
+#endif /* FVP_GICR_REGION_PROTECTION */
+}
+
 void plat_arm_gic_driver_init(void)
 {
+	fvp_gicv3_make_rdistrif_rw();
 	/*
 	 * Get GICD and GICR base addressed through FCONF APIs.
 	 * FCONF is not supported in BL32 for FVP.
@@ -117,6 +153,8 @@
 	int result;
 	const uint64_t *plat_gicr_frames = fvp_gicr_frames;
 
+	fvp_gicv3_make_rdistrif_rw();
+
 	do {
 		result = gicv3_rdistif_probe(*plat_gicr_frames);
 
diff --git a/plat/arm/board/fvp/fvp_io_storage.c b/plat/arm/board/fvp/fvp_io_storage.c
index 109d321..4eef51c 100644
--- a/plat/arm/board/fvp/fvp_io_storage.c
+++ b/plat/arm/board/fvp/fvp_io_storage.c
@@ -20,6 +20,10 @@
 #define BL32_IMAGE_NAME			"bl32.bin"
 #define BL33_IMAGE_NAME			"bl33.bin"
 #define TB_FW_CONFIG_NAME		"fvp_tb_fw_config.dtb"
+#define SOC_FW_CONFIG_NAME		"fvp_soc_fw_config.dtb"
+#define TOS_FW_CONFIG_NAME		"fvp_tsp_fw_config.dtb"
+#define NT_FW_CONFIG_NAME		"fvp_nt_fw_config.dtb"
+#define FW_CONFIG_NAME			"fvp_fw_config.dtb"
 #define HW_CONFIG_NAME			"hw_config.dtb"
 
 #if TRUSTED_BOARD_BOOT
@@ -58,6 +62,22 @@
 		.path = TB_FW_CONFIG_NAME,
 		.mode = FOPEN_MODE_RB
 	},
+	[SOC_FW_CONFIG_ID] = {
+		.path = SOC_FW_CONFIG_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+	[TOS_FW_CONFIG_ID] = {
+		.path = TOS_FW_CONFIG_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+	[NT_FW_CONFIG_ID] = {
+		.path = NT_FW_CONFIG_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+	[FW_CONFIG_ID] = {
+		.path = FW_CONFIG_NAME,
+		.mode = FOPEN_MODE_RB
+	},
 	[HW_CONFIG_ID] = {
 		.path = HW_CONFIG_NAME,
 		.mode = FOPEN_MODE_RB
diff --git a/plat/arm/board/fvp/fvp_measured_boot.c b/plat/arm/board/fvp/fvp_measured_boot.c
deleted file mode 100644
index b145aae..0000000
--- a/plat/arm/board/fvp/fvp_measured_boot.c
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <drivers/measured_boot/event_log.h>
-#include <plat/arm/common/plat_arm.h>
-
-/* FVP table with platform specific image IDs, names and PCRs */
-static const image_data_t fvp_images_data[] = {
-	{ BL2_IMAGE_ID, BL2_STRING, PCR_0 },		/* Reserved for BL2 */
-	{ BL31_IMAGE_ID, BL31_STRING, PCR_0 },
-	{ BL32_IMAGE_ID, BL32_STRING, PCR_0 },
-	{ BL32_EXTRA1_IMAGE_ID, BL32_EXTRA1_IMAGE_STRING, PCR_0 },
-	{ BL32_EXTRA2_IMAGE_ID, BL32_EXTRA2_IMAGE_STRING, PCR_0 },
-	{ BL33_IMAGE_ID, BL33_STRING, PCR_0 },
-	{ GPT_IMAGE_ID, GPT_IMAGE_STRING, PCR_0 },
-	{ HW_CONFIG_ID, HW_CONFIG_STRING, PCR_0 },
-	{ NT_FW_CONFIG_ID, NT_FW_CONFIG_STRING, PCR_0 },
-	{ SCP_BL2_IMAGE_ID, SCP_BL2_IMAGE_STRING, PCR_0 },
-	{ SOC_FW_CONFIG_ID, SOC_FW_CONFIG_STRING, PCR_0 },
-	{ STM32_IMAGE_ID, STM32_IMAGE_STRING, PCR_0 },
-	{ TOS_FW_CONFIG_ID, TOS_FW_CONFIG_STRING, PCR_0 },
-	{ INVALID_ID, NULL, (unsigned int)(-1) }	/* Terminator */
-};
-
-static const measured_boot_data_t fvp_measured_boot_data = {
-	fvp_images_data,
-	arm_set_nt_fw_info,
-	arm_set_tos_fw_info
-};
-
-/*
- * Function retuns pointer to FVP plat_measured_boot_data_t structure
- */
-const measured_boot_data_t *plat_get_measured_boot_data(void)
-{
-	return &fvp_measured_boot_data;
-}
diff --git a/plat/arm/board/fvp/fvp_pm.c b/plat/arm/board/fvp/fvp_pm.c
index 333d892..6b9d618 100644
--- a/plat/arm/board/fvp/fvp_pm.c
+++ b/plat/arm/board/fvp/fvp_pm.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -138,21 +138,37 @@
 	fvp_pwrc_clr_wen(mpidr);
 }
 
-
 /*******************************************************************************
  * FVP handler called when a CPU is about to enter standby.
  ******************************************************************************/
 static void fvp_cpu_standby(plat_local_state_t cpu_state)
 {
+	u_register_t scr = read_scr_el3();
 
 	assert(cpu_state == ARM_LOCAL_STATE_RET);
 
 	/*
-	 * Enter standby state
-	 * dsb is good practice before using wfi to enter low power states
+	 * Enable the Non-secure interrupt to wake the CPU.
+	 * In GICv3 affinity routing mode, the Non-secure Group 1 interrupts
+	 * use Physical FIQ at EL3 whereas in GICv2, Physical IRQ is used.
+	 * Enabling both the bits works for both GICv2 mode and GICv3 affinity
+	 * routing mode.
+	 */
+	write_scr_el3(scr | SCR_IRQ_BIT | SCR_FIQ_BIT);
+	isb();
+
+	/*
+	 * Enter standby state.
+	 * dsb is good practice before using wfi to enter low power states.
 	 */
 	dsb();
 	wfi();
+
+	/*
+	 * Restore SCR_EL3 to the original value, synchronisation of SCR_EL3
+	 * is done by eret in el3_exit() to save some execution cycles.
+	 */
+	write_scr_el3(scr);
 }
 
 /*******************************************************************************
diff --git a/plat/arm/board/fvp/include/platform_def.h b/plat/arm/board/fvp/include/platform_def.h
index 8defcf8..d89e122 100644
--- a/plat/arm/board/fvp/include/platform_def.h
+++ b/plat/arm/board/fvp/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -43,6 +43,11 @@
 #define PLAT_ARM_TRUSTED_DRAM_BASE	UL(0x06000000)
 #define PLAT_ARM_TRUSTED_DRAM_SIZE	UL(0x02000000)	/* 32 MB */
 
+#if ENABLE_RME
+#define PLAT_ARM_RMM_BASE		(RMM_BASE)
+#define PLAT_ARM_RMM_SIZE		(RMM_LIMIT - RMM_BASE)
+#endif
+
 /*
  * Max size of SPMC is 2MB for fvp. With SPMD enabled this value corresponds to
  * max size of BL32 image.
@@ -61,12 +66,13 @@
 #define PLAT_ARM_DRAM2_BASE		ULL(0x880000000)
 #define PLAT_ARM_DRAM2_SIZE		UL(0x80000000)
 
-#define PLAT_HW_CONFIG_DTB_BASE		ULL(0x82000000)
-#define PLAT_HW_CONFIG_DTB_SIZE		ULL(0x8000)
+/* Range of kernel DTB load address */
+#define FVP_DTB_DRAM_MAP_START		ULL(0x82000000)
+#define FVP_DTB_DRAM_MAP_SIZE		ULL(0x02000000)	/* 32 MB */
 
 #define ARM_DTB_DRAM_NS			MAP_REGION_FLAT(		\
-					PLAT_HW_CONFIG_DTB_BASE,	\
-					PLAT_HW_CONFIG_DTB_SIZE,	\
+					FVP_DTB_DRAM_MAP_START,		\
+					FVP_DTB_DRAM_MAP_SIZE,		\
 					MT_MEMORY | MT_RO | MT_NS)
 /*
  * Load address of BL33 for this platform port
@@ -80,15 +86,27 @@
 #if defined(IMAGE_BL31)
 # if SPM_MM
 #  define PLAT_ARM_MMAP_ENTRIES		10
-#  define MAX_XLAT_TABLES		9
+#  if ENABLE_RME
+#   define MAX_XLAT_TABLES		10
+#  else
+#   define MAX_XLAT_TABLES		9
+# endif
 #  define PLAT_SP_IMAGE_MMAP_REGIONS	30
 #  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	10
 # else
 #  define PLAT_ARM_MMAP_ENTRIES		9
 #  if USE_DEBUGFS
-#   define MAX_XLAT_TABLES		8
+#   if ENABLE_RME
+#    define MAX_XLAT_TABLES		9
+#   else
+#    define MAX_XLAT_TABLES		8
+#   endif
 #  else
-#   define MAX_XLAT_TABLES		7
+#   if ENABLE_RME
+#    define MAX_XLAT_TABLES		8
+#   else
+#    define MAX_XLAT_TABLES		7
+#   endif
 #  endif
 # endif
 #elif defined(IMAGE_BL32)
@@ -115,7 +133,7 @@
 #if USE_ROMLIB
 #define PLAT_ARM_MAX_ROMLIB_RW_SIZE	UL(0x1000)
 #define PLAT_ARM_MAX_ROMLIB_RO_SIZE	UL(0xe000)
-#define FVP_BL2_ROMLIB_OPTIMIZATION UL(0x6000)
+#define FVP_BL2_ROMLIB_OPTIMIZATION	UL(0x5000)
 #else
 #define PLAT_ARM_MAX_ROMLIB_RW_SIZE	UL(0)
 #define PLAT_ARM_MAX_ROMLIB_RO_SIZE	UL(0)
@@ -137,25 +155,32 @@
 #endif
 
 #if RESET_TO_BL31
-/* Size of Trusted SRAM - the first 4KB of shared memory */
+/* Size of Trusted SRAM - the first 4KB of shared memory - GPT L0 Tables */
 #define PLAT_ARM_MAX_BL31_SIZE		(PLAT_ARM_TRUSTED_SRAM_SIZE - \
-					 ARM_SHARED_RAM_SIZE)
+					 ARM_SHARED_RAM_SIZE - \
+					 ARM_L0_GPT_SIZE)
 #else
 /*
  * Since BL31 NOBITS overlays BL2 and BL1-RW, PLAT_ARM_MAX_BL31_SIZE is
  * calculated using the current BL31 PROGBITS debug size plus the sizes of
  * BL2 and BL1-RW
  */
-#define PLAT_ARM_MAX_BL31_SIZE		UL(0x3D000)
+#define PLAT_ARM_MAX_BL31_SIZE		(UL(0x3D000) - ARM_L0_GPT_SIZE)
 #endif /* RESET_TO_BL31 */
 
 #ifndef __aarch64__
+#if RESET_TO_SP_MIN
+/* Size of Trusted SRAM - the first 4KB of shared memory */
+#define PLAT_ARM_MAX_BL32_SIZE		(PLAT_ARM_TRUSTED_SRAM_SIZE - \
+					 ARM_SHARED_RAM_SIZE)
+#else
 /*
  * Since BL32 NOBITS overlays BL2 and BL1-RW, PLAT_ARM_MAX_BL32_SIZE is
  * calculated using the current SP_MIN PROGBITS debug size plus the sizes of
  * BL2 and BL1-RW
  */
 # define PLAT_ARM_MAX_BL32_SIZE		UL(0x3B000)
+#endif /* RESET_TO_SP_MIN */
 #endif
 
 /*
@@ -171,7 +196,7 @@
 # if TRUSTED_BOARD_BOOT
 #  define PLATFORM_STACK_SIZE		UL(0x1000)
 # else
-#  define PLATFORM_STACK_SIZE		UL(0x440)
+#  define PLATFORM_STACK_SIZE		UL(0x600)
 # endif
 #elif defined(IMAGE_BL2U)
 # define PLATFORM_STACK_SIZE		UL(0x400)
@@ -179,14 +204,26 @@
 #  define PLATFORM_STACK_SIZE		UL(0x800)
 #elif defined(IMAGE_BL32)
 # define PLATFORM_STACK_SIZE		UL(0x440)
+#elif defined(IMAGE_RMM)
+# define PLATFORM_STACK_SIZE		UL(0x440)
 #endif
 
 #define MAX_IO_DEVICES			3
 #define MAX_IO_HANDLES			4
 
 /* Reserve the last block of flash for PSCI MEM PROTECT flag */
-#define PLAT_ARM_FIP_BASE		V2M_FLASH0_BASE
-#define PLAT_ARM_FIP_MAX_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+#define PLAT_ARM_FLASH_IMAGE_BASE	V2M_FLASH0_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+#if ARM_GPT_SUPPORT
+/*
+ * Offset of the FIP in the GPT image. BL1 component uses this option
+ * as it does not load the partition table to get the FIP base
+ * address. At sector 34 by default (i.e. after reserved sectors 0-33)
+ * Offset = 34 * 512(sector size) = 17408 i.e. 0x4400
+ */
+#define PLAT_ARM_FIP_OFFSET_IN_GPT	0x4400
+#endif /* ARM_GPT_SUPPORT */
 
 #define PLAT_ARM_NVM_BASE		V2M_FLASH0_BASE
 #define PLAT_ARM_NVM_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
@@ -206,6 +243,9 @@
 #define PLAT_ARM_TSP_UART_BASE		V2M_IOFPGA_UART2_BASE
 #define PLAT_ARM_TSP_UART_CLK_IN_HZ	V2M_IOFPGA_UART2_CLK_IN_HZ
 
+#define PLAT_ARM_TRP_UART_BASE		V2M_IOFPGA_UART3_BASE
+#define PLAT_ARM_TRP_UART_CLK_IN_HZ	V2M_IOFPGA_UART3_CLK_IN_HZ
+
 #define PLAT_FVP_SMMUV3_BASE		UL(0x2b400000)
 
 /* CCI related constants */
@@ -301,4 +341,9 @@
 #define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
 #endif
 
+/*
+ * Maximum size of Event Log buffer used in Measured Boot Event Log driver
+ */
+#define	PLAT_ARM_EVENT_LOG_MAX_SIZE		UL(0x400)
+
 #endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/fvp/platform.mk b/plat/arm/board/fvp/platform.mk
index 4da0d76..0d2c319 100644
--- a/plat/arm/board/fvp/platform.mk
+++ b/plat/arm/board/fvp/platform.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, Arm Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 # Use the GICv3 driver on the FVP by default
 FVP_USE_GIC_DRIVER	:= FVP_GICV3
 
@@ -16,6 +18,10 @@
 # Default number of threads per CPU on FVP
 FVP_MAX_PE_PER_CPU	:= 1
 
+# Disable redistributor frame of inactive/fused CPU cores by marking it as read
+# only; enable redistributor frames of all CPU cores by default.
+FVP_GICR_REGION_PROTECTION		:= 0
+
 FVP_DT_PREFIX		:= fvp-base-gicv3-psci
 
 # The FVP platform depends on this macro to build with correct GIC driver.
@@ -30,6 +36,9 @@
 # Pass FVP_MAX_PE_PER_CPU to the build system.
 $(eval $(call add_define,FVP_MAX_PE_PER_CPU))
 
+# Pass FVP_GICR_REGION_PROTECTION to the build system.
+$(eval $(call add_define,FVP_GICR_REGION_PROTECTION))
+
 # Sanity check the cluster count and if FVP_CLUSTER_COUNT <= 2,
 # choose the CCI driver , else the CCN driver
 ifeq ($(FVP_CLUSTER_COUNT), 0)
@@ -118,14 +127,22 @@
 					lib/cpus/aarch64/cortex_a76ae.S		\
 					lib/cpus/aarch64/cortex_a77.S		\
 					lib/cpus/aarch64/cortex_a78.S		\
+					lib/cpus/aarch64/neoverse_n_common.S	\
 					lib/cpus/aarch64/neoverse_n1.S		\
+					lib/cpus/aarch64/neoverse_n2.S		\
 					lib/cpus/aarch64/neoverse_e1.S		\
 					lib/cpus/aarch64/neoverse_v1.S		\
+					lib/cpus/aarch64/neoverse_demeter.S	\
 					lib/cpus/aarch64/cortex_a78_ae.S	\
-					lib/cpus/aarch64/cortex_klein.S	        \
-					lib/cpus/aarch64/cortex_matterhorn.S	\
+					lib/cpus/aarch64/cortex_a510.S		\
+					lib/cpus/aarch64/cortex_a710.S	\
+					lib/cpus/aarch64/cortex_makalu.S	\
+					lib/cpus/aarch64/cortex_makalu_elp_arm.S \
 					lib/cpus/aarch64/cortex_a65.S		\
-					lib/cpus/aarch64/cortex_a65ae.S
+					lib/cpus/aarch64/cortex_a65ae.S		\
+					lib/cpus/aarch64/cortex_a78c.S		\
+					lib/cpus/aarch64/cortex_hayes.S		\
+					lib/cpus/aarch64/cortex_hunter.S
 	endif
 	# AArch64/AArch32 cores
 	FVP_CPU_LIBS	+=	lib/cpus/aarch64/cortex_a55.S		\
@@ -172,6 +189,10 @@
 BL2_SOURCES		+=	plat/arm/common/fconf/fconf_nv_cntr_getter.c
 endif
 
+ifeq (${ENABLE_RME},1)
+BL2_SOURCES		+=	plat/arm/board/fvp/aarch64/fvp_helpers.S
+endif
+
 ifeq (${BL2_AT_EL3},1)
 BL2_SOURCES		+=	plat/arm/board/fvp/${ARCH}/fvp_helpers.S	\
 				plat/arm/board/fvp/fvp_bl2_el3_setup.c		\
@@ -209,11 +230,12 @@
 # Support for fconf in BL31
 # Added separately from the above list for better readability
 ifeq ($(filter 1,${BL2_AT_EL3} ${RESET_TO_BL31}),)
-BL31_SOURCES		+=	common/fdt_wrappers.c				\
-				lib/fconf/fconf.c				\
+BL31_SOURCES		+=	lib/fconf/fconf.c				\
 				lib/fconf/fconf_dyn_cfg_getter.c		\
 				plat/arm/board/fvp/fconf/fconf_hw_config_getter.c
 
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
 ifeq (${SEC_INT_DESC_IN_FCONF},1)
 BL31_SOURCES		+=	plat/arm/common/fconf/fconf_sec_intr_config.c
 endif
@@ -358,10 +380,22 @@
 BL2_SOURCES		+=	plat/arm/board/fvp/fvp_trusted_boot.c
 
 ifeq (${MEASURED_BOOT},1)
-BL2_SOURCES		+=	plat/arm/board/fvp/fvp_measured_boot.c
+BL1_SOURCES		+=	plat/arm/board/fvp/fvp_common_measured_boot.c	\
+				plat/arm/board/fvp/fvp_bl1_measured_boot.c
+BL2_SOURCES		+=	plat/arm/board/fvp/fvp_common_measured_boot.c	\
+				plat/arm/board/fvp/fvp_bl2_measured_boot.c
 endif
 
 # FVP being a development platform, enable capability to disable Authentication
 # dynamically if TRUSTED_BOARD_BOOT is set.
 DYN_DISABLE_AUTH	:=	1
 endif
+
+# enable trace buffer control registers access to NS by default
+ENABLE_TRBE_FOR_NS		:= 1
+
+# enable trace system registers access to NS by default
+ENABLE_SYS_REG_TRACE_FOR_NS	:= 1
+
+# enable trace filter control registers access to NS by default
+ENABLE_TRF_FOR_NS		:= 1
diff --git a/plat/arm/board/fvp/sp_min/sp_min-fvp.mk b/plat/arm/board/fvp/sp_min/sp_min-fvp.mk
index 64cb7ad..0d8cca5 100644
--- a/plat/arm/board/fvp/sp_min/sp_min-fvp.mk
+++ b/plat/arm/board/fvp/sp_min/sp_min-fvp.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 # SP_MIN source files specific to FVP platform
 BL32_SOURCES		+=	drivers/arm/fvp/fvp_pwrc.c			\
 				drivers/cfi/v2m/v2m_flash.c			\
@@ -22,10 +24,11 @@
 # Support for fconf in SP_MIN(BL32)
 # Added separately from the above list for better readability
 ifeq ($(filter 1,${BL2_AT_EL3} ${RESET_TO_SP_MIN}),)
-BL32_SOURCES		+=	common/fdt_wrappers.c				\
-				lib/fconf/fconf.c				\
+BL32_SOURCES		+=	lib/fconf/fconf.c				\
 				plat/arm/board/fvp/fconf/fconf_hw_config_getter.c
 
+BL32_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
 ifeq (${SEC_INT_DESC_IN_FCONF},1)
 BL32_SOURCES		+=	plat/arm/common/fconf/fconf_sec_intr_config.c
 endif
diff --git a/plat/arm/board/fvp/trp/trp-fvp.mk b/plat/arm/board/fvp/trp/trp-fvp.mk
new file mode 100644
index 0000000..a450541
--- /dev/null
+++ b/plat/arm/board/fvp/trp/trp-fvp.mk
@@ -0,0 +1,12 @@
+#
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# TRP source files specific to FVP platform
+
+RMM_SOURCES		+=	plat/arm/board/fvp/aarch64/fvp_helpers.S
+
+include plat/arm/common/trp/arm_trp.mk
+
diff --git a/plat/arm/board/fvp_r/fvp_r_bl1_arch_setup.c b/plat/arm/board/fvp_r/fvp_r_bl1_arch_setup.c
new file mode 100644
index 0000000..ae6af6c
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_bl1_arch_setup.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include "../../../../bl1/bl1_private.h"
+#include <arch.h>
+
+#include <fvp_r_arch_helpers.h>
+
+/*******************************************************************************
+ * Function that does the first bit of architectural setup that affects
+ * execution in the non-secure address space.
+ ******************************************************************************/
+void bl1_arch_setup(void)
+{
+	/* v8-R64 does not include SCRs. */
+}
+
+/*******************************************************************************
+ * Set the Secure EL1 required architectural state
+ ******************************************************************************/
+void bl1_arch_next_el_setup(void)
+{
+	u_register_t next_sctlr;
+
+	/* Use the same endianness than the current BL */
+	next_sctlr = (read_sctlr_el2() & SCTLR_EE_BIT);
+
+	/* Set SCTLR Secure EL1 */
+	next_sctlr |= SCTLR_EL1_RES1;
+
+	write_sctlr_el1(next_sctlr);
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_bl1_entrypoint.S b/plat/arm/board/fvp_r/fvp_r_bl1_entrypoint.S
new file mode 100644
index 0000000..15f4c43
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_bl1_entrypoint.S
@@ -0,0 +1,93 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <el2_common_macros.S>
+#include <lib/xlat_mpu/xlat_mpu.h>
+
+	.globl	bl1_entrypoint
+	.globl	bl1_run_next_image
+
+
+	/* -----------------------------------------------------
+	 * bl1_entrypoint() is the entry point into the trusted
+	 * firmware code when a cpu is released from warm or
+	 * cold reset.
+	 * -----------------------------------------------------
+	 */
+
+func bl1_entrypoint
+	/* ---------------------------------------------------------------------
+	 * If the reset address is programmable then bl1_entrypoint() is
+	 * executed only on the cold boot path. Therefore, we can skip the warm
+	 * boot mailbox mechanism.
+	 * ---------------------------------------------------------------------
+	 */
+	el2_entrypoint_common					\
+		_init_sctlr=1					\
+		_warm_boot_mailbox=!PROGRAMMABLE_RESET_ADDRESS	\
+		_secondary_cold_boot=!COLD_BOOT_SINGLE_CPU	\
+		_init_memory=1					\
+		_init_c_runtime=1				\
+		_exception_vectors=bl1_exceptions		\
+		_pie_fixup_size=0
+
+	/* --------------------------------------------------------------------
+	 * Perform BL1 setup
+	 * --------------------------------------------------------------------
+	 */
+	bl	bl1_setup
+
+	/* --------------------------------------------------------------------
+	 * Initialize platform and jump to our c-entry point
+	 * for this type of reset.
+	 * --------------------------------------------------------------------
+	 */
+	bl	bl1_main
+
+	/* ---------------------------------------------
+	 * Should never reach this point.
+	 * ---------------------------------------------
+	 */
+	no_ret	plat_panic_handler
+endfunc bl1_entrypoint
+
+func bl1_run_next_image
+	mov	x20,x0
+
+	/* ---------------------------------------------
+	 * MPU needs to be disabled because both BL1 and BL33 execute
+	 * in EL2, and therefore share the same address space.
+	 * BL33 will initialize the address space according to its
+	 * own requirement.
+	 * ---------------------------------------------
+	 */
+	bl	disable_mpu_icache_el2
+
+	/* ---------------------------------------------
+	 * Wipe clean and disable all MPU regions.  This function expects
+	 * that the MPU has already been turned off, and caching concerns
+	 * addressed, but it also explicitly turns off the MPU.
+	 * ---------------------------------------------
+	 */
+	bl	clear_all_mpu_regions
+
+	/* --------------------------------------------------
+	 * Do the transition to next boot image.
+	 * --------------------------------------------------
+	 */
+	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
+	msr	elr_el2, x0
+	msr	spsr_el2, x1
+
+	ldp	x6, x7, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x30)]
+	ldp	x4, x5, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x20)]
+	ldp	x2, x3, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x10)]
+	ldp	x0, x1, [x20, #(ENTRY_POINT_INFO_ARGS_OFFSET + 0x0)]
+	exception_return
+endfunc bl1_run_next_image
diff --git a/plat/arm/board/fvp_r/fvp_r_bl1_exceptions.S b/plat/arm/board/fvp_r/fvp_r_bl1_exceptions.S
new file mode 100644
index 0000000..43c2e01
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_bl1_exceptions.S
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <bl1/bl1.h>
+#include <common/bl_common.h>
+#include <context.h>
+
+/* -----------------------------------------------------------------------------
+ * File contains an EL2 equivalent of the EL3 vector table from:
+ * 	.../bl1/aarch64/bl1_exceptions.S
+ * -----------------------------------------------------------------------------
+ */
+
+/* -----------------------------------------------------------------------------
+ * Very simple stackless exception handlers used by BL1.
+ * -----------------------------------------------------------------------------
+ */
+	.globl	bl1_exceptions
+
+vector_base bl1_exceptions
+
+	/* -----------------------------------------------------
+	 * Current EL with SP0 : 0x0 - 0x200
+	 * -----------------------------------------------------
+	 */
+vector_entry SynchronousExceptionSP0
+	mov	x0, #SYNC_EXCEPTION_SP_EL0
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry SynchronousExceptionSP0
+
+vector_entry IrqSP0
+	mov	x0, #IRQ_SP_EL0
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry IrqSP0
+
+vector_entry FiqSP0
+	mov	x0, #FIQ_SP_EL0
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry FiqSP0
+
+vector_entry SErrorSP0
+	mov	x0, #SERROR_SP_EL0
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry SErrorSP0
+
+	/* -----------------------------------------------------
+	 * Current EL with SPx: 0x200 - 0x400
+	 * -----------------------------------------------------
+	 */
+vector_entry SynchronousExceptionSPx
+	mov	x0, #SYNC_EXCEPTION_SP_ELX
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry SynchronousExceptionSPx
+
+vector_entry IrqSPx
+	mov	x0, #IRQ_SP_ELX
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry IrqSPx
+
+vector_entry FiqSPx
+	mov	x0, #FIQ_SP_ELX
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry FiqSPx
+
+vector_entry SErrorSPx
+	mov	x0, #SERROR_SP_ELX
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry SErrorSPx
+
+	/* -----------------------------------------------------
+	 * Lower EL using AArch64 : 0x400 - 0x600
+	 * -----------------------------------------------------
+	 */
+vector_entry SynchronousExceptionA64
+	/* The current v8-R64 implementation does not support conduit calls */
+	b	el2_panic
+end_vector_entry SynchronousExceptionA64
+
+vector_entry IrqA64
+	mov	x0, #IRQ_AARCH64
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry IrqA64
+
+vector_entry FiqA64
+	mov	x0, #FIQ_AARCH64
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry FiqA64
+
+vector_entry SErrorA64
+	mov	x0, #SERROR_AARCH64
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+end_vector_entry SErrorA64
+
+
+unexpected_sync_exception:
+	mov	x0, #SYNC_EXCEPTION_AARCH64
+	bl	plat_report_exception
+	no_ret	plat_panic_handler
+
+	/* -----------------------------------------------------
+	 * Save Secure/Normal world context and jump to
+	 * BL1 SMC handler.
+	 * -----------------------------------------------------
+	 */
diff --git a/plat/arm/board/fvp_r/fvp_r_bl1_main.c b/plat/arm/board/fvp_r/fvp_r_bl1_main.c
new file mode 100644
index 0000000..841a176
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_bl1_main.c
@@ -0,0 +1,268 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include "../../../../bl1/bl1_private.h"
+#include <arch.h>
+#include <arch_features.h>
+#include <arch_helpers.h>
+#include <bl1/bl1.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/auth/auth_mod.h>
+#include <drivers/console.h>
+#include <lib/cpus/errata_report.h>
+#include <lib/utils.h>
+#include <smccc_helpers.h>
+#include <tools_share/uuid.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+
+#include <platform_def.h>
+
+
+void cm_prepare_el2_exit(void);
+
+void bl1_run_next_image(const struct entry_point_info *bl_ep_info);
+
+/*******************************************************************************
+ * Function to perform late architectural and platform specific initialization.
+ * It also queries the platform to load and run next BL image. Only called
+ * by the primary cpu after a cold boot.
+ ******************************************************************************/
+void bl1_transfer_bl33(void)
+{
+	unsigned int image_id;
+
+	/* Get the image id of next image to load and run. */
+	image_id = bl1_plat_get_next_image_id();
+
+#if !ARM_DISABLE_TRUSTED_WDOG
+	/* Disable watchdog before leaving BL1 */
+	plat_arm_secure_wdt_stop();
+#endif
+
+	bl1_run_next_image(&bl1_plat_get_image_desc(image_id)->ep_info);
+}
+
+/*******************************************************************************
+ * This function locates and loads the BL33 raw binary image in the trusted SRAM.
+ * Called by the primary cpu after a cold boot.
+ * TODO: Add support for alternative image load mechanism e.g using virtio/elf
+ * loader etc.
+ ******************************************************************************/
+void bl1_load_bl33(void)
+{
+	image_desc_t *desc;
+	image_info_t *info;
+	int err;
+
+	/* Get the image descriptor */
+	desc = bl1_plat_get_image_desc(BL33_IMAGE_ID);
+	assert(desc != NULL);
+
+	/* Get the image info */
+	info = &desc->image_info;
+	INFO("BL1: Loading BL33\n");
+
+	err = bl1_plat_handle_pre_image_load(BL33_IMAGE_ID);
+	if (err != 0) {
+		ERROR("Failure in pre image load handling of BL33 (%d)\n", err);
+		plat_error_handler(err);
+	}
+
+	err = load_auth_image(BL33_IMAGE_ID, info);
+	if (err != 0) {
+		ERROR("Failed to load BL33 firmware.\n");
+		plat_error_handler(err);
+	}
+
+	/* Allow platform to handle image information. */
+	err = bl1_plat_handle_post_image_load(BL33_IMAGE_ID);
+	if (err != 0) {
+		ERROR("Failure in post image load handling of BL33 (%d)\n", err);
+		plat_error_handler(err);
+	}
+
+	NOTICE("BL1: Booting BL33\n");
+}
+
+/*******************************************************************************
+ * Helper utility to calculate the BL2 memory layout taking into consideration
+ * the BL1 RW data assuming that it is at the top of the memory layout.
+ ******************************************************************************/
+void bl1_calc_bl2_mem_layout(const meminfo_t *bl1_mem_layout,
+			meminfo_t *bl2_mem_layout)
+{
+	assert(bl1_mem_layout != NULL);
+	assert(bl2_mem_layout != NULL);
+
+	/*
+	 * Remove BL1 RW data from the scope of memory visible to BL2.
+	 * This is assuming BL1 RW data is at the top of bl1_mem_layout.
+	 */
+	assert(bl1_mem_layout->total_base < BL1_RW_BASE);
+	bl2_mem_layout->total_base = bl1_mem_layout->total_base;
+	bl2_mem_layout->total_size = BL1_RW_BASE - bl1_mem_layout->total_base;
+
+	flush_dcache_range((uintptr_t)bl2_mem_layout, sizeof(meminfo_t));
+}
+
+/*******************************************************************************
+ * This function prepares for entry to BL33
+ ******************************************************************************/
+void bl1_prepare_next_image(unsigned int image_id)
+{
+	unsigned int mode = MODE_EL1;
+	image_desc_t *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 (el_implemented(1) == EL_IMPL_A64ONLY) {
+		ERROR("EL1 supports AArch64-only. Please set build flag %s",
+				"CTX_INCLUDE_AARCH32_REGS = 0\n");
+		panic();
+	}
+#endif
+
+	/* Get the image descriptor. */
+	desc = bl1_plat_get_image_desc(image_id);
+	assert(desc != NULL);
+
+	/* Get the entry point info. */
+	next_bl_ep = &desc->ep_info;
+
+	/* FVP-R is only secure */
+	assert(GET_SECURITY_STATE(next_bl_ep->h.attr) == SECURE);
+
+	/* Prepare the SPSR for the next BL image. */
+	next_bl_ep->spsr = (uint32_t)SPSR_64((uint64_t) mode,
+		(uint64_t)MODE_SP_ELX, DISABLE_ALL_EXCEPTIONS);
+
+	/* Allow platform to make change */
+	bl1_plat_set_ep_info(image_id, next_bl_ep);
+
+	/* Prepare context for the next EL */
+	cm_prepare_el2_exit();
+
+	/* Indicate that image is in execution state. */
+	desc->state = IMAGE_STATE_EXECUTED;
+
+	print_entry_point_info(next_bl_ep);
+}
+
+/*******************************************************************************
+ * Setup function for BL1.
+ ******************************************************************************/
+void bl1_setup(void)
+{
+	/* Perform early platform-specific setup */
+	bl1_early_platform_setup();
+
+	/* Perform late platform-specific setup */
+	bl1_plat_arch_setup();
+}
+
+/*******************************************************************************
+ * Function to perform late architectural and platform specific initialization.
+ * It also queries the platform to load and run next BL image. Only called
+ * by the primary cpu after a cold boot.
+ ******************************************************************************/
+void bl1_main(void)
+{
+	unsigned int image_id;
+
+	/* Announce our arrival */
+	NOTICE(FIRMWARE_WELCOME_STR);
+	NOTICE("BL1: %s\n", version_string);
+	NOTICE("BL1: %s\n", build_message);
+
+	INFO("BL1: RAM %p - %p\n", (void *)BL1_RAM_BASE, (void *)BL1_RAM_LIMIT);
+
+	print_errata_status();
+
+#if ENABLE_ASSERTIONS
+	u_register_t val;
+	/*
+	 * Ensure that MMU/Caches and coherency are turned on
+	 */
+	val = read_sctlr_el2();
+
+	assert((val & SCTLR_M_BIT) != 0U);
+	assert((val & SCTLR_C_BIT) != 0U);
+	assert((val & SCTLR_I_BIT) != 0U);
+	/*
+	 * Check that Cache Writeback Granule (CWG) in CTR_EL0 matches the
+	 * provided platform value
+	 */
+	val = (read_ctr_el0() >> CTR_CWG_SHIFT) & CTR_CWG_MASK;
+	/*
+	 * If CWG is zero, then no CWG information is available but we can
+	 * at least check the platform value is less than the architectural
+	 * maximum.
+	 */
+	if (val != 0) {
+		assert(SIZE_FROM_LOG2_WORDS(val) == CACHE_WRITEBACK_GRANULE);
+	} else {
+		assert(MAX_CACHE_LINE_SIZE >= CACHE_WRITEBACK_GRANULE);
+	}
+#endif /* ENABLE_ASSERTIONS */
+
+	/* Perform remaining generic architectural setup from ELmax */
+	bl1_arch_setup();
+
+#if TRUSTED_BOARD_BOOT
+	/* Initialize authentication module */
+	auth_mod_init();
+#endif /* TRUSTED_BOARD_BOOT */
+
+	/* Perform platform setup in BL1. */
+	bl1_platform_setup();
+
+	/* Get the image id of next image to load and run. */
+	image_id = bl1_plat_get_next_image_id();
+
+	/*
+	 * We currently interpret any image id other than
+	 * BL2_IMAGE_ID as the start of firmware update.
+	 */
+	if (image_id == BL33_IMAGE_ID) {
+		bl1_load_bl33();
+	} else {
+		NOTICE("BL1-FWU: *******FWU Process Started*******\n");
+	}
+
+	bl1_prepare_next_image(image_id);
+
+	console_flush();
+
+	bl1_transfer_bl33();
+}
+
+/*******************************************************************************
+ * Function called just before handing over to the next BL to inform the user
+ * about the boot progress. In debug mode, also print details about the BL
+ * image's execution context.
+ ******************************************************************************/
+void bl1_print_next_bl_ep_info(const entry_point_info_t *bl_ep_info)
+{
+	NOTICE("BL1: Booting BL31\n");
+	print_entry_point_info(bl_ep_info);
+}
+
+#if SPIN_ON_BL1_EXIT
+void print_debug_loop_message(void)
+{
+	NOTICE("BL1: Debug loop, spinning forever\n");
+	NOTICE("BL1: Please connect the debugger to continue\n");
+}
+#endif
+
diff --git a/plat/arm/board/fvp_r/fvp_r_bl1_setup.c b/plat/arm/board/fvp_r/fvp_r_bl1_setup.c
new file mode 100644
index 0000000..68872c1
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_bl1_setup.c
@@ -0,0 +1,247 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/* Use the xlat_tables_v2 data structures: */
+#define XLAT_TABLES_LIB_V2	1
+
+#include <assert.h>
+
+#include <bl1/bl1.h>
+#include <common/tbbr/tbbr_img_def.h>
+#include <drivers/arm/sp805.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
+#include <lib/xlat_mpu/xlat_mpu.h>
+
+#include "fvp_r_private.h"
+#include <plat/arm/common/arm_config.h>
+#include <plat/arm/common/arm_def.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+#define MAP_BL1_TOTAL		MAP_REGION_FLAT(			\
+					bl1_tzram_layout.total_base,	\
+					bl1_tzram_layout.total_size,	\
+					MT_MEMORY | MT_RW | MT_SECURE)
+/*
+ * If SEPARATE_CODE_AND_RODATA=1 we define a region for each section
+ * otherwise one region is defined containing both
+ */
+#if SEPARATE_CODE_AND_RODATA
+#define MAP_BL1_RO		MAP_REGION_FLAT(			\
+					BL_CODE_BASE,			\
+					BL1_CODE_END - BL_CODE_BASE,	\
+					MT_CODE | MT_SECURE),		\
+				MAP_REGION_FLAT(			\
+					BL1_RO_DATA_BASE,		\
+					BL1_RO_DATA_END			\
+						- BL_RO_DATA_BASE,	\
+					MT_RO_DATA | MT_SECURE)
+#else
+#define MAP_BL1_RO		MAP_REGION_FLAT(			\
+					BL_CODE_BASE,			\
+					BL1_CODE_END - BL_CODE_BASE,	\
+					MT_CODE | MT_SECURE)
+#endif
+
+/* Data structure which holds the extents of the trusted SRAM for BL1*/
+static meminfo_t bl1_tzram_layout;
+
+struct meminfo *bl1_plat_sec_mem_layout(void)
+{
+	return &bl1_tzram_layout;
+}
+
+void arm_bl1_early_platform_setup(void)
+{
+
+#if !ARM_DISABLE_TRUSTED_WDOG
+	/* Enable watchdog */
+	plat_arm_secure_wdt_start();
+#endif
+
+	/* Initialize the console to provide early debug support */
+	arm_console_boot_init();
+
+	/* Allow BL1 to see the whole Trusted RAM */
+	bl1_tzram_layout.total_base = ARM_BL_RAM_BASE;
+	bl1_tzram_layout.total_size = ARM_BL_RAM_SIZE;
+}
+
+/* Boolean variable to hold condition whether firmware update needed or not */
+static bool is_fwu_needed;
+
+/*******************************************************************************
+ * Perform any BL1 specific platform actions.
+ ******************************************************************************/
+void bl1_early_platform_setup(void)
+{
+	arm_bl1_early_platform_setup();
+
+	/* Initialize the platform config for future decision making */
+	fvp_config_setup();
+
+	/*
+	 * Initialize Interconnect for this cluster during cold boot.
+	 * No need for locks as no other CPU is active.
+	 */
+	fvp_interconnect_init();
+	/*
+	 * Enable coherency in Interconnect for the primary CPU's cluster.
+	 */
+	fvp_interconnect_enable();
+}
+
+void arm_bl1_plat_arch_setup(void)
+{
+	const mmap_region_t bl_regions[] = {
+		MAP_BL1_TOTAL,
+		MAP_BL1_RO,
+#if USE_ROMLIB
+		ARM_MAP_ROMLIB_CODE,
+		ARM_MAP_ROMLIB_DATA,
+#endif
+#if ARM_CRYPTOCELL_INTEG
+		ARM_MAP_BL_COHERENT_RAM,
+#endif
+		/* DRAM1_region: */
+		MAP_REGION_FLAT(					\
+			PLAT_ARM_DRAM1_BASE,				\
+			PLAT_ARM_DRAM1_SIZE,				\
+			MT_MEMORY | MT_SECURE | MT_EXECUTE		\
+			| MT_RW | MT_NON_CACHEABLE),
+		/* NULL terminator: */
+		{0}
+	};
+
+	setup_page_tables(bl_regions, plat_arm_get_mmap());
+	enable_mpu_el2(0);
+
+	arm_setup_romlib();
+}
+
+void plat_arm_secure_wdt_start(void)
+{
+	sp805_start(ARM_SP805_TWDG_BASE, ARM_TWDG_LOAD_VAL);
+}
+
+void plat_arm_secure_wdt_stop(void)
+{
+	sp805_stop(ARM_SP805_TWDG_BASE);
+}
+
+/*
+ * Perform the platform specific architecture setup shared between
+ * ARM standard platforms.
+ */
+void arm_bl1_platform_setup(void)
+{
+	uint32_t fw_config_max_size;
+
+	/* Initialise the IO layer and register platform IO devices */
+	plat_arm_io_setup();
+
+	/* Check if we need FWU before further processing */
+	is_fwu_needed = plat_arm_bl1_fwu_needed();
+	if (is_fwu_needed) {
+		ERROR("Skip platform setup as FWU detected\n");
+		return;
+	}
+
+	/* Set global DTB info for fixed fw_config information */
+	fw_config_max_size = ARM_FW_CONFIG_LIMIT - ARM_FW_CONFIG_BASE;
+	set_config_info(ARM_FW_CONFIG_BASE, fw_config_max_size, FW_CONFIG_ID);
+
+	assert(bl1_plat_get_image_desc(BL33_IMAGE_ID) != NULL);
+
+	/*
+	 * Allow access to the System counter timer module and program
+	 * counter frequency for non secure images during FWU
+	 */
+#ifdef ARM_SYS_TIMCTL_BASE
+	arm_configure_sys_timer();
+#endif
+#if (ARM_ARCH_MAJOR > 7) || defined(ARMV7_SUPPORTS_GENERIC_TIMER)
+	write_cntfrq_el0(plat_get_syscnt_freq2());
+#endif
+}
+
+void bl1_platform_setup(void)
+{
+	arm_bl1_platform_setup();
+
+	/* Initialize System level generic or SP804 timer */
+	fvp_timer_init();
+}
+
+__dead2 void bl1_plat_fwu_done(void *client_cookie, void *reserved)
+{
+	/* Setup the watchdog to reset the system as soon as possible */
+	sp805_refresh(ARM_SP805_TWDG_BASE, 1U);
+
+	while (true) {
+		wfi();
+	}
+}
+
+unsigned int bl1_plat_get_next_image_id(void)
+{
+	return  is_fwu_needed ? NS_BL1U_IMAGE_ID : BL33_IMAGE_ID;
+}
+
+/*
+ * Returns BL33 image details.
+ */
+struct image_desc *bl1_plat_get_image_desc(unsigned int image_id)
+{
+	static image_desc_t bl33_img_desc = BL33_IMAGE_DESC;
+
+	return &bl33_img_desc;
+}
+
+/*
+ * This function populates the default arguments to BL33.
+ * The BL33 memory layout structure is allocated and the
+ * calculated layout is populated in arg1 to BL33.
+ */
+int bl1_plat_handle_post_image_load(unsigned int image_id)
+{
+	meminfo_t *bl33_secram_layout;
+	meminfo_t *bl1_secram_layout;
+	image_desc_t *image_desc;
+	entry_point_info_t *ep_info;
+
+	if (image_id != BL33_IMAGE_ID) {
+		return 0;
+	}
+	/* Get the image descriptor */
+	image_desc = bl1_plat_get_image_desc(BL33_IMAGE_ID);
+	assert(image_desc != NULL);
+
+	/* Get the entry point info */
+	ep_info = &image_desc->ep_info;
+
+	/* Find out how much free trusted ram remains after BL1 load */
+	bl1_secram_layout = bl1_plat_sec_mem_layout();
+
+	/*
+	 * Create a new layout of memory for BL33 as seen by BL1 i.e.
+	 * tell it the amount of total and free memory available.
+	 * This layout is created at the first free address visible
+	 * to BL33. BL33 will read the memory layout before using its
+	 * memory for other purposes.
+	 */
+	bl33_secram_layout = (meminfo_t *) bl1_secram_layout->total_base;
+
+	bl1_calc_bl2_mem_layout(bl1_secram_layout, bl33_secram_layout);
+
+	ep_info->args.arg1 = (uintptr_t)bl33_secram_layout;
+
+	VERBOSE("BL1: BL3 memory layout address = %p\n",
+		(void *) bl33_secram_layout);
+	return 0;
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_common.c b/plat/arm/board/fvp_r/fvp_r_common.c
new file mode 100644
index 0000000..edcf658
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_common.c
@@ -0,0 +1,289 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/* This uses xlat_mpu, but tables are set up using V2 mmap_region_t */
+#define XLAT_TABLES_LIB_V2	1
+
+#include <assert.h>
+#include <common/debug.h>
+
+#include <drivers/arm/cci.h>
+#include <drivers/arm/gicv2.h>
+#include <drivers/arm/sp804_delay_timer.h>
+#include <drivers/generic_delay_timer.h>
+#include <lib/mmio.h>
+#include <lib/smccc.h>
+#include <lib/xlat_tables/xlat_tables_compat.h>
+#include <services/arm_arch_svc.h>
+
+#include "fvp_r_private.h"
+#include <plat/arm/common/arm_config.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+
+/* Defines for GIC Driver build time selection */
+#define FVP_R_GICV3		2
+
+/*******************************************************************************
+ * arm_config holds the characteristics of the differences between the FVP_R
+ * platforms. It will be populated during cold boot at each boot stage by the
+ * primary before enabling the MPU (to allow interconnect configuration) &
+ * used thereafter. Each BL will have its own copy to allow independent
+ * operation.
+ ******************************************************************************/
+arm_config_t arm_config;
+
+#define MAP_DEVICE0	MAP_REGION_FLAT(DEVICE0_BASE,			\
+					DEVICE0_SIZE,			\
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+#define MAP_DEVICE1	MAP_REGION_FLAT(DEVICE1_BASE,			\
+					DEVICE1_SIZE,			\
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+/*
+ * Need to be mapped with write permissions in order to set a new non-volatile
+ * counter value.
+ */
+#define MAP_DEVICE2	MAP_REGION_FLAT(DEVICE2_BASE,			\
+					DEVICE2_SIZE,			\
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+/*
+ * Table of memory regions for various BL stages to map using the MPU.
+ * This doesn't include Trusted SRAM as setup_page_tables() already takes care
+ * of mapping it.
+ *
+ * The flash needs to be mapped as writable in order to erase the FIP's Table of
+ * Contents in case of unrecoverable error (see plat_error_handler()).
+ */
+#ifdef IMAGE_BL1
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	V2M_MAP_FLASH0_RW,
+	V2M_MAP_IOFPGA,
+	MAP_DEVICE0,
+	MAP_DEVICE1,
+#if TRUSTED_BOARD_BOOT
+	/* To access the Root of Trust Public Key registers. */
+	MAP_DEVICE2,
+#endif
+	{0}
+};
+#endif
+
+ARM_CASSERT_MMAP
+
+static const int fvp_cci400_map[] = {
+	PLAT_FVP_R_CCI400_CLUS0_SL_PORT,
+	PLAT_FVP_R_CCI400_CLUS1_SL_PORT,
+};
+
+static const int fvp_cci5xx_map[] = {
+	PLAT_FVP_R_CCI5XX_CLUS0_SL_PORT,
+	PLAT_FVP_R_CCI5XX_CLUS1_SL_PORT,
+};
+
+static unsigned int get_interconnect_master(void)
+{
+	unsigned int master;
+	u_register_t mpidr;
+
+	mpidr = read_mpidr_el1();
+	master = ((arm_config.flags & ARM_CONFIG_FVP_SHIFTED_AFF) != 0U) ?
+		MPIDR_AFFLVL2_VAL(mpidr) : MPIDR_AFFLVL1_VAL(mpidr);
+
+	assert(master < FVP_R_CLUSTER_COUNT);
+	return master;
+}
+
+/*******************************************************************************
+ * Initialize the platform config for future decision making
+ ******************************************************************************/
+void __init fvp_config_setup(void)
+{
+	unsigned int rev, hbi, bld, arch, sys_id;
+
+	arm_config.flags |= ARM_CONFIG_BASE_MMAP;
+	sys_id = mmio_read_32(V2M_FVP_R_SYSREGS_BASE + V2M_SYS_ID);
+	rev = (sys_id >> V2M_SYS_ID_REV_SHIFT) & V2M_SYS_ID_REV_MASK;
+	hbi = (sys_id >> V2M_SYS_ID_HBI_SHIFT) & V2M_SYS_ID_HBI_MASK;
+	bld = (sys_id >> V2M_SYS_ID_BLD_SHIFT) & V2M_SYS_ID_BLD_MASK;
+	arch = (sys_id >> V2M_SYS_ID_ARCH_SHIFT) & V2M_SYS_ID_ARCH_MASK;
+
+	if (arch != ARCH_MODEL) {
+		ERROR("This firmware is for FVP_R models\n");
+		panic();
+	}
+
+	/*
+	 * The build field in the SYS_ID tells which variant of the GIC
+	 * memory is implemented by the model.
+	 */
+	switch (bld) {
+	case BLD_GIC_VE_MMAP:
+		ERROR("Legacy Versatile Express memory map for GIC %s",
+				"peripheral is not supported\n");
+		panic();
+		break;
+	case BLD_GIC_A53A57_MMAP:
+		break;
+	default:
+		ERROR("Unsupported board build %x\n", bld);
+		panic();
+	}
+
+	/*
+	 * The hbi field in the SYS_ID is 0x020 for the Base FVP_R & 0x010
+	 * for the Foundation FVP_R.
+	 */
+	switch (hbi) {
+	case HBI_FOUNDATION_FVP_R:
+		arm_config.flags = 0;
+
+		/*
+		 * Check for supported revisions of Foundation FVP_R
+		 * Allow future revisions to run but emit warning diagnostic
+		 */
+		switch (rev) {
+		case REV_FOUNDATION_FVP_R_V2_0:
+		case REV_FOUNDATION_FVP_R_V2_1:
+		case REV_FOUNDATION_FVP_R_v9_1:
+		case REV_FOUNDATION_FVP_R_v9_6:
+			break;
+		default:
+			WARN("Unrecognized Foundation FVP_R revision %x\n", rev);
+			break;
+		}
+		break;
+	case HBI_BASE_FVP_R:
+		arm_config.flags |= (ARM_CONFIG_BASE_MMAP | ARM_CONFIG_HAS_TZC);
+
+		/*
+		 * Check for supported revisions
+		 * Allow future revisions to run but emit warning diagnostic
+		 */
+		switch (rev) {
+		case REV_BASE_FVP_R_V0:
+			arm_config.flags |= ARM_CONFIG_FVP_HAS_CCI400;
+			break;
+		default:
+			WARN("Unrecognized Base FVP_R revision %x\n", rev);
+			break;
+		}
+		break;
+	default:
+		ERROR("Unsupported board HBI number 0x%x\n", hbi);
+		panic();
+	}
+
+	/*
+	 * We assume that the presence of MT bit, and therefore shifted
+	 * affinities, is uniform across the platform: either all CPUs, or no
+	 * CPUs implement it.
+	 */
+	if ((read_mpidr_el1() & MPIDR_MT_MASK) != 0U) {
+		arm_config.flags |= ARM_CONFIG_FVP_SHIFTED_AFF;
+	}
+}
+
+
+void __init fvp_interconnect_init(void)
+{
+	uintptr_t cci_base = 0U;
+	const int *cci_map = NULL;
+	unsigned int map_size = 0U;
+
+	/* Initialize the right interconnect */
+	if ((arm_config.flags & ARM_CONFIG_FVP_HAS_CCI5XX) != 0U) {
+		cci_base = PLAT_FVP_R_CCI5XX_BASE;
+		cci_map = fvp_cci5xx_map;
+		map_size = ARRAY_SIZE(fvp_cci5xx_map);
+	} else if ((arm_config.flags & ARM_CONFIG_FVP_HAS_CCI400) != 0U) {
+		cci_base = PLAT_FVP_R_CCI400_BASE;
+		cci_map = fvp_cci400_map;
+		map_size = ARRAY_SIZE(fvp_cci400_map);
+	} else {
+		return;
+	}
+
+	assert(cci_base != 0U);
+	assert(cci_map != NULL);
+	cci_init(cci_base, cci_map, map_size);
+}
+
+void fvp_interconnect_enable(void)
+{
+	unsigned int master;
+
+	if ((arm_config.flags & (ARM_CONFIG_FVP_HAS_CCI400 |
+				 ARM_CONFIG_FVP_HAS_CCI5XX)) != 0U) {
+		master = get_interconnect_master();
+		cci_enable_snoop_dvm_reqs(master);
+	}
+}
+
+void fvp_interconnect_disable(void)
+{
+	unsigned int master;
+
+	if ((arm_config.flags & (ARM_CONFIG_FVP_HAS_CCI400 |
+				 ARM_CONFIG_FVP_HAS_CCI5XX)) != 0U) {
+		master = get_interconnect_master();
+		cci_disable_snoop_dvm_reqs(master);
+	}
+}
+
+#if TRUSTED_BOARD_BOOT
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	assert(heap_addr != NULL);
+	assert(heap_size != NULL);
+
+	return arm_get_mbedtls_heap(heap_addr, heap_size);
+}
+#endif
+
+void fvp_timer_init(void)
+{
+#if USE_SP804_TIMER
+	/* Enable the clock override for SP804 timer 0, which means that no
+	 * clock dividers are applied and the raw (35MHz) clock will be used.
+	 */
+	mmio_write_32(V2M_SP810_BASE, FVP_R_SP810_CTRL_TIM0_OV);
+
+	/* Initialize delay timer driver using SP804 dual timer 0 */
+	sp804_timer_init(V2M_SP804_TIMER0_BASE,
+			SP804_TIMER_CLKMULT, SP804_TIMER_CLKDIV);
+#else
+	generic_delay_timer_init();
+
+	/* Enable System level generic timer */
+	mmio_write_32(ARM_SYS_CNTCTL_BASE + CNTCR_OFF,
+			CNTCR_FCREQ(0U) | CNTCR_EN);
+#endif /* USE_SP804_TIMER */
+}
+
+/* Get SOC version */
+int32_t plat_get_soc_version(void)
+{
+	return (int32_t)
+		((ARM_SOC_IDENTIFICATION_CODE << ARM_SOC_IDENTIFICATION_SHIFT)
+		 | (ARM_SOC_CONTINUATION_CODE << ARM_SOC_CONTINUATION_SHIFT)
+		 | FVP_R_SOC_ID);
+}
+
+/* Get SOC revision */
+int32_t plat_get_soc_revision(void)
+{
+	unsigned int sys_id;
+
+	sys_id = mmio_read_32(V2M_SYSREGS_BASE + V2M_SYS_ID);
+	return (int32_t)((sys_id >> V2M_SYS_ID_REV_SHIFT) &
+			V2M_SYS_ID_REV_MASK);
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_context_mgmt.c b/plat/arm/board/fvp_r/fvp_r_context_mgmt.c
new file mode 100644
index 0000000..d172d2d
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_context_mgmt.c
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+
+/************************************************************
+ * For R-class everything is in secure world.
+ * Prepare the CPU system registers for first entry into EL1
+ ************************************************************/
+void cm_prepare_el2_exit(void)
+{
+	uint64_t hcr_el2 = 0U;
+
+	/*
+	 * The use of ARMv8.3 pointer authentication (PAuth) is governed
+	 * by fields in HCR_EL2, which trigger a 'trap to EL2' if not
+	 * enabled. This register initialized at boot up, update PAuth
+	 * bits.
+	 *
+	 * HCR_API_BIT: Set to one to disable traps to EL2 if lower ELs
+	 * access PAuth registers
+	 *
+	 * HCR_APK_BIT: Set to one to disable traps to EL2 if lower ELs
+	 * access PAuth instructions
+	 */
+	hcr_el2 = read_hcr_el2();
+	write_hcr_el2(hcr_el2 | HCR_API_BIT | HCR_APK_BIT);
+
+	/*
+	 * Initialise CNTHCTL_EL2. All fields are architecturally UNKNOWN
+	 * on reset and are set to zero except for field(s) listed below.
+	 *
+	 * CNTHCTL_EL2.EL1PCEN: Set to one to disable traps to EL2
+	 * if lower ELs accesses to the physical timer registers.
+	 *
+	 * CNTHCTL_EL2.EL1PCTEN: Set to one to disable traps to EL2
+	 * if lower ELs access to the physical counter registers.
+	 */
+	write_cnthctl_el2(CNTHCTL_RESET_VAL | EL1PCEN_BIT | EL1PCTEN_BIT);
+
+	/*
+	 * On Armv8-R, the EL1&0 memory system architecture is configurable
+	 * as a VMSA or PMSA. All the fields architecturally UNKNOWN on reset
+	* and are set to zero except for field listed below.
+	*
+	* VCTR_EL2.MSA: Set to one to ensure the VMSA is enabled so that
+	* rich OS can boot.
+	*/
+	write_vtcr_el2(VTCR_RESET_VAL | VTCR_EL2_MSA);
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_debug.S b/plat/arm/board/fvp_r/fvp_r_debug.S
new file mode 100644
index 0000000..88f0a29
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_debug.S
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/debug.h>
+
+	.globl el2_panic
+
+	/***********************************************************
+	 * The common implementation of do_panic for all BL stages
+	 ***********************************************************/
+
+.section .rodata.panic_str, "aS"
+	panic_msg: .asciz "PANIC at PC : 0x"
+
+/*
+ * el2_panic will be redefined by the
+ * crash reporting mechanism (if enabled)
+ */
+el2_panic:
+	mov	x6, x30
+	bl	plat_crash_console_init
+
+	/* Check if the console is initialized */
+	cbz	x0, _panic_handler
+
+	/* The console is initialized */
+	adr	x4, panic_msg
+	bl	asm_print_str
+	mov	x4, x6
+
+	/* The panic location is lr -4 */
+	sub	x4, x4, #4
+	bl	asm_print_hex
+
+	bl	plat_crash_console_flush
+
+_panic_handler:
+	/* Pass to plat_panic_handler the address from where el2_panic was
+	 * called, not the address of the call from el2_panic.
+	 */
+	mov	x30, x6
+	b	plat_panic_handler
diff --git a/plat/arm/board/fvp_r/fvp_r_def.h b/plat/arm/board/fvp_r/fvp_r_def.h
new file mode 100644
index 0000000..eda39cf
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_def.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FVP_R_DEF_H
+#define FVP_R_DEF_H
+
+#include <lib/utils_def.h>
+
+/******************************************************************************
+ * FVP-R topology constants
+ *****************************************************************************/
+#define FVP_R_CLUSTER_COUNT		2
+#define FVP_R_MAX_CPUS_PER_CLUSTER	4
+#define FVP_R_MAX_PE_PER_CPU		1
+#define FVP_R_PRIMARY_CPU		0x0
+
+/******************************************************************************
+ * Definition of platform soc id
+ *****************************************************************************/
+#define FVP_R_SOC_ID			0
+
+/*******************************************************************************
+ * FVP_R memory map related constants
+ ******************************************************************************/
+
+#define FLASH1_BASE			UL(0x8c000000)
+#define FLASH1_SIZE			UL(0x04000000)
+
+#define PSRAM_BASE			UL(0x94000000)
+#define PSRAM_SIZE			UL(0x04000000)
+
+#define VRAM_BASE			UL(0x98000000)
+#define VRAM_SIZE			UL(0x02000000)
+
+/* Aggregate of all devices in the first GB */
+#define DEVICE0_BASE			UL(0xa0000000)
+#define DEVICE0_SIZE			UL(0x0c200000)
+
+/*
+ *  In case of FVP_R models with CCN, the CCN register space overlaps into
+ *  the NSRAM area.
+ */
+#define DEVICE1_BASE			UL(0xae000000)
+#define DEVICE1_SIZE			UL(0x1A00000)
+
+#define NSRAM_BASE			UL(0xae000000)
+#define NSRAM_SIZE			UL(0x10000)
+/* Devices in the second GB */
+#define DEVICE2_BASE			UL(0xffe00000)
+#define DEVICE2_SIZE			UL(0x00200000)
+
+#define PCIE_EXP_BASE			UL(0xc0000000)
+#define TZRNG_BASE			UL(0x7fe60000)
+
+/* Non-volatile counters */
+#define TRUSTED_NVCTR_BASE		UL(0xffe70000)
+#define TFW_NVCTR_BASE			(TRUSTED_NVCTR_BASE + UL(0x0000))
+#define TFW_NVCTR_SIZE			UL(4)
+#define NTFW_CTR_BASE			(TRUSTED_NVCTR_BASE + UL(0x0004))
+#define NTFW_CTR_SIZE			UL(4)
+
+/* Keys */
+#define SOC_KEYS_BASE			UL(0xffe80000)
+#define TZ_PUB_KEY_HASH_BASE		(SOC_KEYS_BASE + UL(0x0000))
+#define TZ_PUB_KEY_HASH_SIZE		UL(32)
+#define HU_KEY_BASE			(SOC_KEYS_BASE + UL(0x0020))
+#define HU_KEY_SIZE			UL(16)
+#define END_KEY_BASE			(SOC_KEYS_BASE + UL(0x0044))
+#define END_KEY_SIZE			UL(32)
+
+/* Constants to distinguish FVP_R type */
+#define HBI_BASE_FVP_R			U(0x020)
+#define REV_BASE_FVP_R_V0		U(0x0)
+#define REV_BASE_FVP_R_REVC		U(0x2)
+
+#define HBI_FOUNDATION_FVP_R		U(0x010)
+#define REV_FOUNDATION_FVP_R_V2_0	U(0x0)
+#define REV_FOUNDATION_FVP_R_V2_1	U(0x1)
+#define REV_FOUNDATION_FVP_R_v9_1	U(0x2)
+#define REV_FOUNDATION_FVP_R_v9_6	U(0x3)
+
+#define BLD_GIC_VE_MMAP			U(0x0)
+#define BLD_GIC_A53A57_MMAP		U(0x1)
+
+#define ARCH_MODEL			U(0x1)
+
+/* FVP_R Power controller base address*/
+#define PWRC_BASE			UL(0x1c100000)
+
+/* FVP_R SP804 timer frequency is 35 MHz*/
+#define SP804_TIMER_CLKMULT		1
+#define SP804_TIMER_CLKDIV		35
+
+/* SP810 controller. FVP_R specific flags */
+#define FVP_R_SP810_CTRL_TIM0_OV		BIT_32(16)
+#define FVP_R_SP810_CTRL_TIM1_OV		BIT_32(18)
+#define FVP_R_SP810_CTRL_TIM2_OV		BIT_32(20)
+#define FVP_R_SP810_CTRL_TIM3_OV		BIT_32(22)
+
+#endif /* FVP_R_DEF_H */
diff --git a/plat/arm/board/fvp_r/fvp_r_err.c b/plat/arm/board/fvp_r/fvp_r_err.c
new file mode 100644
index 0000000..7ee752b
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_err.c
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+
+#include <common/debug.h>
+#include <drivers/arm/sp805.h>
+#include <drivers/cfi/v2m_flash.h>
+#include <plat/arm/common/plat_arm.h>
+#include <platform_def.h>
+
+/*
+ * FVP_R error handler
+ */
+__dead2 void plat_arm_error_handler(int err)
+{
+	int ret;
+
+	switch (err) {
+	case -ENOENT:
+	case -EAUTH:
+		/* Image load or authentication error. Erase the ToC */
+		INFO("Erasing FIP ToC from flash...\n");
+		(void)nor_unlock(PLAT_ARM_FLASH_IMAGE_BASE);
+		ret = nor_word_program(PLAT_ARM_FLASH_IMAGE_BASE, 0);
+		if (ret != 0) {
+			ERROR("Cannot erase ToC\n");
+		} else {
+			INFO("Done\n");
+		}
+		break;
+	default:
+		/* Unexpected error */
+		break;
+	}
+
+	(void)console_flush();
+
+	/* Setup the watchdog to reset the system as soon as possible */
+	sp805_refresh(ARM_SP805_TWDG_BASE, 1U);
+
+	while (true) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_helpers.S b/plat/arm/board/fvp_r/fvp_r_helpers.S
new file mode 100644
index 0000000..ba85777
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_helpers.S
@@ -0,0 +1,128 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <drivers/arm/fvp/fvp_pwrc.h>
+#include <drivers/arm/gicv2.h>
+#include <drivers/arm/gicv3.h>
+
+#include <platform_def.h>
+
+
+	.globl	plat_secondary_cold_boot_setup
+	.globl	plat_get_my_entrypoint
+	.globl	plat_is_my_cpu_primary
+
+	/* -----------------------------------------------------
+	 * void plat_secondary_cold_boot_setup (void);
+	 *
+	 * This function performs any platform specific actions
+	 * needed for a secondary cpu after a cold reset e.g
+	 * mark the cpu's presence, mechanism to place it in a
+	 * holding pen etc.
+	 * TODO: Should we read the PSYS register to make sure
+	 * that the request has gone through.
+	 * -----------------------------------------------------
+	 */
+func plat_secondary_cold_boot_setup
+	/* ---------------------------------------------
+	 * Power down this cpu.
+	 * TODO: Do we need to worry about powering the
+	 * cluster down as well here? That will need
+	 * locks which we won't have unless an elf-
+	 * loader zeroes out the zi section.
+	 * ---------------------------------------------
+	 */
+	mrs	x0, mpidr_el1
+	mov_imm	x1, PWRC_BASE
+	str	w0, [x1, #PPOFFR_OFF]
+
+	/* ---------------------------------------------
+	 * There is no sane reason to come out of this
+	 * wfi so panic if we do. This cpu will be pow-
+	 * ered on and reset by the cpu_on pm api
+	 * ---------------------------------------------
+	 */
+	dsb	sy
+	wfi
+	no_ret	plat_panic_handler
+endfunc plat_secondary_cold_boot_setup
+
+	/* ---------------------------------------------------------------------
+	 * uintptr_t plat_get_my_entrypoint (void);
+	 *
+	 * Main job of this routine is to distinguish between a cold and warm
+	 * boot. On FVP_R, this information can be queried from the power
+	 * controller. The Power Control SYS Status Register (PSYSR) indicates
+	 * the wake-up reason for the CPU.
+	 *
+	 * For a cold boot, return 0.
+	 * For a warm boot, read the mailbox and return the address it contains.
+	 *
+	 * TODO: PSYSR is a common register and should be
+	 * 	accessed using locks. Since it is not possible
+	 * 	to use locks immediately after a cold reset
+	 * 	we are relying on the fact that after a cold
+	 * 	reset all cpus will read the same WK field
+	 * ---------------------------------------------------------------------
+	 */
+func plat_get_my_entrypoint
+	/* ---------------------------------------------------------------------
+	 * When bit PSYSR.WK indicates either "Wake by PPONR" or "Wake by GIC
+	 * WakeRequest signal" then it is a warm boot.
+	 * ---------------------------------------------------------------------
+	 */
+	mrs	x2, mpidr_el1
+	mov_imm	x1, PWRC_BASE
+	str	w2, [x1, #PSYSR_OFF]
+	ldr	w2, [x1, #PSYSR_OFF]
+	ubfx	w2, w2, #PSYSR_WK_SHIFT, #PSYSR_WK_WIDTH
+	cmp	w2, #WKUP_PPONR
+	beq	warm_reset
+	cmp	w2, #WKUP_GICREQ
+	beq	warm_reset
+
+	/* Cold reset */
+	mov	x0, #0
+	ret
+
+warm_reset:
+	/* ---------------------------------------------------------------------
+	 * A mailbox is maintained in the trusted SRAM. It is flushed out of the
+	 * caches after every update using normal memory so it is safe to read
+	 * it here with SO attributes.
+	 * ---------------------------------------------------------------------
+	 */
+	mov_imm	x0, PLAT_ARM_TRUSTED_MAILBOX_BASE
+	ldr	x0, [x0]
+	cbz	x0, _panic_handler
+	ret
+
+	/* ---------------------------------------------------------------------
+	 * The power controller indicates this is a warm reset but the mailbox
+	 * is empty. This should never happen!
+	 * ---------------------------------------------------------------------
+	 */
+_panic_handler:
+	no_ret	plat_panic_handler
+endfunc plat_get_my_entrypoint
+
+	/* -----------------------------------------------------
+	 * unsigned int plat_is_my_cpu_primary (void);
+	 *
+	 * Find out whether the current cpu is the primary
+	 * cpu.
+	 * -----------------------------------------------------
+	 */
+func plat_is_my_cpu_primary
+	mrs	x0, mpidr_el1
+	mov_imm	x1, MPIDR_AFFINITY_MASK
+	and	x0, x0, x1
+	cmp	x0, #FVP_R_PRIMARY_CPU
+	cset	w0, eq
+	ret
+endfunc plat_is_my_cpu_primary
diff --git a/plat/arm/board/fvp_r/fvp_r_io_storage.c b/plat/arm/board/fvp_r/fvp_r_io_storage.c
new file mode 100644
index 0000000..3b44828
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_io_storage.c
@@ -0,0 +1,105 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_semihosting.h>
+#include <drivers/io/io_storage.h>
+#include <lib/semihosting.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/common_def.h>
+
+/* Semihosting filenames */
+#define BL33_IMAGE_NAME			"bl33.bin"
+
+#if TRUSTED_BOARD_BOOT
+#define TRUSTED_KEY_CERT_NAME		"trusted_key.crt"
+#define NT_FW_KEY_CERT_NAME		"nt_fw_key.crt"
+#define NT_FW_CONTENT_CERT_NAME		"nt_fw_content.crt"
+#endif /* TRUSTED_BOARD_BOOT */
+
+/* IO devices */
+static const io_dev_connector_t *sh_dev_con;
+static uintptr_t sh_dev_handle;
+
+static const io_file_spec_t sh_file_spec[] = {
+	[BL33_IMAGE_ID] = {
+		.path = BL33_IMAGE_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+#if TRUSTED_BOARD_BOOT
+	[TRUSTED_KEY_CERT_ID] = {
+		.path = TRUSTED_KEY_CERT_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+	[NON_TRUSTED_FW_KEY_CERT_ID] = {
+		.path = NT_FW_KEY_CERT_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
+		.path = NT_FW_CONTENT_CERT_NAME,
+		.mode = FOPEN_MODE_RB
+	},
+#endif /* TRUSTED_BOARD_BOOT */
+};
+
+
+static int open_semihosting(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	/* See if the file exists on semi-hosting.*/
+	result = io_dev_init(sh_dev_handle, (uintptr_t)NULL);
+	if (result == 0) {
+		result = io_open(sh_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using Semi-hosting IO\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+void plat_arm_io_setup(void)
+{
+	int io_result;
+
+	io_result = arm_io_setup();
+	if (io_result < 0) {
+		panic();
+	}
+
+	/* Register the additional IO devices on this platform */
+	io_result = register_io_dev_sh(&sh_dev_con);
+	if (io_result < 0) {
+		panic();
+	}
+
+	/* Open connections to devices and cache the handles */
+	io_result = io_dev_open(sh_dev_con, (uintptr_t)NULL, &sh_dev_handle);
+	if (io_result < 0) {
+		panic();
+	}
+}
+
+/*
+ * FVP_R provides semihosting as an alternative to load images
+ */
+int plat_arm_get_alt_image_source(unsigned int image_id, uintptr_t *dev_handle,
+				  uintptr_t *image_spec)
+{
+	int result = open_semihosting((const uintptr_t)&sh_file_spec[image_id]);
+
+	if (result == 0) {
+		*dev_handle = sh_dev_handle;
+		*image_spec = (uintptr_t)&sh_file_spec[image_id];
+	}
+
+	return result;
+}
diff --git a/plat/arm/board/fvp_r/fvp_r_misc_helpers.S b/plat/arm/board/fvp_r/fvp_r_misc_helpers.S
new file mode 100644
index 0000000..67ad164
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_misc_helpers.S
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <asm_macros.S>
+
+	.globl	disable_mpu_el2
+	.globl	disable_mpu_icache_el2
+
+/* ---------------------------------------------------------------------------
+ * Disable the MPU at EL2.
+ * ---------------------------------------------------------------------------
+ */
+
+func disable_mpu_el2
+	mov	x1, #(SCTLR_M_BIT | SCTLR_C_BIT)
+do_disable_mpu_el2:
+	mrs	x0, sctlr_el2
+	bic	x0, x0, x1
+	msr	sctlr_el2, x0
+	isb	/* ensure MMU is off */
+	dsb	sy
+	ret
+endfunc disable_mpu_el2
+
+
+func disable_mpu_icache_el2
+	mov	x1, #(SCTLR_M_BIT | SCTLR_C_BIT | SCTLR_I_BIT)
+	b	do_disable_mpu_el2
+endfunc disable_mpu_icache_el2
diff --git a/plat/arm/board/fvp_r/fvp_r_private.h b/plat/arm/board/fvp_r/fvp_r_private.h
new file mode 100644
index 0000000..48f6e89
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_private.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FVP_R_PRIVATE_H
+#define FVP_R_PRIVATE_H
+
+#include <plat/arm/common/plat_arm.h>
+
+/*******************************************************************************
+ * Function and variable prototypes
+ ******************************************************************************/
+
+void fvp_config_setup(void);
+
+void fvp_interconnect_init(void);
+void fvp_interconnect_enable(void);
+void fvp_interconnect_disable(void);
+void fvp_timer_init(void);
+
+#endif /* FVP_R_PRIVATE_H */
diff --git a/plat/arm/board/fvp_r/fvp_r_stack_protector.c b/plat/arm/board/fvp_r/fvp_r_stack_protector.c
new file mode 100644
index 0000000..69b6312
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_stack_protector.c
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <fvp_r_arch_helpers.h>
+#include <plat/common/platform.h>
+
+#define RANDOM_CANARY_VALUE ((u_register_t) 8092347823957523895ULL)
+
+u_register_t plat_get_stack_protector_canary(void)
+{
+	/*
+	 * Ideally, a random number should be returned instead of the
+	 * combination of a timer's value and a compile-time constant. As the
+	 * FVP_R does not have any random number generator, this is better than
+	 * nothing but not necessarily really secure.
+	 */
+	return RANDOM_CANARY_VALUE ^ read_cntpct_el0();
+}
+
diff --git a/plat/arm/board/fvp_r/fvp_r_trusted_boot.c b/plat/arm/board/fvp_r/fvp_r_trusted_boot.c
new file mode 100644
index 0000000..de0b28f
--- /dev/null
+++ b/plat/arm/board/fvp_r/fvp_r_trusted_boot.c
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <lib/fconf/fconf.h>
+#include <lib/mmio.h>
+#include <tools_share/tbbr_oid.h>
+
+#include <plat/arm/common/fconf_nv_cntr_getter.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+
+/*
+ * Return the ROTPK hash in the following ASN.1 structure in DER format:
+ *
+ * AlgorithmIdentifier  ::=  SEQUENCE  {
+ *     algorithm	OBJECT IDENTIFIER,
+ *     parameters	ANY DEFINED BY algorithm OPTIONAL
+ * }
+ *
+ * DigestInfo ::= SEQUENCE {
+ *     digestAlgorithm	AlgorithmIdentifier,
+ *     digest		OCTET STRING
+ * }
+ */
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	return arm_get_rotpk_info(cookie, key_ptr, key_len, flags);
+}
+
+/*
+ * Store a new non-volatile counter value.
+ *
+ * On some FVP_R versions, the non-volatile counters are read-only so this
+ * function will always fail.
+ *
+ * Return: 0 = success, Otherwise = error
+ */
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	const char *oid;
+	uintptr_t nv_ctr_addr;
+
+	assert(cookie != NULL);
+
+	oid = (const char *)cookie;
+	if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		nv_ctr_addr = FCONF_GET_PROPERTY(cot, nv_cntr_addr,
+						TRUSTED_NV_CTR_ID);
+	} else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		nv_ctr_addr = FCONF_GET_PROPERTY(cot, nv_cntr_addr,
+						NON_TRUSTED_NV_CTR_ID);
+	} else {
+		return 1;
+	}
+
+	mmio_write_32(nv_ctr_addr, nv_ctr);
+
+	/*
+	 * If the FVP_R models a locked counter then its value cannot be updated
+	 * and the above write operation has been silently ignored.
+	 */
+	return (mmio_read_32(nv_ctr_addr) == nv_ctr) ? 0 : 1;
+}
diff --git a/plat/arm/board/fvp_r/include/fvp_r_arch_helpers.h b/plat/arm/board/fvp_r/include/fvp_r_arch_helpers.h
new file mode 100644
index 0000000..92bf484
--- /dev/null
+++ b/plat/arm/board/fvp_r/include/fvp_r_arch_helpers.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FVP_R_ARCH_HELPERS_H
+#define FVP_R_ARCH_HELPERS_H
+
+#include <arch_helpers.h>
+
+/*******************************************************************************
+ * MPU register definitions
+ ******************************************************************************/
+#define MPUIR_EL2		S3_4_C0_C0_4
+#define PRBAR_EL2		S3_4_C6_C8_0
+#define PRLAR_EL2		S3_4_C6_C8_1
+#define PRSELR_EL2		S3_4_C6_C2_1
+#define PRENR_EL2		S3_4_C6_C1_1
+
+/* v8-R64 MPU registers */
+DEFINE_RENAME_SYSREG_RW_FUNCS(mpuir_el2, MPUIR_EL2)
+DEFINE_RENAME_SYSREG_RW_FUNCS(prenr_el2, PRENR_EL2)
+DEFINE_RENAME_SYSREG_RW_FUNCS(prselr_el2, PRSELR_EL2)
+DEFINE_RENAME_SYSREG_RW_FUNCS(prbar_el2, PRBAR_EL2)
+DEFINE_RENAME_SYSREG_RW_FUNCS(prlar_el2, PRLAR_EL2)
+
+#endif /* FVP_R_ARCH_HELPERS_H */
diff --git a/plat/arm/board/fvp_r/include/platform_def.h b/plat/arm/board/fvp_r/include/platform_def.h
new file mode 100644
index 0000000..ea3a258
--- /dev/null
+++ b/plat/arm/board/fvp_r/include/platform_def.h
@@ -0,0 +1,268 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef FVP_R_PLATFORM_DEF_H
+#define FVP_R_PLATFORM_DEF_H
+
+#define PLAT_V2M_OFFSET			0x80000000
+
+#define BL33_IMAGE_DESC {				\
+	.image_id = BL33_IMAGE_ID,			\
+	SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,	\
+		VERSION_2, image_info_t, 0),		\
+	.image_info.image_base = PLAT_ARM_DRAM1_BASE + 0x1000,		\
+	.image_info.image_max_size = UL(0x3ffff000), \
+	SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,	\
+		VERSION_2, entry_point_info_t, SECURE | EXECUTABLE),\
+	.ep_info.pc = PLAT_ARM_DRAM1_BASE + 0x1000,				\
+	.ep_info.spsr = SPSR_64(MODE_EL2, MODE_SP_ELX, DISABLE_ALL_EXCEPTIONS),	\
+}
+
+#include "../fvp_r_def.h"
+#include <drivers/arm/tzc400.h>
+#include <lib/utils_def.h>
+#include <plat/arm/board/common/v2m_def.h>
+
+/* These are referenced by arm_def.h #included next, so #define first. */
+#define PLAT_ARM_TRUSTED_ROM_BASE	UL(0x80000000)
+#define PLAT_ARM_TRUSTED_SRAM_BASE	UL(0x84000000)
+#define PLAT_ARM_TRUSTED_DRAM_BASE	UL(0x86000000)
+#define PLAT_ARM_DRAM1_BASE		ULL(0x0)
+#define PLAT_ARM_DRAM2_BASE		ULL(0x080000000)
+
+#define PLAT_HW_CONFIG_DTB_BASE		ULL(0x12000000)
+#define PLAT_ARM_SYS_CNTCTL_BASE	UL(0xaa430000)
+#define PLAT_ARM_SYS_CNTREAD_BASE	UL(0xaa800000)
+#define PLAT_ARM_SYS_TIMCTL_BASE	UL(0xaa810000)
+#define PLAT_ARM_SYS_CNT_BASE_S		UL(0xaa820000)
+#define PLAT_ARM_SYS_CNT_BASE_NS	UL(0xaa830000)
+#define PLAT_ARM_SP805_TWDG_BASE	UL(0xaa490000)
+
+#include <plat/arm/common/arm_def.h>
+#include <plat/common/common_def.h>
+
+
+/* Required to create plat_regions: */
+#define MIN_LVL_BLOCK_DESC	U(1)
+
+/* Required platform porting definitions */
+#define PLATFORM_CORE_COUNT  (U(FVP_R_CLUSTER_COUNT) * \
+			      U(FVP_R_MAX_CPUS_PER_CLUSTER) * \
+			      U(FVP_R_MAX_PE_PER_CPU))
+
+#define PLAT_NUM_PWR_DOMAINS (U(FVP_R_CLUSTER_COUNT) + \
+			      PLATFORM_CORE_COUNT + U(1))
+
+#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL2
+
+/*
+ * Other platform porting definitions are provided by included headers
+ */
+
+/*
+ * Required ARM standard platform porting definitions
+ */
+#define PLAT_ARM_CLUSTER_COUNT		U(FVP_R_CLUSTER_COUNT)
+#define PLAT_ARM_DRAM1_SIZE		ULL(0x7fffffff)
+#define PLAT_ARM_TRUSTED_SRAM_SIZE	UL(0x00040000)	/* 256 KB */
+#define PLAT_ARM_TRUSTED_ROM_SIZE	UL(0x04000000)	/* 64 MB */
+#define PLAT_ARM_TRUSTED_DRAM_SIZE	UL(0x02000000)	/* 32 MB */
+
+/* These two are defined thus in arm_def.h, but doesn't seem to see it... */
+#define PLAT_BL1_RO_LIMIT               (BL1_RO_BASE \
+					+ PLAT_ARM_TRUSTED_ROM_SIZE)
+
+#define PLAT_ARM_SYS_CNTCTL_BASE	UL(0xaa430000)
+#define PLAT_ARM_SYS_CNTREAD_BASE	UL(0xaa800000)
+#define PLAT_ARM_SYS_TIMCTL_BASE	UL(0xaa810000)
+#define PLAT_ARM_SYS_CNT_BASE_S		UL(0xaa820000)
+#define PLAT_ARM_SYS_CNT_BASE_NS	UL(0xaa830000)
+#define PLAT_ARM_SP805_TWDG_BASE	UL(0xaa490000)
+
+/* virtual address used by dynamic mem_protect for chunk_base */
+#define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xc0000000)
+
+/* No SCP in FVP_R */
+#define PLAT_ARM_SCP_TZC_DRAM1_SIZE	UL(0x0)
+
+#define PLAT_ARM_DRAM2_SIZE		UL(0x80000000)
+
+#define PLAT_HW_CONFIG_DTB_SIZE		ULL(0x8000)
+
+#define ARM_DTB_DRAM_NS			MAP_REGION_FLAT(		\
+					PLAT_HW_CONFIG_DTB_BASE,	\
+					PLAT_HW_CONFIG_DTB_SIZE,	\
+					MT_MEMORY | MT_RO | MT_NS)
+
+#define V2M_FVP_R_SYSREGS_BASE		UL(0x9c010000)
+
+/*
+ * Load address of BL33 for this platform port,
+ * U-Boot specifically must be loaded at a 4K aligned address.
+ */
+#define PLAT_ARM_NS_IMAGE_BASE		(PLAT_ARM_DRAM1_BASE + 0x1000)
+
+/*
+ * PLAT_ARM_MMAP_ENTRIES depends on the number of entries in the
+ * plat_arm_mmap array defined for each BL stage.
+ */
+#if !USE_ROMLIB
+# define PLAT_ARM_MMAP_ENTRIES		11
+# define MAX_XLAT_TABLES		5
+#else
+# define PLAT_ARM_MMAP_ENTRIES		12
+# define MAX_XLAT_TABLES		6
+#endif
+# define N_MPU_REGIONS			16  /* number of MPU regions */
+# define ALL_MPU_EL2_REGIONS_USED	0xffffffff
+	/* this is the PRENR_EL2 value if all MPU regions are in use */
+
+/*
+ * PLAT_ARM_MAX_BL1_RW_SIZE is calculated using the current BL1 RW debug size
+ * plus a little space for growth.
+ */
+#define PLAT_ARM_MAX_BL1_RW_SIZE	UL(0xB000)
+
+/*
+ * PLAT_ARM_MAX_ROMLIB_RW_SIZE is define to use a full page
+ */
+
+#if USE_ROMLIB
+#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	UL(0x1000)
+#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	UL(0xe000)
+#define FVP_R_BL2_ROMLIB_OPTIMIZATION UL(0x6000)
+#else
+#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	UL(0)
+#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	UL(0)
+#define FVP_R_BL2_ROMLIB_OPTIMIZATION UL(0)
+#endif
+
+/*
+ * PLAT_ARM_MAX_BL2_SIZE is calculated using the current BL2 debug size plus a
+ * little space for growth.
+ */
+#if TRUSTED_BOARD_BOOT
+#if COT_DESC_IN_DTB
+# define PLAT_ARM_MAX_BL2_SIZE	(UL(0x1E000) - FVP_R_BL2_ROMLIB_OPTIMIZATION)
+#else
+# define PLAT_ARM_MAX_BL2_SIZE	(UL(0x1D000) - FVP_R_BL2_ROMLIB_OPTIMIZATION)
+#endif
+#else
+# define PLAT_ARM_MAX_BL2_SIZE	(UL(0x13000) - FVP_R_BL2_ROMLIB_OPTIMIZATION)
+#endif
+
+/*
+ * Since BL31 NOBITS overlays BL2 and BL1-RW, PLAT_ARM_MAX_BL31_SIZE is
+ * calculated using the current BL31 PROGBITS debug size plus the sizes of
+ * BL2 and BL1-RW
+ */
+#define PLAT_ARM_MAX_BL31_SIZE		UL(0x3D000)
+
+/*
+ * Size of cacheable stacks
+ */
+#if defined(IMAGE_BL1)
+# if TRUSTED_BOARD_BOOT
+#  define PLATFORM_STACK_SIZE		UL(0x1000)
+# else
+#  define PLATFORM_STACK_SIZE		UL(0x500)
+# endif
+#endif
+
+#define MAX_IO_DEVICES			3
+#define MAX_IO_HANDLES			4
+
+/*
+ * These nominally reserve the last block of flash for PSCI MEM PROTECT flag,
+ * but no PSCI in FVP_R platform, so reserve nothing:
+ */
+#define PLAT_ARM_FLASH_IMAGE_BASE	(PLAT_ARM_DRAM1_BASE + UL(0x40000000))
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(PLAT_ARM_DRAM1_SIZE - UL(0x40000000))
+
+#define PLAT_ARM_NVM_BASE		V2M_FLASH0_BASE
+#define PLAT_ARM_NVM_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+/*
+ * PL011 related constants
+ */
+#define PLAT_ARM_BOOT_UART_BASE		V2M_IOFPGA_UART0_BASE
+#define PLAT_ARM_BOOT_UART_CLK_IN_HZ	V2M_IOFPGA_UART0_CLK_IN_HZ
+
+#define PLAT_ARM_RUN_UART_BASE		V2M_IOFPGA_UART1_BASE
+#define PLAT_ARM_RUN_UART_CLK_IN_HZ	V2M_IOFPGA_UART1_CLK_IN_HZ
+
+#define PLAT_ARM_CRASH_UART_BASE	PLAT_ARM_RUN_UART_BASE
+#define PLAT_ARM_CRASH_UART_CLK_IN_HZ	PLAT_ARM_RUN_UART_CLK_IN_HZ
+
+#define PLAT_ARM_TSP_UART_BASE		V2M_IOFPGA_UART2_BASE
+#define PLAT_ARM_TSP_UART_CLK_IN_HZ	V2M_IOFPGA_UART2_CLK_IN_HZ
+
+/* CCI related constants */
+#define PLAT_FVP_R_CCI400_BASE		UL(0xac090000)
+#define PLAT_FVP_R_CCI400_CLUS0_SL_PORT	3
+#define PLAT_FVP_R_CCI400_CLUS1_SL_PORT	4
+
+/* CCI-500/CCI-550 on Base platform */
+#define PLAT_FVP_R_CCI5XX_BASE		UL(0xaa000000)
+#define PLAT_FVP_R_CCI5XX_CLUS0_SL_PORT	5
+#define PLAT_FVP_R_CCI5XX_CLUS1_SL_PORT	6
+
+/* System timer related constants */
+#define PLAT_ARM_NSTIMER_FRAME_ID	U(1)
+
+/* Mailbox base address */
+#define PLAT_ARM_TRUSTED_MAILBOX_BASE	ARM_TRUSTED_SRAM_BASE
+
+
+/* TrustZone controller related constants
+ *
+ * Currently only filters 0 and 2 are connected on Base FVP_R.
+ * Filter 0 : CPU clusters (no access to DRAM by default)
+ * Filter 1 : not connected
+ * Filter 2 : LCDs (access to VRAM allowed by default)
+ * Filter 3 : not connected
+ * Programming unconnected filters will have no effect at the
+ * moment. These filter could, however, be connected in future.
+ * So care should be taken not to configure the unused filters.
+ *
+ * Allow only non-secure access to all DRAM to supported devices.
+ * Give access to the CPUs and Virtio. Some devices
+ * would normally use the default ID so allow that too.
+ */
+#define PLAT_ARM_TZC_BASE		UL(0xaa4a0000)
+#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
+
+#define PLAT_ARM_TZC_NS_DEV_ACCESS	(				\
+		TZC_REGION_ACCESS_RDWR(FVP_R_NSAID_DEFAULT)	|	\
+		TZC_REGION_ACCESS_RDWR(FVP_R_NSAID_PCI)		|	\
+		TZC_REGION_ACCESS_RDWR(FVP_R_NSAID_AP)		|	\
+		TZC_REGION_ACCESS_RDWR(FVP_R_NSAID_VIRTIO)	|	\
+		TZC_REGION_ACCESS_RDWR(FVP_R_NSAID_VIRTIO_OLD))
+
+/*
+ * GIC related constants to cater for both GICv2 and GICv3 instances of an
+ * FVP_R. They could be overridden at runtime in case the FVP_R implements the
+ * legacy VE memory map.
+ */
+#define PLAT_ARM_GICD_BASE		BASE_GICD_BASE
+#define PLAT_ARM_GICR_BASE		BASE_GICR_BASE
+#define PLAT_ARM_GICC_BASE		BASE_GICC_BASE
+
+#define PLAT_ARM_SP_IMAGE_STACK_BASE	(PLAT_SP_IMAGE_NS_BUF_BASE +	\
+					 PLAT_SP_IMAGE_NS_BUF_SIZE)
+
+#define PLAT_SP_PRI			PLAT_RAS_PRI
+
+/*
+ * Physical and virtual address space limits for MPU in AARCH64 & AARCH32 modes
+ */
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 36)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 36)
+
+#define ARM_SOC_CONTINUATION_SHIFT	U(24)
+#define ARM_SOC_IDENTIFICATION_SHIFT	U(16)
+
+#endif /* FVP_R_PLATFORM_DEF_H */
diff --git a/plat/arm/board/fvp_r/platform.mk b/plat/arm/board/fvp_r/platform.mk
new file mode 100644
index 0000000..93b5cf2
--- /dev/null
+++ b/plat/arm/board/fvp_r/platform.mk
@@ -0,0 +1,99 @@
+#
+# Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Only aarch64 ARCH supported for FVP_R
+ARCH	:= aarch64
+
+# Override to exclude BL2, BL2U, BL31, and BL33 for FVP_R
+override NEED_BL2	:= no
+override NEED_BL2U	:= no
+override NEED_BL31	:= no
+NEED_BL32		:= no
+
+override CTX_INCLUDE_AARCH32_REGS	:=	0
+
+# Use MPU-based memory management:
+XLAT_MPU_LIB_V1		:=	1
+
+# FVP R will not have more than 2 clusters so just use CCI interconnect
+FVP_R_INTERCONNECT_SOURCES	:= 	drivers/arm/cci/cci.c
+
+
+include plat/arm/board/common/board_common.mk
+include plat/arm/common/arm_common.mk
+
+PLAT_INCLUDES		:=	-Iplat/arm/board/fvp_r/include
+
+FVP_R_BL_COMMON_SOURCES	:=	plat/arm/board/fvp_r/fvp_r_common.c		\
+				plat/arm/board/fvp_r/fvp_r_context_mgmt.c	\
+				plat/arm/board/fvp_r/fvp_r_debug.S		\
+				plat/arm/board/fvp_r/fvp_r_err.c		\
+				plat/arm/board/fvp_r/fvp_r_helpers.S		\
+				plat/arm/board/fvp_r/fvp_r_misc_helpers.S
+
+FVP_R_BL1_SOURCES	:=	plat/arm/board/fvp_r/fvp_r_bl1_arch_setup.c	\
+				plat/arm/board/fvp_r/fvp_r_bl1_setup.c		\
+				plat/arm/board/fvp_r/fvp_r_io_storage.c		\
+				plat/arm/board/fvp_r/fvp_r_bl1_entrypoint.S	\
+				plat/arm/board/fvp_r/fvp_r_bl1_exceptions.S	\
+				plat/arm/board/fvp_r/fvp_r_bl1_main.c
+
+FVP_R_CPU_LIBS		:=	lib/cpus/${ARCH}/aem_generic.S
+
+FVP_R_DYNC_CFG_SOURCES	:=	common/fdt_wrappers.c				\
+				plat/arm/common/arm_dyn_cfg.c
+
+ifeq (${TRUSTED_BOARD_BOOT},1)
+FVP_R_AUTH_SOURCES	:=	drivers/auth/auth_mod.c				\
+				drivers/auth/crypto_mod.c			\
+				drivers/auth/img_parser_mod.c			\
+				lib/fconf/fconf_tbbr_getter.c			\
+				plat/common/tbbr/plat_tbbr.c			\
+				drivers/auth/tbbr/tbbr_cot_bl1_r64.c		\
+				drivers/auth/tbbr/tbbr_cot_common.c		\
+				plat/arm/board/common/board_arm_trusted_boot.c	\
+				plat/arm/board/common/rotpk/arm_dev_rotpk.S	\
+				plat/arm/board/fvp_r/fvp_r_trusted_boot.c
+
+FVP_R_BL1_SOURCES	+=	${MBEDTLS_SOURCES}				\
+				${FVP_R_AUTH_SOURCES}
+endif
+
+ifeq (${USE_SP804_TIMER},1)
+FVP_R_BL_COMMON_SOURCES		+=	drivers/arm/sp804/sp804_delay_timer.c
+else
+FVP_R_BL_COMMON_SOURCES		+=	drivers/delay_timer/generic_delay_timer.c
+endif
+
+# Enable Activity Monitor Unit extensions by default
+ENABLE_AMU			:=	1
+
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+FVP_R_BL_COMMON_SOURCES	+=	plat/arm/board/fvp_r/fvp_r_stack_protector.c
+endif
+
+override BL1_SOURCES	:=	drivers/arm/sp805/sp805.c			\
+				drivers/cfi/v2m/v2m_flash.c			\
+				drivers/delay_timer/delay_timer.c		\
+				drivers/io/io_fip.c				\
+				drivers/io/io_memmap.c				\
+				drivers/io/io_storage.c				\
+				drivers/io/io_semihosting.c			\
+				lib/cpus/aarch64/cpu_helpers.S			\
+				lib/fconf/fconf_dyn_cfg_getter.c		\
+				lib/semihosting/semihosting.c			\
+				lib/semihosting/${ARCH}/semihosting_call.S	\
+				plat/arm/common/arm_bl1_setup.c			\
+				plat/arm/common/arm_err.c			\
+				plat/arm/common/arm_io_storage.c		\
+				plat/arm/common/fconf/arm_fconf_io.c		\
+				plat/common/plat_bl1_common.c			\
+				plat/common/aarch64/platform_up_stack.S		\
+				${FVP_R_BL1_SOURCES}				\
+				${FVP_R_BL_COMMON_SOURCES}			\
+				${FVP_R_CPU_LIBS}				\
+				${FVP_R_DYNC_CFG_SOURCES}			\
+				${FVP_R_INTERCONNECT_SOURCES}
diff --git a/plat/arm/board/fvp_ve/include/platform_def.h b/plat/arm/board/fvp_ve/include/platform_def.h
index 3f2fcee..bd8ef6a 100644
--- a/plat/arm/board/fvp_ve/include/platform_def.h
+++ b/plat/arm/board/fvp_ve/include/platform_def.h
@@ -303,8 +303,8 @@
 #define MAX_IO_HANDLES			4
 
 /* Reserve the last block of flash for PSCI MEM PROTECT flag */
-#define PLAT_ARM_FIP_BASE		V2M_FLASH1_BASE
-#define PLAT_ARM_FIP_MAX_SIZE		(V2M_FLASH1_SIZE - V2M_FLASH_BLOCK_SIZE)
+#define PLAT_ARM_FLASH_IMAGE_BASE	V2M_FLASH1_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(V2M_FLASH1_SIZE - V2M_FLASH_BLOCK_SIZE)
 
 #define PLAT_ARM_NVM_BASE		V2M_FLASH1_BASE
 #define PLAT_ARM_NVM_SIZE		(V2M_FLASH1_SIZE - V2M_FLASH_BLOCK_SIZE)
diff --git a/plat/arm/board/fvp_ve/platform.mk b/plat/arm/board/fvp_ve/platform.mk
index ac45d57..f7eace8 100644
--- a/plat/arm/board/fvp_ve/platform.mk
+++ b/plat/arm/board/fvp_ve/platform.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2019-2020, Arm Limited. All rights reserved.
+# Copyright (c) 2019-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 ifdef ARM_CORTEX_A5
 # Use the SP804 timer instead of the generic one
 USE_SP804_TIMER	:= 1
@@ -125,10 +127,13 @@
 # Firmware Configuration Framework sources
 include lib/fconf/fconf.mk
 
+BL1_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+BL2_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+
 # Add `libfdt` and Arm common helpers required for Dynamic Config
 include lib/libfdt/libfdt.mk
 
 DYN_CFG_SOURCES		+=	plat/arm/common/arm_dyn_cfg.c		\
-				plat/arm/common/arm_dyn_cfg_helpers.c	\
-				common/fdt_wrappers.c
+				plat/arm/common/arm_dyn_cfg_helpers.c
 
+DYN_CFG_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
diff --git a/plat/arm/board/juno/fdts/juno_fw_config.dts b/plat/arm/board/juno/fdts/juno_fw_config.dts
index c0538f8..4b88efe 100644
--- a/plat/arm/board/juno/fdts/juno_fw_config.dts
+++ b/plat/arm/board/juno/fdts/juno_fw_config.dts
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -17,5 +17,11 @@
 			max-size = <0x200>;
 			id = <TB_FW_CONFIG_ID>;
 		};
+
+		hw-config {
+			load-address = <0x0 0x82000000>;
+			max-size = <0x8000>;
+			id = <HW_CONFIG_ID>;
+		};
 	};
 };
diff --git a/plat/arm/board/juno/include/platform_def.h b/plat/arm/board/juno/include/platform_def.h
index 91c3ae7..d61ba5d 100644
--- a/plat/arm/board/juno/include/platform_def.h
+++ b/plat/arm/board/juno/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -53,6 +53,15 @@
 #define PLAT_ARM_DRAM2_BASE		ULL(0x880000000)
 #define PLAT_ARM_DRAM2_SIZE		ULL(0x180000000)
 
+/* Range of kernel DTB load address */
+#define JUNO_DTB_DRAM_MAP_START		ULL(0x82000000)
+#define JUNO_DTB_DRAM_MAP_SIZE		ULL(0x00008000) /* 32KB */
+
+#define ARM_DTB_DRAM_NS			MAP_REGION_FLAT(		\
+					JUNO_DTB_DRAM_MAP_START,	\
+					JUNO_DTB_DRAM_MAP_SIZE,		\
+					MT_MEMORY | MT_RO | MT_NS)
+
 /* virtual address used by dynamic mem_protect for chunk_base */
 #define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xc0000000)
 
@@ -108,7 +117,7 @@
 
 #ifdef IMAGE_BL31
 #  define PLAT_ARM_MMAP_ENTRIES		7
-#  define MAX_XLAT_TABLES		3
+#  define MAX_XLAT_TABLES		5
 #endif
 
 #ifdef IMAGE_BL32
diff --git a/plat/arm/board/juno/juno_bl1_setup.c b/plat/arm/board/juno/juno_bl1_setup.c
index 2234055..a9d5cc3 100644
--- a/plat/arm/board/juno/juno_bl1_setup.c
+++ b/plat/arm/board/juno/juno_bl1_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -62,11 +62,11 @@
  ******************************************************************************/
 bool plat_arm_bl1_fwu_needed(void)
 {
-	const int32_t *nv_flags_ptr = (const int32_t *)V2M_SYS_NVFLAGS_ADDR;
+	int32_t nv_flags = (int32_t)mmio_read_32(V2M_SYS_NVFLAGS_ADDR);
 
 	/* Check if TOC is invalid or watchdog reset happened. */
-	return (!arm_io_is_toc_valid() || (((*nv_flags_ptr == -EAUTH) ||
-		(*nv_flags_ptr == -ENOENT)) && is_watchdog_reset()));
+	return (!arm_io_is_toc_valid() || (((nv_flags == -EAUTH) ||
+		(nv_flags == -ENOENT)) && is_watchdog_reset()));
 }
 
 /*******************************************************************************
@@ -86,13 +86,11 @@
  ******************************************************************************/
 __dead2 void bl1_plat_fwu_done(void *client_cookie, void *reserved)
 {
-	unsigned int *nv_flags_clr = (unsigned int *)
-			(V2M_SYSREGS_BASE + V2M_SYS_NVFLAGSCLR);
-	unsigned int *nv_flags_ptr = (unsigned int *)
-			(V2M_SYSREGS_BASE + V2M_SYS_NVFLAGS);
+	uint32_t nv_flags = mmio_read_32(V2M_SYS_NVFLAGS_ADDR);
 
 	/* Clear the NV flags register. */
-	*nv_flags_clr = *nv_flags_ptr;
+	mmio_write_32((V2M_SYSREGS_BASE + V2M_SYS_NVFLAGSCLR),
+		      nv_flags);
 
 	/* Setup the watchdog to reset the system as soon as possible */
 	sp805_refresh(ARM_SP805_TWDG_BASE, 1U);
diff --git a/plat/arm/board/juno/juno_bl2_setup.c b/plat/arm/board/juno/juno_bl2_setup.c
index 95ef77c..849acd6 100644
--- a/plat/arm/board/juno/juno_bl2_setup.c
+++ b/plat/arm/board/juno/juno_bl2_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2017,2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -8,6 +8,9 @@
 
 #include <common/bl_common.h>
 #include <common/desc_image_load.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
+
 #include <plat/arm/common/plat_arm.h>
 
 #if JUNO_AARCH32_EL3_RUNTIME
@@ -30,4 +33,41 @@
 
 	return err;
 }
+
+#else
+
+/*******************************************************************************
+ * This function returns the list of executable images
+ ******************************************************************************/
+struct bl_params *plat_get_next_bl_params(void)
+{
+	struct bl_params *arm_bl_params = arm_get_next_bl_params();
+
+#if __aarch64__
+	const struct dyn_cfg_dtb_info_t *fw_config_info;
+	bl_mem_params_node_t *param_node;
+	uintptr_t fw_config_base = 0U;
+	entry_point_info_t *ep_info;
+
+	/* Get BL31 image node */
+	param_node = get_bl_mem_params_node(BL31_IMAGE_ID);
+	assert(param_node != NULL);
+
+	/* Get fw_config load address */
+	fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, FW_CONFIG_ID);
+	assert(fw_config_info != NULL);
+
+	fw_config_base = fw_config_info->config_addr;
+	assert(fw_config_base != 0U);
+
+	/*
+	 * Get the entry point info of BL31 image and override
+	 * arg1 of entry point info with fw_config base address
+	 */
+	ep_info = &param_node->ep_info;
+	ep_info->args.arg1 = (uint32_t)fw_config_base;
+#endif /* __aarch64__ */
+
+	return arm_bl_params;
+}
 #endif /* JUNO_AARCH32_EL3_RUNTIME */
diff --git a/plat/arm/board/juno/juno_bl31_setup.c b/plat/arm/board/juno/juno_bl31_setup.c
new file mode 100644
index 0000000..7a0a6d9
--- /dev/null
+++ b/plat/arm/board/juno/juno_bl31_setup.c
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
+
+#include <plat/arm/common/plat_arm.h>
+
+void __init bl31_early_platform_setup2(u_register_t arg0,
+		u_register_t arg1, u_register_t arg2, u_register_t arg3)
+{
+	const struct dyn_cfg_dtb_info_t *soc_fw_config_info;
+
+	INFO("BL31 FCONF: FW_CONFIG address = %lx\n", (uintptr_t)arg1);
+
+	/* Fill the properties struct with the info from the config dtb */
+	fconf_populate("FW_CONFIG", arg1);
+
+	soc_fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, SOC_FW_CONFIG_ID);
+	if (soc_fw_config_info != NULL) {
+		arg1 = soc_fw_config_info->config_addr;
+	}
+
+	arm_bl31_early_platform_setup((void *)arg0, arg1, arg2, (void *)arg3);
+
+	/*
+	 * Initialize Interconnect for this cluster during cold boot.
+	 * No need for locks as no other CPU is active.
+	 */
+	plat_arm_interconnect_init();
+
+	/*
+	 * Enable Interconnect coherency for the primary CPU's cluster.
+	 * Earlier bootloader stages might already do this (e.g. Trusted
+	 * Firmware's BL1 does it) but we can't assume so. There is no harm in
+	 * executing this code twice anyway.
+	 * Platform specific PSCI code will enable coherency for other
+	 * clusters.
+	 */
+	plat_arm_interconnect_enter_coherency();
+}
+
+void __init bl31_plat_arch_setup(void)
+{
+	arm_bl31_plat_arch_setup();
+
+	/* HW_CONFIG was also loaded by BL2 */
+	const struct dyn_cfg_dtb_info_t *hw_config_info;
+
+	hw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, HW_CONFIG_ID);
+	assert(hw_config_info != NULL);
+
+	fconf_populate("HW_CONFIG", hw_config_info->config_addr);
+}
diff --git a/plat/arm/board/juno/juno_common.c b/plat/arm/board/juno/juno_common.c
index da4918c..038f604 100644
--- a/plat/arm/board/juno/juno_common.c
+++ b/plat/arm/board/juno/juno_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -75,6 +75,7 @@
 	ARM_V2M_MAP_MEM_PROTECT,
 #endif
 	SOC_CSS_MAP_DEVICE,
+	ARM_DTB_DRAM_NS,
 	{0}
 };
 #endif
@@ -117,9 +118,9 @@
 int32_t plat_get_soc_version(void)
 {
 	return (int32_t)
-		((ARM_SOC_IDENTIFICATION_CODE << ARM_SOC_IDENTIFICATION_SHIFT)
-		 | (ARM_SOC_CONTINUATION_CODE << ARM_SOC_CONTINUATION_SHIFT)
-		 | JUNO_SOC_ID);
+		(SOC_ID_SET_JEP_106(ARM_SOC_CONTINUATION_CODE,
+				    ARM_SOC_IDENTIFICATION_CODE) |
+		 (JUNO_SOC_ID & SOC_ID_IMPL_DEF_MASK));
 }
 
 /* Get SOC revision */
@@ -128,6 +129,6 @@
 	unsigned int sys_id;
 
 	sys_id = mmio_read_32(V2M_SYSREGS_BASE + V2M_SYS_ID);
-	return (int32_t)((sys_id >> V2M_SYS_ID_REV_SHIFT) &
-			V2M_SYS_ID_REV_MASK);
+	return (int32_t)(((sys_id >> V2M_SYS_ID_REV_SHIFT) &
+			  V2M_SYS_ID_REV_MASK) & SOC_ID_REV_MASK);
 }
diff --git a/plat/arm/board/juno/juno_decl.h b/plat/arm/board/juno/juno_decl.h
deleted file mode 100644
index cd87c3b..0000000
--- a/plat/arm/board/juno/juno_decl.h
+++ /dev/null
@@ -1,12 +0,0 @@
-/*
- * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef JUNO_DECL_H
-#define JUNO_DECL_H
-
-int juno_getentropy(void *buf, size_t len);
-
-#endif /* JUNO_DECL_H */
diff --git a/plat/arm/board/juno/juno_err.c b/plat/arm/board/juno/juno_err.c
index 60699cc..02d751e 100644
--- a/plat/arm/board/juno/juno_err.c
+++ b/plat/arm/board/juno/juno_err.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,10 +16,8 @@
  */
 void __dead2 plat_arm_error_handler(int err)
 {
-	uint32_t *flags_ptr = (uint32_t *)V2M_SYS_NVFLAGS_ADDR;
-
 	/* Propagate the err code in the NV-flags register */
-	*flags_ptr = err;
+	mmio_write_32(V2M_SYS_NVFLAGS_ADDR, (uint32_t)err);
 
 	/* Setup the watchdog to reset the system as soon as possible */
 	sp805_refresh(ARM_SP805_TWDG_BASE, 1U);
diff --git a/plat/arm/board/juno/juno_security.c b/plat/arm/board/juno/juno_security.c
index 1e64c02..654a7f1 100644
--- a/plat/arm/board/juno/juno_security.c
+++ b/plat/arm/board/juno/juno_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -115,6 +115,14 @@
 	/* Drive SPIDEN LOW to disable invasive debug of secure state. */
 	mmio_write_32(SSC_REG_BASE + SSC_DBGCFG_CLR,
 		1U << SPIDEN_INT_CLR_SHIFT);
+
+	/* Set internal drive selection for SPNIDEN. */
+	mmio_write_32(SSC_REG_BASE + SSC_DBGCFG_SET,
+		1U << SPNIDEN_SEL_SET_SHIFT);
+
+	/* Drive SPNIDEN LOW to disable non-invasive debug of secure state. */
+	mmio_write_32(SSC_REG_BASE + SSC_DBGCFG_CLR,
+		1U << SPNIDEN_INT_CLR_SHIFT);
 #endif
 }
 
diff --git a/plat/arm/board/juno/juno_stack_protector.c b/plat/arm/board/juno/juno_stack_protector.c
index 236eb5b..3924af8 100644
--- a/plat/arm/board/juno/juno_stack_protector.c
+++ b/plat/arm/board/juno/juno_stack_protector.c
@@ -7,26 +7,21 @@
 #include <arch_helpers.h>
 #include <common/debug.h>
 #include <lib/utils.h>
+#include <plat/common/plat_trng.h>
 #include <platform_def.h>
 
-#include "juno_decl.h"
-
 u_register_t plat_get_stack_protector_canary(void)
 {
-	u_register_t c[TRNG_NBYTES / sizeof(u_register_t)];
-	u_register_t ret = 0;
-	size_t i;
+	uint64_t entropy;
 
-	if (juno_getentropy(c, sizeof(c)) != 0) {
+	if (!plat_get_entropy(&entropy)) {
 		ERROR("Not enough entropy to initialize canary value\n");
 		panic();
 	}
 
-	/*
-	 * On Juno we get 128-bits of entropy in one round.
-	 * Fuse the values together to form the canary.
-	 */
-	for (i = 0; i < ARRAY_SIZE(c); i++)
-		ret ^= c[i];
-	return ret;
+	if (sizeof(entropy) == sizeof(u_register_t)) {
+		return entropy;
+	}
+
+	return (entropy & 0xffffffffULL) ^ (entropy >> 32);
 }
diff --git a/plat/arm/board/juno/juno_trng.c b/plat/arm/board/juno/juno_trng.c
index 7869d3e..09552a6 100644
--- a/plat/arm/board/juno/juno_trng.c
+++ b/plat/arm/board/juno/juno_trng.c
@@ -4,19 +4,29 @@
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <arm_acle.h>
 #include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <lib/mmio.h>
 #include <lib/utils_def.h>
 #include <platform_def.h>
 
-#include "juno_decl.h"
+#include <lib/smccc.h>
+#include <services/trng_svc.h>
+#include <smccc_helpers.h>
+
+#include <plat/common/platform.h>
 
 #define NSAMPLE_CLOCKS	1 /* min 1 cycle, max 231 cycles */
 #define NRETRIES	5
 
-static inline int output_valid(void)
+/* initialised to false */
+static bool juno_trng_initialized;
+
+static bool output_valid(void)
 {
 	int i;
 
@@ -25,59 +35,74 @@
 
 		val = mmio_read_32(TRNG_BASE + TRNG_STATUS);
 		if (val & 1U)
-			break;
+			return true;
 	}
-	if (i >= NRETRIES)
-		return 0; /* No output data available. */
-	return 1;
+	return false; /* No output data available. */
 }
 
+DEFINE_SVC_UUID2(_plat_trng_uuid,
+	0x23523c58, 0x7448, 0x4083, 0x9d, 0x16,
+	0xe3, 0xfa, 0xb9, 0xf1, 0x73, 0xbc
+);
+uuid_t plat_trng_uuid;
+
+static uint32_t crc_value = ~0U;
+
 /*
- * This function fills `buf` with `len` bytes of entropy.
- * It uses the Trusted Entropy Source peripheral on Juno.
- * Returns 0 when the buffer has been filled with entropy
- * successfully and -1 otherwise.
+ * Uses the Trusted Entropy Source peripheral on Juno to return 8 bytes of
+ * entropy. Returns 'true' when done successfully, 'false' otherwise.
  */
-int juno_getentropy(void *buf, size_t len)
+bool plat_get_entropy(uint64_t *out)
 {
-	uint8_t *bp = buf;
+	uint64_t ret;
 
-	assert(buf);
-	assert(len);
-	assert(!check_uptr_overflow((uintptr_t)bp, len));
+	assert(out);
+	assert(!check_uptr_overflow((uintptr_t)out, sizeof(*out)));
 
-	/* Disable interrupt mode. */
-	mmio_write_32(TRNG_BASE + TRNG_INTMASK, 0);
-	/* Program TRNG to sample for `NSAMPLE_CLOCKS`. */
-	mmio_write_32(TRNG_BASE + TRNG_CONFIG, NSAMPLE_CLOCKS);
+	if (!juno_trng_initialized) {
+		/* Disable interrupt mode. */
+		mmio_write_32(TRNG_BASE + TRNG_INTMASK, 0);
+		/* Program TRNG to sample for `NSAMPLE_CLOCKS`. */
+		mmio_write_32(TRNG_BASE + TRNG_CONFIG, NSAMPLE_CLOCKS);
+		/* Abort any potentially pending sampling. */
+		mmio_write_32(TRNG_BASE + TRNG_CONTROL, 2);
+		/* Reset TRNG outputs. */
+		mmio_write_32(TRNG_BASE + TRNG_STATUS, 1);
 
-	while (len > 0) {
-		int i;
+		juno_trng_initialized = true;
+	}
 
+	if (!output_valid()) {
 		/* Start TRNG. */
 		mmio_write_32(TRNG_BASE + TRNG_CONTROL, 1);
 
-		/* Check if output is valid. */
 		if (!output_valid())
-			return -1;
-
-		/* Fill entropy buffer. */
-		for (i = 0; i < TRNG_NOUTPUTS; i++) {
-			size_t n;
-			uint32_t val;
-
-			val = mmio_read_32(TRNG_BASE + i * sizeof(uint32_t));
-			n = MIN(len, sizeof(uint32_t));
-			memcpy(bp, &val, n);
-			bp += n;
-			len -= n;
-			if (len == 0)
-				break;
-		}
-
-		/* Reset TRNG outputs. */
-		mmio_write_32(TRNG_BASE + TRNG_STATUS, 1);
+			return false;
 	}
 
-	return 0;
+	/* CRC each two 32-bit registers together, combine the pairs */
+	crc_value = __crc32w(crc_value, mmio_read_32(TRNG_BASE + 0));
+	crc_value = __crc32w(crc_value, mmio_read_32(TRNG_BASE + 4));
+	ret = (uint64_t)crc_value << 32;
+
+	crc_value = __crc32w(crc_value, mmio_read_32(TRNG_BASE + 8));
+	crc_value = __crc32w(crc_value, mmio_read_32(TRNG_BASE + 12));
+	*out = ret | crc_value;
+
+	/* Acknowledge current cycle, clear output registers. */
+	mmio_write_32(TRNG_BASE + TRNG_STATUS, 1);
+	/* Trigger next TRNG cycle. */
+	mmio_write_32(TRNG_BASE + TRNG_CONTROL, 1);
+
+	return true;
+}
+
+void plat_entropy_setup(void)
+{
+	uint64_t dummy;
+
+	plat_trng_uuid = _plat_trng_uuid;
+
+	/* Initialise the entropy source and trigger RNG generation */
+	plat_get_entropy(&dummy);
 }
diff --git a/plat/arm/board/juno/platform.mk b/plat/arm/board/juno/platform.mk
index 78704b5..2c84eb3 100644
--- a/plat/arm/board/juno/platform.mk
+++ b/plat/arm/board/juno/platform.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 # Include GICv2 driver files
 include drivers/arm/gic/v2/gicv2.mk
 
@@ -44,6 +46,8 @@
 $(eval $(call add_define,JUNO_TZMP1))
 endif
 
+TRNG_SUPPORT		:=	1
+
 ifeq (${JUNO_AARCH32_EL3_RUNTIME}, 1)
 # Include BL32 in FIP
 NEED_BL32		:= yes
@@ -81,6 +85,9 @@
 				lib/cpus/aarch64/cortex_a57.S		\
 				lib/cpus/aarch64/cortex_a72.S		\
 				lib/utils/mem_region.c			\
+				lib/fconf/fconf.c			\
+				lib/fconf/fconf_dyn_cfg_getter.c	\
+				plat/arm/board/juno/juno_bl31_setup.c	\
 				plat/arm/board/juno/juno_pm.c		\
 				plat/arm/board/juno/juno_topology.c	\
 				plat/arm/common/arm_nor_psci_mem_protect.c \
@@ -88,6 +95,8 @@
 				${JUNO_INTERCONNECT_SOURCES}		\
 				${JUNO_SECURITY_SOURCES}
 
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
 ifeq (${CSS_USE_SCMI_SDS_DRIVER},1)
 BL1_SOURCES		+=	drivers/arm/css/sds/sds.c
 endif
@@ -108,7 +117,7 @@
 all : bl1_romlib.bin
 endif
 
-bl1_romlib.bin : $(BUILD_PLAT)/bl1.bin $(BUILD_PLAT)/romlib/romlib.bin
+bl1_romlib.bin : $(BUILD_PLAT)/bl1.bin romlib.bin
 	@echo "Building combined BL1 and ROMLIB binary for Juno $@"
 	./lib/romlib/gen_combined_bl1_romlib.sh -o bl1_romlib.bin $(BUILD_PLAT)
 
@@ -164,17 +173,27 @@
     endif
 endif
 
+BL1_CPPFLAGS += -march=armv8-a+crc
+BL2_CPPFLAGS += -march=armv8-a+crc
+BL2U_CPPFLAGS += -march=armv8-a+crc
+BL31_CPPFLAGS += -march=armv8-a+crc
+BL32_CPPFLAGS += -march=armv8-a+crc
+
 # Add the FDT_SOURCES and options for Dynamic Config
 FDT_SOURCES		+=	plat/arm/board/juno/fdts/${PLAT}_fw_config.dts	\
-				plat/arm/board/juno/fdts/${PLAT}_tb_fw_config.dts
+				plat/arm/board/juno/fdts/${PLAT}_tb_fw_config.dts \
+				fdts/${PLAT}.dts
 
 FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
 TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
+HW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}.dtb
 
 # Add the FW_CONFIG to FIP and specify the same to certtool
 $(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
 # Add the TB_FW_CONFIG to FIP and specify the same to certtool
 $(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
+# Add the HW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${HW_CONFIG},--hw-config,${HW_CONFIG}))
 
 include plat/arm/board/common/board_common.mk
 include plat/arm/common/arm_common.mk
diff --git a/plat/arm/board/morello/morello_bl31_setup.c b/plat/arm/board/morello/morello_bl31_setup.c
index 5b91e87..59dd37b 100644
--- a/plat/arm/board/morello/morello_bl31_setup.c
+++ b/plat/arm/board/morello/morello_bl31_setup.c
@@ -8,6 +8,7 @@
 #include <drivers/arm/css/css_mhu_doorbell.h>
 #include <drivers/arm/css/scmi.h>
 #include <drivers/arm/css/sds.h>
+#include <lib/cassert.h>
 #include <plat/arm/common/plat_arm.h>
 
 #include "morello_def.h"
@@ -17,18 +18,21 @@
  * Platform information structure stored in SDS.
  * This structure holds information about platform's DDR
  * size which is an information about multichip setup
- * 	- multichip mode
- * 	- slave_count
- * 	- Local DDR size in GB, DDR memory in master board
- * 	- Remote DDR size in GB, DDR memory in slave board
+ *	- Local DDR size in bytes, DDR memory in master board
+ *	- Remote DDR size in bytes, DDR memory in slave board
+ *	- slave_count
+ *	- multichip mode
  */
 struct morello_plat_info {
-	bool multichip_mode;
+	uint64_t local_ddr_size;
+	uint64_t remote_ddr_size;
 	uint8_t slave_count;
-	uint8_t local_ddr_size;
-	uint8_t remote_ddr_size;
+	bool multichip_mode;
 } __packed;
 
+/* Compile time assertion to ensure the size of structure is 18 bytes */
+CASSERT(sizeof(struct morello_plat_info) == MORELLO_SDS_PLATFORM_INFO_SIZE,
+		assert_invalid_plat_info_size);
 /*
  * BL33 image information structure stored in SDS.
  * This structure holds the source & destination addresses and
@@ -80,6 +84,7 @@
 	int ret;
 	struct morello_plat_info plat_info;
 	struct morello_bl33_info bl33_info;
+	struct morello_plat_info *copy_dest;
 
 	ret = sds_init();
 	if (ret != SDS_OK) {
@@ -99,8 +104,8 @@
 
 	/* Validate plat_info SDS */
 	if ((plat_info.local_ddr_size == 0U)
-		|| (plat_info.local_ddr_size > MORELLO_MAX_DDR_CAPACITY_GB)
-		|| (plat_info.remote_ddr_size > MORELLO_MAX_DDR_CAPACITY_GB)
+		|| (plat_info.local_ddr_size > MORELLO_MAX_DDR_CAPACITY)
+		|| (plat_info.remote_ddr_size > MORELLO_MAX_DDR_CAPACITY)
 		|| (plat_info.slave_count > MORELLO_MAX_SLAVE_COUNT)) {
 		ERROR("platform info SDS is corrupted\n");
 		panic();
@@ -127,5 +132,6 @@
 	 * and platform information should be passed to BL33 using NT_FW_CONFIG
 	 * passing mechanism.
 	 */
-	mmio_write_32(MORELLO_PLATFORM_INFO_BASE, *(uint32_t *)&plat_info);
+	copy_dest = (struct morello_plat_info *)MORELLO_PLATFORM_INFO_BASE;
+	*copy_dest = plat_info;
 }
diff --git a/plat/arm/board/morello/morello_def.h b/plat/arm/board/morello/morello_def.h
index 09db303..793729b 100644
--- a/plat/arm/board/morello/morello_def.h
+++ b/plat/arm/board/morello/morello_def.h
@@ -18,8 +18,8 @@
 /* SDS Platform information defines */
 #define MORELLO_SDS_PLATFORM_INFO_STRUCT_ID	U(8)
 #define MORELLO_SDS_PLATFORM_INFO_OFFSET	U(0)
-#define MORELLO_SDS_PLATFORM_INFO_SIZE		U(4)
-#define MORELLO_MAX_DDR_CAPACITY_GB		U(64)
+#define MORELLO_SDS_PLATFORM_INFO_SIZE		U(18)
+#define MORELLO_MAX_DDR_CAPACITY		U(0x1000000000)
 #define MORELLO_MAX_SLAVE_COUNT			U(16)
 
 /* SDS BL33 image information defines */
@@ -28,6 +28,6 @@
 #define MORELLO_SDS_BL33_INFO_SIZE		U(12)
 
 /* Base address of non-secure SRAM where Platform information will be filled */
-#define MORELLO_PLATFORM_INFO_BASE		UL(0x06008000)
+#define MORELLO_PLATFORM_INFO_BASE		UL(0x06000000)
 
 #endif /* MORELLO_DEF_H */
diff --git a/plat/arm/board/morello/platform.mk b/plat/arm/board/morello/platform.mk
index 2a23bc6..fc7d4d3 100644
--- a/plat/arm/board/morello/platform.mk
+++ b/plat/arm/board/morello/platform.mk
@@ -65,5 +65,3 @@
 include plat/arm/common/arm_common.mk
 include plat/arm/css/common/css_common.mk
 include plat/arm/board/common/board_common.mk
-
-override ERRATA_N1_1542419		:=	1
diff --git a/plat/arm/board/n1sdp/platform.mk b/plat/arm/board/n1sdp/platform.mk
index 4b621e3..f20397a 100644
--- a/plat/arm/board/n1sdp/platform.mk
+++ b/plat/arm/board/n1sdp/platform.mk
@@ -69,7 +69,7 @@
 USE_COHERENT_MEM			:=	0
 
 # Enable the flag since N1SDP has a system level cache
-NEOVERSE_N1_EXTERNAL_LLC		:=	1
+NEOVERSE_Nx_EXTERNAL_LLC		:=	1
 include plat/arm/common/arm_common.mk
 include plat/arm/css/common/css_common.mk
 include plat/arm/board/common/board_common.mk
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_nt_fw_config.dts b/plat/arm/board/rddaniel/fdts/rddaniel_nt_fw_config.dts
deleted file mode 100644
index 4d4580d..0000000
--- a/plat/arm/board/rddaniel/fdts/rddaniel_nt_fw_config.dts
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/dts-v1/;
-/ {
-	/* compatible string */
-	compatible = "arm,rd-daniel";
-
-	/*
-	 * Place holder for system-id node with default values. The
-	 * value of platform-id and config-id will be set to the
-	 * correct values during the BL2 stage of boot.
-	 */
-	system-id {
-		platform-id = <0x0>;
-		config-id = <0x0>;
-		multi-chip-mode = <0x0>;
-	};
-};
diff --git a/plat/arm/board/rddaniel/include/platform_def.h b/plat/arm/board/rddaniel/include/platform_def.h
deleted file mode 100644
index a118ca3..0000000
--- a/plat/arm/board/rddaniel/include/platform_def.h
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PLATFORM_DEF_H
-#define PLATFORM_DEF_H
-
-#include <lib/utils_def.h>
-
-#include <sgi_base_platform_def.h>
-
-#define PLAT_ARM_CLUSTER_COUNT		U(16)
-#define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(1)
-#define CSS_SGI_MAX_PE_PER_CPU		U(1)
-
-#define PLAT_CSS_MHU_BASE		UL(0x45400000)
-#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
-
-#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
-#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
-
-/* TZC Related Constants */
-#define PLAT_ARM_TZC_BASE		UL(0x21830000)
-#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
-
-#define TZC400_OFFSET			UL(0x1000000)
-#define TZC400_COUNT			4
-
-#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
-					 (n * TZC400_OFFSET))
-
-#define TZC_NSAID_ALL_AP		U(0)
-#define TZC_NSAID_PCI			U(1)
-#define TZC_NSAID_HDLCD0		U(2)
-#define TZC_NSAID_CLCD			U(7)
-#define TZC_NSAID_AP			U(9)
-#define TZC_NSAID_VIRTIO		U(15)
-
-#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_ALL_AP)) | \
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_HDLCD0)) | \
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_PCI))    | \
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_AP))     | \
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_CLCD))   | \
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_VIRTIO))
-
-/*
- * Physical and virtual address space limits for MMU in AARCH64 & AARCH32 modes
- */
-#ifdef __aarch64__
-#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 42)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 42)
-#else
-#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
-#endif
-
-/* GIC related constants */
-#define PLAT_ARM_GICD_BASE		UL(0x30000000)
-#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
-#define PLAT_ARM_GICR_BASE		UL(0x30140000)
-
-#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/rddaniel/platform.mk b/plat/arm/board/rddaniel/platform.mk
deleted file mode 100644
index 7422d63..0000000
--- a/plat/arm/board/rddaniel/platform.mk
+++ /dev/null
@@ -1,57 +0,0 @@
-# Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-# RD-Daniel platform uses GIC-Clayton which is based on GICv4.1
-GIC_ENABLE_V4_EXTN	:=	1
-
-include plat/arm/css/sgi/sgi-common.mk
-
-RDDANIEL_BASE		=	plat/arm/board/rddaniel
-
-PLAT_INCLUDES		+=	-I${RDDANIEL_BASE}/include/
-
-SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_v1.S
-
-BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
-				${RDDANIEL_BASE}/rddaniel_err.c
-
-BL2_SOURCES		+=	${RDDANIEL_BASE}/rddaniel_plat.c	\
-				${RDDANIEL_BASE}/rddaniel_security.c	\
-				${RDDANIEL_BASE}/rddaniel_err.c		\
-				lib/utils/mem_region.c			\
-				drivers/arm/tzc/tzc400.c		\
-				plat/arm/common/arm_tzc400.c		\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-BL31_SOURCES		+=	${SGI_CPU_SOURCES}			\
-				${RDDANIEL_BASE}/rddaniel_plat.c	\
-				${RDDANIEL_BASE}/rddaniel_topology.c	\
-				drivers/cfi/v2m/v2m_flash.c		\
-				lib/utils/mem_region.c			\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-ifeq (${TRUSTED_BOARD_BOOT}, 1)
-BL1_SOURCES		+=	${RDDANIEL_BASE}/rddaniel_trusted_boot.c
-BL2_SOURCES		+=	${RDDANIEL_BASE}/rddaniel_trusted_boot.c
-endif
-
-# Add the FDT_SOURCES and options for Dynamic Config
-FDT_SOURCES		+=	${RDDANIEL_BASE}/fdts/${PLAT}_fw_config.dts	\
-				${RDDANIEL_BASE}/fdts/${PLAT}_tb_fw_config.dts
-FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
-TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
-
-# Add the FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
-# Add the TB_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
-
-FDT_SOURCES		+=	${RDDANIEL_BASE}/fdts/${PLAT}_nt_fw_config.dts
-NT_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_nt_fw_config.dtb
-
-# Add the NT_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${NT_FW_CONFIG},--nt-fw-config,${NT_FW_CONFIG}))
-
-override CTX_INCLUDE_AARCH32_REGS	:= 0
diff --git a/plat/arm/board/rddaniel/rddaniel_err.c b/plat/arm/board/rddaniel/rddaniel_err.c
deleted file mode 100644
index 5e10942..0000000
--- a/plat/arm/board/rddaniel/rddaniel_err.c
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-
-/*
- * rddaniel error handler
- */
-void __dead2 plat_arm_error_handler(int err)
-{
-	while (1) {
-		wfi();
-	}
-}
diff --git a/plat/arm/board/rddaniel/rddaniel_topology.c b/plat/arm/board/rddaniel/rddaniel_topology.c
deleted file mode 100644
index 55f5e04..0000000
--- a/plat/arm/board/rddaniel/rddaniel_topology.c
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-#include <plat/arm/css/common/css_pm.h>
-
-/******************************************************************************
- * The power domain tree descriptor.
- ******************************************************************************/
-const unsigned char rd_daniel_pd_tree_desc[] = {
-	PLAT_ARM_CLUSTER_COUNT,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER
-};
-
-/*******************************************************************************
- * This function returns the topology tree information.
- ******************************************************************************/
-const unsigned char *plat_get_power_domain_tree_desc(void)
-{
-	return rd_daniel_pd_tree_desc;
-}
-
-/*******************************************************************************
- * The array mapping platform core position (implemented by plat_my_core_pos())
- * to the SCMI power domain ID implemented by SCP.
- ******************************************************************************/
-const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x4)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x5)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x6)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x7)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x8)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x9)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xA)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xB)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xC)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xD)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xE)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xF))
-};
diff --git a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_fw_config.dts b/plat/arm/board/rddanielxlr/fdts/rddanielxlr_fw_config.dts
deleted file mode 100644
index 9c9cefe..0000000
--- a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_fw_config.dts
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/tbbr/tbbr_img_def.h>
-
-/dts-v1/;
-
-/ {
-	dtb-registry {
-		compatible = "fconf,dyn_cfg-dtb_registry";
-
-		tb_fw-config {
-			load-address = <0x0 0x4001300>;
-			max-size = <0x200>;
-			id = <TB_FW_CONFIG_ID>;
-		};
-
-		nt_fw-config {
-			load-address = <0x0 0xFEF00000>;
-			max-size = <0x0100000>;
-			id = <NT_FW_CONFIG_ID>;
-		};
-	};
-};
diff --git a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_nt_fw_config.dts b/plat/arm/board/rddanielxlr/fdts/rddanielxlr_nt_fw_config.dts
deleted file mode 100644
index 42d07a4..0000000
--- a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_nt_fw_config.dts
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/dts-v1/;
-/ {
-	/* compatible string */
-	compatible = "arm,rd-daniel-xlr";
-
-	/*
-	 * Place holder for system-id node with default values. The
-	 * value of platform-id and config-id will be set to the
-	 * correct values during the BL2 stage of boot.
-	 */
-	system-id {
-		platform-id = <0x0>;
-		config-id = <0x0>;
-		multi-chip-mode = <0x0>;
-	};
-};
diff --git a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_tb_fw_config.dts b/plat/arm/board/rddanielxlr/fdts/rddanielxlr_tb_fw_config.dts
deleted file mode 100644
index 49eda27..0000000
--- a/plat/arm/board/rddanielxlr/fdts/rddanielxlr_tb_fw_config.dts
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/dts-v1/;
-
-/ {
-	tb_fw-config {
-		compatible = "arm,tb_fw";
-
-		/* Disable authentication for development */
-		disable_auth = <0x0>;
-
-		/*
-		 * The following two entries are placeholders for Mbed TLS
-		 * heap information. The default values don't matter since
-		 * they will be overwritten by BL1.
-		 * In case of having shared Mbed TLS heap between BL1 and BL2,
-		 * BL1 will populate these two properties with the respective
-		 * info about the shared heap. This info will be available for
-		 * BL2 in order to locate and re-use the heap.
-		 */
-		mbedtls_heap_addr = <0x0 0x0>;
-		mbedtls_heap_size = <0x0>;
-	};
-};
diff --git a/plat/arm/board/rddanielxlr/include/platform_def.h b/plat/arm/board/rddanielxlr/include/platform_def.h
deleted file mode 100644
index b1376b8..0000000
--- a/plat/arm/board/rddanielxlr/include/platform_def.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PLATFORM_DEF_H
-#define PLATFORM_DEF_H
-
-#include <lib/utils_def.h>
-#include <sgi_base_platform_def.h>
-
-#define PLAT_ARM_CLUSTER_COUNT		U(4)
-#define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(1)
-#define CSS_SGI_MAX_PE_PER_CPU		U(1)
-
-#define PLAT_CSS_MHU_BASE		UL(0x45400000)
-#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
-
-#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
-#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
-
-/* Virtual address used by dynamic mem_protect for chunk_base */
-#define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xC0000000)
-
-/* Physical and virtual address space limits for MMU in AARCH64 mode */
-#define PLAT_PHY_ADDR_SPACE_SIZE	CSS_SGI_REMOTE_CHIP_MEM_OFFSET( \
-						CSS_SGI_CHIP_COUNT)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	CSS_SGI_REMOTE_CHIP_MEM_OFFSET( \
-						CSS_SGI_CHIP_COUNT)
-
-/* GIC related constants */
-#define PLAT_ARM_GICD_BASE		UL(0x30000000)
-#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
-#define PLAT_ARM_GICR_BASE		UL(0x30140000)
-
-#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/rddanielxlr/platform.mk b/plat/arm/board/rddanielxlr/platform.mk
deleted file mode 100644
index 8cbad52..0000000
--- a/plat/arm/board/rddanielxlr/platform.mk
+++ /dev/null
@@ -1,66 +0,0 @@
-# Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-# Enable GICv4 extension with multichip driver
-GIC_ENABLE_V4_EXTN		:=	1
-GICV3_IMPL_GIC600_MULTICHIP	:=	1
-
-include plat/arm/css/sgi/sgi-common.mk
-
-RDDANIELXLR_BASE	=	plat/arm/board/rddanielxlr
-
-PLAT_INCLUDES		+=	-I${RDDANIELXLR_BASE}/include/
-
-SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_v1.S
-
-BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
-				${RDDANIELXLR_BASE}/rddanielxlr_err.c
-
-BL2_SOURCES		+=	${RDDANIELXLR_BASE}/rddanielxlr_plat.c	\
-				${RDDANIELXLR_BASE}/rddanielxlr_security.c	\
-				${RDDANIELXLR_BASE}/rddanielxlr_err.c	\
-				lib/utils/mem_region.c			\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-BL31_SOURCES		+=	${SGI_CPU_SOURCES}			\
-				${RDDANIELXLR_BASE}/rddanielxlr_plat.c	\
-				${RDDANIELXLR_BASE}/rddanielxlr_topology.c	\
-				drivers/cfi/v2m/v2m_flash.c		\
-				drivers/arm/gic/v3/gic600_multichip.c	\
-				lib/utils/mem_region.c			\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-ifeq (${TRUSTED_BOARD_BOOT}, 1)
-BL1_SOURCES		+=	${RDDANIELXLR_BASE}/rddanielxlr_trusted_boot.c
-BL2_SOURCES		+=	${RDDANIELXLR_BASE}/rddanielxlr_trusted_boot.c
-endif
-
-# Enable dynamic addition of MMAP regions in BL31
-BL31_CFLAGS		+=	-DPLAT_XLAT_TABLES_DYNAMIC
-
-# Add the FDT_SOURCES and options for Dynamic Config
-FDT_SOURCES		+=	${RDDANIELXLR_BASE}/fdts/${PLAT}_fw_config.dts	\
-				${RDDANIELXLR_BASE}/fdts/${PLAT}_tb_fw_config.dts
-FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
-TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
-
-# Add the FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
-# Add the TB_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
-
-$(eval $(call CREATE_SEQ,SEQ,4))
-ifneq ($(CSS_SGI_CHIP_COUNT),$(filter $(CSS_SGI_CHIP_COUNT),$(SEQ)))
- $(error  "Chip count for RD-Daniel Config-XLR should be either $(SEQ) \
- currently it is set to ${CSS_SGI_CHIP_COUNT}.")
-endif
-
-FDT_SOURCES		+=	${RDDANIELXLR_BASE}/fdts/${PLAT}_nt_fw_config.dts
-NT_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_nt_fw_config.dtb
-
-# Add the NT_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${NT_FW_CONFIG},--nt-fw-config,${NT_FW_CONFIG}))
-
-override CTX_INCLUDE_AARCH32_REGS	:= 0
diff --git a/plat/arm/board/rddanielxlr/rddanielxlr_err.c b/plat/arm/board/rddanielxlr/rddanielxlr_err.c
deleted file mode 100644
index bff57cd..0000000
--- a/plat/arm/board/rddanielxlr/rddanielxlr_err.c
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-
-/*
- * rddanielxlr error handler
- */
-void __dead2 plat_arm_error_handler(int err)
-{
-	while (true) {
-		wfi();
-	}
-}
diff --git a/plat/arm/board/rddanielxlr/rddanielxlr_plat.c b/plat/arm/board/rddanielxlr/rddanielxlr_plat.c
deleted file mode 100644
index 4b5f16a..0000000
--- a/plat/arm/board/rddanielxlr/rddanielxlr_plat.c
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <drivers/arm/gic600_multichip.h>
-#include <plat/arm/common/plat_arm.h>
-#include <plat/common/platform.h>
-#include <sgi_base_platform_def.h>
-#include <sgi_plat.h>
-
-#if defined(IMAGE_BL31)
-static const mmap_region_t rddanielxlr_dynamic_mmap[] = {
-	ARM_MAP_SHARED_RAM_REMOTE_CHIP(1),
-	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(1),
-	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(1),
-#if (CSS_SGI_CHIP_COUNT > 2)
-	ARM_MAP_SHARED_RAM_REMOTE_CHIP(2),
-	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(2),
-	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(2),
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-	ARM_MAP_SHARED_RAM_REMOTE_CHIP(3),
-	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(3),
-	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(3)
-#endif
-};
-
-static struct gic600_multichip_data rddanielxlr_multichip_data __init = {
-	.rt_owner_base = PLAT_ARM_GICD_BASE,
-	.rt_owner = 0,
-	.chip_count = CSS_SGI_CHIP_COUNT,
-	.chip_addrs = {
-		PLAT_ARM_GICD_BASE >> 16,
-		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(1)) >> 16,
-#if (CSS_SGI_CHIP_COUNT > 2)
-		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(2)) >> 16,
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(3)) >> 16,
-#endif
-	},
-	.spi_ids = {
-		{32, 255},
-		{0, 0},
-#if (CSS_SGI_CHIP_COUNT > 2)
-		{0, 0},
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-		{0, 0},
-#endif
-	}
-};
-
-static uintptr_t rddanielxlr_multichip_gicr_frames[] = {
-	/* Chip 0's GICR Base */
-	PLAT_ARM_GICR_BASE,
-	/* Chip 1's GICR BASE */
-	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(1),
-#if (CSS_SGI_CHIP_COUNT > 2)
-	/* Chip 2's GICR BASE */
-	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(2),
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-	/* Chip 3's GICR BASE */
-	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(3),
-#endif
-	UL(0)	/* Zero Termination */
-};
-#endif /* IMAGE_BL31 */
-
-unsigned int plat_arm_sgi_get_platform_id(void)
-{
-	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_ID_OFFSET)
-				& SID_SYSTEM_ID_PART_NUM_MASK;
-}
-
-unsigned int plat_arm_sgi_get_config_id(void)
-{
-	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_CFG_OFFSET);
-}
-
-unsigned int plat_arm_sgi_get_multi_chip_mode(void)
-{
-	return (mmio_read_32(SID_REG_BASE + SID_NODE_ID_OFFSET) &
-			SID_MULTI_CHIP_MODE_MASK) >> SID_MULTI_CHIP_MODE_SHIFT;
-}
-
-/*
- * bl31_platform_setup_function is guarded by IMAGE_BL31 macro because
- * PLAT_XLAT_TABLES_DYNAMIC macro is set to build only for BL31 and not
- * for other stages.
- */
-#if defined(IMAGE_BL31)
-void bl31_platform_setup(void)
-{
-	int ret;
-	unsigned int i;
-
-	if ((plat_arm_sgi_get_multi_chip_mode() == 0) &&
-			(CSS_SGI_CHIP_COUNT > 1)) {
-		ERROR("Chip Count is set to %u but multi-chip mode is not "
-			"enabled\n", CSS_SGI_CHIP_COUNT);
-		panic();
-	} else if ((plat_arm_sgi_get_multi_chip_mode() == 1) &&
-			(CSS_SGI_CHIP_COUNT > 1)) {
-		INFO("Enabling support for multi-chip in RD-Daniel Cfg-XLR\n");
-
-		for (i = 0; i < ARRAY_SIZE(rddanielxlr_dynamic_mmap); i++) {
-			ret = mmap_add_dynamic_region(
-					rddanielxlr_dynamic_mmap[i].base_pa,
-					rddanielxlr_dynamic_mmap[i].base_va,
-					rddanielxlr_dynamic_mmap[i].size,
-					rddanielxlr_dynamic_mmap[i].attr);
-			if (ret != 0) {
-				ERROR("Failed to add dynamic mmap entry "
-						"(ret=%d)\n", ret);
-				panic();
-			}
-		}
-
-		plat_arm_override_gicr_frames(
-			rddanielxlr_multichip_gicr_frames);
-		gic600_multichip_init(&rddanielxlr_multichip_data);
-	}
-
-	sgi_bl31_common_platform_setup();
-}
-#endif /* IMAGE_BL31 */
diff --git a/plat/arm/board/rddanielxlr/rddanielxlr_security.c b/plat/arm/board/rddanielxlr/rddanielxlr_security.c
deleted file mode 100644
index 541f800..0000000
--- a/plat/arm/board/rddanielxlr/rddanielxlr_security.c
+++ /dev/null
@@ -1,10 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/* Initialize the secure environment */
-void plat_arm_security_setup(void)
-{
-}
diff --git a/plat/arm/board/rddanielxlr/rddanielxlr_topology.c b/plat/arm/board/rddanielxlr/rddanielxlr_topology.c
deleted file mode 100644
index 610e667..0000000
--- a/plat/arm/board/rddanielxlr/rddanielxlr_topology.c
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <plat/arm/common/plat_arm.h>
-#include <plat/arm/css/common/css_pm.h>
-#include <sgi_variant.h>
-
-/******************************************************************************
- * The power domain tree descriptor.
- ******************************************************************************/
-const unsigned char rd_daniel_xlr_pd_tree_desc_multi_chip[] = {
-	((PLAT_ARM_CLUSTER_COUNT) * (CSS_SGI_CHIP_COUNT)),
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-#if (CSS_SGI_CHIP_COUNT > 1)
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-#endif
-#if (CSS_SGI_CHIP_COUNT > 2)
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER,
-	CSS_SGI_MAX_CPUS_PER_CLUSTER
-#endif
-};
-
-/*******************************************************************************
- * This function returns the topology tree information.
- ******************************************************************************/
-const unsigned char *plat_get_power_domain_tree_desc(void)
-{
-	if (plat_arm_sgi_get_multi_chip_mode() == 1)
-		return rd_daniel_xlr_pd_tree_desc_multi_chip;
-	panic();
-}
-
-/*******************************************************************************
- * The array mapping platform core position (implemented by plat_my_core_pos())
- * to the SCMI power domain ID implemented by SCP.
- ******************************************************************************/
-const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
-#if (CSS_SGI_CHIP_COUNT > 1)
-	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x3)),
-#endif
-#if (CSS_SGI_CHIP_COUNT > 2)
-	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x3)),
-#endif
-#if (CSS_SGI_CHIP_COUNT > 3)
-	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x3))
-#endif
-};
diff --git a/plat/arm/board/rddanielxlr/rddanielxlr_trusted_boot.c b/plat/arm/board/rddanielxlr/rddanielxlr_trusted_boot.c
deleted file mode 100644
index 4592b8f..0000000
--- a/plat/arm/board/rddanielxlr/rddanielxlr_trusted_boot.c
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-
-/*
- * Return the ROTPK hash in the following ASN.1 structure in DER format:
- *
- * AlgorithmIdentifier  ::=  SEQUENCE  {
- *     algorithm         OBJECT IDENTIFIER,
- *     parameters        ANY DEFINED BY algorithm OPTIONAL
- * }
- *
- * DigestInfo ::= SEQUENCE {
- *     digestAlgorithm   AlgorithmIdentifier,
- *     digest            OCTET STRING
- * }
- */
-int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
-			unsigned int *flags)
-{
-	return arm_get_rotpk_info(cookie, key_ptr, key_len, flags);
-}
diff --git a/plat/arm/board/rde1edge/include/platform_def.h b/plat/arm/board/rde1edge/include/platform_def.h
index 3fb6409..a9b30a4 100644
--- a/plat/arm/board/rde1edge/include/platform_def.h
+++ b/plat/arm/board/rde1edge/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, Arm Limited. All rights reserved.
+ * Copyright (c) 2018-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,7 +9,8 @@
 
 #include <lib/utils_def.h>
 
-#include <sgi_base_platform_def.h>
+#include <sgi_sdei.h>
+#include <sgi_soc_platform_def.h>
 
 #define PLAT_ARM_CLUSTER_COUNT		U(2)
 #define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(8)
diff --git a/plat/arm/board/rde1edge/platform.mk b/plat/arm/board/rde1edge/platform.mk
index a7c0434..0f9dd49 100644
--- a/plat/arm/board/rde1edge/platform.mk
+++ b/plat/arm/board/rde1edge/platform.mk
@@ -12,6 +12,8 @@
 
 SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_e1.S
 
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c
+
 BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
 				${RDE1EDGE_BASE}/rde1edge_err.c
 
@@ -56,4 +58,9 @@
    ${CSS_SGI_CHIP_COUNT}.")
 endif
 
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),0)
+ $(error "CSS_SGI_PLATFORM_VARIANT for RD-E1-Edge should always be 0, \
+     currently set to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
+
 override CTX_INCLUDE_AARCH32_REGS	:= 0
diff --git a/plat/arm/board/rde1edge/rde1edge_security.c b/plat/arm/board/rde1edge/rde1edge_security.c
index 2123e09..35f81d1 100644
--- a/plat/arm/board/rde1edge/rde1edge_security.c
+++ b/plat/arm/board/rde1edge/rde1edge_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Arm Limited. All rights reserved.
+ * Copyright (c) 2019-2021, Arm Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,7 +7,7 @@
 #include <platform_def.h>
 
 #include <common/debug.h>
-#include <drivers/arm/tzc_dmc620.h>
+#include <sgi_dmc620_tzc_regions.h>
 
 uintptr_t rde1edge_dmc_base[] = {
 	RDE1EDGE_DMC620_BASE0,
@@ -20,11 +20,7 @@
 };
 
 static const tzc_dmc620_acc_addr_data_t rde1edge_acc_addr_data[] = {
-	{
-		.region_base = ARM_AP_TZC_DRAM1_BASE,
-		.region_top = ARM_AP_TZC_DRAM1_BASE + ARM_TZC_DRAM1_SIZE - 1,
-		.sec_attr = TZC_DMC620_REGION_S_RDWR
-	}
+	CSS_SGI_DMC620_TZC_REGIONS_DEF
 };
 
 static const tzc_dmc620_config_data_t rde1edge_plat_config_data = {
diff --git a/plat/arm/board/rdn1edge/include/platform_def.h b/plat/arm/board/rdn1edge/include/platform_def.h
index ab63e23..a61b0d5 100644
--- a/plat/arm/board/rdn1edge/include/platform_def.h
+++ b/plat/arm/board/rdn1edge/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,7 +9,8 @@
 
 #include <lib/utils_def.h>
 
-#include <sgi_base_platform_def.h>
+#include <sgi_sdei.h>
+#include <sgi_soc_platform_def.h>
 
 #define PLAT_ARM_CLUSTER_COUNT		U(2)
 #define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(4)
diff --git a/plat/arm/board/rdn1edge/platform.mk b/plat/arm/board/rdn1edge/platform.mk
index b313426..22ab312 100644
--- a/plat/arm/board/rdn1edge/platform.mk
+++ b/plat/arm/board/rdn1edge/platform.mk
@@ -15,6 +15,8 @@
 
 SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_n1.S
 
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c
+
 BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
 				${RDN1EDGE_BASE}/rdn1edge_err.c
 
@@ -63,4 +65,9 @@
    set to ${CSS_SGI_CHIP_COUNT}.")
 endif
 
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),0)
+ $(error "CSS_SGI_PLATFORM_VARIANT for RD-N1-Edge should always be 0, \
+     currently set to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
+
 override CTX_INCLUDE_AARCH32_REGS	:= 0
diff --git a/plat/arm/board/rdn1edge/rdn1edge_plat.c b/plat/arm/board/rdn1edge/rdn1edge_plat.c
index f62c6f4..1dbbf26 100644
--- a/plat/arm/board/rdn1edge/rdn1edge_plat.c
+++ b/plat/arm/board/rdn1edge/rdn1edge_plat.c
@@ -8,7 +8,7 @@
 #include <drivers/arm/gic600_multichip.h>
 #include <plat/arm/common/plat_arm.h>
 #include <plat/common/platform.h>
-#include <sgi_base_platform_def.h>
+#include <sgi_soc_platform_def.h>
 #include <sgi_plat.h>
 
 #if defined(IMAGE_BL31)
diff --git a/plat/arm/board/rdn1edge/rdn1edge_security.c b/plat/arm/board/rdn1edge/rdn1edge_security.c
index ffa8935..4943532 100644
--- a/plat/arm/board/rdn1edge/rdn1edge_security.c
+++ b/plat/arm/board/rdn1edge/rdn1edge_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,7 +7,7 @@
 #include <platform_def.h>
 
 #include <common/debug.h>
-#include <drivers/arm/tzc_dmc620.h>
+#include <sgi_dmc620_tzc_regions.h>
 
 uintptr_t rdn1edge_dmc_base[] = {
 	RDN1EDGE_DMC620_BASE0,
@@ -20,11 +20,7 @@
 };
 
 static const tzc_dmc620_acc_addr_data_t rdn1edge_acc_addr_data[] = {
-	{
-		.region_base = ARM_AP_TZC_DRAM1_BASE,
-		.region_top = ARM_AP_TZC_DRAM1_BASE + ARM_TZC_DRAM1_SIZE - 1,
-		.sec_attr = TZC_DMC620_REGION_S_RDWR
-	}
+	CSS_SGI_DMC620_TZC_REGIONS_DEF
 };
 
 static const tzc_dmc620_config_data_t rdn1edge_plat_config_data = {
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts b/plat/arm/board/rdn2/fdts/rdn2_fw_config.dts
similarity index 100%
rename from plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts
rename to plat/arm/board/rdn2/fdts/rdn2_fw_config.dts
diff --git a/plat/arm/board/rdn2/fdts/rdn2_nt_fw_config.dts b/plat/arm/board/rdn2/fdts/rdn2_nt_fw_config.dts
new file mode 100644
index 0000000..bbc36fc
--- /dev/null
+++ b/plat/arm/board/rdn2/fdts/rdn2_nt_fw_config.dts
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/dts-v1/;
+/ {
+	/* compatible string */
+	compatible = "arm,rd-n2";
+
+	/*
+	 * Place holder for system-id node with default values. The
+	 * value of platform-id and config-id will be set to the
+	 * correct values during the BL2 stage of boot.
+	 */
+	system-id {
+		platform-id = <0x0>;
+		config-id = <0x0>;
+		multi-chip-mode = <0x0>;
+	};
+};
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts b/plat/arm/board/rdn2/fdts/rdn2_tb_fw_config.dts
similarity index 100%
rename from plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts
rename to plat/arm/board/rdn2/fdts/rdn2_tb_fw_config.dts
diff --git a/plat/arm/board/rdn2/include/platform_def.h b/plat/arm/board/rdn2/include/platform_def.h
new file mode 100644
index 0000000..194814f
--- /dev/null
+++ b/plat/arm/board/rdn2/include/platform_def.h
@@ -0,0 +1,84 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <lib/utils_def.h>
+
+#include <sgi_soc_platform_def_v2.h>
+
+#if (CSS_SGI_PLATFORM_VARIANT == 1)
+#define PLAT_ARM_CLUSTER_COUNT		U(8)
+#else
+#define PLAT_ARM_CLUSTER_COUNT		U(16)
+#endif
+
+#define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(1)
+#define CSS_SGI_MAX_PE_PER_CPU		U(1)
+
+#define PLAT_CSS_MHU_BASE		UL(0x2A920000)
+#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
+
+#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
+#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
+
+/* TZC Related Constants */
+#define PLAT_ARM_TZC_BASE		UL(0x10720000)
+#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
+
+#define TZC400_OFFSET			UL(0x1000000)
+
+#if (CSS_SGI_PLATFORM_VARIANT == 1)
+#define TZC400_COUNT			U(2)
+#else
+#define TZC400_COUNT			U(8)
+#endif
+
+#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
+						(n * TZC400_OFFSET))
+
+#define TZC_NSAID_ALL_AP		U(0)
+#define TZC_NSAID_PCI			U(1)
+#define TZC_NSAID_HDLCD0		U(2)
+#define TZC_NSAID_DMA			U(5)
+#define TZC_NSAID_DMA2			U(8)
+#define TZC_NSAID_CLCD			U(7)
+#define TZC_NSAID_AP			U(9)
+#define TZC_NSAID_VIRTIO		U(15)
+
+#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_ALL_AP)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_HDLCD0)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_PCI))    | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_DMA))    | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_DMA2))   | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_AP))     | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_CLCD))   | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_VIRTIO))
+
+/*
+ * Physical and virtual address space limits for MMU in AARCH64 & AARCH32 modes
+ */
+#ifdef __aarch64__
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 42)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 42)
+#else
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
+#endif
+
+/* GIC related constants */
+#define PLAT_ARM_GICD_BASE		UL(0x30000000)
+#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
+
+#if (CSS_SGI_PLATFORM_VARIANT == 1)
+#define PLAT_ARM_GICR_BASE		UL(0x30100000)
+#else
+#define PLAT_ARM_GICR_BASE		UL(0x301C0000)
+#endif
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/rdn2/platform.mk b/plat/arm/board/rdn2/platform.mk
new file mode 100644
index 0000000..5b24c32
--- /dev/null
+++ b/plat/arm/board/rdn2/platform.mk
@@ -0,0 +1,67 @@
+# Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# RD-N2 platform uses GIC-700 which is based on GICv4.1
+GIC_ENABLE_V4_EXTN	:=	1
+
+include plat/arm/css/sgi/sgi-common.mk
+
+RDN2_BASE		=	plat/arm/board/rdn2
+
+PLAT_INCLUDES		+=	-I${RDN2_BASE}/include/
+
+SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_n2.S
+
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat_v2.c
+
+BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDN2_BASE}/rdn2_err.c
+
+BL2_SOURCES		+=	${RDN2_BASE}/rdn2_plat.c		\
+				${RDN2_BASE}/rdn2_security.c		\
+				${RDN2_BASE}/rdn2_err.c			\
+				lib/utils/mem_region.c			\
+				drivers/arm/tzc/tzc400.c		\
+				plat/arm/common/arm_tzc400.c		\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+BL31_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDN2_BASE}/rdn2_plat.c		\
+				${RDN2_BASE}/rdn2_topology.c		\
+				drivers/cfi/v2m/v2m_flash.c		\
+				lib/utils/mem_region.c			\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+ifeq (${TRUSTED_BOARD_BOOT}, 1)
+BL1_SOURCES		+=	${RDN2_BASE}/rdn2_trusted_boot.c
+BL2_SOURCES		+=	${RDN2_BASE}/rdn2_trusted_boot.c
+endif
+
+# Add the FDT_SOURCES and options for Dynamic Config
+FDT_SOURCES		+=	${RDN2_BASE}/fdts/${PLAT}_fw_config.dts	\
+				${RDN2_BASE}/fdts/${PLAT}_tb_fw_config.dts
+FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
+TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
+
+# Add the FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
+# Add the TB_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
+
+FDT_SOURCES		+=	${RDN2_BASE}/fdts/${PLAT}_nt_fw_config.dts
+NT_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_nt_fw_config.dtb
+
+# Add the NT_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${NT_FW_CONFIG},--nt-fw-config))
+
+override CTX_INCLUDE_AARCH32_REGS	:= 0
+override ENABLE_AMU			:= 1
+
+RD_N2_VARIANTS	:= 0 1
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),\
+	$(filter $(CSS_SGI_PLATFORM_VARIANT),$(RD_N2_VARIANTS)))
+ $(error "CSS_SGI_PLATFORM_VARIANT for RD-N2 should be 0 or 1, currently set \
+     to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
diff --git a/plat/arm/board/rdn2/rdn2_err.c b/plat/arm/board/rdn2/rdn2_err.c
new file mode 100644
index 0000000..802ac21
--- /dev/null
+++ b/plat/arm/board/rdn2/rdn2_err.c
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * rdn2 error handler
+ */
+void __dead2 plat_arm_error_handler(int err)
+{
+	while (1) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/rdn2/rdn2_plat.c b/plat/arm/board/rdn2/rdn2_plat.c
new file mode 100644
index 0000000..5bf14e3
--- /dev/null
+++ b/plat/arm/board/rdn2/rdn2_plat.c
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/common/platform.h>
+#include <sgi_plat.h>
+
+unsigned int plat_arm_sgi_get_platform_id(void)
+{
+	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_ID_OFFSET)
+			    & SID_SYSTEM_ID_PART_NUM_MASK;
+}
+
+unsigned int plat_arm_sgi_get_config_id(void)
+{
+	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_CFG_OFFSET);
+}
+
+unsigned int plat_arm_sgi_get_multi_chip_mode(void)
+{
+	return (mmio_read_32(SID_REG_BASE + SID_NODE_ID_OFFSET) &
+			     SID_MULTI_CHIP_MODE_MASK) >>
+			     SID_MULTI_CHIP_MODE_SHIFT;
+}
+
+void bl31_platform_setup(void)
+{
+	sgi_bl31_common_platform_setup();
+}
diff --git a/plat/arm/board/rdn2/rdn2_security.c b/plat/arm/board/rdn2/rdn2_security.c
new file mode 100644
index 0000000..9568b60
--- /dev/null
+++ b/plat/arm/board/rdn2/rdn2_security.c
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <platform_def.h>
+
+
+static const arm_tzc_regions_info_t tzc_regions[] = {
+	ARM_TZC_REGIONS_DEF,
+	{}
+};
+
+/* Initialize the secure environment */
+void plat_arm_security_setup(void)
+{
+
+	int i;
+
+	for (i = 0; i < TZC400_COUNT; i++)
+		arm_tzc400_setup(TZC400_BASE(i), tzc_regions);
+
+}
diff --git a/plat/arm/board/rdn2/rdn2_topology.c b/plat/arm/board/rdn2/rdn2_topology.c
new file mode 100644
index 0000000..cad6c37
--- /dev/null
+++ b/plat/arm/board/rdn2/rdn2_topology.c
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/arm/css/common/css_pm.h>
+
+/******************************************************************************
+ * The power domain tree descriptor.
+ ******************************************************************************/
+const unsigned char rd_n2_pd_tree_desc[] = {
+	PLAT_ARM_CLUSTER_COUNT,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+#if (CSS_SGI_PLATFORM_VARIANT == 0)
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+#endif
+};
+
+/*******************************************************************************
+ * This function returns the topology tree information.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	return rd_n2_pd_tree_desc;
+}
+
+/*******************************************************************************
+ * The array mapping platform core position (implemented by plat_my_core_pos())
+ * to the SCMI power domain ID implemented by SCP.
+ ******************************************************************************/
+const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x4)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x5)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x6)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x7)),
+#if (CSS_SGI_PLATFORM_VARIANT == 0)
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x8)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x9)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xA)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xB)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xC)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xD)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xE)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xF)),
+#endif
+};
diff --git a/plat/arm/board/rddaniel/rddaniel_trusted_boot.c b/plat/arm/board/rdn2/rdn2_trusted_boot.c
similarity index 100%
rename from plat/arm/board/rddaniel/rddaniel_trusted_boot.c
rename to plat/arm/board/rdn2/rdn2_trusted_boot.c
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts b/plat/arm/board/rdv1/fdts/rdv1_fw_config.dts
similarity index 100%
copy from plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts
copy to plat/arm/board/rdv1/fdts/rdv1_fw_config.dts
diff --git a/plat/arm/board/rdv1/fdts/rdv1_nt_fw_config.dts b/plat/arm/board/rdv1/fdts/rdv1_nt_fw_config.dts
new file mode 100644
index 0000000..62ba2c3
--- /dev/null
+++ b/plat/arm/board/rdv1/fdts/rdv1_nt_fw_config.dts
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/dts-v1/;
+/ {
+	/* compatible string */
+	compatible = "arm,rd-v1";
+
+	/*
+	 * Place holder for system-id node with default values. The
+	 * value of platform-id and config-id will be set to the
+	 * correct values during the BL2 stage of boot.
+	 */
+	system-id {
+		platform-id = <0x0>;
+		config-id = <0x0>;
+		multi-chip-mode = <0x0>;
+	};
+};
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts b/plat/arm/board/rdv1/fdts/rdv1_tb_fw_config.dts
similarity index 100%
copy from plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts
copy to plat/arm/board/rdv1/fdts/rdv1_tb_fw_config.dts
diff --git a/plat/arm/board/rdv1/include/platform_def.h b/plat/arm/board/rdv1/include/platform_def.h
new file mode 100644
index 0000000..5b98b4e
--- /dev/null
+++ b/plat/arm/board/rdv1/include/platform_def.h
@@ -0,0 +1,65 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <lib/utils_def.h>
+
+#include <sgi_soc_platform_def.h>
+
+#define PLAT_ARM_CLUSTER_COUNT		U(16)
+#define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(1)
+#define CSS_SGI_MAX_PE_PER_CPU		U(1)
+
+#define PLAT_CSS_MHU_BASE		UL(0x45400000)
+#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
+
+#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
+#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
+
+/* TZC Related Constants */
+#define PLAT_ARM_TZC_BASE		UL(0x21830000)
+#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
+
+#define TZC400_OFFSET			UL(0x1000000)
+#define TZC400_COUNT			4
+
+#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
+					 (n * TZC400_OFFSET))
+
+#define TZC_NSAID_ALL_AP		U(0)
+#define TZC_NSAID_PCI			U(1)
+#define TZC_NSAID_HDLCD0		U(2)
+#define TZC_NSAID_CLCD			U(7)
+#define TZC_NSAID_AP			U(9)
+#define TZC_NSAID_VIRTIO		U(15)
+
+#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_ALL_AP)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_HDLCD0)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_PCI))    | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_AP))     | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_CLCD))   | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_VIRTIO))
+
+/*
+ * Physical and virtual address space limits for MMU in AARCH64 & AARCH32 modes
+ */
+#ifdef __aarch64__
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 42)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 42)
+#else
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
+#endif
+
+/* GIC related constants */
+#define PLAT_ARM_GICD_BASE		UL(0x30000000)
+#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
+#define PLAT_ARM_GICR_BASE		UL(0x30140000)
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/rdv1/platform.mk b/plat/arm/board/rdv1/platform.mk
new file mode 100644
index 0000000..11f5212
--- /dev/null
+++ b/plat/arm/board/rdv1/platform.mk
@@ -0,0 +1,65 @@
+# Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# RD-V1 platform uses GIC-700 which is based on GICv4.1
+GIC_ENABLE_V4_EXTN	:=	1
+
+include plat/arm/css/sgi/sgi-common.mk
+
+RDV1_BASE		=	plat/arm/board/rdv1
+
+PLAT_INCLUDES		+=	-I${RDV1_BASE}/include/
+
+SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_v1.S
+
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c
+
+BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDV1_BASE}/rdv1_err.c
+
+BL2_SOURCES		+=	${RDV1_BASE}/rdv1_plat.c	\
+				${RDV1_BASE}/rdv1_security.c	\
+				${RDV1_BASE}/rdv1_err.c		\
+				lib/utils/mem_region.c			\
+				drivers/arm/tzc/tzc400.c		\
+				plat/arm/common/arm_tzc400.c		\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+BL31_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDV1_BASE}/rdv1_plat.c	\
+				${RDV1_BASE}/rdv1_topology.c	\
+				drivers/cfi/v2m/v2m_flash.c		\
+				lib/utils/mem_region.c			\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+ifeq (${TRUSTED_BOARD_BOOT}, 1)
+BL1_SOURCES		+=	${RDV1_BASE}/rdv1_trusted_boot.c
+BL2_SOURCES		+=	${RDV1_BASE}/rdv1_trusted_boot.c
+endif
+
+# Add the FDT_SOURCES and options for Dynamic Config
+FDT_SOURCES		+=	${RDV1_BASE}/fdts/${PLAT}_fw_config.dts	\
+				${RDV1_BASE}/fdts/${PLAT}_tb_fw_config.dts
+FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
+TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
+
+# Add the FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
+# Add the TB_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
+
+FDT_SOURCES		+=	${RDV1_BASE}/fdts/${PLAT}_nt_fw_config.dts
+NT_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_nt_fw_config.dtb
+
+# Add the NT_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${NT_FW_CONFIG},--nt-fw-config,${NT_FW_CONFIG}))
+
+override CTX_INCLUDE_AARCH32_REGS	:= 0
+override ENABLE_AMU			:= 1
+
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),0)
+ $(error "CSS_SGI_PLATFORM_VARIANT for RD-V1 should always be 0, \
+     currently set to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
diff --git a/plat/arm/board/rdv1/rdv1_err.c b/plat/arm/board/rdv1/rdv1_err.c
new file mode 100644
index 0000000..68f9a3e
--- /dev/null
+++ b/plat/arm/board/rdv1/rdv1_err.c
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * rdv1 error handler
+ */
+void __dead2 plat_arm_error_handler(int err)
+{
+	while (1) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/rddaniel/rddaniel_plat.c b/plat/arm/board/rdv1/rdv1_plat.c
similarity index 100%
rename from plat/arm/board/rddaniel/rddaniel_plat.c
rename to plat/arm/board/rdv1/rdv1_plat.c
diff --git a/plat/arm/board/rddaniel/rddaniel_security.c b/plat/arm/board/rdv1/rdv1_security.c
similarity index 100%
rename from plat/arm/board/rddaniel/rddaniel_security.c
rename to plat/arm/board/rdv1/rdv1_security.c
diff --git a/plat/arm/board/rdv1/rdv1_topology.c b/plat/arm/board/rdv1/rdv1_topology.c
new file mode 100644
index 0000000..ab64fd8
--- /dev/null
+++ b/plat/arm/board/rdv1/rdv1_topology.c
@@ -0,0 +1,62 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/arm/css/common/css_pm.h>
+
+/******************************************************************************
+ * The power domain tree descriptor.
+ ******************************************************************************/
+const unsigned char rd_v1_pd_tree_desc[] = {
+	PLAT_ARM_CLUSTER_COUNT,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER
+};
+
+/*******************************************************************************
+ * This function returns the topology tree information.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	return rd_v1_pd_tree_desc;
+}
+
+/*******************************************************************************
+ * The array mapping platform core position (implemented by plat_my_core_pos())
+ * to the SCMI power domain ID implemented by SCP.
+ ******************************************************************************/
+const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x4)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x5)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x6)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x7)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x8)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x9)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xA)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xB)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xC)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xD)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xE)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0xF))
+};
diff --git a/plat/arm/board/rddaniel/rddaniel_trusted_boot.c b/plat/arm/board/rdv1/rdv1_trusted_boot.c
similarity index 100%
copy from plat/arm/board/rddaniel/rddaniel_trusted_boot.c
copy to plat/arm/board/rdv1/rdv1_trusted_boot.c
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts b/plat/arm/board/rdv1mc/fdts/rdv1mc_fw_config.dts
similarity index 100%
copy from plat/arm/board/rddaniel/fdts/rddaniel_fw_config.dts
copy to plat/arm/board/rdv1mc/fdts/rdv1mc_fw_config.dts
diff --git a/plat/arm/board/rdv1mc/fdts/rdv1mc_nt_fw_config.dts b/plat/arm/board/rdv1mc/fdts/rdv1mc_nt_fw_config.dts
new file mode 100644
index 0000000..71c7db3
--- /dev/null
+++ b/plat/arm/board/rdv1mc/fdts/rdv1mc_nt_fw_config.dts
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/dts-v1/;
+/ {
+	/* compatible string */
+	compatible = "arm,rd-v1-mc";
+
+	/*
+	 * Place holder for system-id node with default values. The
+	 * value of platform-id and config-id will be set to the
+	 * correct values during the BL2 stage of boot.
+	 */
+	system-id {
+		platform-id = <0x0>;
+		config-id = <0x0>;
+		multi-chip-mode = <0x0>;
+	};
+};
diff --git a/plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts b/plat/arm/board/rdv1mc/fdts/rdv1mc_tb_fw_config.dts
similarity index 100%
copy from plat/arm/board/rddaniel/fdts/rddaniel_tb_fw_config.dts
copy to plat/arm/board/rdv1mc/fdts/rdv1mc_tb_fw_config.dts
diff --git a/plat/arm/board/rdv1mc/include/platform_def.h b/plat/arm/board/rdv1mc/include/platform_def.h
new file mode 100644
index 0000000..12ce806
--- /dev/null
+++ b/plat/arm/board/rdv1mc/include/platform_def.h
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <lib/utils_def.h>
+#include <sgi_soc_platform_def.h>
+
+#define PLAT_ARM_CLUSTER_COUNT		U(4)
+#define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(1)
+#define CSS_SGI_MAX_PE_PER_CPU		U(1)
+
+#define PLAT_CSS_MHU_BASE		UL(0x45400000)
+#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
+
+#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
+#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
+
+/* TZC Related Constants */
+#define PLAT_ARM_TZC_BASE		UL(0x21830000)
+#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
+					 (n * TZC400_OFFSET))
+#define TZC400_OFFSET			UL(0x1000000)
+#define TZC400_COUNT			U(8)
+#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
+
+#define TZC_NSAID_ALL_AP		U(0)
+#define TZC_NSAID_PCI			U(1)
+#define TZC_NSAID_HDLCD0		U(2)
+#define TZC_NSAID_CLCD			U(7)
+#define TZC_NSAID_AP			U(9)
+#define TZC_NSAID_VIRTIO		U(15)
+
+#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_ALL_AP)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_HDLCD0)) | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_PCI))    | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_AP))     | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_CLCD))   | \
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_VIRTIO))
+
+/* Virtual address used by dynamic mem_protect for chunk_base */
+#define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xC0000000)
+
+/* Physical and virtual address space limits for MMU in AARCH64 mode */
+#define PLAT_PHY_ADDR_SPACE_SIZE	CSS_SGI_REMOTE_CHIP_MEM_OFFSET( \
+						CSS_SGI_CHIP_COUNT)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	CSS_SGI_REMOTE_CHIP_MEM_OFFSET( \
+						CSS_SGI_CHIP_COUNT)
+
+/* GIC related constants */
+#define PLAT_ARM_GICD_BASE		UL(0x30000000)
+#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
+#define PLAT_ARM_GICR_BASE		UL(0x30140000)
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/rdv1mc/platform.mk b/plat/arm/board/rdv1mc/platform.mk
new file mode 100644
index 0000000..df0b09a
--- /dev/null
+++ b/plat/arm/board/rdv1mc/platform.mk
@@ -0,0 +1,76 @@
+# Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Enable GICv4 extension with multichip driver
+GIC_ENABLE_V4_EXTN		:=	1
+GICV3_IMPL_GIC600_MULTICHIP	:=	1
+
+include plat/arm/css/sgi/sgi-common.mk
+
+RDV1MC_BASE	=	plat/arm/board/rdv1mc
+
+PLAT_INCLUDES		+=	-I${RDV1MC_BASE}/include/
+
+SGI_CPU_SOURCES		:=	lib/cpus/aarch64/neoverse_v1.S
+
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c
+
+BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDV1MC_BASE}/rdv1mc_err.c
+
+BL2_SOURCES		+=	${RDV1MC_BASE}/rdv1mc_plat.c	\
+				${RDV1MC_BASE}/rdv1mc_security.c	\
+				${RDV1MC_BASE}/rdv1mc_err.c	\
+				drivers/arm/tzc/tzc400.c	\
+				plat/arm/common/arm_tzc400.c	\
+				lib/utils/mem_region.c			\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+BL31_SOURCES		+=	${SGI_CPU_SOURCES}			\
+				${RDV1MC_BASE}/rdv1mc_plat.c	\
+				${RDV1MC_BASE}/rdv1mc_topology.c	\
+				drivers/cfi/v2m/v2m_flash.c		\
+				drivers/arm/gic/v3/gic600_multichip.c	\
+				lib/utils/mem_region.c			\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+ifeq (${TRUSTED_BOARD_BOOT}, 1)
+BL1_SOURCES		+=	${RDV1MC_BASE}/rdv1mc_trusted_boot.c
+BL2_SOURCES		+=	${RDV1MC_BASE}/rdv1mc_trusted_boot.c
+endif
+
+# Enable dynamic addition of MMAP regions in BL31
+BL31_CFLAGS		+=	-DPLAT_XLAT_TABLES_DYNAMIC
+
+# Add the FDT_SOURCES and options for Dynamic Config
+FDT_SOURCES		+=	${RDV1MC_BASE}/fdts/${PLAT}_fw_config.dts	\
+				${RDV1MC_BASE}/fdts/${PLAT}_tb_fw_config.dts
+FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
+TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
+
+# Add the FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
+# Add the TB_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
+
+$(eval $(call CREATE_SEQ,SEQ,4))
+ifneq ($(CSS_SGI_CHIP_COUNT),$(filter $(CSS_SGI_CHIP_COUNT),$(SEQ)))
+ $(error  "Chip count for RD-V1-MC should be either $(SEQ) \
+ currently it is set to ${CSS_SGI_CHIP_COUNT}.")
+endif
+
+FDT_SOURCES		+=	${RDV1MC_BASE}/fdts/${PLAT}_nt_fw_config.dts
+NT_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_nt_fw_config.dtb
+
+# Add the NT_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${NT_FW_CONFIG},--nt-fw-config,${NT_FW_CONFIG}))
+
+override CTX_INCLUDE_AARCH32_REGS	:= 0
+override ENABLE_AMU			:= 1
+
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),0)
+ $(error "CSS_SGI_PLATFORM_VARIANT for RD-V1-MC should always be 0, \
+     currently set to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
diff --git a/plat/arm/board/rdv1mc/rdv1mc_err.c b/plat/arm/board/rdv1mc/rdv1mc_err.c
new file mode 100644
index 0000000..755a503
--- /dev/null
+++ b/plat/arm/board/rdv1mc/rdv1mc_err.c
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * rdv1mc error handler
+ */
+void __dead2 plat_arm_error_handler(int err)
+{
+	while (true) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/rdv1mc/rdv1mc_plat.c b/plat/arm/board/rdv1mc/rdv1mc_plat.c
new file mode 100644
index 0000000..d859400
--- /dev/null
+++ b/plat/arm/board/rdv1mc/rdv1mc_plat.c
@@ -0,0 +1,131 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/arm/gic600_multichip.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <sgi_soc_platform_def.h>
+#include <sgi_plat.h>
+
+#if defined(IMAGE_BL31)
+static const mmap_region_t rdv1mc_dynamic_mmap[] = {
+	ARM_MAP_SHARED_RAM_REMOTE_CHIP(1),
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(1),
+	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(1),
+#if (CSS_SGI_CHIP_COUNT > 2)
+	ARM_MAP_SHARED_RAM_REMOTE_CHIP(2),
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(2),
+	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(2),
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+	ARM_MAP_SHARED_RAM_REMOTE_CHIP(3),
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(3),
+	SOC_CSS_MAP_DEVICE_REMOTE_CHIP(3)
+#endif
+};
+
+static struct gic600_multichip_data rdv1mc_multichip_data __init = {
+	.rt_owner_base = PLAT_ARM_GICD_BASE,
+	.rt_owner = 0,
+	.chip_count = CSS_SGI_CHIP_COUNT,
+	.chip_addrs = {
+		PLAT_ARM_GICD_BASE >> 16,
+		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(1)) >> 16,
+#if (CSS_SGI_CHIP_COUNT > 2)
+		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(2)) >> 16,
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+		(PLAT_ARM_GICD_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(3)) >> 16,
+#endif
+	},
+	.spi_ids = {
+		{32, 255},
+		{0, 0},
+#if (CSS_SGI_CHIP_COUNT > 2)
+		{0, 0},
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+		{0, 0},
+#endif
+	}
+};
+
+static uintptr_t rdv1mc_multichip_gicr_frames[] = {
+	/* Chip 0's GICR Base */
+	PLAT_ARM_GICR_BASE,
+	/* Chip 1's GICR BASE */
+	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(1),
+#if (CSS_SGI_CHIP_COUNT > 2)
+	/* Chip 2's GICR BASE */
+	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(2),
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+	/* Chip 3's GICR BASE */
+	PLAT_ARM_GICR_BASE + CSS_SGI_REMOTE_CHIP_MEM_OFFSET(3),
+#endif
+	UL(0)	/* Zero Termination */
+};
+#endif /* IMAGE_BL31 */
+
+unsigned int plat_arm_sgi_get_platform_id(void)
+{
+	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_ID_OFFSET)
+				& SID_SYSTEM_ID_PART_NUM_MASK;
+}
+
+unsigned int plat_arm_sgi_get_config_id(void)
+{
+	return mmio_read_32(SID_REG_BASE + SID_SYSTEM_CFG_OFFSET);
+}
+
+unsigned int plat_arm_sgi_get_multi_chip_mode(void)
+{
+	return (mmio_read_32(SID_REG_BASE + SID_NODE_ID_OFFSET) &
+			SID_MULTI_CHIP_MODE_MASK) >> SID_MULTI_CHIP_MODE_SHIFT;
+}
+
+/*
+ * bl31_platform_setup_function is guarded by IMAGE_BL31 macro because
+ * PLAT_XLAT_TABLES_DYNAMIC macro is set to build only for BL31 and not
+ * for other stages.
+ */
+#if defined(IMAGE_BL31)
+void bl31_platform_setup(void)
+{
+	int ret;
+	unsigned int i;
+
+	if ((plat_arm_sgi_get_multi_chip_mode() == 0) &&
+			(CSS_SGI_CHIP_COUNT > 1)) {
+		ERROR("Chip Count is set to %u but multi-chip mode is not "
+			"enabled\n", CSS_SGI_CHIP_COUNT);
+		panic();
+	} else if ((plat_arm_sgi_get_multi_chip_mode() == 1) &&
+			(CSS_SGI_CHIP_COUNT > 1)) {
+		INFO("Enabling support for multi-chip in RD-V1-MC\n");
+
+		for (i = 0; i < ARRAY_SIZE(rdv1mc_dynamic_mmap); i++) {
+			ret = mmap_add_dynamic_region(
+					rdv1mc_dynamic_mmap[i].base_pa,
+					rdv1mc_dynamic_mmap[i].base_va,
+					rdv1mc_dynamic_mmap[i].size,
+					rdv1mc_dynamic_mmap[i].attr);
+			if (ret != 0) {
+				ERROR("Failed to add dynamic mmap entry "
+						"(ret=%d)\n", ret);
+				panic();
+			}
+		}
+
+		plat_arm_override_gicr_frames(
+			rdv1mc_multichip_gicr_frames);
+		gic600_multichip_init(&rdv1mc_multichip_data);
+	}
+
+	sgi_bl31_common_platform_setup();
+}
+#endif /* IMAGE_BL31 */
diff --git a/plat/arm/board/rdv1mc/rdv1mc_security.c b/plat/arm/board/rdv1mc/rdv1mc_security.c
new file mode 100644
index 0000000..adc0bf8
--- /dev/null
+++ b/plat/arm/board/rdv1mc/rdv1mc_security.c
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <plat/arm/common/plat_arm.h>
+#include <platform_def.h>
+
+/* TZC memory regions for the first chip */
+static const arm_tzc_regions_info_t tzc_regions[] = {
+	ARM_TZC_REGIONS_DEF,
+	{}
+};
+
+#if CSS_SGI_CHIP_COUNT > 1
+static const arm_tzc_regions_info_t tzc_regions_mc[][CSS_SGI_CHIP_COUNT - 1] = {
+	{
+		/* TZC memory regions for second chip */
+		SGI_PLAT_TZC_NS_REMOTE_REGIONS_DEF(1),
+		{}
+	},
+#if CSS_SGI_CHIP_COUNT > 2
+	{
+		/* TZC memory regions for third chip */
+		SGI_PLAT_TZC_NS_REMOTE_REGIONS_DEF(2),
+		{}
+	},
+#endif
+#if CSS_SGI_CHIP_COUNT > 3
+	{
+		/* TZC memory regions for fourth chip */
+		SGI_PLAT_TZC_NS_REMOTE_REGIONS_DEF(3),
+		{}
+	},
+#endif
+};
+#endif /* CSS_SGI_CHIP_COUNT */
+
+/* Initialize the secure environment */
+void plat_arm_security_setup(void)
+{
+	unsigned int i;
+
+	INFO("Configuring TrustZone Controller for Chip 0\n");
+
+	for (i = 0; i < TZC400_COUNT; i++) {
+		arm_tzc400_setup(TZC400_BASE(i), tzc_regions);
+	}
+
+#if CSS_SGI_CHIP_COUNT > 1
+	unsigned int j;
+
+	for (i = 1; i < CSS_SGI_CHIP_COUNT; i++) {
+		INFO("Configuring TrustZone Controller for Chip %u\n", i);
+
+		for (j = 0; j < TZC400_COUNT; j++) {
+			arm_tzc400_setup(CSS_SGI_REMOTE_CHIP_MEM_OFFSET(i)
+				+ TZC400_BASE(j), tzc_regions_mc[i-1]);
+		}
+	}
+#endif
+}
diff --git a/plat/arm/board/rdv1mc/rdv1mc_topology.c b/plat/arm/board/rdv1mc/rdv1mc_topology.c
new file mode 100644
index 0000000..4486e5c
--- /dev/null
+++ b/plat/arm/board/rdv1mc/rdv1mc_topology.c
@@ -0,0 +1,78 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/arm/css/common/css_pm.h>
+#include <sgi_variant.h>
+
+/******************************************************************************
+ * The power domain tree descriptor.
+ ******************************************************************************/
+const unsigned char rd_v1_mc_pd_tree_desc_multi_chip[] = {
+	((PLAT_ARM_CLUSTER_COUNT) * (CSS_SGI_CHIP_COUNT)),
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+#if (CSS_SGI_CHIP_COUNT > 1)
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+#endif
+#if (CSS_SGI_CHIP_COUNT > 2)
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER,
+	CSS_SGI_MAX_CPUS_PER_CLUSTER
+#endif
+};
+
+/*******************************************************************************
+ * This function returns the topology tree information.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	if (plat_arm_sgi_get_multi_chip_mode() == 1)
+		return rd_v1_mc_pd_tree_desc_multi_chip;
+	panic();
+}
+
+/*******************************************************************************
+ * The array mapping platform core position (implemented by plat_my_core_pos())
+ * to the SCMI power domain ID implemented by SCP.
+ ******************************************************************************/
+const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
+#if (CSS_SGI_CHIP_COUNT > 1)
+	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x1) | SET_SCMI_DOMAIN_ID(0x3)),
+#endif
+#if (CSS_SGI_CHIP_COUNT > 2)
+	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x2) | SET_SCMI_DOMAIN_ID(0x3)),
+#endif
+#if (CSS_SGI_CHIP_COUNT > 3)
+	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x3) | SET_SCMI_DOMAIN_ID(0x3))
+#endif
+};
diff --git a/plat/arm/board/rddaniel/rddaniel_trusted_boot.c b/plat/arm/board/rdv1mc/rdv1mc_trusted_boot.c
similarity index 100%
copy from plat/arm/board/rddaniel/rddaniel_trusted_boot.c
copy to plat/arm/board/rdv1mc/rdv1mc_trusted_boot.c
diff --git a/plat/arm/board/sgi575/include/platform_def.h b/plat/arm/board/sgi575/include/platform_def.h
index 95986cf..72d5f7c 100644
--- a/plat/arm/board/sgi575/include/platform_def.h
+++ b/plat/arm/board/sgi575/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,7 +9,8 @@
 
 #include <lib/utils_def.h>
 
-#include <sgi_base_platform_def.h>
+#include <sgi_sdei.h>
+#include <sgi_soc_platform_def.h>
 
 #define PLAT_ARM_CLUSTER_COUNT		U(2)
 #define CSS_SGI_MAX_CPUS_PER_CLUSTER	U(4)
diff --git a/plat/arm/board/sgi575/platform.mk b/plat/arm/board/sgi575/platform.mk
index 56f5733..0761b77 100644
--- a/plat/arm/board/sgi575/platform.mk
+++ b/plat/arm/board/sgi575/platform.mk
@@ -12,6 +12,8 @@
 
 SGI_CPU_SOURCES		:=	lib/cpus/aarch64/cortex_a75.S
 
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c
+
 BL1_SOURCES		+=	${SGI_CPU_SOURCES}			\
 				${SGI575_BASE}/sgi575_err.c
 
@@ -56,3 +58,8 @@
  $(error  "Chip count for SGI575 should be 1, currently set to \
    ${CSS_SGI_CHIP_COUNT}.")
 endif
+
+ifneq ($(CSS_SGI_PLATFORM_VARIANT),0)
+ $(error "CSS_SGI_PLATFORM_VARIANT for SGI575 should always be 0,\
+     currently set to ${CSS_SGI_PLATFORM_VARIANT}.")
+endif
diff --git a/plat/arm/board/sgi575/sgi575_security.c b/plat/arm/board/sgi575/sgi575_security.c
index 440f18d..17d07d1 100644
--- a/plat/arm/board/sgi575/sgi575_security.c
+++ b/plat/arm/board/sgi575/sgi575_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,8 +7,7 @@
 #include <platform_def.h>
 
 #include <common/debug.h>
-#include <drivers/arm/tzc_dmc620.h>
-#include <plat/arm/common/plat_arm.h>
+#include <sgi_dmc620_tzc_regions.h>
 
 uintptr_t sgi575_dmc_base[] = {
 	SGI575_DMC620_BASE0,
@@ -21,11 +20,7 @@
 };
 
 static const tzc_dmc620_acc_addr_data_t sgi575_acc_addr_data[] = {
-	{
-		.region_base = ARM_AP_TZC_DRAM1_BASE,
-		.region_top = ARM_AP_TZC_DRAM1_BASE + ARM_TZC_DRAM1_SIZE - 1,
-		.sec_attr = TZC_DMC620_REGION_S_RDWR
-	}
+	CSS_SGI_DMC620_TZC_REGIONS_DEF
 };
 
 static const tzc_dmc620_config_data_t sgi575_plat_config_data = {
diff --git a/plat/arm/board/sgm775/platform.mk b/plat/arm/board/sgm775/platform.mk
index a649939..f8df1a7 100644
--- a/plat/arm/board/sgm775/platform.mk
+++ b/plat/arm/board/sgm775/platform.mk
@@ -4,6 +4,8 @@
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+$(warning Platform ${PLAT} is deprecated. Some of the features might not work as expected)
+
 include plat/arm/css/sgm/sgm-common.mk
 
 SGM775_BASE= plat/arm/board/sgm775
diff --git a/plat/arm/board/tc/fdts/tc_fw_config.dts b/plat/arm/board/tc/fdts/tc_fw_config.dts
new file mode 100644
index 0000000..a84c7f8
--- /dev/null
+++ b/plat/arm/board/tc/fdts/tc_fw_config.dts
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/tbbr/tbbr_img_def.h>
+
+/dts-v1/;
+
+/ {
+	dtb-registry {
+		compatible = "fconf,dyn_cfg-dtb_registry";
+
+		tb_fw-config {
+			load-address = <0x0 0x4001300>;
+			max-size = <0x400>;
+			id = <TB_FW_CONFIG_ID>;
+		};
+
+		tos_fw-config {
+			load-address = <0x0 0x04001700>;
+			max-size = <0x1000>;
+			id = <TOS_FW_CONFIG_ID>;
+		};
+
+		hw-config {
+			load-address = <0x0 0x83000000>;
+			max-size = <0x8000>;
+			id = <HW_CONFIG_ID>;
+		};
+	};
+};
diff --git a/plat/arm/board/tc/fdts/tc_spmc_manifest.dts b/plat/arm/board/tc/fdts/tc_spmc_manifest.dts
new file mode 100644
index 0000000..d3a5e1a
--- /dev/null
+++ b/plat/arm/board/tc/fdts/tc_spmc_manifest.dts
@@ -0,0 +1,125 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/dts-v1/;
+
+/ {
+	compatible = "arm,ffa-core-manifest-1.0";
+	#address-cells = <2>;
+	#size-cells = <1>;
+
+	attribute {
+		spmc_id = <0x8000>;
+		maj_ver = <0x1>;
+		min_ver = <0x1>;
+		exec_state = <0x0>;
+		load_address = <0x0 0xfd000000>;
+		entrypoint = <0x0 0xfd000000>;
+		binary_size = <0x80000>;
+	};
+
+	hypervisor {
+		compatible = "hafnium,hafnium";
+		vm1 {
+			is_ffa_partition;
+			debug_name = "cactus-primary";
+			load_address = <0xfe000000>;
+			vcpu_count = <8>;
+			mem_size = <1048576>;
+		};
+		vm2 {
+			is_ffa_partition;
+			debug_name = "cactus-secondary";
+			load_address = <0xfe100000>;
+			vcpu_count = <8>;
+			mem_size = <1048576>;
+		};
+		vm3 {
+			is_ffa_partition;
+			debug_name = "cactus-tertiary";
+			load_address = <0xfe200000>;
+			vcpu_count = <1>;
+			mem_size = <1048576>;
+		};
+		vm4 {
+			is_ffa_partition;
+			debug_name = "ivy";
+			load_address = <0xfe600000>;
+			vcpu_count = <1>;
+			mem_size = <1048576>;
+		};
+	};
+
+	cpus {
+		#address-cells = <0x2>;
+		#size-cells = <0x0>;
+
+		CPU0:cpu@0 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x0>;
+			enable-method = "psci";
+		};
+
+		/*
+		 * SPMC (Hafnium) requires secondary cpu nodes are declared in
+		 * descending order
+		 */
+		CPU7:cpu@700 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x700>;
+			enable-method = "psci";
+		};
+
+		CPU6:cpu@600 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x600>;
+			enable-method = "psci";
+		};
+
+		CPU5:cpu@500 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x500>;
+			enable-method = "psci";
+		};
+
+		CPU4:cpu@400 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x400>;
+			enable-method = "psci";
+		};
+
+		CPU3:cpu@300 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x300>;
+			enable-method = "psci";
+		};
+
+		CPU2:cpu@200 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x200>;
+			enable-method = "psci";
+		};
+
+		CPU1:cpu@100 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x100>;
+			enable-method = "psci";
+		};
+	};
+
+	/* 32MB of TC_TZC_DRAM1_BASE */
+	memory@fd000000 {
+		device_type = "memory";
+		reg = <0x0 0xfd000000 0x2000000>;
+	};
+};
diff --git a/plat/arm/board/tc/fdts/tc_spmc_optee_sp_manifest.dts b/plat/arm/board/tc/fdts/tc_spmc_optee_sp_manifest.dts
new file mode 100644
index 0000000..92e2ddd
--- /dev/null
+++ b/plat/arm/board/tc/fdts/tc_spmc_optee_sp_manifest.dts
@@ -0,0 +1,124 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+/dts-v1/;
+
+/ {
+	compatible = "arm,ffa-core-manifest-1.0";
+	#address-cells = <2>;
+	#size-cells = <1>;
+
+	attribute {
+		spmc_id = <0x8000>;
+		maj_ver = <0x1>;
+		min_ver = <0x1>;
+		exec_state = <0x0>;
+		load_address = <0x0 0xfd000000>;
+		entrypoint = <0x0 0xfd000000>;
+		binary_size = <0x80000>;
+	};
+
+	hypervisor {
+		compatible = "hafnium,hafnium";
+		vm1 {
+			is_ffa_partition;
+			debug_name = "op-tee";
+			load_address = <0xfd280000>;
+			vcpu_count = <8>;
+#ifdef TS_SP_FW_CONFIG
+			mem_size = <26738688>; /* 25MB TZC DRAM */
+#else
+			mem_size = <30928896>; /* 29MB TZC DRAM */
+#endif
+		};
+#ifdef TS_SP_FW_CONFIG
+		vm2 {
+			is_ffa_partition;
+			debug_name = "internal-trusted-storage";
+			load_address = <0xfee00000>;
+			vcpu_count = <1>;
+			mem_size = <2097152>; /* 2MB TZC DRAM */
+		};
+		vm3 {
+			is_ffa_partition;
+			debug_name = "crypto";
+			load_address = <0xfec00000>;
+			vcpu_count = <1>;
+			mem_size = <2097152>; /* 2MB TZC DRAM */
+		};
+#endif
+	};
+
+	cpus {
+		#address-cells = <0x2>;
+		#size-cells = <0x0>;
+
+		CPU0:cpu@0 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x0>;
+			enable-method = "psci";
+		};
+
+		/*
+		 * SPMC (Hafnium) requires secondary cpu nodes are declared in
+		 * descending order
+		 */
+		CPU7:cpu@700 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x700>;
+			enable-method = "psci";
+		};
+
+		CPU6:cpu@600 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x600>;
+			enable-method = "psci";
+		};
+
+		CPU5:cpu@500 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x500>;
+			enable-method = "psci";
+		};
+
+		CPU4:cpu@400 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x400>;
+			enable-method = "psci";
+		};
+
+		CPU3:cpu@300 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x300>;
+			enable-method = "psci";
+		};
+
+		CPU2:cpu@200 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x200>;
+			enable-method = "psci";
+		};
+
+		CPU1:cpu@100 {
+			device_type = "cpu";
+			compatible = "arm,armv8";
+			reg = <0x0 0x100>;
+			enable-method = "psci";
+		};
+	};
+
+	/* 32MB of TC_TZC_DRAM1_BASE */
+	memory@fd000000 {
+		device_type = "memory";
+		reg = <0x0 0xfd000000 0x2000000>;
+	};
+};
diff --git a/plat/arm/board/tc/fdts/tc_tb_fw_config.dts b/plat/arm/board/tc/fdts/tc_tb_fw_config.dts
new file mode 100644
index 0000000..4c6ccef
--- /dev/null
+++ b/plat/arm/board/tc/fdts/tc_tb_fw_config.dts
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/libc/cdefs.h>
+
+/dts-v1/;
+
+/ {
+	tb_fw-config {
+		compatible = "arm,tb_fw";
+
+		/* Disable authentication for development */
+		disable_auth = <0x0>;
+		/*
+		 * The following two entries are placeholders for Mbed TLS
+		 * heap information. The default values don't matter since
+		 * they will be overwritten by BL1.
+		 * In case of having shared Mbed TLS heap between BL1 and BL2,
+		 * BL1 will populate these two properties with the respective
+		 * info about the shared heap. This info will be available for
+		 * BL2 in order to locate and re-use the heap.
+		 */
+		mbedtls_heap_addr = <0x0 0x0>;
+		mbedtls_heap_size = <0x0>;
+	};
+
+	secure-partitions {
+		compatible = "arm,sp";
+#ifdef ARM_BL2_SP_LIST_DTS
+	#include __XSTRING(ARM_BL2_SP_LIST_DTS)
+#else
+#ifdef TS_SP_FW_CONFIG
+		internal-trusted-storage {
+		       uuid = "dc1eef48-b17a-4ccf-ac8b-dfcff7711b14";
+		       load-address = <0xfee00000>;
+		};
+		crypto {
+		       uuid = "d9df52d5-16a2-4bb2-9aa4-d26d3b84e8c0";
+		       load-address = <0xfec00000>;
+		};
+#endif
+#if OPTEE_SP_FW_CONFIG
+		op-tee {
+		       uuid = "486178e0-e7f8-11e3-bc5e-0002a5d5c51b";
+		       load-address = <0xfd280000>;
+		};
+#else
+		cactus-primary {
+			uuid = "b4b5671e-4a90-4fe1-b81f-fb13dae1dacb";
+			load-address = <0xfe000000>;
+			owner = "SiP";
+		};
+
+		cactus-secondary {
+			uuid = "d1582309-f023-47b9-827c-4464f5578fc8";
+			load-address = <0xfe100000>;
+			owner = "Plat";
+		};
+
+		cactus-tertiary {
+			uuid = "79b55c73-1d8c-44b9-8593-61e1770ad8d2";
+			load-address = <0xfe200000>;
+		};
+
+		ivy {
+			uuid = "eaba83d8-baaf-4eaf-8144-f7fdcbe544a7";
+			load-address = <0xfe600000>;
+			owner = "Plat";
+		};
+#endif
+#endif /* ARM_BL2_SP_LIST_DTS */
+	};
+};
diff --git a/plat/arm/board/tc0/include/plat_macros.S b/plat/arm/board/tc/include/plat_macros.S
similarity index 100%
rename from plat/arm/board/tc0/include/plat_macros.S
rename to plat/arm/board/tc/include/plat_macros.S
diff --git a/plat/arm/board/tc/include/platform_def.h b/plat/arm/board/tc/include/platform_def.h
new file mode 100644
index 0000000..745d91c
--- /dev/null
+++ b/plat/arm/board/tc/include/platform_def.h
@@ -0,0 +1,277 @@
+/*
+ * Copyright (c) 2020-2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <lib/utils_def.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <plat/arm/board/common/board_css_def.h>
+#include <plat/arm/board/common/v2m_def.h>
+#include <plat/arm/common/arm_def.h>
+#include <plat/arm/common/arm_spm_def.h>
+#include <plat/arm/css/common/css_def.h>
+#include <plat/arm/soc/common/soc_css_def.h>
+#include <plat/common/common_def.h>
+
+#define PLATFORM_CORE_COUNT		8
+
+#define PLAT_ARM_TRUSTED_SRAM_SIZE	0x00080000	/* 512 KB */
+
+/*
+ * The top 16MB of ARM_DRAM1 is configured as secure access only using the TZC,
+ * its base is ARM_AP_TZC_DRAM1_BASE.
+ *
+ * Reserve 32MB below ARM_AP_TZC_DRAM1_BASE for:
+ *   - BL32_BASE when SPD_spmd is enabled
+ *   - Region to load Trusted OS
+ */
+#define TC_TZC_DRAM1_BASE		(ARM_AP_TZC_DRAM1_BASE -	\
+					 TC_TZC_DRAM1_SIZE)
+#define TC_TZC_DRAM1_SIZE		UL(0x02000000)	/* 32 MB */
+#define TC_TZC_DRAM1_END		(TC_TZC_DRAM1_BASE +		\
+					 TC_TZC_DRAM1_SIZE - 1)
+
+#define TC_NS_DRAM1_BASE		ARM_DRAM1_BASE
+#define TC_NS_DRAM1_SIZE		(ARM_DRAM1_SIZE -		\
+					 ARM_TZC_DRAM1_SIZE -		\
+					 TC_TZC_DRAM1_SIZE)
+#define TC_NS_DRAM1_END		(TC_NS_DRAM1_BASE +		\
+					 TC_NS_DRAM1_SIZE - 1)
+
+/*
+ * Mappings for TC DRAM1 (non-secure) and TC TZC DRAM1 (secure)
+ */
+#define TC_MAP_NS_DRAM1		MAP_REGION_FLAT(		\
+						TC_NS_DRAM1_BASE,	\
+						TC_NS_DRAM1_SIZE,	\
+						MT_MEMORY | MT_RW | MT_NS)
+
+
+#define TC_MAP_TZC_DRAM1		MAP_REGION_FLAT(		\
+						TC_TZC_DRAM1_BASE,	\
+						TC_TZC_DRAM1_SIZE,	\
+						MT_MEMORY | MT_RW | MT_SECURE)
+
+#define PLAT_HW_CONFIG_DTB_BASE	ULL(0x83000000)
+#define PLAT_HW_CONFIG_DTB_SIZE	ULL(0x8000)
+
+#define PLAT_DTB_DRAM_NS MAP_REGION_FLAT(	\
+					PLAT_HW_CONFIG_DTB_BASE,	\
+					PLAT_HW_CONFIG_DTB_SIZE,	\
+					MT_MEMORY | MT_RO | MT_NS)
+/*
+ * Max size of SPMC is 2MB for tc. With SPMD enabled this value corresponds to
+ * max size of BL32 image.
+ */
+#if defined(SPD_spmd)
+#define PLAT_ARM_SPMC_BASE		TC_TZC_DRAM1_BASE
+#define PLAT_ARM_SPMC_SIZE		UL(0x200000)  /* 2 MB */
+#endif
+
+/*
+ * PLAT_ARM_MMAP_ENTRIES depends on the number of entries in the
+ * plat_arm_mmap array defined for each BL stage.
+ */
+#if defined(IMAGE_BL31)
+# if SPM_MM
+#  define PLAT_ARM_MMAP_ENTRIES		9
+#  define MAX_XLAT_TABLES		7
+#  define PLAT_SP_IMAGE_MMAP_REGIONS	7
+#  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	10
+# else
+#  define PLAT_ARM_MMAP_ENTRIES		8
+#  define MAX_XLAT_TABLES		8
+# endif
+#elif defined(IMAGE_BL32)
+# define PLAT_ARM_MMAP_ENTRIES		8
+# define MAX_XLAT_TABLES		5
+#elif !USE_ROMLIB
+# define PLAT_ARM_MMAP_ENTRIES		11
+# define MAX_XLAT_TABLES		7
+#else
+# define PLAT_ARM_MMAP_ENTRIES		12
+# define MAX_XLAT_TABLES		6
+#endif
+
+/*
+ * PLAT_ARM_MAX_BL1_RW_SIZE is calculated using the current BL1 RW debug size
+ * plus a little space for growth.
+ */
+#define PLAT_ARM_MAX_BL1_RW_SIZE	0xC000
+
+/*
+ * PLAT_ARM_MAX_ROMLIB_RW_SIZE is define to use a full page
+ */
+
+#if USE_ROMLIB
+#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	0x1000
+#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	0xe000
+#else
+#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	0
+#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	0
+#endif
+
+/*
+ * PLAT_ARM_MAX_BL2_SIZE is calculated using the current BL2 debug size plus a
+ * little space for growth.
+ */
+#if TRUSTED_BOARD_BOOT
+# define PLAT_ARM_MAX_BL2_SIZE		0x20000
+#else
+# define PLAT_ARM_MAX_BL2_SIZE		0x14000
+#endif
+
+/*
+ * Since BL31 NOBITS overlays BL2 and BL1-RW, PLAT_ARM_MAX_BL31_SIZE is
+ * calculated using the current BL31 PROGBITS debug size plus the sizes of
+ * BL2 and BL1-RW
+ */
+#define PLAT_ARM_MAX_BL31_SIZE		0x3F000
+
+/*
+ * Size of cacheable stacks
+ */
+#if defined(IMAGE_BL1)
+# if TRUSTED_BOARD_BOOT
+#  define PLATFORM_STACK_SIZE		0x1000
+# else
+#  define PLATFORM_STACK_SIZE		0x440
+# endif
+#elif defined(IMAGE_BL2)
+# if TRUSTED_BOARD_BOOT
+#  define PLATFORM_STACK_SIZE		0x1000
+# else
+#  define PLATFORM_STACK_SIZE		0x400
+# endif
+#elif defined(IMAGE_BL2U)
+# define PLATFORM_STACK_SIZE		0x400
+#elif defined(IMAGE_BL31)
+# if SPM_MM
+#  define PLATFORM_STACK_SIZE		0x500
+# else
+#  define PLATFORM_STACK_SIZE		0x400
+# endif
+#elif defined(IMAGE_BL32)
+# define PLATFORM_STACK_SIZE		0x440
+#endif
+
+
+#define TC_DEVICE_BASE			0x21000000
+#define TC_DEVICE_SIZE			0x5f000000
+
+// TC_MAP_DEVICE covers different peripherals
+// available to the platform
+#define TC_MAP_DEVICE	MAP_REGION_FLAT(		\
+					TC_DEVICE_BASE,	\
+					TC_DEVICE_SIZE,	\
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+
+#define TC_FLASH0_RO	MAP_REGION_FLAT(V2M_FLASH0_BASE,\
+						V2M_FLASH0_SIZE,	\
+						MT_DEVICE | MT_RO | MT_SECURE)
+
+#define PLAT_ARM_NSTIMER_FRAME_ID	0
+
+#define PLAT_ARM_TRUSTED_ROM_BASE	0x0
+#define PLAT_ARM_TRUSTED_ROM_SIZE	0x00080000	/* 512KB */
+
+#define PLAT_ARM_NSRAM_BASE		0x06000000
+#define PLAT_ARM_NSRAM_SIZE		0x00080000	/* 512KB */
+
+#define PLAT_ARM_DRAM2_BASE		ULL(0x8080000000)
+#define PLAT_ARM_DRAM2_SIZE		ULL(0x180000000)
+#define PLAT_ARM_DRAM2_END		(PLAT_ARM_DRAM2_BASE + PLAT_ARM_DRAM2_SIZE - 1ULL)
+
+#define PLAT_ARM_G1S_IRQ_PROPS(grp)	CSS_G1S_IRQ_PROPS(grp)
+#define PLAT_ARM_G0_IRQ_PROPS(grp)	ARM_G0_IRQ_PROPS(grp)
+
+#define PLAT_ARM_SP_IMAGE_STACK_BASE	(PLAT_SP_IMAGE_NS_BUF_BASE +	\
+					 PLAT_SP_IMAGE_NS_BUF_SIZE)
+
+/*******************************************************************************
+ * Memprotect definitions
+ ******************************************************************************/
+/* PSCI memory protect definitions:
+ * This variable is stored in a non-secure flash because some ARM reference
+ * platforms do not have secure NVRAM. Real systems that provided MEM_PROTECT
+ * support must use a secure NVRAM to store the PSCI MEM_PROTECT definitions.
+ */
+#define PLAT_ARM_MEM_PROT_ADDR		(V2M_FLASH0_BASE + \
+					 V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+/*Secure Watchdog Constants */
+#define SBSA_SECURE_WDOG_BASE		UL(0x2A480000)
+#define SBSA_SECURE_WDOG_TIMEOUT	UL(100)
+
+#define PLAT_ARM_SCMI_CHANNEL_COUNT	1
+
+#define PLAT_ARM_CLUSTER_COUNT		U(1)
+#define PLAT_MAX_CPUS_PER_CLUSTER	U(8)
+#define PLAT_MAX_PE_PER_CPU		U(1)
+
+#define PLAT_CSS_MHU_BASE		UL(0x45400000)
+#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
+
+#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
+#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
+
+/*
+ * Physical and virtual address space limits for MMU in AARCH64
+ */
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 36)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 36)
+
+/* GIC related constants */
+#define PLAT_ARM_GICD_BASE		UL(0x30000000)
+#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
+#define PLAT_ARM_GICR_BASE		UL(0x30080000)
+
+/*
+ * PLAT_CSS_MAX_SCP_BL2_SIZE is calculated using the current
+ * SCP_BL2 size plus a little space for growth.
+ */
+#define PLAT_CSS_MAX_SCP_BL2_SIZE	0x20000
+
+/*
+ * PLAT_CSS_MAX_SCP_BL2U_SIZE is calculated using the current
+ * SCP_BL2U size plus a little space for growth.
+ */
+#define PLAT_CSS_MAX_SCP_BL2U_SIZE	0x20000
+
+/* TZC Related Constants */
+#define PLAT_ARM_TZC_BASE		UL(0x25000000)
+#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
+
+#define TZC400_OFFSET			UL(0x1000000)
+#define TZC400_COUNT			4
+
+#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
+					 (n * TZC400_OFFSET))
+
+#define TZC_NSAID_DEFAULT		U(0)
+
+#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
+		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_DEFAULT))
+
+/*
+ * The first region below, TC_TZC_DRAM1_BASE (0xfd000000) to
+ * ARM_SCP_TZC_DRAM1_END (0xffffffff) will mark the last 48 MB of DRAM as
+ * secure. The second and third regions gives non secure access to rest of DRAM.
+ */
+#define TC_TZC_REGIONS_DEF	\
+	{TC_TZC_DRAM1_BASE, ARM_SCP_TZC_DRAM1_END,	\
+		TZC_REGION_S_RDWR, PLAT_ARM_TZC_NS_DEV_ACCESS},	\
+	{TC_NS_DRAM1_BASE, TC_NS_DRAM1_END, ARM_TZC_NS_DRAM_S_ACCESS,	\
+		PLAT_ARM_TZC_NS_DEV_ACCESS},	\
+	{PLAT_ARM_DRAM2_BASE, PLAT_ARM_DRAM2_END,	\
+		ARM_TZC_NS_DRAM_S_ACCESS, PLAT_ARM_TZC_NS_DEV_ACCESS}
+
+/* virtual address used by dynamic mem_protect for chunk_base */
+#define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xc0000000)
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/tc/include/tc_helpers.S b/plat/arm/board/tc/include/tc_helpers.S
new file mode 100644
index 0000000..5f54856
--- /dev/null
+++ b/plat/arm/board/tc/include/tc_helpers.S
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <platform_def.h>
+#include <cpu_macros.S>
+
+	.globl	plat_arm_calc_core_pos
+	.globl	plat_reset_handler
+
+	/* ---------------------------------------------------------------------
+	 * unsigned int plat_arm_calc_core_pos(u_register_t mpidr)
+	 *
+	 * Function to calculate the core position on TC.
+	 *
+	 * (ClusterId * PLAT_MAX_CPUS_PER_CLUSTER * PLAT_MAX_PE_PER_CPU) +
+	 * (CPUId * PLAT_MAX_PE_PER_CPU) +
+	 * ThreadId
+	 *
+	 * which can be simplified as:
+	 *
+	 * ((ClusterId * PLAT_MAX_CPUS_PER_CLUSTER + CPUId) * PLAT_MAX_PE_PER_CPU)
+	 * + ThreadId
+	 * ---------------------------------------------------------------------
+	 */
+func plat_arm_calc_core_pos
+	/*
+	 * Check for MT bit in MPIDR. If not set, shift MPIDR to left to make it
+	 * look as if in a multi-threaded implementation.
+	 */
+	tst	x0, #MPIDR_MT_MASK
+	lsl	x3, x0, #MPIDR_AFFINITY_BITS
+	csel	x3, x3, x0, eq
+
+	/* Extract individual affinity fields from MPIDR */
+	ubfx	x0, x3, #MPIDR_AFF0_SHIFT, #MPIDR_AFFINITY_BITS
+	ubfx	x1, x3, #MPIDR_AFF1_SHIFT, #MPIDR_AFFINITY_BITS
+	ubfx	x2, x3, #MPIDR_AFF2_SHIFT, #MPIDR_AFFINITY_BITS
+
+	/* Compute linear position */
+	mov	x4, #PLAT_MAX_CPUS_PER_CLUSTER
+	madd	x1, x2, x4, x1
+	mov	x5, #PLAT_MAX_PE_PER_CPU
+	madd	x0, x1, x5, x0
+	ret
+endfunc plat_arm_calc_core_pos
+
+	/* -----------------------------------------------------
+	 * void plat_reset_handler(void);
+	 *
+	 * Determine the CPU MIDR and disable power down bit for
+	 * that CPU.
+	 * -----------------------------------------------------
+	 */
+func plat_reset_handler
+	ret
+endfunc plat_reset_handler
diff --git a/plat/arm/board/tc/include/tc_plat.h b/plat/arm/board/tc/include/tc_plat.h
new file mode 100644
index 0000000..28c0308
--- /dev/null
+++ b/plat/arm/board/tc/include/tc_plat.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TC_PLAT_H
+#define TC_PLAT_H
+
+void tc_bl31_common_platform_setup(void);
+
+#endif /* TC_PLAT_H */
diff --git a/plat/arm/board/tc/platform.mk b/plat/arm/board/tc/platform.mk
new file mode 100644
index 0000000..8765fa2
--- /dev/null
+++ b/plat/arm/board/tc/platform.mk
@@ -0,0 +1,152 @@
+# Copyright (c) 2021, Arm Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+include common/fdt_wrappers.mk
+
+ifeq ($(filter ${TARGET_PLATFORM}, 0 1),)
+        $(error TARGET_PLATFORM must be 0 or 1)
+endif
+
+CSS_LOAD_SCP_IMAGES	:=	1
+
+CSS_USE_SCMI_SDS_DRIVER	:=	1
+
+RAS_EXTENSION		:=	0
+
+SDEI_SUPPORT		:=	0
+
+EL3_EXCEPTION_HANDLING	:=	0
+
+HANDLE_EA_EL3_FIRST	:=	0
+
+# System coherency is managed in hardware
+HW_ASSISTED_COHERENCY	:=	1
+
+# When building for systems with hardware-assisted coherency, there's no need to
+# use USE_COHERENT_MEM. Require that USE_COHERENT_MEM must be set to 0 too.
+USE_COHERENT_MEM	:=	0
+
+GIC_ENABLE_V4_EXTN	:=      1
+
+# GIC-600 configuration
+GICV3_SUPPORT_GIC600	:=	1
+
+# Enable SVE
+ENABLE_SVE_FOR_NS	:=	1
+ENABLE_SVE_FOR_SWD	:=	1
+
+# Include GICv3 driver files
+include drivers/arm/gic/v3/gicv3.mk
+
+ENT_GIC_SOURCES		:=	${GICV3_SOURCES}		\
+				plat/common/plat_gicv3.c	\
+				plat/arm/common/arm_gicv3.c
+
+override NEED_BL2U	:=	no
+
+override ARM_PLAT_MT	:=	1
+
+TC_BASE	=	plat/arm/board/tc
+
+PLAT_INCLUDES		+=	-I${TC_BASE}/include/
+
+# Common CPU libraries
+TC_CPU_SOURCES	:=	lib/cpus/aarch64/cortex_a510.S
+
+# CPU libraries for TARGET_PLATFORM=0
+ifeq (${TARGET_PLATFORM}, 0)
+TC_CPU_SOURCES	+=	lib/cpus/aarch64/cortex_a710.S \
+			lib/cpus/aarch64/cortex_x2.S
+endif
+
+# CPU libraries for TARGET_PLATFORM=1
+ifeq (${TARGET_PLATFORM}, 1)
+TC_CPU_SOURCES	+=	lib/cpus/aarch64/cortex_makalu.S \
+			lib/cpus/aarch64/cortex_makalu_elp_arm.S
+endif
+
+INTERCONNECT_SOURCES	:=	${TC_BASE}/tc_interconnect.c
+
+PLAT_BL_COMMON_SOURCES	+=	${TC_BASE}/tc_plat.c	\
+				${TC_BASE}/include/tc_helpers.S
+
+BL1_SOURCES		+=	${INTERCONNECT_SOURCES}	\
+				${TC_CPU_SOURCES}	\
+				${TC_BASE}/tc_trusted_boot.c	\
+				${TC_BASE}/tc_err.c	\
+				drivers/arm/sbsa/sbsa.c
+
+
+BL2_SOURCES		+=	${TC_BASE}/tc_security.c	\
+				${TC_BASE}/tc_err.c		\
+				${TC_BASE}/tc_trusted_boot.c		\
+				${TC_BASE}/tc_bl2_setup.c		\
+				lib/utils/mem_region.c			\
+				drivers/arm/tzc/tzc400.c		\
+				plat/arm/common/arm_tzc400.c		\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+BL31_SOURCES		+=	${INTERCONNECT_SOURCES}	\
+				${TC_CPU_SOURCES}	\
+				${ENT_GIC_SOURCES}			\
+				${TC_BASE}/tc_bl31_setup.c	\
+				${TC_BASE}/tc_topology.c	\
+				lib/fconf/fconf.c			\
+				lib/fconf/fconf_dyn_cfg_getter.c	\
+				drivers/cfi/v2m/v2m_flash.c		\
+				lib/utils/mem_region.c			\
+				plat/arm/common/arm_nor_psci_mem_protect.c
+
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
+# Add the FDT_SOURCES and options for Dynamic Config
+FDT_SOURCES		+=	${TC_BASE}/fdts/${PLAT}_fw_config.dts	\
+				${TC_BASE}/fdts/${PLAT}_tb_fw_config.dts
+FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
+TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
+
+# Add the FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
+# Add the TB_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
+
+ifeq (${SPD},spmd)
+ifeq ($(ARM_SPMC_MANIFEST_DTS),)
+ARM_SPMC_MANIFEST_DTS	:=	${TC_BASE}/fdts/${PLAT}_spmc_manifest.dts
+endif
+
+FDT_SOURCES		+=	${ARM_SPMC_MANIFEST_DTS}
+TC_TOS_FW_CONFIG	:=	${BUILD_PLAT}/fdts/$(notdir $(basename ${ARM_SPMC_MANIFEST_DTS})).dtb
+
+# Add the TOS_FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TC_TOS_FW_CONFIG},--tos-fw-config,${TC_TOS_FW_CONFIG}))
+endif
+
+#Device tree
+TC_HW_CONFIG_DTS	:=	fdts/tc.dts
+TC_HW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}.dtb
+FDT_SOURCES		+=	${TC_HW_CONFIG_DTS}
+$(eval TC_HW_CONFIG	:=	${BUILD_PLAT}/$(patsubst %.dts,%.dtb,$(TC_HW_CONFIG_DTS)))
+
+# Add the HW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${TC_HW_CONFIG},--hw-config,${TC_HW_CONFIG}))
+
+override CTX_INCLUDE_AARCH32_REGS	:= 0
+
+override CTX_INCLUDE_PAUTH_REGS	:= 1
+
+override ENABLE_SPE_FOR_LOWER_ELS	:= 0
+
+override ENABLE_AMU := 1
+override ENABLE_AMU_AUXILIARY_COUNTERS := 1
+override ENABLE_AMU_FCONF := 1
+
+override ENABLE_MPMM := 1
+override ENABLE_MPMM_FCONF := 1
+
+include plat/arm/common/arm_common.mk
+include plat/arm/css/common/css_common.mk
+include plat/arm/soc/common/soc_css.mk
+include plat/arm/board/common/board_common.mk
diff --git a/plat/arm/board/tc/tc_bl2_setup.c b/plat/arm/board/tc/tc_bl2_setup.c
new file mode 100644
index 0000000..74ef569
--- /dev/null
+++ b/plat/arm/board/tc/tc_bl2_setup.c
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/bl_common.h>
+#include <common/desc_image_load.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
+
+#include <plat/arm/common/plat_arm.h>
+
+/*******************************************************************************
+ * This function returns the list of executable images
+ ******************************************************************************/
+struct bl_params *plat_get_next_bl_params(void)
+{
+	struct bl_params *arm_bl_params = arm_get_next_bl_params();
+
+	const struct dyn_cfg_dtb_info_t *fw_config_info;
+	bl_mem_params_node_t *param_node;
+	uintptr_t fw_config_base = 0U;
+	entry_point_info_t *ep_info;
+
+	/* Get BL31 image node */
+	param_node = get_bl_mem_params_node(BL31_IMAGE_ID);
+	assert(param_node != NULL);
+
+	/* Get fw_config load address */
+	fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, FW_CONFIG_ID);
+	assert(fw_config_info != NULL);
+
+	fw_config_base = fw_config_info->config_addr;
+	assert(fw_config_base != 0U);
+
+	/*
+	 * Get the entry point info of BL31 image and override
+	 * arg1 of entry point info with fw_config base address
+	 */
+	ep_info = &param_node->ep_info;
+	ep_info->args.arg1 = (uint32_t)fw_config_base;
+
+	return arm_bl_params;
+}
diff --git a/plat/arm/board/tc/tc_bl31_setup.c b/plat/arm/board/tc/tc_bl31_setup.c
new file mode 100644
index 0000000..0523ef8
--- /dev/null
+++ b/plat/arm/board/tc/tc_bl31_setup.c
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <libfdt.h>
+#include <tc_plat.h>
+
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/arm/css/css_mhu_doorbell.h>
+#include <drivers/arm/css/scmi.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+
+static scmi_channel_plat_info_t tc_scmi_plat_info[] = {
+	{
+		.scmi_mbx_mem = CSS_SCMI_PAYLOAD_BASE,
+		.db_reg_addr = PLAT_CSS_MHU_BASE + SENDER_REG_SET(0),
+		.db_preserve_mask = 0xfffffffe,
+		.db_modify_mask = 0x1,
+		.ring_doorbell = &mhuv2_ring_doorbell,
+	}
+};
+
+void bl31_platform_setup(void)
+{
+	tc_bl31_common_platform_setup();
+}
+
+scmi_channel_plat_info_t *plat_css_get_scmi_info(int channel_id)
+{
+
+	return &tc_scmi_plat_info[channel_id];
+
+}
+
+void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
+				u_register_t arg2, u_register_t arg3)
+{
+	arm_bl31_early_platform_setup((void *)arg0, arg1, arg2, (void *)arg3);
+
+	/* Fill the properties struct with the info from the config dtb */
+	fconf_populate("FW_CONFIG", arg1);
+}
+
+void tc_bl31_common_platform_setup(void)
+{
+	arm_bl31_platform_setup();
+}
+
+const plat_psci_ops_t *plat_arm_psci_override_pm_ops(plat_psci_ops_t *ops)
+{
+	return css_scmi_override_pm_ops(ops);
+}
+
+void __init bl31_plat_arch_setup(void)
+{
+	arm_bl31_plat_arch_setup();
+
+	/* HW_CONFIG was also loaded by BL2 */
+	const struct dyn_cfg_dtb_info_t *hw_config_info;
+
+	hw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, HW_CONFIG_ID);
+	assert(hw_config_info != NULL);
+
+	fconf_populate("HW_CONFIG", hw_config_info->config_addr);
+}
diff --git a/plat/arm/board/tc/tc_err.c b/plat/arm/board/tc/tc_err.c
new file mode 100644
index 0000000..9ed7e92
--- /dev/null
+++ b/plat/arm/board/tc/tc_err.c
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+
+/*
+ * tc error handler
+ */
+void __dead2 plat_arm_error_handler(int err)
+{
+	while (true) {
+		wfi();
+	}
+}
diff --git a/plat/arm/board/tc0/tc0_interconnect.c b/plat/arm/board/tc/tc_interconnect.c
similarity index 100%
rename from plat/arm/board/tc0/tc0_interconnect.c
rename to plat/arm/board/tc/tc_interconnect.c
diff --git a/plat/arm/board/tc/tc_plat.c b/plat/arm/board/tc/tc_plat.c
new file mode 100644
index 0000000..a9668e1
--- /dev/null
+++ b/plat/arm/board/tc/tc_plat.c
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <platform_def.h>
+
+#include <plat/common/platform.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/arm/ccn.h>
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <drivers/arm/sbsa.h>
+
+#if SPM_MM
+#include <services/spm_mm_partition.h>
+#endif
+
+/*
+ * Table of regions for different BL stages to map using the MMU.
+ * This doesn't include Trusted RAM as the 'mem_layout' argument passed to
+ * arm_configure_mmu_elx() will give the available subset of that.
+ */
+#if IMAGE_BL1
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	TC_FLASH0_RO,
+	TC_MAP_DEVICE,
+	{0}
+};
+#endif
+#if IMAGE_BL2
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	TC_FLASH0_RO,
+	TC_MAP_DEVICE,
+	TC_MAP_NS_DRAM1,
+#if defined(SPD_spmd)
+	TC_MAP_TZC_DRAM1,
+#endif
+#if ARM_BL31_IN_DRAM
+	ARM_MAP_BL31_SEC_DRAM,
+#endif
+#if SPM_MM
+	ARM_SP_IMAGE_MMAP,
+#endif
+#if TRUSTED_BOARD_BOOT && !BL2_AT_EL3
+	ARM_MAP_BL1_RW,
+#endif
+#ifdef SPD_opteed
+	ARM_MAP_OPTEE_CORE_MEM,
+	ARM_OPTEE_PAGEABLE_LOAD_MEM,
+#endif
+	{0}
+};
+#endif
+#if IMAGE_BL31
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	V2M_MAP_IOFPGA,
+	TC_MAP_DEVICE,
+	PLAT_DTB_DRAM_NS,
+#if SPM_MM
+	ARM_SPM_BUF_EL3_MMAP,
+#endif
+	{0}
+};
+
+#if SPM_MM && defined(IMAGE_BL31)
+const mmap_region_t plat_arm_secure_partition_mmap[] = {
+	PLAT_ARM_SECURE_MAP_DEVICE,
+	ARM_SP_IMAGE_MMAP,
+	ARM_SP_IMAGE_NS_BUF_MMAP,
+	ARM_SP_CPER_BUF_MMAP,
+	ARM_SP_IMAGE_RW_MMAP,
+	ARM_SPM_BUF_EL0_MMAP,
+	{0}
+};
+#endif /* SPM_MM && defined(IMAGE_BL31) */
+#endif
+
+ARM_CASSERT_MMAP
+
+#if SPM_MM && defined(IMAGE_BL31)
+/*
+ * Boot information passed to a secure partition during initialisation. Linear
+ * indices in MP information will be filled at runtime.
+ */
+static spm_mm_mp_info_t sp_mp_info[] = {
+	[0] = {0x81000000, 0},
+	[1] = {0x81000100, 0},
+	[2] = {0x81000200, 0},
+	[3] = {0x81000300, 0},
+	[4] = {0x81010000, 0},
+	[5] = {0x81010100, 0},
+	[6] = {0x81010200, 0},
+	[7] = {0x81010300, 0},
+};
+
+const spm_mm_boot_info_t plat_arm_secure_partition_boot_info = {
+	.h.type              = PARAM_SP_IMAGE_BOOT_INFO,
+	.h.version           = VERSION_1,
+	.h.size              = sizeof(spm_mm_boot_info_t),
+	.h.attr              = 0,
+	.sp_mem_base         = ARM_SP_IMAGE_BASE,
+	.sp_mem_limit        = ARM_SP_IMAGE_LIMIT,
+	.sp_image_base       = ARM_SP_IMAGE_BASE,
+	.sp_stack_base       = PLAT_SP_IMAGE_STACK_BASE,
+	.sp_heap_base        = ARM_SP_IMAGE_HEAP_BASE,
+	.sp_ns_comm_buf_base = PLAT_SP_IMAGE_NS_BUF_BASE,
+	.sp_shared_buf_base  = PLAT_SPM_BUF_BASE,
+	.sp_image_size       = ARM_SP_IMAGE_SIZE,
+	.sp_pcpu_stack_size  = PLAT_SP_IMAGE_STACK_PCPU_SIZE,
+	.sp_heap_size        = ARM_SP_IMAGE_HEAP_SIZE,
+	.sp_ns_comm_buf_size = PLAT_SP_IMAGE_NS_BUF_SIZE,
+	.sp_shared_buf_size  = PLAT_SPM_BUF_SIZE,
+	.num_sp_mem_regions  = ARM_SP_IMAGE_NUM_MEM_REGIONS,
+	.num_cpus            = PLATFORM_CORE_COUNT,
+	.mp_info             = &sp_mp_info[0],
+};
+
+const struct mmap_region *plat_get_secure_partition_mmap(void *cookie)
+{
+	return plat_arm_secure_partition_mmap;
+}
+
+const struct spm_mm_boot_info *plat_get_secure_partition_boot_info(
+		void *cookie)
+{
+	return &plat_arm_secure_partition_boot_info;
+}
+#endif /* SPM_MM && defined(IMAGE_BL31) */
+
+#if TRUSTED_BOARD_BOOT
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	assert(heap_addr != NULL);
+	assert(heap_size != NULL);
+
+	return arm_get_mbedtls_heap(heap_addr, heap_size);
+}
+#endif
+
+void plat_arm_secure_wdt_start(void)
+{
+	sbsa_wdog_start(SBSA_SECURE_WDOG_BASE, SBSA_SECURE_WDOG_TIMEOUT);
+}
+
+void plat_arm_secure_wdt_stop(void)
+{
+	sbsa_wdog_stop(SBSA_SECURE_WDOG_BASE);
+}
diff --git a/plat/arm/board/tc/tc_security.c b/plat/arm/board/tc/tc_security.c
new file mode 100644
index 0000000..6a34501
--- /dev/null
+++ b/plat/arm/board/tc/tc_security.c
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <platform_def.h>
+
+static const arm_tzc_regions_info_t tzc_regions[] = {
+	TC_TZC_REGIONS_DEF,
+	{}
+};
+
+/* Initialize the secure environment */
+void plat_arm_security_setup(void)
+{
+	unsigned int i;
+
+	for (i = 0U; i < TZC400_COUNT; i++) {
+		arm_tzc400_setup(TZC400_BASE(i), tzc_regions);
+	}
+}
diff --git a/plat/arm/board/tc/tc_topology.c b/plat/arm/board/tc/tc_topology.c
new file mode 100644
index 0000000..9e18da6
--- /dev/null
+++ b/plat/arm/board/tc/tc_topology.c
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/arm/css/common/css_pm.h>
+
+/******************************************************************************
+ * The power domain tree descriptor.
+ ******************************************************************************/
+const unsigned char tc_pd_tree_desc[] = {
+	PLAT_ARM_CLUSTER_COUNT,
+	PLAT_MAX_CPUS_PER_CLUSTER,
+};
+
+/*******************************************************************************
+ * This function returns the topology tree information.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	return tc_pd_tree_desc;
+}
+
+/*******************************************************************************
+ * The array mapping platform core position (implemented by plat_my_core_pos())
+ * to the SCMI power domain ID implemented by SCP.
+ ******************************************************************************/
+const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x4)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x5)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x6)),
+	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x7)),
+};
+
+/*******************************************************************************
+ * This function returns the core count within the cluster corresponding to
+ * `mpidr`.
+ ******************************************************************************/
+unsigned int plat_arm_get_cluster_core_count(u_register_t mpidr)
+{
+	return PLAT_MAX_CPUS_PER_CLUSTER;
+}
+
+#if ARM_PLAT_MT
+/******************************************************************************
+ * Return the number of PE's supported by the CPU.
+ *****************************************************************************/
+unsigned int plat_arm_get_cpu_pe_count(u_register_t mpidr)
+{
+	return PLAT_MAX_PE_PER_CPU;
+}
+#endif
diff --git a/plat/arm/board/tc0/tc0_trusted_boot.c b/plat/arm/board/tc/tc_trusted_boot.c
similarity index 100%
rename from plat/arm/board/tc0/tc0_trusted_boot.c
rename to plat/arm/board/tc/tc_trusted_boot.c
diff --git a/plat/arm/board/tc0/fdts/tc0_fw_config.dts b/plat/arm/board/tc0/fdts/tc0_fw_config.dts
deleted file mode 100644
index 4b6abd4..0000000
--- a/plat/arm/board/tc0/fdts/tc0_fw_config.dts
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/tbbr/tbbr_img_def.h>
-
-/dts-v1/;
-
-/ {
-	dtb-registry {
-		compatible = "fconf,dyn_cfg-dtb_registry";
-
-		tb_fw-config {
-			load-address = <0x0 0x4001300>;
-			max-size = <0x400>;
-			id = <TB_FW_CONFIG_ID>;
-		};
-
-		tos_fw-config {
-			load-address = <0x0 0x04001700>;
-			max-size = <0x1000>;
-			id = <TOS_FW_CONFIG_ID>;
-		};
-
-		hw-config {
-			load-address = <0x0 0x83000000>;
-			max-size = <0x01000000>;
-			id = <HW_CONFIG_ID>;
-		};
-	};
-};
diff --git a/plat/arm/board/tc0/fdts/tc0_spmc_manifest.dts b/plat/arm/board/tc0/fdts/tc0_spmc_manifest.dts
deleted file mode 100644
index b6c543a..0000000
--- a/plat/arm/board/tc0/fdts/tc0_spmc_manifest.dts
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-/dts-v1/;
-
-/ {
-	compatible = "arm,ffa-core-manifest-1.0";
-	#address-cells = <2>;
-	#size-cells = <1>;
-
-	attribute {
-		spmc_id = <0x8000>;
-		maj_ver = <0x1>;
-		min_ver = <0x0>;
-		exec_state = <0x0>;
-		load_address = <0x0 0xfd000000>;
-		entrypoint = <0x0 0xfd000000>;
-		binary_size = <0x80000>;
-	};
-
-	chosen {
-		linux,initrd-start = <0>;
-		linux,initrd-end = <0>;
-	};
-
-	hypervisor {
-		compatible = "hafnium,hafnium";
-		vm1 {
-			is_ffa_partition;
-			debug_name = "cactus-primary";
-			load_address = <0xfe000000>;
-		};
-		vm2 {
-			is_ffa_partition;
-			debug_name = "cactus-secondary";
-			load_address = <0xfe100000>;
-			vcpu_count = <4>;
-			mem_size = <1048576>;
-		};
-		vm3 {
-			is_ffa_partition;
-			debug_name = "cactus-tertiary";
-			load_address = <0xfe200000>;
-			vcpu_count = <4>;
-			mem_size = <1048576>;
-		};
-	};
-
-	cpus {
-		#address-cells = <0x2>;
-		#size-cells = <0x0>;
-
-		CPU0:cpu@0 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x0 0x0>;
-			enable-method = "psci";
-		};
-
-		/*
-		 * SPM(Hafnium) requires secondary cpu nodes are declared in
-		 * descending order
-		 */
-		CPU3:cpu@300 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x0 0x300>;
-			enable-method = "psci";
-		};
-
-		CPU2:cpu@200 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x0 0x200>;
-			enable-method = "psci";
-		};
-
-		CPU1:cpu@100 {
-			device_type = "cpu";
-			compatible = "arm,armv8";
-			reg = <0x0 0x100>;
-			enable-method = "psci";
-		};
-	};
-
-	/* 32MB of TC0_TZC_DRAM1_BASE */
-	memory@fd000000 {
-		device_type = "memory";
-		reg = <0x0 0xfd000000 0x2000000>;
-	};
-};
diff --git a/plat/arm/board/tc0/fdts/tc0_tb_fw_config.dts b/plat/arm/board/tc0/fdts/tc0_tb_fw_config.dts
deleted file mode 100644
index 3df94bf..0000000
--- a/plat/arm/board/tc0/fdts/tc0_tb_fw_config.dts
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-/dts-v1/;
-
-/ {
-	tb_fw-config {
-		compatible = "arm,tb_fw";
-
-		/* Disable authentication for development */
-		disable_auth = <0x0>;
-		/*
-		 * The following two entries are placeholders for Mbed TLS
-		 * heap information. The default values don't matter since
-		 * they will be overwritten by BL1.
-		 * In case of having shared Mbed TLS heap between BL1 and BL2,
-		 * BL1 will populate these two properties with the respective
-		 * info about the shared heap. This info will be available for
-		 * BL2 in order to locate and re-use the heap.
-		 */
-		mbedtls_heap_addr = <0x0 0x0>;
-		mbedtls_heap_size = <0x0>;
-	};
-
-	secure-partitions {
-		compatible = "arm,sp";
-		cactus-primary {
-			uuid = <0xb4b5671e 0x4a904fe1 0xb81ffb13 0xdae1dacb>;
-			load-address = <0xfe000000>;
-			owner = "SiP";
-		};
-
-		cactus-secondary {
-			uuid = <0xd1582309 0xf02347b9 0x827c4464 0xf5578fc8>;
-			load-address = <0xfe100000>;
-			owner = "Plat";
-		};
-
-		cactus-tertiary {
-			uuid = <0x79b55c73 0x1d8c44b9 0x859361e1 0x770ad8d2>;
-			load-address = <0xfe200000>;
-		};
-	};
-};
diff --git a/plat/arm/board/tc0/include/platform_def.h b/plat/arm/board/tc0/include/platform_def.h
deleted file mode 100644
index 72a035f..0000000
--- a/plat/arm/board/tc0/include/platform_def.h
+++ /dev/null
@@ -1,266 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PLATFORM_DEF_H
-#define PLATFORM_DEF_H
-
-#include <lib/utils_def.h>
-#include <lib/xlat_tables/xlat_tables_defs.h>
-#include <plat/arm/board/common/board_css_def.h>
-#include <plat/arm/board/common/v2m_def.h>
-#include <plat/arm/common/arm_def.h>
-#include <plat/arm/common/arm_spm_def.h>
-#include <plat/arm/css/common/css_def.h>
-#include <plat/arm/soc/common/soc_css_def.h>
-#include <plat/common/common_def.h>
-
-#define PLATFORM_CORE_COUNT		4
-
-#define PLAT_ARM_TRUSTED_SRAM_SIZE	0x00080000	/* 512 KB */
-
-/*
- * The top 16MB of ARM_DRAM1 is configured as secure access only using the TZC,
- * its base is ARM_AP_TZC_DRAM1_BASE.
- *
- * Reserve 32MB below ARM_AP_TZC_DRAM1_BASE for:
- *   - BL32_BASE when SPD_spmd is enabled
- *   - Region to load Trusted OS
- */
-#define TC0_TZC_DRAM1_BASE		(ARM_AP_TZC_DRAM1_BASE -	\
-					 TC0_TZC_DRAM1_SIZE)
-#define TC0_TZC_DRAM1_SIZE		UL(0x02000000)	/* 32 MB */
-#define TC0_TZC_DRAM1_END		(TC0_TZC_DRAM1_BASE +		\
-					 TC0_TZC_DRAM1_SIZE - 1)
-
-#define TC0_NS_DRAM1_BASE		ARM_DRAM1_BASE
-#define TC0_NS_DRAM1_SIZE		(ARM_DRAM1_SIZE -		\
-					 ARM_TZC_DRAM1_SIZE -		\
-					 TC0_TZC_DRAM1_SIZE)
-#define TC0_NS_DRAM1_END		(TC0_NS_DRAM1_BASE +		\
-					 TC0_NS_DRAM1_SIZE - 1)
-
-/*
- * Mappings for TC0 DRAM1 (non-secure) and TC0 TZC DRAM1 (secure)
- */
-#define TC0_MAP_NS_DRAM1		MAP_REGION_FLAT(		\
-						TC0_NS_DRAM1_BASE,	\
-						TC0_NS_DRAM1_SIZE,	\
-						MT_MEMORY | MT_RW | MT_NS)
-
-
-#define TC0_MAP_TZC_DRAM1		MAP_REGION_FLAT(		\
-						TC0_TZC_DRAM1_BASE,	\
-						TC0_TZC_DRAM1_SIZE,	\
-						MT_MEMORY | MT_RW | MT_SECURE)
-/*
- * Max size of SPMC is 2MB for tc0. With SPMD enabled this value corresponds to
- * max size of BL32 image.
- */
-#if defined(SPD_spmd)
-#define PLAT_ARM_SPMC_BASE		TC0_TZC_DRAM1_BASE
-#define PLAT_ARM_SPMC_SIZE		UL(0x200000)  /* 2 MB */
-#endif
-
-/*
- * PLAT_ARM_MMAP_ENTRIES depends on the number of entries in the
- * plat_arm_mmap array defined for each BL stage.
- */
-#if defined(IMAGE_BL31)
-# if SPM_MM
-#  define PLAT_ARM_MMAP_ENTRIES		9
-#  define MAX_XLAT_TABLES		7
-#  define PLAT_SP_IMAGE_MMAP_REGIONS	7
-#  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	10
-# else
-#  define PLAT_ARM_MMAP_ENTRIES		8
-#  define MAX_XLAT_TABLES		8
-# endif
-#elif defined(IMAGE_BL32)
-# define PLAT_ARM_MMAP_ENTRIES		8
-# define MAX_XLAT_TABLES		5
-#elif !USE_ROMLIB
-# define PLAT_ARM_MMAP_ENTRIES		11
-# define MAX_XLAT_TABLES		7
-#else
-# define PLAT_ARM_MMAP_ENTRIES		12
-# define MAX_XLAT_TABLES		6
-#endif
-
-/*
- * PLAT_ARM_MAX_BL1_RW_SIZE is calculated using the current BL1 RW debug size
- * plus a little space for growth.
- */
-#define PLAT_ARM_MAX_BL1_RW_SIZE	0xC000
-
-/*
- * PLAT_ARM_MAX_ROMLIB_RW_SIZE is define to use a full page
- */
-
-#if USE_ROMLIB
-#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	0x1000
-#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	0xe000
-#else
-#define PLAT_ARM_MAX_ROMLIB_RW_SIZE	0
-#define PLAT_ARM_MAX_ROMLIB_RO_SIZE	0
-#endif
-
-/*
- * PLAT_ARM_MAX_BL2_SIZE is calculated using the current BL2 debug size plus a
- * little space for growth.
- */
-#if TRUSTED_BOARD_BOOT
-# define PLAT_ARM_MAX_BL2_SIZE		0x1E000
-#else
-# define PLAT_ARM_MAX_BL2_SIZE		0x14000
-#endif
-
-/*
- * Since BL31 NOBITS overlays BL2 and BL1-RW, PLAT_ARM_MAX_BL31_SIZE is
- * calculated using the current BL31 PROGBITS debug size plus the sizes of
- * BL2 and BL1-RW
- */
-#define PLAT_ARM_MAX_BL31_SIZE		0x3B000
-
-/*
- * Size of cacheable stacks
- */
-#if defined(IMAGE_BL1)
-# if TRUSTED_BOARD_BOOT
-#  define PLATFORM_STACK_SIZE		0x1000
-# else
-#  define PLATFORM_STACK_SIZE		0x440
-# endif
-#elif defined(IMAGE_BL2)
-# if TRUSTED_BOARD_BOOT
-#  define PLATFORM_STACK_SIZE		0x1000
-# else
-#  define PLATFORM_STACK_SIZE		0x400
-# endif
-#elif defined(IMAGE_BL2U)
-# define PLATFORM_STACK_SIZE		0x400
-#elif defined(IMAGE_BL31)
-# if SPM_MM
-#  define PLATFORM_STACK_SIZE		0x500
-# else
-#  define PLATFORM_STACK_SIZE		0x400
-# endif
-#elif defined(IMAGE_BL32)
-# define PLATFORM_STACK_SIZE		0x440
-#endif
-
-
-#define TC0_DEVICE_BASE			0x21000000
-#define TC0_DEVICE_SIZE			0x5f000000
-
-// TC0_MAP_DEVICE covers different peripherals
-// available to the platform
-#define TC0_MAP_DEVICE	MAP_REGION_FLAT(		\
-					TC0_DEVICE_BASE,	\
-					TC0_DEVICE_SIZE,	\
-					MT_DEVICE | MT_RW | MT_SECURE)
-
-
-#define TC0_FLASH0_RO	MAP_REGION_FLAT(V2M_FLASH0_BASE,\
-						V2M_FLASH0_SIZE,	\
-						MT_DEVICE | MT_RO | MT_SECURE)
-
-#define PLAT_ARM_NSTIMER_FRAME_ID	0
-
-#define PLAT_ARM_TRUSTED_ROM_BASE	0x0
-#define PLAT_ARM_TRUSTED_ROM_SIZE	0x00080000	/* 512KB */
-
-#define PLAT_ARM_NSRAM_BASE		0x06000000
-#define PLAT_ARM_NSRAM_SIZE		0x00080000	/* 512KB */
-
-#define PLAT_ARM_DRAM2_BASE		ULL(0x8080000000)
-#define PLAT_ARM_DRAM2_SIZE		ULL(0x180000000)
-
-#define PLAT_ARM_G1S_IRQ_PROPS(grp)	CSS_G1S_IRQ_PROPS(grp)
-#define PLAT_ARM_G0_IRQ_PROPS(grp)	ARM_G0_IRQ_PROPS(grp)
-
-#define PLAT_ARM_SP_IMAGE_STACK_BASE	(PLAT_SP_IMAGE_NS_BUF_BASE +	\
-					 PLAT_SP_IMAGE_NS_BUF_SIZE)
-
-/*******************************************************************************
- * Memprotect definitions
- ******************************************************************************/
-/* PSCI memory protect definitions:
- * This variable is stored in a non-secure flash because some ARM reference
- * platforms do not have secure NVRAM. Real systems that provided MEM_PROTECT
- * support must use a secure NVRAM to store the PSCI MEM_PROTECT definitions.
- */
-#define PLAT_ARM_MEM_PROT_ADDR		(V2M_FLASH0_BASE + \
-					 V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
-
-/*Secure Watchdog Constants */
-#define SBSA_SECURE_WDOG_BASE		UL(0x2A480000)
-#define SBSA_SECURE_WDOG_TIMEOUT	UL(100)
-
-#define PLAT_ARM_SCMI_CHANNEL_COUNT	1
-
-#define PLAT_ARM_CLUSTER_COUNT		U(1)
-#define PLAT_MAX_CPUS_PER_CLUSTER	U(4)
-#define PLAT_MAX_PE_PER_CPU		U(1)
-
-#define PLAT_CSS_MHU_BASE		UL(0x45400000)
-#define PLAT_MHUV2_BASE			PLAT_CSS_MHU_BASE
-
-#define CSS_SYSTEM_PWR_DMN_LVL		ARM_PWR_LVL2
-#define PLAT_MAX_PWR_LVL		ARM_PWR_LVL1
-
-/*
- * Physical and virtual address space limits for MMU in AARCH64
- */
-#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 36)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 36)
-
-/* GIC related constants */
-#define PLAT_ARM_GICD_BASE		UL(0x30000000)
-#define PLAT_ARM_GICC_BASE		UL(0x2C000000)
-#define PLAT_ARM_GICR_BASE		UL(0x30140000)
-
-/*
- * PLAT_CSS_MAX_SCP_BL2_SIZE is calculated using the current
- * SCP_BL2 size plus a little space for growth.
- */
-#define PLAT_CSS_MAX_SCP_BL2_SIZE	0x20000
-
-/*
- * PLAT_CSS_MAX_SCP_BL2U_SIZE is calculated using the current
- * SCP_BL2U size plus a little space for growth.
- */
-#define PLAT_CSS_MAX_SCP_BL2U_SIZE	0x20000
-
-/* TZC Related Constants */
-#define PLAT_ARM_TZC_BASE		UL(0x25000000)
-#define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT(0)
-
-#define TZC400_OFFSET			UL(0x1000000)
-#define TZC400_COUNT			4
-
-#define TZC400_BASE(n)			(PLAT_ARM_TZC_BASE + \
-					 (n * TZC400_OFFSET))
-
-#define TZC_NSAID_DEFAULT		U(0)
-
-#define PLAT_ARM_TZC_NS_DEV_ACCESS	\
-		(TZC_REGION_ACCESS_RDWR(TZC_NSAID_DEFAULT))
-
-/*
- * The first region below, TC0_TZC_DRAM1_BASE (0xfd000000) to
- * ARM_SCP_TZC_DRAM1_END (0xffffffff) will mark the last 48 MB of DRAM as
- * secure. The second region gives non secure access to rest of DRAM.
- */
-#define TC0_TZC_REGIONS_DEF						\
-	{TC0_TZC_DRAM1_BASE, ARM_SCP_TZC_DRAM1_END,			\
-		TZC_REGION_S_RDWR, PLAT_ARM_TZC_NS_DEV_ACCESS},		\
-	{TC0_NS_DRAM1_BASE, TC0_NS_DRAM1_END, ARM_TZC_NS_DRAM_S_ACCESS, \
-		PLAT_ARM_TZC_NS_DEV_ACCESS}
-
-/* virtual address used by dynamic mem_protect for chunk_base */
-#define PLAT_ARM_MEM_PROTEC_VA_FRAME	UL(0xc0000000)
-
-#endif /* PLATFORM_DEF_H */
diff --git a/plat/arm/board/tc0/include/tc0_helpers.S b/plat/arm/board/tc0/include/tc0_helpers.S
deleted file mode 100644
index 90623a2..0000000
--- a/plat/arm/board/tc0/include/tc0_helpers.S
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <platform_def.h>
-#include <cpu_macros.S>
-
-	.globl	plat_arm_calc_core_pos
-	.globl	plat_reset_handler
-
-	/* ---------------------------------------------------------------------
-	 * unsigned int plat_arm_calc_core_pos(u_register_t mpidr)
-	 *
-	 * Function to calculate the core position on TC0.
-	 *
-	 * (ClusterId * PLAT_MAX_CPUS_PER_CLUSTER * PLAT_MAX_PE_PER_CPU) +
-	 * (CPUId * PLAT_MAX_PE_PER_CPU) +
-	 * ThreadId
-	 *
-	 * which can be simplified as:
-	 *
-	 * ((ClusterId * PLAT_MAX_CPUS_PER_CLUSTER + CPUId) * PLAT_MAX_PE_PER_CPU)
-	 * + ThreadId
-	 * ---------------------------------------------------------------------
-	 */
-func plat_arm_calc_core_pos
-	/*
-	 * Check for MT bit in MPIDR. If not set, shift MPIDR to left to make it
-	 * look as if in a multi-threaded implementation.
-	 */
-	tst	x0, #MPIDR_MT_MASK
-	lsl	x3, x0, #MPIDR_AFFINITY_BITS
-	csel	x3, x3, x0, eq
-
-	/* Extract individual affinity fields from MPIDR */
-	ubfx	x0, x3, #MPIDR_AFF0_SHIFT, #MPIDR_AFFINITY_BITS
-	ubfx	x1, x3, #MPIDR_AFF1_SHIFT, #MPIDR_AFFINITY_BITS
-	ubfx	x2, x3, #MPIDR_AFF2_SHIFT, #MPIDR_AFFINITY_BITS
-
-	/* Compute linear position */
-	mov	x4, #PLAT_MAX_CPUS_PER_CLUSTER
-	madd	x1, x2, x4, x1
-	mov	x5, #PLAT_MAX_PE_PER_CPU
-	madd	x0, x1, x5, x0
-	ret
-endfunc plat_arm_calc_core_pos
-
-	/* -----------------------------------------------------
-	 * void plat_reset_handler(void);
-	 *
-	 * Determine the CPU MIDR and disable power down bit for
-	 * that CPU.
-	 * -----------------------------------------------------
-	 */
-func plat_reset_handler
-	ret
-endfunc plat_reset_handler
diff --git a/plat/arm/board/tc0/include/tc0_plat.h b/plat/arm/board/tc0/include/tc0_plat.h
deleted file mode 100644
index f0cb431..0000000
--- a/plat/arm/board/tc0/include/tc0_plat.h
+++ /dev/null
@@ -1,12 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef tc0_bl31_common_platform_setup_PLAT_H
-#define tc0_bl31_common_platform_setup_PLAT_H
-
-void tc0_bl31_common_platform_setup(void);
-
-#endif /* tc0_bl31_common_platform_setup_PLAT_H */
diff --git a/plat/arm/board/tc0/platform.mk b/plat/arm/board/tc0/platform.mk
deleted file mode 100644
index 5d2cc38..0000000
--- a/plat/arm/board/tc0/platform.mk
+++ /dev/null
@@ -1,114 +0,0 @@
-# Copyright (c) 2020, Arm Limited. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-CSS_LOAD_SCP_IMAGES	:=	1
-
-CSS_USE_SCMI_SDS_DRIVER	:=	1
-
-RAS_EXTENSION		:=	0
-
-SDEI_SUPPORT		:=	0
-
-EL3_EXCEPTION_HANDLING	:=	0
-
-HANDLE_EA_EL3_FIRST	:=	0
-
-# System coherency is managed in hardware
-HW_ASSISTED_COHERENCY	:=	1
-
-# When building for systems with hardware-assisted coherency, there's no need to
-# use USE_COHERENT_MEM. Require that USE_COHERENT_MEM must be set to 0 too.
-USE_COHERENT_MEM	:=	0
-
-GIC_ENABLE_V4_EXTN	:=      1
-
-# GIC-600 configuration
-GICV3_SUPPORT_GIC600	:=	1
-
-
-# Include GICv3 driver files
-include drivers/arm/gic/v3/gicv3.mk
-
-ENT_GIC_SOURCES		:=	${GICV3_SOURCES}		\
-				plat/common/plat_gicv3.c	\
-				plat/arm/common/arm_gicv3.c
-
-override NEED_BL2U	:=	no
-
-override ARM_PLAT_MT	:=	1
-
-TC0_BASE	=	plat/arm/board/tc0
-
-PLAT_INCLUDES		+=	-I${TC0_BASE}/include/
-
-TC0_CPU_SOURCES	:=	lib/cpus/aarch64/cortex_matterhorn.S
-
-INTERCONNECT_SOURCES	:=	${TC0_BASE}/tc0_interconnect.c
-
-PLAT_BL_COMMON_SOURCES	+=	${TC0_BASE}/tc0_plat.c	\
-				${TC0_BASE}/include/tc0_helpers.S
-
-BL1_SOURCES		+=	${INTERCONNECT_SOURCES}	\
-				${TC0_CPU_SOURCES}	\
-				${TC0_BASE}/tc0_trusted_boot.c	\
-				${TC0_BASE}/tc0_err.c	\
-				drivers/arm/sbsa/sbsa.c
-
-
-BL2_SOURCES		+=	${TC0_BASE}/tc0_security.c	\
-				${TC0_BASE}/tc0_err.c		\
-				${TC0_BASE}/tc0_trusted_boot.c		\
-				lib/utils/mem_region.c			\
-				drivers/arm/tzc/tzc400.c		\
-				plat/arm/common/arm_tzc400.c		\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-BL31_SOURCES		+=	${INTERCONNECT_SOURCES}	\
-				${TC0_CPU_SOURCES}	\
-				${ENT_GIC_SOURCES}			\
-				${TC0_BASE}/tc0_bl31_setup.c	\
-				${TC0_BASE}/tc0_topology.c	\
-				drivers/cfi/v2m/v2m_flash.c		\
-				lib/utils/mem_region.c			\
-				plat/arm/common/arm_nor_psci_mem_protect.c
-
-# Add the FDT_SOURCES and options for Dynamic Config
-FDT_SOURCES		+=	${TC0_BASE}/fdts/${PLAT}_fw_config.dts	\
-				${TC0_BASE}/fdts/${PLAT}_tb_fw_config.dts
-FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_fw_config.dtb
-TB_FW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}_tb_fw_config.dtb
-
-# Add the FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${FW_CONFIG},--fw-config,${FW_CONFIG}))
-# Add the TB_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${TB_FW_CONFIG},--tb-fw-config,${TB_FW_CONFIG}))
-
-ifeq (${SPD},spmd)
-FDT_SOURCES		+=	${TC0_BASE}/fdts/${PLAT}_spmc_manifest.dts
-TC0_TOS_FW_CONFIG	:=	${BUILD_PLAT}/fdts/${PLAT}_spmc_manifest.dtb
-
-# Add the TOS_FW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${TC0_TOS_FW_CONFIG},--tos-fw-config,${TC0_TOS_FW_CONFIG}))
-endif
-
-#Device tree
-TC0_HW_CONFIG_DTS	:=	fdts/tc0.dts
-TC0_HW_CONFIG		:=	${BUILD_PLAT}/fdts/${PLAT}.dtb
-FDT_SOURCES		+=	${TC0_HW_CONFIG_DTS}
-$(eval TC0_HW_CONFIG	:=	${BUILD_PLAT}/$(patsubst %.dts,%.dtb,$(TC0_HW_CONFIG_DTS)))
-
-# Add the HW_CONFIG to FIP and specify the same to certtool
-$(eval $(call TOOL_ADD_PAYLOAD,${TC0_HW_CONFIG},--hw-config,${TC0_HW_CONFIG}))
-
-override CTX_INCLUDE_AARCH32_REGS	:= 0
-
-override CTX_INCLUDE_PAUTH_REGS	:= 1
-
-override ENABLE_SPE_FOR_LOWER_ELS	:= 0
-
-include plat/arm/common/arm_common.mk
-include plat/arm/css/common/css_common.mk
-include plat/arm/soc/common/soc_css.mk
-include plat/arm/board/common/board_common.mk
diff --git a/plat/arm/board/tc0/tc0_bl31_setup.c b/plat/arm/board/tc0/tc0_bl31_setup.c
deleted file mode 100644
index b91b11c..0000000
--- a/plat/arm/board/tc0/tc0_bl31_setup.c
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <libfdt.h>
-#include <tc0_plat.h>
-
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/arm/css/css_mhu_doorbell.h>
-#include <drivers/arm/css/scmi.h>
-#include <plat/arm/common/plat_arm.h>
-#include <plat/common/platform.h>
-
-static scmi_channel_plat_info_t tc0_scmi_plat_info[] = {
-	{
-		.scmi_mbx_mem = CSS_SCMI_PAYLOAD_BASE,
-		.db_reg_addr = PLAT_CSS_MHU_BASE + SENDER_REG_SET(0),
-		.db_preserve_mask = 0xfffffffe,
-		.db_modify_mask = 0x1,
-		.ring_doorbell = &mhuv2_ring_doorbell,
-	}
-};
-
-void bl31_platform_setup(void)
-{
-	tc0_bl31_common_platform_setup();
-}
-
-scmi_channel_plat_info_t *plat_css_get_scmi_info(int channel_id)
-{
-
-	return &tc0_scmi_plat_info[channel_id];
-
-}
-
-void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
-				u_register_t arg2, u_register_t arg3)
-{
-	arm_bl31_early_platform_setup((void *)arg0, arg1, arg2, (void *)arg3);
-}
-
-void tc0_bl31_common_platform_setup(void)
-{
-	arm_bl31_platform_setup();
-}
-
-const plat_psci_ops_t *plat_arm_psci_override_pm_ops(plat_psci_ops_t *ops)
-{
-	return css_scmi_override_pm_ops(ops);
-}
diff --git a/plat/arm/board/tc0/tc0_err.c b/plat/arm/board/tc0/tc0_err.c
deleted file mode 100644
index 83f2e9f..0000000
--- a/plat/arm/board/tc0/tc0_err.c
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-
-/*
- * tc0 error handler
- */
-void __dead2 plat_arm_error_handler(int err)
-{
-	while (true) {
-		wfi();
-	}
-}
diff --git a/plat/arm/board/tc0/tc0_plat.c b/plat/arm/board/tc0/tc0_plat.c
deleted file mode 100644
index e12ad56..0000000
--- a/plat/arm/board/tc0/tc0_plat.c
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <platform_def.h>
-
-#include <plat/common/platform.h>
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/arm/ccn.h>
-#include <plat/arm/common/plat_arm.h>
-#include <plat/common/platform.h>
-#include <drivers/arm/sbsa.h>
-
-#if SPM_MM
-#include <services/spm_mm_partition.h>
-#endif
-
-/*
- * Table of regions for different BL stages to map using the MMU.
- * This doesn't include Trusted RAM as the 'mem_layout' argument passed to
- * arm_configure_mmu_elx() will give the available subset of that.
- */
-#if IMAGE_BL1
-const mmap_region_t plat_arm_mmap[] = {
-	ARM_MAP_SHARED_RAM,
-	TC0_FLASH0_RO,
-	TC0_MAP_DEVICE,
-	{0}
-};
-#endif
-#if IMAGE_BL2
-const mmap_region_t plat_arm_mmap[] = {
-	ARM_MAP_SHARED_RAM,
-	TC0_FLASH0_RO,
-	TC0_MAP_DEVICE,
-	TC0_MAP_NS_DRAM1,
-#if defined(SPD_spmd)
-	TC0_MAP_TZC_DRAM1,
-#endif
-#if ARM_BL31_IN_DRAM
-	ARM_MAP_BL31_SEC_DRAM,
-#endif
-#if SPM_MM
-	ARM_SP_IMAGE_MMAP,
-#endif
-#if TRUSTED_BOARD_BOOT && !BL2_AT_EL3
-	ARM_MAP_BL1_RW,
-#endif
-	{0}
-};
-#endif
-#if IMAGE_BL31
-const mmap_region_t plat_arm_mmap[] = {
-	ARM_MAP_SHARED_RAM,
-	V2M_MAP_IOFPGA,
-	TC0_MAP_DEVICE,
-#if SPM_MM
-	ARM_SPM_BUF_EL3_MMAP,
-#endif
-	{0}
-};
-
-#if SPM_MM && defined(IMAGE_BL31)
-const mmap_region_t plat_arm_secure_partition_mmap[] = {
-	PLAT_ARM_SECURE_MAP_DEVICE,
-	ARM_SP_IMAGE_MMAP,
-	ARM_SP_IMAGE_NS_BUF_MMAP,
-	ARM_SP_CPER_BUF_MMAP,
-	ARM_SP_IMAGE_RW_MMAP,
-	ARM_SPM_BUF_EL0_MMAP,
-	{0}
-};
-#endif /* SPM_MM && defined(IMAGE_BL31) */
-#endif
-
-ARM_CASSERT_MMAP
-
-#if SPM_MM && defined(IMAGE_BL31)
-/*
- * Boot information passed to a secure partition during initialisation. Linear
- * indices in MP information will be filled at runtime.
- */
-static spm_mm_mp_info_t sp_mp_info[] = {
-	[0] = {0x81000000, 0},
-	[1] = {0x81000100, 0},
-	[2] = {0x81000200, 0},
-	[3] = {0x81000300, 0},
-	[4] = {0x81010000, 0},
-	[5] = {0x81010100, 0},
-	[6] = {0x81010200, 0},
-	[7] = {0x81010300, 0},
-};
-
-const spm_mm_boot_info_t plat_arm_secure_partition_boot_info = {
-	.h.type              = PARAM_SP_IMAGE_BOOT_INFO,
-	.h.version           = VERSION_1,
-	.h.size              = sizeof(spm_mm_boot_info_t),
-	.h.attr              = 0,
-	.sp_mem_base         = ARM_SP_IMAGE_BASE,
-	.sp_mem_limit        = ARM_SP_IMAGE_LIMIT,
-	.sp_image_base       = ARM_SP_IMAGE_BASE,
-	.sp_stack_base       = PLAT_SP_IMAGE_STACK_BASE,
-	.sp_heap_base        = ARM_SP_IMAGE_HEAP_BASE,
-	.sp_ns_comm_buf_base = PLAT_SP_IMAGE_NS_BUF_BASE,
-	.sp_shared_buf_base  = PLAT_SPM_BUF_BASE,
-	.sp_image_size       = ARM_SP_IMAGE_SIZE,
-	.sp_pcpu_stack_size  = PLAT_SP_IMAGE_STACK_PCPU_SIZE,
-	.sp_heap_size        = ARM_SP_IMAGE_HEAP_SIZE,
-	.sp_ns_comm_buf_size = PLAT_SP_IMAGE_NS_BUF_SIZE,
-	.sp_shared_buf_size  = PLAT_SPM_BUF_SIZE,
-	.num_sp_mem_regions  = ARM_SP_IMAGE_NUM_MEM_REGIONS,
-	.num_cpus            = PLATFORM_CORE_COUNT,
-	.mp_info             = &sp_mp_info[0],
-};
-
-const struct mmap_region *plat_get_secure_partition_mmap(void *cookie)
-{
-	return plat_arm_secure_partition_mmap;
-}
-
-const struct spm_mm_boot_info *plat_get_secure_partition_boot_info(
-		void *cookie)
-{
-	return &plat_arm_secure_partition_boot_info;
-}
-#endif /* SPM_MM && defined(IMAGE_BL31) */
-
-#if TRUSTED_BOARD_BOOT
-int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
-{
-	assert(heap_addr != NULL);
-	assert(heap_size != NULL);
-
-	return arm_get_mbedtls_heap(heap_addr, heap_size);
-}
-#endif
-
-void plat_arm_secure_wdt_start(void)
-{
-	sbsa_wdog_start(SBSA_SECURE_WDOG_BASE, SBSA_SECURE_WDOG_TIMEOUT);
-}
-
-void plat_arm_secure_wdt_stop(void)
-{
-	sbsa_wdog_stop(SBSA_SECURE_WDOG_BASE);
-}
diff --git a/plat/arm/board/tc0/tc0_security.c b/plat/arm/board/tc0/tc0_security.c
deleted file mode 100644
index f543762..0000000
--- a/plat/arm/board/tc0/tc0_security.c
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (c) 2020, Arm Limited. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-#include <platform_def.h>
-
-static const arm_tzc_regions_info_t tzc_regions[] = {
-	TC0_TZC_REGIONS_DEF,
-	{}
-};
-
-/* Initialize the secure environment */
-void plat_arm_security_setup(void)
-{
-	unsigned int i;
-
-	for (i = 0U; i < TZC400_COUNT; i++) {
-		arm_tzc400_setup(TZC400_BASE(i), tzc_regions);
-	}
-}
diff --git a/plat/arm/board/tc0/tc0_topology.c b/plat/arm/board/tc0/tc0_topology.c
deleted file mode 100644
index 5478fbc..0000000
--- a/plat/arm/board/tc0/tc0_topology.c
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <plat/arm/common/plat_arm.h>
-#include <plat/arm/css/common/css_pm.h>
-
-/******************************************************************************
- * The power domain tree descriptor.
- ******************************************************************************/
-const unsigned char tc0_pd_tree_desc[] = {
-	PLAT_ARM_CLUSTER_COUNT,
-	PLAT_MAX_CPUS_PER_CLUSTER,
-};
-
-/*******************************************************************************
- * This function returns the topology tree information.
- ******************************************************************************/
-const unsigned char *plat_get_power_domain_tree_desc(void)
-{
-	return tc0_pd_tree_desc;
-}
-
-/*******************************************************************************
- * The array mapping platform core position (implemented by plat_my_core_pos())
- * to the SCMI power domain ID implemented by SCP.
- ******************************************************************************/
-const uint32_t plat_css_core_pos_to_scmi_dmn_id_map[] = {
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x0)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x1)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x2)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x3)),
-	(SET_SCMI_CHANNEL_ID(0x0) | SET_SCMI_DOMAIN_ID(0x4)),
-};
-
-/*******************************************************************************
- * This function returns the core count within the cluster corresponding to
- * `mpidr`.
- ******************************************************************************/
-unsigned int plat_arm_get_cluster_core_count(u_register_t mpidr)
-{
-	return PLAT_MAX_CPUS_PER_CLUSTER;
-}
-
-#if ARM_PLAT_MT
-/******************************************************************************
- * Return the number of PE's supported by the CPU.
- *****************************************************************************/
-unsigned int plat_arm_get_cpu_pe_count(u_register_t mpidr)
-{
-	return PLAT_MAX_PE_PER_CPU;
-}
-#endif
diff --git a/plat/arm/common/aarch64/arm_bl2_mem_params_desc.c b/plat/arm/common/aarch64/arm_bl2_mem_params_desc.c
index 6a8943d..0666e57 100644
--- a/plat/arm/common/aarch64/arm_bl2_mem_params_desc.c
+++ b/plat/arm/common/aarch64/arm_bl2_mem_params_desc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -75,8 +75,10 @@
 	    .image_info.image_base = BL31_BASE,
 	    .image_info.image_max_size = BL31_LIMIT - BL31_BASE,
 
-# ifdef BL32_BASE
+# if defined(BL32_BASE)
 	    .next_handoff_image_id = BL32_IMAGE_ID,
+# elif ENABLE_RME
+	    .next_handoff_image_id = RMM_IMAGE_ID,
 # else
 	    .next_handoff_image_id = BL33_IMAGE_ID,
 # endif
@@ -99,6 +101,22 @@
 		    VERSION_2, image_info_t, IMAGE_ATTRIB_SKIP_LOADING),
 	    .next_handoff_image_id = INVALID_IMAGE_ID,
     },
+
+# if ENABLE_RME
+	/* Fill RMM related information */
+    {
+	    .image_id = RMM_IMAGE_ID,
+	    SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+		    VERSION_2, entry_point_info_t, EP_REALM | EXECUTABLE),
+	    .ep_info.pc = RMM_BASE,
+	    SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+		    VERSION_2, image_info_t, 0),
+	    .image_info.image_base = RMM_BASE,
+	    .image_info.image_max_size = RMM_LIMIT - RMM_BASE,
+	    .next_handoff_image_id = BL33_IMAGE_ID,
+    },
+# endif
+
 # ifdef BL32_BASE
 	/* Fill BL32 related information */
     {
@@ -113,7 +131,11 @@
 	    .image_info.image_base = BL32_BASE,
 	    .image_info.image_max_size = BL32_LIMIT - BL32_BASE,
 
+# if ENABLE_RME
+	    .next_handoff_image_id = RMM_IMAGE_ID,
+# else
 	    .next_handoff_image_id = BL33_IMAGE_ID,
+# endif
     },
 
 	/*
diff --git a/plat/arm/common/arm_bl1_fwu.c b/plat/arm/common/arm_bl1_fwu.c
index 124c1af..ce2c356 100644
--- a/plat/arm/common/arm_bl1_fwu.c
+++ b/plat/arm/common/arm_bl1_fwu.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -16,6 +16,8 @@
 #include <plat/arm/common/plat_arm.h>
 #include <plat/common/platform.h>
 
+#pragma weak bl1_plat_get_image_desc
+
 /* Struct to keep track of usable memory */
 typedef struct bl1_mem_info {
 	uintptr_t mem_base;
diff --git a/plat/arm/common/arm_bl1_setup.c b/plat/arm/common/arm_bl1_setup.c
index 4b2a062..320bb82 100644
--- a/plat/arm/common/arm_bl1_setup.c
+++ b/plat/arm/common/arm_bl1_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -22,14 +22,17 @@
 #pragma weak bl1_early_platform_setup
 #pragma weak bl1_plat_arch_setup
 #pragma weak bl1_plat_sec_mem_layout
+#pragma weak arm_bl1_early_platform_setup
 #pragma weak bl1_plat_prepare_exit
 #pragma weak bl1_plat_get_next_image_id
 #pragma weak plat_arm_bl1_fwu_needed
+#pragma weak arm_bl1_plat_arch_setup
+#pragma weak arm_bl1_platform_setup
 
 #define MAP_BL1_TOTAL		MAP_REGION_FLAT(			\
 					bl1_tzram_layout.total_base,	\
 					bl1_tzram_layout.total_size,	\
-					MT_MEMORY | MT_RW | MT_SECURE)
+					MT_MEMORY | MT_RW | EL3_PAS)
 /*
  * If SEPARATE_CODE_AND_RODATA=1 we define a region for each section
  * otherwise one region is defined containing both
@@ -38,17 +41,17 @@
 #define MAP_BL1_RO		MAP_REGION_FLAT(			\
 					BL_CODE_BASE,			\
 					BL1_CODE_END - BL_CODE_BASE,	\
-					MT_CODE | MT_SECURE),		\
+					MT_CODE | EL3_PAS),		\
 				MAP_REGION_FLAT(			\
 					BL1_RO_DATA_BASE,		\
 					BL1_RO_DATA_END			\
 						- BL_RO_DATA_BASE,	\
-					MT_RO_DATA | MT_SECURE)
+					MT_RO_DATA | EL3_PAS)
 #else
 #define MAP_BL1_RO		MAP_REGION_FLAT(			\
 					BL_CODE_BASE,			\
 					BL1_CODE_END - BL_CODE_BASE,	\
-					MT_CODE | MT_SECURE)
+					MT_CODE | EL3_PAS)
 #endif
 
 /* Data structure which holds the extents of the trusted SRAM for BL1*/
diff --git a/plat/arm/common/arm_bl2_setup.c b/plat/arm/common/arm_bl2_setup.c
index c90e93c..08c014d 100644
--- a/plat/arm/common/arm_bl2_setup.c
+++ b/plat/arm/common/arm_bl2_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,17 +9,25 @@
 
 #include <platform_def.h>
 
+#include <arch_features.h>
 #include <arch_helpers.h>
 #include <common/bl_common.h>
 #include <common/debug.h>
 #include <common/desc_image_load.h>
 #include <drivers/generic_delay_timer.h>
+#include <drivers/partition/partition.h>
 #include <lib/fconf/fconf.h>
 #include <lib/fconf/fconf_dyn_cfg_getter.h>
+#if ENABLE_RME
+#include <lib/gpt_rme/gpt_rme.h>
+#endif /* ENABLE_RME */
 #ifdef SPD_opteed
 #include <lib/optee_utils.h>
 #endif
 #include <lib/utils.h>
+#if ENABLE_RME
+#include <plat/arm/common/arm_pas_def.h>
+#endif /* ENABLE_RME */
 #include <plat/arm/common/plat_arm.h>
 #include <plat/common/platform.h>
 
@@ -40,15 +48,18 @@
 #pragma weak bl2_platform_setup
 #pragma weak bl2_plat_arch_setup
 #pragma weak bl2_plat_sec_mem_layout
-#if MEASURED_BOOT
-#pragma weak bl2_plat_get_hash
-#endif
 
+#if ENABLE_RME
+#define MAP_BL2_TOTAL		MAP_REGION_FLAT(			\
+					bl2_tzram_layout.total_base,	\
+					bl2_tzram_layout.total_size,	\
+					MT_MEMORY | MT_RW | MT_ROOT)
+#else
 #define MAP_BL2_TOTAL		MAP_REGION_FLAT(			\
 					bl2_tzram_layout.total_base,	\
 					bl2_tzram_layout.total_size,	\
 					MT_MEMORY | MT_RW | MT_SECURE)
-
+#endif /* ENABLE_RME */
 
 #pragma weak arm_bl2_plat_handle_post_image_load
 
@@ -70,6 +81,12 @@
 
 	/* Initialise the IO layer and register platform IO devices */
 	plat_arm_io_setup();
+
+	/* Load partition table */
+#if ARM_GPT_SUPPORT
+	partition_init(GPT_IMAGE_ID);
+#endif /* ARM_GPT_SUPPORT */
+
 }
 
 void bl2_early_platform_setup2(u_register_t arg0, u_register_t arg1, u_register_t arg2, u_register_t arg3)
@@ -86,6 +103,11 @@
 void bl2_plat_preload_setup(void)
 {
 	arm_bl2_dyn_cfg_init();
+
+#if ARM_GPT_SUPPORT && !PSA_FWU_SUPPORT
+	/* Always use the FIP from bank 0 */
+	arm_set_fip_addr(0U);
+#endif /* ARM_GPT_SUPPORT && !PSA_FWU_SUPPORT */
 }
 
 /*
@@ -93,8 +115,10 @@
  */
 void arm_bl2_platform_setup(void)
 {
+#if !ENABLE_RME
 	/* Initialize the secure environment */
 	plat_arm_security_setup();
+#endif
 
 #if defined(PLAT_ARM_MEM_PROT_ADDR)
 	arm_nor_psci_do_static_mem_protect();
@@ -106,9 +130,54 @@
 	arm_bl2_platform_setup();
 }
 
+#if ENABLE_RME
+
+static void arm_bl2_plat_gpt_setup(void)
+{
+	/*
+	 * The GPT library might modify the gpt regions structure to optimize
+	 * the layout, so the array cannot be constant.
+	 */
+	pas_region_t pas_regions[] = {
+		ARM_PAS_KERNEL,
+		ARM_PAS_SECURE,
+		ARM_PAS_REALM,
+		ARM_PAS_EL3_DRAM,
+		ARM_PAS_GPTS
+	};
+
+	/* Initialize entire protected space to GPT_GPI_ANY. */
+	if (gpt_init_l0_tables(GPCCR_PPS_4GB, ARM_L0_GPT_ADDR_BASE,
+		ARM_L0_GPT_SIZE) < 0) {
+		ERROR("gpt_init_l0_tables() failed!\n");
+		panic();
+	}
+
+	/* Carve out defined PAS ranges. */
+	if (gpt_init_pas_l1_tables(GPCCR_PGS_4K,
+				   ARM_L1_GPT_ADDR_BASE,
+				   ARM_L1_GPT_SIZE,
+				   pas_regions,
+				   (unsigned int)(sizeof(pas_regions) /
+				   sizeof(pas_region_t))) < 0) {
+		ERROR("gpt_init_pas_l1_tables() failed!\n");
+		panic();
+	}
+
+	INFO("Enabling Granule Protection Checks\n");
+	if (gpt_enable() < 0) {
+		ERROR("gpt_enable() failed!\n");
+		panic();
+	}
+}
+
+#endif /* ENABLE_RME */
+
 /*******************************************************************************
- * Perform the very early platform specific architectural setup here. At the
- * moment this is only initializes the mmu in a quick and dirty way.
+ * Perform the very early platform specific architectural setup here.
+ * When RME is enabled the secure environment is initialised before
+ * initialising and enabling Granule Protection.
+ * This function initialises the MMU in a quick and dirty way.
  ******************************************************************************/
 void arm_bl2_plat_arch_setup(void)
 {
@@ -131,13 +200,29 @@
 		ARM_MAP_BL_COHERENT_RAM,
 #endif
 		ARM_MAP_BL_CONFIG_REGION,
+#if ENABLE_RME
+		ARM_MAP_L0_GPT_REGION,
+#endif
 		{0}
 	};
 
+#if ENABLE_RME
+	/* Initialise the secure environment */
+	plat_arm_security_setup();
+#endif
 	setup_page_tables(bl_regions, plat_arm_get_mmap());
 
 #ifdef __aarch64__
+#if ENABLE_RME
+	/* BL2 runs in EL3 when RME enabled. */
+	assert(get_armv9_2_feat_rme_support() != 0U);
+	enable_mmu_el3(0);
+
+	/* Initialise and enable granule protection after MMU. */
+	arm_bl2_plat_gpt_setup();
+#else
 	enable_mmu_el1(0);
+#endif
 #else
 	enable_mmu_svc_mon(0);
 #endif
@@ -221,7 +306,7 @@
  ******************************************************************************/
 int arm_bl2_plat_handle_post_image_load(unsigned int image_id)
 {
-#if defined(SPD_spmd) && SPMD_SPM_AT_SEL2
+#if defined(SPD_spmd) && BL2_ENABLE_SP_LOAD
 	/* For Secure Partitions we don't need post processing */
 	if ((image_id >= (MAX_NUMBER_IDS - MAX_SP_IDS)) &&
 		(image_id < MAX_NUMBER_IDS)) {
@@ -235,11 +320,3 @@
 {
 	return arm_bl2_plat_handle_post_image_load(image_id);
 }
-
-#if MEASURED_BOOT
-/* Read TCG_DIGEST_SIZE bytes of BL2 hash data */
-void bl2_plat_get_hash(void *data)
-{
-	arm_bl2_get_hash(data);
-}
-#endif
diff --git a/plat/arm/common/arm_bl31_setup.c b/plat/arm/common/arm_bl31_setup.c
index 81ef6e7..a6f7df5 100644
--- a/plat/arm/common/arm_bl31_setup.c
+++ b/plat/arm/common/arm_bl31_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,6 +13,9 @@
 #include <drivers/console.h>
 #include <lib/debugfs.h>
 #include <lib/extensions/ras.h>
+#if ENABLE_RME
+#include <lib/gpt_rme/gpt_rme.h>
+#endif
 #include <lib/mmio.h>
 #include <lib/xlat_tables/xlat_tables_compat.h>
 #include <plat/arm/common/plat_arm.h>
@@ -25,6 +28,9 @@
  */
 static entry_point_info_t bl32_image_ep_info;
 static entry_point_info_t bl33_image_ep_info;
+#if ENABLE_RME
+static entry_point_info_t rmm_image_ep_info;
+#endif
 
 #if !RESET_TO_BL31
 /*
@@ -43,7 +49,7 @@
 #define MAP_BL31_TOTAL		MAP_REGION_FLAT(			\
 					BL31_START,			\
 					BL31_END - BL31_START,		\
-					MT_MEMORY | MT_RW | MT_SECURE)
+					MT_MEMORY | MT_RW | EL3_PAS)
 #if RECLAIM_INIT_CODE
 IMPORT_SYM(unsigned long, __INIT_CODE_START__, BL_INIT_CODE_BASE);
 IMPORT_SYM(unsigned long, __INIT_CODE_END__, BL_CODE_END_UNALIGNED);
@@ -58,7 +64,7 @@
 					BL_INIT_CODE_BASE,		\
 					BL_INIT_CODE_END		\
 						- BL_INIT_CODE_BASE,	\
-					MT_CODE | MT_SECURE)
+					MT_CODE | EL3_PAS)
 #endif
 
 #if SEPARATE_NOBITS_REGION
@@ -66,7 +72,7 @@
 					BL31_NOBITS_BASE,		\
 					BL31_NOBITS_LIMIT 		\
 						- BL31_NOBITS_BASE,	\
-					MT_MEMORY | MT_RW | MT_SECURE)
+					MT_MEMORY | MT_RW | EL3_PAS)
 
 #endif
 /*******************************************************************************
@@ -80,8 +86,18 @@
 	entry_point_info_t *next_image_info;
 
 	assert(sec_state_is_valid(type));
-	next_image_info = (type == NON_SECURE)
-			? &bl33_image_ep_info : &bl32_image_ep_info;
+	if (type == NON_SECURE) {
+		next_image_info = &bl33_image_ep_info;
+	}
+#if ENABLE_RME
+	else if (type == REALM) {
+		next_image_info = &rmm_image_ep_info;
+	}
+#endif
+	else {
+		next_image_info = &bl32_image_ep_info;
+	}
+
 	/*
 	 * None of the images on the ARM development platforms can have 0x0
 	 * as the entrypoint
@@ -148,27 +164,6 @@
 	bl33_image_ep_info.spsr = arm_get_spsr_for_bl33_entry();
 	SET_SECURITY_STATE(bl33_image_ep_info.h.attr, NON_SECURE);
 
-#if defined(SPD_spmd) && !(ARM_LINUX_KERNEL_AS_BL33)
-	/*
-	 * Hafnium in normal world expects its manifest address in x0, which
-	 * is loaded at base of DRAM.
-	 */
-	bl33_image_ep_info.args.arg0 = (u_register_t)ARM_DRAM1_BASE;
-#endif
-
-# if ARM_LINUX_KERNEL_AS_BL33
-	/*
-	 * According to the file ``Documentation/arm64/booting.txt`` of the
-	 * Linux kernel tree, Linux expects the physical address of the device
-	 * tree blob (DTB) in x0, while x1-x3 are reserved for future use and
-	 * must be 0.
-	 */
-	bl33_image_ep_info.args.arg0 = (u_register_t)ARM_PRELOADED_DTB_BASE;
-	bl33_image_ep_info.args.arg1 = 0U;
-	bl33_image_ep_info.args.arg2 = 0U;
-	bl33_image_ep_info.args.arg3 = 0U;
-# endif
-
 #else /* RESET_TO_BL31 */
 
 	/*
@@ -190,22 +185,53 @@
 	bl_params_node_t *bl_params = params_from_bl2->head;
 
 	/*
-	 * Copy BL33 and BL32 (if present), entry point information.
+	 * Copy BL33, BL32 and RMM (if present), entry point information.
 	 * They are stored in Secure RAM, in BL2's address space.
 	 */
 	while (bl_params != NULL) {
-		if (bl_params->image_id == BL32_IMAGE_ID)
+		if (bl_params->image_id == BL32_IMAGE_ID) {
 			bl32_image_ep_info = *bl_params->ep_info;
-
-		if (bl_params->image_id == BL33_IMAGE_ID)
+		}
+#if ENABLE_RME
+		else if (bl_params->image_id == RMM_IMAGE_ID) {
+			rmm_image_ep_info = *bl_params->ep_info;
+		}
+#endif
+		else if (bl_params->image_id == BL33_IMAGE_ID) {
 			bl33_image_ep_info = *bl_params->ep_info;
+		}
 
 		bl_params = bl_params->next_params_info;
 	}
 
 	if (bl33_image_ep_info.pc == 0U)
 		panic();
+#if ENABLE_RME
+	if (rmm_image_ep_info.pc == 0U)
+		panic();
+#endif
 #endif /* RESET_TO_BL31 */
+
+# if ARM_LINUX_KERNEL_AS_BL33
+	/*
+	 * According to the file ``Documentation/arm64/booting.txt`` of the
+	 * Linux kernel tree, Linux expects the physical address of the device
+	 * tree blob (DTB) in x0, while x1-x3 are reserved for future use and
+	 * must be 0.
+	 * Repurpose the option to load Hafnium hypervisor in the normal world.
+	 * It expects its manifest address in x0. This is essentially the linux
+	 * dts (passed to the primary VM) by adding 'hypervisor' and chosen
+	 * nodes specifying the Hypervisor configuration.
+	 */
+#if RESET_TO_BL31
+	bl33_image_ep_info.args.arg0 = (u_register_t)ARM_PRELOADED_DTB_BASE;
+#else
+	bl33_image_ep_info.args.arg0 = (u_register_t)hw_config;
+#endif
+	bl33_image_ep_info.args.arg1 = 0U;
+	bl33_image_ep_info.args.arg2 = 0U;
+	bl33_image_ep_info.args.arg3 = 0U;
+# endif
 }
 
 void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
@@ -355,6 +381,9 @@
 {
 	const mmap_region_t bl_regions[] = {
 		MAP_BL31_TOTAL,
+#if ENABLE_RME
+		ARM_MAP_L0_GPT_REGION,
+#endif
 #if RECLAIM_INIT_CODE
 		MAP_BL_INIT_CODE,
 #endif
@@ -376,6 +405,19 @@
 
 	enable_mmu_el3(0);
 
+#if ENABLE_RME
+	/*
+	 * Initialise Granule Protection library and enable GPC for the primary
+	 * processor. The tables have already been initialized by a previous BL
+	 * stage, so there is no need to provide any PAS here. This function
+	 * sets up pointers to those tables.
+	 */
+	if (gpt_runtime_init() < 0) {
+		ERROR("gpt_runtime_init() failed!\n");
+		panic();
+	}
+#endif /* ENABLE_RME */
+
 	arm_setup_romlib();
 }
 
diff --git a/plat/arm/common/arm_common.c b/plat/arm/common/arm_common.c
index 7d9fd6c..946b732 100644
--- a/plat/arm/common/arm_common.c
+++ b/plat/arm/common/arm_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -151,10 +151,10 @@
 	 */
 	mmio_write_32(ARM_SYS_TIMCTL_BASE + CNTCTLBASE_CNTFRQ, freq_val);
 
-#if defined(PLAT_juno) || defined(PLAT_n1sdp)
+#if defined(PLAT_juno) || defined(PLAT_n1sdp) || defined(PLAT_morello)
 	/*
 	 * Initialize CNTFRQ register in Non-secure CNTBase frame.
-	 * This is only required for Juno and N1SDP, because they do not
+	 * This is required for Juno, N1SDP and Morello because they do not
 	 * follow ARM ARM in that the value updated in CNTFRQ is not
 	 * reflected in CNTBASEN_CNTFRQ. Hence update the value manually.
 	 */
diff --git a/plat/arm/common/arm_common.mk b/plat/arm/common/arm_common.mk
index 74afc53..78efb0f 100644
--- a/plat/arm/common/arm_common.mk
+++ b/plat/arm/common/arm_common.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 ifeq (${ARCH}, aarch64)
   # On ARM standard platorms, the TSP can execute from Trusted SRAM, Trusted
   # DRAM (if available) or the TZC secured area of DRAM.
@@ -52,9 +54,10 @@
 $(eval $(call add_define,ARM_RECOM_STATE_ID_ENC))
 
 # Process ARM_DISABLE_TRUSTED_WDOG flag
-# By default, Trusted Watchdog is always enabled unless SPIN_ON_BL1_EXIT is set
+# By default, Trusted Watchdog is always enabled unless
+# SPIN_ON_BL1_EXIT or ENABLE_RME is set
 ARM_DISABLE_TRUSTED_WDOG	:=	0
-ifeq (${SPIN_ON_BL1_EXIT}, 1)
+ifneq ($(filter 1,${SPIN_ON_BL1_EXIT} ${ENABLE_RME}),)
 ARM_DISABLE_TRUSTED_WDOG	:=	1
 endif
 $(eval $(call assert_boolean,ARM_DISABLE_TRUSTED_WDOG))
@@ -86,11 +89,7 @@
 $(eval $(call add_define,ARM_LINUX_KERNEL_AS_BL33))
 
 ifeq (${ARM_LINUX_KERNEL_AS_BL33},1)
-  ifeq (${ARCH},aarch64)
-    ifneq (${RESET_TO_BL31},1)
-      $(error "ARM_LINUX_KERNEL_AS_BL33 is only available if RESET_TO_BL31=1.")
-    endif
-  else
+  ifneq (${ARCH},aarch64)
     ifneq (${RESET_TO_SP_MIN},1)
       $(error "ARM_LINUX_KERNEL_AS_BL33 is only available if RESET_TO_SP_MIN=1.")
     endif
@@ -98,12 +97,20 @@
   ifndef PRELOADED_BL33_BASE
     $(error "PRELOADED_BL33_BASE must be set if ARM_LINUX_KERNEL_AS_BL33 is used.")
   endif
-  ifndef ARM_PRELOADED_DTB_BASE
-    $(error "ARM_PRELOADED_DTB_BASE must be set if ARM_LINUX_KERNEL_AS_BL33 is used.")
+  ifeq (${RESET_TO_BL31},1)
+    ifndef ARM_PRELOADED_DTB_BASE
+      $(error "ARM_PRELOADED_DTB_BASE must be set if ARM_LINUX_KERNEL_AS_BL33 is
+       used with RESET_TO_BL31.")
+    endif
+    $(eval $(call add_define,ARM_PRELOADED_DTB_BASE))
   endif
-  $(eval $(call add_define,ARM_PRELOADED_DTB_BASE))
 endif
 
+# Arm Ethos-N NPU SiP service
+ARM_ETHOSN_NPU_DRIVER			:=	0
+$(eval $(call assert_boolean,ARM_ETHOSN_NPU_DRIVER))
+$(eval $(call add_define,ARM_ETHOSN_NPU_DRIVER))
+
 # Use an implementation of SHA-256 with a smaller memory footprint but reduced
 # speed.
 $(eval $(call add_define,MBEDTLS_SHA256_SMALLER))
@@ -153,9 +160,9 @@
 $(eval $(call assert_boolean,ARM_CRYPTOCELL_INTEG))
 $(eval $(call add_define,ARM_CRYPTOCELL_INTEG))
 
-# Enable PIE support for RESET_TO_BL31 case
-ifeq (${RESET_TO_BL31},1)
-    ENABLE_PIE			:=	1
+# Enable PIE support for RESET_TO_BL31/RESET_TO_SP_MIN case
+ifneq ($(filter 1,${RESET_TO_BL31} ${RESET_TO_SP_MIN}),)
+	ENABLE_PIE			:=	1
 endif
 
 # CryptoCell integration relies on coherent buffers for passing data from
@@ -166,6 +173,36 @@
     endif
 endif
 
+# Disable GPT parser support, use FIP image by default
+ARM_GPT_SUPPORT			:=	0
+$(eval $(call assert_boolean,ARM_GPT_SUPPORT))
+$(eval $(call add_define,ARM_GPT_SUPPORT))
+
+# Include necessary sources to parse GPT image
+ifeq (${ARM_GPT_SUPPORT}, 1)
+  BL2_SOURCES	+=	drivers/partition/gpt.c		\
+			drivers/partition/partition.c
+endif
+
+# Enable CRC instructions via extension for ARMv8-A CPUs.
+# For ARMv8.1-A, and onwards CRC instructions are default enabled.
+# Enable HW computed CRC support unconditionally in BL2 component.
+ifeq (${ARM_ARCH_MINOR},0)
+  BL2_CPPFLAGS += -march=armv8-a+crc
+endif
+
+ifeq ($(PSA_FWU_SUPPORT),1)
+    # GPT support is recommended as per PSA FWU specification hence
+    # PSA FWU implementation is tightly coupled with GPT support,
+    # and it does not support other formats.
+    ifneq ($(ARM_GPT_SUPPORT),1)
+      $(error For PSA_FWU_SUPPORT, ARM_GPT_SUPPORT must be enabled)
+    endif
+    FWU_MK := drivers/fwu/fwu.mk
+    $(info Including ${FWU_MK})
+    include ${FWU_MK}
+endif
+
 ifeq (${ARCH}, aarch64)
 PLAT_INCLUDES		+=	-Iinclude/plat/arm/common/aarch64
 endif
@@ -175,18 +212,22 @@
 				plat/arm/common/arm_console.c
 
 ifeq (${ARM_XLAT_TABLES_LIB_V1}, 1)
-PLAT_BL_COMMON_SOURCES	+=	lib/xlat_tables/xlat_tables_common.c		\
+PLAT_BL_COMMON_SOURCES 	+=	lib/xlat_tables/xlat_tables_common.c	      \
 				lib/xlat_tables/${ARCH}/xlat_tables.c
 else
+ifeq (${XLAT_MPU_LIB_V1}, 1)
+include lib/xlat_mpu/xlat_mpu.mk
+PLAT_BL_COMMON_SOURCES	+=	${XLAT_MPU_LIB_V1_SRCS}
+else
 include lib/xlat_tables_v2/xlat_tables.mk
-
-PLAT_BL_COMMON_SOURCES	+=	${XLAT_TABLES_LIB_SRCS}
+PLAT_BL_COMMON_SOURCES	+=      ${XLAT_TABLES_LIB_SRCS}
+endif
 endif
 
 ARM_IO_SOURCES		+=	plat/arm/common/arm_io_storage.c		\
 				plat/arm/common/fconf/arm_fconf_io.c
 ifeq (${SPD},spmd)
-    ifeq (${SPMD_SPM_AT_SEL2},1)
+    ifeq (${BL2_ENABLE_SP_LOAD},1)
          ARM_IO_SOURCES		+=	plat/arm/common/fconf/arm_fconf_sp.c
     endif
 endif
@@ -211,17 +252,23 @@
 				drivers/io/io_storage.c				\
 				plat/arm/common/arm_bl2_setup.c			\
 				plat/arm/common/arm_err.c			\
+				common/tf_crc32.c				\
 				${ARM_IO_SOURCES}
 
 # Firmware Configuration Framework sources
 include lib/fconf/fconf.mk
 
+BL1_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+BL2_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+
 # Add `libfdt` and Arm common helpers required for Dynamic Config
 include lib/libfdt/libfdt.mk
 
 DYN_CFG_SOURCES		+=	plat/arm/common/arm_dyn_cfg.c		\
 				plat/arm/common/arm_dyn_cfg_helpers.c	\
-				common/fdt_wrappers.c
+				common/uuid.c
+
+DYN_CFG_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
 
 BL1_SOURCES		+=	${DYN_CFG_SOURCES}
 BL2_SOURCES		+=	${DYN_CFG_SOURCES}
@@ -235,8 +282,10 @@
 ifeq (${JUNO_AARCH32_EL3_RUNTIME},1)
 BL2_SOURCES		+=	plat/arm/common/aarch32/arm_bl2_mem_params_desc.c
 else
+ifeq ($(filter ${TARGET_PLATFORM}, fpga fvp),)
 BL2_SOURCES		+=	plat/arm/common/${ARCH}/arm_bl2_mem_params_desc.c
 endif
+endif
 BL2_SOURCES		+=	plat/arm/common/arm_image_load.c		\
 				common/desc_image_load.c
 ifeq (${SPD},opteed)
@@ -252,14 +301,26 @@
 				plat/arm/common/arm_topology.c			\
 				plat/common/plat_psci_common.c
 
-ifeq (${ENABLE_PMF}, 1)
+ifneq ($(filter 1,${ENABLE_PMF} ${ARM_ETHOSN_NPU_DRIVER}),)
+ARM_SVC_HANDLER_SRCS :=
+
+ifeq (${ENABLE_PMF},1)
+ARM_SVC_HANDLER_SRCS	+=	lib/pmf/pmf_smc.c
+endif
+
+ifeq (${ARM_ETHOSN_NPU_DRIVER},1)
+ARM_SVC_HANDLER_SRCS	+=	plat/arm/common/fconf/fconf_ethosn_getter.c	\
+				drivers/delay_timer/delay_timer.c		\
+				drivers/arm/ethosn/ethosn_smc.c
+endif
+
 ifeq (${ARCH}, aarch64)
 BL31_SOURCES		+=	plat/arm/common/aarch64/execution_state_switch.c\
 				plat/arm/common/arm_sip_svc.c			\
-				lib/pmf/pmf_smc.c
+				${ARM_SVC_HANDLER_SRCS}
 else
 BL32_SOURCES		+=	plat/arm/common/arm_sip_svc.c			\
-				lib/pmf/pmf_smc.c
+				${ARM_SVC_HANDLER_SRCS}
 endif
 endif
 
@@ -288,9 +349,10 @@
 
 ifeq (${SPD},spmd)
 BL31_SOURCES		+=	plat/common/plat_spmd_manifest.c	\
-				common/fdt_wrappers.c			\
+				common/uuid.c				\
 				${LIBFDT_SRCS}
 
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
 endif
 
 ifneq (${TRUSTED_BOARD_BOOT},0)
@@ -303,7 +365,7 @@
 
     # Include the selected chain of trust sources.
     ifeq (${COT},tbbr)
-	BL1_SOURCES     +=      drivers/auth/tbbr/tbbr_cot_common.c		\
+            BL1_SOURCES	+=	drivers/auth/tbbr/tbbr_cot_common.c		\
 				drivers/auth/tbbr/tbbr_cot_bl1.c
         ifneq (${COT_DESC_IN_DTB},0)
             BL2_SOURCES	+=	lib/fconf/fconf_cot_getter.c
@@ -350,7 +412,7 @@
 endif
 
 ifeq (${MEASURED_BOOT},1)
-    MEASURED_BOOT_MK := drivers/measured_boot/measured_boot.mk
+    MEASURED_BOOT_MK := drivers/measured_boot/event_log/event_log.mk
     $(info Including ${MEASURED_BOOT_MK})
     include ${MEASURED_BOOT_MK}
 endif
diff --git a/plat/arm/common/arm_dyn_cfg.c b/plat/arm/common/arm_dyn_cfg.c
index 6b3a611..6aae9ae 100644
--- a/plat/arm/common/arm_dyn_cfg.c
+++ b/plat/arm/common/arm_dyn_cfg.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -15,10 +15,6 @@
 #include <common/tbbr/tbbr_img_def.h>
 #if TRUSTED_BOARD_BOOT
 #include <drivers/auth/mbedtls/mbedtls_config.h>
-#if MEASURED_BOOT
-#include <drivers/auth/crypto_mod.h>
-#include <mbedtls/md.h>
-#endif
 #endif
 #include <lib/fconf/fconf.h>
 #include <lib/fconf/fconf_dyn_cfg_getter.h>
@@ -115,82 +111,13 @@
 		 * images. It's critical because BL2 won't be able to proceed
 		 * without the heap info.
 		 *
-		 * In MEASURED_BOOT case flushing is done in
-		 * arm_bl1_set_bl2_hash() function which is called after heap
-		 * information is written in the DTB.
+		 * In MEASURED_BOOT case flushing is done in a function which
+		 * is called after heap information is written in the DTB.
 		 */
 		flush_dcache_range(tb_fw_cfg_dtb, fdt_totalsize(dtb));
 #endif /* !MEASURED_BOOT */
 	}
 }
-
-#if MEASURED_BOOT
-/*
- * Calculates and writes BL2 hash data to TB_FW_CONFIG DTB.
- * Executed only from BL1.
- */
-void arm_bl1_set_bl2_hash(const image_desc_t *image_desc)
-{
-	unsigned char hash_data[MBEDTLS_MD_MAX_SIZE];
-	const image_info_t image_info = image_desc->image_info;
-	uintptr_t tb_fw_cfg_dtb;
-	int err;
-	const struct dyn_cfg_dtb_info_t *tb_fw_config_info;
-
-	tb_fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, TB_FW_CONFIG_ID);
-	assert(tb_fw_config_info != NULL);
-
-	tb_fw_cfg_dtb = tb_fw_config_info->config_addr;
-
-	/*
-	 * If tb_fw_cfg_dtb==NULL then DTB is not present for the current
-	 * platform. As such, we cannot write to the DTB at all and pass
-	 * measured data.
-	 */
-	if (tb_fw_cfg_dtb == 0UL) {
-		panic();
-	}
-
-	/* Calculate hash */
-	err = crypto_mod_calc_hash(MBEDTLS_MD_ID,
-					(void *)image_info.image_base,
-					image_info.image_size, hash_data);
-	if (err != 0) {
-		ERROR("%scalculate%s\n", "BL1: unable to ",
-						" BL2 hash");
-		panic();
-	}
-
-	err = arm_set_bl2_hash_info((void *)tb_fw_cfg_dtb, hash_data);
-	if (err < 0) {
-		ERROR("%swrite%sdata%s\n", "BL1: unable to ",
-					" BL2 hash ", "to DTB\n");
-		panic();
-	}
-
-	/*
-	 * Ensure that the info written to the DTB is visible to other
-	 * images. It's critical because BL2 won't be able to proceed
-	 * without the heap info and its hash data.
-	 */
-	flush_dcache_range(tb_fw_cfg_dtb, fdt_totalsize((void *)tb_fw_cfg_dtb));
-}
-
-/*
- * Reads TCG_DIGEST_SIZE bytes of BL2 hash data from the DTB.
- * Executed only from BL2.
- */
-void arm_bl2_get_hash(void *data)
-{
-	const void *bl2_hash;
-
-	assert(data != NULL);
-
-	/* Retrieve TCG_DIGEST_SIZE bytes of BL2 hash data from the DTB */
-	bl2_hash = FCONF_GET_PROPERTY(tbbr, dyn_config, bl2_hash_data);
-	(void)memcpy(data, bl2_hash, TCG_DIGEST_SIZE);
-}
-#endif /* MEASURED_BOOT */
 #endif /* TRUSTED_BOARD_BOOT */
 
 /*
@@ -208,10 +135,7 @@
 			HW_CONFIG_ID,
 			SOC_FW_CONFIG_ID,
 			NT_FW_CONFIG_ID,
-#if defined(SPD_tspd) || defined(SPD_spmd)
-			/* tos_fw_config is only present for TSPD/SPMD */
 			TOS_FW_CONFIG_ID
-#endif
 	};
 
 	const struct dyn_cfg_dtb_info_t *dtb_info;
diff --git a/plat/arm/common/arm_dyn_cfg_helpers.c b/plat/arm/common/arm_dyn_cfg_helpers.c
index 5f20c8d..6a2a6f8 100644
--- a/plat/arm/common/arm_dyn_cfg_helpers.c
+++ b/plat/arm/common/arm_dyn_cfg_helpers.c
@@ -11,6 +11,8 @@
 #endif
 #include <common/fdt_wrappers.h>
 
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
 #include <libfdt.h>
 
 #include <plat/arm/common/arm_dyn_cfg_helpers.h>
@@ -20,18 +22,15 @@
 #define DTB_PROP_MBEDTLS_HEAP_SIZE "mbedtls_heap_size"
 
 #if MEASURED_BOOT
-#define DTB_PROP_BL2_HASH_DATA	"bl2_hash_data"
 #ifdef SPD_opteed
 /*
  * Currently OP-TEE does not support reading DTBs from Secure memory
  * and this property should be removed when this feature is supported.
  */
 #define DTB_PROP_HW_SM_LOG_ADDR	"tpm_event_log_sm_addr"
-#endif
+#endif /* SPD_opteed */
 #define DTB_PROP_HW_LOG_ADDR	"tpm_event_log_addr"
 #define DTB_PROP_HW_LOG_SIZE    "tpm_event_log_size"
-
-static int dtb_root = -1;
 #endif /* MEASURED_BOOT */
 
 /*******************************************************************************
@@ -81,9 +80,8 @@
  */
 int arm_set_dtb_mbedtls_heap_info(void *dtb, void *heap_addr, size_t heap_size)
 {
-#if !MEASURED_BOOT
 	int dtb_root;
-#endif
+
 	/*
 	 * Verify that the DTB is valid, before attempting to write to it,
 	 * and get the DTB root node.
@@ -123,32 +121,8 @@
 
 #if MEASURED_BOOT
 /*
- * This function writes the BL2 hash data in HW_FW_CONFIG DTB.
- * When it is called, it is guaranteed that a DTB is available.
- *
- * This function is supposed to be called only by BL1.
- *
- * Returns:
- *	0 = success
- *    < 0 = error
- */
-int arm_set_bl2_hash_info(void *dtb, void *data)
-{
-	assert(dtb_root >= 0);
-
-	/*
-	 * Write the BL2 hash data in the DTB.
-	 */
-	return fdtw_write_inplace_bytes(dtb, dtb_root,
-					DTB_PROP_BL2_HASH_DATA,
-					TCG_DIGEST_SIZE, data);
-}
-
-/*
  * Write the Event Log address and its size in the DTB.
  *
- * This function is supposed to be called only by BL2.
- *
  * Returns:
  *	0 = success
  *    < 0 = error
@@ -231,14 +205,20 @@
  *	0 = success
  *    < 0 = error
  */
-int arm_set_tos_fw_info(uintptr_t config_base, uintptr_t log_addr,
-			size_t log_size)
+int arm_set_tos_fw_info(uintptr_t log_addr, size_t log_size)
 {
+	uintptr_t config_base;
+	const bl_mem_params_node_t *cfg_mem_params;
 	int err;
 
-	assert(config_base != 0UL);
 	assert(log_addr != 0UL);
 
+	/* Get the config load address and size of TOS_FW_CONFIG */
+	cfg_mem_params = get_bl_mem_params_node(TOS_FW_CONFIG_ID);
+	assert(cfg_mem_params != NULL);
+
+	config_base = cfg_mem_params->image_info.image_base;
+
 	/* Write the Event Log address and its size in the DTB */
 	err = arm_set_event_log_info(config_base,
 #ifdef SPD_opteed
@@ -263,23 +243,25 @@
  *	0 = success
  *    < 0 = error
  */
-int arm_set_nt_fw_info(uintptr_t config_base,
+int arm_set_nt_fw_info(
 #ifdef SPD_opteed
 			uintptr_t log_addr,
 #endif
 			size_t log_size, uintptr_t *ns_log_addr)
 {
+	uintptr_t config_base;
 	uintptr_t ns_addr;
 	const bl_mem_params_node_t *cfg_mem_params;
 	int err;
 
-	assert(config_base != 0UL);
 	assert(ns_log_addr != NULL);
 
 	/* Get the config load address and size from NT_FW_CONFIG */
 	cfg_mem_params = get_bl_mem_params_node(NT_FW_CONFIG_ID);
 	assert(cfg_mem_params != NULL);
 
+	config_base = cfg_mem_params->image_info.image_base;
+
 	/* Calculate Event Log address in Non-secure memory */
 	ns_addr = cfg_mem_params->image_info.image_base +
 			cfg_mem_params->image_info.image_max_size;
@@ -300,4 +282,87 @@
 	*ns_log_addr = (err < 0) ? 0UL : ns_addr;
 	return err;
 }
+
+/*
+ * This function writes the Event Log address and its size
+ * in the TB_FW_CONFIG DTB.
+ *
+ * This function is supposed to be called only by BL1.
+ *
+ * Returns:
+ *     0 = success
+ *   < 0 = error
+ */
+int arm_set_tb_fw_info(uintptr_t log_addr, size_t log_size)
+{
+	/*
+	 * Read tb_fw_config device tree for Event Log properties
+	 * and write the Event Log address and its size in the DTB
+	 */
+	const struct dyn_cfg_dtb_info_t *tb_fw_config_info;
+	uintptr_t tb_fw_cfg_dtb;
+	int err;
+
+	tb_fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, TB_FW_CONFIG_ID);
+	assert(tb_fw_config_info != NULL);
+
+	tb_fw_cfg_dtb = tb_fw_config_info->config_addr;
+
+	err = arm_set_event_log_info(tb_fw_cfg_dtb,
+#ifdef SPD_opteed
+				     0UL,
+#endif
+				     log_addr, log_size);
+	return err;
+}
+
+/*
+ * This function reads the Event Log address and its size
+ * properties present in TB_FW_CONFIG DTB.
+ *
+ * This function is supposed to be called only by BL2.
+ *
+ * Returns:
+ *     0 = success
+ *   < 0 = error
+ * Alongside returns Event Log address and its size.
+ */
+
+int arm_get_tb_fw_info(uint64_t *log_addr, size_t *log_size)
+{
+	/* As libfdt uses void *, we can't avoid this cast */
+	const struct dyn_cfg_dtb_info_t *tb_fw_config_info;
+	int node, rc;
+
+	tb_fw_config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, TB_FW_CONFIG_ID);
+	assert(tb_fw_config_info != NULL);
+
+	void *dtb = (void *)tb_fw_config_info->config_addr;
+	const char *compatible = "arm,tpm_event_log";
+
+	/* Assert the node offset point to compatible property */
+	node = fdt_node_offset_by_compatible(dtb, -1, compatible);
+	if (node < 0) {
+		WARN("The compatible property '%s'%s", compatible,
+		     " not specified in TB_FW config.\n");
+		return node;
+	}
+
+	VERBOSE("Dyn cfg: '%s'%s", compatible, " found in the config\n");
+
+	rc = fdt_read_uint64(dtb, node, DTB_PROP_HW_LOG_ADDR, log_addr);
+	if (rc != 0) {
+		ERROR("%s%s", DTB_PROP_HW_LOG_ADDR,
+		      " not specified in TB_FW config.\n");
+		return rc;
+	}
+
+	rc = fdt_read_uint32(dtb, node, DTB_PROP_HW_LOG_SIZE, (uint32_t *)log_size);
+	if (rc != 0) {
+		ERROR("%s%s", DTB_PROP_HW_LOG_SIZE,
+		      " not specified in TB_FW config.\n");
+	}
+
+	return rc;
+}
 #endif /* MEASURED_BOOT */
diff --git a/plat/arm/common/arm_image_load.c b/plat/arm/common/arm_image_load.c
index ed7f1f5..c411c6c 100644
--- a/plat/arm/common/arm_image_load.c
+++ b/plat/arm/common/arm_image_load.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -32,44 +32,42 @@
 		next_bl_params_cpy_ptr);
 }
 
-#if defined(SPD_spmd) && SPMD_SPM_AT_SEL2
+#if defined(SPD_spmd) && BL2_ENABLE_SP_LOAD
 /*******************************************************************************
  * This function appends Secure Partitions to list of loadable images.
  ******************************************************************************/
 static void plat_add_sp_images_load_info(struct bl_load_info *load_info)
 {
-	bl_load_info_node_t *node_info = load_info->head;
-	unsigned int index = 0;
+	bl_load_info_node_t *curr_node = load_info->head;
+	bl_load_info_node_t *prev_node;
 
-	if (sp_mem_params_descs[index].image_id == 0) {
+	/* Shortcut for empty SP list */
+	if (sp_mem_params_descs[0].image_id == 0) {
 		ERROR("No Secure Partition Image available\n");
 		return;
 	}
 
 	/* Traverse through the bl images list */
 	do {
-		node_info = node_info->next_load_info;
-	} while (node_info->next_load_info != NULL);
+		curr_node = curr_node->next_load_info;
+	} while (curr_node->next_load_info != NULL);
 
-	for (; index < MAX_SP_IDS; index++) {
+	prev_node = curr_node;
+
+	for (unsigned int index = 0; index < MAX_SP_IDS; index++) {
+		if (sp_mem_params_descs[index].image_id == 0) {
+			return;
+		}
+		curr_node = &sp_mem_params_descs[index].load_node_mem;
 		/* Populate the image information */
-		node_info->image_id = sp_mem_params_descs[index].image_id;
-		node_info->image_info = &sp_mem_params_descs[index].image_info;
+		curr_node->image_id = sp_mem_params_descs[index].image_id;
+		curr_node->image_info = &sp_mem_params_descs[index].image_info;
 
-		if ((index + 1U) == MAX_SP_IDS) {
-			INFO("Reached Max number of SPs\n");
-			return;
-		}
-
-		if (sp_mem_params_descs[index + 1U].image_id == 0) {
-			return;
-		}
-
-		node_info->next_load_info =
-			&sp_mem_params_descs[index + 1U].load_node_mem;
-		node_info = node_info->next_load_info;
-
+		prev_node->next_load_info = curr_node;
+		prev_node = curr_node;
 	}
+
+	INFO("Reached Max number of SPs\n");
 }
 #endif
 
@@ -78,7 +76,7 @@
  ******************************************************************************/
 struct bl_load_info *plat_get_bl_image_load_info(void)
 {
-#if defined(SPD_spmd) && SPMD_SPM_AT_SEL2
+#if defined(SPD_spmd) && BL2_ENABLE_SP_LOAD
 	bl_load_info_t *bl_load_info;
 
 	bl_load_info = get_bl_load_info_from_mem_params_desc();
diff --git a/plat/arm/common/arm_io_storage.c b/plat/arm/common/arm_io_storage.c
index 34b4101..387086a 100644
--- a/plat/arm/common/arm_io_storage.c
+++ b/plat/arm/common/arm_io_storage.c
@@ -1,14 +1,16 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <common/debug.h>
+#include <drivers/fwu/fwu_metadata.h>
 #include <drivers/io/io_driver.h>
 #include <drivers/io/io_fip.h>
 #include <drivers/io/io_memmap.h>
 #include <drivers/io/io_storage.h>
+#include <drivers/partition/partition.h>
 #include <lib/utils.h>
 
 #include <plat/arm/common/arm_fconf_getter.h>
@@ -23,6 +25,13 @@
 static const io_dev_connector_t *memmap_dev_con;
 uintptr_t memmap_dev_handle;
 
+#if ARM_GPT_SUPPORT
+/* fip partition names */
+static const char * const fip_part_names[] = {"FIP_A", "FIP_B"};
+CASSERT(sizeof(fip_part_names)/sizeof(char *) == NR_OF_FW_BANKS,
+	assert_fip_partition_names_missing);
+#endif /* ARM_GPT_SUPPORT */
+
 /* Weak definitions may be overridden in specific ARM standard platform */
 #pragma weak plat_arm_io_setup
 #pragma weak plat_arm_get_alt_image_source
@@ -136,3 +145,106 @@
 {
 	return (io_dev_init(fip_dev_handle, (uintptr_t)FIP_IMAGE_ID) == 0);
 }
+
+#if ARM_GPT_SUPPORT
+/******************************************************************************
+ * Retrieve partition entry details such as offset and length, and set these
+ * details in the I/O policy of the requested image.
+ *
+ * @image_id: image id whose I/O policy to be updated
+ *
+ * @part_name: partition name whose details to be retrieved
+ *
+ * Returns 0 on success, error otherwise
+ * Alongside, returns device handle and image specification of requested
+ * image.
+ ******************************************************************************/
+int arm_set_image_source(unsigned int image_id, const char *part_name,
+			 uintptr_t *dev_handle, uintptr_t *image_spec)
+{
+	const partition_entry_t *entry = get_partition_entry(part_name);
+
+	if (entry == NULL) {
+		ERROR("Unable to find the %s partition\n", part_name);
+		return -ENOENT;
+	}
+
+	struct plat_io_policy *policy = FCONF_GET_PROPERTY(arm,
+							   io_policies,
+							   image_id);
+
+	assert(policy != NULL);
+	assert(policy->image_spec != 0UL);
+
+	io_block_spec_t *spec = (io_block_spec_t *)policy->image_spec;
+	/* set offset and length of the image */
+	spec->offset = PLAT_ARM_FLASH_IMAGE_BASE + entry->start;
+	spec->length = entry->length;
+
+	*dev_handle = *(policy->dev_handle);
+	*image_spec = policy->image_spec;
+
+	return 0;
+}
+
+/*******************************************************************************
+ * Set the source offset and length of the FIP image in its I/O policy.
+ *
+ * @active_fw_bank_idx: active firmware bank index gathered from FWU metadata.
+ ******************************************************************************/
+void arm_set_fip_addr(uint32_t active_fw_bank_idx)
+{
+	uintptr_t dev_handle __unused;
+	uintptr_t image_spec __unused;
+
+	assert(active_fw_bank_idx < NR_OF_FW_BANKS);
+
+	INFO("Booting with partition %s\n", fip_part_names[active_fw_bank_idx]);
+
+	int result = arm_set_image_source(FIP_IMAGE_ID,
+					  fip_part_names[active_fw_bank_idx],
+					  &dev_handle,
+					  &image_spec);
+	if (result != 0) {
+		panic();
+	}
+}
+#endif /* ARM_GPT_SUPPORT */
+
+#if PSA_FWU_SUPPORT
+/*******************************************************************************
+ * Read the FIP partition of the GPT image corresponding to the active firmware
+ * bank to get its offset and length, and update these details in the I/O policy
+ * of the FIP image.
+ ******************************************************************************/
+void plat_fwu_set_images_source(struct fwu_metadata *metadata)
+{
+	arm_set_fip_addr(metadata->active_index);
+}
+
+/*******************************************************************************
+ * Read the requested FWU metadata partition of the GPT image to get its offset
+ * and length, and update these details in the I/O policy of the requested FWU
+ * metadata image.
+ ******************************************************************************/
+int plat_fwu_set_metadata_image_source(unsigned int image_id,
+				       uintptr_t *dev_handle,
+				       uintptr_t *image_spec)
+{
+	int result = -1;
+
+	if (image_id == FWU_METADATA_IMAGE_ID) {
+		result = arm_set_image_source(FWU_METADATA_IMAGE_ID,
+					      "FWU-Metadata",
+					      dev_handle,
+					      image_spec);
+	} else if (image_id == BKUP_FWU_METADATA_IMAGE_ID) {
+		result = arm_set_image_source(BKUP_FWU_METADATA_IMAGE_ID,
+					      "Bkup-FWU-Metadata",
+					      dev_handle,
+					      image_spec);
+	}
+
+	return result;
+}
+#endif /* PSA_FWU_SUPPORT */
diff --git a/plat/arm/common/arm_sip_svc.c b/plat/arm/common/arm_sip_svc.c
index 9f5d455..6456c78 100644
--- a/plat/arm/common/arm_sip_svc.c
+++ b/plat/arm/common/arm_sip_svc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2019,2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -8,6 +8,7 @@
 
 #include <common/debug.h>
 #include <common/runtime_svc.h>
+#include <drivers/arm/ethosn.h>
 #include <lib/debugfs.h>
 #include <lib/pmf/pmf.h>
 #include <plat/arm/common/arm_sip_svc.h>
@@ -50,6 +51,8 @@
 {
 	int call_count = 0;
 
+#if ENABLE_PMF
+
 	/*
 	 * Dispatch PMF calls to PMF SMC handler and return its return
 	 * value
@@ -59,6 +62,8 @@
 				handle, flags);
 	}
 
+#endif /* ENABLE_PMF */
+
 #if USE_DEBUGFS
 
 	if (is_debugfs_fid(smc_fid)) {
@@ -68,6 +73,15 @@
 
 #endif /* USE_DEBUGFS */
 
+#if ARM_ETHOSN_NPU_DRIVER
+
+	if (is_ethosn_fid(smc_fid)) {
+		return ethosn_smc_handler(smc_fid, x1, x2, x3, x4, cookie,
+					  handle, flags);
+	}
+
+#endif /* ARM_ETHOSN_NPU_DRIVER */
+
 	switch (smc_fid) {
 	case ARM_SIP_SVC_EXE_STATE_SWITCH: {
 		/* Execution state can be switched only if EL3 is AArch64 */
@@ -92,6 +106,11 @@
 		/* PMF calls */
 		call_count += PMF_NUM_SMC_CALLS;
 
+#if ARM_ETHOSN_NPU_DRIVER
+		/* ETHOSN calls */
+		call_count += ETHOSN_NUM_SMC_CALLS;
+#endif /* ARM_ETHOSN_NPU_DRIVER */
+
 		/* State switch call */
 		call_count += 1;
 
diff --git a/plat/arm/common/fconf/arm_fconf_io.c b/plat/arm/common/fconf/arm_fconf_io.c
index 48286c2..aea2f38 100644
--- a/plat/arm/common/fconf/arm_fconf_io.c
+++ b/plat/arm/common/fconf/arm_fconf_io.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,6 +9,7 @@
 #include <common/debug.h>
 #include <common/fdt_wrappers.h>
 #include <drivers/io/io_storage.h>
+#include <drivers/partition/partition.h>
 #include <lib/object_pool.h>
 #include <libfdt.h>
 #include <tools_share/firmware_image_package.h>
@@ -17,11 +18,40 @@
 #include <plat/arm/common/arm_fconf_io_storage.h>
 #include <platform_def.h>
 
-const io_block_spec_t fip_block_spec = {
-	.offset = PLAT_ARM_FIP_BASE,
-	.length = PLAT_ARM_FIP_MAX_SIZE
+#if PSA_FWU_SUPPORT
+/* metadata entry details */
+static io_block_spec_t fwu_metadata_spec;
+#endif /* PSA_FWU_SUPPORT */
+
+io_block_spec_t fip_block_spec = {
+/*
+ * This is fixed FIP address used by BL1, BL2 loads partition table
+ * to get FIP address.
+ */
+#if ARM_GPT_SUPPORT
+	.offset = PLAT_ARM_FLASH_IMAGE_BASE + PLAT_ARM_FIP_OFFSET_IN_GPT,
+#else
+	.offset = PLAT_ARM_FLASH_IMAGE_BASE,
+#endif /* ARM_GPT_SUPPORT */
+	.length = PLAT_ARM_FLASH_IMAGE_MAX_SIZE
 };
 
+#if ARM_GPT_SUPPORT
+static const io_block_spec_t gpt_spec = {
+	.offset         = PLAT_ARM_FLASH_IMAGE_BASE,
+	/*
+	 * PLAT_PARTITION_BLOCK_SIZE = 512
+	 * PLAT_PARTITION_MAX_ENTRIES = 128
+	 * each sector has 4 partition entries, and there are
+	 * 2 reserved sectors i.e. protective MBR and primary
+	 * GPT header hence length gets calculated as,
+	 * length = 512 * (128/4 + 2)
+	 */
+	.length         = PLAT_PARTITION_BLOCK_SIZE *
+			  (PLAT_PARTITION_MAX_ENTRIES / 4 + 2),
+};
+#endif /* ARM_GPT_SUPPORT */
+
 const io_uuid_spec_t arm_uuid_spec[MAX_NUMBER_IDS] = {
 	[BL2_IMAGE_ID] = {UUID_TRUSTED_BOOT_FIRMWARE_BL2},
 	[TB_FW_CONFIG_ID] = {UUID_TB_FW_CONFIG},
@@ -37,6 +67,7 @@
 	[SOC_FW_CONFIG_ID] = {UUID_SOC_FW_CONFIG},
 	[TOS_FW_CONFIG_ID] = {UUID_TOS_FW_CONFIG},
 	[NT_FW_CONFIG_ID] = {UUID_NT_FW_CONFIG},
+	[RMM_IMAGE_ID] = {UUID_REALM_MONITOR_MGMT_FIRMWARE},
 #endif /* ARM_IO_IN_DTB */
 #if TRUSTED_BOARD_BOOT
 	[TRUSTED_BOOT_FW_CERT_ID] = {UUID_TRUSTED_BOOT_FW_CERT},
@@ -60,6 +91,27 @@
 
 /* By default, ARM platforms load images from the FIP */
 struct plat_io_policy policies[MAX_NUMBER_IDS] = {
+#if ARM_GPT_SUPPORT
+	[GPT_IMAGE_ID] = {
+		&memmap_dev_handle,
+		(uintptr_t)&gpt_spec,
+		open_memmap
+	},
+#endif /* ARM_GPT_SUPPORT */
+#if PSA_FWU_SUPPORT
+	[FWU_METADATA_IMAGE_ID] = {
+		&memmap_dev_handle,
+		/* filled runtime from partition information */
+		(uintptr_t)&fwu_metadata_spec,
+		open_memmap
+	},
+	[BKUP_FWU_METADATA_IMAGE_ID] = {
+		&memmap_dev_handle,
+		/* filled runtime from partition information */
+		(uintptr_t)&fwu_metadata_spec,
+		open_memmap
+	},
+#endif /* PSA_FWU_SUPPORT */
 	[FIP_IMAGE_ID] = {
 		&memmap_dev_handle,
 		(uintptr_t)&fip_block_spec,
@@ -111,6 +163,11 @@
 		(uintptr_t)&arm_uuid_spec[BL33_IMAGE_ID],
 		open_fip
 	},
+	[RMM_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&arm_uuid_spec[RMM_IMAGE_ID],
+		open_fip
+	},
 	[HW_CONFIG_ID] = {
 		&fip_dev_handle,
 		(uintptr_t)&arm_uuid_spec[HW_CONFIG_ID],
@@ -249,7 +306,6 @@
 {
 	int err, node;
 	unsigned int i;
-	unsigned int j;
 
 	union uuid_helper_t uuid_helper;
 	io_uuid_spec_t *uuid_ptr;
@@ -268,26 +324,26 @@
 	/* Locate the uuid cells and read the value for all the load info uuid */
 	for (i = 0; i < FCONF_ARM_IO_UUID_NUMBER; i++) {
 		uuid_ptr = pool_alloc(&fconf_arm_uuids_pool);
-		err = fdt_read_uint32_array(dtb, node, load_info[i].name,
-					    4, uuid_helper.word);
+		err = fdtw_read_uuid(dtb, node, load_info[i].name, 16,
+				     (uint8_t *)&uuid_helper);
 		if (err < 0) {
 			WARN("FCONF: Read cell failed for %s\n", load_info[i].name);
 			return err;
 		}
 
-		/* Convert uuid from big endian to little endian */
-		for (j = 0U; j < 4U; j++) {
-			uuid_helper.word[j] =
-				((uuid_helper.word[j] >> 24U) & 0xff) |
-				((uuid_helper.word[j] << 8U) & 0xff0000) |
-				((uuid_helper.word[j] >> 8U) & 0xff00) |
-				((uuid_helper.word[j] << 24U) & 0xff000000);
-		}
-
-		VERBOSE("FCONF: arm-io_policies.%s cell found with value = 0x%x 0x%x 0x%x 0x%x\n",
+		VERBOSE("FCONF: arm-io_policies.%s cell found with value = "
+			"%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x\n",
 			load_info[i].name,
-			uuid_helper.word[0], uuid_helper.word[1],
-			uuid_helper.word[2], uuid_helper.word[3]);
+			uuid_helper.uuid_struct.time_low[0], uuid_helper.uuid_struct.time_low[1],
+			uuid_helper.uuid_struct.time_low[2], uuid_helper.uuid_struct.time_low[3],
+			uuid_helper.uuid_struct.time_mid[0], uuid_helper.uuid_struct.time_mid[1],
+			uuid_helper.uuid_struct.time_hi_and_version[0],
+			uuid_helper.uuid_struct.time_hi_and_version[1],
+			uuid_helper.uuid_struct.clock_seq_hi_and_reserved,
+			uuid_helper.uuid_struct.clock_seq_low,
+			uuid_helper.uuid_struct.node[0], uuid_helper.uuid_struct.node[1],
+			uuid_helper.uuid_struct.node[2], uuid_helper.uuid_struct.node[3],
+			uuid_helper.uuid_struct.node[4], uuid_helper.uuid_struct.node[5]);
 
 		uuid_ptr->uuid = uuid_helper.uuid_struct;
 		policies[load_info[i].image_id].image_spec = (uintptr_t)uuid_ptr;
diff --git a/plat/arm/common/fconf/arm_fconf_sp.c b/plat/arm/common/fconf/arm_fconf_sp.c
index 7950e7f..552393c 100644
--- a/plat/arm/common/fconf/arm_fconf_sp.c
+++ b/plat/arm/common/fconf/arm_fconf_sp.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -37,7 +37,6 @@
 	const unsigned int plat_start = SP_PKG5_ID;
 	unsigned int plat_index = plat_start;
 	const unsigned int plat_end = plat_start + MAX_SP_IDS / 2;
-	unsigned int j;
 
 	/* As libfdt use void *, we can't avoid this cast */
 	const void *dtb = (void *)config;
@@ -59,29 +58,28 @@
 		}
 
 		/* Read UUID */
-		err = fdt_read_uint32_array(dtb, sp_node, "uuid", 4,
-					    uuid_helper.word);
+		err = fdtw_read_uuid(dtb, sp_node, "uuid", 16,
+				     (uint8_t *)&uuid_helper);
 		if (err < 0) {
 			ERROR("FCONF: cannot read SP uuid\n");
 			return -1;
 		}
 
-		/* Convert uuid from big endian to little endian */
-		for (j = 0U; j < 4U; j++) {
-			uuid_helper.word[j] =
-				((uuid_helper.word[j] >> 24U) & 0xff) |
-				((uuid_helper.word[j] << 8U) & 0xff0000) |
-				((uuid_helper.word[j] >> 8U) & 0xff00) |
-				((uuid_helper.word[j] << 24U) & 0xff000000);
-		}
-
 		arm_sp.uuids[index] = uuid_helper;
-		VERBOSE("FCONF: %s UUID %x-%x-%x-%x load_addr=%lx\n",
+		VERBOSE("FCONF: %s UUID"
+			" %02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x"
+			" load_addr=%lx\n",
 			__func__,
-			uuid_helper.word[0],
-			uuid_helper.word[1],
-			uuid_helper.word[2],
-			uuid_helper.word[3],
+			uuid_helper.uuid_struct.time_low[0], uuid_helper.uuid_struct.time_low[1],
+			uuid_helper.uuid_struct.time_low[2], uuid_helper.uuid_struct.time_low[3],
+			uuid_helper.uuid_struct.time_mid[0], uuid_helper.uuid_struct.time_mid[1],
+			uuid_helper.uuid_struct.time_hi_and_version[0],
+			uuid_helper.uuid_struct.time_hi_and_version[1],
+			uuid_helper.uuid_struct.clock_seq_hi_and_reserved,
+			uuid_helper.uuid_struct.clock_seq_low,
+			uuid_helper.uuid_struct.node[0], uuid_helper.uuid_struct.node[1],
+			uuid_helper.uuid_struct.node[2], uuid_helper.uuid_struct.node[3],
+			uuid_helper.uuid_struct.node[4], uuid_helper.uuid_struct.node[5],
 			arm_sp.load_addr[index]);
 
 		/* Read Load address */
diff --git a/plat/arm/common/fconf/fconf_ethosn_getter.c b/plat/arm/common/fconf/fconf_ethosn_getter.c
new file mode 100644
index 0000000..0af1a20
--- /dev/null
+++ b/plat/arm/common/fconf/fconf_ethosn_getter.c
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <common/fdt_wrappers.h>
+#include <libfdt.h>
+#include <plat/arm/common/fconf_ethosn_getter.h>
+
+struct ethosn_config_t ethosn_config = {.num_cores = 0};
+
+static uint8_t fdt_node_get_status(const void *fdt, int node)
+{
+	int len;
+	uint8_t status = ETHOSN_STATUS_DISABLED;
+	const char *node_status;
+
+	node_status = fdt_getprop(fdt, node, "status", &len);
+	if (node_status == NULL ||
+	    (len == 5 && /* Includes null character */
+	     strncmp(node_status, "okay", 4U) == 0)) {
+		status = ETHOSN_STATUS_ENABLED;
+	}
+
+	return status;
+}
+
+int fconf_populate_ethosn_config(uintptr_t config)
+{
+	int ethosn_node;
+	const void *hw_conf_dtb = (const void *)config;
+
+	/* Find offset to node with 'ethosn' compatible property */
+	INFO("Probing Arm Ethos-N NPU\n");
+	uint32_t total_core_count = 0U;
+
+	fdt_for_each_compatible_node(hw_conf_dtb, ethosn_node, "ethosn") {
+		int sub_node;
+		uint8_t ethosn_status;
+		uint32_t device_core_count = 0U;
+
+		/* If the Arm Ethos-N NPU is disabled the core check can be skipped */
+		ethosn_status = fdt_node_get_status(hw_conf_dtb, ethosn_node);
+		if (ethosn_status == ETHOSN_STATUS_DISABLED) {
+			continue;
+		}
+
+		fdt_for_each_subnode(sub_node, hw_conf_dtb, ethosn_node) {
+			int err;
+			uintptr_t core_addr;
+			uint8_t core_status;
+
+			if (total_core_count >= ETHOSN_CORE_NUM_MAX) {
+				ERROR("FCONF: Reached max number of Arm Ethos-N NPU cores\n");
+				return -FDT_ERR_BADSTRUCTURE;
+			}
+
+			/* Check that the sub node is "ethosn-core" compatible */
+			if (fdt_node_check_compatible(hw_conf_dtb,
+						      sub_node,
+						      "ethosn-core") != 0) {
+				/* Ignore incompatible sub node */
+				continue;
+			}
+
+			core_status = fdt_node_get_status(hw_conf_dtb, sub_node);
+			if (core_status == ETHOSN_STATUS_DISABLED) {
+				continue;
+			}
+
+			err = fdt_get_reg_props_by_index(hw_conf_dtb,
+							 ethosn_node,
+							 device_core_count,
+							 &core_addr,
+							 NULL);
+			if (err < 0) {
+				ERROR(
+				"FCONF: Failed to read reg property for Arm Ethos-N NPU core %u\n",
+						device_core_count);
+				return err;
+			}
+
+			INFO("NPU core probed at address 0x%lx\n", core_addr);
+			ethosn_config.core[total_core_count].addr = core_addr;
+			total_core_count++;
+			device_core_count++;
+		}
+
+		if ((sub_node < 0) && (sub_node != -FDT_ERR_NOTFOUND)) {
+			ERROR("FCONF: Failed to parse sub nodes\n");
+			return -FDT_ERR_BADSTRUCTURE;
+		}
+
+		if (device_core_count == 0U) {
+			ERROR(
+			"FCONF: Enabled Arm Ethos-N NPU device must have at least one enabled core\n");
+			return -FDT_ERR_BADSTRUCTURE;
+		}
+	}
+
+	if (total_core_count == 0U) {
+		ERROR("FCONF: Can't find 'ethosn' compatible node in dtb\n");
+		return -FDT_ERR_BADSTRUCTURE;
+	}
+
+	ethosn_config.num_cores = total_core_count;
+
+	INFO("%d NPU core%s probed\n",
+	     ethosn_config.num_cores,
+	     ethosn_config.num_cores > 1 ? "s" : "");
+
+	return 0;
+}
+
+FCONF_REGISTER_POPULATOR(HW_CONFIG, ethosn_config, fconf_populate_ethosn_config);
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 270093c..f15c137 100644
--- a/plat/arm/common/sp_min/arm_sp_min_setup.c
+++ b/plat/arm/common/sp_min/arm_sp_min_setup.c
@@ -32,7 +32,9 @@
  * Check that BL32_BASE is above ARM_FW_CONFIG_LIMIT. The reserved page
  * is required for SOC_FW_CONFIG/TOS_FW_CONFIG passed from BL2.
  */
+#if !RESET_TO_SP_MIN
 CASSERT(BL32_BASE >= ARM_FW_CONFIG_LIMIT, assert_bl32_base_overflows);
+#endif
 
 /*******************************************************************************
  * Return a pointer to the 'entry_point_info' structure of the next image for the
diff --git a/plat/arm/common/trp/arm_trp.mk b/plat/arm/common/trp/arm_trp.mk
new file mode 100644
index 0000000..997111f
--- /dev/null
+++ b/plat/arm/common/trp/arm_trp.mk
@@ -0,0 +1,10 @@
+#
+# Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# TRP source files common to ARM standard platforms
+RMM_SOURCES		+=	plat/arm/common/trp/arm_trp_setup.c	\
+				plat/arm/common/arm_topology.c		\
+				plat/common/aarch64/platform_mp_stack.S
diff --git a/plat/arm/common/trp/arm_trp_setup.c b/plat/arm/common/trp/arm_trp_setup.c
new file mode 100644
index 0000000..8e48293
--- /dev/null
+++ b/plat/arm/common/trp/arm_trp_setup.c
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/arm/pl011.h>
+#include <drivers/console.h>
+#include <plat/arm/common/plat_arm.h>
+#include <platform_def.h>
+
+/*******************************************************************************
+ * Initialize the UART
+ ******************************************************************************/
+static console_t arm_trp_runtime_console;
+
+void arm_trp_early_platform_setup(void)
+{
+	/*
+	 * Initialize a different console than already in use to display
+	 * messages from trp
+	 */
+	int rc = console_pl011_register(PLAT_ARM_TRP_UART_BASE,
+					PLAT_ARM_TRP_UART_CLK_IN_HZ,
+					ARM_CONSOLE_BAUDRATE,
+					&arm_trp_runtime_console);
+	if (rc == 0) {
+		panic();
+	}
+
+	console_set_scope(&arm_trp_runtime_console,
+			  CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME);
+}
+
+void trp_early_platform_setup(void)
+{
+	arm_trp_early_platform_setup();
+}
diff --git a/plat/arm/css/common/css_pm.c b/plat/arm/css/common/css_pm.c
index 8e74526..926b8ec 100644
--- a/plat/arm/css/common/css_pm.c
+++ b/plat/arm/css/common/css_pm.c
@@ -123,6 +123,9 @@
 	/* Prevent interrupts from spuriously waking up this cpu */
 	plat_arm_gic_cpuif_disable();
 
+	/* Turn redistributor off */
+	plat_arm_gic_redistif_off();
+
 	/* Cluster is to be turned off, so disable coherency */
 	if (CSS_CLUSTER_PWR_STATE(target_state) == ARM_LOCAL_STATE_OFF) {
 		plat_arm_interconnect_exit_coherency();
diff --git a/plat/arm/css/sgi/aarch64/sgi_helper.S b/plat/arm/css/sgi/aarch64/sgi_helper.S
index 04bfb77..ced59e8 100644
--- a/plat/arm/css/sgi/aarch64/sgi_helper.S
+++ b/plat/arm/css/sgi/aarch64/sgi_helper.S
@@ -9,6 +9,8 @@
 #include <platform_def.h>
 #include <cortex_a75.h>
 #include <neoverse_n1.h>
+#include <neoverse_v1.h>
+#include <neoverse_n2.h>
 #include <cpu_macros.S>
 
 	.globl	plat_arm_calc_core_pos
@@ -66,6 +68,8 @@
 func plat_reset_handler
 	jump_if_cpu_midr CORTEX_A75_MIDR, A75
 	jump_if_cpu_midr NEOVERSE_N1_MIDR, N1
+	jump_if_cpu_midr NEOVERSE_V1_MIDR, V1
+	jump_if_cpu_midr NEOVERSE_N2_MIDR, N2
 	ret
 
 	/* -----------------------------------------------------
@@ -85,4 +89,18 @@
 	msr	NEOVERSE_N1_CPUPWRCTLR_EL1, x0
 	isb
 	ret
+
+V1:
+	mrs	x0, NEOVERSE_V1_CPUPWRCTLR_EL1
+	bic	x0, x0, #NEOVERSE_V1_CPUPWRCTLR_EL1_CORE_PWRDN_BIT
+	msr	NEOVERSE_V1_CPUPWRCTLR_EL1, x0
+	isb
+	ret
+
+N2:
+	mrs	x0, NEOVERSE_N2_CPUPWRCTLR_EL1
+	bic	x0, x0, #NEOVERSE_N2_CORE_PWRDN_EN_BIT
+	msr	NEOVERSE_N2_CPUPWRCTLR_EL1, x0
+	isb
+	ret
 endfunc plat_reset_handler
diff --git a/plat/arm/css/sgi/include/sgi_base_platform_def.h b/plat/arm/css/sgi/include/sgi_base_platform_def.h
index 159084f..c9c8c04 100644
--- a/plat/arm/css/sgi/include/sgi_base_platform_def.h
+++ b/plat/arm/css/sgi/include/sgi_base_platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,12 +9,9 @@
 
 #include <lib/utils_def.h>
 #include <lib/xlat_tables/xlat_tables_defs.h>
-#include <plat/arm/board/common/board_css_def.h>
-#include <plat/arm/board/common/v2m_def.h>
 #include <plat/arm/common/arm_def.h>
 #include <plat/arm/common/arm_spm_def.h>
 #include <plat/arm/css/common/css_def.h>
-#include <plat/arm/soc/common/soc_css_def.h>
 #include <plat/common/common_def.h>
 
 #define PLATFORM_CORE_COUNT		(CSS_SGI_CHIP_COUNT *		\
@@ -29,14 +26,17 @@
 
 /*
  * PLAT_ARM_MMAP_ENTRIES depends on the number of entries in the
- * plat_arm_mmap array defined for each BL stage.
+ * plat_arm_mmap array defined for each BL stage. In addition to that, on
+ * multi-chip platforms, address regions on each of the remote chips are
+ * also mapped. In BL31, for instance, three address regions on the remote
+ * chips are accessed - secure ram, css device and soc device regions.
  */
 #if defined(IMAGE_BL31)
 # if SPM_MM
-#  define PLAT_ARM_MMAP_ENTRIES		9
-#  define MAX_XLAT_TABLES		7
-#  define PLAT_SP_IMAGE_MMAP_REGIONS	7
-#  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	10
+#  define PLAT_ARM_MMAP_ENTRIES		(9  + ((CSS_SGI_CHIP_COUNT - 1) * 3))
+#  define MAX_XLAT_TABLES		(7  + ((CSS_SGI_CHIP_COUNT - 1) * 3))
+#  define PLAT_SP_IMAGE_MMAP_REGIONS	9
+#  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	11
 # else
 #  define PLAT_ARM_MMAP_ENTRIES		(5 + ((CSS_SGI_CHIP_COUNT - 1) * 3))
 #  define MAX_XLAT_TABLES		(6 + ((CSS_SGI_CHIP_COUNT - 1) * 3))
@@ -44,6 +44,17 @@
 #elif defined(IMAGE_BL32)
 # define PLAT_ARM_MMAP_ENTRIES		8
 # define MAX_XLAT_TABLES		5
+#elif defined(IMAGE_BL2)
+# define PLAT_ARM_MMAP_ENTRIES		(11 + (CSS_SGI_CHIP_COUNT - 1))
+
+/*
+ * MAX_XLAT_TABLES entries need to be doubled because when the address width
+ * exceeds 40 bits an additional level of translation is required. In case of
+ * multichip platforms peripherals also fall into address space with width
+ * > 40 bits
+ *
+ */
+# define MAX_XLAT_TABLES		(7  + ((CSS_SGI_CHIP_COUNT - 1) * 2))
 #elif !USE_ROMLIB
 # define PLAT_ARM_MMAP_ENTRIES		11
 # define MAX_XLAT_TABLES		7
@@ -72,12 +83,17 @@
 
 /*
  * PLAT_ARM_MAX_BL2_SIZE is calculated using the current BL2 debug size plus a
- * little space for growth.
+ * little space for growth. Additional 8KiB space is added per chip in
+ * order to accommodate the additional level of translation required for "TZC"
+ * peripheral access which lies in >4TB address space.
+ *
  */
 #if TRUSTED_BOARD_BOOT
-# define PLAT_ARM_MAX_BL2_SIZE		0x1D000
+# define PLAT_ARM_MAX_BL2_SIZE		(0x20000 + ((CSS_SGI_CHIP_COUNT - 1) * \
+							0x2000))
 #else
-# define PLAT_ARM_MAX_BL2_SIZE		0x14000
+# define PLAT_ARM_MAX_BL2_SIZE		(0x14000 + ((CSS_SGI_CHIP_COUNT - 1) * \
+							0x2000))
 #endif
 
 /*
@@ -168,48 +184,36 @@
 
 #define PLAT_SP_PRI				PLAT_RAS_PRI
 
-#if RAS_EXTENSION
-/* Allocate 128KB for CPER buffers */
-#define PLAT_SP_BUF_BASE			ULL(0x20000)
-
-#define PLAT_ARM_SP_IMAGE_STACK_BASE		(PLAT_SP_IMAGE_NS_BUF_BASE + \
-						PLAT_SP_IMAGE_NS_BUF_SIZE + \
-						PLAT_SP_BUF_BASE)
-
-/* Platform specific SMC FID's used for RAS */
-#define SP_DMC_ERROR_INJECT_EVENT_AARCH64	0xC4000042
-#define SP_DMC_ERROR_INJECT_EVENT_AARCH32	0x84000042
-
-#define SP_DMC_ERROR_OVERFLOW_EVENT_AARCH64	0xC4000043
-#define SP_DMC_ERROR_OVERFLOW_EVENT_AARCH32	0x84000043
-
-#define SP_DMC_ERROR_ECC_EVENT_AARCH64		0xC4000044
-#define SP_DMC_ERROR_ECC_EVENT_AARCH32		0x84000044
-
-/* ARM SDEI dynamic shared event numbers */
-#define SGI_SDEI_DS_EVENT_0			804
-#define SGI_SDEI_DS_EVENT_1			805
-
-#define PLAT_ARM_PRIVATE_SDEI_EVENTS	\
-	SDEI_DEFINE_EVENT_0(ARM_SDEI_SGI), \
-	SDEI_EXPLICIT_EVENT(SGI_SDEI_DS_EVENT_0, SDEI_MAPF_CRITICAL), \
-	SDEI_EXPLICIT_EVENT(SGI_SDEI_DS_EVENT_1, SDEI_MAPF_CRITICAL),
-#define PLAT_ARM_SHARED_SDEI_EVENTS
-
-#define ARM_SP_CPER_BUF_BASE			(PLAT_SP_IMAGE_NS_BUF_BASE + \
-						PLAT_SP_IMAGE_NS_BUF_SIZE)
-#define ARM_SP_CPER_BUF_SIZE			ULL(0x20000)
-#define ARM_SP_CPER_BUF_MMAP			MAP_REGION2(		\
-						ARM_SP_CPER_BUF_BASE,	\
-						ARM_SP_CPER_BUF_BASE,	\
-						ARM_SP_CPER_BUF_SIZE,	\
-						MT_RW_DATA | MT_NS | MT_USER, \
+#if SPM_MM && RAS_EXTENSION
+/*
+ * CPER buffer memory of 128KB is reserved and it is placed adjacent to the
+ * memory shared between EL3 and S-EL0.
+ */
+#define CSS_SGI_SP_CPER_BUF_BASE	(PLAT_SP_IMAGE_NS_BUF_BASE + \
+					 PLAT_SP_IMAGE_NS_BUF_SIZE)
+#define CSS_SGI_SP_CPER_BUF_SIZE	ULL(0x20000)
+#define CSS_SGI_SP_CPER_BUF_MMAP	MAP_REGION2(			       \
+						CSS_SGI_SP_CPER_BUF_BASE,      \
+						CSS_SGI_SP_CPER_BUF_BASE,      \
+						CSS_SGI_SP_CPER_BUF_SIZE,      \
+						MT_RW_DATA | MT_NS | MT_USER,  \
 						PAGE_SIZE)
 
-#else
+/*
+ * Secure partition stack follows right after the memory space reserved for
+ * CPER buffer memory.
+ */
+#define PLAT_ARM_SP_IMAGE_STACK_BASE		(PLAT_SP_IMAGE_NS_BUF_BASE +   \
+						 PLAT_SP_IMAGE_NS_BUF_SIZE +   \
+						 CSS_SGI_SP_CPER_BUF_SIZE)
+#elif SPM_MM
+/*
+ * Secure partition stack follows right after the memory region that is shared
+ * between EL3 and S-EL0.
+ */
 #define PLAT_ARM_SP_IMAGE_STACK_BASE	(PLAT_SP_IMAGE_NS_BUF_BASE +	\
 					 PLAT_SP_IMAGE_NS_BUF_SIZE)
-#endif /* RAS_EXTENSION */
+#endif /* SPM_MM && RAS_EXTENSION */
 
 /* Platform ID address */
 #define SSC_VERSION                     (SSC_REG_BASE + SSC_VERSION_OFFSET)
@@ -241,4 +245,17 @@
 /* Number of SCMI channels on the platform */
 #define PLAT_ARM_SCMI_CHANNEL_COUNT	CSS_SGI_CHIP_COUNT
 
+/*
+ * Mapping definition of the TrustZone Controller for ARM SGI/RD platforms
+ * where both the DRAM regions are marked for non-secure access. This applies
+ * to multi-chip platforms.
+ */
+#define SGI_PLAT_TZC_NS_REMOTE_REGIONS_DEF(n)				\
+	{CSS_SGI_REMOTE_CHIP_MEM_OFFSET(n) + ARM_DRAM1_BASE,		\
+		CSS_SGI_REMOTE_CHIP_MEM_OFFSET(n) + ARM_DRAM1_END,	\
+		ARM_TZC_NS_DRAM_S_ACCESS, PLAT_ARM_TZC_NS_DEV_ACCESS},	\
+	{CSS_SGI_REMOTE_CHIP_MEM_OFFSET(n) + ARM_DRAM2_BASE,		\
+		CSS_SGI_REMOTE_CHIP_MEM_OFFSET(n) + ARM_DRAM2_END,	\
+		ARM_TZC_NS_DRAM_S_ACCESS, PLAT_ARM_TZC_NS_DEV_ACCESS}
+
 #endif /* SGI_BASE_PLATFORM_DEF_H */
diff --git a/plat/arm/css/sgi/include/sgi_dmc620_tzc_regions.h b/plat/arm/css/sgi/include/sgi_dmc620_tzc_regions.h
new file mode 100644
index 0000000..e939163
--- /dev/null
+++ b/plat/arm/css/sgi/include/sgi_dmc620_tzc_regions.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SGI_DMC620_TZC_REGIONS_H
+#define SGI_DMC620_TZC_REGIONS_H
+
+#include <drivers/arm/tzc_dmc620.h>
+
+#if SPM_MM
+#define CSS_SGI_DMC620_TZC_REGIONS_DEF				\
+	{							\
+		.region_base = ARM_AP_TZC_DRAM1_BASE,		\
+		.region_top = PLAT_SP_IMAGE_NS_BUF_BASE - 1,	\
+		.sec_attr = TZC_DMC620_REGION_S_RDWR		\
+	}, {							\
+		.region_base = PLAT_SP_IMAGE_NS_BUF_BASE,	\
+		.region_top = PLAT_ARM_SP_IMAGE_STACK_BASE - 1,	\
+		.sec_attr = TZC_DMC620_REGION_S_NS_RDWR		\
+	}, {							\
+		.region_base = PLAT_ARM_SP_IMAGE_STACK_BASE,	\
+		.region_top = ARM_AP_TZC_DRAM1_END,		\
+		.sec_attr = TZC_DMC620_REGION_S_RDWR		\
+	}
+#else
+#define CSS_SGI_DMC620_TZC_REGIONS_DEF				\
+	{							\
+		.region_base = ARM_AP_TZC_DRAM1_BASE,		\
+		.region_top = ARM_AP_TZC_DRAM1_END,		\
+		.sec_attr = TZC_DMC620_REGION_S_RDWR		\
+	}
+#endif /* SPM_MM */
+
+#endif /* SGI_DMC620_TZC_REGIONS_H */
diff --git a/plat/arm/css/sgi/include/sgi_ras.h b/plat/arm/css/sgi/include/sgi_ras.h
index a449eae..e69a684 100644
--- a/plat/arm/css/sgi/include/sgi_ras.h
+++ b/plat/arm/css/sgi/include/sgi_ras.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -12,7 +12,6 @@
  * id used with Standalone MM code
  */
 struct sgi_ras_ev_map {
-	int ras_ev_num;		/* RAS Event number */
 	int sdei_ev_num;	/* SDEI Event number */
 	int intr;		/* Physical intr number */
 };
diff --git a/plat/arm/css/sgi/include/sgi_sdei.h b/plat/arm/css/sgi/include/sgi_sdei.h
new file mode 100644
index 0000000..f380122
--- /dev/null
+++ b/plat/arm/css/sgi/include/sgi_sdei.h
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SGI_SDEI_H
+#define SGI_SDEI_H
+
+#if SDEI_SUPPORT
+
+/* ARM SDEI dynamic shared event numbers */
+#define SGI_SDEI_DS_EVENT_0		U(804)
+#define SGI_SDEI_DS_EVENT_1		U(805)
+
+#define PLAT_ARM_PRIVATE_SDEI_EVENTS					      \
+		SDEI_DEFINE_EVENT_0(ARM_SDEI_SGI),			      \
+		SDEI_EXPLICIT_EVENT(SGI_SDEI_DS_EVENT_0, SDEI_MAPF_CRITICAL), \
+		SDEI_EXPLICIT_EVENT(SGI_SDEI_DS_EVENT_1, SDEI_MAPF_CRITICAL),
+
+#define PLAT_ARM_SHARED_SDEI_EVENTS
+
+#endif /* SDEI_SUPPORT */
+
+#endif /* SGI_SDEI_H */
diff --git a/plat/arm/css/sgi/include/sgi_soc_css_def_v2.h b/plat/arm/css/sgi/include/sgi_soc_css_def_v2.h
new file mode 100644
index 0000000..bebc597
--- /dev/null
+++ b/plat/arm/css/sgi/include/sgi_soc_css_def_v2.h
@@ -0,0 +1,216 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SGI_SOC_CSS_DEF_V2_H
+#define SGI_SOC_CSS_DEF_V2_H
+
+#include <lib/utils_def.h>
+#include <plat/common/common_def.h>
+
+/*
+ * Definitions common to all ARM CSS SoCs
+ */
+
+/* Following covers ARM CSS SoC Peripherals */
+
+#define SOC_SYSTEM_PERIPH_BASE		UL(0x0C000000)
+#define SOC_SYSTEM_PERIPH_SIZE		UL(0x02000000)
+
+#define SOC_PLATFORM_PERIPH_BASE	UL(0x0E000000)
+#define SOC_PLATFORM_PERIPH_SIZE	UL(0x02000000)
+
+#define SOC_CSS_PCIE_CONTROL_BASE	UL(0x0ef20000)
+
+/* PL011 UART related constants */
+#define SOC_CSS_UART1_BASE		UL(0x0ef80000)
+#define SOC_CSS_UART0_BASE		UL(0x0ef70000)
+
+/* Memory controller */
+#define SOC_MEMCNTRL_BASE		UL(0x10000000)
+#define SOC_MEMCNTRL_SIZE		UL(0x10000000)
+
+#define SOC_CSS_UART0_CLK_IN_HZ		UL(7372800)
+#define SOC_CSS_UART1_CLK_IN_HZ		UL(7372800)
+
+/* SoC NIC-400 Global Programmers View (GPV) */
+#define SOC_CSS_NIC400_BASE		UL(0x0ED00000)
+
+#define SOC_CSS_NIC400_USB_EHCI		U(0)
+#define SOC_CSS_NIC400_TLX_MASTER	U(1)
+#define SOC_CSS_NIC400_USB_OHCI		U(2)
+#define SOC_CSS_NIC400_PL354_SMC	U(3)
+/*
+ * The apb4_bridge controls access to:
+ *   - the PCIe configuration registers
+ *   - the MMU units for USB, HDLCD and DMA
+ */
+#define SOC_CSS_NIC400_APB4_BRIDGE	U(4)
+
+/* Non-volatile counters */
+#define SOC_TRUSTED_NVCTR_BASE		UL(0x0EE70000)
+#define TFW_NVCTR_BASE			(SOC_TRUSTED_NVCTR_BASE + 0x0000)
+#define TFW_NVCTR_SIZE			U(4)
+#define NTFW_CTR_BASE			(SOC_TRUSTED_NVCTR_BASE + 0x0004)
+#define NTFW_CTR_SIZE			U(4)
+
+/* Keys */
+#define SOC_KEYS_BASE			UL(0x0EE80000)
+#define TZ_PUB_KEY_HASH_BASE		(SOC_KEYS_BASE + 0x0000)
+#define TZ_PUB_KEY_HASH_SIZE		U(32)
+#define HU_KEY_BASE			(SOC_KEYS_BASE + 0x0020)
+#define HU_KEY_SIZE			U(16)
+#define END_KEY_BASE			(SOC_KEYS_BASE + 0x0044)
+#define END_KEY_SIZE			U(32)
+
+#define SOC_PLATFORM_PERIPH_MAP_DEVICE	MAP_REGION_FLAT(			\
+						SOC_PLATFORM_PERIPH_BASE, 	\
+						SOC_PLATFORM_PERIPH_SIZE, 	\
+						MT_DEVICE | MT_RW | MT_SECURE)
+
+#if SPM_MM
+/*
+ * Memory map definition for the platform peripheral memory region that is
+ * accessible from S-EL0 (with secure user mode access).
+ */
+#define SOC_PLATFORM_PERIPH_MAP_DEVICE_USER				       \
+		MAP_REGION_FLAT(					       \
+			SOC_PLATFORM_PERIPH_BASE,			       \
+			SOC_PLATFORM_PERIPH_SIZE,			       \
+			MT_DEVICE | MT_RW | MT_SECURE | MT_USER)
+#endif
+
+#define SOC_SYSTEM_PERIPH_MAP_DEVICE	MAP_REGION_FLAT(			\
+						SOC_SYSTEM_PERIPH_BASE,		\
+						SOC_SYSTEM_PERIPH_SIZE,		\
+						MT_DEVICE | MT_RW | MT_SECURE)
+
+#define SOC_MEMCNTRL_MAP_DEVICE		MAP_REGION_FLAT(			\
+						SOC_MEMCNTRL_BASE,		\
+						SOC_MEMCNTRL_SIZE,		\
+						MT_DEVICE | MT_RW | MT_SECURE)
+
+/*
+ * The bootsec_bridge controls access to a bunch of peripherals, e.g. the UARTs.
+ */
+#define SOC_CSS_NIC400_BOOTSEC_BRIDGE		U(5)
+#define SOC_CSS_NIC400_BOOTSEC_BRIDGE_UART1	UL(1 << 12)
+
+/*
+ * Required platform porting definitions common to all ARM CSS SoCs
+ */
+/* 2MB used for SCP DDR retraining */
+#define PLAT_ARM_SCP_TZC_DRAM1_SIZE	UL(0x00200000)
+
+/* V2M motherboard system registers & offsets */
+#define V2M_SYSREGS_BASE		UL(0x0C010000)
+#define V2M_SYS_LED			U(0x8)
+
+/*
+ * V2M sysled bit definitions. The values written to this
+ * register are defined in arch.h & runtime_svc.h. Only
+ * used by the primary cpu to diagnose any cold boot issues.
+ *
+ * SYS_LED[0]   - Security state (S=0/NS=1)
+ * SYS_LED[2:1] - Exception Level (EL3-EL0)
+ * SYS_LED[7:3] - Exception Class (Sync/Async & origin)
+ *
+ */
+#define V2M_SYS_LED_SS_SHIFT		U(0)
+#define V2M_SYS_LED_EL_SHIFT		U(1)
+#define V2M_SYS_LED_EC_SHIFT		U(3)
+
+#define V2M_SYS_LED_SS_MASK		U(0x01)
+#define V2M_SYS_LED_EL_MASK		U(0x03)
+#define V2M_SYS_LED_EC_MASK		U(0x1f)
+
+/* NOR Flash */
+#define V2M_FLASH0_BASE			UL(0x08000000)
+#define V2M_FLASH0_SIZE			UL(0x04000000)
+#define V2M_FLASH_BLOCK_SIZE		UL(0x00040000)	/* 256 KB */
+
+/*
+ * The flash can be mapped either as read-only or read-write.
+ *
+ * If it is read-write then it should also be mapped as device memory because
+ * NOR flash programming involves sending a fixed, ordered sequence of commands.
+ *
+ * If it is read-only then it should also be mapped as:
+ * - Normal memory, because reading from NOR flash is transparent, it is like
+ *   reading from RAM.
+ * - Non-executable by default. If some parts of the flash need to be executable
+ *   then platform code is responsible for re-mapping the appropriate portion
+ *   of it as executable.
+ */
+#define V2M_MAP_FLASH0_RW		MAP_REGION_FLAT(V2M_FLASH0_BASE,\
+						V2M_FLASH0_SIZE,	\
+						MT_DEVICE | MT_RW | MT_SECURE)
+
+#define V2M_MAP_FLASH0_RO		MAP_REGION_FLAT(V2M_FLASH0_BASE,\
+						V2M_FLASH0_SIZE,	\
+						MT_RO_DATA | MT_SECURE)
+
+#define SGI_MAP_FLASH0_RO		MAP_REGION_FLAT(V2M_FLASH0_BASE,\
+						V2M_FLASH0_SIZE,	\
+						MT_DEVICE | MT_RO | MT_SECURE)
+
+/* Platform ID address */
+#define BOARD_CSS_PLAT_ID_REG_ADDR		UL(0x0EFE00E0)
+
+/* Platform ID related accessors */
+#define BOARD_CSS_PLAT_ID_REG_ID_MASK		U(0x0F)
+#define BOARD_CSS_PLAT_ID_REG_ID_SHIFT		U(0x00)
+#define BOARD_CSS_PLAT_ID_REG_VERSION_MASK	U(0xF00)
+#define BOARD_CSS_PLAT_ID_REG_VERSION_SHIFT	U(0x08)
+#define BOARD_CSS_PLAT_TYPE_RTL			U(0x00)
+#define BOARD_CSS_PLAT_TYPE_FPGA		U(0x01)
+#define BOARD_CSS_PLAT_TYPE_EMULATOR		U(0x02)
+#define BOARD_CSS_PLAT_TYPE_FVP			U(0x03)
+
+#ifndef __ASSEMBLER__
+
+#include <lib/mmio.h>
+
+#define BOARD_CSS_GET_PLAT_TYPE(addr)					\
+	((mmio_read_32(addr) & BOARD_CSS_PLAT_ID_REG_ID_MASK)		\
+	>> BOARD_CSS_PLAT_ID_REG_ID_SHIFT)
+
+#endif /* __ASSEMBLER__ */
+
+
+#define MAX_IO_DEVICES			U(3)
+#define MAX_IO_HANDLES			U(4)
+
+/* Reserve the last block of flash for PSCI MEM PROTECT flag */
+#define PLAT_ARM_FLASH_IMAGE_BASE	V2M_FLASH0_BASE
+#define PLAT_ARM_FLASH_IMAGE_MAX_SIZE	(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+#if ARM_GPT_SUPPORT
+/*
+ * Offset of the FIP in the GPT image. BL1 component uses this option
+ * as it does not load the partition table to get the FIP base
+ * address. At sector 34 by default (i.e. after reserved sectors 0-33)
+ * Offset = 34 * 512(sector size) = 17408 i.e. 0x4400
+ */
+#define PLAT_ARM_FIP_OFFSET_IN_GPT		0x4400
+#endif /* ARM_GPT_SUPPORT */
+
+#define PLAT_ARM_NVM_BASE		V2M_FLASH0_BASE
+#define PLAT_ARM_NVM_SIZE		(V2M_FLASH0_SIZE - V2M_FLASH_BLOCK_SIZE)
+
+/* UART related constants */
+#define PLAT_ARM_BOOT_UART_BASE			SOC_CSS_UART0_BASE
+#define PLAT_ARM_BOOT_UART_CLK_IN_HZ		SOC_CSS_UART0_CLK_IN_HZ
+
+#define PLAT_ARM_RUN_UART_BASE			SOC_CSS_UART1_BASE
+#define PLAT_ARM_RUN_UART_CLK_IN_HZ		SOC_CSS_UART1_CLK_IN_HZ
+
+#define PLAT_ARM_SP_MIN_RUN_UART_BASE		SOC_CSS_UART1_BASE
+#define PLAT_ARM_SP_MIN_RUN_UART_CLK_IN_HZ	SOC_CSS_UART1_CLK_IN_HZ
+
+#define PLAT_ARM_CRASH_UART_BASE		PLAT_ARM_RUN_UART_BASE
+#define PLAT_ARM_CRASH_UART_CLK_IN_HZ		PLAT_ARM_RUN_UART_CLK_IN_HZ
+
+#endif /* SGI_SOC_CSS_DEF_V2_H */
diff --git a/plat/arm/css/sgi/include/sgi_soc_platform_def.h b/plat/arm/css/sgi/include/sgi_soc_platform_def.h
new file mode 100644
index 0000000..405d62f
--- /dev/null
+++ b/plat/arm/css/sgi/include/sgi_soc_platform_def.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SGI_SOC_PLATFORM_DEF_H
+#define SGI_SOC_PLATFORM_DEF_H
+
+#include <sgi_base_platform_def.h>
+#include <plat/arm/board/common/board_css_def.h>
+#include <plat/arm/board/common/v2m_def.h>
+#include <plat/arm/soc/common/soc_css_def.h>
+
+/* Map the System registers to access from S-EL0 */
+#define CSS_SYSTEMREG_DEVICE_BASE	(0x1C010000)
+#define CSS_SYSTEMREG_DEVICE_SIZE	(0x00010000)
+#define PLAT_ARM_SECURE_MAP_SYSTEMREG	MAP_REGION_FLAT(		    \
+						CSS_SYSTEMREG_DEVICE_BASE,  \
+						CSS_SYSTEMREG_DEVICE_SIZE,  \
+						(MT_DEVICE | MT_RW |	    \
+						 MT_SECURE | MT_USER))
+
+/* Map the NOR2 Flash to access from S-EL0 */
+#define CSS_NOR2_FLASH_DEVICE_BASE	(0x10000000)
+#define CSS_NOR2_FLASH_DEVICE_SIZE	(0x04000000)
+#define PLAT_ARM_SECURE_MAP_NOR2	MAP_REGION_FLAT(                    \
+						CSS_NOR2_FLASH_DEVICE_BASE, \
+						CSS_NOR2_FLASH_DEVICE_SIZE, \
+						(MT_DEVICE | MT_RW |	    \
+						 MT_SECURE | MT_USER))
+
+#endif /* SGI_SOC_PLATFORM_DEF_H */
diff --git a/plat/arm/css/sgi/include/sgi_soc_platform_def_v2.h b/plat/arm/css/sgi/include/sgi_soc_platform_def_v2.h
new file mode 100644
index 0000000..20dd682
--- /dev/null
+++ b/plat/arm/css/sgi/include/sgi_soc_platform_def_v2.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SGI_SOC_PLATFORM_DEF_V2_H
+#define SGI_SOC_PLATFORM_DEF_V2_H
+
+#include <sgi_base_platform_def.h>
+#include <sgi_soc_css_def_v2.h>
+
+/* Map the System registers to access from S-EL0 */
+#define CSS_SYSTEMREG_DEVICE_BASE	(0x0C010000)
+#define CSS_SYSTEMREG_DEVICE_SIZE	(0x00010000)
+#define PLAT_ARM_SECURE_MAP_SYSTEMREG	MAP_REGION_FLAT(                    \
+						CSS_SYSTEMREG_DEVICE_BASE,  \
+						CSS_SYSTEMREG_DEVICE_SIZE,  \
+						(MT_DEVICE | MT_RW |	    \
+						 MT_SECURE | MT_USER))
+
+/* Map the NOR2 Flash to access from S-EL0 */
+#define CSS_NOR2_FLASH_DEVICE_BASE	(0x001054000000)
+#define CSS_NOR2_FLASH_DEVICE_SIZE	(0x000004000000)
+#define PLAT_ARM_SECURE_MAP_NOR2	MAP_REGION_FLAT(                    \
+						CSS_NOR2_FLASH_DEVICE_BASE, \
+						CSS_NOR2_FLASH_DEVICE_SIZE, \
+						(MT_DEVICE | MT_RW |	    \
+						 MT_SECURE | MT_USER))
+
+#endif /* SGI_SOC_PLATFORM_DEF_V2_H */
diff --git a/plat/arm/css/sgi/include/sgi_variant.h b/plat/arm/css/sgi/include/sgi_variant.h
index f4c5300..0062b97 100644
--- a/plat/arm/css/sgi/include/sgi_variant.h
+++ b/plat/arm/css/sgi/include/sgi_variant.h
@@ -14,8 +14,14 @@
 #define RD_N1E1_EDGE_SID_VER_PART_NUM		0x0786
 #define RD_E1_EDGE_CONFIG_ID			0x2
 
-/* SID Version values for RD-Daniel */
-#define RD_DANIEL_SID_VER_PART_NUM		0x078a
+/* SID Version values for RD-V1 */
+#define RD_V1_SID_VER_PART_NUM			0x078a
+
+/* SID Version values for RD-N2 */
+#define RD_N2_SID_VER_PART_NUM			0x07B7
+
+/* SID Version values for RD-N2 variants */
+#define RD_N2_CFG1_SID_VER_PART_NUM		0x07B6
 
 /* Structure containing SGI platform variant information */
 typedef struct sgi_platform_info {
diff --git a/plat/arm/css/sgi/sgi-common.mk b/plat/arm/css/sgi/sgi-common.mk
index 6b9e0cd..8baf4ee 100644
--- a/plat/arm/css/sgi/sgi-common.mk
+++ b/plat/arm/css/sgi/sgi-common.mk
@@ -18,6 +18,8 @@
 
 CSS_SGI_CHIP_COUNT		:=	1
 
+CSS_SGI_PLATFORM_VARIANT	:=	0
+
 INTERCONNECT_SOURCES	:=	${CSS_ENT_BASE}/sgi_interconnect.c
 
 PLAT_INCLUDES		+=	-I${CSS_ENT_BASE}/include
@@ -32,8 +34,7 @@
 				plat/common/plat_gicv3.c	\
 				plat/arm/common/arm_gicv3.c
 
-PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/sgi_plat.c	\
-				${CSS_ENT_BASE}/aarch64/sgi_helper.S
+PLAT_BL_COMMON_SOURCES	+=	${CSS_ENT_BASE}/aarch64/sgi_helper.S
 
 BL1_SOURCES		+=	${INTERCONNECT_SOURCES}			\
 				drivers/arm/sbsa/sbsa.c
@@ -58,10 +59,14 @@
 
 $(eval $(call add_define,CSS_SGI_CHIP_COUNT))
 
+$(eval $(call add_define,CSS_SGI_PLATFORM_VARIANT))
+
 override CSS_LOAD_SCP_IMAGES	:=	0
 override NEED_BL2U		:=	no
 override ARM_BL31_IN_DRAM	:=	1
 override ARM_PLAT_MT		:=	1
+override PSCI_EXTENDED_STATE_ID	:=	1
+override ARM_RECOM_STATE_ID_ENC	:=	1
 
 # System coherency is managed in hardware
 HW_ASSISTED_COHERENCY	:=	1
diff --git a/plat/arm/css/sgi/sgi_bl31_setup.c b/plat/arm/css/sgi/sgi_bl31_setup.c
index a4aed00..541689b 100644
--- a/plat/arm/css/sgi/sgi_bl31_setup.c
+++ b/plat/arm/css/sgi/sgi_bl31_setup.c
@@ -28,7 +28,7 @@
 		.ring_doorbell = &mhu_ring_doorbell,
 };
 
-static scmi_channel_plat_info_t rd_n1e1_edge_scmi_plat_info[] = {
+static scmi_channel_plat_info_t plat_rd_scmi_info[] = {
 	{
 		.scmi_mbx_mem = CSS_SCMI_PAYLOAD_BASE,
 		.db_reg_addr = PLAT_CSS_MHU_BASE + SENDER_REG_SET(0),
@@ -74,10 +74,12 @@
 scmi_channel_plat_info_t *plat_css_get_scmi_info(int channel_id)
 {
 	if (sgi_plat_info.platform_id == RD_N1E1_EDGE_SID_VER_PART_NUM ||
-		sgi_plat_info.platform_id == RD_DANIEL_SID_VER_PART_NUM) {
-		if (channel_id >= ARRAY_SIZE(rd_n1e1_edge_scmi_plat_info))
+		sgi_plat_info.platform_id == RD_V1_SID_VER_PART_NUM ||
+		sgi_plat_info.platform_id == RD_N2_SID_VER_PART_NUM ||
+		sgi_plat_info.platform_id == RD_N2_CFG1_SID_VER_PART_NUM) {
+		if (channel_id >= ARRAY_SIZE(plat_rd_scmi_info))
 			panic();
-		return &rd_n1e1_edge_scmi_plat_info[channel_id];
+		return &plat_rd_scmi_info[channel_id];
 	}
 	else if (sgi_plat_info.platform_id == SGI575_SSC_VER_PART_NUM)
 		return &sgi575_scmi_plat_info;
@@ -107,12 +109,11 @@
 const plat_psci_ops_t *plat_arm_psci_override_pm_ops(plat_psci_ops_t *ops)
 {
 	/*
-	 * For RD-E1-Edge and RD-Daniel platforms, only CPU power ON/OFF
-	 * PSCI platform callbacks are supported.
+	 * For RD-E1-Edge, only CPU power ON/OFF, PSCI platform callbacks are
+	 * supported.
 	 */
 	if (((sgi_plat_info.platform_id == RD_N1E1_EDGE_SID_VER_PART_NUM) &&
-	    (sgi_plat_info.config_id == RD_E1_EDGE_CONFIG_ID)) ||
-	    (sgi_plat_info.platform_id == RD_DANIEL_SID_VER_PART_NUM)) {
+	    (sgi_plat_info.config_id == RD_E1_EDGE_CONFIG_ID))) {
 		ops->cpu_standby = NULL;
 		ops->system_off = NULL;
 		ops->system_reset = NULL;
diff --git a/plat/arm/css/sgi/sgi_plat.c b/plat/arm/css/sgi/sgi_plat.c
index 39eb89e..20c52e9 100644
--- a/plat/arm/css/sgi/sgi_plat.c
+++ b/plat/arm/css/sgi/sgi_plat.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -49,6 +49,15 @@
 	CSS_SGI_MAP_DEVICE,
 	SOC_CSS_MAP_DEVICE,
 	ARM_MAP_NS_DRAM1,
+#if CSS_SGI_CHIP_COUNT > 1
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(1),
+#endif
+#if CSS_SGI_CHIP_COUNT > 2
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(2),
+#endif
+#if CSS_SGI_CHIP_COUNT > 3
+	CSS_SGI_MAP_DEVICE_REMOTE_CHIP(3),
+#endif
 #if ARM_BL31_IN_DRAM
 	ARM_MAP_BL31_SEC_DRAM,
 #endif
@@ -78,10 +87,14 @@
 
 #if SPM_MM && defined(IMAGE_BL31)
 const mmap_region_t plat_arm_secure_partition_mmap[] = {
+	PLAT_ARM_SECURE_MAP_SYSTEMREG,
+	PLAT_ARM_SECURE_MAP_NOR2,
 	PLAT_ARM_SECURE_MAP_DEVICE,
 	ARM_SP_IMAGE_MMAP,
 	ARM_SP_IMAGE_NS_BUF_MMAP,
-	ARM_SP_CPER_BUF_MMAP,
+#if RAS_EXTENSION
+	CSS_SGI_SP_CPER_BUF_MMAP,
+#endif
 	ARM_SP_IMAGE_RW_MMAP,
 	ARM_SPM_BUF_EL0_MMAP,
 	{0}
diff --git a/plat/arm/css/sgi/sgi_plat_v2.c b/plat/arm/css/sgi/sgi_plat_v2.c
new file mode 100644
index 0000000..131cdf2
--- /dev/null
+++ b/plat/arm/css/sgi/sgi_plat_v2.c
@@ -0,0 +1,165 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <platform_def.h>
+
+#include <plat/arm/common/plat_arm.h>
+#include <plat/common/platform.h>
+#include <drivers/arm/sbsa.h>
+
+#if SPM_MM
+#include <services/spm_mm_partition.h>
+#endif
+
+/*
+ * Table of regions for different BL stages to map using the MMU.
+ */
+#if IMAGE_BL1
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	SGI_MAP_FLASH0_RO,
+	CSS_SGI_MAP_DEVICE,
+	SOC_PLATFORM_PERIPH_MAP_DEVICE,
+	SOC_SYSTEM_PERIPH_MAP_DEVICE,
+	{0}
+};
+#endif
+
+#if IMAGE_BL2
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+	SGI_MAP_FLASH0_RO,
+#ifdef PLAT_ARM_MEM_PROT_ADDR
+	ARM_V2M_MAP_MEM_PROTECT,
+#endif
+	CSS_SGI_MAP_DEVICE,
+	SOC_MEMCNTRL_MAP_DEVICE,
+	SOC_PLATFORM_PERIPH_MAP_DEVICE,
+	SOC_SYSTEM_PERIPH_MAP_DEVICE,
+	ARM_MAP_NS_DRAM1,
+#if ARM_BL31_IN_DRAM
+	ARM_MAP_BL31_SEC_DRAM,
+#endif
+#if SPM_MM
+	ARM_SP_IMAGE_MMAP,
+#endif
+#if TRUSTED_BOARD_BOOT && !BL2_AT_EL3
+	ARM_MAP_BL1_RW,
+#endif
+	{0}
+};
+#endif
+
+#if IMAGE_BL31
+const mmap_region_t plat_arm_mmap[] = {
+	ARM_MAP_SHARED_RAM,
+#ifdef PLAT_ARM_MEM_PROT_ADDR
+	ARM_V2M_MAP_MEM_PROTECT,
+#endif
+	CSS_SGI_MAP_DEVICE,
+	SOC_PLATFORM_PERIPH_MAP_DEVICE,
+	SOC_SYSTEM_PERIPH_MAP_DEVICE,
+#if SPM_MM
+	ARM_SPM_BUF_EL3_MMAP,
+#endif
+	{0}
+};
+
+#if SPM_MM && defined(IMAGE_BL31)
+const mmap_region_t plat_arm_secure_partition_mmap[] = {
+	PLAT_ARM_SECURE_MAP_SYSTEMREG,
+	PLAT_ARM_SECURE_MAP_NOR2,
+	SOC_PLATFORM_PERIPH_MAP_DEVICE_USER,
+	ARM_SP_IMAGE_MMAP,
+	ARM_SP_IMAGE_NS_BUF_MMAP,
+	ARM_SP_IMAGE_RW_MMAP,
+	ARM_SPM_BUF_EL0_MMAP,
+	{0}
+};
+#endif /* SPM_MM && defined(IMAGE_BL31) */
+#endif
+
+ARM_CASSERT_MMAP
+
+#if SPM_MM && defined(IMAGE_BL31)
+/*
+ * Boot information passed to a secure partition during initialisation. Linear
+ * indices in MP information will be filled at runtime.
+ */
+static spm_mm_mp_info_t sp_mp_info[] = {
+	[0] = {0x81000000, 0},
+	[1] = {0x81010000, 0},
+	[2] = {0x81020000, 0},
+	[3] = {0x81030000, 0},
+	[4] = {0x81040000, 0},
+	[5] = {0x81050000, 0},
+	[6] = {0x81060000, 0},
+	[7] = {0x81070000, 0},
+	[8] = {0x81080000, 0},
+	[9] = {0x81090000, 0},
+	[10] = {0x810a0000, 0},
+	[11] = {0x810b0000, 0},
+	[12] = {0x810c0000, 0},
+	[13] = {0x810d0000, 0},
+	[14] = {0x810e0000, 0},
+	[15] = {0x810f0000, 0},
+};
+
+const spm_mm_boot_info_t plat_arm_secure_partition_boot_info = {
+	.h.type              = PARAM_SP_IMAGE_BOOT_INFO,
+	.h.version           = VERSION_1,
+	.h.size              = sizeof(spm_mm_boot_info_t),
+	.h.attr              = 0,
+	.sp_mem_base         = ARM_SP_IMAGE_BASE,
+	.sp_mem_limit        = ARM_SP_IMAGE_LIMIT,
+	.sp_image_base       = ARM_SP_IMAGE_BASE,
+	.sp_stack_base       = PLAT_SP_IMAGE_STACK_BASE,
+	.sp_heap_base        = ARM_SP_IMAGE_HEAP_BASE,
+	.sp_ns_comm_buf_base = PLAT_SP_IMAGE_NS_BUF_BASE,
+	.sp_shared_buf_base  = PLAT_SPM_BUF_BASE,
+	.sp_image_size       = ARM_SP_IMAGE_SIZE,
+	.sp_pcpu_stack_size  = PLAT_SP_IMAGE_STACK_PCPU_SIZE,
+	.sp_heap_size        = ARM_SP_IMAGE_HEAP_SIZE,
+	.sp_ns_comm_buf_size = PLAT_SP_IMAGE_NS_BUF_SIZE,
+	.sp_shared_buf_size  = PLAT_SPM_BUF_SIZE,
+	.num_sp_mem_regions  = ARM_SP_IMAGE_NUM_MEM_REGIONS,
+	.num_cpus            = PLATFORM_CORE_COUNT,
+	.mp_info             = &sp_mp_info[0],
+};
+
+const struct mmap_region *plat_get_secure_partition_mmap(void *cookie)
+{
+	return plat_arm_secure_partition_mmap;
+}
+
+const struct spm_mm_boot_info *plat_get_secure_partition_boot_info(
+		void *cookie)
+{
+	return &plat_arm_secure_partition_boot_info;
+}
+#endif /* SPM_MM && defined(IMAGE_BL31) */
+
+#if TRUSTED_BOARD_BOOT
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	assert(heap_addr != NULL);
+	assert(heap_size != NULL);
+
+	return arm_get_mbedtls_heap(heap_addr, heap_size);
+}
+#endif
+
+void plat_arm_secure_wdt_start(void)
+{
+	sbsa_wdog_start(SBSA_SECURE_WDOG_BASE, SBSA_SECURE_WDOG_TIMEOUT);
+}
+
+void plat_arm_secure_wdt_stop(void)
+{
+	sbsa_wdog_stop(SBSA_SECURE_WDOG_BASE);
+}
diff --git a/plat/arm/css/sgi/sgi_ras.c b/plat/arm/css/sgi/sgi_ras.c
index f56544e..4f03ac4 100644
--- a/plat/arm/css/sgi/sgi_ras.c
+++ b/plat/arm/css/sgi/sgi_ras.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -20,44 +20,51 @@
 static int sgi_ras_intr_handler(const struct err_record_info *err_rec,
 				int probe_data,
 				const struct err_handler_data *const data);
-struct efi_guid {
-	uint32_t	data1;
-	uint16_t	data2;
-	uint16_t	data3;
-	uint8_t		data4[8];
-};
-
 typedef struct mm_communicate_header {
 	struct efi_guid	header_guid;
 	size_t		message_len;
 	uint8_t		data[8];
 } mm_communicate_header_t;
 
+/*
+ * GUID to indicate that the MM communication message is intended for DMC-620
+ * MM driver.
+ */
+const struct efi_guid dmc620_ecc_event_guid = {
+	0x5ef0afd5, 0xe01a, 0x4c30,
+	{0x86, 0x19, 0x45, 0x46, 0x26, 0x91, 0x80, 0x98}
+};
+
 struct sgi_ras_ev_map sgi575_ras_map[] = {
 
-	/* DMC620 error overflow interrupt*/
-	{SP_DMC_ERROR_OVERFLOW_EVENT_AARCH64, SGI_SDEI_DS_EVENT_1, 33},
+	/* DMC 0 error ECC error interrupt*/
+	{SGI_SDEI_DS_EVENT_0, 35},
 
-	/* DMC620 error ECC error interrupt*/
-	{SP_DMC_ERROR_ECC_EVENT_AARCH64, SGI_SDEI_DS_EVENT_0, 35},
+	/* DMC 1 error ECC error interrupt*/
+	{SGI_SDEI_DS_EVENT_1, 39},
 };
 
 #define SGI575_RAS_MAP_SIZE	ARRAY_SIZE(sgi575_ras_map)
 
 struct err_record_info sgi_err_records[] = {
 	{
+		/* DMC 0 error record info */
 		.handler = &sgi_ras_intr_handler,
+		.aux_data = (void *)0,
+	}, {
+		/* DMC 1 error record info */
+		.handler = &sgi_ras_intr_handler,
+		.aux_data = (void *)1,
 	},
 };
 
 struct ras_interrupt sgi_ras_interrupts[] = {
 	{
-		.intr_number = 33,
-		.err_record = &sgi_err_records[0],
-	},
-	{
 		.intr_number = 35,
 		.err_record = &sgi_err_records[0],
+	}, {
+		.intr_number = 39,
+		.err_record = &sgi_err_records[1],
 	}
 };
 
@@ -111,6 +118,7 @@
 	struct sgi_ras_ev_map *ras_map;
 	mm_communicate_header_t *header;
 	uint32_t intr;
+	int ret;
 
 	cm_el1_sysregs_context_save(NON_SECURE);
 	intr = data->interrupt;
@@ -120,7 +128,7 @@
 	 * this interrupt
 	 */
 	ras_map = find_ras_event_map_by_intr(intr);
-	assert(ras_map);
+	assert(ras_map != NULL);
 
 	/*
 	 * Populate the MM_COMMUNICATE payload to share the
@@ -137,9 +145,10 @@
 	 */
 	header = (void *) PLAT_SPM_BUF_BASE;
 	memset(header, 0, sizeof(*header));
-	memcpy(&header->data, &ras_map->ras_ev_num,
-	       sizeof(ras_map->ras_ev_num));
-	header->message_len = 4;
+	memcpy(&header->data, &err_rec->aux_data, sizeof(err_rec->aux_data));
+	header->message_len = sizeof(err_rec->aux_data);
+	memcpy(&header->header_guid, (void *) &dmc620_ecc_event_guid,
+			sizeof(const struct efi_guid));
 
 	spm_mm_sp_call(MM_COMMUNICATE_AARCH64, (uint64_t)header, 0,
 		       plat_my_core_pos());
@@ -152,9 +161,20 @@
 	plat_ic_end_of_interrupt(intr);
 
 	/* Dispatch the event to the SDEI client */
-	sdei_dispatch_event(ras_map->sdei_ev_num);
+	ret = sdei_dispatch_event(ras_map->sdei_ev_num);
+	if (ret != 0) {
+		/*
+		 * sdei_dispatch_event() may return failing result in some cases,
+		 * for example kernel may not have registered a handler or RAS event
+		 * may happen early during boot. We restore the NS context when
+		 * sdei_dispatch_event() returns failing result.
+		 */
+		ERROR("SDEI dispatch failed: %d", ret);
+		cm_el1_sysregs_context_restore(NON_SECURE);
+		cm_set_next_eret_context(NON_SECURE);
+	}
 
-	return 0;
+	return ret;
 }
 
 int sgi_ras_intr_handler_setup(void)
diff --git a/plat/brcm/board/common/board_arm_trusted_boot.c b/plat/brcm/board/common/board_arm_trusted_boot.c
index 7a4dad0..da18c31 100644
--- a/plat/brcm/board/common/board_arm_trusted_boot.c
+++ b/plat/brcm/board/common/board_arm_trusted_boot.c
@@ -5,6 +5,7 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
 #include <stdint.h>
 #include <string.h>
 
@@ -344,7 +345,7 @@
 
 	for (rownum = start_row; rownum <= end_row; rownum++) {
 		rowdata = sotp_mem_read(rownum, SOTP_ROW_NO_ECC);
-		INFO("%d 0x%llx\n", rownum, rowdata);
+		INFO("%d 0x%" PRIx64 "\n", rownum, rowdata);
 	}
 }
 #endif
diff --git a/plat/brcm/board/common/board_common.mk b/plat/brcm/board/common/board_common.mk
index 3069f91..3b3e92d 100644
--- a/plat/brcm/board/common/board_common.mk
+++ b/plat/brcm/board/common/board_common.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2015 - 2020, Broadcom
+# Copyright (c) 2015 - 2021, Broadcom
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -36,6 +36,10 @@
 DRIVER_SPI_ENABLE := 0
 endif
 
+ifeq (${DRIVER_I2C_ENABLE},)
+DRIVER_I2C_ENABLE := 0
+endif
+
 # By default, Trusted Watchdog is always enabled unless SPIN_ON_BL1_EXIT is set
 ifeq (${BRCM_DISABLE_TRUSTED_WDOG},)
 BRCM_DISABLE_TRUSTED_WDOG	:=	0
@@ -114,7 +118,8 @@
 
 PLAT_INCLUDES		+=	-Iplat/brcm/board/common \
 				-Iinclude/drivers/brcm \
-				-Iinclude/drivers/brcm/emmc
+				-Iinclude/drivers/brcm/emmc \
+				-Iinclude/drivers/brcm/mdio
 
 PLAT_BL_COMMON_SOURCES	+=	plat/brcm/common/brcm_common.c \
 				plat/brcm/board/common/cmn_sec.c \
@@ -181,6 +186,12 @@
 				drivers/brcm/spi_flash.c
 endif
 
+ifeq (${DRIVER_I2C_ENABLE},1)
+$(eval $(call add_define,DRIVER_I2C_ENABLE))
+BL2_SOURCES		+= 	drivers/brcm/i2c/i2c.c
+PLAT_INCLUDES		+=	-Iinclude/drivers/brcm/i2c
+endif
+
 ifeq (${DRIVER_OCOTP_ENABLE},1)
 $(eval $(call add_define,DRIVER_OCOTP_ENABLE))
 BL2_SOURCES		+= drivers/brcm/ocotp.c
diff --git a/plat/brcm/board/stingray/driver/sr_usb.h b/plat/brcm/board/stingray/driver/sr_usb.h
new file mode 100644
index 0000000..5033683
--- /dev/null
+++ b/plat/brcm/board/stingray/driver/sr_usb.h
@@ -0,0 +1,135 @@
+/*
+ * Copyright (c) 2019 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SR_USB_H
+#define SR_USB_H
+
+#define CDRU_PM_RESET_N_R	BIT(CDRU_MISC_RESET_CONTROL__CDRU_PM_RESET_N_R)
+#define CDRU_USBSS_RESET_N	BIT(CDRU_MISC_RESET_CONTROL__CDRU_USBSS_RESET_N)
+#define CDRU_MISC_CLK_USBSS \
+			BIT(CDRU_MISC_CLK_ENABLE_CONTROL__CDRU_USBSS_CLK_EN_R)
+
+#define RESCAL_I_RSTB			BIT(26)
+#define RESCAL_I_PWRDNB			BIT(27)
+
+#define DRDU3_U3PHY_CTRL		0x68500014
+#define	PHY_RESET			BIT(1)
+#define	POR_RESET			BIT(28)
+#define	MDIO_RESET			BIT(29)
+
+#define DRDU3_PWR_CTRL			0x6850002c
+#define POWER_CTRL_OVRD			BIT(2)
+
+#define USB3H_U3PHY_CTRL		0x68510014
+#define USB3H_U3SOFT_RST_N		BIT(30)
+
+#define USB3H_PWR_CTRL			0x68510028
+
+#define USB3_PHY_MDIO_BLOCK_BASE_REG	0x1f
+#define BDC_AXI_SOFT_RST_N_OFFSET	0
+#define XHC_AXI_SOFT_RST_N_OFFSET	1
+#define MDIO_BUS_ID			3
+#define USB3H_PHY_ID			5
+#define USB3DRD_PHY_ID			2
+
+#define USB3_PHY_RXPMD_BLOCK_BASE	0x8020
+#define USB3_PHY_RXPMD_REG1		0x1
+#define USB3_PHY_RXPMD_REG2		0x2
+#define USB3_PHY_RXPMD_REG5		0x5
+#define USB3_PHY_RXPMD_REG7		0x7
+
+#define USB3_PHY_TXPMD_BLOCK_BASE	0x8040
+#define USB3_PHY_TXPMD_REG1		0x1
+#define USB3_PHY_TXPMD_REG2		0x2
+
+#define USB3_PHY_ANA_BLOCK_BASE		0x8090
+#define USB3_PHY_ANA_REG0		0x0
+#define USB3_PHY_ANA_REG1		0x1
+#define USB3_PHY_ANA_REG2		0x2
+#define USB3_PHY_ANA_REG5		0x5
+#define USB3_PHY_ANA_REG8		0x8
+#define USB3_PHY_ANA_REG11		0xb
+
+#define USB3_PHY_AEQ_BLOCK_BASE		0x80e0
+#define USB3_PHY_AEQ_REG1		0x1
+#define USB3_PHY_AEQ_REG3		0x3
+
+#ifdef USB_DMA_COHERENT
+#define DRDU3_U3XHC_SOFT_RST_N		BIT(31)
+#define DRDU3_U3BDC_SOFT_RST_N		BIT(30)
+
+#define DRDU3_SOFT_RESET_CTRL		0x68500030
+#define DRDU3_XHC_AXI_SOFT_RST_N	BIT(1)
+#define DRDU3_BDC_AXI_SOFT_RST_N	BIT(0)
+
+#define DRDU2_PHY_CTRL			0x6852000c
+#define DRDU2_U2SOFT_RST_N		BIT(29)
+
+#define USB3H_SOFT_RESET_CTRL		0x6851002c
+#define USB3H_XHC_AXI_SOFT_RST_N	BIT(1)
+
+#define DRDU2_SOFT_RESET_CTRL		0x68520020
+#define DRDU2_BDC_AXI_SOFT_RST_N	BIT(0)
+
+#define DRD2U3H_XHC_REGS_AXIWRA		0x68511c08
+#define DRD2U3H_XHC_REGS_AXIRDA		0x68511c0c
+#define DRDU2D_BDC_REGS_AXIWRA		0x68521c08
+#define DRDU2D_BDC_REGS_AXIRDA		0x68521c0c
+#define DRDU3H_XHC_REGS_AXIWRA		0x68501c08
+#define DRDU3H_XHC_REGS_AXIRDA		0x68501c0c
+#define DRDU3D_BDC_REGS_AXIWRA		0x68502c08
+#define DRDU3D_BDC_REGS_AXIRDA		0x68502c0c
+/* cacheable write-back, allocate on both reads and writes */
+#define USBAXI_AWCACHE		0xf
+#define USBAXI_ARCACHE		0xf
+/* non-secure */
+#define USBAXI_AWPROT		0x8
+#define USBAXI_ARPROT		0x8
+#define USBAXIWR_SA_VAL		((USBAXI_AWCACHE << 4 | USBAXI_AWPROT) << 0)
+#define USBAXIWR_SA_MASK	((0xf << 4 | 0xf) << 0)
+#define USBAXIWR_UA_VAL		((USBAXI_AWCACHE << 4 | USBAXI_AWPROT) << 16)
+#define USBAXIWR_UA_MASK	((0xf << 4 | 0xf) << 0)
+#define USBAXIRD_SA_VAL		((USBAXI_ARCACHE << 4 | USBAXI_ARPROT) << 0)
+#define USBAXIRD_SA_MASK	((0xf << 4 | 0xf) << 0)
+#define USBAXIRD_UA_VAL		((USBAXI_ARCACHE << 4 | USBAXI_ARPROT) << 16)
+#define USBAXIRD_UA_MASK	((0xf << 4 | 0xf) << 0)
+#endif /* USB_DMA_COHERENT */
+
+#define ICFG_DRDU3_SID_CTRL		0x6850001c
+#define ICFG_USB3H_SID_CTRL		0x6851001c
+#define ICFG_DRDU2_SID_CTRL		0x68520010
+#define ICFG_USB_SID_SHIFT		5
+#define ICFG_USB_SID_AWADDR_OFFSET	0x0
+#define ICFG_USB_SID_ARADDR_OFFSET	0x4
+
+#define USBIC_GPV_BASE			0x68600000
+#define USBIC_GPV_SECURITY0		(USBIC_GPV_BASE + 0x8)
+#define USBIC_GPV_SECURITY0_FIELD	BIT(0)
+#define USBIC_GPV_SECURITY1		(USBIC_GPV_BASE + 0xc)
+#define USBIC_GPV_SECURITY1_FIELD	(BIT(0) | BIT(1))
+#define USBIC_GPV_SECURITY2		(USBIC_GPV_BASE + 0x10)
+#define USBIC_GPV_SECURITY2_FIELD	(BIT(0) | BIT(1))
+#define USBIC_GPV_SECURITY4		(USBIC_GPV_BASE + 0x18)
+#define USBIC_GPV_SECURITY4_FIELD	BIT(0)
+#define USBIC_GPV_SECURITY10		(USBIC_GPV_BASE + 0x30)
+#define USBIC_GPV_SECURITY10_FIELD	(0x7 << 0)
+
+#define USBSS_TZPCDECPROT_BASE		0x68540800
+#define USBSS_TZPCDECPROT0set		(USBSS_TZPCDECPROT_BASE + 0x4)
+#define USBSS_TZPCDECPROT0clr		(USBSS_TZPCDECPROT_BASE + 0x8)
+#define DECPROT0_USBSS_DRD2U3H		BIT(3)
+#define DECPROT0_USBSS_DRDU2H		BIT(2)
+#define DECPROT0_USBSS_DRDU3D		BIT(1)
+#define DECPROT0_USBSS_DRDU2D		BIT(0)
+#define USBSS_TZPCDECPROT0 \
+		(DECPROT0_USBSS_DRD2U3H | \
+		DECPROT0_USBSS_DRDU2H |   \
+		DECPROT0_USBSS_DRDU3D |   \
+		DECPROT0_USBSS_DRDU2D)
+
+int32_t usb_device_init(unsigned int);
+
+#endif /* SR_USB_H */
diff --git a/plat/brcm/board/stingray/driver/usb.c b/plat/brcm/board/stingray/driver/usb.c
new file mode 100644
index 0000000..4a84141
--- /dev/null
+++ b/plat/brcm/board/stingray/driver/usb.c
@@ -0,0 +1,296 @@
+/*
+ * Copyright (c) 2019 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include <mdio.h>
+#include <platform_usb.h>
+#include <sr_utils.h>
+#include "sr_usb.h"
+#include <usbh_xhci_regs.h>
+
+static uint32_t usb_func = USB3_DRD | USB3H_USB2DRD;
+
+static void usb_pm_rescal_init(void)
+{
+	uint32_t data;
+	uint32_t try;
+
+	mmio_setbits_32(CDRU_MISC_RESET_CONTROL, CDRU_PM_RESET_N_R);
+	/* release reset */
+	mmio_setbits_32(CDRU_CHIP_TOP_SPARE_REG0, RESCAL_I_RSTB);
+	udelay(10U);
+	/* power up */
+	mmio_setbits_32(CDRU_CHIP_TOP_SPARE_REG0,
+			RESCAL_I_RSTB | RESCAL_I_PWRDNB);
+	try = 1000U;
+	do {
+		udelay(1U);
+		data = mmio_read_32(CDRU_CHIP_TOP_SPARE_REG1);
+		try--;
+	} while ((data & RESCAL_I_PWRDNB) == 0x0U && (try != 0U));
+
+	if (try == 0U) {
+		ERROR("CDRU_CHIP_TOP_SPARE_REG1: 0x%x\n", data);
+	}
+
+	INFO("USB and PM Rescal Init done..\n");
+}
+
+const unsigned int xhc_portsc_reg_offset[MAX_USB_PORTS] = {
+	XHC_PORTSC1_OFFSET,
+	XHC_PORTSC2_OFFSET,
+	XHC_PORTSC3_OFFSET,
+};
+
+static void usb3h_usb2drd_init(void)
+{
+	uint32_t val;
+
+	INFO("USB3H + USB 2DRD init\n");
+	mmio_clrbits_32(USB3H_U3PHY_CTRL, POR_RESET);
+	val = mmio_read_32(USB3H_PWR_CTRL);
+	val &= ~(0x3U << POWER_CTRL_OVRD);
+	val |= (1U << POWER_CTRL_OVRD);
+	mmio_write_32(USB3H_PWR_CTRL, val);
+	mmio_setbits_32(USB3H_U3PHY_CTRL, PHY_RESET);
+	/* Phy to come out of reset */
+	udelay(2U);
+	mmio_clrbits_32(USB3H_U3PHY_CTRL, MDIO_RESET);
+
+	/* MDIO in reset */
+	udelay(2U);
+	mmio_setbits_32(USB3H_U3PHY_CTRL, MDIO_RESET);
+
+	/* After MDIO reset release */
+	udelay(2U);
+
+	/* USB 3.0 phy Analog Block Initialization */
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_ANA_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG0, 0x4646U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG1, 0x80c9U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG2, 0x88a6U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG5, 0x7c12U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG8, 0x1d07U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_ANA_REG11, 0x25cU);
+
+	/* USB 3.0 phy RXPMD Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_RXPMD_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_RXPMD_REG1, 0x4052U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_RXPMD_REG2, 0x4cU);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_RXPMD_REG5, 0x7U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_RXPMD_REG7, 0x173U);
+
+	/* USB 3.0 phy AEQ Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_AEQ_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_AEQ_REG1, 0x3000U);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_AEQ_REG3, 0x2c70U);
+
+	/* USB 3.0 phy TXPMD Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_TXPMD_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_TXPMD_REG1, 0x100fU);
+	mdio_write(MDIO_BUS_ID, USB3H_PHY_ID, USB3_PHY_TXPMD_REG2, 0x238cU);
+}
+
+static void usb3drd_init(void)
+{
+	uint32_t val;
+
+	INFO("USB3DRD init\n");
+	mmio_clrbits_32(DRDU3_U3PHY_CTRL, POR_RESET);
+	val = mmio_read_32(DRDU3_PWR_CTRL);
+	val &= ~(0x3U << POWER_CTRL_OVRD);
+	val |= (1U << POWER_CTRL_OVRD);
+	mmio_write_32(DRDU3_PWR_CTRL, val);
+	mmio_setbits_32(DRDU3_U3PHY_CTRL, PHY_RESET);
+	/* Phy to come out of reset */
+	udelay(2U);
+	mmio_clrbits_32(DRDU3_U3PHY_CTRL, MDIO_RESET);
+
+	/* MDIO in reset */
+	udelay(2U);
+	mmio_setbits_32(DRDU3_U3PHY_CTRL, MDIO_RESET);
+
+	/* After MDIO reset release */
+	udelay(2U);
+
+	/* USB 3.0 DRD phy Analog Block Initialization */
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_ANA_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG0, 0x4646U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG1, 0x80c9U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG2, 0x88a6U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG5, 0x7c12U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG8, 0x1d07U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_ANA_REG11, 0x25cU);
+
+	/* USB 3.0 DRD phy RXPMD Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_RXPMD_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_RXPMD_REG1, 0x4052U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_RXPMD_REG2, 0x4cU);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_RXPMD_REG5, 0x7U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_RXPMD_REG7, 0x173U);
+
+	/* USB 3.0 DRD phy AEQ Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_AEQ_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_AEQ_REG1, 0x3000U);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_AEQ_REG3, 0x2c70U);
+
+	/* USB 3.0 DRD phy TXPMD Block initialization*/
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_MDIO_BLOCK_BASE_REG,
+			USB3_PHY_TXPMD_BLOCK_BASE);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_TXPMD_REG1, 0x100fU);
+	mdio_write(MDIO_BUS_ID, USB3DRD_PHY_ID, USB3_PHY_TXPMD_REG2, 0x238cU);
+}
+
+static void usb3_phy_init(void)
+{
+	usb_pm_rescal_init();
+
+	if ((usb_func & USB3H_USB2DRD) != 0U) {
+		usb3h_usb2drd_init();
+	}
+
+	if ((usb_func & USB3_DRD) != 0U) {
+		usb3drd_init();
+	}
+}
+
+#ifdef USB_DMA_COHERENT
+void usb_enable_coherence(void)
+{
+	if (usb_func & USB3H_USB2DRD) {
+		mmio_setbits_32(USB3H_SOFT_RESET_CTRL,
+				USB3H_XHC_AXI_SOFT_RST_N);
+		mmio_setbits_32(DRDU2_SOFT_RESET_CTRL,
+				DRDU2_BDC_AXI_SOFT_RST_N);
+		mmio_setbits_32(USB3H_U3PHY_CTRL, USB3H_U3SOFT_RST_N);
+		mmio_setbits_32(DRDU2_PHY_CTRL, DRDU2_U2SOFT_RST_N);
+
+		mmio_clrsetbits_32(DRD2U3H_XHC_REGS_AXIWRA,
+				   (USBAXIWR_UA_MASK | USBAXIWR_SA_MASK),
+				   (USBAXIWR_UA_VAL | USBAXIWR_SA_VAL));
+
+		mmio_clrsetbits_32(DRD2U3H_XHC_REGS_AXIRDA,
+				   (USBAXIRD_UA_MASK | USBAXIRD_SA_MASK),
+				   (USBAXIRD_UA_VAL | USBAXIRD_SA_VAL));
+
+		mmio_clrsetbits_32(DRDU2D_BDC_REGS_AXIWRA,
+				   (USBAXIWR_UA_MASK | USBAXIWR_SA_MASK),
+				   (USBAXIWR_UA_VAL | USBAXIWR_SA_VAL));
+
+		mmio_clrsetbits_32(DRDU2D_BDC_REGS_AXIRDA,
+				   (USBAXIRD_UA_MASK | USBAXIRD_SA_MASK),
+				   (USBAXIRD_UA_VAL | USBAXIRD_SA_VAL));
+
+	}
+
+	if (usb_func & USB3_DRD) {
+		mmio_setbits_32(DRDU3_SOFT_RESET_CTRL,
+				(DRDU3_XHC_AXI_SOFT_RST_N |
+				DRDU3_BDC_AXI_SOFT_RST_N));
+		mmio_setbits_32(DRDU3_U3PHY_CTRL,
+				(DRDU3_U3XHC_SOFT_RST_N |
+				DRDU3_U3BDC_SOFT_RST_N));
+
+		mmio_clrsetbits_32(DRDU3H_XHC_REGS_AXIWRA,
+				   (USBAXIWR_UA_MASK | USBAXIWR_SA_MASK),
+				   (USBAXIWR_UA_VAL | USBAXIWR_SA_VAL));
+
+		mmio_clrsetbits_32(DRDU3H_XHC_REGS_AXIRDA,
+				   (USBAXIRD_UA_MASK | USBAXIRD_SA_MASK),
+				   (USBAXIRD_UA_VAL | USBAXIRD_SA_VAL));
+
+		mmio_clrsetbits_32(DRDU3D_BDC_REGS_AXIWRA,
+				   (USBAXIWR_UA_MASK | USBAXIWR_SA_MASK),
+				   (USBAXIWR_UA_VAL | USBAXIWR_SA_VAL));
+
+		mmio_clrsetbits_32(DRDU3D_BDC_REGS_AXIRDA,
+				   (USBAXIRD_UA_MASK | USBAXIRD_SA_MASK),
+				   (USBAXIRD_UA_VAL | USBAXIRD_SA_VAL));
+	}
+}
+#endif
+
+void xhci_phy_init(void)
+{
+	uint32_t val;
+
+	INFO("usb init start\n");
+	mmio_setbits_32(CDRU_MISC_CLK_ENABLE_CONTROL,
+			CDRU_MISC_CLK_USBSS);
+
+	mmio_setbits_32(CDRU_MISC_RESET_CONTROL, CDRU_USBSS_RESET_N);
+
+	if (usb_func & USB3_DRD) {
+		VERBOSE(" - configure stream_id = 0x6800 for DRDU3\n");
+		val = SR_SID_VAL(0x3U, 0x1U, 0x0U) << ICFG_USB_SID_SHIFT;
+		mmio_write_32(ICFG_DRDU3_SID_CTRL + ICFG_USB_SID_AWADDR_OFFSET,
+				val);
+		mmio_write_32(ICFG_DRDU3_SID_CTRL + ICFG_USB_SID_ARADDR_OFFSET,
+				val);
+
+		/*
+		 * DRDU3 Device USB Space, DRDU3 Host USB Space,
+		 * DRDU3 SS Config
+		 */
+		mmio_setbits_32(USBIC_GPV_SECURITY10,
+				USBIC_GPV_SECURITY10_FIELD);
+	}
+
+	if (usb_func & USB3H_USB2DRD) {
+		VERBOSE(" - configure stream_id = 0x6801 for USB3H\n");
+		val = SR_SID_VAL(0x3U, 0x1U, 0x1U) << ICFG_USB_SID_SHIFT;
+		mmio_write_32(ICFG_USB3H_SID_CTRL + ICFG_USB_SID_AWADDR_OFFSET,
+				val);
+		mmio_write_32(ICFG_USB3H_SID_CTRL + ICFG_USB_SID_ARADDR_OFFSET,
+				val);
+
+		VERBOSE(" - configure stream_id = 0x6802 for DRDU2\n");
+		val = SR_SID_VAL(0x3U, 0x1U, 0x2U) << ICFG_USB_SID_SHIFT;
+		mmio_write_32(ICFG_DRDU2_SID_CTRL + ICFG_USB_SID_AWADDR_OFFSET,
+				val);
+		mmio_write_32(ICFG_DRDU2_SID_CTRL + ICFG_USB_SID_ARADDR_OFFSET,
+				val);
+
+		/* DRDU2 APB Bridge:DRDU2 USB Device, USB3H SS Config */
+		mmio_setbits_32(USBIC_GPV_SECURITY1, USBIC_GPV_SECURITY1_FIELD);
+
+		/*
+		 * USB3H APB Bridge:DRDU2 Host + USB3 Host USB Space,
+		 * USB3H SS Config
+		 */
+		mmio_setbits_32(USBIC_GPV_SECURITY2, USBIC_GPV_SECURITY2_FIELD);
+	}
+
+	/* Configure Host masters as non-Secure */
+	mmio_setbits_32(USBSS_TZPCDECPROT0set, USBSS_TZPCDECPROT0);
+
+	/* CCN Slave on USBIC */
+	mmio_setbits_32(USBIC_GPV_SECURITY0, USBIC_GPV_SECURITY0_FIELD);
+
+	/* SLAVE_8:IDM Register Space */
+	mmio_setbits_32(USBIC_GPV_SECURITY4, USBIC_GPV_SECURITY4_FIELD);
+
+	usb3_phy_init();
+#ifdef USB_DMA_COHERENT
+	usb_enable_coherence();
+#endif
+
+	usb_device_init(usb_func);
+
+	INFO("PLAT USB: init done.\n");
+}
diff --git a/plat/brcm/board/stingray/driver/usb_phy.c b/plat/brcm/board/stingray/driver/usb_phy.c
new file mode 100644
index 0000000..54c98e1
--- /dev/null
+++ b/plat/brcm/board/stingray/driver/usb_phy.c
@@ -0,0 +1,601 @@
+/*
+ * Copyright (c) 2019 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <platform_usb.h>
+#include <usb_phy.h>
+
+#define USB_PHY_ALREADY_STARTED	(-2)
+#define USB_MAX_DEVICES		 2
+#define USB3H_USB2DRD_PHY	 0
+#define USB3_DRD_PHY		 1
+
+/* Common bit fields for all the USB2 phy */
+#define USB2_PHY_ISO		DRDU2_U2PHY_ISO
+#define USB2_AFE_PLL_PWRDWNB	DRDU2_U2AFE_PLL_PWRDWNB
+#define USB2_AFE_BG_PWRDWNB	DRDU2_U2AFE_BG_PWRDWNB
+#define USB2_AFE_LDO_PWRDWNB	DRDU2_U2AFE_LDO_PWRDWNB
+#define USB2_CTRL_CORERDY	DRDU2_U2CTRL_CORERDY
+
+#define USB2_PHY_PCTL_MASK	DRDU2_U2PHY_PCTL_MASK
+#define USB2_PHY_PCTL_OFFSET	DRDU2_U2PHY_PCTL_OFFSET
+#define USB2_PHY_PCTL_VAL	U2PHY_PCTL_VAL
+
+#define USB2_PLL_RESETB		DRDU2_U2PLL_RESETB
+#define USB2_PHY_RESETB		DRDU2_U2PHY_RESETB
+
+static usb_phy_port_t usb_phy_port[2U][MAX_NR_PORTS];
+
+static usb_phy_t usb_phy_info[2U] = {
+	{DRDU2_U2PLL_NDIV_FRAC, USB3H_PIPE_CTRL, 0U, USB3H_DRDU2_PHY},
+	{0U, 0U, DRDU3_PIPE_CTRL, DRDU3_PHY}
+};
+
+typedef struct {
+	void *pcd_id;
+} usb_platform_dev;
+
+/* index 0: USB3H + USB2 DRD, 1: USB3 DRD */
+static usb_platform_dev xhci_devices_configs[USB_MAX_DEVICES] = {
+	{&usb_phy_info[0U]},
+	{&usb_phy_info[1U]}
+};
+
+static int32_t pll_lock_check(uint32_t address, uint32_t bit)
+{
+	uint32_t retry;
+	uint32_t data;
+
+	retry = PLL_LOCK_RETRY_COUNT;
+	do {
+		data = mmio_read_32(address);
+		if ((data & bit) != 0U) {
+			return 0;
+		}
+		udelay(1);
+	} while (--retry != 0);
+
+	ERROR("%s(): FAIL (0x%08x)\n", __func__, address);
+	return -1;
+}
+
+/*
+ * USB2 PHY using external FSM bringup sequence
+ * Total #3 USB2 phys. All phys has the same
+ * bringup sequence. Register bit fields for
+ * some of the PHY's are different.
+ * Bit fields which are different are passed using
+ * struct u2_phy_ext_fsm with bit-fields and register addr.
+ */
+
+static void u2_phy_ext_fsm_power_on(struct u2_phy_ext_fsm *u2_phy)
+{
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_PHY_ISO);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, u2_phy->phy_iddq);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+
+	mmio_clrbits_32(u2_phy->phy_ctrl_reg,
+			(USB2_AFE_BG_PWRDWNB |
+			 USB2_AFE_PLL_PWRDWNB |
+			 USB2_AFE_LDO_PWRDWNB |
+			 USB2_CTRL_CORERDY));
+
+	mmio_clrsetbits_32(u2_phy->phy_ctrl_reg,
+			   (USB2_PHY_PCTL_MASK << USB2_PHY_PCTL_OFFSET),
+			   (USB2_PHY_PCTL_VAL << USB2_PHY_PCTL_OFFSET));
+	/* Delay as per external FSM spec */
+	udelay(160U);
+
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_CTRL_CORERDY);
+	/* Delay as per external FSM spec */
+	udelay(50U);
+
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_AFE_BG_PWRDWNB);
+	/* Delay as per external FSM spec */
+	udelay(200U);
+
+	mmio_setbits_32(u2_phy->pwr_ctrl_reg, u2_phy->pwr_onin);
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_AFE_LDO_PWRDWNB);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+
+	mmio_setbits_32(u2_phy->pwr_ctrl_reg, u2_phy->pwr_okin);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_AFE_PLL_PWRDWNB);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+
+	mmio_clrbits_32(u2_phy->phy_ctrl_reg, USB2_PHY_ISO);
+	/* Delay as per external FSM spec */
+	udelay(10U);
+	mmio_clrbits_32(u2_phy->phy_ctrl_reg, u2_phy->phy_iddq);
+	/* Delay as per external FSM spec */
+	udelay(1U);
+
+	mmio_setbits_32(u2_phy->pll_ctrl_reg, USB2_PLL_RESETB);
+	mmio_setbits_32(u2_phy->phy_ctrl_reg, USB2_PHY_RESETB);
+
+}
+
+static int32_t usb3h_u2_phy_power_on(uint32_t base)
+{
+	int32_t status;
+	struct u2_phy_ext_fsm u2_phy;
+
+	u2_phy.pll_ctrl_reg = base + USB3H_U2PLL_CTRL;
+	u2_phy.phy_ctrl_reg = base + USB3H_U2PHY_CTRL;
+	u2_phy.phy_iddq = USB3H_U2PHY_IDDQ;
+	u2_phy.pwr_ctrl_reg = base + USB3H_PWR_CTRL;
+	u2_phy.pwr_okin = USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWROKIN;
+	u2_phy.pwr_onin = USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWRONIN;
+
+	u2_phy_ext_fsm_power_on(&u2_phy);
+
+	status = pll_lock_check(base + USB3H_U2PLL_CTRL, USB3H_U2PLL_LOCK);
+	if (status != 0) {
+		/* re-try by toggling the PLL reset */
+		mmio_clrbits_32(base + USB3H_U2PLL_CTRL,
+				(uint32_t)USB3H_U2PLL_RESETB);
+		mmio_setbits_32(base + USB3H_U2PLL_CTRL, USB3H_U2PLL_RESETB);
+		status = pll_lock_check(base + USB3H_U2PLL_CTRL,
+					USB3H_U2PLL_LOCK);
+		if (status != 0)
+			ERROR("%s() re-try PLL lock FAIL (0x%08x)\n", __func__,
+			      base + USB3H_U2PLL_CTRL);
+	}
+
+	mmio_clrsetbits_32(base + USB3H_U2PHY_CTRL,
+			   (USB3H_U2PHY_PCTL_MASK << USB3H_U2PHY_PCTL_OFFSET),
+			   (U2PHY_PCTL_NON_DRV_LOW << USB3H_U2PHY_PCTL_OFFSET));
+	return status;
+}
+
+static int32_t usb3h_u3_phy_power_on(uint32_t base)
+{
+	int32_t status;
+
+	/* Set pctl with mode and soft reset */
+	mmio_clrsetbits_32(base + USB3H_U3PHY_CTRL,
+			   (USB3H_U3PHY_PCTL_MASK << USB3H_U3PHY_PCTL_OFFSET),
+			   (U3PHY_PCTL_VAL << USB3H_U3PHY_PCTL_OFFSET));
+
+	mmio_clrbits_32(base + USB3H_U3PHY_PLL_CTRL,
+			(uint32_t) USB3H_U3SSPLL_SUSPEND_EN);
+	mmio_setbits_32(base + USB3H_U3PHY_PLL_CTRL, USB3H_U3PLL_SEQ_START);
+	mmio_setbits_32(base + USB3H_U3PHY_PLL_CTRL, USB3H_U3PLL_RESETB);
+
+	/* Time to stabilize the PLL Control */
+	mdelay(1U);
+
+	status = pll_lock_check(base + USB3H_U3PHY_PLL_CTRL,
+				USB3H_U3PLL_SS_LOCK);
+
+	return status;
+}
+
+static int32_t drdu3_u2_phy_power_on(uint32_t base)
+{
+	int32_t status;
+	struct u2_phy_ext_fsm u2_phy;
+
+	u2_phy.pll_ctrl_reg = base + DRDU3_U2PLL_CTRL;
+	u2_phy.phy_ctrl_reg = base + DRDU3_U2PHY_CTRL;
+	u2_phy.phy_iddq = DRDU3_U2PHY_IDDQ;
+	u2_phy.pwr_ctrl_reg = base + DRDU3_PWR_CTRL;
+	u2_phy.pwr_okin = DRDU3_U2PHY_DFE_SWITCH_PWROKIN;
+	u2_phy.pwr_onin = DRDU3_U2PHY_DFE_SWITCH_PWRONIN;
+
+	u2_phy_ext_fsm_power_on(&u2_phy);
+
+	status = pll_lock_check(base + DRDU3_U2PLL_CTRL, DRDU3_U2PLL_LOCK);
+	if (status != 0) {
+		/* re-try by toggling the PLL reset */
+		mmio_clrbits_32(base + DRDU3_U2PLL_CTRL,
+				(uint32_t)DRDU2_U2PLL_RESETB);
+		mmio_setbits_32(base + DRDU3_U2PLL_CTRL, DRDU3_U2PLL_RESETB);
+
+		status = pll_lock_check(base + DRDU3_U2PLL_CTRL,
+					DRDU3_U2PLL_LOCK);
+		if (status != 0) {
+			ERROR("%s() re-try PLL lock FAIL (0x%08x)\n", __func__,
+			      base + DRDU3_U2PLL_CTRL);
+		}
+	}
+	mmio_clrsetbits_32(base + DRDU3_U2PHY_CTRL,
+			   (DRDU3_U2PHY_PCTL_MASK << DRDU3_U2PHY_PCTL_OFFSET),
+			   (U2PHY_PCTL_NON_DRV_LOW << DRDU3_U2PHY_PCTL_OFFSET));
+
+	return status;
+}
+
+static int32_t drdu3_u3_phy_power_on(uint32_t base)
+{
+	int32_t status;
+
+	/* Set pctl with mode and soft reset */
+	mmio_clrsetbits_32(base + DRDU3_U3PHY_CTRL,
+			   (DRDU3_U3PHY_PCTL_MASK << DRDU3_U3PHY_PCTL_OFFSET),
+			   (U3PHY_PCTL_VAL << DRDU3_U3PHY_PCTL_OFFSET));
+
+	mmio_clrbits_32(base + DRDU3_U3PHY_PLL_CTRL,
+			(uint32_t) DRDU3_U3SSPLL_SUSPEND_EN);
+	mmio_setbits_32(base + DRDU3_U3PHY_PLL_CTRL, DRDU3_U3PLL_SEQ_START);
+	mmio_setbits_32(base + DRDU3_U3PHY_PLL_CTRL, DRDU3_U3PLL_RESETB);
+
+	/* Time to stabilize the PLL Control */
+	mdelay(1U);
+
+	status = pll_lock_check(base + DRDU3_U3PHY_PLL_CTRL,
+				DRDU3_U3PLL_SS_LOCK);
+
+	return status;
+}
+
+static int32_t drdu2_u2_phy_power_on(uint32_t base)
+{
+	int32_t status;
+	struct u2_phy_ext_fsm u2_phy;
+
+	u2_phy.pll_ctrl_reg = base + DRDU2_U2PLL_CTRL;
+	u2_phy.phy_ctrl_reg = base + DRDU2_PHY_CTRL;
+	u2_phy.phy_iddq = DRDU2_U2IDDQ;
+	u2_phy.pwr_ctrl_reg = base + DRDU2_PWR_CTRL;
+	u2_phy.pwr_okin = DRDU2_U2PHY_DFE_SWITCH_PWROKIN_I;
+	u2_phy.pwr_onin = DRDU2_U2PHY_DFE_SWITCH_PWRONIN_I;
+
+	u2_phy_ext_fsm_power_on(&u2_phy);
+
+	status = pll_lock_check(base + DRDU2_U2PLL_CTRL, DRDU2_U2PLL_LOCK);
+	if (status != 0) {
+		/* re-try by toggling the PLL reset */
+		mmio_clrbits_32(base + DRDU2_U2PLL_CTRL,
+				(uint32_t)DRDU2_U2PLL_RESETB);
+		mmio_setbits_32(base + DRDU2_U2PLL_CTRL, DRDU2_U2PLL_RESETB);
+
+		status = pll_lock_check(base + DRDU2_U2PLL_CTRL,
+					DRDU2_U2PLL_LOCK);
+		if (status != 0)
+			ERROR("%s() re-try PLL lock FAIL (0x%08x)\n", __func__,
+			      base + DRDU2_U2PLL_CTRL);
+	}
+	mmio_clrsetbits_32(base + DRDU2_PHY_CTRL,
+			   (DRDU2_U2PHY_PCTL_MASK << DRDU2_U2PHY_PCTL_OFFSET),
+			   (U2PHY_PCTL_NON_DRV_LOW << DRDU2_U2PHY_PCTL_OFFSET));
+
+	return status;
+}
+
+void u3h_u2drd_phy_reset(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *phy = phy_port->p;
+
+	switch (phy_port->port_id) {
+	case USB3HS_PORT:
+		mmio_clrbits_32(phy->usb3hreg + USB3H_U2PHY_CTRL,
+				(uint32_t) USB3H_U2CTRL_CORERDY);
+		mmio_setbits_32(phy->usb3hreg + USB3H_U2PHY_CTRL,
+				USB3H_U2CTRL_CORERDY);
+		break;
+	case DRDU2_PORT:
+		mmio_clrbits_32(phy->drdu2reg + DRDU2_PHY_CTRL,
+				(uint32_t) DRDU2_U2CTRL_CORERDY);
+		mmio_setbits_32(phy->drdu2reg + DRDU2_PHY_CTRL,
+				DRDU2_U2CTRL_CORERDY);
+		break;
+	}
+}
+
+void u3drd_phy_reset(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *phy = phy_port->p;
+
+	if (phy_port->port_id == DRD3HS_PORT) {
+		mmio_clrbits_32(phy->drdu3reg + DRDU3_U2PHY_CTRL,
+				(uint32_t) DRDU3_U2CTRL_CORERDY);
+		mmio_setbits_32(phy->drdu3reg + DRDU3_U2PHY_CTRL,
+				DRDU3_U2CTRL_CORERDY);
+	}
+}
+
+static int32_t u3h_u2drd_phy_power_on(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *phy = phy_port->p;
+	int32_t status;
+
+	switch (phy_port->port_id) {
+	case USB3SS_PORT:
+		mmio_clrbits_32(phy->usb3hreg + USB3H_PHY_PWR_CTRL,
+				(uint32_t) USB3H_DISABLE_USB30_P0);
+		status = usb3h_u3_phy_power_on(phy->usb3hreg);
+		if (status != 0) {
+			goto err_usb3h_phy_on;
+		}
+		break;
+	case USB3HS_PORT:
+		mmio_clrbits_32(phy->usb3hreg + USB3H_PHY_PWR_CTRL,
+				(uint32_t) USB3H_DISABLE_EUSB_P1);
+		mmio_setbits_32(AXI_DEBUG_CTRL,
+				AXI_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+		mmio_setbits_32(USB3H_DEBUG_CTRL,
+				USB3H_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+
+		mmio_clrbits_32(phy->usb3hreg + USB3H_PWR_CTRL,
+				USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWRONIN);
+		/* Delay as per external FSM spec */
+		udelay(10U);
+		mmio_clrbits_32(phy->usb3hreg + USB3H_PWR_CTRL,
+				USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWROKIN);
+		status = usb3h_u2_phy_power_on(phy->usb3hreg);
+		if (status != 0) {
+			goto err_usb3h_phy_on;
+		}
+		break;
+	case DRDU2_PORT:
+		mmio_clrbits_32(phy->usb3hreg + USB3H_PHY_PWR_CTRL,
+				(uint32_t) USB3H_DISABLE_EUSB_P0);
+		mmio_setbits_32(AXI_DEBUG_CTRL,
+				AXI_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+		mmio_setbits_32(USB3H_DEBUG_CTRL,
+				USB3H_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+
+		mmio_clrbits_32(phy->usb3hreg + DRDU2_PWR_CTRL,
+				DRDU2_U2PHY_DFE_SWITCH_PWRONIN_I);
+		/* Delay as per external FSM spec */
+		udelay(10U);
+		mmio_clrbits_32(phy->usb3hreg + DRDU2_PWR_CTRL,
+				DRDU2_U2PHY_DFE_SWITCH_PWROKIN_I);
+
+		status = drdu2_u2_phy_power_on(phy->drdu2reg);
+		if (status != 0) {
+			mmio_setbits_32(phy->usb3hreg + USB3H_PHY_PWR_CTRL,
+					USB3H_DISABLE_EUSB_P0);
+			goto err_drdu2_phy_on;
+		}
+		break;
+	}
+
+	/* Device Mode */
+	if (phy_port->port_id == DRDU2_PORT) {
+		mmio_write_32(phy->drdu2reg + DRDU2_SOFT_RESET_CTRL,
+			      DRDU2_BDC_AXI_SOFT_RST_N);
+		mmio_setbits_32(phy->drdu2reg + DRDU2_PHY_CTRL,
+				DRDU2_U2SOFT_RST_N);
+	}
+	/* Host Mode */
+	mmio_write_32(phy->usb3hreg + USB3H_SOFT_RESET_CTRL,
+		      USB3H_XHC_AXI_SOFT_RST_N);
+	mmio_setbits_32(phy->usb3hreg + USB3H_U3PHY_CTRL, USB3H_U3SOFT_RST_N);
+
+	return 0U;
+ err_usb3h_phy_on:mmio_setbits_32(phy->usb3hreg + USB3H_PHY_PWR_CTRL,
+			(USB3H_DISABLE_EUSB_P1 |
+			 USB3H_DISABLE_USB30_P0));
+ err_drdu2_phy_on:
+
+	return status;
+}
+
+static int32_t u3drd_phy_power_on(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *phy = phy_port->p;
+	int32_t status;
+
+	switch (phy_port->port_id) {
+	case DRD3SS_PORT:
+		mmio_clrbits_32(phy->drdu3reg + DRDU3_PHY_PWR_CTRL,
+				(uint32_t) DRDU3_DISABLE_USB30_P0);
+
+		status = drdu3_u3_phy_power_on(phy->drdu3reg);
+		if (status != 0) {
+			goto err_drdu3_phy_on;
+		}
+		break;
+	case DRD3HS_PORT:
+		mmio_clrbits_32(phy->drdu3reg + DRDU3_PHY_PWR_CTRL,
+				(uint32_t) DRDU3_DISABLE_EUSB_P0);
+		mmio_setbits_32(AXI_DEBUG_CTRL,
+				AXI_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+		mmio_setbits_32(USB3H_DEBUG_CTRL,
+				USB3H_DBG_CTRL_SSPHY_DRD_MODE_DISABLE);
+
+		mmio_clrbits_32(phy->drdu3reg + DRDU3_PWR_CTRL,
+				DRDU3_U2PHY_DFE_SWITCH_PWRONIN);
+		/* Delay as per external FSM spec */
+		udelay(10U);
+		mmio_clrbits_32(phy->drdu3reg + DRDU3_PWR_CTRL,
+				DRDU3_U2PHY_DFE_SWITCH_PWROKIN);
+
+		status = drdu3_u2_phy_power_on(phy->drdu3reg);
+		if (status != 0) {
+			goto err_drdu3_phy_on;
+		}
+
+		/* Host Mode */
+		mmio_setbits_32(phy->drdu3reg + DRDU3_SOFT_RESET_CTRL,
+				DRDU3_XHC_AXI_SOFT_RST_N);
+		mmio_setbits_32(phy->drdu3reg + DRDU3_U3PHY_CTRL,
+				DRDU3_U3XHC_SOFT_RST_N);
+		/* Device Mode */
+		mmio_setbits_32(phy->drdu3reg + DRDU3_SOFT_RESET_CTRL,
+				DRDU3_BDC_AXI_SOFT_RST_N);
+		mmio_setbits_32(phy->drdu3reg + DRDU3_U3PHY_CTRL,
+				DRDU3_U3BDC_SOFT_RST_N);
+		break;
+	}
+
+	return 0U;
+ err_drdu3_phy_on:mmio_setbits_32(phy->drdu3reg + DRDU3_PHY_PWR_CTRL,
+			(DRDU3_DISABLE_EUSB_P0 |
+			 DRDU3_DISABLE_USB30_P0));
+
+	return status;
+}
+
+static void u3h_u2drd_phy_power_off(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *p = phy_port->p;
+
+	switch (phy_port->port_id) {
+	case USB3SS_PORT:
+		mmio_setbits_32(p->usb3hreg + USB3H_PHY_PWR_CTRL,
+				USB3H_DISABLE_USB30_P0);
+		break;
+	case USB3HS_PORT:
+		mmio_setbits_32(p->usb3hreg + USB3H_PHY_PWR_CTRL,
+				USB3H_DISABLE_EUSB_P1);
+		break;
+	case DRDU2_PORT:
+		mmio_setbits_32(p->usb3hreg + USB3H_PHY_PWR_CTRL,
+				USB3H_DISABLE_EUSB_P0);
+		break;
+	}
+}
+
+static void u3drd_phy_power_off(usb_phy_port_t *phy_port)
+{
+	usb_phy_t *p = phy_port->p;
+
+	switch (phy_port->port_id) {
+	case DRD3SS_PORT:
+		mmio_setbits_32(p->drdu3reg + DRDU3_PHY_PWR_CTRL,
+				DRDU3_DISABLE_USB30_P0);
+		break;
+	case DRD3HS_PORT:
+		mmio_setbits_32(p->drdu3reg + DRDU3_PHY_PWR_CTRL,
+				DRDU3_DISABLE_EUSB_P0);
+		break;
+	}
+}
+
+int32_t usb_info_fill(usb_phy_t *phy_info)
+{
+	int32_t index;
+
+	if (phy_info->initialized != 0U) {
+		return USB_PHY_ALREADY_STARTED;
+	}
+
+	if (phy_info->phy_id == USB3H_DRDU2_PHY) {
+		phy_info->phy_port = usb_phy_port[USB3H_DRDU2_PHY - 1U];
+		phy_info->ports_enabled = 0x7U;
+	} else {
+		phy_info->phy_port = usb_phy_port[DRDU3_PHY - 1U];
+		phy_info->ports_enabled = 0x3U;
+	}
+
+	for (index = MAX_NR_PORTS - 1U; index > -1; index--) {
+		phy_info->phy_port[index].enabled = (phy_info->ports_enabled
+						     >> index) & 0x1U;
+		phy_info->phy_port[index].p = phy_info;
+		phy_info->phy_port[index].port_id = index;
+	}
+
+	return 0U;
+}
+
+int32_t usb_phy_init(usb_platform_dev *device)
+{
+	int32_t status;
+	usb_phy_t *phy_info;
+	uint32_t index;
+
+	phy_info = (usb_phy_t *)device->pcd_id;
+
+	status = usb_info_fill(phy_info);
+	if (status != 0) {
+		return (status == USB_PHY_ALREADY_STARTED) ? 0 : status;
+	}
+
+	for (index = 0U; index < MAX_NR_PORTS; index++) {
+		if (phy_info->phy_port[index].enabled != 0U) {
+			switch (phy_info->phy_id) {
+			case USB3H_DRDU2_PHY:
+				status =
+				    u3h_u2drd_phy_power_on(&phy_info->
+							   phy_port[index]);
+				break;
+			default:
+				status =
+				    u3drd_phy_power_on(&phy_info->
+						       phy_port[index]);
+			}
+		}
+	}
+
+	phy_info->initialized = !status;
+	return status;
+}
+
+void usb_phy_shutdown(usb_platform_dev *device)
+{
+	usb_phy_t *phy_info;
+	uint32_t index;
+
+	phy_info = (usb_phy_t *)device->pcd_id;
+
+	phy_info->initialized = 0U;
+
+	for (index = 0U; index < MAX_NR_PORTS; index++) {
+		if (phy_info->phy_port[index].enabled != 0U) {
+			switch (phy_info->phy_id) {
+			case USB3H_DRDU2_PHY:
+				u3h_u2drd_phy_power_off(&phy_info->
+							phy_port[index]);
+				break;
+			case DRDU3_PHY:
+				u3drd_phy_power_off(&phy_info->phy_port[index]);
+				break;
+			default:
+				INFO("%s: invalid phy id 0x%x\n", __func__,
+				     phy_info->phy_id);
+			}
+		}
+	}
+}
+
+int32_t usb_xhci_init(usb_platform_dev *device)
+{
+	int32_t status;
+
+	status = usb_phy_init(device);
+	if (status == USB_PHY_ALREADY_STARTED) {
+		status = 0U;
+	}
+
+	return status;
+}
+
+int32_t usb_device_init(unsigned int usb_func)
+{
+	int32_t status;
+	int32_t devices_initialized = 0U;
+
+	if ((usb_func & USB3H_USB2DRD) != 0U) {
+		status = usb_xhci_init(
+				&xhci_devices_configs[USB3H_USB2DRD_PHY]);
+		if (status == 0) {
+			devices_initialized++;
+		} else {
+			ERROR("%s(): USB3H_USB2DRD init failure\n", __func__);
+		}
+	}
+
+	if ((usb_func & USB3_DRD) != 0U) {
+		status = usb_xhci_init(&xhci_devices_configs[USB3_DRD_PHY]);
+		if (status == 0) {
+			devices_initialized++;
+		} else {
+			ERROR("%s(): USB3_DRD init failure\n", __func__);
+		}
+	}
+
+	return devices_initialized;
+}
diff --git a/plat/brcm/board/stingray/include/platform_usb.h b/plat/brcm/board/stingray/include/platform_usb.h
new file mode 100644
index 0000000..5b5309f
--- /dev/null
+++ b/plat/brcm/board/stingray/include/platform_usb.h
@@ -0,0 +1,19 @@
+/*
+ * Copyright (c) 2019 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_USB_H
+#define PLATFORM_USB_H
+
+#include <platform_def.h>
+
+#define USB3_DRD		BIT(0U)
+#define USB3H_USB2DRD		BIT(1U)
+
+extern const unsigned int xhc_portsc_reg_offset[MAX_USB_PORTS];
+
+void xhci_phy_init(void);
+
+#endif /* PLATFORM_USB_H */
diff --git a/plat/brcm/board/stingray/include/sr_def.h b/plat/brcm/board/stingray/include/sr_def.h
index be0dee1..277836e 100644
--- a/plat/brcm/board/stingray/include/sr_def.h
+++ b/plat/brcm/board/stingray/include/sr_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, Broadcom
+ * Copyright (c) 2016-2021, Broadcom
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -193,6 +193,11 @@
 #define PLAT_CHIP_REV_GET	(mmio_read_32(ICFG_CHIP_REVISION_ID))
 
 /*******************************************************************************
+ * CMIC MII (MDIO) related constant
+ ******************************************************************************/
+#define PLAT_CMIC_MIIM_BASE	0x68920000U
+
+/*******************************************************************************
  * Timers related constants
  ******************************************************************************/
 /* ChipcommonG_tim0_TIM_TIMER1Load 0x68930000 */
diff --git a/plat/brcm/board/stingray/include/usb_phy.h b/plat/brcm/board/stingray/include/usb_phy.h
new file mode 100644
index 0000000..7d83182
--- /dev/null
+++ b/plat/brcm/board/stingray/include/usb_phy.h
@@ -0,0 +1,244 @@
+/*
+ * Copyright (c) 2017 - 2021, Broadcom
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef USB_PHY_H
+#define USB_PHY_H
+
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include <platform_def.h>
+
+#define DRDU2_U2PLL_NDIV_FRAC_OFFSET            0x0U
+
+#define DRDU2_U2PLL_NDIV_INT                    0x4U
+
+#define DRDU2_U2PLL_CTRL                        0x8U
+#define DRDU2_U2PLL_LOCK                        BIT(6U)
+#define DRDU2_U2PLL_RESETB                      BIT(5U)
+#define DRDU2_U2PLL_PDIV_MASK                   0xFU
+#define DRDU2_U2PLL_PDIV_OFFSET                 1U
+#define DRDU2_U2PLL_SUSPEND_EN                  BIT(0U)
+
+#define DRDU2_PHY_CTRL                          0x0CU
+#define DRDU2_U2IDDQ                            BIT(30U)
+#define DRDU2_U2SOFT_RST_N                      BIT(29U)
+#define DRDU2_U2PHY_ON_FLAG                     BIT(22U)
+#define DRDU2_U2PHY_PCTL_MASK                   0xFFFFU
+#define DRDU2_U2PHY_PCTL_OFFSET                 6U
+#define DRDU2_U2PHY_RESETB                      BIT(5U)
+#define DRDU2_U2PHY_ISO                         BIT(4U)
+#define DRDU2_U2AFE_BG_PWRDWNB                  BIT(3U)
+#define DRDU2_U2AFE_PLL_PWRDWNB                 BIT(2U)
+#define DRDU2_U2AFE_LDO_PWRDWNB                 BIT(1U)
+#define DRDU2_U2CTRL_CORERDY                    BIT(0U)
+
+#define DRDU2_STRAP_CTRL                        0x18U
+#define DRDU2_FORCE_HOST_MODE                   BIT(5U)
+#define DRDU2_FORCE_DEVICE_MODE                 BIT(4U)
+#define BDC_USB_STP_SPD_MASK                    0x7U
+#define BDC_USB_STP_SPD_OFFSET                  0U
+
+#define DRDU2_PWR_CTRL                          0x1CU
+#define DRDU2_U2PHY_DFE_SWITCH_PWROKIN_I        BIT(2U)
+#define DRDU2_U2PHY_DFE_SWITCH_PWRONIN_I        BIT(1U)
+
+#define DRDU2_SOFT_RESET_CTRL                   0x20U
+#define DRDU2_BDC_AXI_SOFT_RST_N                BIT(0U)
+
+#define USB3H_U2PLL_NDIV_FRAC                   0x4U
+
+#define USB3H_U2PLL_NDIV_INT                    0x8U
+
+#define USB3H_U2PLL_CTRL                        0xCU
+#define USB3H_U2PLL_LOCK                        BIT(6U)
+#define USB3H_U2PLL_RESETB                      BIT(5U)
+#define USB3H_U2PLL_PDIV_MASK                   0xFU
+#define USB3H_U2PLL_PDIV_OFFSET                 1U
+
+#define USB3H_U2PHY_CTRL                        0x10U
+#define USB3H_U2PHY_ON_FLAG                     22U
+#define USB3H_U2PHY_PCTL_MASK                   0xFFFFU
+#define USB3H_U2PHY_PCTL_OFFSET                 6U
+#define USB3H_U2PHY_IDDQ                        BIT(29U)
+#define USB3H_U2PHY_RESETB                      BIT(5U)
+#define USB3H_U2PHY_ISO                         BIT(4U)
+#define USB3H_U2AFE_BG_PWRDWNB                  BIT(3U)
+#define USB3H_U2AFE_PLL_PWRDWNB                 BIT(2U)
+#define USB3H_U2AFE_LDO_PWRDWNB                 BIT(1U)
+#define USB3H_U2CTRL_CORERDY                    BIT(0U)
+
+#define USB3H_U3PHY_CTRL                        0x14U
+#define USB3H_U3SOFT_RST_N                      BIT(30U)
+#define USB3H_U3MDIO_RESETB_I                   BIT(29U)
+#define USB3H_U3POR_RESET_I                     BIT(28U)
+#define USB3H_U3PHY_PCTL_MASK                   0xFFFFU
+#define USB3H_U3PHY_PCTL_OFFSET                 2U
+#define USB3H_U3PHY_RESETB                      BIT(1U)
+
+#define USB3H_U3PHY_PLL_CTRL                    0x18U
+#define USB3H_U3PLL_REFCLK_MASK                 0x7U
+#define USB3H_U3PLL_REFCLK_OFFSET               4U
+#define USB3H_U3PLL_SS_LOCK                     BIT(3U)
+#define USB3H_U3PLL_SEQ_START                   BIT(2U)
+#define USB3H_U3SSPLL_SUSPEND_EN                BIT(1U)
+#define USB3H_U3PLL_RESETB                      BIT(0U)
+
+#define USB3H_PWR_CTRL                          0x28U
+#define USB3H_PWR_CTRL_OVERRIDE_I_R             4U
+#define USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWROKIN BIT(11U)
+#define USB3H_PWR_CTRL_U2PHY_DFE_SWITCH_PWRONIN BIT(10U)
+
+#define USB3H_SOFT_RESET_CTRL                   0x2CU
+#define USB3H_XHC_AXI_SOFT_RST_N                BIT(1U)
+
+#define USB3H_PHY_PWR_CTRL                      0x38U
+#define USB3H_DISABLE_USB30_P0                  BIT(2U)
+#define USB3H_DISABLE_EUSB_P1                   BIT(1U)
+#define USB3H_DISABLE_EUSB_P0                   BIT(0U)
+
+
+#define DRDU3_U2PLL_NDIV_FRAC                   0x4U
+
+#define DRDU3_U2PLL_NDIV_INT                    0x8U
+
+#define DRDU3_U2PLL_CTRL                        0xCU
+#define DRDU3_U2PLL_LOCK                        BIT(6U)
+#define DRDU3_U2PLL_RESETB                      BIT(5U)
+#define DRDU3_U2PLL_PDIV_MASK                   0xFU
+#define DRDU3_U2PLL_PDIV_OFFSET                 1U
+
+#define DRDU3_U2PHY_CTRL                        0x10U
+#define DRDU3_U2PHY_IDDQ                        BIT(29U)
+#define DRDU3_U2PHY_ON_FLAG                     BIT(22U)
+#define DRDU3_U2PHY_PCTL_MASK                   0xFFFFU
+#define DRDU3_U2PHY_PCTL_OFFSET                 6U
+#define DRDU3_U2PHY_RESETB                      BIT(5U)
+#define DRDU3_U2PHY_ISO                         BIT(4U)
+#define DRDU3_U2AFE_BG_PWRDWNB                  BIT(3U)
+#define DRDU3_U2AFE_PLL_PWRDWNB                 BIT(2U)
+#define DRDU3_U2AFE_LDO_PWRDWNB                 BIT(1U)
+#define DRDU3_U2CTRL_CORERDY                    BIT(0U)
+
+#define DRDU3_U3PHY_CTRL                        0x14U
+#define DRDU3_U3XHC_SOFT_RST_N                  BIT(31U)
+#define DRDU3_U3BDC_SOFT_RST_N                  BIT(30U)
+#define DRDU3_U3MDIO_RESETB_I                   BIT(29U)
+#define DRDU3_U3POR_RESET_I                     BIT(28U)
+#define DRDU3_U3PHY_PCTL_MASK                   0xFFFFU
+#define DRDU3_U3PHY_PCTL_OFFSET                 2U
+#define DRDU3_U3PHY_RESETB                      BIT(1U)
+
+#define DRDU3_U3PHY_PLL_CTRL                    0x18U
+#define DRDU3_U3PLL_REFCLK_MASK                 0x7U
+#define DRDU3_U3PLL_REFCLK_OFFSET               4U
+#define DRDU3_U3PLL_SS_LOCK                     BIT(3U)
+#define DRDU3_U3PLL_SEQ_START                   BIT(2U)
+#define DRDU3_U3SSPLL_SUSPEND_EN                BIT(1U)
+#define DRDU3_U3PLL_RESETB                      BIT(0U)
+
+#define DRDU3_STRAP_CTRL                        0x28U
+#define BDC_USB_STP_SPD_MASK                    0x7U
+#define BDC_USB_STP_SPD_OFFSET                  0U
+#define BDC_USB_STP_SPD_SS                      0x0U
+#define BDC_USB_STP_SPD_HS                      0x2U
+
+#define DRDU3_PWR_CTRL                          0x2cU
+#define DRDU3_U2PHY_DFE_SWITCH_PWROKIN          BIT(12U)
+#define DRDU3_U2PHY_DFE_SWITCH_PWRONIN          BIT(11U)
+#define DRDU3_PWR_CTRL_OVERRIDE_I_R             4U
+
+#define DRDU3_SOFT_RESET_CTRL                   0x30U
+#define DRDU3_XHC_AXI_SOFT_RST_N                BIT(1U)
+#define DRDU3_BDC_AXI_SOFT_RST_N                BIT(0U)
+
+#define DRDU3_PHY_PWR_CTRL                      0x3cU
+#define DRDU3_DISABLE_USB30_P0                  BIT(2U)
+#define DRDU3_DISABLE_EUSB_P1                   BIT(1U)
+#define DRDU3_DISABLE_EUSB_P0                   BIT(0U)
+
+#define PLL_REFCLK_PAD                          0x0U
+#define PLL_REFCLK_25MHZ                        0x1U
+#define PLL_REFCLK_96MHZ                        0x2U
+#define PLL_REFCLK_INTERNAL                     0x3U
+/* USB PLL lock time out for 10 ms */
+#define PLL_LOCK_RETRY_COUNT                    10000U
+
+
+#define U2PLL_NDIV_INT_VAL                      0x13U
+#define U2PLL_NDIV_FRAC_VAL                     0x1005U
+#define U2PLL_PDIV_VAL                          0x1U
+/*
+ * Using external FSM
+ * BIT-3:2: device mode; mode is not effect
+ * BIT-1: soft reset active low
+ */
+#define U2PHY_PCTL_VAL                          0x0003U
+/* Non-driving signal low */
+#define U2PHY_PCTL_NON_DRV_LOW                  0x0002U
+#define U3PHY_PCTL_VAL                          0x0006U
+
+#define MAX_NR_PORTS                            3U
+
+#define USB3H_DRDU2_PHY                         1U
+#define DRDU3_PHY                               2U
+
+#define USB_HOST_MODE                           1U
+#define USB_DEV_MODE                            2U
+
+#define USB3SS_PORT                             0U
+#define DRDU2_PORT                              1U
+#define USB3HS_PORT                             2U
+
+#define DRD3SS_PORT                             0U
+#define DRD3HS_PORT                             1U
+
+#define SR_USB_PHY_COUNT                        2U
+
+#define DRDU3_PIPE_CTRL			0x68500000U
+#define DRDU3H_XHC_REGS_CPLIVER		0x68501000U
+#define USB3H_PIPE_CTRL			0x68510000U
+#define DRD2U3H_XHC_REGS_CPLIVER	0x68511000U
+#define DRDU2_U2PLL_NDIV_FRAC		0x68520000U
+
+#define AXI_DEBUG_CTRL				0x68500038U
+#define AXI_DBG_CTRL_SSPHY_DRD_MODE_DISABLE	BIT(12U)
+
+#define USB3H_DEBUG_CTRL			0x68510034U
+#define USB3H_DBG_CTRL_SSPHY_DRD_MODE_DISABLE	BIT(7U)
+
+typedef struct _usb_phy_port usb_phy_port_t;
+
+typedef struct {
+	uint32_t drdu2reg;
+	uint32_t usb3hreg;
+	uint32_t drdu3reg;
+	uint32_t phy_id;
+	uint32_t ports_enabled;
+	uint32_t initialized;
+	usb_phy_port_t *phy_port;
+} usb_phy_t;
+
+struct _usb_phy_port {
+	uint32_t port_id;
+	uint32_t mode;
+	uint32_t enabled;
+	usb_phy_t *p;
+};
+
+struct u2_phy_ext_fsm {
+	uint32_t pll_ctrl_reg;
+	uint32_t phy_ctrl_reg;
+	uint32_t phy_iddq;
+	uint32_t pwr_ctrl_reg;
+	uint32_t pwr_okin;
+	uint32_t pwr_onin;
+};
+
+#endif /* USB_PHY_H */
diff --git a/plat/brcm/board/stingray/platform.mk b/plat/brcm/board/stingray/platform.mk
index c5509bb..aa2fe86 100644
--- a/plat/brcm/board/stingray/platform.mk
+++ b/plat/brcm/board/stingray/platform.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2019-2020, Broadcom
+# Copyright (c) 2019-2021, Broadcom
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -73,6 +73,12 @@
 BOARD_CFG := bcm958742t
 endif
 
+# Use USB
+ifeq (${USE_USB},yes)
+$(info Using USB)
+$(eval $(call add_define,USE_USB))
+endif
+
 # Use PAXB
 ifeq (${USE_PAXB},yes)
 $(info Using PAXB)
@@ -190,17 +196,22 @@
 				plat/${SOC_DIR}/src/tz_sec.c \
 				drivers/arm/tzc/tzc400.c \
 				plat/${SOC_DIR}/driver/plat_emmc.c \
-				plat/${SOC_DIR}/src/topology.c
+				plat/${SOC_DIR}/src/topology.c \
+				drivers/brcm/mdio/mdio.c
 
 ifeq (${USE_CHIMP},yes)
 PLAT_BL_COMMON_SOURCES	+=	drivers/brcm/chimp.c
 endif
 
+ifeq (${USE_USB},yes)
+PLAT_BL_COMMON_SOURCES	+=	plat/${SOC_DIR}/driver/usb.c \
+				plat/${SOC_DIR}/driver/usb_phy.c
+endif
+
 BL2_SOURCES		+=	plat/${SOC_DIR}/driver/ihost_pll_config.c \
 				plat/${SOC_DIR}/src/bl2_setup.c \
 				plat/${SOC_DIR}/driver/swreg.c
 
-
 ifeq (${USE_DDR},yes)
 PLAT_INCLUDES		+=	-Iplat/${SOC_DIR}/driver/ddr/soc/include
 else
diff --git a/plat/brcm/board/stingray/src/bl31_setup.c b/plat/brcm/board/stingray/src/bl31_setup.c
index a2a274d..04df6a0 100644
--- a/plat/brcm/board/stingray/src/bl31_setup.c
+++ b/plat/brcm/board/stingray/src/bl31_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015 - 2020, Broadcom
+ * Copyright (c) 2015 - 2021, Broadcom
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -28,6 +28,9 @@
 #include <paxb.h>
 #include <paxc.h>
 #include <platform_def.h>
+#ifdef USE_USB
+#include <platform_usb.h>
+#endif
 #include <sdio.h>
 #include <sr_utils.h>
 #include <timer_sync.h>
diff --git a/plat/brcm/board/stingray/src/brcm_pm_ops.c b/plat/brcm/board/stingray/src/brcm_pm_ops.c
index 03a604c..5e07fac 100644
--- a/plat/brcm/board/stingray/src/brcm_pm_ops.c
+++ b/plat/brcm/board/stingray/src/brcm_pm_ops.c
@@ -6,6 +6,7 @@
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
 
 #include <arch_helpers.h>
 #include <common/debug.h>
@@ -119,7 +120,7 @@
 		standbywfil2 = CDRU_PROC_EVENT_CLEAR__IH3_CDRU_STANDBYWFIL2;
 		break;
 	default:
-		ERROR("Invalid cluster #%llx\n", MPIDR_AFFLVL1_VAL(mpidr));
+		ERROR("Invalid cluster #%" PRIx64 "\n", MPIDR_AFFLVL1_VAL(mpidr));
 		return;
 	}
 	/* Clear the WFI status bit */
diff --git a/plat/common/aarch64/plat_common.c b/plat/common/aarch64/plat_common.c
index ba4c366..38a5786 100644
--- a/plat/common/aarch64/plat_common.c
+++ b/plat/common/aarch64/plat_common.c
@@ -5,6 +5,8 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <arch_helpers.h>
 #include <drivers/console.h>
@@ -28,7 +30,7 @@
 #pragma weak plat_sdei_validate_entry_point
 #endif
 
-#pragma weak plat_ea_handler
+#pragma weak plat_ea_handler = plat_default_ea_handler
 
 void bl31_plat_runtime_setup(void)
 {
@@ -53,7 +55,7 @@
  */
 void plat_sdei_handle_masked_trigger(uint64_t mpidr, unsigned int intr)
 {
-	WARN("Spurious SDEI interrupt %u on masked PE %llx\n", intr, mpidr);
+	WARN("Spurious SDEI interrupt %u on masked PE %" PRIx64 "\n", intr, mpidr);
 }
 
 /*
@@ -79,7 +81,7 @@
 #endif /* !ENABLE_BACKTRACE */
 
 /* RAS functions common to AArch64 ARM platforms */
-void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
+void plat_default_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
 		void *handle, uint64_t flags)
 {
 #if RAS_EXTENSION
@@ -90,9 +92,10 @@
 #endif
 	unsigned int level = (unsigned int)GET_EL(read_spsr_el3());
 
+	ERROR_NL();
 	ERROR("Unhandled External Abort received on 0x%lx from %s\n",
 		read_mpidr_el1(), get_el_str(level));
-	ERROR("exception reason=%u syndrome=0x%llx\n", ea_reason, syndrome);
+	ERROR("exception reason=%u syndrome=0x%" PRIx64 "\n", ea_reason, syndrome);
 #if HANDLE_EA_EL3_FIRST
 	/* Skip backtrace for lower EL */
 	if (level != MODE_EL3) {
diff --git a/plat/common/aarch64/platform_mp_stack.S b/plat/common/aarch64/platform_mp_stack.S
index c34a4cf..c0668ea 100644
--- a/plat/common/aarch64/platform_mp_stack.S
+++ b/plat/common/aarch64/platform_mp_stack.S
@@ -14,7 +14,7 @@
 	.weak	plat_set_my_stack
 
 	/* ---------------------------------------------------------------------
-	 * When the compatility layer is disabled, the platform APIs
+	 * When the compatibility layer is disabled, the platform APIs
 	 * plat_get_my_stack() and plat_set_my_stack() are supported by the
 	 * platform and the previous APIs platform_get_stack() and
 	 * platform_set_stack() are defined in terms of new APIs making use of
diff --git a/plat/common/plat_bl1_common.c b/plat/common/plat_bl1_common.c
index 1c6d68b..bcf9f89 100644
--- a/plat/common/plat_bl1_common.c
+++ b/plat/common/plat_bl1_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, Arm Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -27,9 +27,6 @@
 #pragma weak bl1_plat_fwu_done
 #pragma weak bl1_plat_handle_pre_image_load
 #pragma weak bl1_plat_handle_post_image_load
-#if MEASURED_BOOT
-#pragma weak bl1_plat_set_bl2_hash
-#endif
 
 unsigned int bl1_plat_get_next_image_id(void)
 {
@@ -118,12 +115,3 @@
 		(void *) bl2_secram_layout);
 	return 0;
 }
-
-#if MEASURED_BOOT
-/*
- * Calculates and writes BL2 hash data to TB_FW_CONFIG DTB.
- */
-void bl1_plat_set_bl2_hash(const image_desc_t *image_desc)
-{
-}
-#endif
diff --git a/plat/common/plat_spmd_manifest.c b/plat/common/plat_spmd_manifest.c
index 8f4018c..b1fc13c 100644
--- a/plat/common/plat_spmd_manifest.c
+++ b/plat/common/plat_spmd_manifest.c
@@ -6,8 +6,10 @@
 
 #include <assert.h>
 #include <errno.h>
-#include <string.h>
+#include <inttypes.h>
 #include <libfdt.h>
+#include <stdint.h>
+#include <string.h>
 
 #include <common/bl_common.h>
 #include <common/debug.h>
@@ -80,8 +82,8 @@
 	VERBOSE("  version: %u.%u\n", attr->major_version, attr->minor_version);
 	VERBOSE("  spmc_id: 0x%x\n", attr->spmc_id);
 	VERBOSE("  binary_size: 0x%x\n", attr->binary_size);
-	VERBOSE("  load_address: 0x%llx\n", attr->load_address);
-	VERBOSE("  entrypoint: 0x%llx\n", attr->entrypoint);
+	VERBOSE("  load_address: 0x%" PRIx64 "\n", attr->load_address);
+	VERBOSE("  entrypoint: 0x%" PRIx64 "\n", attr->entrypoint);
 
 	return 0;
 }
diff --git a/plat/hisilicon/hikey/hikey_bl1_setup.c b/plat/hisilicon/hikey/hikey_bl1_setup.c
index 86e4fd6..31ff820 100644
--- a/plat/hisilicon/hikey/hikey_bl1_setup.c
+++ b/plat/hisilicon/hikey/hikey_bl1_setup.c
@@ -1,11 +1,13 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <arch_helpers.h>
@@ -27,6 +29,7 @@
 /* Data structure which holds the extents of the trusted RAM for BL1 */
 static meminfo_t bl1_tzram_layout;
 static console_t console;
+static struct mmc_device_info mmc_info;
 
 enum {
 	BOOT_NORMAL = 0,
@@ -78,7 +81,6 @@
 void bl1_platform_setup(void)
 {
 	dw_mmc_params_t params;
-	struct mmc_device_info info;
 
 	assert((HIKEY_BL1_MMC_DESC_BASE >= SRAM_BASE) &&
 	       ((SRAM_BASE + SRAM_SIZE) >=
@@ -99,8 +101,8 @@
 	params.clk_rate = 24 * 1000 * 1000;
 	params.bus_width = MMC_BUS_WIDTH_8;
 	params.flags = MMC_FLAG_CMD23;
-	info.mmc_dev_type = MMC_IS_EMMC;
-	dw_mmc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	dw_mmc_init(&params, &mmc_info);
 
 	hikey_io_setup();
 }
@@ -155,7 +157,7 @@
 		__asm__ volatile ("msr	cpacr_el1, %0" : : "r"(data));
 		__asm__ volatile ("mrs	%0, cpacr_el1" : "=r"(data));
 	} while ((data & (3 << 20)) != (3 << 20));
-	INFO("cpacr_el1:0x%llx\n", data);
+	INFO("cpacr_el1:0x%" PRIx64 "\n", data);
 
 	ep_info->args.arg0 = 0xffff & read_mpidr();
 	ep_info->spsr = SPSR_64(MODE_EL1, MODE_SP_ELX,
diff --git a/plat/hisilicon/hikey/hikey_bl2_setup.c b/plat/hisilicon/hikey/hikey_bl2_setup.c
index feb7f8a..a90f12c 100644
--- a/plat/hisilicon/hikey/hikey_bl2_setup.c
+++ b/plat/hisilicon/hikey/hikey_bl2_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -33,6 +33,7 @@
 
 static meminfo_t bl2_el3_tzram_layout;
 static console_t console;
+static struct mmc_device_info mmc_info;
 
 enum {
 	BOOT_MODE_RECOVERY = 0,
@@ -290,7 +291,6 @@
 void bl2_platform_setup(void)
 {
 	dw_mmc_params_t params;
-	struct mmc_device_info info;
 
 	hikey_sp804_init();
 	hikey_gpio_init();
@@ -322,8 +322,8 @@
 	params.clk_rate = 24 * 1000 * 1000;
 	params.bus_width = MMC_BUS_WIDTH_8;
 	params.flags = MMC_FLAG_CMD23;
-	info.mmc_dev_type = MMC_IS_EMMC;
-	dw_mmc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	dw_mmc_init(&params, &mmc_info);
 
 	hikey_io_setup();
 }
diff --git a/plat/hisilicon/poplar/bl1_plat_setup.c b/plat/hisilicon/poplar/bl1_plat_setup.c
index 047ba62..acc1f0e 100644
--- a/plat/hisilicon/poplar/bl1_plat_setup.c
+++ b/plat/hisilicon/poplar/bl1_plat_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -30,6 +30,10 @@
 static meminfo_t bl2_tzram_layout;
 static console_t console;
 
+#if !POPLAR_RECOVERY
+static struct mmc_device_info mmc_info;
+#endif
+
 /*
  * Cannot use default weak implementation in bl1_main.c because BL1 RW data is
  * not at the top of the secure memory.
@@ -90,7 +94,6 @@
 {
 	int i;
 #if !POPLAR_RECOVERY
-	struct mmc_device_info info;
 	dw_mmc_params_t params = EMMC_INIT_PARAMS(POPLAR_EMMC_DESC_BASE);
 #endif
 
@@ -103,8 +106,8 @@
 #if !POPLAR_RECOVERY
 	/* SoC-specific emmc register are initialized/configured by bootrom */
 	INFO("BL1: initializing emmc\n");
-	info.mmc_dev_type = MMC_IS_EMMC;
-	dw_mmc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	dw_mmc_init(&params, &mmc_info);
 #endif
 
 	plat_io_setup();
diff --git a/plat/hisilicon/poplar/bl2_plat_setup.c b/plat/hisilicon/poplar/bl2_plat_setup.c
index 482935c..ee46772 100644
--- a/plat/hisilicon/poplar/bl2_plat_setup.c
+++ b/plat/hisilicon/poplar/bl2_plat_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -26,6 +26,9 @@
 
 static meminfo_t bl2_tzram_layout __aligned(CACHE_WRITEBACK_GRANULE);
 static console_t console;
+#if !POPLAR_RECOVERY
+static struct mmc_device_info mmc_info;
+#endif
 
 /*******************************************************************************
  * Transfer SCP_BL2 from Trusted RAM using the SCP Download protocol.
@@ -171,8 +174,6 @@
 {
 	struct meminfo *mem_layout = (struct meminfo *)arg1;
 #if !POPLAR_RECOVERY
-	struct mmc_device_info info;
-
 	dw_mmc_params_t params = EMMC_INIT_PARAMS(POPLAR_EMMC_DESC_BASE);
 #endif
 
@@ -187,8 +188,8 @@
 #if !POPLAR_RECOVERY
 	/* SoC-specific emmc register are initialized/configured by bootrom */
 	INFO("BL2: initializing emmc\n");
-	info.mmc_dev_type = MMC_IS_EMMC;
-	dw_mmc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	dw_mmc_init(&params, &mmc_info);
 #endif
 
 	plat_io_setup();
diff --git a/plat/hisilicon/poplar/bl31_plat_setup.c b/plat/hisilicon/poplar/bl31_plat_setup.c
index a4e17ca..fe60ddc 100644
--- a/plat/hisilicon/poplar/bl31_plat_setup.c
+++ b/plat/hisilicon/poplar/bl31_plat_setup.c
@@ -6,7 +6,9 @@
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
 #include <stddef.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <platform_def.h>
@@ -130,6 +132,6 @@
 			       BL_COHERENT_RAM_BASE,
 			       BL_COHERENT_RAM_END);
 
-	INFO("Boot BL33 from 0x%lx for %llu Bytes\n",
+	INFO("Boot BL33 from 0x%lx for %" PRIu64 " Bytes\n",
 	     bl33_image_ep_info.pc, bl33_image_ep_info.args.arg2);
 }
diff --git a/plat/imx/common/imx_io_storage.c b/plat/imx/common/imx_io_storage.c
new file mode 100644
index 0000000..bb35662
--- /dev/null
+++ b/plat/imx/common/imx_io_storage.c
@@ -0,0 +1,301 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <drivers/io/io_block.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_fip.h>
+#include <drivers/io/io_memmap.h>
+#include <drivers/mmc.h>
+#include <lib/utils_def.h>
+#include <tbbr_img_def.h>
+#include <tools_share/firmware_image_package.h>
+
+#include <platform_def.h>
+
+static const io_dev_connector_t *fip_dev_con;
+static uintptr_t fip_dev_handle;
+
+#ifndef IMX_FIP_MMAP
+static const io_dev_connector_t *mmc_dev_con;
+static uintptr_t mmc_dev_handle;
+
+static const io_block_spec_t mmc_fip_spec = {
+	.offset = IMX_FIP_MMC_BASE,
+	.length = IMX_FIP_SIZE
+};
+
+static const io_block_dev_spec_t mmc_dev_spec = {
+	/* It's used as temp buffer in block driver. */
+	.buffer		= {
+		.offset	= IMX_FIP_BASE,
+		/* do we need a new value? */
+		.length = IMX_FIP_SIZE
+	},
+	.ops		= {
+		.read	= mmc_read_blocks,
+		.write	= mmc_write_blocks,
+	},
+	.block_size	= MMC_BLOCK_SIZE,
+};
+
+static int open_mmc(const uintptr_t spec);
+
+#else
+static const io_dev_connector_t *memmap_dev_con;
+static uintptr_t memmap_dev_handle;
+
+static const io_block_spec_t fip_block_spec = {
+	.offset = IMX_FIP_BASE,
+	.length = IMX_FIP_SIZE
+};
+static int open_memmap(const uintptr_t spec);
+#endif
+
+static int open_fip(const uintptr_t spec);
+
+static const io_uuid_spec_t bl31_uuid_spec = {
+	.uuid = UUID_EL3_RUNTIME_FIRMWARE_BL31,
+};
+
+static const io_uuid_spec_t bl32_uuid_spec = {
+	.uuid = UUID_SECURE_PAYLOAD_BL32,
+};
+
+static const io_uuid_spec_t bl32_extra1_uuid_spec = {
+	.uuid = UUID_SECURE_PAYLOAD_BL32_EXTRA1,
+};
+
+static const io_uuid_spec_t bl32_extra2_uuid_spec = {
+	.uuid = UUID_SECURE_PAYLOAD_BL32_EXTRA2,
+};
+
+static const io_uuid_spec_t bl33_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FIRMWARE_BL33,
+};
+
+#if TRUSTED_BOARD_BOOT
+static const io_uuid_spec_t tb_fw_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_BOOT_FW_CERT,
+};
+
+static const io_uuid_spec_t trusted_key_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_KEY_CERT,
+};
+
+static const io_uuid_spec_t soc_fw_key_cert_uuid_spec = {
+	.uuid = UUID_SOC_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t tos_fw_key_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_OS_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t tos_fw_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_OS_FW_CONTENT_CERT,
+};
+
+static const io_uuid_spec_t soc_fw_content_cert_uuid_spec = {
+	.uuid = UUID_SOC_FW_CONTENT_CERT,
+};
+
+static const io_uuid_spec_t nt_fw_key_cert_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t nt_fw_cert_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FW_CONTENT_CERT,
+};
+#endif /* TRUSTED_BOARD_BOOT */
+
+/* TODO: this structure is replicated multiple times. rationalize it ! */
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+static const struct plat_io_policy policies[] = {
+#ifndef IMX_FIP_MMAP
+	[FIP_IMAGE_ID] = {
+		&mmc_dev_handle,
+		(uintptr_t)&mmc_fip_spec,
+		open_mmc
+	},
+#else
+	[FIP_IMAGE_ID] = {
+		&memmap_dev_handle,
+		(uintptr_t)&fip_block_spec,
+		open_memmap
+	},
+#endif
+	[BL31_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl31_uuid_spec,
+		open_fip
+	},
+	[BL32_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl32_uuid_spec,
+		open_fip
+	},
+	[BL32_EXTRA1_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl32_extra1_uuid_spec,
+		open_fip
+	},
+	[BL32_EXTRA2_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl32_extra2_uuid_spec,
+		open_fip
+	},
+	[BL33_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl33_uuid_spec,
+		open_fip
+	},
+#if TRUSTED_BOARD_BOOT
+	[TRUSTED_BOOT_FW_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tb_fw_cert_uuid_spec,
+		open_fip
+	},
+	[SOC_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&soc_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&trusted_key_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_OS_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tos_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[NON_TRUSTED_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&nt_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[SOC_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&soc_fw_content_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tos_fw_cert_uuid_spec,
+		open_fip
+	},
+	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&nt_fw_cert_uuid_spec,
+		open_fip
+	},
+#endif /* TRUSTED_BOARD_BOOT */
+};
+
+static int open_fip(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	/* See if a Firmware Image Package is available */
+	result = io_dev_init(fip_dev_handle, (uintptr_t)FIP_IMAGE_ID);
+	if (result == 0) {
+		result = io_open(fip_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using FIP\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+#ifndef IMX_FIP_MMAP
+static int open_mmc(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_handle;
+
+	result = io_dev_init(mmc_dev_handle, (uintptr_t)NULL);
+	if (result == 0) {
+		result = io_open(mmc_dev_handle, spec, &local_handle);
+		if (result == 0) {
+			io_close(local_handle);
+		}
+	}
+	return result;
+}
+#else
+static int open_memmap(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	result = io_dev_init(memmap_dev_handle, (uintptr_t)NULL);
+	if (result == 0) {
+		result = io_open(memmap_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using Memmap\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+#endif
+
+int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
+			  uintptr_t *image_spec)
+{
+	int result;
+	const struct plat_io_policy *policy;
+
+	assert(image_id < ARRAY_SIZE(policies));
+
+	policy = &policies[image_id];
+	result = policy->check(policy->image_spec);
+	assert(result == 0);
+
+	*image_spec = policy->image_spec;
+	*dev_handle = *policy->dev_handle;
+
+	return result;
+}
+
+void plat_imx_io_setup(void)
+{
+	int result __unused;
+
+#ifndef IMX_FIP_MMAP
+	result = register_io_dev_block(&mmc_dev_con);
+	assert(result == 0);
+
+	result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_dev_spec,
+			     &mmc_dev_handle);
+	assert(result == 0);
+
+#else
+	result = register_io_dev_memmap(&memmap_dev_con);
+	assert(result == 0);
+
+	result = io_dev_open(memmap_dev_con, (uintptr_t)NULL,
+			     &memmap_dev_handle);
+	assert(result == 0);
+#endif
+
+	result = register_io_dev_fip(&fip_dev_con);
+	assert(result == 0);
+
+	result = io_dev_open(fip_dev_con, (uintptr_t)NULL,
+			     &fip_dev_handle);
+	assert(result == 0);
+}
diff --git a/plat/imx/common/imx_sip_handler.c b/plat/imx/common/imx_sip_handler.c
index f9f5577..d4b3425 100644
--- a/plat/imx/common/imx_sip_handler.c
+++ b/plat/imx/common/imx_sip_handler.c
@@ -14,6 +14,7 @@
 #include <common/runtime_svc.h>
 #include <imx_sip_svc.h>
 #include <lib/el3_runtime/context_mgmt.h>
+#include <lib/mmio.h>
 #include <sci/sci.h>
 
 #if defined(PLAT_imx8qm) || defined(PLAT_imx8qx)
@@ -145,6 +146,37 @@
 
 #endif /* defined(PLAT_imx8qm) || defined(PLAT_imx8qx) */
 
+#if defined(PLAT_imx8mm) || defined(PLAT_imx8mq)
+int imx_src_handler(uint32_t smc_fid,
+		    u_register_t x1,
+		    u_register_t x2,
+		    u_register_t x3,
+		    void *handle)
+{
+	uint32_t val;
+
+	switch (x1) {
+	case IMX_SIP_SRC_SET_SECONDARY_BOOT:
+		if (x2 != 0U) {
+			mmio_setbits_32(IMX_SRC_BASE + SRC_GPR10_OFFSET,
+					SRC_GPR10_PERSIST_SECONDARY_BOOT);
+		} else {
+			mmio_clrbits_32(IMX_SRC_BASE + SRC_GPR10_OFFSET,
+					SRC_GPR10_PERSIST_SECONDARY_BOOT);
+		}
+		break;
+	case IMX_SIP_SRC_IS_SECONDARY_BOOT:
+		val = mmio_read_32(IMX_SRC_BASE + SRC_GPR10_OFFSET);
+		return !!(val & SRC_GPR10_PERSIST_SECONDARY_BOOT);
+	default:
+		return SMC_UNK;
+
+	};
+
+	return 0;
+}
+#endif /* defined(PLAT_imx8mm) || defined(PLAT_imx8mq) */
+
 static uint64_t imx_get_commit_hash(u_register_t x2,
 		    u_register_t x3,
 		    u_register_t x4)
diff --git a/plat/imx/common/imx_sip_svc.c b/plat/imx/common/imx_sip_svc.c
index 20e1479..fd54820 100644
--- a/plat/imx/common/imx_sip_svc.c
+++ b/plat/imx/common/imx_sip_svc.c
@@ -48,6 +48,11 @@
 	case IMX_SIP_MISC_SET_TEMP:
 		SMC_RET1(handle, imx_misc_set_temp_handler(smc_fid, x1, x2, x3, x4));
 #endif
+#if defined(PLAT_imx8mm) || defined(PLAT_imx8mq)
+	case IMX_SIP_SRC:
+		SMC_RET1(handle, imx_src_handler(smc_fid, x1, x2, x3, handle));
+		break;
+#endif
 	case  IMX_SIP_BUILDINFO:
 		SMC_RET1(handle, imx_buildinfo_handler(smc_fid, x1, x2, x3, x4));
 	default:
diff --git a/plat/imx/common/include/imx_sip_svc.h b/plat/imx/common/include/imx_sip_svc.h
index 0a2d750..6c7a760 100644
--- a/plat/imx/common/include/imx_sip_svc.h
+++ b/plat/imx/common/include/imx_sip_svc.h
@@ -17,6 +17,10 @@
 #define IMX_SIP_BUILDINFO			0xC2000003
 #define IMX_SIP_BUILDINFO_GET_COMMITHASH	0x00
 
+#define IMX_SIP_SRC			0xC2000005
+#define IMX_SIP_SRC_SET_SECONDARY_BOOT	0x10
+#define IMX_SIP_SRC_IS_SECONDARY_BOOT	0x11
+
 #define IMX_SIP_GET_SOC_INFO		0xC2000006
 
 #define IMX_SIP_WAKEUP_SRC		0xC2000009
@@ -38,6 +42,11 @@
 			 u_register_t x2, u_register_t x3);
 #endif
 
+#if defined(PLAT_imx8mm) || defined(PLAT_imx8mq)
+int imx_src_handler(uint32_t smc_fid, u_register_t x1,
+		    u_register_t x2, u_register_t x3, void *handle);
+#endif
+
 #if (defined(PLAT_imx8qm) || defined(PLAT_imx8qx))
 int imx_cpufreq_handler(uint32_t smc_fid, u_register_t x1,
 			u_register_t x2, u_register_t x3);
diff --git a/plat/imx/imx7/common/imx7.mk b/plat/imx/imx7/common/imx7.mk
index 3a95772..fdde9a9 100644
--- a/plat/imx/imx7/common/imx7.mk
+++ b/plat/imx/imx7/common/imx7.mk
@@ -16,6 +16,7 @@
 				-Iplat/imx/imx7/include			\
 				-Idrivers/imx/timer			\
 				-Idrivers/imx/usdhc			\
+				-Iinclude/common/tbbr
 
 # Translation tables library
 include lib/xlat_tables_v2/xlat_tables.mk
@@ -46,7 +47,7 @@
 				plat/imx/imx7/common/imx7_bl2_el3_common.c	\
 				plat/imx/imx7/common/imx7_helpers.S		\
 				plat/imx/imx7/common/imx7_image_load.c		\
-				plat/imx/imx7/common/imx7_io_storage.c		\
+				plat/imx/common/imx_io_storage.c		\
 				plat/imx/common/aarch32/imx_uart_console.S	\
 				${XLAT_TABLES_LIB_SRCS}
 
diff --git a/plat/imx/imx7/common/imx7_bl2_el3_common.c b/plat/imx/imx7/common/imx7_bl2_el3_common.c
index 7f156e3..4e5028c 100644
--- a/plat/imx/imx7/common/imx7_bl2_el3_common.c
+++ b/plat/imx/imx7/common/imx7_bl2_el3_common.c
@@ -173,7 +173,7 @@
 	console_set_scope(&console, console_scope);
 
 	/* Open handles to persistent storage */
-	plat_imx7_io_setup();
+	plat_imx_io_setup();
 
 	/* Setup higher-level functionality CAAM, RTC etc */
 	imx_caam_init();
@@ -183,7 +183,7 @@
 	VERBOSE("\tOPTEE       0x%08x-0x%08x\n", IMX7_OPTEE_BASE, IMX7_OPTEE_LIMIT);
 	VERBOSE("\tATF/BL2     0x%08x-0x%08x\n", BL2_RAM_BASE, BL2_RAM_LIMIT);
 	VERBOSE("\tSHRAM       0x%08x-0x%08x\n", SHARED_RAM_BASE, SHARED_RAM_LIMIT);
-	VERBOSE("\tFIP         0x%08x-0x%08x\n", IMX7_FIP_BASE, IMX7_FIP_LIMIT);
+	VERBOSE("\tFIP         0x%08x-0x%08x\n", IMX_FIP_BASE, IMX_FIP_LIMIT);
 	VERBOSE("\tDTB-OVERLAY 0x%08x-0x%08x\n", IMX7_DTB_OVERLAY_BASE, IMX7_DTB_OVERLAY_LIMIT);
 	VERBOSE("\tDTB         0x%08x-0x%08x\n", IMX7_DTB_BASE, IMX7_DTB_LIMIT);
 	VERBOSE("\tUBOOT/BL33  0x%08x-0x%08x\n", IMX7_UBOOT_BASE, IMX7_UBOOT_LIMIT);
diff --git a/plat/imx/imx7/common/imx7_io_storage.c b/plat/imx/imx7/common/imx7_io_storage.c
deleted file mode 100644
index 977181d..0000000
--- a/plat/imx/imx7/common/imx7_io_storage.c
+++ /dev/null
@@ -1,270 +0,0 @@
-/*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <platform_def.h>
-
-#include <common/debug.h>
-#include <drivers/io/io_block.h>
-#include <drivers/io/io_driver.h>
-#include <drivers/io/io_fip.h>
-#include <drivers/io/io_memmap.h>
-#include <drivers/mmc.h>
-#include <tools_share/firmware_image_package.h>
-
-static const io_dev_connector_t *fip_dev_con;
-static uintptr_t fip_dev_handle;
-
-#ifndef IMX7_FIP_MMAP
-static const io_dev_connector_t *mmc_dev_con;
-static uintptr_t mmc_dev_handle;
-
-static const io_block_spec_t mmc_fip_spec = {
-	.offset = IMX7_FIP_MMC_BASE,
-	.length = IMX7_FIP_SIZE
-};
-
-static const io_block_dev_spec_t mmc_dev_spec = {
-	/* It's used as temp buffer in block driver. */
-	.buffer		= {
-		.offset	= IMX7_FIP_BASE,
-		/* do we need a new value? */
-		.length = IMX7_FIP_SIZE
-	},
-	.ops		= {
-		.read	= mmc_read_blocks,
-		.write	= mmc_write_blocks,
-	},
-	.block_size	= MMC_BLOCK_SIZE,
-};
-
-static int open_mmc(const uintptr_t spec);
-
-#else
-static const io_dev_connector_t *memmap_dev_con;
-static uintptr_t memmap_dev_handle;
-
-static const io_block_spec_t fip_block_spec = {
-	.offset = IMX7_FIP_BASE,
-	.length = IMX7_FIP_SIZE
-};
-static int open_memmap(const uintptr_t spec);
-#endif
-static int open_fip(const uintptr_t spec);
-
-static const io_uuid_spec_t bl32_uuid_spec = {
-	.uuid = UUID_SECURE_PAYLOAD_BL32,
-};
-
-static const io_uuid_spec_t bl32_extra1_uuid_spec = {
-	.uuid = UUID_SECURE_PAYLOAD_BL32_EXTRA1,
-};
-
-static const io_uuid_spec_t bl32_extra2_uuid_spec = {
-	.uuid = UUID_SECURE_PAYLOAD_BL32_EXTRA2,
-};
-
-static const io_uuid_spec_t bl33_uuid_spec = {
-	.uuid = UUID_NON_TRUSTED_FIRMWARE_BL33,
-};
-
-#if TRUSTED_BOARD_BOOT
-static const io_uuid_spec_t tb_fw_cert_uuid_spec = {
-	.uuid = UUID_TRUSTED_BOOT_FW_CERT,
-};
-
-static const io_uuid_spec_t trusted_key_cert_uuid_spec = {
-	.uuid = UUID_TRUSTED_KEY_CERT,
-};
-
-static const io_uuid_spec_t tos_fw_key_cert_uuid_spec = {
-	.uuid = UUID_TRUSTED_OS_FW_KEY_CERT,
-};
-
-static const io_uuid_spec_t tos_fw_cert_uuid_spec = {
-	.uuid = UUID_TRUSTED_OS_FW_CONTENT_CERT,
-};
-
-static const io_uuid_spec_t nt_fw_key_cert_uuid_spec = {
-	.uuid = UUID_NON_TRUSTED_FW_KEY_CERT,
-};
-
-static const io_uuid_spec_t nt_fw_cert_uuid_spec = {
-	.uuid = UUID_NON_TRUSTED_FW_CONTENT_CERT,
-};
-#endif /* TRUSTED_BOARD_BOOT */
-
-/* TODO: this structure is replicated multiple times. rationalize it ! */
-struct plat_io_policy {
-	uintptr_t *dev_handle;
-	uintptr_t image_spec;
-	int (*check)(const uintptr_t spec);
-};
-
-static const struct plat_io_policy policies[] = {
-#ifndef IMX7_FIP_MMAP
-	[FIP_IMAGE_ID] = {
-		&mmc_dev_handle,
-		(uintptr_t)&mmc_fip_spec,
-		open_mmc
-	},
-#else
-	[FIP_IMAGE_ID] = {
-		&memmap_dev_handle,
-		(uintptr_t)&fip_block_spec,
-		open_memmap
-	},
-#endif
-	[BL32_IMAGE_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&bl32_uuid_spec,
-		open_fip
-	},
-	[BL32_EXTRA1_IMAGE_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&bl32_extra1_uuid_spec,
-		open_fip
-	},
-	[BL32_EXTRA2_IMAGE_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&bl32_extra2_uuid_spec,
-		open_fip
-	},
-	[BL33_IMAGE_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&bl33_uuid_spec,
-		open_fip
-	},
-#if TRUSTED_BOARD_BOOT
-	[TRUSTED_BOOT_FW_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&tb_fw_cert_uuid_spec,
-		open_fip
-	},
-	[TRUSTED_KEY_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&trusted_key_cert_uuid_spec,
-		open_fip
-	},
-	[TRUSTED_OS_FW_KEY_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&tos_fw_key_cert_uuid_spec,
-		open_fip
-	},
-	[NON_TRUSTED_FW_KEY_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&nt_fw_key_cert_uuid_spec,
-		open_fip
-	},
-	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&tos_fw_cert_uuid_spec,
-		open_fip
-	},
-	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
-		&fip_dev_handle,
-		(uintptr_t)&nt_fw_cert_uuid_spec,
-		open_fip
-	},
-#endif /* TRUSTED_BOARD_BOOT */
-};
-
-static int open_fip(const uintptr_t spec)
-{
-	int result;
-	uintptr_t local_image_handle;
-
-	/* See if a Firmware Image Package is available */
-	result = io_dev_init(fip_dev_handle, (uintptr_t)FIP_IMAGE_ID);
-	if (result == 0) {
-		result = io_open(fip_dev_handle, spec, &local_image_handle);
-		if (result == 0) {
-			VERBOSE("Using FIP\n");
-			io_close(local_image_handle);
-		}
-	}
-	return result;
-}
-
-#ifndef IMX7_FIP_MMAP
-static int open_mmc(const uintptr_t spec)
-{
-	int result;
-	uintptr_t local_handle;
-
-	result = io_dev_init(mmc_dev_handle, (uintptr_t)NULL);
-	if (result == 0) {
-		result = io_open(mmc_dev_handle, spec, &local_handle);
-		if (result == 0)
-			io_close(local_handle);
-	}
-	return result;
-}
-#else
-static int open_memmap(const uintptr_t spec)
-{
-	int result;
-	uintptr_t local_image_handle;
-
-	result = io_dev_init(memmap_dev_handle, (uintptr_t)NULL);
-	if (result == 0) {
-		result = io_open(memmap_dev_handle, spec, &local_image_handle);
-		if (result == 0) {
-			VERBOSE("Using Memmap\n");
-			io_close(local_image_handle);
-		}
-	}
-	return result;
-}
-#endif
-
-int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
-			  uintptr_t *image_spec)
-{
-	int result;
-	const struct plat_io_policy *policy;
-
-	assert(image_id < ARRAY_SIZE(policies));
-
-	policy = &policies[image_id];
-	result = policy->check(policy->image_spec);
-	assert(result == 0);
-
-	*image_spec = policy->image_spec;
-	*dev_handle = *policy->dev_handle;
-
-	return result;
-}
-
-void plat_imx7_io_setup(void)
-{
-	int result __unused;
-
-#ifndef IMX7_FIP_MMAP
-	result = register_io_dev_block(&mmc_dev_con);
-	assert(result == 0);
-
-	result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_dev_spec,
-			     &mmc_dev_handle);
-	assert(result == 0);
-
-#else
-	result = register_io_dev_memmap(&memmap_dev_con);
-	assert(result == 0);
-
-	result = io_dev_open(memmap_dev_con, (uintptr_t)NULL,
-			     &memmap_dev_handle);
-	assert(result == 0);
-
-#endif
-	result = register_io_dev_fip(&fip_dev_con);
-	assert(result == 0);
-
-	result = io_dev_open(fip_dev_con, (uintptr_t)NULL,
-			     &fip_dev_handle);
-	assert(result == 0);
-}
diff --git a/plat/imx/imx7/include/imx7_def.h b/plat/imx/imx7/include/imx7_def.h
index 77a8ca3..d92a2d1 100644
--- a/plat/imx/imx7/include/imx7_def.h
+++ b/plat/imx/imx7/include/imx7_def.h
@@ -13,7 +13,7 @@
 /*******************************************************************************
  * Function and variable prototypes
  ******************************************************************************/
-void plat_imx7_io_setup(void);
+void plat_imx_io_setup(void);
 void imx7_platform_setup(u_register_t arg1, u_register_t arg2,
 			 u_register_t arg3, u_register_t arg4);
 
diff --git a/plat/imx/imx7/picopi/include/platform_def.h b/plat/imx/imx7/picopi/include/platform_def.h
index 141571c..5f2975d 100644
--- a/plat/imx/imx7/picopi/include/platform_def.h
+++ b/plat/imx/imx7/picopi/include/platform_def.h
@@ -92,12 +92,12 @@
 #define IMX7_UBOOT_LIMIT		(IMX7_UBOOT_BASE + IMX7_UBOOT_SIZE)
 
 /* Define FIP image absolute location 0x80000000 - 0x80100000 */
-#define IMX7_FIP_SIZE			0x00100000
-#define IMX7_FIP_BASE			(DRAM_BASE)
-#define IMX7_FIP_LIMIT			(IMX7_FIP_BASE + IMX7_FIP_SIZE)
+#define IMX_FIP_SIZE			0x00100000
+#define IMX_FIP_BASE			(DRAM_BASE)
+#define IMX_FIP_LIMIT			(IMX_FIP_BASE + IMX_FIP_SIZE)
 
 /* Define FIP image location at 1MB offset */
-#define IMX7_FIP_MMC_BASE		(1024 * 1024)
+#define IMX_FIP_MMC_BASE		(1024 * 1024)
 
 /* Define the absolute location of DTB 0x83000000 - 0x83100000 */
 #define IMX7_DTB_SIZE			0x00100000
diff --git a/plat/imx/imx7/picopi/picopi_bl2_el3_setup.c b/plat/imx/imx7/picopi/picopi_bl2_el3_setup.c
index 3cf5c36..2df96ae 100644
--- a/plat/imx/imx7/picopi/picopi_bl2_el3_setup.c
+++ b/plat/imx/imx7/picopi/picopi_bl2_el3_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -43,6 +43,8 @@
 	 IOMUXC_SW_PAD_CTL_PAD_SD3_SLEW_SLOW         | \
 	 IOMUXC_SW_PAD_CTL_PAD_SD3_DSE_3_X6)
 
+static struct mmc_device_info mmc_info;
+
 static void picopi_setup_pinmux(void)
 {
 	/* Configure UART5 TX */
@@ -93,14 +95,13 @@
 static void picopi_usdhc_setup(void)
 {
 	imx_usdhc_params_t params;
-	struct mmc_device_info info;
 
 	zeromem(&params, sizeof(imx_usdhc_params_t));
 	params.reg_base = PLAT_PICOPI_BOOT_MMC_BASE;
 	params.clk_rate = 25000000;
 	params.bus_width = MMC_BUS_WIDTH_8;
-	info.mmc_dev_type = MMC_IS_EMMC;
-	imx_usdhc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	imx_usdhc_init(&params, &mmc_info);
 }
 
 static void picopi_setup_usb_clocks(void)
diff --git a/plat/imx/imx7/warp7/include/platform_def.h b/plat/imx/imx7/warp7/include/platform_def.h
index 4afcb54..683e50d 100644
--- a/plat/imx/imx7/warp7/include/platform_def.h
+++ b/plat/imx/imx7/warp7/include/platform_def.h
@@ -94,12 +94,12 @@
 #define IMX7_UBOOT_LIMIT		(IMX7_UBOOT_BASE + IMX7_UBOOT_SIZE)
 
 /* Define FIP image absolute location 0x80000000 - 0x80100000 */
-#define IMX7_FIP_SIZE			0x00100000
-#define IMX7_FIP_BASE			(DRAM_BASE)
-#define IMX7_FIP_LIMIT			(IMX7_FIP_BASE + IMX7_FIP_SIZE)
+#define IMX_FIP_SIZE			0x00100000
+#define IMX_FIP_BASE			(DRAM_BASE)
+#define IMX_FIP_LIMIT			(IMX_FIP_BASE + IMX_FIP_SIZE)
 
 /* Define FIP image location at 1MB offset */
-#define IMX7_FIP_MMC_BASE		(1024 * 1024)
+#define IMX_FIP_MMC_BASE		(1024 * 1024)
 
 /* Define the absolute location of DTB 0x83000000 - 0x83100000 */
 #define IMX7_DTB_SIZE			0x00100000
diff --git a/plat/imx/imx7/warp7/warp7_bl2_el3_setup.c b/plat/imx/imx7/warp7/warp7_bl2_el3_setup.c
index 935a411..ec13ade 100644
--- a/plat/imx/imx7/warp7/warp7_bl2_el3_setup.c
+++ b/plat/imx/imx7/warp7/warp7_bl2_el3_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -69,6 +69,8 @@
 	 IOMUXC_SW_PAD_CTL_PAD_ECSPI1_SCLK_HYS_EN		| \
 	 IOMUXC_SW_PAD_CTL_PAD_ECSPI1_SCLK_DSE_1_X4)
 
+static struct mmc_device_info mmc_info;
+
 static void warp7_setup_pinmux(void)
 {
 	/* Configure UART1 TX */
@@ -99,14 +101,13 @@
 static void warp7_usdhc_setup(void)
 {
 	imx_usdhc_params_t params;
-	struct mmc_device_info info;
 
 	zeromem(&params, sizeof(imx_usdhc_params_t));
 	params.reg_base = PLAT_WARP7_BOOT_MMC_BASE;
 	params.clk_rate = 25000000;
 	params.bus_width = MMC_BUS_WIDTH_8;
-	info.mmc_dev_type = MMC_IS_EMMC;
-	imx_usdhc_init(&params, &info);
+	mmc_info.mmc_dev_type = MMC_IS_EMMC;
+	imx_usdhc_init(&params, &mmc_info);
 }
 
 static void warp7_setup_usb_clocks(void)
diff --git a/plat/imx/imx8m/imx8m_image_load.c b/plat/imx/imx8m/imx8m_image_load.c
new file mode 100644
index 0000000..3a03069
--- /dev/null
+++ b/plat/imx/imx8m/imx8m_image_load.c
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/bl_common.h>
+#include <common/desc_image_load.h>
+
+#include <platform_def.h>
+#include <plat/common/platform.h>
+
+void plat_flush_next_bl_params(void)
+{
+	flush_bl_params_desc();
+}
+
+bl_load_info_t *plat_get_bl_image_load_info(void)
+{
+	return get_bl_load_info_from_mem_params_desc();
+}
+
+bl_params_t *plat_get_next_bl_params(void)
+{
+	return get_next_bl_params_from_mem_params_desc();
+}
diff --git a/plat/imx/imx8m/imx8m_psci_common.c b/plat/imx/imx8m/imx8m_psci_common.c
index dbb772d..9dfd311 100644
--- a/plat/imx/imx8m/imx8m_psci_common.c
+++ b/plat/imx/imx8m/imx8m_psci_common.c
@@ -152,19 +152,45 @@
 		req_state->pwr_domain_state[i] = PLAT_STOP_OFF_STATE;
 }
 
-void __dead2 imx_system_reset(void)
+static void __dead2 imx_wdog_restart(bool external_reset)
 {
 	uintptr_t wdog_base = IMX_WDOG_BASE;
 	unsigned int val;
 
-	/* WDOG_B reset */
 	val = mmio_read_16(wdog_base);
-#ifdef IMX_WDOG_B_RESET
-	val = (val & 0x00FF) | WDOG_WCR_WDZST | WDOG_WCR_WDE |
-		WDOG_WCR_WDT | WDOG_WCR_SRS;
-#else
-	val = (val & 0x00FF) | WDOG_WCR_WDZST | WDOG_WCR_SRS;
-#endif
+	/*
+	 * Common watchdog init flags, for additional details check
+	 * 6.6.4.1 Watchdog Control Register (WDOGx_WCR)
+	 *
+	 * Initial bit selection:
+	 * WDOG_WCR_WDE - Enable the watchdog.
+	 *
+	 * 0x000E mask is used to keep previous values (that could be set
+	 * in SPL) of WDBG and WDE/WDT (both are write-one once-only bits).
+	 */
+	val = (val & 0x000E) | WDOG_WCR_WDE;
+	if (external_reset) {
+		/*
+		 * To assert WDOG_B (external reset) we have
+		 * to set WDA bit 0 (already set in previous step).
+		 * SRS bits are required to be set to 1 (no effect on the
+		 * system).
+		 */
+		val |= WDOG_WCR_SRS;
+	} else {
+		/*
+		 * To assert Software Reset Signal (internal reset) we have
+		 * to set SRS bit to 0 (already set in previous step).
+		 * SRE bit is required to be set to 1 when used in
+		 * conjunction with the Software Reset Signal before
+		 * SRS asserton, otherwise SRS bit will just automatically
+		 * reset to 1.
+		 *
+		 * Also we set WDA to 1 (no effect on system).
+		 */
+		val |= WDOG_WCR_SRE | WDOG_WCR_WDA;
+	}
+
 	mmio_write_16(wdog_base, val);
 
 	mmio_write_16(wdog_base + WDOG_WSR, 0x5555);
@@ -173,6 +199,27 @@
 		;
 }
 
+void __dead2 imx_system_reset(void)
+{
+#ifdef IMX_WDOG_B_RESET
+	imx_wdog_restart(true);
+#else
+	imx_wdog_restart(false);
+#endif
+}
+
+int imx_system_reset2(int is_vendor, int reset_type, u_register_t cookie)
+{
+	imx_wdog_restart(false);
+
+	/*
+	 * imx_wdog_restart cannot return (as it's  a __dead function),
+	 * however imx_system_reset2 has to return some value according
+	 * to PSCI v1.1 spec.
+	 */
+	return 0;
+}
+
 void __dead2 imx_system_off(void)
 {
 	mmio_write_32(IMX_SNVS_BASE + SNVS_LPCR, SNVS_LPCR_SRTC_ENV |
diff --git a/plat/imx/imx8m/imx8mm/imx8mm_bl2_el3_setup.c b/plat/imx/imx8m/imx8mm/imx8mm_bl2_el3_setup.c
new file mode 100644
index 0000000..c39dd93
--- /dev/null
+++ b/plat/imx/imx8m/imx8mm/imx8mm_bl2_el3_setup.c
@@ -0,0 +1,143 @@
+/*
+ * Copyright 2017-2021 NXP
+ * Copyright 2021 Arm
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <arch_helpers.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <common/desc_image_load.h>
+#include <context.h>
+#include <drivers/console.h>
+#include <drivers/generic_delay_timer.h>
+#include <drivers/mmc.h>
+#include <lib/mmio.h>
+#include <lib/optee_utils.h>
+#include <lib/utils.h>
+#include <stdbool.h>
+#include <tbbr_img_def.h>
+
+#include <imx_aipstz.h>
+#include <imx_csu.h>
+#include <imx_uart.h>
+#include <imx_usdhc.h>
+#include <plat/common/platform.h>
+
+#include "imx8mm_private.h"
+#include "platform_def.h"
+
+static const struct aipstz_cfg aipstz[] = {
+	{IMX_AIPSTZ1, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ2, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ3, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ4, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{0},
+};
+
+static void imx8mm_usdhc_setup(void)
+{
+	imx_usdhc_params_t params;
+	struct mmc_device_info info;
+
+	params.reg_base = PLAT_IMX8MM_BOOT_MMC_BASE;
+	/*
+	   The imx8mm SD Card Speed modes for USDHC2
+	   +--------------+--------------------+--------------+--------------+
+	   |Bus Speed Mode|Max. Clock Frequency|Max. Bus Speed|Signal Voltage|
+	   +--------------+--------------------+--------------+--------------+
+	   |Default Speed | 25 MHz             | 12.5 MB/s    | 3.3V         |
+	   |High Speed    | 50 MHz             | 25 MB/s      | 3.3V         |
+	   +--------------+--------------------+--------------+--------------+
+
+	   We pick 50 Mhz here for High Speed access.
+	*/
+	params.clk_rate = 50000000;
+	params.bus_width = MMC_BUS_WIDTH_1;
+	params.flags = 0;
+	info.mmc_dev_type = MMC_IS_SD;
+	info.ocr_voltage = OCR_3_3_3_4 | OCR_3_2_3_3;
+	imx_usdhc_init(&params, &info);
+}
+
+void bl2_el3_early_platform_setup(u_register_t arg1, u_register_t arg2,
+				  u_register_t arg3, u_register_t arg4)
+{
+	int i;
+	static console_t console;
+
+	/* enable CSU NS access permission */
+	for (i = 0; i < MAX_CSU_NUM; i++) {
+		mmio_write_32(IMX_CSU_BASE + i * 4, CSU_CSL_OPEN_ACCESS);
+	}
+
+	/* config the aips access permission */
+	imx_aipstz_init(aipstz);
+
+	console_imx_uart_register(IMX_BOOT_UART_BASE, IMX_BOOT_UART_CLK_IN_HZ,
+		IMX_CONSOLE_BAUDRATE, &console);
+
+	generic_delay_timer_init();
+
+	/* select the CKIL source to 32K OSC */
+	mmio_write_32(0x30360124, 0x1);
+
+	imx8mm_usdhc_setup();
+
+	/* Open handles to a FIP image */
+	plat_imx_io_setup();
+}
+
+void bl2_el3_plat_arch_setup(void)
+{
+}
+
+void bl2_platform_setup(void)
+{
+}
+
+int bl2_plat_handle_post_image_load(unsigned int image_id)
+{
+	int err = 0;
+	bl_mem_params_node_t *bl_mem_params = get_bl_mem_params_node(image_id);
+	bl_mem_params_node_t *pager_mem_params = NULL;
+	bl_mem_params_node_t *paged_mem_params = NULL;
+
+	assert(bl_mem_params);
+
+	switch (image_id) {
+	case BL32_IMAGE_ID:
+		pager_mem_params = get_bl_mem_params_node(BL32_EXTRA1_IMAGE_ID);
+		assert(pager_mem_params);
+
+		paged_mem_params = get_bl_mem_params_node(BL32_EXTRA2_IMAGE_ID);
+		assert(paged_mem_params);
+
+		err = parse_optee_header(&bl_mem_params->ep_info,
+					 &pager_mem_params->image_info,
+					 &paged_mem_params->image_info);
+		if (err != 0) {
+			WARN("OPTEE header parse error.\n");
+		}
+
+		break;
+	default:
+		/* Do nothing in default case */
+		break;
+	}
+
+	return err;
+}
+
+unsigned int plat_get_syscnt_freq2(void)
+{
+	return COUNTER_FREQUENCY;
+}
+
+void bl2_plat_runtime_setup(void)
+{
+	return;
+}
diff --git a/plat/imx/imx8m/imx8mm/imx8mm_bl2_mem_params_desc.c b/plat/imx/imx8m/imx8mm/imx8mm_bl2_mem_params_desc.c
new file mode 100644
index 0000000..e44345d
--- /dev/null
+++ b/plat/imx/imx8m/imx8mm/imx8mm_bl2_mem_params_desc.c
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <common/desc_image_load.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+static bl_mem_params_node_t bl2_mem_params_descs[] = {
+	{
+		.image_id = BL31_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | EXECUTABLE | EP_FIRST_EXE),
+		.ep_info.pc = BL31_BASE,
+		.ep_info.spsr = SPSR_64(MODE_EL3, MODE_SP_ELX,
+					DISABLE_ALL_EXCEPTIONS),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_PLAT_SETUP),
+		.image_info.image_base = BL31_BASE,
+		.image_info.image_max_size = BL31_LIMIT - BL31_BASE,
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		.image_id = BL32_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | EXECUTABLE),
+		.ep_info.pc = BL32_BASE,
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2,
+				      image_info_t, 0),
+
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size = BL32_SIZE,
+
+		.next_handoff_image_id = BL33_IMAGE_ID,
+	},
+	{
+		.image_id = BL32_EXTRA1_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2,
+				      image_info_t, IMAGE_ATTRIB_SKIP_LOADING),
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size =  BL32_SIZE,
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		/* This is a zero sized image so we don't set base or size */
+		.image_id = BL32_EXTRA2_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		.image_id = BL33_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      NON_SECURE | EXECUTABLE),
+		# ifdef PRELOADED_BL33_BASE
+			.ep_info.pc = PLAT_NS_IMAGE_OFFSET,
+
+			SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+					      VERSION_2, image_info_t,
+					      IMAGE_ATTRIB_SKIP_LOADING),
+		# else
+			.ep_info.pc = PLAT_NS_IMAGE_OFFSET,
+
+			SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+					      VERSION_2, image_info_t, 0),
+			.image_info.image_base = PLAT_NS_IMAGE_OFFSET,
+			.image_info.image_max_size = PLAT_NS_IMAGE_SIZE,
+		# endif /* PRELOADED_BL33_BASE */
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	}
+};
+
+REGISTER_BL_IMAGE_DESCS(bl2_mem_params_descs);
diff --git a/plat/imx/imx8m/imx8mm/imx8mm_psci.c b/plat/imx/imx8m/imx8mm/imx8mm_psci.c
index e558724..815d3a2 100644
--- a/plat/imx/imx8m/imx8mm/imx8mm_psci.c
+++ b/plat/imx/imx8m/imx8mm/imx8mm_psci.c
@@ -28,6 +28,7 @@
 	.pwr_domain_pwr_down_wfi = imx_pwr_domain_pwr_down_wfi,
 	.get_sys_suspend_power_state = imx_get_sys_suspend_power_state,
 	.system_reset = imx_system_reset,
+	.system_reset2 = imx_system_reset2,
 	.system_off = imx_system_off,
 };
 
diff --git a/plat/imx/imx8m/imx8mm/imx8mm_rotpk.S b/plat/imx/imx8m/imx8mm/imx8mm_rotpk.S
new file mode 100644
index 0000000..544ee8a
--- /dev/null
+++ b/plat/imx/imx8m/imx8mm/imx8mm_rotpk.S
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+	.global imx8mm_rotpk_hash
+	.global imx8mm_rotpk_hash_end
+imx8mm_rotpk_hash:
+	/* DER header */
+	.byte 0x30, 0x31, 0x30, 0x0D, 0x06, 0x09, 0x60, 0x86, 0x48
+	.byte 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0x04, 0x20
+	/* SHA256 */
+	.incbin ROTPK_HASH
+imx8mm_rotpk_hash_end:
diff --git a/plat/imx/imx8m/imx8mm/imx8mm_trusted_boot.c b/plat/imx/imx8m/imx8mm/imx8mm_trusted_boot.c
new file mode 100644
index 0000000..a4384d7
--- /dev/null
+++ b/plat/imx/imx8m/imx8mm/imx8mm_trusted_boot.c
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/common/platform.h>
+
+extern char imx8mm_rotpk_hash[], imx8mm_rotpk_hash_end[];
+
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	*key_ptr = imx8mm_rotpk_hash;
+	*key_len = imx8mm_rotpk_hash_end - imx8mm_rotpk_hash;
+	*flags = ROTPK_IS_HASH;
+
+	return 0;
+}
+
+int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
+{
+	*nv_ctr = 0;
+
+	return 0;
+}
+
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	return 1;
+}
+
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	return get_mbedtls_heap_helper(heap_addr, heap_size);
+}
diff --git a/plat/imx/imx8m/imx8mm/include/imx8mm_private.h b/plat/imx/imx8m/imx8mm/include/imx8mm_private.h
new file mode 100644
index 0000000..5e0ef97
--- /dev/null
+++ b/plat/imx/imx8m/imx8mm/include/imx8mm_private.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef IMX8MM_PRIVATE_H
+#define IMX8MM_PRIVATE_H
+
+/*******************************************************************************
+ * Function and variable prototypes
+ ******************************************************************************/
+void plat_imx_io_setup(void);
+
+#endif /* IMX8MM_PRIVATE_H */
diff --git a/plat/imx/imx8m/imx8mm/include/platform_def.h b/plat/imx/imx8m/imx8mm/include/platform_def.h
index 1041459..6709678 100644
--- a/plat/imx/imx8m/imx8mm/include/platform_def.h
+++ b/plat/imx/imx8m/imx8mm/include/platform_def.h
@@ -1,9 +1,12 @@
 /*
- * Copyright (c) 2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <arch.h>
+#include <common/tbbr/tbbr_img_def.h>
+
 #define PLATFORM_LINKER_FORMAT		"elf64-littleaarch64"
 #define PLATFORM_LINKER_ARCH		aarch64
 
@@ -34,11 +37,27 @@
 #define PLAT_SDEI_NORMAL_PRI		0x20
 #define PLAT_SDEI_SGI_PRIVATE		U(9)
 
+#if defined(NEED_BL2)
+#define BL2_BASE			U(0x920000)
+#define BL2_LIMIT			U(0x940000)
+#define BL31_BASE			U(0x900000)
+#define BL31_LIMIT			U(0x920000)
+#define IMX_FIP_BASE			U(0x40310000)
+#define IMX_FIP_SIZE			U(0x000300000)
+#define IMX_FIP_LIMIT			U(FIP_BASE + FIP_SIZE)
+
+/* Define FIP image location on eMMC */
+#define IMX_FIP_MMC_BASE		U(0x100000)
+
+#define PLAT_IMX8MM_BOOT_MMC_BASE	U(0x30B50000) /* SD */
+#else
 #define BL31_BASE			U(0x920000)
 #define BL31_LIMIT			U(0x940000)
+#endif
 
 /* non-secure uboot base */
 #define PLAT_NS_IMAGE_OFFSET		U(0x40200000)
+#define PLAT_NS_IMAGE_SIZE		U(0x00200000)
 
 /* GICv3 base address */
 #define PLAT_GICD_BASE			U(0x38800000)
@@ -106,6 +125,8 @@
 #define SRC_OTG1PHY_SCR			U(0x20)
 #define SRC_OTG2PHY_SCR			U(0x24)
 #define SRC_GPR1_OFFSET			U(0x74)
+#define SRC_GPR10_OFFSET		U(0x98)
+#define SRC_GPR10_PERSIST_SECONDARY_BOOT	BIT(30)
 
 #define SNVS_LPCR			U(0x38)
 #define SNVS_LPCR_SRTC_ENV		BIT(0)
@@ -127,3 +148,7 @@
 #define COUNTER_FREQUENCY		8000000 /* 8MHz */
 
 #define IMX_WDOG_B_RESET
+
+#define MAX_IO_HANDLES			3U
+#define MAX_IO_DEVICES			2U
+#define MAX_IO_BLOCK_DEVICES		1U
diff --git a/plat/imx/imx8m/imx8mm/platform.mk b/plat/imx/imx8m/imx8mm/platform.mk
index ac636fa..ac5a809 100644
--- a/plat/imx/imx8m/imx8mm/platform.mk
+++ b/plat/imx/imx8m/imx8mm/platform.mk
@@ -6,7 +6,9 @@
 
 PLAT_INCLUDES		:=	-Iplat/imx/common/include		\
 				-Iplat/imx/imx8m/include		\
-				-Iplat/imx/imx8m/imx8mm/include
+				-Iplat/imx/imx8m/imx8mm/include		\
+				-Idrivers/imx/usdhc			\
+				-Iinclude/common/tbbr
 
 # Include GICv3 driver files
 include drivers/arm/gic/v3/gicv3.mk
@@ -39,6 +41,94 @@
 				drivers/delay_timer/generic_delay_timer.c	\
 				${IMX_GIC_SOURCES}
 
+ifeq (${NEED_BL2},yes)
+BL2_SOURCES		+=	common/desc_image_load.c			\
+				plat/imx/common/imx8_helpers.S			\
+				plat/imx/common/imx_uart_console.S		\
+				plat/imx/imx8m/imx8mm/imx8mm_bl2_el3_setup.c	\
+				plat/imx/imx8m/imx8mm/gpc.c			\
+				plat/imx/imx8m/imx_aipstz.c			\
+				plat/common/plat_psci_common.c			\
+				lib/xlat_tables/aarch64/xlat_tables.c		\
+				lib/xlat_tables/xlat_tables_common.c		\
+				lib/cpus/aarch64/cortex_a53.S			\
+				drivers/delay_timer/delay_timer.c		\
+				drivers/delay_timer/generic_delay_timer.c	\
+				${PLAT_GIC_SOURCES}				\
+				${PLAT_DRAM_SOURCES}				\
+				drivers/mmc/mmc.c				\
+				drivers/io/io_block.c				\
+				drivers/io/io_fip.c				\
+				drivers/io/io_memmap.c				\
+				drivers/io/io_storage.c				\
+				drivers/imx/usdhc/imx_usdhc.c			\
+				plat/imx/imx8m/imx8mm/imx8mm_bl2_mem_params_desc.c	\
+				plat/imx/common/imx_io_storage.c		\
+				plat/imx/imx8m/imx8m_image_load.c		\
+				lib/optee/optee_utils.c
+endif
+
+# Add the build options to pack BLx images and kernel device tree
+# in the FIP if the platform requires.
+ifneq ($(BL2),)
+RESET_TO_BL31		:=	0
+$(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/tb_fw.crt,--tb-fw-cert))
+endif
+ifneq ($(BL32_EXTRA1),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA1,--tos-fw-extra1))
+endif
+ifneq ($(BL32_EXTRA2),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA2,--tos-fw-extra2))
+endif
+ifneq ($(HW_CONFIG),)
+$(eval $(call TOOL_ADD_IMG,HW_CONFIG,--hw-config))
+endif
+
+ifeq (${NEED_BL2},yes)
+$(eval $(call add_define,NEED_BL2))
+LOAD_IMAGE_V2		:=	1
+# Non-TF Boot ROM
+BL2_AT_EL3		:=	1
+endif
+
+ifneq (${TRUSTED_BOARD_BOOT},0)
+
+include drivers/auth/mbedtls/mbedtls_crypto.mk
+include drivers/auth/mbedtls/mbedtls_x509.mk
+
+AUTH_SOURCES	:=	drivers/auth/auth_mod.c			\
+			drivers/auth/crypto_mod.c		\
+			drivers/auth/img_parser_mod.c		\
+			drivers/auth/tbbr/tbbr_cot_common.c     \
+			drivers/auth/tbbr/tbbr_cot_bl2.c
+
+BL2_SOURCES	+=	${AUTH_SOURCES}					\
+			plat/common/tbbr/plat_tbbr.c			\
+			plat/imx/imx8m/imx8mm/imx8mm_trusted_boot.c	\
+			plat/imx/imx8m/imx8mm/imx8mm_rotpk.S
+
+ROT_KEY             = $(BUILD_PLAT)/rot_key.pem
+ROTPK_HASH          = $(BUILD_PLAT)/rotpk_sha256.bin
+
+$(eval $(call add_define_val,ROTPK_HASH,'"$(ROTPK_HASH)"'))
+$(eval $(call MAKE_LIB_DIRS))
+
+$(BUILD_PLAT)/bl2/imx8mm_rotpk.o: $(ROTPK_HASH)
+
+certificates: $(ROT_KEY)
+
+$(ROT_KEY): | $(BUILD_PLAT)
+	@echo "  OPENSSL $@"
+	@if [ ! -f $(ROT_KEY) ]; then \
+		openssl genrsa 2048 > $@ 2>/dev/null; \
+	fi
+
+$(ROTPK_HASH): $(ROT_KEY)
+	@echo "  OPENSSL $@"
+	$(Q)openssl rsa -in $< -pubout -outform DER 2>/dev/null |\
+	openssl dgst -sha256 -binary > $@ 2>/dev/null
+endif
+
 USE_COHERENT_MEM	:=	1
 RESET_TO_BL31		:=	1
 A53_DISABLE_NON_TEMPORAL_HINT := 0
diff --git a/plat/imx/imx8m/imx8mn/include/platform_def.h b/plat/imx/imx8m/imx8mn/include/platform_def.h
index 2444e66..9c46d8d 100644
--- a/plat/imx/imx8m/imx8mn/include/platform_def.h
+++ b/plat/imx/imx8m/imx8mn/include/platform_def.h
@@ -34,6 +34,11 @@
 #define PLAT_WAIT_RET_STATE		U(1)
 #define PLAT_STOP_OFF_STATE		U(3)
 
+#define PLAT_PRI_BITS			U(3)
+#define PLAT_SDEI_CRITICAL_PRI		0x10
+#define PLAT_SDEI_NORMAL_PRI		0x20
+#define PLAT_SDEI_SGI_PRIVATE		U(9)
+
 #define BL31_BASE			U(0x960000)
 #define BL31_LIMIT			U(0x980000)
 
diff --git a/plat/imx/imx8m/imx8mn/platform.mk b/plat/imx/imx8m/imx8mn/platform.mk
index 8c4ad1c..2087089 100644
--- a/plat/imx/imx8m/imx8mn/platform.mk
+++ b/plat/imx/imx8m/imx8mn/platform.mk
@@ -31,6 +31,8 @@
 				plat/imx/common/imx_sip_handler.c		\
 				plat/imx/common/imx_sip_svc.c			\
 				plat/imx/common/imx_uart_console.S		\
+				plat/imx/common/imx_ehf.c                       \
+				plat/imx/common/imx_sdei.c                      \
 				lib/cpus/aarch64/cortex_a53.S			\
 				drivers/arm/tzc/tzc380.c			\
 				drivers/delay_timer/delay_timer.c		\
@@ -54,3 +56,6 @@
 
 IMX_BOOT_UART_BASE	?=	0x30890000
 $(eval $(call add_define,IMX_BOOT_UART_BASE))
+
+EL3_EXCEPTION_HANDLING := 1
+SDEI_SUPPORT := 1
diff --git a/plat/imx/imx8m/imx8mp/imx8mp_bl2_el3_setup.c b/plat/imx/imx8m/imx8mp/imx8mp_bl2_el3_setup.c
new file mode 100644
index 0000000..08cbeeb
--- /dev/null
+++ b/plat/imx/imx8m/imx8mp/imx8mp_bl2_el3_setup.c
@@ -0,0 +1,117 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdbool.h>
+
+#include <arch_helpers.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <common/desc_image_load.h>
+#include <common/tbbr/tbbr_img_def.h>
+#include <context.h>
+#include <drivers/arm/tzc380.h>
+#include <drivers/console.h>
+#include <drivers/generic_delay_timer.h>
+#include <drivers/mmc.h>
+#include <lib/el3_runtime/context_mgmt.h>
+#include <lib/mmio.h>
+#include <lib/optee_utils.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#include <imx8m_caam.h>
+#include "imx8mp_private.h"
+#include <imx_aipstz.h>
+#include <imx_rdc.h>
+#include <imx_uart.h>
+#include <plat/common/platform.h>
+#include <plat_imx8.h>
+#include <platform_def.h>
+
+
+static const struct aipstz_cfg aipstz[] = {
+	{IMX_AIPSTZ1, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ2, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ3, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{IMX_AIPSTZ4, 0x77777777, 0x77777777, .opacr = {0x0, 0x0, 0x0, 0x0, 0x0}, },
+	{0},
+};
+
+void bl2_el3_early_platform_setup(u_register_t arg0, u_register_t arg1,
+		u_register_t arg2, u_register_t arg3)
+{
+	static console_t console;
+	unsigned int i;
+
+	/* Enable CSU NS access permission */
+	for (i = 0U; i < 64; i++) {
+		mmio_write_32(IMX_CSU_BASE + i * 4, 0x00ff00ff);
+	}
+
+	imx_aipstz_init(aipstz);
+
+	console_imx_uart_register(IMX_BOOT_UART_BASE, IMX_BOOT_UART_CLK_IN_HZ,
+		IMX_CONSOLE_BAUDRATE, &console);
+
+	generic_delay_timer_init();
+
+	/* select the CKIL source to 32K OSC */
+	mmio_write_32(IMX_ANAMIX_BASE + ANAMIX_MISC_CTL, 0x1);
+
+	/* Open handles to a FIP image */
+	plat_imx_io_setup();
+}
+
+void bl2_el3_plat_arch_setup(void)
+{
+}
+
+void bl2_platform_setup(void)
+{
+}
+
+int bl2_plat_handle_post_image_load(unsigned int image_id)
+{
+	int err = 0;
+	bl_mem_params_node_t *bl_mem_params = get_bl_mem_params_node(image_id);
+	bl_mem_params_node_t *pager_mem_params = NULL;
+	bl_mem_params_node_t *paged_mem_params = NULL;
+
+	assert(bl_mem_params);
+
+	switch (image_id) {
+	case BL32_IMAGE_ID:
+		pager_mem_params = get_bl_mem_params_node(BL32_EXTRA1_IMAGE_ID);
+		assert(pager_mem_params);
+
+		paged_mem_params = get_bl_mem_params_node(BL32_EXTRA2_IMAGE_ID);
+		assert(paged_mem_params);
+
+		err = parse_optee_header(&bl_mem_params->ep_info,
+					 &pager_mem_params->image_info,
+					 &paged_mem_params->image_info);
+		if (err != 0) {
+			WARN("OPTEE header parse error.\n");
+		}
+
+		break;
+	default:
+		/* Do nothing in default case */
+		break;
+	}
+
+	return err;
+}
+
+unsigned int plat_get_syscnt_freq2(void)
+{
+	return COUNTER_FREQUENCY;
+}
+
+void bl2_plat_runtime_setup(void)
+{
+	return;
+}
diff --git a/plat/imx/imx8m/imx8mp/imx8mp_bl2_mem_params_desc.c b/plat/imx/imx8m/imx8mp/imx8mp_bl2_mem_params_desc.c
new file mode 100644
index 0000000..f2f6808
--- /dev/null
+++ b/plat/imx/imx8m/imx8mp/imx8mp_bl2_mem_params_desc.c
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <common/desc_image_load.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+static bl_mem_params_node_t bl2_mem_params_descs[] = {
+	{
+		.image_id = BL31_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | EXECUTABLE | EP_FIRST_EXE),
+		.ep_info.pc = BL31_BASE,
+		.ep_info.spsr = SPSR_64(MODE_EL3, MODE_SP_ELX,
+					DISABLE_ALL_EXCEPTIONS),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_PLAT_SETUP),
+		.image_info.image_base = BL31_BASE,
+		.image_info.image_max_size = BL31_LIMIT - BL31_BASE,
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		.image_id = BL32_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | EXECUTABLE),
+		.ep_info.pc = BL32_BASE,
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2,
+				      image_info_t, 0),
+
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size = BL32_SIZE,
+
+		.next_handoff_image_id = BL33_IMAGE_ID,
+	},
+	{
+		.image_id = BL32_EXTRA1_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP, VERSION_2,
+				      image_info_t, IMAGE_ATTRIB_SKIP_LOADING),
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size =  BL32_SIZE,
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		/* This is a zero sized image so we don't set base or size */
+		.image_id = BL32_EXTRA2_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	{
+		.image_id = BL33_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP, VERSION_2,
+				      entry_point_info_t,
+				      NON_SECURE | EXECUTABLE),
+		# ifdef PRELOADED_BL33_BASE
+			.ep_info.pc = PLAT_NS_IMAGE_OFFSET,
+
+			SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+					      VERSION_2, image_info_t,
+					      IMAGE_ATTRIB_SKIP_LOADING),
+		# else
+			.ep_info.pc = PLAT_NS_IMAGE_OFFSET,
+
+			SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+					      VERSION_2, image_info_t, 0),
+			.image_info.image_base = PLAT_NS_IMAGE_OFFSET,
+			.image_info.image_max_size = PLAT_NS_IMAGE_SIZE,
+		# endif /* PRELOADED_BL33_BASE */
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	}
+};
+
+REGISTER_BL_IMAGE_DESCS(bl2_mem_params_descs);
diff --git a/plat/imx/imx8m/imx8mp/imx8mp_rotpk.S b/plat/imx/imx8m/imx8mp/imx8mp_rotpk.S
new file mode 100644
index 0000000..a4c7ce1
--- /dev/null
+++ b/plat/imx/imx8m/imx8mp/imx8mp_rotpk.S
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+	.global imx8mp_rotpk_hash
+	.global imx8mp_rotpk_hash_end
+imx8mp_rotpk_hash:
+	/* DER header */
+	.byte 0x30, 0x31, 0x30, 0x0D, 0x06, 0x09, 0x60, 0x86, 0x48
+	.byte 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0x04, 0x20
+	/* SHA256 */
+	.incbin ROTPK_HASH
+imx8mp_rotpk_hash_end:
diff --git a/plat/imx/imx8m/imx8mp/imx8mp_trusted_boot.c b/plat/imx/imx8m/imx8mp/imx8mp_trusted_boot.c
new file mode 100644
index 0000000..5d1a6c2
--- /dev/null
+++ b/plat/imx/imx8m/imx8mp/imx8mp_trusted_boot.c
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat/common/platform.h>
+
+extern char imx8mp_rotpk_hash[], imx8mp_rotpk_hash_end[];
+
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	*key_ptr = imx8mp_rotpk_hash;
+	*key_len = imx8mp_rotpk_hash_end - imx8mp_rotpk_hash;
+	*flags = ROTPK_IS_HASH;
+
+	return 0;
+}
+
+int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
+{
+	*nv_ctr = 0;
+
+	return 0;
+}
+
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	return 1;
+}
+
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	return get_mbedtls_heap_helper(heap_addr, heap_size);
+}
diff --git a/plat/imx/imx8m/imx8mp/include/imx8mp_private.h b/plat/imx/imx8m/imx8mp/include/imx8mp_private.h
new file mode 100644
index 0000000..0a02334
--- /dev/null
+++ b/plat/imx/imx8m/imx8mp/include/imx8mp_private.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef IMX8MP_PRIVATE_H
+#define IMX8MP_PRIVATE_H
+
+/*******************************************************************************
+ * Function and variable prototypes
+ ******************************************************************************/
+void plat_imx_io_setup(void);
+
+#endif /* IMX8MP_PRIVATE_H */
diff --git a/plat/imx/imx8m/imx8mp/include/platform_def.h b/plat/imx/imx8m/imx8mp/include/platform_def.h
index 644adc7..14b7ea0 100644
--- a/plat/imx/imx8m/imx8mp/include/platform_def.h
+++ b/plat/imx/imx8m/imx8mp/include/platform_def.h
@@ -6,6 +6,7 @@
 #ifndef PLATFORM_DEF_H
 #define PLATFORM_DEF_H
 
+#include <common/tbbr/tbbr_img_def.h>
 #include <lib/utils_def.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
 
@@ -34,11 +35,32 @@
 #define PLAT_WAIT_RET_STATE		U(1)
 #define PLAT_STOP_OFF_STATE		U(3)
 
+#if defined(NEED_BL2)
+#define BL2_BASE			U(0x960000)
+#define BL2_LIMIT			U(0x980000)
+#define BL31_BASE			U(0x940000)
+#define BL31_LIMIT			U(0x960000)
+#define IMX_FIP_BASE			U(0x40310000)
+#define IMX_FIP_SIZE			U(0x000300000)
+#define IMX_FIP_LIMIT			U(FIP_BASE + FIP_SIZE)
+
+/* Define FIP image location on eMMC */
+#define IMX_FIP_MMC_BASE		U(0x100000)
+
+#define PLAT_IMX8MP_BOOT_MMC_BASE	U(0x30B50000) /* SD */
+#else
 #define BL31_BASE			U(0x960000)
 #define BL31_LIMIT			U(0x980000)
+#endif
+
+#define PLAT_PRI_BITS			U(3)
+#define PLAT_SDEI_CRITICAL_PRI		0x10
+#define PLAT_SDEI_NORMAL_PRI		0x20
+#define PLAT_SDEI_SGI_PRIVATE		U(9)
 
 /* non-secure uboot base */
 #define PLAT_NS_IMAGE_OFFSET		U(0x40200000)
+#define PLAT_NS_IMAGE_SIZE		U(0x00200000)
 
 /* GICv3 base address */
 #define PLAT_GICD_BASE			U(0x38800000)
@@ -145,6 +167,10 @@
 
 #define IMX_WDOG_B_RESET
 
+#define MAX_IO_HANDLES			3U
+#define MAX_IO_DEVICES			2U
+#define MAX_IO_BLOCK_DEVICES		1U
+
 #define GIC_MAP		MAP_REGION_FLAT(IMX_GIC_BASE, IMX_GIC_SIZE, MT_DEVICE | MT_RW)
 #define AIPS_MAP	MAP_REGION_FLAT(IMX_AIPS_BASE, IMX_AIPS_SIZE, MT_DEVICE | MT_RW) /* AIPS map */
 #define OCRAM_S_MAP	MAP_REGION_FLAT(OCRAM_S_BASE, OCRAM_S_SIZE, MT_MEMORY | MT_RW) /* OCRAM_S */
diff --git a/plat/imx/imx8m/imx8mp/platform.mk b/plat/imx/imx8m/imx8mp/platform.mk
index 1d11e3d..823b5d6 100644
--- a/plat/imx/imx8m/imx8mp/platform.mk
+++ b/plat/imx/imx8m/imx8mp/platform.mk
@@ -6,7 +6,9 @@
 
 PLAT_INCLUDES		:=	-Iplat/imx/common/include		\
 				-Iplat/imx/imx8m/include		\
-				-Iplat/imx/imx8m/imx8mp/include
+				-Iplat/imx/imx8m/imx8mp/include		\
+				-Idrivers/imx/usdhc			\
+				-Iinclude/common/tbbr
 # Translation tables library
 include lib/xlat_tables_v2/xlat_tables.mk
 
@@ -28,6 +30,8 @@
 				plat/imx/imx8m/imx8mp/imx8mp_psci.c		\
 				plat/imx/imx8m/imx8mp/gpc.c			\
 				plat/imx/common/imx8_topology.c			\
+				plat/imx/common/imx_ehf.c                       \
+				plat/imx/common/imx_sdei.c                      \
 				plat/imx/common/imx_sip_handler.c		\
 				plat/imx/common/imx_sip_svc.c			\
 				plat/imx/common/imx_uart_console.S		\
@@ -38,6 +42,96 @@
 				${IMX_GIC_SOURCES}				\
 				${XLAT_TABLES_LIB_SRCS}
 
+ifeq (${NEED_BL2},yes)
+BL2_SOURCES		+=	common/desc_image_load.c			\
+				plat/imx/common/imx8_helpers.S			\
+				plat/imx/common/imx_uart_console.S		\
+				plat/imx/imx8m/imx8mp/imx8mp_bl2_el3_setup.c	\
+				plat/imx/imx8m/imx8mp/gpc.c			\
+				plat/imx/imx8m/imx_aipstz.c			\
+				plat/imx/imx8m/imx_rdc.c			\
+				plat/imx/imx8m/imx8m_caam.c			\
+				plat/common/plat_psci_common.c			\
+				lib/cpus/aarch64/cortex_a53.S			\
+				drivers/arm/tzc/tzc380.c			\
+				drivers/delay_timer/delay_timer.c		\
+				drivers/delay_timer/generic_delay_timer.c	\
+				${PLAT_GIC_SOURCES}				\
+				${PLAT_DRAM_SOURCES}				\
+				${XLAT_TABLES_LIB_SRCS}				\
+				drivers/mmc/mmc.c				\
+				drivers/io/io_block.c				\
+				drivers/io/io_fip.c				\
+				drivers/io/io_memmap.c				\
+				drivers/io/io_storage.c				\
+				drivers/imx/usdhc/imx_usdhc.c			\
+				plat/imx/imx8m/imx8mp/imx8mp_bl2_mem_params_desc.c	\
+				plat/imx/common/imx_io_storage.c		\
+				plat/imx/imx8m/imx8m_image_load.c		\
+				lib/optee/optee_utils.c
+endif
+
+# Add the build options to pack BLx images and kernel device tree
+# in the FIP if the platform requires.
+ifneq ($(BL2),)
+RESET_TO_BL31		:=	0
+$(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/tb_fw.crt,--tb-fw-cert))
+endif
+ifneq ($(BL32_EXTRA1),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA1,--tos-fw-extra1))
+endif
+ifneq ($(BL32_EXTRA2),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA2,--tos-fw-extra2))
+endif
+ifneq ($(HW_CONFIG),)
+$(eval $(call TOOL_ADD_IMG,HW_CONFIG,--hw-config))
+endif
+
+ifeq (${NEED_BL2},yes)
+$(eval $(call add_define,NEED_BL2))
+LOAD_IMAGE_V2		:=	1
+# Non-TF Boot ROM
+BL2_AT_EL3		:=	1
+endif
+
+ifneq (${TRUSTED_BOARD_BOOT},0)
+
+include drivers/auth/mbedtls/mbedtls_crypto.mk
+include drivers/auth/mbedtls/mbedtls_x509.mk
+
+AUTH_SOURCES	:=	drivers/auth/auth_mod.c			\
+			drivers/auth/crypto_mod.c		\
+			drivers/auth/img_parser_mod.c		\
+			drivers/auth/tbbr/tbbr_cot_common.c     \
+			drivers/auth/tbbr/tbbr_cot_bl2.c
+
+BL2_SOURCES		+=	${AUTH_SOURCES}					\
+				plat/common/tbbr/plat_tbbr.c			\
+				plat/imx/imx8m/imx8mp/imx8mp_trusted_boot.c	\
+				plat/imx/imx8m/imx8mp/imx8mp_rotpk.S
+
+ROT_KEY             = $(BUILD_PLAT)/rot_key.pem
+ROTPK_HASH          = $(BUILD_PLAT)/rotpk_sha256.bin
+
+$(eval $(call add_define_val,ROTPK_HASH,'"$(ROTPK_HASH)"'))
+$(eval $(call MAKE_LIB_DIRS))
+
+$(BUILD_PLAT)/bl2/imx8mp_rotpk.o: $(ROTPK_HASH)
+
+certificates: $(ROT_KEY)
+
+$(ROT_KEY): | $(BUILD_PLAT)
+	@echo "  OPENSSL $@"
+	@if [ ! -f $(ROT_KEY) ]; then \
+		openssl genrsa 2048 > $@ 2>/dev/null; \
+	fi
+
+$(ROTPK_HASH): $(ROT_KEY)
+	@echo "  OPENSSL $@"
+	$(Q)openssl rsa -in $< -pubout -outform DER 2>/dev/null |\
+	openssl dgst -sha256 -binary > $@ 2>/dev/null
+endif
+
 USE_COHERENT_MEM	:=	1
 RESET_TO_BL31		:=	1
 A53_DISABLE_NON_TEMPORAL_HINT := 0
@@ -54,3 +148,6 @@
 
 IMX_BOOT_UART_BASE	?=	0x30890000
 $(eval $(call add_define,IMX_BOOT_UART_BASE))
+
+EL3_EXCEPTION_HANDLING := 1
+SDEI_SUPPORT := 1
diff --git a/plat/imx/imx8m/imx8mq/imx8mq_psci.c b/plat/imx/imx8m/imx8mq/imx8mq_psci.c
index 04e191f..662017d 100644
--- a/plat/imx/imx8m/imx8mq/imx8mq_psci.c
+++ b/plat/imx/imx8m/imx8mq/imx8mq_psci.c
@@ -117,6 +117,7 @@
 	.pwr_domain_pwr_down_wfi = imx_pwr_domain_pwr_down_wfi,
 	.get_sys_suspend_power_state = imx_get_sys_suspend_power_state,
 	.system_reset = imx_system_reset,
+	.system_reset2 = imx_system_reset2,
 	.system_off = imx_system_off,
 };
 
diff --git a/plat/imx/imx8m/imx8mq/include/platform_def.h b/plat/imx/imx8m/imx8mq/include/platform_def.h
index 9db3a13..6d6a865 100644
--- a/plat/imx/imx8m/imx8mq/include/platform_def.h
+++ b/plat/imx/imx8m/imx8mq/include/platform_def.h
@@ -103,6 +103,8 @@
 #define SRC_OTG1PHY_SCR			U(0x20)
 #define SRC_OTG2PHY_SCR			U(0x24)
 #define SRC_GPR1_OFFSET			U(0x74)
+#define SRC_GPR10_OFFSET		U(0x98)
+#define SRC_GPR10_PERSIST_SECONDARY_BOOT	BIT(30)
 
 #define SNVS_LPCR			U(0x38)
 #define SNVS_LPCR_SRTC_ENV		BIT(0)
diff --git a/plat/imx/imx8m/include/gpc.h b/plat/imx/imx8m/include/gpc.h
index 075da91..29b8ecf 100644
--- a/plat/imx/imx8m/include/gpc.h
+++ b/plat/imx/imx8m/include/gpc.h
@@ -32,7 +32,7 @@
 		.pwr_req = name##_PWR_REQ,		\
 		.pgc_offset = name##_PGC,		\
 		.need_sync = false,			\
-		.always_on = true,			\
+		.always_on = (on),			\
 	}
 
 #define IMX_MIX_DOMAIN(name, on)			\
@@ -42,7 +42,7 @@
 		.adb400_sync = name##_ADB400_SYNC,	\
 		.adb400_ack = name##_ADB400_ACK,	\
 		.need_sync = true,			\
-		.always_on = true,			\
+		.always_on = (on),			\
 	}
 
 struct imx_pwr_domain {
diff --git a/plat/imx/imx8m/include/imx8m_psci.h b/plat/imx/imx8m/include/imx8m_psci.h
index c33d25e..7d14d11 100644
--- a/plat/imx/imx8m/include/imx8m_psci.h
+++ b/plat/imx/imx8m/include/imx8m_psci.h
@@ -19,5 +19,6 @@
 void imx_domain_suspend(const psci_power_state_t *target_state);
 void imx_domain_suspend_finish(const psci_power_state_t *target_state);
 void __dead2 imx_pwr_domain_pwr_down_wfi(const psci_power_state_t *target_state);
+int imx_system_reset2(int is_vendor, int reset_type, u_register_t cookie);
 
 #endif /* IMX8M_PSCI_H */
diff --git a/plat/imx/imx8qm/imx8qm_bl31_setup.c b/plat/imx/imx8qm/imx8qm_bl31_setup.c
index 4ca6a5d..d9c9110 100644
--- a/plat/imx/imx8qm/imx8qm_bl31_setup.c
+++ b/plat/imx/imx8qm/imx8qm_bl31_setup.c
@@ -5,6 +5,8 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <stdbool.h>
 
 #include <platform_def.h>
@@ -261,14 +263,14 @@
 			err = sc_rm_get_memreg_info(ipc_handle, mr, &start, &end);
 			if (err)
 				ERROR("Memreg get info failed, %u\n", mr);
-			NOTICE("Memreg %u 0x%llx -- 0x%llx\n", mr, start, end);
+			NOTICE("Memreg %u 0x%" PRIx64 " -- 0x%" PRIx64 "\n", mr, start, end);
 			if (BL31_BASE >= start && (BL31_LIMIT - 1) <= end) {
 				mr_record = mr; /* Record the mr for ATF running */
 			} else {
 				err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 				if (err)
-					ERROR("Memreg assign failed, 0x%llx -- 0x%llx, \
-						err %d\n", start, end, err);
+					ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 ", \
+					      err %d\n", start, end, err);
 			}
 		}
 	}
@@ -280,23 +282,23 @@
 		if ((BL31_LIMIT - 1) < end) {
 			err = sc_rm_memreg_alloc(ipc_handle, &mr, BL31_LIMIT, end);
 			if (err)
-				ERROR("sc_rm_memreg_alloc failed, 0x%llx -- 0x%llx\n",
-					(sc_faddr_t)BL31_LIMIT, end);
+				ERROR("sc_rm_memreg_alloc failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      (sc_faddr_t)BL31_LIMIT, end);
 			err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 			if (err)
-				ERROR("Memreg assign failed, 0x%llx -- 0x%llx\n",
-					(sc_faddr_t)BL31_LIMIT, end);
+				ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      (sc_faddr_t)BL31_LIMIT, end);
 		}
 
 		if (start < (BL31_BASE - 1)) {
 			err = sc_rm_memreg_alloc(ipc_handle, &mr, start, BL31_BASE - 1);
 			if (err)
-				ERROR("sc_rm_memreg_alloc failed, 0x%llx -- 0x%llx\n",
-					start, (sc_faddr_t)BL31_BASE - 1);
+				ERROR("sc_rm_memreg_alloc failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      start, (sc_faddr_t)BL31_BASE - 1);
 			err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 				if (err)
-					ERROR("Memreg assign failed, 0x%llx -- 0x%llx\n",
-						start, (sc_faddr_t)BL31_BASE - 1);
+					ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+					      start, (sc_faddr_t)BL31_BASE - 1);
 		}
 	}
 
diff --git a/plat/imx/imx8qx/imx8qx_bl31_setup.c b/plat/imx/imx8qx/imx8qx_bl31_setup.c
index 3ff5400..3739cd6 100644
--- a/plat/imx/imx8qx/imx8qx_bl31_setup.c
+++ b/plat/imx/imx8qx/imx8qx_bl31_setup.c
@@ -5,7 +5,9 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
 #include <stdbool.h>
+#include <stdint.h>
 
 #include <platform_def.h>
 
@@ -238,14 +240,14 @@
 			if (err)
 				ERROR("Memreg get info failed, %u\n", mr);
 
-			NOTICE("Memreg %u 0x%llx -- 0x%llx\n", mr, start, end);
+			NOTICE("Memreg %u 0x%" PRIx64 " -- 0x%" PRIx64 "\n", mr, start, end);
 			if (BL31_BASE >= start && (BL31_LIMIT - 1) <= end) {
 				mr_record = mr; /* Record the mr for ATF running */
 			} else {
 				err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 				if (err)
-					ERROR("Memreg assign failed, 0x%llx -- 0x%llx, \
-						err %d\n", start, end, err);
+					ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 ", \
+					      err %d\n", start, end, err);
 			}
 		}
 	}
@@ -257,23 +259,23 @@
 		if ((BL31_LIMIT - 1) < end) {
 			err = sc_rm_memreg_alloc(ipc_handle, &mr, BL31_LIMIT, end);
 			if (err)
-				ERROR("sc_rm_memreg_alloc failed, 0x%llx -- 0x%llx\n",
-					(sc_faddr_t)BL31_LIMIT, end);
+				ERROR("sc_rm_memreg_alloc failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      (sc_faddr_t)BL31_LIMIT, end);
 			err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 			if (err)
-				ERROR("Memreg assign failed, 0x%llx -- 0x%llx\n",
-					(sc_faddr_t)BL31_LIMIT, end);
+				ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      (sc_faddr_t)BL31_LIMIT, end);
 		}
 
 		if (start < (BL31_BASE - 1)) {
 			err = sc_rm_memreg_alloc(ipc_handle, &mr, start, BL31_BASE - 1);
 			if (err)
-				ERROR("sc_rm_memreg_alloc failed, 0x%llx -- 0x%llx\n",
-					start, (sc_faddr_t)BL31_BASE - 1);
+				ERROR("sc_rm_memreg_alloc failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      start, (sc_faddr_t)BL31_BASE - 1);
 			err = sc_rm_assign_memreg(ipc_handle, os_part, mr);
 			if (err)
-				ERROR("Memreg assign failed, 0x%llx -- 0x%llx\n",
-					start, (sc_faddr_t)BL31_BASE - 1);
+				ERROR("Memreg assign failed, 0x%" PRIx64 " -- 0x%" PRIx64 "\n",
+				      start, (sc_faddr_t)BL31_BASE - 1);
 		}
 	}
 
diff --git a/plat/intel/soc/agilex/bl2_plat_setup.c b/plat/intel/soc/agilex/bl2_plat_setup.c
index f002947..b6b3e16 100644
--- a/plat/intel/soc/agilex/bl2_plat_setup.c
+++ b/plat/intel/soc/agilex/bl2_plat_setup.c
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Intel Corporation. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, Intel Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -29,6 +29,7 @@
 #include "socfpga_system_manager.h"
 #include "wdt/watchdog.h"
 
+static struct mmc_device_info mmc_info;
 
 const mmap_region_t agilex_plat_mmap[] = {
 	MAP_REGION_FLAT(DRAM_BASE, DRAM_SIZE,
@@ -87,7 +88,6 @@
 void bl2_el3_plat_arch_setup(void)
 {
 
-	struct mmc_device_info info;
 	const mmap_region_t bl_regions[] = {
 		MAP_REGION_FLAT(BL2_BASE, BL2_END - BL2_BASE,
 			MT_MEMORY | MT_RW | MT_SECURE),
@@ -110,12 +110,12 @@
 
 	dw_mmc_params_t params = EMMC_INIT_PARAMS(0x100000, get_mmc_clk());
 
-	info.mmc_dev_type = MMC_IS_SD;
-	info.ocr_voltage = OCR_3_3_3_4 | OCR_3_2_3_3;
+	mmc_info.mmc_dev_type = MMC_IS_SD;
+	mmc_info.ocr_voltage = OCR_3_3_3_4 | OCR_3_2_3_3;
 
 	switch (boot_source) {
 	case BOOT_SOURCE_SDMMC:
-		dw_mmc_init(&params, &info);
+		dw_mmc_init(&params, &mmc_info);
 		socfpga_io_setup(boot_source);
 		break;
 
diff --git a/plat/intel/soc/stratix10/bl2_plat_setup.c b/plat/intel/soc/stratix10/bl2_plat_setup.c
index 721a690..ecf1f01 100644
--- a/plat/intel/soc/stratix10/bl2_plat_setup.c
+++ b/plat/intel/soc/stratix10/bl2_plat_setup.c
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2019-2020, Intel Corporation. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, Intel Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -27,6 +27,7 @@
 #include "s10_pinmux.h"
 #include "wdt/watchdog.h"
 
+static struct mmc_device_info mmc_info;
 
 const mmap_region_t plat_stratix10_mmap[] = {
 	MAP_REGION_FLAT(DRAM_BASE, DRAM_SIZE,
@@ -83,7 +84,6 @@
 void bl2_el3_plat_arch_setup(void)
 {
 
-	struct mmc_device_info info;
 	const mmap_region_t bl_regions[] = {
 		MAP_REGION_FLAT(BL2_BASE, BL2_END - BL2_BASE,
 			MT_MEMORY | MT_RW | MT_SECURE),
@@ -106,12 +106,12 @@
 
 	dw_mmc_params_t params = EMMC_INIT_PARAMS(0x100000, get_mmc_clk());
 
-	info.mmc_dev_type = MMC_IS_SD;
-	info.ocr_voltage = OCR_3_3_3_4 | OCR_3_2_3_3;
+	mmc_info.mmc_dev_type = MMC_IS_SD;
+	mmc_info.ocr_voltage = OCR_3_3_3_4 | OCR_3_2_3_3;
 
 	switch (boot_source) {
 	case BOOT_SOURCE_SDMMC:
-		dw_mmc_init(&params, &info);
+		dw_mmc_init(&params, &mmc_info);
 		socfpga_io_setup(boot_source);
 		break;
 
diff --git a/plat/marvell/armada/a3k/a3700/board/pm_src.c b/plat/marvell/armada/a3k/a3700/board/pm_src.c
index d6eca5d..247f73b 100644
--- a/plat/marvell/armada/a3k/a3700/board/pm_src.c
+++ b/plat/marvell/armada/a3k/a3700/board/pm_src.c
@@ -8,7 +8,7 @@
 #include <a3700_pm.h>
 #include <plat_marvell.h>
 
-/* This struct provides the PM wake up src configuration */
+/* This struct provides the PM wake up src configuration for A3720 Development Board */
 static struct pm_wake_up_src_config wake_up_src_cfg = {
 	.wake_up_src_num = 3,
 	.wake_up_src[0] = {
diff --git a/plat/marvell/armada/a3k/common/a3700_common.mk b/plat/marvell/armada/a3k/common/a3700_common.mk
index 2050d59..d0e8688 100644
--- a/plat/marvell/armada/a3k/common/a3700_common.mk
+++ b/plat/marvell/armada/a3k/common/a3700_common.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (C) 2018 Marvell International Ltd.
+# Copyright (C) 2018-2021 Marvell International Ltd.
 #
 # SPDX-License-Identifier:	BSD-3-Clause
 # https://spdx.org/licenses
@@ -13,7 +13,9 @@
 PLAT_COMMON_BASE		:= $(PLAT_FAMILY_BASE)/common
 MARVELL_DRV_BASE		:= drivers/marvell
 MARVELL_COMMON_BASE		:= $(MARVELL_PLAT_BASE)/common
-HANDLE_EA_EL3_FIRST		:= 1
+ERRATA_A53_1530924		:= 1
+
+include plat/marvell/marvell.mk
 
 #*********** A3700 *************
 
@@ -36,73 +38,87 @@
 				-I$/drivers/arm/gic/common/
 
 PLAT_BL_COMMON_SOURCES	:=	$(PLAT_COMMON_BASE)/aarch64/a3700_common.c \
-				$(MARVELL_COMMON_BASE)/marvell_cci.c	   \
+				$(PLAT_COMMON_BASE)/aarch64/a3700_clock.S \
 				$(MARVELL_DRV_BASE)/uart/a3700_console.S
 
 BL1_SOURCES		+=	$(PLAT_COMMON_BASE)/aarch64/plat_helpers.S \
 				lib/cpus/aarch64/cortex_a53.S
 
-BL31_PORTING_SOURCES	:=	$(PLAT_FAMILY_BASE)/$(PLAT)/board/pm_src.c
-
 MARVELL_DRV		:=	$(MARVELL_DRV_BASE)/comphy/phy-comphy-3700.c
 
 BL31_SOURCES		+=	lib/cpus/aarch64/cortex_a53.S		\
 				$(PLAT_COMMON_BASE)/aarch64/plat_helpers.S \
+				$(PLAT_COMMON_BASE)/plat_cci.c		\
 				$(PLAT_COMMON_BASE)/plat_pm.c		\
 				$(PLAT_COMMON_BASE)/dram_win.c		\
 				$(PLAT_COMMON_BASE)/io_addr_dec.c	\
 				$(PLAT_COMMON_BASE)/marvell_plat_config.c     \
-				$(PLAT_COMMON_BASE)/a3700_ea.c		\
 				$(PLAT_FAMILY_BASE)/$(PLAT)/plat_bl31_setup.c \
+				$(MARVELL_COMMON_BASE)/marvell_cci.c	\
 				$(MARVELL_COMMON_BASE)/marvell_ddr_info.c	\
 				$(MARVELL_COMMON_BASE)/marvell_gicv3.c	\
 				$(MARVELL_GIC_SOURCES)			\
 				drivers/arm/cci/cci.c			\
-				$(BL31_PORTING_SOURCES)			\
 				$(PLAT_COMMON_BASE)/a3700_sip_svc.c	\
 				$(MARVELL_DRV)
 
-ifneq (${WTP},)
+ifeq ($(HANDLE_EA_EL3_FIRST),1)
+BL31_SOURCES		+=	$(PLAT_COMMON_BASE)/a3700_ea.c
+endif
 
-DOIMAGEPATH	:= $(WTP)
-DOIMAGETOOL	:= $(DOIMAGEPATH)/wtptp/linux/tbb_linux
+ifeq ($(CM3_SYSTEM_RESET),1)
+BL31_SOURCES		+=	$(PLAT_COMMON_BASE)/cm3_system_reset.c
+endif
 
-include plat/marvell/marvell.mk
+ifeq ($(A3720_DB_PM_WAKEUP_SRC),1)
+BL31_SOURCES		+=	$(PLAT_FAMILY_BASE)/$(PLAT)/board/pm_src.c
+endif
+
+ifdef WTP
+
+# Do not remove! Following checks are required to ensure correct TF-A builds, removing these checks leads to broken TF-A builds
+$(if $(wildcard $(value WTP)/*),,$(error "'WTP=$(value WTP)' was specified, but '$(value WTP)' directory does not exist"))
+$(if $(shell git -C $(value WTP) rev-parse --show-cdup 2>&1),$(error "'WTP=$(value WTP)' was specified, but '$(value WTP)' does not contain valid A3700-utils-marvell git repository"))
+
+TBB		:= $(WTP)/wtptp/src/TBB_Linux/release/TBB_linux
+
+BUILD_UART	:= uart-images
+UART_IMAGE	:= $(BUILD_UART).tgz.bin
 
 ifeq ($(MARVELL_SECURE_BOOT),1)
-DOIMAGE_CFG	:= $(DOIMAGEPATH)/atf-tim.txt
-IMAGESPATH	:= $(DOIMAGEPATH)/tim/trusted
-
-TIMNCFG		:= $(DOIMAGEPATH)/atf-timN.txt
-TIMNSIG		:= $(IMAGESPATH)/timnsign.txt
-TIM2IMGARGS	:= -i $(DOIMAGE_CFG) -n $(TIMNCFG)
-TIMN_IMAGE	:= $$(grep "Image Filename:" -m 1 $(TIMNCFG) | cut -c 17-)
+TIM_CFG		:= $(BUILD_PLAT)/atf-tim.txt
+TIM_UART_CFG	:= $(BUILD_PLAT)/$(BUILD_UART)/atf-tim.txt
+IMAGESPATH	:= $(WTP)/tim/trusted
+TIMN_CFG	:= $(BUILD_PLAT)/atf-timN.txt
+TIMN_UART_CFG	:= $(BUILD_PLAT)/$(BUILD_UART)/atf-timN.txt
+TIMN_SIG	:= $(IMAGESPATH)/timnsign.txt
+TIM2IMGARGS	:= -i $(TIM_CFG) -n $(TIMN_CFG)
+TIMN_UART_IMAGE	:= $$(grep "Image Filename:" -m 1 $(TIMN_UART_CFG) | cut -c 17-)
 else #MARVELL_SECURE_BOOT
-DOIMAGE_CFG	:= $(DOIMAGEPATH)/atf-ntim.txt
-IMAGESPATH	:= $(DOIMAGEPATH)/tim/untrusted
-TIM2IMGARGS	:= -i $(DOIMAGE_CFG)
+TIM_CFG		:= $(BUILD_PLAT)/atf-ntim.txt
+TIM_UART_CFG	:= $(BUILD_PLAT)/$(BUILD_UART)/atf-ntim.txt
+IMAGESPATH	:= $(WTP)/tim/untrusted
+TIM2IMGARGS	:= -i $(TIM_CFG)
 endif #MARVELL_SECURE_BOOT
 
-TIMBUILD	:= $(DOIMAGEPATH)/script/buildtim.sh
-TIM2IMG		:= $(DOIMAGEPATH)/script/tim2img.pl
+TIM_UART_IMAGE	:= $$(grep "Image Filename:" -m 1 $(TIM_UART_CFG) | cut -c 17-)
+
+TIMBUILD	:= $(WTP)/script/buildtim.sh
+TIM2IMG		:= $(WTP)/script/tim2img.pl
+TIMDDRTOOL	:= $(WTP)/tim/ddr/ddr_tool
+
+$(TIMBUILD): $(TIMDDRTOOL)
 
 # WTMI_IMG is used to specify the customized RTOS image running over
 # Service CPU (CM3 processor). By the default, it points to a
 # baremetal binary of fuse programming in A3700_utils.
-WTMI_IMG	:= $(DOIMAGEPATH)/wtmi/fuse/build/fuse.bin
-
-# WTMI_SYSINIT_IMG is used for the system early initialization,
-# such as AVS settings, clock-tree setup and dynamic DDR PHY training.
-# After the initialization is done, this image will be wiped out
-# from the memory and CM3 will continue with RTOS image or other application.
-WTMI_SYSINIT_IMG	:= $(DOIMAGEPATH)/wtmi/sys_init/build/sys_init.bin
+WTMI_IMG	:= $(WTP)/wtmi/fuse/build/fuse.bin
 
 # WTMI_MULTI_IMG is composed of CM3 RTOS image (WTMI_IMG)
-# and sys-init image (WTMI_SYSINIT_IMG).
-WTMI_MULTI_IMG		:= $(DOIMAGEPATH)/wtmi/build/wtmi.bin
+# and sys-init image.
+WTMI_MULTI_IMG		:= $(WTP)/wtmi/build/wtmi.bin
 
-WTMI_ENC_IMG		:= $(DOIMAGEPATH)/wtmi/build/wtmi-enc.bin
-BUILD_UART		:= uart-images
+WTMI_ENC_IMG		:= wtmi-enc.bin
 
 SRCPATH			:= $(dir $(BL33))
 
@@ -113,70 +129,119 @@
 BOOTDEV			?= SPINOR
 PARTNUM			?= 0
 
-TIM_IMAGE		:= $$(grep "Image Filename:" -m 1 $(DOIMAGE_CFG) | cut -c 17-)
-TIMBLDARGS		:= $(MARVELL_SECURE_BOOT) $(BOOTDEV) $(IMAGESPATH) $(DOIMAGEPATH) $(CLOCKSPRESET) \
-				$(DDR_TOPOLOGY) $(PARTNUM) $(DEBUG) $(DOIMAGE_CFG) $(TIMNCFG) $(TIMNSIG) 1
-TIMBLDUARTARGS		:= $(MARVELL_SECURE_BOOT) UART $(IMAGESPATH) $(DOIMAGEPATH) $(CLOCKSPRESET) \
-				$(DDR_TOPOLOGY) 0 0 $(DOIMAGE_CFG) $(TIMNCFG) $(TIMNSIG) 0
-DOIMAGE_FLAGS		:= -r $(DOIMAGE_CFG) -v -D
+TIMBLDARGS		:= $(MARVELL_SECURE_BOOT) $(BOOTDEV) $(IMAGESPATH) $(WTP) $(CLOCKSPRESET) \
+				$(DDR_TOPOLOGY) $(PARTNUM) $(DEBUG) $(TIM_CFG) $(TIMN_CFG) $(TIMN_SIG) 1
+TIMBLDUARTARGS		:= $(MARVELL_SECURE_BOOT) UART $(IMAGESPATH) $(WTP) $(CLOCKSPRESET) \
+				$(DDR_TOPOLOGY) 0 0 $(TIM_UART_CFG) $(TIMN_UART_CFG) $(TIMN_SIG) 0
 
-mrvl_flash: ${BUILD_PLAT}/${FIP_NAME} ${DOIMAGETOOL}
-	$(shell truncate -s %128K ${BUILD_PLAT}/bl1.bin)
-	$(shell cat ${BUILD_PLAT}/bl1.bin ${BUILD_PLAT}/${FIP_NAME} > ${BUILD_PLAT}/${BOOT_IMAGE})
-	$(shell truncate -s %4 ${BUILD_PLAT}/${BOOT_IMAGE})
-	$(if $(value MV_DDR_PATH),,$(error "Platform '${PLAT}' for target '$@' requires MV_DDR_PATH. Please set MV_DDR_PATH to point to the right directory"))
-	${Q}${MAKE} --no-print-directory -C ${DOIMAGEPATH} WTMI_IMG=$(WTMI_IMG) MV_DDR_PATH=$(MV_DDR_PATH)
-	$(shell truncate -s %4 $(WTMI_IMG))
-	@echo
-	@echo "Building uart images"
-	$(TIMBUILD) $(TIMBLDUARTARGS)
-	@sed -i 's|WTMI_IMG|$(WTMI_MULTI_IMG)|1' $(DOIMAGE_CFG)
-	@sed -i 's|BOOT_IMAGE|$(BUILD_PLAT)/$(BOOT_IMAGE)|1' $(DOIMAGE_CFG)
+UART_IMAGES		:= $(BUILD_UART)/$(TIM_UART_IMAGE)
 ifeq ($(MARVELL_SECURE_BOOT),1)
-	@sed -i 's|WTMI_IMG|$(WTMI_MULTI_IMG)|1' $(TIMNCFG)
-	@sed -i 's|BOOT_IMAGE|$(BUILD_PLAT)/$(BOOT_IMAGE)|1' $(TIMNCFG)
+UART_IMAGES		+= $(BUILD_UART)/$(TIMN_UART_IMAGE)
 endif
-	$(DOIMAGETOOL) $(DOIMAGE_FLAGS)
-	@if [ -e "$(TIMNCFG)" ]; then $(DOIMAGETOOL) -r $(TIMNCFG); fi
-	@rm -rf $(BUILD_PLAT)/$(BUILD_UART)*
-	@mkdir $(BUILD_PLAT)/$(BUILD_UART)
-	@mv -t $(BUILD_PLAT)/$(BUILD_UART) $(TIM_IMAGE) $(DOIMAGE_CFG) $(TIMN_IMAGE) $(TIMNCFG)
-	@find . -name "*_h.*" |xargs cp -ut $(BUILD_PLAT)/$(BUILD_UART)
-	@mv $(subst .bin,_h.bin,$(WTMI_MULTI_IMG)) $(BUILD_PLAT)/$(BUILD_UART)/wtmi_h.bin
-	@tar czf $(BUILD_PLAT)/$(BUILD_UART).tgz.bin -C $(BUILD_PLAT) ./$(BUILD_UART)
-	@echo
-	@echo "Building flash image"
-	$(TIMBUILD) $(TIMBLDARGS)
-	sed -i 's|WTMI_IMG|$(WTMI_MULTI_IMG)|1' $(DOIMAGE_CFG)
-	sed -i 's|BOOT_IMAGE|$(BUILD_PLAT)/$(BOOT_IMAGE)|1' $(DOIMAGE_CFG)
+UART_IMAGES		+= $(BUILD_UART)/wtmi_h.bin $(BUILD_UART)/boot-image_h.bin
+
+CRYPTOPP_LIBDIR		?= $(CRYPTOPP_PATH)
+CRYPTOPP_INCDIR		?= $(CRYPTOPP_PATH)
+
+$(TBB): FORCE
+#	Do not remove! Following checks are required to ensure correct TF-A builds, removing these checks leads to broken TF-A builds
+	$(if $(CRYPTOPP_LIBDIR),,$(error "Platform '$(PLAT)' for WTP image tool requires CRYPTOPP_PATH or CRYPTOPP_LIBDIR. Please set CRYPTOPP_PATH or CRYPTOPP_LIBDIR to point to the right directory"))
+	$(if $(CRYPTOPP_INCDIR),,$(error "Platform '$(PLAT)' for WTP image tool requires CRYPTOPP_PATH or CRYPTOPP_INCDIR. Please set CRYPTOPP_PATH or CRYPTOPP_INCDIR to point to the right directory"))
+	$(if $(wildcard $(CRYPTOPP_LIBDIR)/*),,$(error "Either 'CRYPTOPP_PATH' or 'CRYPTOPP_LIB' was set to '$(CRYPTOPP_LIBDIR)', but '$(CRYPTOPP_LIBDIR)' does not exist"))
+	$(if $(wildcard $(CRYPTOPP_INCDIR)/*),,$(error "Either 'CRYPTOPP_PATH' or 'CRYPTOPP_INCDIR' was set to '$(CRYPTOPP_INCDIR)', but '$(CRYPTOPP_INCDIR)' does not exist"))
+ifdef CRYPTOPP_PATH
+	$(Q)$(MAKE) --no-print-directory -C $(CRYPTOPP_PATH) -f GNUmakefile
+endif
+	$(Q)$(MAKE) --no-print-directory -C $(WTP)/wtptp/src/TBB_Linux -f TBB_linux.mak LIBDIR=$(CRYPTOPP_LIBDIR) INCDIR=$(CRYPTOPP_INCDIR)
+
+$(WTMI_MULTI_IMG): FORCE
+	$(Q)$(MAKE) --no-print-directory -C $(WTP) WTMI_IMG=$(WTMI_IMG) DDR_TOPOLOGY=$(DDR_TOPOLOGY) CLOCKSPRESET=$(CLOCKSPRESET) WTMI
+
+$(BUILD_PLAT)/wtmi.bin: $(WTMI_MULTI_IMG)
+	$(Q)cp -a $(WTMI_MULTI_IMG) $(BUILD_PLAT)/wtmi.bin
+
+$(TIMDDRTOOL): FORCE
+#	Do not remove! Following checks are required to ensure correct TF-A builds, removing these checks leads to broken TF-A builds
+	$(if $(value MV_DDR_PATH),,$(error "Platform '${PLAT}' for ddr tool requires MV_DDR_PATH. Please set MV_DDR_PATH to point to the right directory"))
+	$(if $(wildcard $(value MV_DDR_PATH)/*),,$(error "'MV_DDR_PATH=$(value MV_DDR_PATH)' was specified, but '$(value MV_DDR_PATH)' directory does not exist"))
+	$(if $(shell git -C $(value MV_DDR_PATH) rev-parse --show-cdup 2>&1),$(error "'MV_DDR_PATH=$(value MV_DDR_PATH)' was specified, but '$(value MV_DDR_PATH)' does not contain valid mv-ddr-marvell git repository"))
+	$(Q)$(MAKE) --no-print-directory -C $(WTP) MV_DDR_PATH=$(MV_DDR_PATH) DDR_TOPOLOGY=$(DDR_TOPOLOGY) mv_ddr
+
+$(BUILD_PLAT)/$(UART_IMAGE): $(BUILD_PLAT)/$(BOOT_IMAGE) $(BUILD_PLAT)/wtmi.bin $(TBB) $(TIMBUILD) $(TIMDDRTOOL)
+	@$(ECHO_BLANK_LINE)
+	@echo "Building uart images"
+	$(Q)mkdir -p $(BUILD_PLAT)/$(BUILD_UART)
+	$(Q)cp -a $(BUILD_PLAT)/wtmi.bin $(BUILD_PLAT)/$(BUILD_UART)/wtmi.bin
+	$(Q)cp -a $(BUILD_PLAT)/$(BOOT_IMAGE) $(BUILD_PLAT)/$(BUILD_UART)/$(BOOT_IMAGE)
+	$(Q)cd $(BUILD_PLAT)/$(BUILD_UART) && $(TIMBUILD) $(TIMBLDUARTARGS)
+	$(Q)sed -i 's|WTMI_IMG|wtmi.bin|1' $(TIM_UART_CFG)
+	$(Q)sed -i 's|BOOT_IMAGE|$(BOOT_IMAGE)|1' $(TIM_UART_CFG)
 ifeq ($(MARVELL_SECURE_BOOT),1)
-	@sed -i 's|WTMI_IMG|$(WTMI_MULTI_IMG)|1' $(TIMNCFG)
-	@sed -i 's|BOOT_IMAGE|$(BUILD_PLAT)/$(BOOT_IMAGE)|1' $(TIMNCFG)
-	@echo -e "\n\t=======================================================\n";
-	@echo -e "\t  Secure boot. Encrypting wtmi and boot-image \n";
-	@echo -e "\t=======================================================\n";
-	@truncate -s %16 $(WTMI_MULTI_IMG)
-	@openssl enc -aes-256-cbc -e -in $(WTMI_MULTI_IMG) \
-	-out $(WTMI_ENC_IMG) \
+	$(Q)sed -i 's|WTMI_IMG|wtmi.bin|1' $(TIMN_UART_CFG)
+	$(Q)sed -i 's|BOOT_IMAGE|$(BOOT_IMAGE)|1' $(TIMN_UART_CFG)
+endif
+	$(Q)cd $(BUILD_PLAT)/$(BUILD_UART) && $(TBB) -r $(TIM_UART_CFG) -v -D
+ifeq ($(MARVELL_SECURE_BOOT),1)
+	$(Q)cd $(BUILD_PLAT)/$(BUILD_UART) && $(TBB) -r $(TIMN_UART_CFG)
+endif
+	$(Q)tar czf $(BUILD_PLAT)/$(UART_IMAGE) -C $(BUILD_PLAT) $(UART_IMAGES)
+	@$(ECHO_BLANK_LINE)
+	@echo "Built $@ successfully"
+	@$(ECHO_BLANK_LINE)
+
+$(BUILD_PLAT)/$(FLASH_IMAGE): $(BUILD_PLAT)/$(BOOT_IMAGE) $(BUILD_PLAT)/wtmi.bin $(TBB) $(TIMBUILD) $(TIMDDRTOOL) $(TIM2IMG)
+	@$(ECHO_BLANK_LINE)
+	@echo "Building flash image"
+	$(Q)cd $(BUILD_PLAT) && $(TIMBUILD) $(TIMBLDARGS)
+	$(Q)sed -i 's|WTMI_IMG|wtmi.bin|1' $(TIM_CFG)
+	$(Q)sed -i 's|BOOT_IMAGE|$(BOOT_IMAGE)|1' $(TIM_CFG)
+ifeq ($(MARVELL_SECURE_BOOT),1)
+	$(Q)sed -i 's|WTMI_IMG|wtmi.bin|1' $(TIMN_CFG)
+	$(Q)sed -i 's|BOOT_IMAGE|$(BOOT_IMAGE)|1' $(TIMN_CFG)
+	@$(ECHO_BLANK_LINE)
+	@echo "=======================================================";
+	@echo "  Secure boot. Encrypting wtmi and boot-image";
+	@echo "=======================================================";
+	@$(ECHO_BLANK_LINE)
+	$(Q)cp $(BUILD_PLAT)/wtmi.bin $(BUILD_PLAT)/wtmi-align.bin
+	$(Q)truncate -s %16 $(BUILD_PLAT)/wtmi-align.bin
+	$(Q)openssl enc -aes-256-cbc -e -in $(BUILD_PLAT)/wtmi-align.bin \
+	-out $(BUILD_PLAT)/$(WTMI_ENC_IMG) \
 	-K `cat $(IMAGESPATH)/aes-256.txt` -nosalt \
 	-iv `cat $(IMAGESPATH)/iv.txt` -p
-	@truncate -s %16 $(BUILD_PLAT)/$(BOOT_IMAGE);
-	@openssl enc -aes-256-cbc -e -in $(BUILD_PLAT)/$(BOOT_IMAGE) \
+	$(Q)truncate -s %16 $(BUILD_PLAT)/$(BOOT_IMAGE);
+	$(Q)openssl enc -aes-256-cbc -e -in $(BUILD_PLAT)/$(BOOT_IMAGE) \
 	-out $(BUILD_PLAT)/$(BOOT_ENC_IMAGE) \
 	-K `cat $(IMAGESPATH)/aes-256.txt` -nosalt \
 	-iv `cat $(IMAGESPATH)/iv.txt` -p
 endif
-	$(DOIMAGETOOL) $(DOIMAGE_FLAGS)
-	@if [ -e "$(TIMNCFG)" ]; then $(DOIMAGETOOL) -r $(TIMNCFG); fi
-	@if [ "$(MARVELL_SECURE_BOOT)" = "1" ]; then sed -i 's|$(WTMI_MULTI_IMG)|$(WTMI_ENC_IMG)|1;s|$(BOOT_IMAGE)|$(BOOT_ENC_IMAGE)|1;' $(TIMNCFG); fi
-	$(TIM2IMG) $(TIM2IMGARGS) -o $(BUILD_PLAT)/$(FLASH_IMAGE)
-	@mv -t $(BUILD_PLAT) $(TIM_IMAGE) $(DOIMAGE_CFG) $(TIMN_IMAGE) $(TIMNCFG) $(WTMI_IMG) $(WTMI_SYSINIT_IMG) $(WTMI_MULTI_IMG)
-	@if [ "$(MARVELL_SECURE_BOOT)" = "1" ]; then mv -t $(BUILD_PLAT) $(WTMI_ENC_IMG) OtpHash.txt; fi
-	@find . -name "*.txt" | grep -E "CSK[[:alnum:]]_KeyHash.txt|Tim_msg.txt|TIMHash.txt" | xargs rm -f
+	$(Q)cd $(BUILD_PLAT) && $(TBB) -r $(TIM_CFG) -v -D
+ifeq ($(MARVELL_SECURE_BOOT),1)
+	$(Q)cd $(BUILD_PLAT) && $(TBB) -r $(TIMN_CFG)
+	$(Q)sed -i 's|wtmi.bin|$(WTMI_ENC_IMG)|1' $(TIMN_CFG)
+	$(Q)sed -i 's|$(BOOT_IMAGE)|$(BOOT_ENC_IMAGE)|1' $(TIMN_CFG)
+endif
+	$(Q)cd $(BUILD_PLAT) && $(TIM2IMG) $(TIM2IMGARGS) -o $(BUILD_PLAT)/$(FLASH_IMAGE)
+	@$(ECHO_BLANK_LINE)
+	@echo "Built $@ successfully"
+	@$(ECHO_BLANK_LINE)
 
-else # ${WTP}
+clean realclean distclean: mrvl_clean
 
-mrvl_flash:
+.PHONY: mrvl_clean
+mrvl_clean:
+	-$(Q)$(MAKE) --no-print-directory -C $(WTP) MV_DDR_PATH=$(MV_DDR_PATH) clean
+	-$(Q)$(MAKE) --no-print-directory -C $(WTP)/wtptp/src/TBB_Linux -f TBB_linux.mak clean
+ifdef CRYPTOPP_PATH
+	-$(Q)$(MAKE) --no-print-directory -C $(CRYPTOPP_PATH) -f GNUmakefile clean
+endif
+
+else # WTP
+
+$(BUILD_PLAT)/$(UART_IMAGE) $(BUILD_PLAT)/$(FLASH_IMAGE):
 	$(error "Platform '${PLAT}' for target '$@' requires WTP. Please set WTP to point to the right directory")
 
-endif # ${WTP}
+endif # WTP
+
+.PHONY: mrvl_uart
+mrvl_uart: $(BUILD_PLAT)/$(UART_IMAGE)
diff --git a/plat/marvell/armada/a3k/common/a3700_ea.c b/plat/marvell/armada/a3k/common/a3700_ea.c
index dd46beb..bc12845 100644
--- a/plat/marvell/armada/a3k/common/a3700_ea.c
+++ b/plat/marvell/armada/a3k/common/a3700_ea.c
@@ -4,20 +4,87 @@
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
  */
+
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <common/bl_common.h>
 #include <common/debug.h>
 #include <arch_helpers.h>
+#include <plat/common/platform.h>
+#include <bl31/ea_handle.h>
 
-#define ADVK_SERROR_SYNDROME 0xbf000002
+#define A53_SERR_INT_AXI_SLVERR_ON_EXTERNAL_ACCESS 0xbf000002
 
+#if !ENABLE_BACKTRACE
+static const char *get_el_str(unsigned int el)
+{
+	if (el == MODE_EL3) {
+		return "EL3";
+	} else if (el == MODE_EL2) {
+		return "EL2";
+	}
+	return "S-EL1";
+}
+#endif /* !ENABLE_BACKTRACE */
+
+/*
+ * This source file with custom plat_ea_handler function is compiled only when
+ * building TF-A with compile option HANDLE_EA_EL3_FIRST=1
+ */
 void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
 		void *handle, uint64_t flags)
 {
-	if (syndrome != ADVK_SERROR_SYNDROME) {
-		ERROR("Unhandled External Abort received on 0x%lx at EL3!\n",
-			read_mpidr_el1());
-		ERROR(" exception reason=%u syndrome=0x%llx\n", ea_reason,
-				syndrome);
-		panic();
+	unsigned int level = (unsigned int)GET_EL(read_spsr_el3());
+
+	/*
+	 * Asynchronous External Abort with syndrome 0xbf000002 on Cortex A53
+	 * core means SError interrupt caused by AXI SLVERR on external access.
+	 *
+	 * In most cases this indicates a bug in U-Boot or Linux kernel driver
+	 * pci-aardvark.c which implements access to A3700 PCIe config space.
+	 * Driver does not wait for PCIe PIO transfer completion and try to
+	 * start a new PCIe PIO transfer while previous has not finished yet.
+	 * A3700 PCIe controller in this case sends SLVERR via AXI which results
+	 * in a fatal Asynchronous SError interrupt on Cortex A53 CPU.
+	 *
+	 * Following patches fix that bug in U-Boot and Linux kernel drivers:
+	 * https://source.denx.de/u-boot/u-boot/-/commit/eccbd4ad8e4e182638eafbfb87ac139c04f24a01
+	 * https://git.kernel.org/stable/c/f18139966d072dab8e4398c95ce955a9742e04f7
+	 *
+	 * As a hacky workaround for unpatched U-Boot and Linux kernel drivers
+	 * ignore all asynchronous aborts with that syndrome value received on
+	 * CPU from level lower than EL3.
+	 *
+	 * Because these aborts are delivered on CPU asynchronously, they are
+	 * imprecise and we cannot check the real reason of abort and neither
+	 * who and why sent this abort. We expect that on A3700 it is always
+	 * PCIe controller.
+	 *
+	 * Hence ignoring all aborts with this syndrome value is just a giant
+	 * hack that we need only because of bugs in old U-Boot and Linux kernel
+	 * versions and because it was decided that TF-A would implement this
+	 * hack for U-Boot and Linux kernel it in this way. New patched U-Boot
+	 * and kernel versions do not need it anymore.
+	 *
+	 * Links to discussion about this workaround:
+	 * https://lore.kernel.org/linux-pci/20190316161243.29517-1-repk@triplefau.lt/
+	 * https://lore.kernel.org/linux-pci/971be151d24312cc533989a64bd454b4@www.loen.fr/
+	 * https://review.trustedfirmware.org/c/TF-A/trusted-firmware-a/+/1541
+	 */
+	if (level < MODE_EL3 && ea_reason == ERROR_EA_ASYNC &&
+	    syndrome == A53_SERR_INT_AXI_SLVERR_ON_EXTERNAL_ACCESS) {
+		ERROR_NL();
+		ERROR("Ignoring Asynchronous External Abort with"
+		     " syndrome 0x%" PRIx64 " received on 0x%lx from %s\n",
+		     syndrome, read_mpidr_el1(), get_el_str(level));
+		ERROR("SError interrupt: AXI SLVERR on external access\n");
+		ERROR("This indicates a bug in pci-aardvark.c driver\n");
+		ERROR("Please update U-Boot/Linux to the latest version\n");
+		ERROR_NL();
+		console_flush();
+		return;
 	}
+
+	plat_default_ea_handler(ea_reason, syndrome, cookie, handle, flags);
 }
diff --git a/plat/marvell/armada/a3k/common/aarch64/a3700_clock.S b/plat/marvell/armada/a3k/common/aarch64/a3700_clock.S
new file mode 100644
index 0000000..f79516f
--- /dev/null
+++ b/plat/marvell/armada/a3k/common/aarch64/a3700_clock.S
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2018 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:	BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <asm_macros.S>
+#include <platform_def.h>
+
+/*
+ * Below address in used only for reading, therefore no problem with concurrent
+ * Linux access.
+ */
+#define MVEBU_TEST_PIN_LATCH_N (MVEBU_NB_GPIO_REG_BASE + 0x8)
+ #define MVEBU_XTAL_MODE_MASK		BIT(9)
+
+	/* -----------------------------------------------------
+	 * uint32_t get_ref_clk (void);
+	 *
+	 * returns reference clock in MHz (25 or 40)
+	 * -----------------------------------------------------
+	 */
+.globl	get_ref_clk
+func get_ref_clk
+	mov_imm	x0, MVEBU_TEST_PIN_LATCH_N
+	ldr	w0, [x0]
+	tst	w0, #MVEBU_XTAL_MODE_MASK
+	bne	40
+	mov	w0, #25
+	ret
+40:
+	mov	w0, #40
+	ret
+endfunc get_ref_clk
diff --git a/plat/marvell/armada/a3k/common/cm3_system_reset.c b/plat/marvell/armada/a3k/common/cm3_system_reset.c
new file mode 100644
index 0000000..548ff51
--- /dev/null
+++ b/plat/marvell/armada/a3k/common/cm3_system_reset.c
@@ -0,0 +1,62 @@
+/*
+ * Copyright (C) 2020 Marek Behun, CZ.NIC
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <stdbool.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include <mvebu_def.h>
+
+/* Cortex-M3 Secure Processor Mailbox Registers */
+#define MVEBU_RWTM_PARAM0_REG			(MVEBU_RWTM_REG_BASE)
+#define MVEBU_RWTM_CMD_REG			(MVEBU_RWTM_REG_BASE + 0x40)
+#define MVEBU_RWTM_HOST_INT_RESET_REG		(MVEBU_RWTM_REG_BASE + 0xC8)
+#define MVEBU_RWTM_HOST_INT_MASK_REG		(MVEBU_RWTM_REG_BASE + 0xCC)
+#define MVEBU_RWTM_HOST_INT_SP_COMPLETE		BIT(0)
+
+#define MVEBU_RWTM_REBOOT_CMD		0x0009
+#define MVEBU_RWTM_REBOOT_MAGIC		0xDEADBEEF
+
+static inline bool rwtm_completed(void)
+{
+	return (mmio_read_32(MVEBU_RWTM_HOST_INT_RESET_REG) &
+		MVEBU_RWTM_HOST_INT_SP_COMPLETE) != 0;
+}
+
+static bool rwtm_wait(int ms)
+{
+	while (ms && !rwtm_completed()) {
+		mdelay(1);
+		--ms;
+	}
+
+	return rwtm_completed();
+}
+
+void cm3_system_reset(void)
+{
+	int tries = 5;
+
+	for (; tries > 0; --tries) {
+		mmio_clrbits_32(MVEBU_RWTM_HOST_INT_RESET_REG,
+				MVEBU_RWTM_HOST_INT_SP_COMPLETE);
+
+		mmio_write_32(MVEBU_RWTM_PARAM0_REG, MVEBU_RWTM_REBOOT_MAGIC);
+		mmio_write_32(MVEBU_RWTM_CMD_REG, MVEBU_RWTM_REBOOT_CMD);
+
+		if (rwtm_wait(10)) {
+			break;
+		}
+
+		mdelay(100);
+	}
+
+	/* If we reach here, the command is not implemented. */
+	ERROR("System reset command not implemented in WTMI firmware!\n");
+}
diff --git a/plat/marvell/armada/a3k/common/dram_win.c b/plat/marvell/armada/a3k/common/dram_win.c
index 694f6d4..e89f295 100644
--- a/plat/marvell/armada/a3k/common/dram_win.c
+++ b/plat/marvell/armada/a3k/common/dram_win.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 Marvell International Ltd.
+ * Copyright (C) 2018-2021 Marvell International Ltd.
  *
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
@@ -92,33 +92,35 @@
 	},
 
 	/*
-	 * If total dram size is more than 2GB, now there is only one case - 4GB
-	 *  dram; we will use below cpu windows configurations:
-	 *  - Internal Regs, CCI-400, Boot Rom and PCIe windows are kept as
-	 *    default;
-	 *  - Use 4 CPU decode windows for DRAM, which cover 3.375GB DRAM;
-	 *    DDR window 0 is configured in tim header with 2GB size, no need to
-	 *    configure it again here;
+	 * If total DRAM size is more than 2GB, now there is only one case:
+	 * 4GB of DRAM; to better utilize address space (for maximization of
+	 * DRAM usage), we will use the configuration of CPU windows below:
+	 *  - Internal Regs and Boot ROM windows are kept as default;
+	 *  - CCI-400 is moved from its default address to another address
+	 *    (this is actually done even if DRAM size is not more than 2 GB,
+	 *     because the firmware is compiled with that address as a
+	 *     constant);
+	 *  - PCIe window is moved to another address;
+	 *  - Use 4 CPU decode windows for DRAM, which cover 3.75GB DRAM;
+	 *    DDR window 0 is configured in tim header with 2G B size, no need
+	 *    to configure it again here;
 	 *
-	 *	0xFFFFFFFF ---> |-----------------------|
-	 *			|	  Boot ROM	| 64KB
+	 *	0xFFFFFFFF ---> +-----------------------+
+	 *			|	 Boot ROM	| 64 KB
 	 *	0xFFF00000 ---> +-----------------------+
 	 *			:			:
-	 *	0xF0000000 ---> |-----------------------|
-	 *			|	  PCIE		| 128 MB
-	 *	0xE8000000 ---> |-----------------------|
-	 *			|	  DDR window 3	| 128 MB
-	 *	0xE0000000 ---> +-----------------------+
+	 *	0xFE010000 ---> +-----------------------+
+	 *			|	 CCI Regs	| 64 KB
+	 *	0xFE000000 ---> +-----------------------+
 	 *			:			:
-	 *	0xD8010000 ---> |-----------------------|
-	 *			|	  CCI Regs	| 64 KB
-	 *	0xD8000000 ---> +-----------------------+
-	 *			:			:
-	 *			:			:
+	 *	0xFA000000 ---> +-----------------------+
+	 *			|	 PCIE		| 128 MB
+	 *	0xF2000000 ---> +-----------------------+
+	 *			|	 DDR window 3	| 512 MB
 	 *	0xD2000000 ---> +-----------------------+
-	 *			|	 Internal Regs	| 32MB
+	 *			|	 Internal Regs	| 32 MB
 	 *	0xD0000000 ---> |-----------------------|
-	 *			 |	  DDR window 2	| 256 MB
+	 *			|	 DDR window 2	| 256 MB
 	 *	0xC0000000 ---> |-----------------------|
 	 *			|			|
 	 *			|	 DDR window 1	| 1 GB
@@ -155,14 +157,14 @@
 						0xc0000000},
 		{CPU_WIN_ENABLED,
 			CPU_WIN_TARGET_DRAM,
-				0xe0000000,
-					0x08000000,
-						0xe0000000},
+				0xd2000000,
+					0x20000000,
+						0xd2000000},
 		{CPU_WIN_ENABLED,
 			CPU_WIN_TARGET_PCIE,
-				0xe8000000,
+				0xf2000000,
 					0x08000000,
-						0xe8000000},
+						0xf2000000},
 	},
 };
 
diff --git a/plat/marvell/armada/a3k/common/include/a3700_plat_def.h b/plat/marvell/armada/a3k/common/include/a3700_plat_def.h
index c7f40ad..83d9561 100644
--- a/plat/marvell/armada/a3k/common/include/a3700_plat_def.h
+++ b/plat/marvell/armada/a3k/common/include/a3700_plat_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 Marvell International Ltd.
+ * Copyright (C) 2018-2021 Marvell International Ltd.
  *
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
@@ -41,8 +41,14 @@
 #define MVEBU_GICR_BASE			0x1D40000
 #define MVEBU_GICC_BASE			0x1D80000
 
-/* CCI-400 */
-#define MVEBU_CCI_BASE			0x8000000
+/*
+ * CCI-400 base address
+ * This address is absolute, not relative to MVEBU_REGS_BASE.
+ * This is not the default CCI base address (that would be 0xD8000000).
+ * Rather we remap CCI to this address to better utilize the address space.
+ * (The remapping is done in plat/marvell/armada/a3k/common/plat_cci.c)
+ */
+#define MVEBU_CCI_BASE			0xFE000000
 
 /*****************************************************************************
  * North and south bridge register base
@@ -119,4 +125,10 @@
  */
 #define MVEBU_COMPHY_REG_BASE			(MVEBU_REGS_BASE + 0x18300)
 
+/*****************************************************************************
+ * Cortex-M3 Secure Processor Mailbox constants
+ *****************************************************************************
+ */
+#define MVEBU_RWTM_REG_BASE			(MVEBU_REGS_BASE + 0xB0000)
+
 #endif /* A3700_PLAT_DEF_H */
diff --git a/plat/marvell/armada/a3k/common/include/a3700_pm.h b/plat/marvell/armada/a3k/common/include/a3700_pm.h
index cc6cf43..44dbb9f 100644
--- a/plat/marvell/armada/a3k/common/include/a3700_pm.h
+++ b/plat/marvell/armada/a3k/common/include/a3700_pm.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2016 Marvell International Ltd.
+ * Copyright (C) 2016-2020 Marvell International Ltd.
  *
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
@@ -48,4 +48,6 @@
 
 struct pm_wake_up_src_config *mv_wake_up_src_config_get(void);
 
+void cm3_system_reset(void);
+
 #endif /* A3700_PM_H */
diff --git a/plat/marvell/armada/a3k/common/include/platform_def.h b/plat/marvell/armada/a3k/common/include/platform_def.h
index 3d839f8..f19d96b 100644
--- a/plat/marvell/armada/a3k/common/include/platform_def.h
+++ b/plat/marvell/armada/a3k/common/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2016-2019 Marvell International Ltd.
+ * Copyright (C) 2016-2021 Marvell International Ltd.
  *
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
@@ -148,7 +148,7 @@
 #define PLAT_MARVELL_SHARED_RAM_CACHED		1
 
 /* CCI related constants */
-#define PLAT_MARVELL_CCI_BASE		(MVEBU_REGS_BASE + MVEBU_CCI_BASE)
+#define PLAT_MARVELL_CCI_BASE			MVEBU_CCI_BASE
 #define PLAT_MARVELL_CCI_CLUSTER0_SL_IFACE_IX	3
 #define PLAT_MARVELL_CCI_CLUSTER1_SL_IFACE_IX	4
 
@@ -163,14 +163,7 @@
 /*
  * PL011 related constants
  */
-#define PLAT_MARVELL_BOOT_UART_BASE		(MVEBU_REGS_BASE + 0x12000)
-#define PLAT_MARVELL_BOOT_UART_CLK_IN_HZ	25804800
-
-#define PLAT_MARVELL_CRASH_UART_BASE		PLAT_MARVELL_BOOT_UART_BASE
-#define PLAT_MARVELL_CRASH_UART_CLK_IN_HZ	PLAT_MARVELL_BOOT_UART_CLK_IN_HZ
-
-#define PLAT_MARVELL_BL31_RUN_UART_BASE		PLAT_MARVELL_BOOT_UART_BASE
-#define PLAT_MARVELL_BL31_RUN_UART_CLK_IN_HZ	PLAT_MARVELL_BOOT_UART_CLK_IN_HZ
+#define PLAT_MARVELL_UART_BASE			(MVEBU_REGS_BASE + 0x12000)
 
 /* Required platform porting definitions */
 #define PLAT_MAX_PWR_LVL			MPIDR_AFFLVL1
@@ -227,6 +220,8 @@
 #define CPU_DEC_RLR_REMAP_LOW_MASK		\
 			(0xffff <<  CPU_DEC_BR_BASE_OFFS)
 
+#define CPU_DEC_CCI_BASE_REG		(MVEBU_CPU_DEC_WIN_REG_BASE + 0xe0)
+
 /* Securities */
 #define IRQ_SEC_OS_TICK_INT	MARVELL_IRQ_SEC_PHY_TIMER
 
diff --git a/plat/marvell/armada/a3k/common/io_addr_dec.c b/plat/marvell/armada/a3k/common/io_addr_dec.c
index b27633c..fea7f81 100644
--- a/plat/marvell/armada/a3k/common/io_addr_dec.c
+++ b/plat/marvell/armada/a3k/common/io_addr_dec.c
@@ -67,17 +67,14 @@
 	mmio_write_32(MVEBU_DEC_WIN_CTRL_REG(dec_win->dec_reg_base,
 		      win_id, dec_win->win_offset), ctrl);
 
-	INFO("set_io_addr_dec %d result: ctrl(0x%x) base(0x%x)",
+	INFO("set_io_addr_dec %d result: ctrl(0x%x) base(0x%x) remap(0x%x)\n",
 	     win_id, mmio_read_32(MVEBU_DEC_WIN_CTRL_REG(dec_win->dec_reg_base,
 	     win_id, dec_win->win_offset)),
 	     mmio_read_32(MVEBU_DEC_WIN_BASE_REG(dec_win->dec_reg_base,
-			  win_id, dec_win->win_offset)));
-	if (win_id < dec_win->max_remap)
-		INFO(" remap(%x)\n",
-		     mmio_read_32(MVEBU_DEC_WIN_REMAP_REG(dec_win->dec_reg_base,
-		     win_id, dec_win->win_offset)));
-	else
-		INFO("\n");
+			  win_id, dec_win->win_offset)),
+	     (win_id < dec_win->max_remap) ?
+		mmio_read_32(MVEBU_DEC_WIN_REMAP_REG(dec_win->dec_reg_base,
+			     win_id, dec_win->win_offset)) : 0);
 }
 
 /* Set io decode window */
@@ -167,12 +164,11 @@
 			ERROR("Failed to set IO address decode\n");
 			return -1;
 		}
-		INFO("Set IO decode window successfully, base(0x%x)",
-		     io_dec_win->dec_reg_base);
-		INFO(" win_attr(%x) max_dram_win(%d) max_remap(%d)",
+		INFO("Set IO decode window successfully, base(0x%x)"
+		     " win_attr(%x) max_dram_win(%d) max_remap(%d)"
+		     " win_offset(%d)\n", io_dec_win->dec_reg_base,
 		     io_dec_win->win_attr, io_dec_win->max_dram_win,
-		     io_dec_win->max_remap);
-		INFO(" win_offset(%d)\n", io_dec_win->win_offset);
+		     io_dec_win->max_remap, io_dec_win->win_offset);
 	}
 
 	return 0;
diff --git a/plat/marvell/armada/a3k/common/plat_cci.c b/plat/marvell/armada/a3k/common/plat_cci.c
new file mode 100644
index 0000000..56f091f
--- /dev/null
+++ b/plat/marvell/armada/a3k/common/plat_cci.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2021 Marek Behun <marek.behun@nic.cz>
+ *
+ * Based on plat/marvell/armada/common/marvell_cci.c
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <drivers/arm/cci.h>
+#include <lib/mmio.h>
+
+#include <plat_marvell.h>
+
+static const int cci_map[] = {
+	PLAT_MARVELL_CCI_CLUSTER0_SL_IFACE_IX,
+	PLAT_MARVELL_CCI_CLUSTER1_SL_IFACE_IX
+};
+
+/*
+ * This redefines the weak definition in
+ * plat/marvell/armada/common/marvell_cci.c
+ */
+void plat_marvell_interconnect_init(void)
+{
+	/*
+	 * To better utilize the address space, we remap CCI base address from
+	 * the default (0xD8000000) to MVEBU_CCI_BASE.
+	 * This has to be done here, rather than in cpu_wins_init(), because
+	 * cpu_wins_init() is called later.
+	 */
+	mmio_write_32(CPU_DEC_CCI_BASE_REG, MVEBU_CCI_BASE >> 20);
+
+	cci_init(PLAT_MARVELL_CCI_BASE, cci_map, ARRAY_SIZE(cci_map));
+}
diff --git a/plat/marvell/armada/a3k/common/plat_pm.c b/plat/marvell/armada/a3k/common/plat_pm.c
index f8ce6fe..e2d15ab 100644
--- a/plat/marvell/armada/a3k/common/plat_pm.c
+++ b/plat/marvell/armada/a3k/common/plat_pm.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 Marvell International Ltd.
+ * Copyright (C) 2018-2020 Marvell International Ltd.
  *
  * SPDX-License-Identifier:	BSD-3-Clause
  * https://spdx.org/licenses
@@ -590,6 +590,13 @@
 	return NULL;
 }
 
+#pragma weak mv_wake_up_src_config_get
+struct pm_wake_up_src_config *mv_wake_up_src_config_get(void)
+{
+	static struct pm_wake_up_src_config wake_up_src_cfg = {};
+	return &wake_up_src_cfg;
+}
+
 static void a3700_set_wake_up_source(void)
 {
 	struct pm_wake_up_src_config *wake_up_src;
@@ -763,6 +770,11 @@
 	panic();
 }
 
+#pragma weak cm3_system_reset
+void cm3_system_reset(void)
+{
+}
+
 /*****************************************************************************
  * A3700 handlers to reset the system
  *****************************************************************************
@@ -780,6 +792,9 @@
 			   2 * sizeof(uint64_t));
 #endif
 
+	/* Use Cortex-M3 secure coprocessor for system reset */
+	cm3_system_reset();
+
 	/* Trigger the warm reset */
 	mmio_write_32(MVEBU_WARM_RESET_REG, MVEBU_WARM_RESET_MAGIC);
 
diff --git a/plat/marvell/armada/a8k/a70x0_mochabin/board/dram_port.c b/plat/marvell/armada/a8k/a70x0_mochabin/board/dram_port.c
new file mode 100644
index 0000000..68d335b
--- /dev/null
+++ b/plat/marvell/armada/a8k/a70x0_mochabin/board/dram_port.c
@@ -0,0 +1,227 @@
+/*
+ * Copyright (C) 2021 Sartura Ltd.
+ * Copyright (C) 2021 Globalscale technologies, Inc.
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mv_ddr_if.h>
+#include <plat_marvell.h>
+
+/*
+ * This function may modify the default DRAM parameters
+ * based on information received from SPD or bootloader
+ * configuration located on non volatile storage
+ */
+void plat_marvell_dram_update_topology(void)
+{
+}
+
+/*
+ * This struct provides the DRAM training code with
+ * the appropriate board DRAM configuration
+ */
+#if DDR_TOPOLOGY == 0
+static struct mv_ddr_topology_map board_topology_map_2g = {
+/* 1CS 4Gb x4 devices of Samsung K4A4G085WF */
+	DEBUG_LEVEL_ERROR,
+	0x1, /* active interfaces */
+	/* cs_mask, mirror, dqs_swap, ck_swap X subphys */
+	{ { { {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0} },
+	   SPEED_BIN_DDR_2400R,		/* speed_bin */
+	   MV_DDR_DEV_WIDTH_8BIT,	/* sdram device width */
+	   MV_DDR_DIE_CAP_4GBIT,	/* die capacity */
+	   MV_DDR_FREQ_SAR,		/* frequency */
+	   0, 0,			/* cas_l, cas_wl */
+	   MV_DDR_TEMP_LOW} },		/* temperature */
+	BUS_MASK_32BIT,	/* subphys mask */
+	MV_DDR_CFG_DEFAULT,		/* ddr configuration data source */
+	NOT_COMBINED,			/* ddr twin-die combined*/
+	{ {0} },			/* raw spd data */
+	{0},				/* timing parameters */
+	{				/* electrical configuration */
+		{			/* memory electrical configuration */
+			MV_DDR_RTT_NOM_PARK_RZQ_DISABLE,	/* rtt_nom */
+			{
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV4, /* rtt_park 1cs */
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV1  /* rtt_park 2cs */
+			},
+			{
+				MV_DDR_RTT_WR_DYN_ODT_OFF,	/* rtt_wr 1cs */
+				MV_DDR_RTT_WR_RZQ_DIV2		/* rtt_wr 2cs */
+			},
+			MV_DDR_DIC_RZQ_DIV7	/* dic */
+		},
+		{			/* phy electrical configuration */
+			MV_DDR_OHM_30,	/* data_drv_p */
+			MV_DDR_OHM_30,	/* data_drv_n */
+			MV_DDR_OHM_30,	/* ctrl_drv_p */
+			MV_DDR_OHM_30,	/* ctrl_drv_n */
+			{
+				MV_DDR_OHM_60,	/* odt_p 1cs */
+				MV_DDR_OHM_120	/* odt_p 2cs */
+			},
+			{
+				MV_DDR_OHM_60,	/* odt_n 1cs */
+				MV_DDR_OHM_120	/* odt_n 2cs */
+			},
+		},
+		{			/* mac electrical configuration */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_pattern */
+			MV_DDR_ODT_CFG_ALWAYS_ON,	/* odtcfg_write */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_read */
+		},
+	}
+};
+#endif
+
+#if DDR_TOPOLOGY == 1
+static struct mv_ddr_topology_map board_topology_map_4g = {
+/* 1CS 8Gb x4 devices of Samsung K4A8G085WC-BCTD */
+	DEBUG_LEVEL_ERROR,
+	0x1, /* active interfaces */
+	/* cs_mask, mirror, dqs_swap, ck_swap X subphys */
+	{ { { {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0},
+	      {0x1, 0x2, 0, 0} },
+	   SPEED_BIN_DDR_2400R,		/* speed_bin */
+	   MV_DDR_DEV_WIDTH_8BIT,	/* sdram device width */
+	   MV_DDR_DIE_CAP_8GBIT,	/* die capacity */
+	   MV_DDR_FREQ_SAR,		/* frequency */
+	   0, 0,			/* cas_l, cas_wl */
+	   MV_DDR_TEMP_LOW} },		/* temperature */
+	BUS_MASK_32BIT,	/* subphys mask */
+	MV_DDR_CFG_DEFAULT,		/* ddr configuration data source */
+	NOT_COMBINED,			/* ddr twin-die combined*/
+	{ {0} },			/* raw spd data */
+	{0},				/* timing parameters */
+	{				/* electrical configuration */
+		{			/* memory electrical configuration */
+			MV_DDR_RTT_NOM_PARK_RZQ_DISABLE,	/* rtt_nom */
+			{
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV4, /* rtt_park 1cs */
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV1  /* rtt_park 2cs */
+			},
+			{
+				MV_DDR_RTT_WR_DYN_ODT_OFF,	/* rtt_wr 1cs */
+				MV_DDR_RTT_WR_RZQ_DIV2		/* rtt_wr 2cs */
+			},
+			MV_DDR_DIC_RZQ_DIV7	/* dic */
+		},
+		{			/* phy electrical configuration */
+			MV_DDR_OHM_30,	/* data_drv_p */
+			MV_DDR_OHM_30,	/* data_drv_n */
+			MV_DDR_OHM_30,	/* ctrl_drv_p */
+			MV_DDR_OHM_30,	/* ctrl_drv_n */
+			{
+				MV_DDR_OHM_60,	/* odt_p 1cs */
+				MV_DDR_OHM_120	/* odt_p 2cs */
+			},
+			{
+				MV_DDR_OHM_60,	/* odt_n 1cs */
+				MV_DDR_OHM_120	/* odt_n 2cs */
+			},
+		},
+		{			/* mac electrical configuration */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_pattern */
+			MV_DDR_ODT_CFG_ALWAYS_ON,	/* odtcfg_write */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_read */
+		},
+	}
+};
+#endif
+
+#if DDR_TOPOLOGY == 2
+static struct mv_ddr_topology_map board_topology_map_8g = {
+/* 2CS 8Gb x8 devices of Micron MT40A1G8WE-083E IT */
+	DEBUG_LEVEL_ERROR,
+	0x1, /* active interfaces */
+	/* cs_mask, mirror, dqs_swap, ck_swap X subphys */
+	{ { { {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0},
+	      {0x3, 0x2, 0, 0} },
+	   SPEED_BIN_DDR_2400R,		/* speed_bin */
+	   MV_DDR_DEV_WIDTH_8BIT,	/* sdram device width */
+	   MV_DDR_DIE_CAP_8GBIT,	/* die capacity */
+	   MV_DDR_FREQ_SAR,		/* frequency */
+	   0, 0,			/* cas_l, cas_wl */
+	   MV_DDR_TEMP_LOW} },		/* temperature */
+	BUS_MASK_32BIT,	/* subphys mask */
+	MV_DDR_CFG_DEFAULT,		/* ddr configuration data source */
+	NOT_COMBINED,			/* ddr twin-die combined*/
+	{ {0} },			/* raw spd data */
+	{0},				/* timing parameters */
+	{				/* electrical configuration */
+		{			/* memory electrical configuration */
+			MV_DDR_RTT_NOM_PARK_RZQ_DISABLE,	/* rtt_nom */
+			{
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV4, /* rtt_park 1cs */
+				MV_DDR_RTT_NOM_PARK_RZQ_DIV1  /* rtt_park 2cs */
+			},
+			{
+				MV_DDR_RTT_WR_DYN_ODT_OFF,	/* rtt_wr 1cs */
+				MV_DDR_RTT_WR_RZQ_DIV2		/* rtt_wr 2cs */
+			},
+			MV_DDR_DIC_RZQ_DIV7	/* dic */
+		},
+		{			/* phy electrical configuration */
+			MV_DDR_OHM_30,	/* data_drv_p */
+			MV_DDR_OHM_30,	/* data_drv_n */
+			MV_DDR_OHM_30,	/* ctrl_drv_p */
+			MV_DDR_OHM_30,	/* ctrl_drv_n */
+			{
+				MV_DDR_OHM_60,	/* odt_p 1cs */
+				MV_DDR_OHM_120	/* odt_p 2cs */
+			},
+			{
+				MV_DDR_OHM_60,	/* odt_n 1cs */
+				MV_DDR_OHM_120	/* odt_n 2cs */
+			},
+		},
+		{			/* mac electrical configuration */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_pattern */
+			MV_DDR_ODT_CFG_ALWAYS_ON,	/* odtcfg_write */
+			MV_DDR_ODT_CFG_NORMAL,		/* odtcfg_read */
+		},
+	}
+};
+#endif
+
+struct mv_ddr_topology_map *mv_ddr_topology_map_get(void)
+{
+/* a70x0_mochabin board supports 3 DDR4 models (2G/1CS, 4G/1CS, 8G/2CS) */
+#if DDR_TOPOLOGY == 0
+	return &board_topology_map_2g;
+#elif DDR_TOPOLOGY == 1
+	return &board_topology_map_4g;
+#elif DDR_TOPOLOGY == 2
+	return &board_topology_map_8g;
+#else
+	#error "Unknown DDR topology"
+#endif
+}
diff --git a/plat/marvell/armada/a8k/a70x0_mochabin/board/marvell_plat_config.c b/plat/marvell/armada/a8k/a70x0_mochabin/board/marvell_plat_config.c
new file mode 100644
index 0000000..1ed6323
--- /dev/null
+++ b/plat/marvell/armada/a8k/a70x0_mochabin/board/marvell_plat_config.c
@@ -0,0 +1,145 @@
+/*
+ * Copyright (C) 2021 Sartura Ltd.
+ * Copyright (C) 2021 Globalscale technologies, Inc.
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <armada_common.h>
+
+/*
+ * If bootrom is currently at BLE there's no need to include the memory
+ * maps structure at this point
+ */
+#include <mvebu_def.h>
+#ifndef IMAGE_BLE
+
+/*****************************************************************************
+ * AMB Configuration
+ *****************************************************************************
+ */
+struct addr_map_win amb_memory_map[] = {
+	/* CP0 SPI1 CS0 Direct Mode access */
+	{0xf900,	0x1000000,	AMB_SPI1_CS0_ID},
+};
+
+int marvell_get_amb_memory_map(struct addr_map_win **win,
+			       uint32_t *size, uintptr_t base)
+{
+	*win = amb_memory_map;
+	if (*win == NULL)
+		*size = 0;
+	else
+		*size = ARRAY_SIZE(amb_memory_map);
+
+	return 0;
+}
+#endif
+
+/*****************************************************************************
+ * IO_WIN Configuration
+ *****************************************************************************
+ */
+struct addr_map_win io_win_memory_map[] = {
+#ifndef IMAGE_BLE
+	/* MCI 0 indirect window */
+	{MVEBU_MCI_REG_BASE_REMAP(0),	0x100000, MCI_0_TID},
+	/* MCI 1 indirect window */
+	{MVEBU_MCI_REG_BASE_REMAP(1),	0x100000, MCI_1_TID},
+#endif
+};
+
+uint32_t marvell_get_io_win_gcr_target(int ap_index)
+{
+	return PIDI_TID;
+}
+
+int marvell_get_io_win_memory_map(int ap_index, struct addr_map_win **win,
+				  uint32_t *size)
+{
+	*win = io_win_memory_map;
+	if (*win == NULL)
+		*size = 0;
+	else
+		*size = ARRAY_SIZE(io_win_memory_map);
+
+	return 0;
+}
+
+#ifndef IMAGE_BLE
+/*****************************************************************************
+ * IOB Configuration
+ *****************************************************************************
+ */
+struct addr_map_win iob_memory_map[] = {
+	/* PEX1_X1 window */
+	{0x00000000f7000000,	0x1000000,	PEX1_TID},
+	/* PEX2_X1 window */
+	{0x00000000f8000000,	0x1000000,	PEX2_TID},
+	{0x00000000c0000000,	0x30000000,	PEX2_TID},
+	{0x0000000800000000,	0x100000000,	PEX2_TID},
+	/* PEX0_X4 window */
+	{0x00000000f6000000,	0x1000000,	PEX0_TID},
+	/* SPI1_CS0 (RUNIT) window */
+	{0x00000000f9000000,	0x1000000,	RUNIT_TID},
+};
+
+int marvell_get_iob_memory_map(struct addr_map_win **win, uint32_t *size,
+			       uintptr_t base)
+{
+	*win = iob_memory_map;
+	*size = ARRAY_SIZE(iob_memory_map);
+
+	return 0;
+}
+#endif
+
+/*****************************************************************************
+ * CCU Configuration
+ *****************************************************************************
+ */
+struct addr_map_win ccu_memory_map[] = {	/* IO window */
+#ifdef IMAGE_BLE
+	{0x00000000f2000000,	0x4000000,	IO_0_TID}, /* IO window */
+#else
+#if LLC_SRAM
+	/* This entry is prepared for OP-TEE OS that enables the LLC SRAM
+	 * and changes the window target to SRAM_TID.
+	 */
+	{PLAT_MARVELL_LLC_SRAM_BASE, PLAT_MARVELL_LLC_SRAM_SIZE, DRAM_0_TID},
+#endif
+	{0x00000000f2000000,	0xe000000,	IO_0_TID},
+	{0x00000000c0000000,	0x30000000,	IO_0_TID}, /* IO window */
+	{0x0000000800000000,	0x100000000,	IO_0_TID}, /* IO window */
+#endif
+};
+
+uint32_t marvell_get_ccu_gcr_target(int ap)
+{
+	return DRAM_0_TID;
+}
+
+int marvell_get_ccu_memory_map(int ap_index, struct addr_map_win **win,
+			       uint32_t *size)
+{
+	*win = ccu_memory_map;
+	*size = ARRAY_SIZE(ccu_memory_map);
+
+	return 0;
+}
+
+#ifdef IMAGE_BLE
+/*****************************************************************************
+ * SKIP IMAGE Configuration
+ *****************************************************************************
+ */
+#if PLAT_RECOVERY_IMAGE_ENABLE
+void *plat_marvell_get_skip_image_data(void)
+{
+	/* No recovery button on a70x0_mochabin board */
+	return NULL;
+}
+#endif
+#endif
diff --git a/plat/marvell/armada/a8k/a70x0_mochabin/board/phy-porting-layer.h b/plat/marvell/armada/a8k/a70x0_mochabin/board/phy-porting-layer.h
new file mode 100644
index 0000000..ab76c31
--- /dev/null
+++ b/plat/marvell/armada/a8k/a70x0_mochabin/board/phy-porting-layer.h
@@ -0,0 +1,87 @@
+/*
+ * Copyright (C) 2021 Sartura Ltd.
+ * Copyright (C) 2021 Globalscale technologies, Inc.
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#ifndef __PHY_PORTING_LAYER_H
+#define __PHY_PORTING_LAYER_H
+
+#define MAX_LANE_NR		6
+
+static const struct xfi_params
+	xfi_static_values_tab[AP_NUM][CP_NUM][MAX_LANE_NR] = {
+	/* AP0 */
+	{
+		/* CP 0 */
+		{
+			{ 0 }, /* Comphy0 */
+			{ 0 }, /* Comphy1 */
+			{ 0 }, /* Comphy2 */
+			{ 0 }, /* Comphy3 */
+			{ .g1_ffe_res_sel = 0x3, .g1_ffe_cap_sel = 0xf, .align90 = 0x60,
+			  .g1_dfe_res = 0x1, .g1_amp = 0x1c, .g1_emph = 0xe,
+			  .g1_emph_en = 0x1, .g1_tx_amp_adj = 0x1, .g1_tx_emph_en = 0x1,
+			  .g1_tx_emph = 0x0, .g1_rx_selmuff = 0x1, .g1_rx_selmufi = 0x0,
+			  .g1_rx_selmupf = 0x2, .g1_rx_selmupi = 0x2,
+			  .valid = 1 }, /* Comphy4 */
+			{ 0 }, /* Comphy5 */
+		},
+	},
+};
+
+static const struct sata_params
+	sata_static_values_tab[AP_NUM][CP_NUM][MAX_LANE_NR] = {
+	/* AP0 */
+	{
+		/* CP 0 */
+		{
+			{ 0 }, /* Comphy0 */
+			{ 0 }, /* Comphy1 */
+			{ .g1_amp = 0x8, .g2_amp = 0xa, .g3_amp = 0x1e,
+			  .g1_emph = 0x1, .g2_emph = 0x2, .g3_emph = 0xe,
+			  .g1_emph_en = 0x1, .g2_emph_en = 0x1, .g3_emph_en = 0x1,
+			  .g1_tx_amp_adj = 0x1, .g2_tx_amp_adj = 0x1, .g3_tx_amp_adj = 0x1,
+			  .g1_tx_emph_en = 0x0, .g2_tx_emph_en = 0x0, .g3_tx_emph_en = 0x0,
+			  .g1_tx_emph = 0x1, .g2_tx_emph = 0x1, .g3_tx_emph = 0x1,
+			  .g3_dfe_res = 0x1, .g3_ffe_res_sel = 0x4, .g3_ffe_cap_sel = 0xf,
+			  .align90 = 0x61,
+			  .g1_rx_selmuff = 0x3, .g2_rx_selmuff = 0x3, .g3_rx_selmuff = 0x3,
+			  .g1_rx_selmufi = 0x0, .g2_rx_selmufi = 0x0, .g3_rx_selmufi = 0x3,
+			  .g1_rx_selmupf = 0x1, .g2_rx_selmupf = 0x1, .g3_rx_selmupf = 0x2,
+			  .g1_rx_selmupi = 0x0, .g2_rx_selmupi = 0x0, .g3_rx_selmupi = 0x2,
+			  .polarity_invert = COMPHY_POLARITY_NO_INVERT,
+			  .valid = 0x1
+			}, /* Comphy2 */
+			{ .g1_amp = 0x8, .g2_amp = 0xa, .g3_amp = 0x1e,
+			  .g1_emph = 0x1, .g2_emph = 0x2, .g3_emph = 0xe,
+			  .g1_emph_en = 0x1, .g2_emph_en = 0x1, .g3_emph_en = 0x1,
+			  .g1_tx_amp_adj = 0x1, .g2_tx_amp_adj = 0x1, .g3_tx_amp_adj = 0x1,
+			  .g1_tx_emph_en = 0x0, .g2_tx_emph_en = 0x0, .g3_tx_emph_en = 0x0,
+			  .g1_tx_emph = 0x1, .g2_tx_emph = 0x1, .g3_tx_emph = 0x1,
+			  .g3_dfe_res = 0x1, .g3_ffe_res_sel = 0x4, .g3_ffe_cap_sel = 0xf,
+			  .align90 = 0x61,
+			  .g1_rx_selmuff = 0x3, .g2_rx_selmuff = 0x3, .g3_rx_selmuff = 0x3,
+			  .g1_rx_selmufi = 0x0, .g2_rx_selmufi = 0x0, .g3_rx_selmufi = 0x3,
+			  .g1_rx_selmupf = 0x1, .g2_rx_selmupf = 0x1, .g3_rx_selmupf = 0x2,
+			  .g1_rx_selmupi = 0x0, .g2_rx_selmupi = 0x0, .g3_rx_selmupi = 0x2,
+			  .polarity_invert = COMPHY_POLARITY_NO_INVERT,
+			  .valid = 0x1
+			}, /* Comphy3 */
+			{ 0 }, /* Comphy4 */
+			{ 0 }, /* Comphy5 */
+		},
+	},
+};
+
+static const struct usb_params
+	usb_static_values_tab[AP_NUM][CP_NUM][MAX_LANE_NR] = {
+	[0 ... AP_NUM-1][0 ... CP_NUM-1][0 ... MAX_LANE_NR-1] = {
+		.polarity_invert = COMPHY_POLARITY_NO_INVERT
+	},
+};
+
+#endif /* __PHY_PORTING_LAYER_H */
diff --git a/plat/marvell/armada/a8k/a70x0_mochabin/mvebu_def.h b/plat/marvell/armada/a8k/a70x0_mochabin/mvebu_def.h
new file mode 100644
index 0000000..768f735
--- /dev/null
+++ b/plat/marvell/armada/a8k/a70x0_mochabin/mvebu_def.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#ifndef MVEBU_DEF_H
+#define MVEBU_DEF_H
+
+#include <a8k_plat_def.h>
+
+#define CP_COUNT		1	/* A70x0 has single CP0 */
+
+#endif /* MVEBU_DEF_H */
diff --git a/plat/marvell/armada/a8k/a70x0_mochabin/platform.mk b/plat/marvell/armada/a8k/a70x0_mochabin/platform.mk
new file mode 100644
index 0000000..2495591
--- /dev/null
+++ b/plat/marvell/armada/a8k/a70x0_mochabin/platform.mk
@@ -0,0 +1,20 @@
+#
+# Copyright (C) 2021 Marvell International Ltd.
+#
+# SPDX-License-Identifier:     BSD-3-Clause
+# https://spdx.org/licenses
+#
+
+PCI_EP_SUPPORT		:= 0
+
+CP_NUM			:= 1
+$(eval $(call add_define,CP_NUM))
+
+DOIMAGE_SEC     	:=	tools/doimage/secure/sec_img_7K.cfg
+
+MARVELL_MOCHI_DRV	:=	drivers/marvell/mochi/apn806_setup.c
+
+BOARD_DIR		:= $(shell dirname $(lastword $(MAKEFILE_LIST)))
+include plat/marvell/armada/a8k/common/a8k_common.mk
+
+include plat/marvell/armada/common/marvell_common.mk
diff --git a/plat/marvell/armada/a8k/a80x0/board/dram_port.c b/plat/marvell/armada/a8k/a80x0/board/dram_port.c
index 381c871..47bc0a8 100644
--- a/plat/marvell/armada/a8k/a80x0/board/dram_port.c
+++ b/plat/marvell/armada/a8k/a80x0/board/dram_port.c
@@ -138,7 +138,7 @@
 		i2c_init((void *)MVEBU_CP0_I2C_BASE);
 
 		/* select SPD memory page 0 to access DRAM configuration */
-		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 1);
+		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 0);
 
 		/* read data from spd */
 		i2c_read(I2C_SPD_ADDR, 0x0, 1, tm->spd_data.all_bytes,
diff --git a/plat/marvell/armada/a8k/a80x0_mcbin/board/dram_port.c b/plat/marvell/armada/a8k/a80x0_mcbin/board/dram_port.c
index 50a68b3..85c931c 100644
--- a/plat/marvell/armada/a8k/a80x0_mcbin/board/dram_port.c
+++ b/plat/marvell/armada/a8k/a80x0_mcbin/board/dram_port.c
@@ -123,7 +123,7 @@
 		/* initialize the i2c */
 		i2c_init((void *)MVEBU_CP0_I2C_BASE);
 		/* select SPD memory page 0 to access DRAM configuration */
-		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 1);
+		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 0);
 		/* read data from spd */
 		i2c_read(I2C_SPD_ADDR, 0x0, 1, tm->spd_data.all_bytes,
 			 sizeof(tm->spd_data.all_bytes));
diff --git a/plat/marvell/armada/a8k/a80x0_puzzle/board/dram_port.c b/plat/marvell/armada/a8k/a80x0_puzzle/board/dram_port.c
index 3879c98..1d8e9d2 100644
--- a/plat/marvell/armada/a8k/a80x0_puzzle/board/dram_port.c
+++ b/plat/marvell/armada/a8k/a80x0_puzzle/board/dram_port.c
@@ -132,7 +132,7 @@
 		/* initialize the MVEBU_AP_I2C_BASE I2C bus */
 		i2c_init((void *)MVEBU_AP_I2C_BASE);
 		/* select SPD memory page 0 to access DRAM configuration */
-		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 1);
+		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 0);
 		/* read data from spd */
 		i2c_read(I2C_SPD_ADDR, 0x0, 1, tm->spd_data.all_bytes,
 			 sizeof(tm->spd_data.all_bytes));
diff --git a/plat/marvell/armada/a8k/a80x0_puzzle/board/system_power.c b/plat/marvell/armada/a8k/a80x0_puzzle/board/system_power.c
index 5147dd5..eb00874 100644
--- a/plat/marvell/armada/a8k/a80x0_puzzle/board/system_power.c
+++ b/plat/marvell/armada/a8k/a80x0_puzzle/board/system_power.c
@@ -41,8 +41,8 @@
 	len = sizeof(system_off_now);
 	system_off_now[len - 1] = add_xor_checksum(system_off_now, len);
 
-	console_16550_register(PLAT_MARVELL_BOOT_UART_BASE + 0x100,
-		PLAT_MARVELL_BOOT_UART_CLK_IN_HZ, 115200, &console);
+	console_16550_register(PLAT_MARVELL_UART_BASE + 0x100,
+		PLAT_MARVELL_UART_CLK_IN_HZ, 115200, &console);
 
 	/* Send system_off_now to console */
 	for (i = 0; i < len; i++) {
diff --git a/plat/marvell/armada/a8k/common/a8k_common.mk b/plat/marvell/armada/a8k/common/a8k_common.mk
index c827326..4d8a87f 100644
--- a/plat/marvell/armada/a8k/common/a8k_common.mk
+++ b/plat/marvell/armada/a8k/common/a8k_common.mk
@@ -10,13 +10,14 @@
 MARVELL_DRV_BASE	:= drivers/marvell
 MARVELL_COMMON_BASE	:= plat/marvell/armada/common
 
-MARVELL_SVC_TEST		:= 0
+MARVELL_SVC_TEST	:= 0
 $(eval $(call add_define,MARVELL_SVC_TEST))
 
 ERRATA_A72_859971	:= 1
 
 # Enable MSS support for a8k family
 MSS_SUPPORT		:= 1
+$(eval $(call add_define,MSS_SUPPORT))
 
 # Disable EL3 cache for power management
 BL31_CACHE_DISABLE	:= 0
@@ -74,21 +75,28 @@
 # This define specifies DDR type for BLE
 $(eval $(call add_define,CONFIG_DDR4))
 
+# This define specifies DDR topology for BLE
+DDR_TOPOLOGY	?= 0
+$(eval $(call add_define,DDR_TOPOLOGY))
+
 MARVELL_GIC_SOURCES	:=	drivers/arm/gic/common/gic_common.c	\
 				drivers/arm/gic/v2/gicv2_main.c		\
 				drivers/arm/gic/v2/gicv2_helpers.c	\
 				plat/common/plat_gicv2.c
 
-PLAT_INCLUDES		:=	-I$(BOARD_DIR)				\
+PLAT_INCLUDES		+=	-I$(BOARD_DIR)				\
 				-I$(BOARD_DIR)/board			\
+				-I$(CURDIR)/drivers/marvell		\
 				-I$(PLAT_COMMON_BASE)/include		\
 				-I$(PLAT_INCLUDE_BASE)/common
 
 PLAT_BL_COMMON_SOURCES	:=	$(PLAT_COMMON_BASE)/aarch64/a8k_common.c \
 				drivers/ti/uart/aarch64/16550_console.S
 
+ifndef BLE_PORTING_SOURCES
 BLE_PORTING_SOURCES	:=	$(BOARD_DIR)/board/dram_port.c \
 				$(BOARD_DIR)/board/marvell_plat_config.c
+endif
 
 MARVELL_MOCHI_DRV	+=	$(MARVELL_DRV_BASE)/mochi/cp110_setup.c
 
@@ -112,11 +120,20 @@
 				$(MARVELL_DRV_BASE)/amb_adec.c	\
 				$(MARVELL_DRV_BASE)/ccu.c	\
 				$(MARVELL_DRV_BASE)/cache_llc.c	\
-				$(MARVELL_DRV_BASE)/comphy/phy-comphy-cp110.c \
-				$(MARVELL_DRV_BASE)/mc_trustzone/mc_trustzone.c \
-				$(MARVELL_DRV_BASE)/mg_conf_cm3/mg_conf_cm3.c
+				$(MARVELL_DRV_BASE)/comphy/phy-comphy-cp110.c	\
+				$(MARVELL_DRV_BASE)/mc_trustzone/mc_trustzone.c	\
+				$(MARVELL_DRV_BASE)/secure_dfx_access/armada_thermal.c	\
+				$(MARVELL_DRV_BASE)/secure_dfx_access/misc_dfx.c	\
+				$(MARVELL_DRV_BASE)/ddr_phy_access.c	\
+				drivers/rambus/trng_ip_76.c
 
+ifeq (${MSS_SUPPORT}, 1)
+MARVELL_DRV		+=	$(MARVELL_DRV_BASE)/mg_conf_cm3/mg_conf_cm3.c
+endif
+
+ifndef BL31_PORTING_SOURCES
 BL31_PORTING_SOURCES	:=	$(BOARD_DIR)/board/marvell_plat_config.c
+endif
 
 ifeq ($(SYSTEM_POWER_SUPPORT),1)
 BL31_PORTING_SOURCES	+=	$(BOARD_DIR)/board/system_power.c
@@ -138,6 +155,8 @@
 # Add trace functionality for PM
 BL31_SOURCES		+=	$(PLAT_COMMON_BASE)/plat_pm_trace.c
 
+
+ifeq (${MSS_SUPPORT}, 1)
 # Force builds with BL2 image on a80x0 platforms
 ifndef SCP_BL2
  $(error "Error: SCP_BL2 image is mandatory for a8k family")
@@ -145,23 +164,29 @@
 
 # MSS (SCP) build
 include $(PLAT_COMMON_BASE)/mss/mss_a8k.mk
+endif
 
 # BLE (ROM context execution code, AKA binary extension)
 BLE_PATH	?=  $(PLAT_COMMON_BASE)/ble
 
 include ${BLE_PATH}/ble.mk
-$(eval $(call MAKE_BL,e))
+$(eval $(call MAKE_BL,ble))
 
+clean realclean distclean: mrvl_clean
+
+.PHONY: mrvl_clean
 mrvl_clean:
 	@echo "  Doimage CLEAN"
 	${Q}${MAKE} PLAT=${PLAT} --no-print-directory -C ${DOIMAGEPATH} clean
 
-${DOIMAGETOOL}: mrvl_clean
+${DOIMAGETOOL}: FORCE
 	@$(DOIMAGE_LIBS_CHECK)
 	${Q}${MAKE} --no-print-directory -C ${DOIMAGEPATH}
 
-mrvl_flash: ${BUILD_PLAT}/${FIP_NAME} ${DOIMAGETOOL} ${BUILD_PLAT}/ble.bin
-	$(shell truncate -s %128K ${BUILD_PLAT}/bl1.bin)
-	$(shell cat ${BUILD_PLAT}/bl1.bin ${BUILD_PLAT}/${FIP_NAME} > ${BUILD_PLAT}/${BOOT_IMAGE})
-	${DOIMAGETOOL} ${DOIMAGE_FLAGS} ${BUILD_PLAT}/${BOOT_IMAGE} ${BUILD_PLAT}/${FLASH_IMAGE}
-
+${BUILD_PLAT}/${FLASH_IMAGE}: ${ROM_BIN_EXT} ${BUILD_PLAT}/${BOOT_IMAGE} ${DOIMAGETOOL}
+	@${ECHO_BLANK_LINE}
+	@echo "Building flash image"
+	${Q}${DOIMAGETOOL} ${DOIMAGE_FLAGS} ${BUILD_PLAT}/${BOOT_IMAGE} ${BUILD_PLAT}/${FLASH_IMAGE}
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@${ECHO_BLANK_LINE}
diff --git a/plat/marvell/armada/a8k/common/ble/ble.mk b/plat/marvell/armada/a8k/common/ble/ble.mk
index 60fbf5f..160e98f 100644
--- a/plat/marvell/armada/a8k/common/ble/ble.mk
+++ b/plat/marvell/armada/a8k/common/ble/ble.mk
@@ -3,8 +3,6 @@
 # SPDX-License-Identifier:     BSD-3-Clause
 # https://spdx.org/licenses
 
-MV_DDR_PATH		?=	drivers/marvell/mv_ddr
-
 MV_DDR_LIB		=	$(BUILD_PLAT)/ble/mv_ddr_lib.a
 LIBC_LIB		=	$(BUILD_PLAT)/lib/libc.a
 BLE_LIBS		=	$(MV_DDR_LIB) $(LIBC_LIB)
@@ -13,20 +11,25 @@
 BLE_SOURCES		+= 	$(BLE_PATH)/ble_main.c				\
 				$(BLE_PATH)/ble_mem.S				\
 				drivers/delay_timer/delay_timer.c		\
+				drivers/marvell/iob.c				\
 				$(PLAT_MARVELL)/common/aarch64/marvell_helpers.S \
 				$(PLAT_MARVELL)/common/plat_delay_timer.c	\
 				$(PLAT_MARVELL)/common/marvell_console.c
 
-PLAT_INCLUDES		+= 	-I$(MV_DDR_PATH)				\
-				-I$(CURDIR)/include				\
+MV_DDR_INCLUDES		:=	-I$(CURDIR)/include				\
 				-I$(CURDIR)/include/arch/aarch64		\
 				-I$(CURDIR)/include/lib/libc			\
-				-I$(CURDIR)/include/lib/libc/aarch64		\
-				-I$(CURDIR)/drivers/marvell
+				-I$(CURDIR)/include/lib/libc/aarch64
 
 BLE_LINKERFILE		:=	$(BLE_PATH)/ble.ld.S
 
-FORCE:
+BLE_OBJS := $(addprefix $(BUILD_PLAT)/ble/,$(call SOURCES_TO_OBJS,$(BLE_SOURCES)))
+$(BLE_OBJS): PLAT_INCLUDES += -I$(MV_DDR_PATH)
+$(BLE_OBJS): $(MV_DDR_LIB)
 
 $(MV_DDR_LIB): FORCE
-	@+make -C $(MV_DDR_PATH) --no-print-directory PLAT_INCLUDES="$(PLAT_INCLUDES)" PLATFORM=$(PLAT) ARCH=AARCH64 OBJ_DIR=$(BUILD_PLAT)/ble
+#	Do not remove! Following checks are required to ensure correct TF-A builds, removing these checks leads to broken TF-A builds
+	$(if $(value MV_DDR_PATH),,$(error "Platform '$(PLAT)' for BLE requires MV_DDR_PATH. Please set MV_DDR_PATH to point to the right directory"))
+	$(if $(wildcard $(value MV_DDR_PATH)/*),,$(error "'MV_DDR_PATH=$(value MV_DDR_PATH)' was specified, but '$(value MV_DDR_PATH)' directory does not exist"))
+	$(if $(shell git -C $(value MV_DDR_PATH) rev-parse --show-cdup 2>&1),$(error "'MV_DDR_PATH=$(value MV_DDR_PATH)' was specified, but '$(value MV_DDR_PATH)' does not contain valid mv-ddr-marvell git repository"))
+	@+make -C $(MV_DDR_PATH) --no-print-directory PLAT_INCLUDES="$(MV_DDR_INCLUDES)" PLATFORM=$(PLAT) ARCH=AARCH64 OBJ_DIR=$(BUILD_PLAT)/ble
diff --git a/plat/marvell/armada/a8k/common/include/a8k_plat_def.h b/plat/marvell/armada/a8k/common/include/a8k_plat_def.h
index de80315..3a0fd4b 100644
--- a/plat/marvell/armada/a8k/common/include/a8k_plat_def.h
+++ b/plat/marvell/armada/a8k/common/include/a8k_plat_def.h
@@ -64,7 +64,8 @@
 #define MVEBU_AP_GPIO_DATA_IN		(MVEBU_AP_GPIO_REGS + 0x10)
 #define MVEBU_AP_I2C_BASE		(MVEBU_REGS_BASE + 0x511000)
 #define MVEBU_CP0_I2C_BASE		(MVEBU_CP_REGS_BASE(0) + 0x701000)
-#define MVEBU_AP_EXT_TSEN_BASE		(MVEBU_RFU_BASE + 0x8084)
+#define MVEBU_AP_GEN_MGMT_BASE		(MVEBU_RFU_BASE + 0x8000)
+#define MVEBU_AP_EXT_TSEN_BASE		(MVEBU_AP_GEN_MGMT_BASE + 0x84)
 
 #define MVEBU_AP_MC_TRUSTZONE_REG_LOW(ap, win)	(MVEBU_REGS_BASE_AP(ap) + \
 							0x20080 + ((win) * 0x8))
diff --git a/plat/marvell/armada/a8k/common/include/platform_def.h b/plat/marvell/armada/a8k/common/include/platform_def.h
index 7d85059..45860ba 100644
--- a/plat/marvell/armada/a8k/common/include/platform_def.h
+++ b/plat/marvell/armada/a8k/common/include/platform_def.h
@@ -168,14 +168,8 @@
 /*
  * PL011 related constants
  */
-#define PLAT_MARVELL_BOOT_UART_BASE		(MVEBU_REGS_BASE + 0x512000)
-#define PLAT_MARVELL_BOOT_UART_CLK_IN_HZ	200000000
-
-#define PLAT_MARVELL_CRASH_UART_BASE		PLAT_MARVELL_BOOT_UART_BASE
-#define PLAT_MARVELL_CRASH_UART_CLK_IN_HZ	PLAT_MARVELL_BOOT_UART_CLK_IN_HZ
-
-#define PLAT_MARVELL_BL31_RUN_UART_BASE		PLAT_MARVELL_BOOT_UART_BASE
-#define PLAT_MARVELL_BL31_RUN_UART_CLK_IN_HZ	PLAT_MARVELL_BOOT_UART_CLK_IN_HZ
+#define PLAT_MARVELL_UART_BASE			(MVEBU_REGS_BASE + 0x512000)
+#define PLAT_MARVELL_UART_CLK_IN_HZ		200000000
 
 /* Recovery image enable */
 #define PLAT_RECOVERY_IMAGE_ENABLE		0
diff --git a/plat/marvell/armada/a8k/common/mss/mss_a8k.mk b/plat/marvell/armada/a8k/common/mss/mss_a8k.mk
index d8d4921..315fc87 100644
--- a/plat/marvell/armada/a8k/common/mss/mss_a8k.mk
+++ b/plat/marvell/armada/a8k/common/mss/mss_a8k.mk
@@ -11,7 +11,8 @@
 BL2_SOURCES		+=	$(A8K_MSS_SOURCE)/mss_bl2_setup.c \
 				$(MARVELL_MOCHI_DRV)
 
-BL31_SOURCES		+=	$(A8K_MSS_SOURCE)/mss_pm_ipc.c
+BL31_SOURCES		+=	$(A8K_MSS_SOURCE)/mss_pm_ipc.c \
+				$(A8K_MSS_SOURCE)/mss_bl31_setup.c
 
 PLAT_INCLUDES		+=	-I$(A8K_MSS_SOURCE)
 
diff --git a/plat/marvell/armada/a8k/common/mss/mss_bl2_setup.c b/plat/marvell/armada/a8k/common/mss/mss_bl2_setup.c
index b919cb3..dee2d5b 100644
--- a/plat/marvell/armada/a8k/common/mss/mss_bl2_setup.c
+++ b/plat/marvell/armada/a8k/common/mss/mss_bl2_setup.c
@@ -16,7 +16,7 @@
 
 #include <armada_common.h>
 #include <marvell_plat_priv.h> /* timer functionality */
-
+#include "mss_defs.h"
 #include "mss_scp_bootloader.h"
 
 /* MSS windows configuration */
@@ -121,12 +121,17 @@
 
 uintptr_t bl2_plat_get_cp_mss_regs(int ap_idx, int cp_idx)
 {
-	return MVEBU_CP_REGS_BASE(cp_idx) + 0x280000;
+	return MVEBU_CP_REGS_BASE(cp_idx) + MSS_CP_REGS_OFFSET;
+}
+
+uintptr_t bl2_plat_get_cp_mss_sram(int ap_idx, int cp_idx)
+{
+	return MVEBU_CP_REGS_BASE(cp_idx) + MSS_CP_SRAM_OFFSET;
 }
 
 uintptr_t bl2_plat_get_ap_mss_regs(int ap_idx)
 {
-	return MVEBU_REGS_BASE + 0x580000;
+	return MVEBU_REGS_BASE + MSS_AP_REGS_OFFSET;
 }
 
 uint32_t bl2_plat_get_cp_count(int ap_idx)
diff --git a/plat/marvell/armada/a8k/common/mss/mss_bl31_setup.c b/plat/marvell/armada/a8k/common/mss/mss_bl31_setup.c
new file mode 100644
index 0000000..52a8929
--- /dev/null
+++ b/plat/marvell/armada/a8k/common/mss/mss_bl31_setup.c
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <platform_def.h>
+
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <armada_common.h>
+
+#include "mss_defs.h"
+
+void mss_start_cp_cm3(int cp)
+{
+	uint32_t magic;
+	uintptr_t sram = MVEBU_CP_REGS_BASE(cp) + MSS_CP_SRAM_OFFSET;
+	uintptr_t regs = MVEBU_CP_REGS_BASE(cp) + MSS_CP_REGS_OFFSET;
+
+	magic = mmio_read_32(sram);
+
+	/* Make sure the FW was loaded */
+	if (magic != MSS_FW_READY_MAGIC) {
+		return;
+	}
+
+	NOTICE("Starting CP%d MSS CPU\n", cp);
+	/* remove the magic */
+	mmio_write_32(sram, 0);
+	/* Release M3 from reset */
+	mmio_write_32(MSS_M3_RSTCR(regs),
+		      (MSS_M3_RSTCR_RST_OFF << MSS_M3_RSTCR_RST_OFFSET));
+}
diff --git a/plat/marvell/armada/a8k/common/mss/mss_defs.h b/plat/marvell/armada/a8k/common/mss/mss_defs.h
new file mode 100644
index 0000000..6956461
--- /dev/null
+++ b/plat/marvell/armada/a8k/common/mss/mss_defs.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2021 Marvell International Ltd.
+ *
+ * SPDX-License-Identifier:     BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#ifndef MSS_DEFS_H
+#define MSS_DEFS_H
+
+#define MSS_DMA_SRCBR(base)		(base + 0xC0)
+#define MSS_DMA_DSTBR(base)		(base + 0xC4)
+#define MSS_DMA_CTRLR(base)		(base + 0xC8)
+#define MSS_M3_RSTCR(base)		(base + 0xFC)
+
+#define MSS_DMA_CTRLR_SIZE_OFFSET	(0)
+#define MSS_DMA_CTRLR_REQ_OFFSET	(15)
+#define MSS_DMA_CTRLR_REQ_SET		(1)
+#define MSS_DMA_CTRLR_ACK_OFFSET	(12)
+#define MSS_DMA_CTRLR_ACK_MASK		(0x1)
+#define MSS_DMA_CTRLR_ACK_READY		(1)
+#define MSS_M3_RSTCR_RST_OFFSET		(0)
+#define MSS_M3_RSTCR_RST_OFF		(1)
+
+#define MSS_FW_READY_MAGIC		0x46575144 /* FWRD */
+
+#define MSS_AP_REGS_OFFSET		0x00580000
+#define MSS_CP_SRAM_OFFSET		0x00220000
+#define MSS_CP_REGS_OFFSET		0x00280000
+
+void mss_start_cp_cm3(int cp);
+
+#endif /* MSS_DEFS_H */
diff --git a/plat/marvell/armada/a8k/common/plat_bl31_setup.c b/plat/marvell/armada/a8k/common/plat_bl31_setup.c
index 552c9b2..db85cce 100644
--- a/plat/marvell/armada/a8k/common/plat_bl31_setup.c
+++ b/plat/marvell/armada/a8k/common/plat_bl31_setup.c
@@ -16,8 +16,11 @@
 #include <marvell_pm.h>
 #include <mc_trustzone/mc_trustzone.h>
 #include <plat_marvell.h>
+#if MSS_SUPPORT
 #include <mss_ipc_drv.h>
 #include <mss_mem.h>
+#include <mss_defs.h>
+#endif
 
 /* In Armada-8k family AP806/AP807, CP0 connected to PIDI
  * and CP1 connected to IHB via MCI #0
@@ -51,6 +54,7 @@
 	mmio_write_32(MVEBU_CP_MPP_REGS(0, 4), reg | 0x2200000);
 }
 
+#if MSS_SUPPORT
 void marvell_bl31_mss_init(void)
 {
 	struct mss_pm_ctrl_block *mss_pm_crtl =
@@ -70,6 +74,7 @@
 	if (mss_pm_crtl->ipc_state == IPC_INITIALIZED)
 		mv_pm_ipc_init(mss_pm_crtl->ipc_base_address | MVEBU_REGS_BASE);
 }
+#endif
 
 _Bool is_pm_fw_running(void)
 {
@@ -120,16 +125,22 @@
 			   STREAM_ID_BASE + (cp * MAX_STREAM_ID_PER_CP));
 
 		marvell_bl31_mpp_init(cp);
+
+#if MSS_SUPPORT
+		/* Release CP MSS CPU from reset once the CP init is done */
+		mss_start_cp_cm3(cp);
+#endif
 	}
 
 	for (cp = 1; cp < CP_COUNT; cp++)
 		mci_link_tune(cp - 1);
 
+#if MSS_SUPPORT
 	/* initialize IPC between MSS and ATF */
 	if (mailbox[MBOX_IDX_MAGIC] != MVEBU_MAILBOX_MAGIC_NUM ||
 	    mailbox[MBOX_IDX_SUSPEND_MAGIC] != MVEBU_MAILBOX_SUSPEND_STATE)
 		marvell_bl31_mss_init();
-
+#endif
 	/* Configure GPIO */
 	marvell_gpio_config();
 
diff --git a/plat/marvell/armada/a8k/common/plat_ble_setup.c b/plat/marvell/armada/a8k/common/plat_ble_setup.c
index e4e09fb..9c5ee15 100644
--- a/plat/marvell/armada/a8k/common/plat_ble_setup.c
+++ b/plat/marvell/armada/a8k/common/plat_ble_setup.c
@@ -14,6 +14,7 @@
 #include <drivers/marvell/mochi/cp110_setup.h>
 
 #include <armada_common.h>
+#include <efuse_def.h>
 #include <mv_ddr_if.h>
 #include <mvebu_def.h>
 #include <plat_marvell.h>
@@ -27,7 +28,6 @@
 #define MMAP_RESTORE_SAVED		1
 
 /* SAR clock settings */
-#define MVEBU_AP_GEN_MGMT_BASE		(MVEBU_RFU_BASE + 0x8000)
 #define MVEBU_AP_SAR_REG_BASE(r)	(MVEBU_AP_GEN_MGMT_BASE + 0x200 +\
 								((r) << 2))
 
@@ -82,11 +82,6 @@
 					 (0x1 << AVS_SOFT_RESET_OFFSET) | \
 					 (0x1 << AVS_ENABLE_OFFSET))
 
-#define MVEBU_AP_EFUSE_SRV_CTRL_REG	(MVEBU_AP_GEN_MGMT_BASE + 0x8)
-#define EFUSE_SRV_CTRL_LD_SELECT_OFFS	6
-#define EFUSE_SRV_CTRL_LD_SEL_USER_MASK	(1 << EFUSE_SRV_CTRL_LD_SELECT_OFFS)
-
-
 /*
  * - Identification information in the LD-0 eFuse:
  *	DRO:           LD0[74:65] - Not used by the SW
@@ -96,14 +91,7 @@
  *	Cluster 1 PWR: LD0[193] - if set to 1, power down CPU Cluster-1
  *				  resulting in 2 CPUs active only (7020)
  */
-#define MVEBU_AP_LD_EFUSE_BASE		(MVEBU_AP_GEN_MGMT_BASE + 0xF00)
-/* Bits [94:63] - 32 data bits total */
-#define MVEBU_AP_LD0_94_63_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x8)
-/* Bits [125:95] - 31 data bits total, 32nd bit is parity for bits [125:63] */
-#define MVEBU_AP_LD0_125_95_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0xC)
-/* Bits [220:189] - 32 data bits total */
-#define MVEBU_AP_LD0_220_189_EFUSE_OFFS	(MVEBU_AP_LD_EFUSE_BASE + 0x18)
-/* Offsets for the above 2 fields combined into single 64-bit value [125:63] */
+/* Offsets for 2 efuse fields combined into single 64-bit value [125:63] */
 #define EFUSE_AP_LD0_DRO_OFFS		2		/* LD0[74:65] */
 #define EFUSE_AP_LD0_DRO_MASK		0x3FF
 #define EFUSE_AP_LD0_REVID_OFFS		12		/* LD0[78:75] */
@@ -376,20 +364,20 @@
 	uint8_t	 avs_data_bits, min_sw_ver, svc_fields;
 	unsigned int ap_type;
 
-	/* Set access to LD0 */
+	/* Get test EERPOM data */
 	avs_workpoint = avs_update_from_eeprom(0);
 	if (avs_workpoint)
 		goto set_aws_wp;
 
 	/* Set access to LD0 */
 	reg_val = mmio_read_32(MVEBU_AP_EFUSE_SRV_CTRL_REG);
-	reg_val &= ~EFUSE_SRV_CTRL_LD_SELECT_OFFS;
+	reg_val &= ~EFUSE_SRV_CTRL_LD_SELECT_MASK;
 	mmio_write_32(MVEBU_AP_EFUSE_SRV_CTRL_REG, reg_val);
 
 	/* Obtain the value of LD0[125:63] */
-	efuse = mmio_read_32(MVEBU_AP_LD0_125_95_EFUSE_OFFS);
+	efuse = mmio_read_32(MVEBU_AP_LDX_125_95_EFUSE_OFFS);
 	efuse <<= 32;
-	efuse |= mmio_read_32(MVEBU_AP_LD0_94_63_EFUSE_OFFS);
+	efuse |= mmio_read_32(MVEBU_AP_LDX_94_63_EFUSE_OFFS);
 
 	/* SW Revision:
 	 * Starting from SW revision 1 the SVC flow is supported.
@@ -452,7 +440,7 @@
 			perr[i] = 1; /* register the error */
 	}
 
-	single_cluster = mmio_read_32(MVEBU_AP_LD0_220_189_EFUSE_OFFS);
+	single_cluster = mmio_read_32(MVEBU_AP_LDX_220_189_EFUSE_OFFS);
 	single_cluster = (single_cluster >> EFUSE_AP_LD0_CLUSTER_DOWN_OFFS) & 1;
 
 	device_id = cp110_device_id_get(MVEBU_CP_REGS_BASE(0));
@@ -720,7 +708,7 @@
 
 int ble_plat_setup(int *skip)
 {
-	int ret;
+	int ret, cp;
 	unsigned int freq_mode;
 
 	/* Power down unused CPUs */
@@ -745,6 +733,10 @@
 	/* Do required CP-110 setups for BLE stage */
 	cp110_ble_init(MVEBU_CP_REGS_BASE(0));
 
+	/* Config address for each cp other than cp0 */
+	for (cp = 1; cp < CP_COUNT; cp++)
+		update_cp110_default_win(cp);
+
 	/* Setup AVS */
 	ble_plat_svc_config();
 
diff --git a/plat/marvell/armada/a8k/common/plat_pm.c b/plat/marvell/armada/a8k/common/plat_pm.c
index 96e95c2..9ea9276 100644
--- a/plat/marvell/armada/a8k/common/plat_pm.c
+++ b/plat/marvell/armada/a8k/common/plat_pm.c
@@ -18,7 +18,9 @@
 
 #include <armada_common.h>
 #include <marvell_pm.h>
+#if MSS_SUPPORT
 #include <mss_pm_ipc.h>
+#endif
 #include <plat_marvell.h>
 #include <plat_pm_trace.h>
 
@@ -396,6 +398,7 @@
 	/* Power up CPU (CPUs 1-3 are powered off at start of BLE) */
 	plat_marvell_cpu_powerup(mpidr);
 
+#if MSS_SUPPORT
 	if (is_pm_fw_running()) {
 		unsigned int target =
 				((mpidr & 0xFF) + (((mpidr >> 8) & 0xFF) * 2));
@@ -417,11 +420,12 @@
 
 		/* trace message */
 		PM_TRACE(TRACE_PWR_DOMAIN_ON | target);
-	} else {
+	} else
+#endif
+	{
 		/* proprietary CPU ON exection flow */
 		plat_marvell_cpu_on(mpidr);
 	}
-
 	return 0;
 }
 
@@ -441,6 +445,7 @@
  */
 static void a8k_pwr_domain_off(const psci_power_state_t *target_state)
 {
+#if MSS_SUPPORT
 	if (is_pm_fw_running()) {
 		unsigned int idx = plat_my_core_pos();
 
@@ -466,6 +471,7 @@
 	} else {
 		INFO("%s: is not supported without SCP\n", __func__);
 	}
+#endif
 }
 
 /* Get PM config to power off the SoC */
@@ -586,6 +592,7 @@
  */
 static void a8k_pwr_domain_suspend(const psci_power_state_t *target_state)
 {
+#if MSS_SUPPORT
 	if (is_pm_fw_running()) {
 		unsigned int idx;
 
@@ -610,7 +617,9 @@
 
 		/* trace message */
 		PM_TRACE(TRACE_PWR_DOMAIN_SUSPEND);
-	} else {
+	} else
+#endif
+	{
 		uintptr_t *mailbox = (void *)PLAT_MARVELL_MAILBOX_BASE;
 
 		INFO("Suspending to RAM\n");
diff --git a/plat/marvell/armada/a8k/common/plat_pm_trace.c b/plat/marvell/armada/a8k/common/plat_pm_trace.c
index f589ff3..e02a893 100644
--- a/plat/marvell/armada/a8k/common/plat_pm_trace.c
+++ b/plat/marvell/armada/a8k/common/plat_pm_trace.c
@@ -8,10 +8,11 @@
 #include <lib/mmio.h>
 #include <plat/common/platform.h>
 
+#if MSS_SUPPORT
 #include <mss_mem.h>
-#include <plat_pm_trace.h>
 
 #ifdef PM_TRACE_ENABLE
+#include <plat_pm_trace.h>
 
 /* core trace APIs */
 core_trace_func funcTbl[PLATFORM_CORE_COUNT] = {
@@ -90,3 +91,4 @@
 		     AP_MSS_ATF_TRACE_SIZE_MASK));
 }
 #endif /* PM_TRACE_ENABLE */
+#endif /* MSS_SUPPORT */
diff --git a/plat/marvell/armada/common/aarch64/marvell_helpers.S b/plat/marvell/armada/common/aarch64/marvell_helpers.S
index b798f17..3038ec0 100644
--- a/plat/marvell/armada/common/aarch64/marvell_helpers.S
+++ b/plat/marvell/armada/common/aarch64/marvell_helpers.S
@@ -63,8 +63,16 @@
 	 * ---------------------------------------------
 	 */
 func plat_crash_console_init
-	mov_imm	x0, PLAT_MARVELL_CRASH_UART_BASE
-	mov_imm	x1, PLAT_MARVELL_CRASH_UART_CLK_IN_HZ
+#ifdef PLAT_a3700
+	mov	x1, x30
+	bl	get_ref_clk
+	mov	x30, x1
+	mov_imm	x1, 1000000
+	mul	x1, x0, x1
+#else
+	mov_imm	x1, PLAT_MARVELL_UART_CLK_IN_HZ
+#endif
+	mov_imm	x0, PLAT_MARVELL_UART_BASE
 	mov_imm	x2, MARVELL_CONSOLE_BAUDRATE
 #ifdef PLAT_a3700
 	b	console_a3700_core_init
@@ -81,7 +89,7 @@
 	 * ---------------------------------------------
 	 */
 func plat_crash_console_putc
-	mov_imm	x1, PLAT_MARVELL_CRASH_UART_BASE
+	mov_imm	x1, PLAT_MARVELL_UART_BASE
 #ifdef PLAT_a3700
 
 	b	console_a3700_core_putc
@@ -99,7 +107,7 @@
 	 * ---------------------------------------------
 	 */
 func plat_crash_console_flush
-	mov_imm	x0, PLAT_MARVELL_CRASH_UART_BASE
+	mov_imm	x0, PLAT_MARVELL_UART_BASE
 #ifdef PLAT_a3700
 	b	console_a3700_core_flush
 #else
diff --git a/plat/marvell/armada/common/marvell_common.mk b/plat/marvell/armada/common/marvell_common.mk
index af149fa..f0e6edf 100644
--- a/plat/marvell/armada/common/marvell_common.mk
+++ b/plat/marvell/armada/common/marvell_common.mk
@@ -6,10 +6,6 @@
 MARVELL_PLAT_BASE		:= plat/marvell/armada
 MARVELL_PLAT_INCLUDE_BASE	:= include/plat/marvell/armada
 
-include plat/marvell/version.mk
-
-VERSION_STRING			+=(Marvell-${SUBVERSION})
-
 SEPARATE_CODE_AND_RODATA	:= 1
 
 # flag to switch from PLL to ARO
@@ -85,3 +81,19 @@
 ifeq (${MSS_SUPPORT}, 1)
 include $(MARVELL_PLAT_BASE)/common/mss/mss_common.mk
 endif
+
+$(BUILD_PLAT)/$(BOOT_IMAGE): $(BUILD_PLAT)/bl1.bin $(BUILD_PLAT)/$(FIP_NAME)
+	$(if $(shell find $(BUILD_PLAT)/bl1.bin -type f -size +128k),$(error "Image '$(BUILD_PLAT)/bl1.bin' is bigger than 128kB"))
+	@cp $(BUILD_PLAT)/bl1.bin $(BUILD_PLAT)/$(BOOT_IMAGE) || { rm -f $(BUILD_PLAT)/$(BOOT_IMAGE); false; }
+	@truncate -s %128K $(BUILD_PLAT)/$(BOOT_IMAGE) || { rm -f $(BUILD_PLAT)/$(BOOT_IMAGE); false; }
+	@cat $(BUILD_PLAT)/$(FIP_NAME) >> $(BUILD_PLAT)/$(BOOT_IMAGE) || { rm -f $(BUILD_PLAT)/$(BOOT_IMAGE); false; }
+	@truncate -s %4 $(BUILD_PLAT)/$(BOOT_IMAGE) || { rm -f $(BUILD_PLAT)/$(BOOT_IMAGE); false; }
+	@$(ECHO_BLANK_LINE)
+	@echo "Built $@ successfully"
+	@$(ECHO_BLANK_LINE)
+
+.PHONY: mrvl_bootimage
+mrvl_bootimage: $(BUILD_PLAT)/$(BOOT_IMAGE)
+
+.PHONY: mrvl_flash
+mrvl_flash: $(BUILD_PLAT)/$(FLASH_IMAGE)
diff --git a/plat/marvell/armada/common/marvell_console.c b/plat/marvell/armada/common/marvell_console.c
index c84b004..ef54bff 100644
--- a/plat/marvell/armada/common/marvell_console.c
+++ b/plat/marvell/armada/common/marvell_console.c
@@ -14,6 +14,7 @@
 
 #ifdef PLAT_a3700
 #include <drivers/marvell/uart/a3700_console.h>
+#define PLAT_MARVELL_UART_CLK_IN_HZ (get_ref_clk() * 1000000)
 #define console_marvell_register console_a3700_register
 #else
 #include <drivers/ti/uart/uart_16550.h>
@@ -31,8 +32,8 @@
 void marvell_console_boot_init(void)
 {
 	int rc =
-	console_marvell_register(PLAT_MARVELL_BOOT_UART_BASE,
-				 PLAT_MARVELL_BOOT_UART_CLK_IN_HZ,
+	console_marvell_register(PLAT_MARVELL_UART_BASE,
+				 PLAT_MARVELL_UART_CLK_IN_HZ,
 				 MARVELL_CONSOLE_BAUDRATE,
 				 &marvell_boot_console);
 	if (rc == 0) {
@@ -58,8 +59,8 @@
 void marvell_console_runtime_init(void)
 {
 	int rc =
-	console_marvell_register(PLAT_MARVELL_BOOT_UART_BASE,
-				 PLAT_MARVELL_BOOT_UART_CLK_IN_HZ,
+	console_marvell_register(PLAT_MARVELL_UART_BASE,
+				 PLAT_MARVELL_UART_CLK_IN_HZ,
 				 MARVELL_CONSOLE_BAUDRATE,
 				 &marvell_runtime_console);
 	if (rc == 0)
diff --git a/plat/marvell/armada/common/mrvl_sip_svc.c b/plat/marvell/armada/common/mrvl_sip_svc.c
index 0291024..c4c5c0e 100644
--- a/plat/marvell/armada/common/mrvl_sip_svc.c
+++ b/plat/marvell/armada/common/mrvl_sip_svc.c
@@ -9,12 +9,15 @@
 #include <common/runtime_svc.h>
 #include <drivers/marvell/cache_llc.h>
 #include <drivers/marvell/mochi/ap_setup.h>
+#include <drivers/rambus/trng_ip_76.h>
 #include <lib/smccc.h>
 
 #include <marvell_plat_priv.h>
 #include <plat_marvell.h>
 
 #include "comphy/phy-comphy-cp110.h"
+#include "secure_dfx_access/dfx.h"
+#include "ddr_phy_access.h"
 #include <stdbool.h>
 
 /* #define DEBUG_COMPHY */
@@ -36,11 +39,20 @@
 #define MV_SIP_LLC_ENABLE	0x82000011
 #define MV_SIP_PMU_IRQ_ENABLE	0x82000012
 #define MV_SIP_PMU_IRQ_DISABLE	0x82000013
+#define MV_SIP_DFX		0x82000014
+#define MV_SIP_DDR_PHY_WRITE	0x82000015
+#define MV_SIP_DDR_PHY_READ	0x82000016
+
+/* TRNG */
+#define MV_SIP_RNG_64		0xC200FF11
 
 #define MAX_LANE_NR		6
 #define MVEBU_COMPHY_OFFSET	0x441000
 #define MVEBU_CP_BASE_MASK	(~0xffffff)
 
+/* Common PHY register */
+#define COMPHY_TRX_TRAIN_CTRL_REG_0_OFFS	0x120a2c
+
 /* This macro is used to identify COMPHY related calls from SMC function ID */
 #define is_comphy_fid(fid)	\
 	((fid) >= MV_SIP_COMPHY_POWER_ON && (fid) <= MV_SIP_COMPHY_DIG_RESET)
@@ -67,7 +79,7 @@
 			       void *handle,
 			       u_register_t flags)
 {
-	u_register_t ret;
+	u_register_t ret, read, x5 = x1;
 	int i;
 
 	debug("%s: got SMC (0x%x) x1 0x%lx, x2 0x%lx, x3 0x%lx\n",
@@ -81,6 +93,7 @@
 			SMC_RET1(handle, SMC_UNK);
 		}
 
+		x5 = x1 + COMPHY_TRX_TRAIN_CTRL_REG_0_OFFS;
 		x1 += MVEBU_COMPHY_OFFSET;
 
 		if (x2 >= MAX_LANE_NR) {
@@ -95,7 +108,7 @@
 	/* Comphy related FID's */
 	case MV_SIP_COMPHY_POWER_ON:
 		/* x1:  comphy_base, x2: comphy_index, x3: comphy_mode */
-		ret = mvebu_cp110_comphy_power_on(x1, x2, x3);
+		ret = mvebu_cp110_comphy_power_on(x1, x2, x3, x5);
 		SMC_RET1(handle, ret);
 	case MV_SIP_COMPHY_POWER_OFF:
 		/* x1:  comphy_base, x2: comphy_index */
@@ -131,7 +144,33 @@
 		mvebu_pmu_interrupt_disable();
 		SMC_RET1(handle, 0);
 #endif
+	case MV_SIP_DFX:
+		if (x1 >= MV_SIP_DFX_THERMAL_INIT &&
+		    x1 <= MV_SIP_DFX_THERMAL_SEL_CHANNEL) {
+			ret = mvebu_dfx_thermal_handle(x1, &read, x2, x3);
+			SMC_RET2(handle, ret, read);
+		}
+		if (x1 >= MV_SIP_DFX_SREAD && x1 <= MV_SIP_DFX_SWRITE) {
+			ret = mvebu_dfx_misc_handle(x1, &read, x2, x3);
+			SMC_RET2(handle, ret, read);
+		}
 
+		SMC_RET1(handle, SMC_UNK);
+	case MV_SIP_DDR_PHY_WRITE:
+		ret = mvebu_ddr_phy_write(x1, x2);
+		SMC_RET1(handle, ret);
+	case MV_SIP_DDR_PHY_READ:
+		read = 0;
+		ret = mvebu_ddr_phy_read(x1, (uint16_t *)&read);
+		SMC_RET2(handle, ret, read);
+	case MV_SIP_RNG_64:
+		if ((x1 % 2 + 1) > sizeof(read)/4) {
+			ERROR("%s: Maximum %ld random bytes per SMC call\n",
+			      __func__, sizeof(read));
+			SMC_RET1(handle, SMC_UNK);
+		}
+		ret = eip76_rng_get_random((uint8_t *)&read, 4 * (x1 % 2 + 1));
+		SMC_RET2(handle, ret, read);
 	default:
 		ERROR("%s: unhandled SMC (0x%x)\n", __func__, smc_fid);
 		SMC_RET1(handle, SMC_UNK);
diff --git a/plat/marvell/armada/common/mss/mss_scp_bl2_format.h b/plat/marvell/armada/common/mss/mss_scp_bl2_format.h
index 74dddc6..90913b0 100644
--- a/plat/marvell/armada/common/mss/mss_scp_bl2_format.h
+++ b/plat/marvell/armada/common/mss/mss_scp_bl2_format.h
@@ -13,6 +13,7 @@
 #define HEADER_VERSION	0x1
 
 #define MSS_IDRAM_SIZE	0x10000 /* 64KB */
+#define MSS_SRAM_SIZE	0x8000 /* 32KB */
 
 /* Types definitions */
 typedef struct file_header {
diff --git a/plat/marvell/armada/common/mss/mss_scp_bootloader.c b/plat/marvell/armada/common/mss/mss_scp_bootloader.c
index adf570e..fbede1b 100644
--- a/plat/marvell/armada/common/mss/mss_scp_bootloader.c
+++ b/plat/marvell/armada/common/mss/mss_scp_bootloader.c
@@ -19,25 +19,14 @@
 #include <mss_scp_bootloader.h>
 #include <mss_ipc_drv.h>
 #include <mss_mem.h>
+#include <mss_defs.h>
 #include <mss_scp_bl2_format.h>
 
-#define MSS_DMA_SRCBR(base)		(base + 0xC0)
-#define MSS_DMA_DSTBR(base)		(base + 0xC4)
-#define MSS_DMA_CTRLR(base)		(base + 0xC8)
-#define MSS_M3_RSTCR(base)		(base + 0xFC)
-
-#define MSS_DMA_CTRLR_SIZE_OFFSET	(0)
-#define MSS_DMA_CTRLR_REQ_OFFSET	(15)
-#define MSS_DMA_CTRLR_REQ_SET		(1)
-#define MSS_DMA_CTRLR_ACK_OFFSET	(12)
-#define MSS_DMA_CTRLR_ACK_MASK		(0x1)
-#define MSS_DMA_CTRLR_ACK_READY		(1)
-#define MSS_M3_RSTCR_RST_OFFSET		(0)
-#define MSS_M3_RSTCR_RST_OFF		(1)
-
 #define MSS_DMA_TIMEOUT			1000
 #define MSS_EXTERNAL_SPACE		0x50000000
 #define MSS_EXTERNAL_ADDR_MASK		0xfffffff
+#define MSS_INTERNAL_SPACE		0x40000000
+#define MSS_INTERNAL_ADDR_MASK		0x00ffffff
 
 #define DMA_SIZE			128
 
@@ -60,60 +49,118 @@
 	return 0;
 }
 
-static int mss_image_load(uint32_t src_addr, uint32_t size, uintptr_t mss_regs)
+static int mss_iram_dma_load(uint32_t src_addr, uint32_t size,
+			     uintptr_t mss_regs)
 {
 	uint32_t i, loop_num, timeout;
 
+	/* load image to MSS RAM using DMA */
+	loop_num = (size / DMA_SIZE) + !!(size % DMA_SIZE);
+	for (i = 0; i < loop_num; i++) {
+		/* write source address */
+		mmio_write_32(MSS_DMA_SRCBR(mss_regs),
+			      src_addr + (i * DMA_SIZE));
+		/* write destination address */
+		mmio_write_32(MSS_DMA_DSTBR(mss_regs), (i * DMA_SIZE));
+		/* make sure DMA data is ready before triggering it */
+		dsb();
+		/* set the DMA control register */
+		mmio_write_32(MSS_DMA_CTRLR(mss_regs),
+			      ((MSS_DMA_CTRLR_REQ_SET <<
+				MSS_DMA_CTRLR_REQ_OFFSET) |
+			      (DMA_SIZE << MSS_DMA_CTRLR_SIZE_OFFSET)));
+		/* Poll DMA_ACK at MSS_DMACTLR until it is ready */
+		timeout = MSS_DMA_TIMEOUT;
+		while (timeout > 0U) {
+			if (((mmio_read_32(MSS_DMA_CTRLR(mss_regs)) >>
+					  MSS_DMA_CTRLR_ACK_OFFSET) &
+					  MSS_DMA_CTRLR_ACK_MASK)
+					  == MSS_DMA_CTRLR_ACK_READY) {
+				break;
+			}
+			udelay(50);
+			timeout--;
+		}
+		if (timeout == 0) {
+			ERROR("\nMSS DMA failed (timeout)\n");
+			return 1;
+		}
+	}
+	return 0;
+}
+
+static int mss_image_load(uint32_t src_addr, uint32_t size,
+			  uintptr_t mss_regs, uintptr_t sram)
+{
+	uint32_t chunks = 1; /* !sram case */
+	uint32_t chunk_num;
+	int ret;
+
 	/* Check if the img size is not bigger than ID-RAM size of MSS CM3 */
 	if (size > MSS_IDRAM_SIZE) {
 		ERROR("image is too big to fit into MSS CM3 memory\n");
 		return 1;
 	}
 
-	NOTICE("Loading MSS image from addr. 0x%x Size 0x%x to MSS at 0x%lx\n",
-	       src_addr, size, mss_regs);
-	/* load image to MSS RAM using DMA */
-	loop_num = (size / DMA_SIZE) + (((size & (DMA_SIZE - 1)) == 0) ? 0 : 1);
+	/* The CPx MSS DMA cannot access DRAM directly in secure boot mode
+	 * Copy the MSS FW image to MSS SRAM by the CPU first, then run
+	 * MSS DMA for SRAM to IRAM copy
+	 */
+	if (sram != 0) {
+		chunks = size / MSS_SRAM_SIZE + !!(size % MSS_SRAM_SIZE);
+	}
 
-	for (i = 0; i < loop_num; i++) {
-		/* write destination and source addresses */
-		mmio_write_32(MSS_DMA_SRCBR(mss_regs),
-			      MSS_EXTERNAL_SPACE |
-			      ((src_addr & MSS_EXTERNAL_ADDR_MASK) +
-			      (i * DMA_SIZE)));
-		mmio_write_32(MSS_DMA_DSTBR(mss_regs), (i * DMA_SIZE));
+	NOTICE("%s Loading MSS FW from addr. 0x%x Size 0x%x to MSS at 0x%lx\n",
+	       sram == 0 ? "" : "SECURELY", src_addr, size, mss_regs);
+	for (chunk_num = 0; chunk_num < chunks; chunk_num++) {
+		size_t chunk_size = size;
+		uint32_t img_src = MSS_EXTERNAL_SPACE | /* no SRAM */
+				   (src_addr & MSS_EXTERNAL_ADDR_MASK);
 
-		dsb(); /* make sure DMA data is ready before triggering it */
+		if (sram != 0) {
+			uintptr_t chunk_source =
+				  src_addr + MSS_SRAM_SIZE * chunk_num;
 
-		/* set the DMA control register */
-		mmio_write_32(MSS_DMA_CTRLR(mss_regs), ((MSS_DMA_CTRLR_REQ_SET
-			      << MSS_DMA_CTRLR_REQ_OFFSET) |
-			      (DMA_SIZE << MSS_DMA_CTRLR_SIZE_OFFSET)));
+			if (chunk_num != (size / MSS_SRAM_SIZE)) {
+				chunk_size = MSS_SRAM_SIZE;
+			} else {
+				chunk_size =  size % MSS_SRAM_SIZE;
+			}
 
-		/* Poll DMA_ACK at MSS_DMACTLR until it is ready */
-		timeout = MSS_DMA_TIMEOUT;
-		while (timeout) {
-			if ((mmio_read_32(MSS_DMA_CTRLR(mss_regs)) >>
-			     MSS_DMA_CTRLR_ACK_OFFSET & MSS_DMA_CTRLR_ACK_MASK)
-				== MSS_DMA_CTRLR_ACK_READY) {
+			if (chunk_size == 0) {
 				break;
 			}
 
-			udelay(50);
-			timeout--;
+			VERBOSE("Chunk %d -> SRAM 0x%lx from 0x%lx SZ 0x%lx\n",
+				chunk_num, sram, chunk_source, chunk_size);
+			memcpy((void *)sram, (void *)chunk_source, chunk_size);
+			dsb();
+			img_src = MSS_INTERNAL_SPACE |
+				  (sram & MSS_INTERNAL_ADDR_MASK);
 		}
 
-		if (timeout == 0) {
-			ERROR("\nDMA failed to load MSS image\n");
-			return 1;
+		ret = mss_iram_dma_load(img_src, chunk_size, mss_regs);
+		if (ret != 0) {
+			ERROR("MSS FW chunk %d load failed\n", chunk_num);
+			return ret;
 		}
 	}
 
 	bl2_plat_configure_mss_windows(mss_regs);
 
-	/* Release M3 from reset */
-	mmio_write_32(MSS_M3_RSTCR(mss_regs), (MSS_M3_RSTCR_RST_OFF <<
-		      MSS_M3_RSTCR_RST_OFFSET));
+	if (sram != 0) {
+		/* Wipe the MSS SRAM after using it as copy buffer */
+		memset((void *)sram, 0, MSS_SRAM_SIZE);
+		NOTICE("CP MSS startup is postponed\n");
+		/* FW loaded, but CPU startup postponed until final CP setup */
+		mmio_write_32(sram, MSS_FW_READY_MAGIC);
+		dsb();
+	} else {
+		/* Release M3 from reset */
+		mmio_write_32(MSS_M3_RSTCR(mss_regs),
+			      (MSS_M3_RSTCR_RST_OFF <<
+			       MSS_M3_RSTCR_RST_OFFSET));
+	}
 
 	NOTICE("Done\n");
 
@@ -162,7 +209,7 @@
 	VERBOSE("Send info about the SCP_BL2 image to be transferred to SCP\n");
 
 	ret = mss_image_load(single_img, image_size,
-			     bl2_plat_get_ap_mss_regs(ap_idx));
+			     bl2_plat_get_ap_mss_regs(ap_idx), 0);
 	if (ret != 0) {
 		ERROR("SCP Image load failed\n");
 		return -1;
@@ -218,6 +265,8 @@
 			       cp_index, ap_idx);
 			ret = mss_image_load(single_img, image_size,
 					     bl2_plat_get_cp_mss_regs(
+						     ap_idx, cp_index),
+					     bl2_plat_get_cp_mss_sram(
 						     ap_idx, cp_index));
 			if (ret != 0) {
 				ERROR("SCP Image load failed\n");
diff --git a/plat/marvell/armada/common/mss/mss_scp_bootloader.h b/plat/marvell/armada/common/mss/mss_scp_bootloader.h
index 4950d24..d65354a 100644
--- a/plat/marvell/armada/common/mss/mss_scp_bootloader.h
+++ b/plat/marvell/armada/common/mss/mss_scp_bootloader.h
@@ -10,6 +10,7 @@
 
 int scp_bootloader_transfer(void *image, unsigned int image_size);
 uintptr_t bl2_plat_get_cp_mss_regs(int ap_idx, int cp_idx);
+uintptr_t bl2_plat_get_cp_mss_sram(int ap_idx, int cp_idx);
 uintptr_t bl2_plat_get_ap_mss_regs(int ap_idx);
 uint32_t bl2_plat_get_cp_count(int ap_idx);
 uint32_t bl2_plat_get_ap_count(void);
diff --git a/plat/marvell/octeontx/otx2/t91/t9130/board/dram_port.c b/plat/marvell/octeontx/otx2/t91/t9130/board/dram_port.c
index 0befadf..82ce07b 100644
--- a/plat/marvell/octeontx/otx2/t91/t9130/board/dram_port.c
+++ b/plat/marvell/octeontx/otx2/t91/t9130/board/dram_port.c
@@ -149,7 +149,7 @@
 		i2c_init((void *)MVEBU_CP0_I2C_BASE);
 
 		/* select SPD memory page 0 to access DRAM configuration */
-		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 1);
+		i2c_write(I2C_SPD_P0_ADDR, 0x0, 1, tm->spd_data.all_bytes, 0);
 
 		/* read data from spd */
 		i2c_read(I2C_SPD_ADDR, 0x0, 1, tm->spd_data.all_bytes,
diff --git a/plat/marvell/octeontx/otx2/t91/t9130/board/marvell_plat_config.c b/plat/marvell/octeontx/otx2/t91/t9130/board/marvell_plat_config.c
index 7debd65..fbacf54 100644
--- a/plat/marvell/octeontx/otx2/t91/t9130/board/marvell_plat_config.c
+++ b/plat/marvell/octeontx/otx2/t91/t9130/board/marvell_plat_config.c
@@ -46,15 +46,19 @@
  *****************************************************************************
  */
 struct addr_map_win io_win_memory_map[] = {
+#if (CP_COUNT > 1)
+	/* SB (MCi0) internal regs */
+	{0x00000000f4000000,		0x2000000,	MCI_0_TID},
+#if (CP_COUNT > 2)
+	/* SB (MCi1) internal regs */
+	{0x00000000f6000000,		0x2000000,	MCI_1_TID},
+#endif
+#endif
 #ifndef IMAGE_BLE
 	/* SB (MCi0) PCIe0-2 on CP1 */
 	{0x00000000e2000000,		0x3000000,	MCI_0_TID},
 	/* SB (MCi1) PCIe0-2 on CP2 */
 	{0x00000000e5000000,		0x3000000,	MCI_1_TID},
-	/* SB (MCi0) internal regs */
-	{0x00000000f4000000,		0x2000000,	MCI_0_TID},
-	/* SB (MCi1) internal regs */
-	{0x00000000f6000000,		0x2000000,	MCI_1_TID},
 	/* MCI 0 indirect window */
 	{MVEBU_MCI_REG_BASE_REMAP(0),	0x100000,	MCI_0_TID},
 	/* MCI 1 indirect window */
diff --git a/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/board/marvell_plat_config.c b/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/board/marvell_plat_config.c
new file mode 100644
index 0000000..5bae8eb
--- /dev/null
+++ b/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/board/marvell_plat_config.c
@@ -0,0 +1,224 @@
+/*
+ * Copyright (C) 2018 Marvell International Ltd.
+ * Copyright (C) 2021 Semihalf.
+ *
+ * SPDX-License-Identifier:	BSD-3-Clause
+ * https://spdx.org/licenses
+ */
+
+#include <armada_common.h>
+#include <mvebu_def.h>
+
+/*
+ * If bootrom is currently at BLE there's no need to include the memory
+ * maps structure at this point
+ */
+#ifndef IMAGE_BLE
+
+/*****************************************************************************
+ * AMB Configuration
+ *****************************************************************************
+ */
+struct addr_map_win amb_memory_map_cp0[] = {
+	/* CP0 SPI1 CS0 Direct Mode access */
+	{0xef00,	0x1000000,	AMB_SPI1_CS0_ID},
+};
+
+struct addr_map_win amb_memory_map_cp1[] = {
+	/* CP1 SPI1 CS0 Direct Mode access */
+	{0xe800,	0x1000000,	AMB_SPI1_CS0_ID},
+};
+
+int marvell_get_amb_memory_map(struct addr_map_win **win, uint32_t *size,
+			       uintptr_t base)
+{
+	switch (base) {
+	case MVEBU_CP_REGS_BASE(0):
+		*win = amb_memory_map_cp0;
+		*size = ARRAY_SIZE(amb_memory_map_cp0);
+		return 0;
+	case MVEBU_CP_REGS_BASE(1):
+		*win = amb_memory_map_cp1;
+		*size = ARRAY_SIZE(amb_memory_map_cp1);
+		return 0;
+	case MVEBU_CP_REGS_BASE(2):
+	default:
+		*size = 0;
+		*win = 0;
+		return 1;
+	}
+}
+#endif
+
+/*****************************************************************************
+ * IO WIN Configuration
+ *****************************************************************************
+ */
+struct addr_map_win io_win_memory_map[] = {
+#if (CP_COUNT > 1)
+	/* SB (MCi0) internal regs */
+	{0x00000000f4000000,		0x2000000,	MCI_0_TID},
+	/* SB (MCi0) PCIe0-2 on CP1 */
+	{0x00000000e2000000,		0x7000000,	MCI_0_TID},
+	/*
+	 * Due to lack of sufficient number of IO windows registers,
+	 * below CP1 PCIE configuration must be performed in the
+	 * later firmware stages. It should replace the MCI 0 indirect
+	 * window, which becomes no longer needed.
+	 */
+	/* {0x0000000890000000,		0x30000000,	MCI_0_TID}, */
+#if (CP_COUNT > 2)
+	/* SB (MCi1) internal regs */
+	{0x00000000f6000000,		0x2000000,	MCI_1_TID},
+	/* SB (MCi1) PCIe0-2 on CP2 */
+	{0x00000000e9000000,		0x6000000,	MCI_1_TID},
+	/*
+	 * Due to lack of sufficient number of IO windows registers,
+	 * below CP2 PCIE configuration must be performed in the
+	 * later firmware stages. It should replace the MCI 1 indirect
+	 * window, which becomes no longer needed.
+	 */
+	/* {0x00000008c0000000,		0x30000000,	MCI_1_TID}, */
+#endif
+#endif
+#ifndef IMAGE_BLE
+	/* MCI 0 indirect window */
+	{MVEBU_MCI_REG_BASE_REMAP(0),	0x100000,	MCI_0_TID},
+	/* MCI 1 indirect window */
+	{MVEBU_MCI_REG_BASE_REMAP(1),	0x100000,	MCI_1_TID},
+#endif
+};
+
+/* Global Control Register - window default target */
+uint32_t marvell_get_io_win_gcr_target(int ap_index)
+{
+	/*
+	 * PIDI == iMCIP AP to SB internal MoChi connection.
+	 * In other words CP0
+	 */
+	return PIDI_TID;
+}
+
+int marvell_get_io_win_memory_map(int ap_index, struct addr_map_win **win,
+				  uint32_t *size)
+{
+	*win = io_win_memory_map;
+	if (*win == NULL)
+		*size = 0;
+	else
+		*size = ARRAY_SIZE(io_win_memory_map);
+
+	return 0;
+}
+
+#ifndef IMAGE_BLE
+/*****************************************************************************
+ * IOB Configuration
+ *****************************************************************************
+ */
+struct addr_map_win iob_memory_map_cp0[] = {
+	/* SPI1_CS0 (RUNIT) window */
+	{0x00000000ef000000,	0x1000000,	RUNIT_TID},
+	/* PEX2_X1 window */
+	{0x00000000e1000000,	0x1000000,	PEX2_TID},
+	/* PEX1_X1 window */
+	{0x00000000e0000000,	0x1000000,	PEX1_TID},
+	/* PEX0_X4 window */
+	{0x00000000c0000000,	0x20000000,	PEX0_TID},
+	{0x0000000800000000,	0x90000000,	PEX0_TID},
+};
+
+struct addr_map_win iob_memory_map_cp1[] = {
+	/* SPI1_CS0 (RUNIT) window */
+	{0x00000000e8000000,	0x1000000,	RUNIT_TID},
+	/* PEX2_X1 window */
+	{0x00000000e6000000,	0x2000000,	PEX2_TID},
+	{0x00000008b0000000,	0x10000000,	PEX2_TID},
+	/* PEX1_X1 window */
+	{0x00000000e4000000,	0x2000000,	PEX1_TID},
+	{0x00000008a0000000,	0x10000000,	PEX1_TID},
+	/* PEX0_X2 window */
+	{0x00000000e2000000,	0x2000000,	PEX0_TID},
+	{0x0000000890000000,	0x10000000,	PEX0_TID},
+};
+
+struct addr_map_win iob_memory_map_cp2[] = {
+
+	/* PEX2_X1 window */
+	{0x00000000ed000000,	0x2000000,	PEX2_TID},
+	{0x00000008e0000000,	0x10000000,	PEX2_TID},
+	/* PEX1_X1 window */
+	{0x00000000eb000000,	0x2000000,	PEX1_TID},
+	{0x00000008d0000000,	0x10000000,	PEX1_TID},
+	/* PEX0_X1 window */
+	{0x00000000e9000000,	0x2000000,	PEX0_TID},
+	{0x00000008c0000000,	0x10000000,	PEX0_TID},
+};
+
+int marvell_get_iob_memory_map(struct addr_map_win **win, uint32_t *size,
+			       uintptr_t base)
+{
+	switch (base) {
+	case MVEBU_CP_REGS_BASE(0):
+		*win = iob_memory_map_cp0;
+		*size = ARRAY_SIZE(iob_memory_map_cp0);
+		return 0;
+	case MVEBU_CP_REGS_BASE(1):
+		*win = iob_memory_map_cp1;
+		*size = ARRAY_SIZE(iob_memory_map_cp1);
+		return 0;
+	case MVEBU_CP_REGS_BASE(2):
+		*win = iob_memory_map_cp2;
+		*size = ARRAY_SIZE(iob_memory_map_cp2);
+		return 0;
+	default:
+		*size = 0;
+		*win = 0;
+		return 1;
+	}
+}
+#endif
+
+/*****************************************************************************
+ * CCU Configuration
+ *****************************************************************************
+ */
+struct addr_map_win ccu_memory_map[] = {	/* IO window */
+#ifdef IMAGE_BLE
+	{0x00000000f2000000,	0x6000000,	IO_0_TID}, /* IO window */
+#else
+#if LLC_SRAM
+	{PLAT_MARVELL_LLC_SRAM_BASE, PLAT_MARVELL_LLC_SRAM_SIZE, DRAM_0_TID},
+#endif
+	{0x00000000f2000000,	0xe000000,	IO_0_TID}, /* IO window */
+	{0x00000000c0000000,	0x30000000,	IO_0_TID}, /* IO window */
+	{0x0000000800000000,	0x100000000,    IO_0_TID}, /* IO window */
+	{0x0000002000000000,	0x70e000000,	IO_0_TID}, /* IO for CV-OS */
+#endif
+};
+
+uint32_t marvell_get_ccu_gcr_target(int ap)
+{
+	return DRAM_0_TID;
+}
+
+int marvell_get_ccu_memory_map(int ap_index, struct addr_map_win **win,
+			       uint32_t *size)
+{
+	*win = ccu_memory_map;
+	*size = ARRAY_SIZE(ccu_memory_map);
+
+	return 0;
+}
+
+#ifdef IMAGE_BLE
+/*****************************************************************************
+ * SKIP IMAGE Configuration
+ *****************************************************************************
+ */
+void *plat_get_skip_image_data(void)
+{
+	/* No recovery button on CN-9130 board? */
+	return NULL;
+}
+#endif
diff --git a/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/platform.mk b/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/platform.mk
new file mode 100644
index 0000000..ee55455
--- /dev/null
+++ b/plat/marvell/octeontx/otx2/t91/t9130_cex7_eval/platform.mk
@@ -0,0 +1,33 @@
+#
+# Copyright (C) 2018 Marvell International Ltd.
+# Copyright (C) 2021 Semihalf.
+#
+# SPDX-License-Identifier:	BSD-3-Clause
+# https://spdx.org/licenses
+#
+
+PCI_EP_SUPPORT		:=	0
+
+CP_NUM			:=	1
+$(eval $(call add_define,CP_NUM))
+
+DOIMAGE_SEC     	:=	tools/doimage/secure/sec_img_7K.cfg
+
+MARVELL_MOCHI_DRV	:=	drivers/marvell/mochi/ap807_setup.c
+
+BOARD_DIR		:=	$(shell dirname $(lastword $(MAKEFILE_LIST)))
+
+#
+# CN913X CEx7 Evaluation Board shares the DRAM connectivity
+# and SerDes settings with the CN913X DB - reuse relevant
+# board-specific files.
+#
+T9130_DIR		:=	$(BOARD_DIR)/../t9130
+PLAT_INCLUDES		:=	-I$(T9130_DIR)				\
+				-I$(T9130_DIR)/board
+BLE_PORTING_SOURCES	:=	$(T9130_DIR)/board/dram_port.c		\
+				$(BOARD_DIR)/board/marvell_plat_config.c
+
+include plat/marvell/armada/a8k/common/a8k_common.mk
+
+include plat/marvell/armada/common/marvell_common.mk
diff --git a/plat/marvell/version.mk b/plat/marvell/version.mk
deleted file mode 100644
index e072e12..0000000
--- a/plat/marvell/version.mk
+++ /dev/null
@@ -1 +0,0 @@
-SUBVERSION = devel-18.12.0
diff --git a/plat/mediatek/mt8192/plat_mt_gic.c b/plat/mediatek/common/drivers/gic600/mt_gic_v3.c
similarity index 100%
rename from plat/mediatek/mt8192/plat_mt_gic.c
rename to plat/mediatek/common/drivers/gic600/mt_gic_v3.c
diff --git a/plat/mediatek/mt8192/include/mt_gic_v3.h b/plat/mediatek/common/drivers/gic600/mt_gic_v3.h
similarity index 100%
rename from plat/mediatek/mt8192/include/mt_gic_v3.h
rename to plat/mediatek/common/drivers/gic600/mt_gic_v3.h
diff --git a/plat/mediatek/common/drivers/gpio/mtgpio_common.c b/plat/mediatek/common/drivers/gpio/mtgpio_common.c
new file mode 100644
index 0000000..89977a5
--- /dev/null
+++ b/plat/mediatek/common/drivers/gpio/mtgpio_common.c
@@ -0,0 +1,298 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <drivers/gpio.h>
+#include <lib/mmio.h>
+#include <mtgpio.h>
+#include <platform_def.h>
+
+/******************************************************************************
+ *Macro Definition
+ ******************************************************************************/
+#define GPIO_MODE_BITS		4
+#define MAX_GPIO_MODE_PER_REG	8
+#define MAX_GPIO_REG_BITS	32
+#define DIR_BASE		(GPIO_BASE + 0x000)
+#define DOUT_BASE		(GPIO_BASE + 0x100)
+#define DIN_BASE		(GPIO_BASE + 0x200)
+#define MODE_BASE		(GPIO_BASE + 0x300)
+#define SET			0x4
+#define CLR			0x8
+
+static void mt_set_gpio_dir_chip(uint32_t pin, int dir)
+{
+	uint32_t pos, bit;
+
+	assert(pin < MAX_GPIO_PIN);
+	assert(dir < MT_GPIO_DIR_MAX);
+
+	pos = pin / MAX_GPIO_REG_BITS;
+	bit = pin % MAX_GPIO_REG_BITS;
+
+	if (dir == MT_GPIO_DIR_IN) {
+		mmio_write_32(DIR_BASE + 0x10U * pos + CLR, 1U << bit);
+	} else {
+		mmio_write_32(DIR_BASE + 0x10U * pos + SET, 1U << bit);
+	}
+}
+
+static int mt_get_gpio_dir_chip(uint32_t pin)
+{
+	uint32_t pos, bit;
+	uint32_t reg;
+
+	assert(pin < MAX_GPIO_PIN);
+
+	pos = pin / MAX_GPIO_REG_BITS;
+	bit = pin % MAX_GPIO_REG_BITS;
+
+	reg = mmio_read_32(DIR_BASE + 0x10U * pos);
+	return (((reg & (1U << bit)) != 0U) ? MT_GPIO_DIR_OUT : MT_GPIO_DIR_IN);
+}
+
+static void mt_set_gpio_out_chip(uint32_t pin, int output)
+{
+	uint32_t pos, bit;
+
+	assert(pin < MAX_GPIO_PIN);
+	assert(output < MT_GPIO_OUT_MAX);
+
+	pos = pin / MAX_GPIO_REG_BITS;
+	bit = pin % MAX_GPIO_REG_BITS;
+
+	if (output == MT_GPIO_OUT_ZERO) {
+		mmio_write_32(DOUT_BASE + 0x10U * pos + CLR, 1U << bit);
+	} else {
+		mmio_write_32(DOUT_BASE + 0x10U * pos + SET, 1U << bit);
+	}
+}
+
+static int mt_get_gpio_in_chip(uint32_t pin)
+{
+	uint32_t pos, bit;
+	uint32_t reg;
+
+	assert(pin < MAX_GPIO_PIN);
+
+	pos = pin / MAX_GPIO_REG_BITS;
+	bit = pin % MAX_GPIO_REG_BITS;
+
+	reg = mmio_read_32(DIN_BASE + 0x10U * pos);
+	return (((reg & (1U << bit)) != 0U) ? 1 : 0);
+}
+
+static void mt_gpio_set_spec_pull_pupd(uint32_t pin, int enable,
+			       int select)
+{
+	uintptr_t reg1;
+	uintptr_t reg2;
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	uint32_t bit = gpio_info.bit;
+
+	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
+	reg2 = reg1 + (gpio_info.base & 0xf0);
+	if (enable == MT_GPIO_PULL_ENABLE) {
+		mmio_write_32(reg2 + SET, (1U << bit));
+		if (select == MT_GPIO_PULL_DOWN) {
+			mmio_write_32(reg1 + SET, (1U << bit));
+		} else {
+			mmio_write_32(reg1 + CLR, (1U << bit));
+		}
+	} else {
+		mmio_write_32(reg2 + CLR, (1U << bit));
+		mmio_write_32((reg2 + 0x010U) + CLR, (1U << bit));
+	}
+}
+
+static void mt_gpio_set_pull_pu_pd(uint32_t pin, int enable,
+				 int select)
+{
+	uintptr_t reg1;
+	uintptr_t reg2;
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	uint32_t bit = gpio_info.bit;
+
+	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
+	reg2 = reg1 - (gpio_info.base & 0xf0);
+
+	if (enable == MT_GPIO_PULL_ENABLE) {
+		if (select == MT_GPIO_PULL_DOWN) {
+			mmio_write_32(reg1 + CLR, (1U << bit));
+			mmio_write_32(reg2 + SET, (1U << bit));
+		} else {
+			mmio_write_32(reg2 + CLR, (1U << bit));
+			mmio_write_32(reg1 + SET, (1U << bit));
+		}
+	} else {
+		mmio_write_32(reg1 + CLR, (1U << bit));
+		mmio_write_32(reg2 + CLR, (1U << bit));
+	}
+}
+
+static void mt_gpio_set_pull_chip(uint32_t pin, int enable,
+		   int select)
+{
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	if (gpio_info.flag) {
+		mt_gpio_set_spec_pull_pupd(pin, enable, select);
+	} else {
+		mt_gpio_set_pull_pu_pd(pin, enable, select);
+	}
+}
+
+static int mt_gpio_get_spec_pull_pupd(uint32_t pin)
+{
+	uintptr_t reg1;
+	uintptr_t reg2;
+	uint32_t r0;
+	uint32_t r1;
+
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	uint32_t bit = gpio_info.bit;
+
+	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
+	reg2 = reg1 + (gpio_info.base & 0xf0);
+
+	r0 = (mmio_read_32(reg2) >> bit) & 1U;
+	r1 = (mmio_read_32(reg2 + 0x010) >> bit) & 1U;
+	if (r0 == 0U && r1 == 0U) {
+		return MT_GPIO_PULL_NONE;
+	} else {
+		if (mmio_read_32(reg1) & (1U << bit)) {
+			return MT_GPIO_PULL_DOWN;
+		} else {
+			return MT_GPIO_PULL_UP;
+		}
+	}
+}
+
+static int mt_gpio_get_pull_pu_pd(uint32_t pin)
+{
+	uintptr_t reg1;
+	uintptr_t reg2;
+	uint32_t pu;
+	uint32_t pd;
+
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	uint32_t bit = gpio_info.bit;
+
+	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
+	reg2 = reg1 - (gpio_info.base & 0xf0);
+	pu = (mmio_read_32(reg1) >> bit) & 1U;
+	pd = (mmio_read_32(reg2) >> bit) & 1U;
+	if (pu == 1U) {
+		return MT_GPIO_PULL_UP;
+	} else if (pd == 1U) {
+		return MT_GPIO_PULL_DOWN;
+	} else {
+		return MT_GPIO_PULL_NONE;
+	}
+}
+
+static int mt_gpio_get_pull_chip(uint32_t pin)
+{
+	struct mt_pin_info gpio_info;
+
+	gpio_info = mt_pin_infos[pin];
+	if (gpio_info.flag) {
+		return mt_gpio_get_spec_pull_pupd(pin);
+	} else {
+		return mt_gpio_get_pull_pu_pd(pin);
+	}
+}
+
+static void mt_set_gpio_pull_select_chip(uint32_t pin, int sel)
+{
+	assert(pin < MAX_GPIO_PIN);
+
+	if (sel == MT_GPIO_PULL_NONE) {
+		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_DISABLE, MT_GPIO_PULL_DOWN);
+	} else if (sel == MT_GPIO_PULL_UP) {
+		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_ENABLE, MT_GPIO_PULL_UP);
+	} else if (sel == MT_GPIO_PULL_DOWN) {
+		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_ENABLE, MT_GPIO_PULL_DOWN);
+	}
+}
+
+/* get pull-up or pull-down, regardless of resistor value */
+static int mt_get_gpio_pull_select_chip(uint32_t pin)
+{
+	assert(pin < MAX_GPIO_PIN);
+
+	return mt_gpio_get_pull_chip(pin);
+}
+
+static void mt_set_gpio_dir(int gpio, int direction)
+{
+	mt_set_gpio_dir_chip((uint32_t)gpio, direction);
+}
+
+static int mt_get_gpio_dir(int gpio)
+{
+	uint32_t pin;
+
+	pin = (uint32_t)gpio;
+	return mt_get_gpio_dir_chip(pin);
+}
+
+static void mt_set_gpio_pull(int gpio, int pull)
+{
+	uint32_t pin;
+
+	pin = (uint32_t)gpio;
+	mt_set_gpio_pull_select_chip(pin, pull);
+}
+
+static int mt_get_gpio_pull(int gpio)
+{
+	uint32_t pin;
+
+	pin = (uint32_t)gpio;
+	return mt_get_gpio_pull_select_chip(pin);
+}
+
+static void mt_set_gpio_out(int gpio, int value)
+{
+	uint32_t pin;
+
+	pin = (uint32_t)gpio;
+	mt_set_gpio_out_chip(pin, value);
+}
+
+static int mt_get_gpio_in(int gpio)
+{
+	uint32_t pin;
+
+	pin = (uint32_t)gpio;
+	return mt_get_gpio_in_chip(pin);
+}
+
+const gpio_ops_t mtgpio_ops = {
+	 .get_direction = mt_get_gpio_dir,
+	 .set_direction = mt_set_gpio_dir,
+	 .get_value = mt_get_gpio_in,
+	 .set_value = mt_set_gpio_out,
+	 .set_pull = mt_set_gpio_pull,
+	 .get_pull = mt_get_gpio_pull,
+};
+
+void mt_gpio_init(void)
+{
+	gpio_init(&mtgpio_ops);
+}
diff --git a/plat/mediatek/common/drivers/gpio/mtgpio_common.h b/plat/mediatek/common/drivers/gpio/mtgpio_common.h
new file mode 100644
index 0000000..bf51055
--- /dev/null
+++ b/plat/mediatek/common/drivers/gpio/mtgpio_common.h
@@ -0,0 +1,109 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_GPIO_COMMON_H
+#define MT_GPIO_COMMON_H
+
+#include <stdbool.h>
+#include <stdint.h>
+
+#include <plat/common/common_def.h>
+
+/*  Error Code No. */
+#define RSUCCESS        0
+#define ERACCESS        1
+#define ERINVAL         2
+#define ERWRAPPER       3
+#define MAX_GPIO_PIN    MT_GPIO_BASE_MAX
+
+/* GPIO MODE CONTROL VALUE*/
+typedef enum {
+	GPIO_MODE_UNSUPPORTED = -1,
+	GPIO_MODE_GPIO  = 0,
+	GPIO_MODE_00    = 0,
+	GPIO_MODE_01,
+	GPIO_MODE_02,
+	GPIO_MODE_03,
+	GPIO_MODE_04,
+	GPIO_MODE_05,
+	GPIO_MODE_06,
+	GPIO_MODE_07,
+
+	GPIO_MODE_MAX,
+	GPIO_MODE_DEFAULT = GPIO_MODE_00,
+} GPIO_MODE;
+
+/* GPIO DIRECTION */
+typedef enum {
+	MT_GPIO_DIR_UNSUPPORTED = -1,
+	MT_GPIO_DIR_OUT    = 0,
+	MT_GPIO_DIR_IN     = 1,
+	MT_GPIO_DIR_MAX,
+	MT_GPIO_DIR_DEFAULT = MT_GPIO_DIR_IN,
+} GPIO_DIR;
+
+/* GPIO PULL ENABLE*/
+typedef enum {
+	MT_GPIO_PULL_EN_UNSUPPORTED = -1,
+	MT_GPIO_PULL_DISABLE   = 0,
+	MT_GPIO_PULL_ENABLE    = 1,
+	MT_GPIO_PULL_ENABLE_R0 = 2,
+	MT_GPIO_PULL_ENABLE_R1 = 3,
+	MT_GPIO_PULL_ENABLE_R0R1 = 4,
+
+	MT_GPIO_PULL_EN_MAX,
+	MT_GPIO_PULL_EN_DEFAULT = MT_GPIO_PULL_ENABLE,
+} GPIO_PULL_EN;
+
+/* GPIO PULL-UP/PULL-DOWN*/
+typedef enum {
+	MT_GPIO_PULL_UNSUPPORTED = -1,
+	MT_GPIO_PULL_NONE        = 0,
+	MT_GPIO_PULL_UP          = 1,
+	MT_GPIO_PULL_DOWN        = 2,
+	MT_GPIO_PULL_MAX,
+	MT_GPIO_PULL_DEFAULT = MT_GPIO_PULL_DOWN
+} GPIO_PULL;
+
+/* GPIO OUTPUT */
+typedef enum {
+	MT_GPIO_OUT_UNSUPPORTED = -1,
+	MT_GPIO_OUT_ZERO = 0,
+	MT_GPIO_OUT_ONE  = 1,
+
+	MT_GPIO_OUT_MAX,
+	MT_GPIO_OUT_DEFAULT = MT_GPIO_OUT_ZERO,
+	MT_GPIO_DATA_OUT_DEFAULT = MT_GPIO_OUT_ZERO,  /*compatible with DCT*/
+} GPIO_OUT;
+
+/* GPIO INPUT */
+typedef enum {
+	MT_GPIO_IN_UNSUPPORTED = -1,
+	MT_GPIO_IN_ZERO = 0,
+	MT_GPIO_IN_ONE  = 1,
+
+	MT_GPIO_IN_MAX,
+} GPIO_IN;
+
+#define PIN(_id, _flag, _bit, _base, _offset) {		\
+		.id = _id,				\
+		.flag = _flag,				\
+		.bit = _bit,				\
+		.base = _base,				\
+		.offset = _offset,			\
+	}
+
+struct mt_pin_info {
+	uint8_t id;
+	uint8_t flag;
+	uint8_t bit;
+	uint16_t base;
+	uint16_t offset;
+};
+
+void mt_gpio_init(void);
+uintptr_t mt_gpio_find_reg_addr(uint32_t pin);
+#endif /* MT_GPIO_COMMON_H */
diff --git a/plat/mediatek/common/drivers/pmic_wrap/pmic_wrap_init_v2.c b/plat/mediatek/common/drivers/pmic_wrap/pmic_wrap_init_v2.c
new file mode 100644
index 0000000..d9a79c4
--- /dev/null
+++ b/plat/mediatek/common/drivers/pmic_wrap/pmic_wrap_init_v2.c
@@ -0,0 +1,143 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include "platform_def.h"
+#include "pmic_wrap_init.h"
+
+/* pmic wrap module wait_idle and read polling interval (in microseconds) */
+enum pwrap_polling_interval {
+	WAIT_IDLE_POLLING_DELAY_US	= 1,
+	READ_POLLING_DELAY_US		= 2
+};
+
+static uint32_t pwrap_check_idle(void *wacs_register, uint32_t timeout_us)
+{
+	uint32_t reg_rdata = 0U, retry;
+
+	retry = (timeout_us + WAIT_IDLE_POLLING_DELAY_US) /
+		WAIT_IDLE_POLLING_DELAY_US;
+	while (retry != 0) {
+		udelay(WAIT_IDLE_POLLING_DELAY_US);
+		reg_rdata = mmio_read_32((uintptr_t)wacs_register);
+		/* if last read command timeout,clear vldclr bit
+		 * read command state machine:FSM_REQ-->wfdle-->WFVLDCLR;
+		 * write:FSM_REQ-->idle
+		 */
+		switch (GET_WACS_FSM(reg_rdata)) {
+		case SWINF_FSM_WFVLDCLR:
+			mmio_write_32((uintptr_t)&mtk_pwrap->wacs2_vldclr, 0x1);
+			INFO("WACS_FSM = SWINF_FSM_WFVLDCLR\n");
+			break;
+		case SWINF_FSM_WFDLE:
+			INFO("WACS_FSM = SWINF_FSM_WFDLE\n");
+			break;
+		case SWINF_FSM_REQ:
+			INFO("WACS_FSM = SWINF_FSM_REQ\n");
+			break;
+		case SWINF_FSM_IDLE:
+			goto done;
+		default:
+			break;
+		}
+		retry--;
+	};
+
+done:
+	if (retry == 0) {
+		/* timeout */
+		return E_PWR_WAIT_IDLE_TIMEOUT;
+	}
+
+	return 0U;
+}
+
+static uint32_t pwrap_check_vldclr(void *wacs_register, uint32_t timeout_us)
+{
+	uint32_t reg_rdata = 0U, retry;
+
+	retry = (timeout_us + READ_POLLING_DELAY_US) / READ_POLLING_DELAY_US;
+	while (retry != 0) {
+		udelay(READ_POLLING_DELAY_US);
+		reg_rdata = mmio_read_32((uintptr_t)wacs_register);
+		if (GET_WACS_FSM(reg_rdata) == SWINF_FSM_WFVLDCLR) {
+			break;
+		}
+		retry--;
+	};
+
+	if (retry == 0) {
+		/* timeout */
+		return E_PWR_WAIT_IDLE_TIMEOUT;
+	}
+
+	return 0U;
+}
+
+static int32_t pwrap_wacs2(uint32_t write, uint32_t adr, uint32_t wdata,
+			   uint32_t *rdata, uint32_t init_check)
+{
+	uint32_t reg_rdata, return_value;
+
+	if (init_check != 0) {
+		if ((mmio_read_32((uintptr_t)&mtk_pwrap->init_done) & 0x1) == 0) {
+			ERROR("initialization isn't finished\n");
+			return E_PWR_NOT_INIT_DONE;
+		}
+	}
+
+	/* Wait for Software Interface FSM state to be IDLE. */
+	return_value = pwrap_check_idle(&mtk_pwrap->wacs2_sta,
+					PWRAP_WAIT_IDLE_US);
+	if (return_value != 0) {
+		return return_value;
+	}
+
+	/* Set the write data */
+	if (write == 1) {
+		/* Set the write data. */
+		mmio_write_32((uintptr_t)&mtk_pwrap->wacs2_wdata, wdata);
+	}
+
+	/* Send the command. */
+	mmio_write_32((uintptr_t)&mtk_pwrap->wacs2_cmd, (write << 29) | adr);
+
+	if (write == 0) {
+		/*
+		 * Wait for Software Interface FSM state to be WFVLDCLR,
+		 * read the data and clear the valid flag.
+		 */
+		return_value = pwrap_check_vldclr(&mtk_pwrap->wacs2_sta,
+						  PWRAP_READ_US);
+		if (return_value != 0) {
+			return return_value;
+		}
+
+		if (rdata == NULL) {
+			return E_PWR_INVALID_ARG;
+		}
+
+		reg_rdata = mmio_read_32((uintptr_t)&mtk_pwrap->wacs2_rdata);
+		*rdata = reg_rdata;
+		mmio_write_32((uintptr_t)&mtk_pwrap->wacs2_vldclr, 0x1);
+	}
+
+	return return_value;
+}
+
+/* external API for pmic_wrap user */
+int32_t pwrap_read(uint32_t adr, uint32_t *rdata)
+{
+	return pwrap_wacs2(0, adr, 0, rdata, 1);
+}
+
+int32_t pwrap_write(uint32_t adr, uint32_t wdata)
+{
+	return pwrap_wacs2(1, adr, wdata, 0, 1);
+}
diff --git a/plat/mediatek/common/drivers/rtc/rtc_mt6359p.c b/plat/mediatek/common/drivers/rtc/rtc_mt6359p.c
new file mode 100644
index 0000000..124bc8f
--- /dev/null
+++ b/plat/mediatek/common/drivers/rtc/rtc_mt6359p.c
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <rtc.h>
+
+
+static void RTC_Config_Interface(uint32_t addr, uint16_t data,
+			    uint16_t mask, uint16_t shift)
+{
+	uint16_t pmic_reg;
+
+	pmic_reg = RTC_Read(addr);
+
+	pmic_reg &= ~(mask << shift);
+	pmic_reg |= (data << shift);
+
+	RTC_Write(addr, pmic_reg);
+}
+
+static int32_t rtc_disable_2sec_reboot(void)
+{
+	uint16_t reboot;
+
+	reboot = (RTC_Read(RTC_AL_SEC) & ~RTC_BBPU_2SEC_EN) &
+		 ~RTC_BBPU_AUTO_PDN_SEL;
+	RTC_Write(RTC_AL_SEC, reboot);
+
+	return RTC_Write_Trigger();
+}
+
+static int32_t rtc_enable_k_eosc(void)
+{
+	uint16_t alm_dow, alm_sec;
+	int16_t ret;
+
+	/* Turning on eosc cali mode clock */
+	RTC_Config_Interface(PMIC_RG_SCK_TOP_CKPDN_CON0_CLR, 1,
+			PMIC_RG_RTC_EOSC32_CK_PDN_MASK,
+			PMIC_RG_RTC_EOSC32_CK_PDN_SHIFT);
+
+	alm_sec = RTC_Read(RTC_AL_SEC) & (~RTC_LPD_OPT_MASK);
+	RTC_Write(RTC_AL_SEC, alm_sec);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	RTC_Write(RTC_CON, RTC_LPD_EN);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	RTC_Write(RTC_CON, RTC_LPD_RST);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	RTC_Write(RTC_CON, RTC_LPD_EN);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	RTC_Write(RTC_POWERKEY1, RTC_POWERKEY1_KEY);
+	RTC_Write(RTC_POWERKEY2, RTC_POWERKEY2_KEY);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	/* set RTC EOSC calibration period = 8sec */
+	alm_dow = (RTC_Read(RTC_AL_DOW) & (~RTC_RG_EOSC_CALI_TD_MASK)) |
+		  RTC_RG_EOSC_CALI_TD_8SEC;
+	RTC_Write(RTC_AL_DOW, alm_dow);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	RTC_Write(RTC_BBPU,
+		  RTC_Read(RTC_BBPU) | RTC_BBPU_KEY | RTC_BBPU_RELOAD);
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	/* Enable K EOSC mode :use solution1 of eosc cali to fix mt6359p 32K*/
+	RTC_Write(RTC_AL_YEA, (((RTC_Read(RTC_AL_YEA) | RTC_K_EOSC_RSV_0)
+				& (~RTC_K_EOSC_RSV_1)) | (RTC_K_EOSC_RSV_2)));
+	ret = RTC_Write_Trigger();
+	if (ret == 0) {
+		return 0;
+	}
+
+	INFO("[RTC] RTC_enable_k_eosc\n");
+
+	return 1;
+}
+
+void rtc_power_off_sequence(void)
+{
+	uint16_t bbpu;
+	int16_t ret;
+
+	ret = rtc_disable_2sec_reboot();
+	if (ret == 0) {
+		return;
+	}
+
+	ret = rtc_enable_k_eosc();
+	if (ret == 0) {
+		return;
+	}
+
+	bbpu = RTC_BBPU_KEY | RTC_BBPU_PWREN;
+
+	if (Writeif_unlock() != 0) {
+		RTC_Write(RTC_BBPU,
+			  bbpu | RTC_BBPU_RESET_ALARM | RTC_BBPU_RESET_SPAR);
+		RTC_Write(RTC_AL_MASK, RTC_AL_MASK_DOW);
+		ret = RTC_Write_Trigger();
+		if (ret == 0) {
+			return;
+		}
+		mdelay(1);
+
+		bbpu = RTC_Read(RTC_BBPU);
+
+		if (((bbpu & RTC_BBPU_RESET_ALARM) > 0) ||
+		    ((bbpu & RTC_BBPU_RESET_SPAR) > 0)) {
+			INFO("[RTC] timeout\n");
+		}
+
+		bbpu = RTC_Read(RTC_BBPU) | RTC_BBPU_KEY | RTC_BBPU_RELOAD;
+		RTC_Write(RTC_BBPU, bbpu);
+		ret = RTC_Write_Trigger();
+		if (ret == 0) {
+			return;
+		}
+	}
+}
diff --git a/plat/mediatek/common/drivers/rtc/rtc_mt6359p.h b/plat/mediatek/common/drivers/rtc/rtc_mt6359p.h
new file mode 100644
index 0000000..04726e3
--- /dev/null
+++ b/plat/mediatek/common/drivers/rtc/rtc_mt6359p.h
@@ -0,0 +1,197 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RTC_MT6359P_H
+#define RTC_MT6359P_H
+
+/* RTC registers */
+enum {
+	RTC_BBPU = 0x0588,
+	RTC_IRQ_STA = 0x058A,
+	RTC_IRQ_EN = 0x058C,
+	RTC_CII_EN = 0x058E
+};
+
+enum {
+	RTC_AL_SEC = 0x05A0,
+	RTC_AL_MIN = 0x05A2,
+	RTC_AL_HOU = 0x05A4,
+	RTC_AL_DOM = 0x05A6,
+	RTC_AL_DOW = 0x05A8,
+	RTC_AL_MTH = 0x05AA,
+	RTC_AL_YEA = 0x05AC,
+	RTC_AL_MASK = 0x0590
+};
+
+enum {
+	RTC_OSC32CON = 0x05AE,
+	RTC_CON = 0x05C4,
+	RTC_WRTGR = 0x05C2
+};
+
+enum {
+	RTC_POWERKEY1 = 0x05B0,
+	RTC_POWERKEY2 = 0x05B2
+};
+
+enum {
+	RTC_POWERKEY1_KEY	= 0xA357,
+	RTC_POWERKEY2_KEY	= 0x67D2
+};
+
+enum {
+	RTC_PDN1 = 0x05B4,
+	RTC_PDN2 = 0x05B6,
+	RTC_SPAR0 = 0x05B8,
+	RTC_SPAR1 = 0x05BA,
+	RTC_PROT = 0x05BC,
+	RTC_DIFF = 0x05BE,
+	RTC_CALI = 0x05C0
+};
+
+enum {
+	RTC_OSC32CON_UNLOCK1 = 0x1A57,
+	RTC_OSC32CON_UNLOCK2 = 0x2B68
+};
+
+enum {
+	RTC_LPD_EN = 0x0406,
+	RTC_LPD_RST = 0x040E
+};
+
+enum {
+	RTC_LPD_OPT_XOSC_AND_EOSC_LPD	= 0U << 13,
+	RTC_LPD_OPT_EOSC_LPD		= 1U << 13,
+	RTC_LPD_OPT_XOSC_LPD		= 2U << 13,
+	RTC_LPD_OPT_F32K_CK_ALIVE	= 3U << 13,
+};
+
+#define RTC_LPD_OPT_MASK	(3U << 13)
+
+enum {
+	RTC_PROT_UNLOCK1 = 0x586A,
+	RTC_PROT_UNLOCK2 = 0x9136
+};
+
+enum {
+	RTC_BBPU_PWREN	= 1U << 0,
+	RTC_BBPU_SPAR_SW	= 1U << 1,
+	RTC_BBPU_RESET_SPAR	= 1U << 2,
+	RTC_BBPU_RESET_ALARM	= 1U << 3,
+	RTC_BBPU_CLRPKY	= 1U << 4,
+	RTC_BBPU_RELOAD	= 1U << 5,
+	RTC_BBPU_CBUSY	= 1U << 6
+};
+
+enum {
+	RTC_AL_MASK_SEC = 1U << 0,
+	RTC_AL_MASK_MIN = 1U << 1,
+	RTC_AL_MASK_HOU = 1U << 2,
+	RTC_AL_MASK_DOM = 1U << 3,
+	RTC_AL_MASK_DOW = 1U << 4,
+	RTC_AL_MASK_MTH = 1U << 5,
+	RTC_AL_MASK_YEA = 1U << 6
+};
+
+enum {
+	RTC_BBPU_AUTO_PDN_SEL = 1U << 6,
+	RTC_BBPU_2SEC_CK_SEL = 1U << 7,
+	RTC_BBPU_2SEC_EN = 1U << 8,
+	RTC_BBPU_2SEC_MODE = 0x3 << 9,
+	RTC_BBPU_2SEC_STAT_CLEAR = 1U << 11,
+	RTC_BBPU_2SEC_STAT_STA = 1U << 12
+};
+
+enum {
+	RTC_BBPU_KEY	= 0x43 << 8
+};
+
+enum {
+	RTC_EMBCK_SRC_SEL	= 1 << 8,
+	RTC_EMBCK_SEL_MODE	= 3 << 6,
+	RTC_XOSC32_ENB		= 1 << 5,
+	RTC_REG_XOSC32_ENB	= 1 << 15
+};
+
+enum {
+	RTC_K_EOSC_RSV_0	= 1 << 8,
+	RTC_K_EOSC_RSV_1	= 1 << 9,
+	RTC_K_EOSC_RSV_2	= 1 << 10
+};
+
+enum {
+	RTC_RG_EOSC_CALI_TD_1SEC	= 3 << 5,
+	RTC_RG_EOSC_CALI_TD_2SEC	= 4 << 5,
+	RTC_RG_EOSC_CALI_TD_4SEC	= 5 << 5,
+	RTC_RG_EOSC_CALI_TD_8SEC	= 6 << 5,
+	RTC_RG_EOSC_CALI_TD_16SEC	= 7 << 5,
+	RTC_RG_EOSC_CALI_TD_MASK	= 7 << 5
+};
+
+/* PMIC TOP Register Definition */
+enum {
+	PMIC_RG_TOP_CON = 0x0020,
+	PMIC_RG_TOP_CKPDN_CON1 = 0x0112,
+	PMIC_RG_TOP_CKPDN_CON1_SET = 0x0114,
+	PMIC_RG_TOP_CKPDN_CON1_CLR = 0x0116,
+	PMIC_RG_TOP_CKSEL_CON0 = 0x0118,
+	PMIC_RG_TOP_CKSEL_CON0_SET = 0x011A,
+	PMIC_RG_TOP_CKSEL_CON0_CLR = 0x011C
+};
+
+/* PMIC SCK Register Definition */
+enum {
+	PMIC_RG_SCK_TOP_CKPDN_CON0 = 0x0514,
+	PMIC_RG_SCK_TOP_CKPDN_CON0_SET = 0x0516,
+	PMIC_RG_SCK_TOP_CKPDN_CON0_CLR = 0x0518,
+	PMIC_RG_EOSC_CALI_CON0 = 0x53A
+};
+
+enum {
+	PMIC_EOSC_CALI_START_ADDR = 0x53A
+};
+
+enum {
+	PMIC_EOSC_CALI_START_MASK = 0x1,
+	PMIC_EOSC_CALI_START_SHIFT = 0
+};
+
+/* PMIC DCXO Register Definition */
+enum {
+	PMIC_RG_DCXO_CW00 = 0x0788,
+	PMIC_RG_DCXO_CW02 = 0x0790,
+	PMIC_RG_DCXO_CW08 = 0x079C,
+	PMIC_RG_DCXO_CW09 = 0x079E,
+	PMIC_RG_DCXO_CW09_CLR = 0x07A2,
+	PMIC_RG_DCXO_CW10 = 0x07A4,
+	PMIC_RG_DCXO_CW12 = 0x07A8,
+	PMIC_RG_DCXO_CW13 = 0x07AA,
+	PMIC_RG_DCXO_CW15 = 0x07AE,
+	PMIC_RG_DCXO_CW19 = 0x07B6,
+};
+
+enum {
+	PMIC_RG_SRCLKEN_IN0_HW_MODE_MASK = 0x1,
+	PMIC_RG_SRCLKEN_IN0_HW_MODE_SHIFT = 1,
+	PMIC_RG_SRCLKEN_IN1_HW_MODE_MASK = 0x1,
+	PMIC_RG_SRCLKEN_IN1_HW_MODE_SHIFT = 3,
+	PMIC_RG_RTC_EOSC32_CK_PDN_MASK = 0x1,
+	PMIC_RG_RTC_EOSC32_CK_PDN_SHIFT = 2,
+	PMIC_RG_EOSC_CALI_TD_MASK = 0x7,
+	PMIC_RG_EOSC_CALI_TD_SHIFT = 5,
+	PMIC_RG_XO_EN32K_MAN_MASK = 0x1,
+	PMIC_RG_XO_EN32K_MAN_SHIFT = 0
+};
+
+/* external API */
+uint16_t RTC_Read(uint32_t addr);
+void RTC_Write(uint32_t addr, uint16_t data);
+int32_t rtc_busy_wait(void);
+int32_t RTC_Write_Trigger(void);
+int32_t Writeif_unlock(void);
+void rtc_power_off_sequence(void);
+
+#endif /* RTC_MT6359P_H */
diff --git a/plat/mediatek/common/drivers/timer/mt_timer.c b/plat/mediatek/common/drivers/timer/mt_timer.c
new file mode 100644
index 0000000..0860885
--- /dev/null
+++ b/plat/mediatek/common/drivers/timer/mt_timer.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <lib/mmio.h>
+#include <mt_timer.h>
+#include <platform_def.h>
+
+
+uint64_t normal_time_base;
+uint64_t atf_time_base;
+
+void sched_clock_init(uint64_t normal_base, uint64_t atf_base)
+{
+	normal_time_base += normal_base;
+	atf_time_base = atf_base;
+}
+
+uint64_t sched_clock(void)
+{
+	uint64_t cval;
+	uint64_t rel_base;
+
+	rel_base = read_cntpct_el0() - atf_time_base;
+	cval = ((rel_base * 1000U) / SYS_COUNTER_FREQ_IN_MHZ)
+		- normal_time_base;
+	return cval;
+}
+
+void mt_systimer_init(void)
+{
+	/* Enable access in NS mode */
+	mmio_write_32(CNTWACR_REG, CNT_WRITE_ACCESS_CTL_MASK);
+	mmio_write_32(CNTRACR_REG, CNT_READ_ACCESS_CTL_MASK);
+}
diff --git a/plat/mediatek/common/drivers/timer/mt_timer.h b/plat/mediatek/common/drivers/timer/mt_timer.h
new file mode 100644
index 0000000..b353177
--- /dev/null
+++ b/plat/mediatek/common/drivers/timer/mt_timer.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_TIMER_H
+#define MT_TIMER_H
+
+#define SYSTIMER_BASE       (0x10017000)
+#define CNTCR_REG           (SYSTIMER_BASE + 0x0)
+#define CNTSR_REG           (SYSTIMER_BASE + 0x4)
+#define CNTSYS_L_REG        (SYSTIMER_BASE + 0x8)
+#define CNTSYS_H_REG        (SYSTIMER_BASE + 0xc)
+#define CNTWACR_REG         (SYSTIMER_BASE + 0x10)
+#define CNTRACR_REG         (SYSTIMER_BASE + 0x14)
+
+#define TIEO_EN             (1 << 3)
+#define COMP_15_EN          (1 << 10)
+#define COMP_20_EN          (1 << 11)
+#define COMP_25_EN          (1 << 12)
+
+#define COMP_FEATURE_MASK (COMP_15_EN | COMP_20_EN | COMP_25_EN | TIEO_EN)
+#define COMP_15_MASK (COMP_15_EN)
+#define COMP_20_MASK (COMP_20_EN | TIEO_EN)
+#define COMP_25_MASK (COMP_20_EN | COMP_25_EN)
+
+#define CNT_WRITE_ACCESS_CTL_MASK (0x3FFFFF0U)
+#define CNT_READ_ACCESS_CTL_MASK  (0x3FFFFFFU)
+
+void sched_clock_init(uint64_t normal_base, uint64_t atf_base);
+uint64_t sched_clock(void);
+void mt_systimer_init(void);
+
+#endif /* MT_TIMER_H */
diff --git a/plat/mediatek/common/drivers/uart/uart.c b/plat/mediatek/common/drivers/uart/uart.c
new file mode 100644
index 0000000..b940eb3
--- /dev/null
+++ b/plat/mediatek/common/drivers/uart/uart.c
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/mmio.h>
+#include <uart.h>
+
+static struct mt_uart uart_save_addr[DRV_SUPPORT_UART_PORTS];
+
+static const uint32_t uart_base_addr[DRV_SUPPORT_UART_PORTS] = {
+	UART0_BASE,
+	UART1_BASE
+};
+
+void mt_uart_restore(void)
+{
+	int uart_idx = UART_PORT0;
+	struct mt_uart *uart;
+	unsigned long base;
+
+	/* Must NOT print any debug log before UART restore */
+	for (uart_idx = UART_PORT0; uart_idx < HW_SUPPORT_UART_PORTS;
+	     uart_idx++) {
+
+		uart = &uart_save_addr[uart_idx];
+		base = uart->base;
+
+		mmio_write_32(UART_LCR(base), UART_LCR_MODE_B);
+		mmio_write_32(UART_EFR(base), uart->registers.efr);
+		mmio_write_32(UART_LCR(base), uart->registers.lcr);
+		mmio_write_32(UART_FCR(base), uart->registers.fcr);
+
+		/* baudrate */
+		mmio_write_32(UART_HIGHSPEED(base), uart->registers.highspeed);
+		mmio_write_32(UART_FRACDIV_L(base), uart->registers.fracdiv_l);
+		mmio_write_32(UART_FRACDIV_M(base), uart->registers.fracdiv_m);
+		mmio_write_32(UART_LCR(base),
+			      uart->registers.lcr | UART_LCR_DLAB);
+		mmio_write_32(UART_DLL(base), uart->registers.dll);
+		mmio_write_32(UART_DLH(base), uart->registers.dlh);
+		mmio_write_32(UART_LCR(base), uart->registers.lcr);
+		mmio_write_32(UART_SAMPLE_COUNT(base),
+			      uart->registers.sample_count);
+		mmio_write_32(UART_SAMPLE_POINT(base),
+			      uart->registers.sample_point);
+		mmio_write_32(UART_GUARD(base), uart->registers.guard);
+
+		/* flow control */
+		mmio_write_32(UART_ESCAPE_EN(base), uart->registers.escape_en);
+		mmio_write_32(UART_MCR(base), uart->registers.mcr);
+		mmio_write_32(UART_IER(base), uart->registers.ier);
+		mmio_write_32(UART_SCR(base), uart->registers.scr);
+	}
+}
+
+void mt_uart_save(void)
+{
+	int uart_idx = UART_PORT0;
+	struct mt_uart *uart;
+	unsigned long base;
+
+	for (uart_idx = UART_PORT0; uart_idx < HW_SUPPORT_UART_PORTS;
+	     uart_idx++) {
+
+		uart_save_addr[uart_idx].base = uart_base_addr[uart_idx];
+		base = uart_base_addr[uart_idx];
+		uart = &uart_save_addr[uart_idx];
+		uart->registers.lcr = mmio_read_32(UART_LCR(base));
+
+		mmio_write_32(UART_LCR(base), UART_LCR_MODE_B);
+		uart->registers.efr = mmio_read_32(UART_EFR(base));
+		mmio_write_32(UART_LCR(base), uart->registers.lcr);
+		uart->registers.fcr = mmio_read_32(UART_FCR_RD(base));
+
+		/* baudrate */
+		uart->registers.highspeed = mmio_read_32(UART_HIGHSPEED(base));
+		uart->registers.fracdiv_l = mmio_read_32(UART_FRACDIV_L(base));
+		uart->registers.fracdiv_m = mmio_read_32(UART_FRACDIV_M(base));
+		mmio_write_32(UART_LCR(base),
+			      uart->registers.lcr | UART_LCR_DLAB);
+		uart->registers.dll = mmio_read_32(UART_DLL(base));
+		uart->registers.dlh = mmio_read_32(UART_DLH(base));
+		mmio_write_32(UART_LCR(base), uart->registers.lcr);
+		uart->registers.sample_count = mmio_read_32(
+						UART_SAMPLE_COUNT(base));
+		uart->registers.sample_point = mmio_read_32(
+						UART_SAMPLE_POINT(base));
+		uart->registers.guard = mmio_read_32(UART_GUARD(base));
+
+		/* flow control */
+		uart->registers.escape_en = mmio_read_32(UART_ESCAPE_EN(base));
+		uart->registers.mcr = mmio_read_32(UART_MCR(base));
+		uart->registers.ier = mmio_read_32(UART_IER(base));
+		uart->registers.scr = mmio_read_32(UART_SCR(base));
+	}
+}
+
+void mt_console_uart_cg(int on)
+{
+	if (on == 1) {
+		mmio_write_32(UART_CLOCK_GATE_CLR, UART0_CLOCK_GATE_BIT);
+	} else {
+		mmio_write_32(UART_CLOCK_GATE_SET, UART0_CLOCK_GATE_BIT);
+	}
+}
+
+uint32_t mt_console_uart_cg_status(void)
+{
+	return mmio_read_32(UART_CLOCK_GATE_STA) & UART0_CLOCK_GATE_BIT;
+}
diff --git a/plat/mediatek/common/drivers/uart/uart.h b/plat/mediatek/common/drivers/uart/uart.h
new file mode 100644
index 0000000..ac8b94d
--- /dev/null
+++ b/plat/mediatek/common/drivers/uart/uart.h
@@ -0,0 +1,100 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef UART_H
+#define UART_H
+
+#include <platform_def.h>
+
+/* UART HW information */
+#define HW_SUPPORT_UART_PORTS	2
+#define DRV_SUPPORT_UART_PORTS	2
+
+/* console UART clock cg */
+#define UART_CLOCK_GATE_SET		(INFRACFG_AO_BASE + 0x80)
+#define UART_CLOCK_GATE_CLR		(INFRACFG_AO_BASE + 0x84)
+#define UART_CLOCK_GATE_STA		(INFRACFG_AO_BASE + 0x90)
+#define UART0_CLOCK_GATE_BIT		(1U<<22)
+#define UART1_CLOCK_GATE_BIT		(1U<<23)
+
+/* UART registers */
+#define UART_RBR(_baseaddr)			(_baseaddr + 0x0)
+#define UART_THR(_baseaddr)			(_baseaddr + 0x0)
+#define UART_IER(_baseaddr)			(_baseaddr + 0x4)
+#define UART_IIR(_baseaddr)			(_baseaddr + 0x8)
+#define UART_FCR(_baseaddr)			(_baseaddr + 0x8)
+#define UART_LCR(_baseaddr)			(_baseaddr + 0xc)
+#define UART_MCR(_baseaddr)			(_baseaddr + 0x10)
+#define UART_LSR(_baseaddr)			(_baseaddr + 0x14)
+#define UART_MSR(_baseaddr)			(_baseaddr + 0x18)
+#define UART_SCR(_baseaddr)			(_baseaddr + 0x1c)
+#define UART_DLL(_baseaddr)			(_baseaddr + 0x0)
+#define UART_DLH(_baseaddr)			(_baseaddr + 0x4)
+#define UART_EFR(_baseaddr)			(_baseaddr + 0x8)
+#define UART_XON1(_baseaddr)			(_baseaddr + 0x10)
+#define UART_XON2(_baseaddr)			(_baseaddr + 0x14)
+#define UART_XOFF1(_baseaddr)			(_baseaddr + 0x18)
+#define UART_XOFF2(_baseaddr)			(_baseaddr + 0x1c)
+#define UART_AUTOBAUD(_baseaddr)		(_baseaddr + 0x20)
+#define UART_HIGHSPEED(_baseaddr)		(_baseaddr + 0x24)
+#define UART_SAMPLE_COUNT(_baseaddr)		(_baseaddr + 0x28)
+#define UART_SAMPLE_POINT(_baseaddr)		(_baseaddr + 0x2c)
+#define UART_AUTOBAUD_REG(_baseaddr)		(_baseaddr + 0x30)
+#define UART_RATE_FIX_REG(_baseaddr)		(_baseaddr + 0x34)
+#define UART_AUTO_BAUDSAMPLE(_baseaddr)		(_baseaddr + 0x38)
+#define UART_GUARD(_baseaddr)			(_baseaddr + 0x3c)
+#define UART_ESCAPE_DAT(_baseaddr)		(_baseaddr + 0x40)
+#define UART_ESCAPE_EN(_baseaddr)		(_baseaddr + 0x44)
+#define UART_SLEEP_EN(_baseaddr)		(_baseaddr + 0x48)
+#define UART_DMA_EN(_baseaddr)			(_baseaddr + 0x4c)
+#define UART_RXTRI_AD(_baseaddr)		(_baseaddr + 0x50)
+#define UART_FRACDIV_L(_baseaddr)		(_baseaddr + 0x54)
+#define UART_FRACDIV_M(_baseaddr)		(_baseaddr + 0x58)
+#define UART_FCR_RD(_baseaddr)			(_baseaddr + 0x5C)
+#define UART_USB_RX_SEL(_baseaddr)		(_baseaddr + 0xB0)
+#define UART_SLEEP_REQ(_baseaddr)		(_baseaddr + 0xB4)
+#define UART_SLEEP_ACK(_baseaddr)		(_baseaddr + 0xB8)
+#define UART_SPM_SEL(_baseaddr)			(_baseaddr + 0xBC)
+#define UART_LCR_DLAB				0x0080
+#define UART_LCR_MODE_B				0x00bf
+
+enum uart_port_ID {
+	UART_PORT0 = 0,
+	UART_PORT1
+};
+
+struct mt_uart_register {
+	uint32_t dll;
+	uint32_t dlh;
+	uint32_t ier;
+	uint32_t lcr;
+	uint32_t mcr;
+	uint32_t fcr;
+	uint32_t lsr;
+	uint32_t scr;
+	uint32_t efr;
+	uint32_t highspeed;
+	uint32_t sample_count;
+	uint32_t sample_point;
+	uint32_t fracdiv_l;
+	uint32_t fracdiv_m;
+	uint32_t escape_en;
+	uint32_t guard;
+	uint32_t rx_sel;
+};
+
+struct mt_uart {
+	unsigned long base;
+	struct mt_uart_register registers;
+};
+
+/* external API */
+void mt_uart_save(void);
+void mt_uart_restore(void);
+void mt_console_uart_cg(int on);
+uint32_t mt_console_uart_cg_status(void);
+
+#endif /* __UART_H__ */
diff --git a/plat/mediatek/common/lpm/mt_lp_rm.c b/plat/mediatek/common/lpm/mt_lp_rm.c
new file mode 100644
index 0000000..f3148fe
--- /dev/null
+++ b/plat/mediatek/common/lpm/mt_lp_rm.c
@@ -0,0 +1,110 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <mt_lp_rm.h>
+#include <stddef.h>
+
+struct platform_mt_resource_manager {
+	unsigned int count;
+	struct mt_resource_manager *plat_rm;
+};
+
+static struct platform_mt_resource_manager plat_mt_rm;
+
+int mt_lp_rm_register(struct mt_resource_manager *rm)
+{
+	unsigned int i;
+	struct mt_resource_constraint *const *rc;
+
+	if ((rm == NULL) || (rm->consts == NULL) ||
+	    (plat_mt_rm.plat_rm != NULL)) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	for (i = 0U, rc = rm->consts; *rc != NULL; i++, rc++) {
+		if ((*rc)->init != NULL) {
+			(*rc)->init();
+		}
+	}
+
+	plat_mt_rm.plat_rm = rm;
+	plat_mt_rm.count = i;
+
+	return MT_RM_STATUS_OK;
+}
+
+int mt_lp_rm_reset_constraint(int idx, unsigned int cpuid, int stateid)
+{
+	struct mt_resource_constraint const *rc = NULL;
+
+	if ((plat_mt_rm.plat_rm == NULL) || (idx < 0) ||
+	    (idx >= plat_mt_rm.count)) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	rc = plat_mt_rm.plat_rm->consts[idx];
+
+	if ((rc == NULL) || (rc->reset == NULL)) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	return rc->reset(cpuid, stateid);
+}
+
+int mt_lp_rm_find_and_run_constraint(int idx, unsigned int cpuid,
+				     int stateid, void *priv)
+{
+	int i, res = MT_RM_STATUS_BAD;
+	struct mt_resource_constraint *const *rc;
+	struct mt_resource_manager *rm = plat_mt_rm.plat_rm;
+
+	if ((rm == NULL) || (idx < 0) || (idx >= plat_mt_rm.count)) {
+		return res;
+	}
+
+	/* If subsys clk/mtcmos is on, add block-resource-off flag */
+	if (rm->update != NULL) {
+		res = rm->update(rm->consts, stateid, priv);
+		if (res != 0) {
+			return res;
+		}
+	}
+
+	for (i = idx, rc = (rm->consts + idx); *rc != NULL; i++, rc++) {
+		if (((*rc)->is_valid != NULL) &&
+		    ((*rc)->is_valid(cpuid, stateid))) {
+			if (((*rc)->run != NULL) &&
+			    ((*rc)->run(cpuid, stateid) == 0)) {
+				res = i;
+				break;
+			}
+		}
+	}
+
+	return res;
+}
+
+int mt_lp_rm_do_update(int stateid, int type, void const *p)
+{
+	int res = MT_RM_STATUS_BAD;
+	struct mt_resource_constraint *const *rc;
+	struct mt_resource_manager *rm = plat_mt_rm.plat_rm;
+
+	if (rm == NULL) {
+		return res;
+	}
+
+	for (rc = rm->consts; *rc != NULL; rc++) {
+		if ((*rc)->update != NULL) {
+			res = (*rc)->update(stateid, type, p);
+			if (res != MT_RM_STATUS_OK) {
+				break;
+			}
+		}
+	}
+
+	return res;
+}
diff --git a/plat/mediatek/common/lpm/mt_lp_rm.h b/plat/mediatek/common/lpm/mt_lp_rm.h
new file mode 100644
index 0000000..39759f1
--- /dev/null
+++ b/plat/mediatek/common/lpm/mt_lp_rm.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_LP_RM_H
+#define MT_LP_RM_H
+
+#include <stdbool.h>
+
+#define MT_RM_STATUS_OK		0
+#define MT_RM_STATUS_BAD	-1
+
+enum PLAT_MT_LPM_RC_TYPE {
+	PLAT_RC_UPDATE_CONDITION,
+	PLAT_RC_UPDATE_REMAIN_IRQS
+};
+
+struct mt_resource_constraint {
+	int level;
+	int (*init)(void);
+	bool (*is_valid)(unsigned int cpu, int stateid);
+	int (*update)(int stateid, int type, const void *p);
+	int (*run)(unsigned int cpu, int stateid);
+	int (*reset)(unsigned int cpu, int stateid);
+	unsigned int (*allow)(int stateid);
+};
+
+struct mt_resource_manager {
+	int (*update)(struct mt_resource_constraint **con,
+		      int stateid, void *priv);
+	struct mt_resource_constraint **consts;
+};
+
+extern int mt_lp_rm_register(struct mt_resource_manager *rm);
+extern int mt_lp_rm_find_and_run_constraint(int idx, unsigned int cpuid,
+					    int stateid, void *priv);
+extern int mt_lp_rm_reset_constraint(int constraint_id, unsigned int cpuid,
+				     int stateid);
+extern int mt_lp_rm_do_update(int stateid, int type, void const *p);
+#endif /* MT_LP_RM_H */
diff --git a/plat/mediatek/common/mtk_cirq.c b/plat/mediatek/common/mtk_cirq.c
new file mode 100644
index 0000000..9cf7144
--- /dev/null
+++ b/plat/mediatek/common/mtk_cirq.c
@@ -0,0 +1,549 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/arm/gic_common.h>
+#include <lib/mmio.h>
+
+#include <mt_gic_v3.h>
+#include <mtk_cirq.h>
+
+static struct cirq_events cirq_all_events = {
+	.spi_start = CIRQ_SPI_START,
+};
+static uint32_t already_cloned;
+/*
+ * mt_irq_mask_restore: restore all interrupts
+ * @mask: pointer to struct mtk_irq_mask for storing the original mask value.
+ * Return 0 for success; return negative values for failure.
+ * (This is ONLY used for the idle current measurement by the factory mode.)
+ */
+int mt_irq_mask_restore(struct mtk_irq_mask *mask)
+{
+	if (mask == NULL) {
+		return -1;
+	}
+	if (mask->header != IRQ_MASK_HEADER) {
+		return -1;
+	}
+	if (mask->footer != IRQ_MASK_FOOTER) {
+		return -1;
+	}
+
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x4),
+		mask->mask1);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x8),
+		mask->mask2);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0xc),
+		mask->mask3);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x10),
+		mask->mask4);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x14),
+		mask->mask5);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x18),
+		mask->mask6);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x1c),
+		mask->mask7);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x20),
+		mask->mask8);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x24),
+		mask->mask9);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x28),
+		mask->mask10);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x2c),
+		mask->mask11);
+	 mmio_write_32((BASE_GICD_BASE + GICD_ISENABLER + 0x30),
+		mask->mask12);
+	/* make sure dist changes happen */
+	dsb();
+
+	return 0;
+}
+
+/*
+ * mt_irq_mask_all: disable all interrupts
+ * @mask: pointer to struct mtk_irq_mask for storing the original mask value.
+ * Return 0 for success; return negative values for failure.
+ * (This is ONLY used for the idle current measurement by the factory mode.)
+ */
+int mt_irq_mask_all(struct mtk_irq_mask *mask)
+{
+	if (mask != NULL) {
+		/* for SPI */
+		mask->mask1 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x4));
+		mask->mask2 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x8));
+		mask->mask3 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0xc));
+		mask->mask4 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x10));
+		mask->mask5 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x14));
+		mask->mask6 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x18));
+		mask->mask7 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x1c));
+		mask->mask8 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x20));
+		mask->mask9 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x24));
+		mask->mask10 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x28));
+		mask->mask11 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x2c));
+		mask->mask12 = mmio_read_32((BASE_GICD_BASE +
+			GICD_ISENABLER + 0x30));
+
+		/* for SPI */
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x4),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x8),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0xC),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x10),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x14),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x18),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x1C),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x20),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x24),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x28),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x2c),
+			0xFFFFFFFF);
+		mmio_write_32((BASE_GICD_BASE + GICD_ICENABLER + 0x30),
+			0xFFFFFFFF);
+		/* make sure distributor changes happen */
+		dsb();
+
+		mask->header = IRQ_MASK_HEADER;
+		mask->footer = IRQ_MASK_FOOTER;
+
+		return 0;
+	} else {
+		return -1;
+	}
+}
+
+static uint32_t mt_irq_get_pol(uint32_t irq)
+{
+#ifdef CIRQ_WITH_POLARITY
+	uint32_t reg;
+	uint32_t base = INT_POL_CTL0;
+
+	if (irq < 32U) {
+		return 0;
+	}
+
+	reg = ((irq - 32U) / 32U);
+
+	return  mmio_read_32(base + reg * 4U);
+#else
+	return 0;
+#endif
+}
+
+unsigned int mt_irq_get_sens(unsigned int irq)
+{
+	unsigned int config;
+
+	/*
+	 * 2'b10 edge
+	 * 2'b01 level
+	 */
+	config = mmio_read_32(MT_GIC_BASE + GICD_ICFGR + (irq / 16U) * 4U);
+	config = (config >> (irq % 16U) * 2U) & 0x3;
+
+	return config;
+}
+
+static void collect_all_wakeup_events(void)
+{
+	unsigned int i;
+	uint32_t gic_irq;
+	uint32_t cirq;
+	uint32_t cirq_reg;
+	uint32_t cirq_offset;
+	uint32_t mask;
+	uint32_t pol_mask;
+	uint32_t irq_offset;
+	uint32_t irq_mask;
+
+	if ((cirq_all_events.wakeup_events == NULL) ||
+			cirq_all_events.num_of_events == 0U) {
+		return;
+	}
+
+	for (i = 0U; i < cirq_all_events.num_of_events; i++) {
+		if (cirq_all_events.wakeup_events[i] > 0U) {
+			gic_irq = cirq_all_events.wakeup_events[i];
+			cirq = gic_irq - cirq_all_events.spi_start - 32U;
+			cirq_reg = cirq / 32U;
+			cirq_offset = cirq % 32U;
+			mask = 0x1 << cirq_offset;
+			irq_offset = gic_irq % 32U;
+			irq_mask = 0x1 << irq_offset;
+			/*
+			 * CIRQ default masks all
+			 */
+			cirq_all_events.table[cirq_reg].mask |= mask;
+			/*
+			 * CIRQ default pol is low
+			 */
+			pol_mask = mt_irq_get_pol(
+					cirq_all_events.wakeup_events[i])
+					& irq_mask;
+			/*
+			 * 0 means rising
+			 */
+			if (pol_mask == 0U) {
+				cirq_all_events.table[cirq_reg].pol |= mask;
+			}
+			/*
+			 * CIRQ could monitor edge/level trigger
+			 * cirq register (0: edge, 1: level)
+			 */
+			if (mt_irq_get_sens(cirq_all_events.wakeup_events[i])
+				== SENS_EDGE) {
+				cirq_all_events.table[cirq_reg].sen |= mask;
+			}
+
+			cirq_all_events.table[cirq_reg].used = 1U;
+			cirq_all_events.table[cirq_reg].reg_num = cirq_reg;
+		}
+	}
+}
+
+/*
+ * mt_cirq_set_pol: Set the polarity for the specified SYS_CIRQ number.
+ * @cirq_num: the SYS_CIRQ number to set
+ * @pol: polarity to set
+ * @return:
+ *    0: set pol success
+ *   -1: cirq num is out of range
+ */
+#ifdef CIRQ_WITH_POLARITY
+static int mt_cirq_set_pol(uint32_t cirq_num, uint32_t pol)
+{
+	uint32_t base;
+	uint32_t bit = 1U << (cirq_num % 32U);
+
+	if (cirq_num >= CIRQ_IRQ_NUM) {
+		return -1;
+	}
+
+	if (pol == MT_CIRQ_POL_NEG) {
+		base = (cirq_num / 32U) * 4U + CIRQ_POL_CLR_BASE;
+	} else if (pol == MT_CIRQ_POL_POS) {
+		base = (cirq_num / 32U) * 4U + CIRQ_POL_SET_BASE;
+	} else {
+		return -1;
+	}
+
+	mmio_write_32(base, bit);
+	return 0;
+}
+#endif
+
+/*
+ * mt_cirq_mask: Mask the specified SYS_CIRQ.
+ * @cirq_num: the SYS_CIRQ number to mask
+ * @return:
+ *    0: mask success
+ *   -1: cirq num is out of range
+ */
+static int mt_cirq_mask(uint32_t cirq_num)
+{
+	uint32_t bit = 1U << (cirq_num % 32U);
+
+	if (cirq_num >= CIRQ_IRQ_NUM) {
+		return -1;
+	}
+
+	mmio_write_32((cirq_num / 32U) * 4U + CIRQ_MASK_SET_BASE, bit);
+
+	return 0;
+}
+
+/*
+ * mt_cirq_unmask: Unmask the specified SYS_CIRQ.
+ * @cirq_num: the SYS_CIRQ number to unmask
+ * @return:
+ *    0: umask success
+ *   -1: cirq num is out of range
+ */
+static int mt_cirq_unmask(uint32_t cirq_num)
+{
+	uint32_t bit = 1U << (cirq_num % 32U);
+
+	if (cirq_num >= CIRQ_IRQ_NUM) {
+		return -1;
+	}
+
+	mmio_write_32((cirq_num / 32U) * 4U + CIRQ_MASK_CLR_BASE, bit);
+
+	return 0;
+}
+
+uint32_t mt_irq_get_en(uint32_t irq)
+{
+	uint32_t addr, st, val;
+
+	addr = BASE_GICD_BASE + GICD_ISENABLER + (irq / 32U) * 4U;
+	st = mmio_read_32(addr);
+
+	val = (st >> (irq % 32U)) & 1U;
+
+	return val;
+}
+
+static void __cirq_fast_clone(void)
+{
+	struct cirq_reg *reg;
+	unsigned int i;
+
+	for (i = 0U; i < CIRQ_REG_NUM ; ++i) {
+		uint32_t cirq_bit;
+
+		reg = &cirq_all_events.table[i];
+
+		if (reg->used == 0U) {
+			continue;
+		}
+
+		mmio_write_32(CIRQ_SENS_CLR_BASE + (reg->reg_num * 4U),
+				    reg->sen);
+
+		for (cirq_bit = 0U; cirq_bit < 32U; ++cirq_bit) {
+			uint32_t val, cirq_id;
+			uint32_t gic_id;
+#ifdef CIRQ_WITH_POLARITY
+			uint32_t gic_bit, pol;
+#endif
+			uint32_t en;
+
+			val = ((1U << cirq_bit) & reg->mask);
+
+			if (val == 0U) {
+				continue;
+			}
+
+			cirq_id = (reg->reg_num << 5U) + cirq_bit;
+			gic_id = CIRQ_TO_IRQ_NUM(cirq_id);
+#ifdef CIRQ_WITH_POLARITY
+			gic_bit = (0x1U << ((gic_id - 32U) % 32U));
+			pol = mt_irq_get_pol(gic_id) & gic_bit;
+			if (pol != 0U) {
+				mt_cirq_set_pol(cirq_id, MT_CIRQ_POL_NEG);
+			} else {
+				mt_cirq_set_pol(cirq_id, MT_CIRQ_POL_POS);
+			}
+#endif
+			en = mt_irq_get_en(gic_id);
+			if (en == 1U) {
+				mt_cirq_unmask(cirq_id);
+			} else {
+				mt_cirq_mask(cirq_id);
+			}
+		}
+	}
+}
+
+static void cirq_fast_clone(void)
+{
+	if (already_cloned == 0U) {
+		collect_all_wakeup_events();
+		already_cloned = 1U;
+	}
+	__cirq_fast_clone();
+}
+
+void set_wakeup_sources(uint32_t *list, uint32_t num_of_events)
+{
+	cirq_all_events.num_of_events = num_of_events;
+	cirq_all_events.wakeup_events = list;
+}
+/*
+ * mt_cirq_clone_gic: Copy the setting from GIC to SYS_CIRQ
+ */
+void mt_cirq_clone_gic(void)
+{
+	cirq_fast_clone();
+}
+
+uint32_t mt_irq_get_pending_vec(uint32_t start_irq)
+{
+	uint32_t base = 0U;
+	uint32_t pending_vec = 0U;
+	uint32_t reg = start_irq / 32U;
+	uint32_t LSB_num, MSB_num;
+	uint32_t LSB_vec, MSB_vec;
+
+	base = BASE_GICD_BASE;
+
+	/* if start_irq is not aligned 32, do some assembling */
+	MSB_num = start_irq % 32U;
+	if (MSB_num != 0U) {
+		LSB_num = 32U - MSB_num;
+		LSB_vec = mmio_read_32(base + GICD_ISPENDR +
+			reg * 4U) >> MSB_num;
+		MSB_vec = mmio_read_32(base + GICD_ISPENDR +
+			(reg + 1U) * 4U) << LSB_num;
+		pending_vec = MSB_vec | LSB_vec;
+	} else {
+		pending_vec = mmio_read_32(base + GICD_ISPENDR + reg * 4);
+	}
+
+	return pending_vec;
+}
+
+static int mt_cirq_get_mask_vec(unsigned int i)
+{
+	return mmio_read_32((i * 4U) + CIRQ_MASK_BASE);
+}
+
+/*
+ * mt_cirq_ack_all: Ack all the interrupt on SYS_CIRQ
+ */
+void mt_cirq_ack_all(void)
+{
+	uint32_t ack_vec, pend_vec, mask_vec;
+	unsigned int i;
+
+	for (i = 0; i < CIRQ_CTRL_REG_NUM; i++) {
+		/*
+		 * if a irq is pending & not masked, don't ack it
+		 * , since cirq start irq might not be 32 aligned with gic,
+		 * need an exotic API to get proper vector of pending irq
+		 */
+		pend_vec = mt_irq_get_pending_vec(CIRQ_SPI_START
+			+ (i + 1U) * 32U);
+		mask_vec = mt_cirq_get_mask_vec(i);
+		/* those should be acked are: "not (pending & not masked)",
+		 */
+		ack_vec = (~pend_vec) | mask_vec;
+		mmio_write_32(CIRQ_ACK_BASE + (i * 4U), ack_vec);
+	}
+
+	/*
+	 * make sure all cirq setting take effect
+	 * before doing other things
+	 */
+	dsb();
+}
+/*
+ * mt_cirq_enable: Enable SYS_CIRQ
+ */
+void mt_cirq_enable(void)
+{
+	uint32_t st;
+
+	/* level only */
+	mt_cirq_ack_all();
+
+	st = mmio_read_32(CIRQ_CON);
+	/*
+	 * CIRQ could monitor edge/level trigger
+	 */
+	st |= (CIRQ_CON_EN << CIRQ_CON_EN_BITS);
+
+	mmio_write_32(CIRQ_CON, (st & CIRQ_CON_BITS_MASK));
+}
+
+/*
+ * mt_cirq_disable: Disable SYS_CIRQ
+ */
+void mt_cirq_disable(void)
+{
+	uint32_t st;
+
+	st = mmio_read_32(CIRQ_CON);
+	st &= ~(CIRQ_CON_EN << CIRQ_CON_EN_BITS);
+	mmio_write_32(CIRQ_CON, (st & CIRQ_CON_BITS_MASK));
+}
+
+void mt_irq_unmask_for_sleep_ex(uint32_t irq)
+{
+	uint32_t mask;
+
+	mask = 1U << (irq % 32U);
+
+	mmio_write_32(BASE_GICD_BASE + GICD_ISENABLER +
+		((irq / 32U) * 4U), mask);
+}
+
+void mt_cirq_mask_all(void)
+{
+	unsigned int i;
+
+	for (i = 0U; i < CIRQ_CTRL_REG_NUM; i++) {
+		mmio_write_32(CIRQ_MASK_SET_BASE + (i * 4U), 0xFFFFFFFF);
+	}
+	dsb();
+}
+
+static void cirq_fast_sw_flush(void)
+{
+	struct cirq_reg *reg;
+	unsigned int i;
+
+	for (i = 0U; i < CIRQ_REG_NUM ; ++i) {
+		uint32_t cirq_bit;
+
+		reg = &cirq_all_events.table[i];
+
+		if (reg->used == 0U) {
+			continue;
+		}
+
+		reg->pending = mmio_read_32(CIRQ_STA_BASE +
+			(reg->reg_num << 2U));
+		reg->pending &= reg->mask;
+
+		for (cirq_bit = 0U; cirq_bit < 32U; ++cirq_bit) {
+			uint32_t val, cirq_id;
+
+			val = (1U << cirq_bit) & reg->pending;
+			if (val == 0U) {
+				continue;
+			}
+
+			cirq_id = (reg->reg_num << 5U) + cirq_bit;
+			mt_irq_set_pending(CIRQ_TO_IRQ_NUM(cirq_id));
+			if (CIRQ_TO_IRQ_NUM(cirq_id) == MD_WDT_IRQ_BIT_ID) {
+				INFO("Set MD_WDT_IRQ pending in %s\n",
+					__func__);
+			}
+		}
+	}
+}
+
+/*
+ * mt_cirq_disable: Flush interrupt from SYS_CIRQ to GIC
+ */
+void mt_cirq_flush(void)
+{
+	cirq_fast_sw_flush();
+	mt_cirq_mask_all();
+	mt_cirq_ack_all();
+}
+
+void mt_cirq_sw_reset(void)
+{
+	uint32_t st;
+
+	st = mmio_read_32(CIRQ_CON);
+	st |= (CIRQ_SW_RESET << CIRQ_CON_SW_RST_BITS);
+	mmio_write_32(CIRQ_CON, st);
+}
diff --git a/plat/mediatek/common/mtk_cirq.h b/plat/mediatek/common/mtk_cirq.h
new file mode 100644
index 0000000..6e63bb8
--- /dev/null
+++ b/plat/mediatek/common/mtk_cirq.h
@@ -0,0 +1,122 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_MT_CIRQ_H
+#define PLAT_MT_CIRQ_H
+
+#include <stdint.h>
+#include <platform_def.h>
+
+enum {
+	IRQ_MASK_HEADER = 0xF1F1F1F1,
+	IRQ_MASK_FOOTER = 0xF2F2F2F2
+};
+
+struct mtk_irq_mask {
+	uint32_t header;	/* for error checking */
+	uint32_t mask0;
+	uint32_t mask1;
+	uint32_t mask2;
+	uint32_t mask3;
+	uint32_t mask4;
+	uint32_t mask5;
+	uint32_t mask6;
+	uint32_t mask7;
+	uint32_t mask8;
+	uint32_t mask9;
+	uint32_t mask10;
+	uint32_t mask11;
+	uint32_t mask12;
+	uint32_t footer;	/* for error checking */
+};
+
+/*
+ * Define hardware register
+ */
+#define  CIRQ_STA_BASE         (SYS_CIRQ_BASE + U(0x000))
+#define  CIRQ_ACK_BASE         (SYS_CIRQ_BASE + U(0x080))
+#define  CIRQ_MASK_BASE        (SYS_CIRQ_BASE + U(0x100))
+#define  CIRQ_MASK_SET_BASE    (SYS_CIRQ_BASE + U(0x180))
+#define  CIRQ_MASK_CLR_BASE    (SYS_CIRQ_BASE + U(0x200))
+#define  CIRQ_SENS_BASE        (SYS_CIRQ_BASE + U(0x280))
+#define  CIRQ_SENS_SET_BASE    (SYS_CIRQ_BASE + U(0x300))
+#define  CIRQ_SENS_CLR_BASE    (SYS_CIRQ_BASE + U(0x380))
+#define  CIRQ_POL_BASE         (SYS_CIRQ_BASE + U(0x400))
+#define  CIRQ_POL_SET_BASE     (SYS_CIRQ_BASE + U(0x480))
+#define  CIRQ_POL_CLR_BASE     (SYS_CIRQ_BASE + U(0x500))
+#define  CIRQ_CON              (SYS_CIRQ_BASE + U(0x600))
+
+/*
+ * Register placement
+ */
+#define  CIRQ_CON_EN_BITS           U(0)
+#define  CIRQ_CON_EDGE_ONLY_BITS    U(1)
+#define  CIRQ_CON_FLUSH_BITS        U(2)
+#define  CIRQ_CON_SW_RST_BITS       U(20)
+#define  CIRQ_CON_EVENT_BITS        U(31)
+#define  CIRQ_CON_BITS_MASK         U(0x7)
+
+/*
+ * Register setting
+ */
+#define  CIRQ_CON_EN            U(0x1)
+#define  CIRQ_CON_EDGE_ONLY     U(0x1)
+#define  CIRQ_CON_FLUSH         U(0x1)
+#define  CIRQ_SW_RESET          U(0x1)
+
+/*
+ * Define constant
+ */
+#define  CIRQ_CTRL_REG_NUM      ((CIRQ_IRQ_NUM + 31U) / 32U)
+
+#define  MT_CIRQ_POL_NEG        U(0)
+#define  MT_CIRQ_POL_POS        U(1)
+
+#define IRQ_TO_CIRQ_NUM(irq)  ((irq) - (32U + CIRQ_SPI_START))
+#define CIRQ_TO_IRQ_NUM(cirq) ((cirq) + (32U + CIRQ_SPI_START))
+
+/* GIC sensitive */
+#define SENS_EDGE	U(0x2)
+#define SENS_LEVEL	U(0x1)
+
+
+/*
+ * Define function prototypes.
+ */
+int mt_cirq_test(void);
+void mt_cirq_dump_reg(void);
+int mt_irq_mask_restore(struct mtk_irq_mask *mask);
+int mt_irq_mask_all(struct mtk_irq_mask *mask);
+void mt_cirq_clone_gic(void);
+void mt_cirq_enable(void);
+void mt_cirq_flush(void);
+void mt_cirq_disable(void);
+void mt_irq_unmask_for_sleep_ex(uint32_t irq);
+void set_wakeup_sources(uint32_t *list, uint32_t num_of_events);
+void mt_cirq_sw_reset(void);
+
+struct cirq_reg {
+	uint32_t reg_num;
+	uint32_t used;
+	uint32_t mask;
+	uint32_t pol;
+	uint32_t sen;
+	uint32_t pending;
+	uint32_t the_link;
+};
+
+struct cirq_events {
+	uint32_t num_reg;
+	uint32_t spi_start;
+	uint32_t num_of_events;
+	uint32_t *wakeup_events;
+	struct cirq_reg table[CIRQ_REG_NUM];
+	uint32_t dist_base;
+	uint32_t cirq_base;
+	uint32_t used_reg_head;
+};
+
+#endif /* PLAT_MT_CIRQ_H */
diff --git a/plat/mediatek/common/mtk_plat_common.c b/plat/mediatek/common/mtk_plat_common.c
index f57e435..142b5c9 100644
--- a/plat/mediatek/common/mtk_plat_common.c
+++ b/plat/mediatek/common/mtk_plat_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -139,9 +139,9 @@
 
 int32_t plat_get_soc_version(void)
 {
-	uint32_t manfid = (JEDEC_MTK_BKID << 24U) | (JEDEC_MTK_MFID << 16U);
+	uint32_t manfid = SOC_ID_SET_JEP_106(JEDEC_MTK_BKID, JEDEC_MTK_MFID);
 
-	return (int32_t)(manfid | (SOC_CHIP_ID & 0xFFFFU));
+	return (int32_t)(manfid | (SOC_CHIP_ID & SOC_ID_IMPL_DEF_MASK));
 }
 
 int32_t plat_get_soc_revision(void)
diff --git a/plat/mediatek/common/mtk_sip_svc.h b/plat/mediatek/common/mtk_sip_svc.h
index cd4096e..74b17b6 100644
--- a/plat/mediatek/common/mtk_sip_svc.h
+++ b/plat/mediatek/common/mtk_sip_svc.h
@@ -31,6 +31,14 @@
 #define MTK_SIP_KERNEL_BOOT_AARCH32		0x82000200
 #define MTK_SIP_KERNEL_BOOT_AARCH64		0xC2000200
 
+/* VCORE */
+#define MTK_SIP_VCORE_CONTROL_ARCH32		0x82000506
+#define MTK_SIP_VCORE_CONTROL_ARCH64		0xC2000506
+
+/* APUSYS SMC call */
+#define MTK_SIP_APUSYS_CONTROL_AARCH32		0x8200051E
+#define MTK_SIP_APUSYS_CONTROL_AARCH64		0xC200051E
+
 /* Mediatek SiP Calls error code */
 enum {
 	MTK_SIP_E_SUCCESS = 0,
diff --git a/plat/mediatek/mt8183/bl31_plat_setup.c b/plat/mediatek/mt8183/bl31_plat_setup.c
index e96b4ad..7dac8a4 100644
--- a/plat/mediatek/mt8183/bl31_plat_setup.c
+++ b/plat/mediatek/mt8183/bl31_plat_setup.c
@@ -16,6 +16,7 @@
 #include <drivers/generic_delay_timer.h>
 #include <mcucfg.h>
 #include <mt_gic_v3.h>
+#include <mt_timer.h>
 #include <lib/coreboot.h>
 #include <lib/mmio.h>
 #include <mtk_mcdi.h>
@@ -148,6 +149,8 @@
 	mt_gic_driver_init();
 	mt_gic_init();
 
+	mt_systimer_init();
+
 	/* Init mcsi SF */
 	plat_mtk_cci_init_sf();
 
diff --git a/plat/mediatek/mt8183/drivers/sspm/sspm.c b/plat/mediatek/mt8183/drivers/sspm/sspm.c
index 3917638..6e76124 100644
--- a/plat/mediatek/mt8183/drivers/sspm/sspm.c
+++ b/plat/mediatek/mt8183/drivers/sspm/sspm.c
@@ -149,7 +149,7 @@
 
 	while (sspm_ipi_recv_non_blocking(IPI_ID_PLATFORM,
 					  &ipi_data,
-					  sizeof(ipi_data))
+					  sizeof(ipi_data) / sizeof(uint32_t))
 					  && count) {
 		mdelay(100);
 		count--;
diff --git a/plat/mediatek/mt8183/drivers/timer/mt_timer.c b/plat/mediatek/mt8183/drivers/timer/mt_timer.c
new file mode 100644
index 0000000..0da4815
--- /dev/null
+++ b/plat/mediatek/mt8183/drivers/timer/mt_timer.c
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mcucfg.h>
+#include <mt_timer.h>
+#include <platform_def.h>
+
+static void enable_systimer_compensation(void)
+{
+	unsigned int reg;
+
+	reg = mmio_read_32(CNTCR_REG);
+	reg &= ~COMP_15_EN;
+	reg |= COMP_20_EN;
+	mmio_write_32(CNTCR_REG, reg);
+
+	NOTICE("[systimer] CNTCR_REG(0x%x)\n", mmio_read_32(CNTCR_REG));
+}
+
+void mt_systimer_init(void)
+{
+	/* systimer is default on, so we only enable systimer compensation */
+	enable_systimer_compensation();
+}
diff --git a/plat/mediatek/mt8183/drivers/timer/mt_timer.h b/plat/mediatek/mt8183/drivers/timer/mt_timer.h
new file mode 100644
index 0000000..0b8edc5
--- /dev/null
+++ b/plat/mediatek/mt8183/drivers/timer/mt_timer.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_TIMER_H
+#define MT_TIMER_H
+
+
+#define SYSTIMER_BASE       (0x10017000)
+#define CNTCR_REG           (SYSTIMER_BASE + 0x0)
+#define CNTSR_REG           (SYSTIMER_BASE + 0x4)
+
+#define COMP_15_EN          (1 << 10)
+#define COMP_20_EN          (1 << 11)
+
+void mt_systimer_init(void);
+
+#endif /* MT_TIMER_H */
diff --git a/plat/mediatek/mt8183/drivers/uart/uart.c b/plat/mediatek/mt8183/drivers/uart/uart.c
deleted file mode 100644
index 3c6a980..0000000
--- a/plat/mediatek/mt8183/drivers/uart/uart.c
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright (c) 2019, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <lib/mmio.h>
-#include <uart.h>
-
-static struct mt_uart uart_save_addr[DRV_SUPPORT_UART_PORTS];
-
-static const unsigned int uart_base_addr[DRV_SUPPORT_UART_PORTS] = {
-	UART0_BASE,
-	UART1_BASE
-};
-
-void mt_uart_restore(void)
-{
-	int uart_idx = UART_PORT0;
-	struct mt_uart *uart;
-	unsigned long base;
-
-	/* Must NOT print any debug log before UART restore */
-	for (uart_idx = UART_PORT0; uart_idx < HW_SUPPORT_UART_PORTS;
-	     uart_idx++) {
-
-		uart = &uart_save_addr[uart_idx];
-		base = uart->base;
-
-		mmio_write_32(UART_LCR(base), UART_LCR_MODE_B);
-		mmio_write_32(UART_EFR(base), uart->registers.efr);
-		mmio_write_32(UART_LCR(base), uart->registers.lcr);
-		mmio_write_32(UART_FCR(base), uart->registers.fcr);
-
-		/* baudrate */
-		mmio_write_32(UART_HIGHSPEED(base), uart->registers.highspeed);
-		mmio_write_32(UART_FRACDIV_L(base), uart->registers.fracdiv_l);
-		mmio_write_32(UART_FRACDIV_M(base), uart->registers.fracdiv_m);
-		mmio_write_32(UART_LCR(base),
-			      uart->registers.lcr | UART_LCR_DLAB);
-		mmio_write_32(UART_DLL(base), uart->registers.dll);
-		mmio_write_32(UART_DLH(base), uart->registers.dlh);
-		mmio_write_32(UART_LCR(base), uart->registers.lcr);
-		mmio_write_32(UART_SAMPLE_COUNT(base),
-			      uart->registers.sample_count);
-		mmio_write_32(UART_SAMPLE_POINT(base),
-			      uart->registers.sample_point);
-		mmio_write_32(UART_GUARD(base), uart->registers.guard);
-
-		/* flow control */
-		mmio_write_32(UART_ESCAPE_EN(base), uart->registers.escape_en);
-		mmio_write_32(UART_MCR(base), uart->registers.mcr);
-		mmio_write_32(UART_IER(base), uart->registers.ier);
-		mmio_write_32(UART_SCR(base), uart->registers.scr);
-	}
-}
-
-void mt_uart_save(void)
-{
-	int uart_idx = UART_PORT0;
-	struct mt_uart *uart;
-	unsigned long base;
-
-	for (uart_idx = UART_PORT0; uart_idx < HW_SUPPORT_UART_PORTS;
-	     uart_idx++) {
-
-		uart_save_addr[uart_idx].base = uart_base_addr[uart_idx];
-		base = uart_base_addr[uart_idx];
-		uart = &uart_save_addr[uart_idx];
-		uart->registers.lcr = mmio_read_32(UART_LCR(base));
-
-		mmio_write_32(UART_LCR(base), UART_LCR_MODE_B);
-		uart->registers.efr = mmio_read_32(UART_EFR(base));
-		mmio_write_32(UART_LCR(base), uart->registers.lcr);
-		uart->registers.fcr = mmio_read_32(UART_FCR_RD(base));
-
-		/* baudrate */
-		uart->registers.highspeed = mmio_read_32(UART_HIGHSPEED(base));
-		uart->registers.fracdiv_l = mmio_read_32(UART_FRACDIV_L(base));
-		uart->registers.fracdiv_m = mmio_read_32(UART_FRACDIV_M(base));
-		mmio_write_32(UART_LCR(base),
-			      uart->registers.lcr | UART_LCR_DLAB);
-		uart->registers.dll = mmio_read_32(UART_DLL(base));
-		uart->registers.dlh = mmio_read_32(UART_DLH(base));
-		mmio_write_32(UART_LCR(base), uart->registers.lcr);
-		uart->registers.sample_count = mmio_read_32(
-						UART_SAMPLE_COUNT(base));
-		uart->registers.sample_point = mmio_read_32(
-						UART_SAMPLE_POINT(base));
-		uart->registers.guard = mmio_read_32(UART_GUARD(base));
-
-		/* flow control */
-		uart->registers.escape_en = mmio_read_32(UART_ESCAPE_EN(base));
-		uart->registers.mcr = mmio_read_32(UART_MCR(base));
-		uart->registers.ier = mmio_read_32(UART_IER(base));
-		uart->registers.scr = mmio_read_32(UART_SCR(base));
-	}
-}
-
-void mt_console_uart_cg(int on)
-{
-	if (on)
-		mmio_write_32(UART_CLOCK_GATE_CLR, UART0_CLOCK_GATE_BIT);
-	else
-		mmio_write_32(UART_CLOCK_GATE_SET, UART0_CLOCK_GATE_BIT);
-}
-
-int mt_console_uart_cg_status(void)
-{
-	return mmio_read_32(UART_CLOCK_GATE_STA) & UART0_CLOCK_GATE_BIT;
-}
diff --git a/plat/mediatek/mt8183/drivers/uart/uart.h b/plat/mediatek/mt8183/drivers/uart/uart.h
deleted file mode 100644
index be04c35..0000000
--- a/plat/mediatek/mt8183/drivers/uart/uart.h
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright (c) 2019, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef __UART_H__
-#define __UART_H__
-
-#include <platform_def.h>
-
-/* UART HW information */
-#define HW_SUPPORT_UART_PORTS	2
-#define DRV_SUPPORT_UART_PORTS	2
-
-/* console UART clock cg */
-#define UART_CLOCK_GATE_SET		(INFRACFG_AO_BASE + 0x80)
-#define UART_CLOCK_GATE_CLR		(INFRACFG_AO_BASE + 0x84)
-#define UART_CLOCK_GATE_STA		(INFRACFG_AO_BASE + 0x90)
-#define UART0_CLOCK_GATE_BIT		(1U<<22)
-#define UART1_CLOCK_GATE_BIT		(1U<<23)
-
-/* UART registers */
-#define UART_RBR(_baseaddr)			(_baseaddr + 0x0)
-#define UART_THR(_baseaddr)			(_baseaddr + 0x0)
-#define UART_IER(_baseaddr)			(_baseaddr + 0x4)
-#define UART_IIR(_baseaddr)			(_baseaddr + 0x8)
-#define UART_FCR(_baseaddr)			(_baseaddr + 0x8)
-#define UART_LCR(_baseaddr)			(_baseaddr + 0xc)
-#define UART_MCR(_baseaddr)			(_baseaddr + 0x10)
-#define UART_LSR(_baseaddr)			(_baseaddr + 0x14)
-#define UART_MSR(_baseaddr)			(_baseaddr + 0x18)
-#define UART_SCR(_baseaddr)			(_baseaddr + 0x1c)
-#define UART_DLL(_baseaddr)			(_baseaddr + 0x0)
-#define UART_DLH(_baseaddr)			(_baseaddr + 0x4)
-#define UART_EFR(_baseaddr)			(_baseaddr + 0x8)
-#define UART_XON1(_baseaddr)			(_baseaddr + 0x10)
-#define UART_XON2(_baseaddr)			(_baseaddr + 0x14)
-#define UART_XOFF1(_baseaddr)			(_baseaddr + 0x18)
-#define UART_XOFF2(_baseaddr)			(_baseaddr + 0x1c)
-#define UART_AUTOBAUD(_baseaddr)		(_baseaddr + 0x20)
-#define UART_HIGHSPEED(_baseaddr)		(_baseaddr + 0x24)
-#define UART_SAMPLE_COUNT(_baseaddr)		(_baseaddr + 0x28)
-#define UART_SAMPLE_POINT(_baseaddr)		(_baseaddr + 0x2c)
-#define UART_AUTOBAUD_REG(_baseaddr)		(_baseaddr + 0x30)
-#define UART_RATE_FIX_REG(_baseaddr)		(_baseaddr + 0x34)
-#define UART_AUTO_BAUDSAMPLE(_baseaddr)		(_baseaddr + 0x38)
-#define UART_GUARD(_baseaddr)			(_baseaddr + 0x3c)
-#define UART_ESCAPE_DAT(_baseaddr)		(_baseaddr + 0x40)
-#define UART_ESCAPE_EN(_baseaddr)		(_baseaddr + 0x44)
-#define UART_SLEEP_EN(_baseaddr)		(_baseaddr + 0x48)
-#define UART_DMA_EN(_baseaddr)			(_baseaddr + 0x4c)
-#define UART_RXTRI_AD(_baseaddr)		(_baseaddr + 0x50)
-#define UART_FRACDIV_L(_baseaddr)		(_baseaddr + 0x54)
-#define UART_FRACDIV_M(_baseaddr)		(_baseaddr + 0x58)
-#define UART_FCR_RD(_baseaddr)			(_baseaddr + 0x5C)
-#define UART_USB_RX_SEL(_baseaddr)		(_baseaddr + 0xB0)
-#define UART_SLEEP_REQ(_baseaddr)		(_baseaddr + 0xB4)
-#define UART_SLEEP_ACK(_baseaddr)		(_baseaddr + 0xB8)
-#define UART_SPM_SEL(_baseaddr)			(_baseaddr + 0xBC)
-#define UART_LCR_DLAB				0x0080
-#define UART_LCR_MODE_B				0x00bf
-
-enum uart_port_ID {
-	UART_PORT0 = 0,
-	UART_PORT1
-};
-
-struct mt_uart_register {
-	unsigned int dll;
-	unsigned int dlh;
-	unsigned int ier;
-	unsigned int lcr;
-	unsigned int mcr;
-	unsigned int fcr;
-	unsigned int lsr;
-	unsigned int scr;
-	unsigned int efr;
-	unsigned int highspeed;
-	unsigned int sample_count;
-	unsigned int sample_point;
-	unsigned int fracdiv_l;
-	unsigned int fracdiv_m;
-	unsigned int escape_en;
-	unsigned int guard;
-	unsigned int rx_sel;
-};
-
-struct mt_uart {
-	unsigned long base;
-	struct mt_uart_register registers;
-};
-
-/* external API */
-void mt_uart_save(void);
-void mt_uart_restore(void);
-void mt_console_uart_cg(int on);
-int mt_console_uart_cg_status(void);
-
-#endif /* __UART_H__ */
diff --git a/plat/mediatek/mt8183/platform.mk b/plat/mediatek/mt8183/platform.mk
index 3ccc928..1615cf9 100644
--- a/plat/mediatek/mt8183/platform.mk
+++ b/plat/mediatek/mt8183/platform.mk
@@ -8,17 +8,18 @@
 MTK_PLAT_SOC  := ${MTK_PLAT}/${PLAT}
 
 PLAT_INCLUDES := -I${MTK_PLAT}/common/                            \
+                 -I${MTK_PLAT}/common/drivers/uart/                \
                  -I${MTK_PLAT_SOC}/drivers/                       \
                  -I${MTK_PLAT_SOC}/drivers/emi_mpu/               \
                  -I${MTK_PLAT_SOC}/drivers/devapc/                \
                  -I${MTK_PLAT_SOC}/drivers/mcdi/                  \
                  -I${MTK_PLAT_SOC}/drivers/spmc/                  \
                  -I${MTK_PLAT_SOC}/drivers/gpio/                  \
+                 -I${MTK_PLAT_SOC}/drivers/timer/                 \
                  -I${MTK_PLAT_SOC}/drivers/pmic/                  \
                  -I${MTK_PLAT_SOC}/drivers/spm/                   \
                  -I${MTK_PLAT_SOC}/drivers/sspm/                  \
                  -I${MTK_PLAT_SOC}/drivers/rtc/                   \
-                 -I${MTK_PLAT_SOC}/drivers/uart/                  \
                  -I${MTK_PLAT_SOC}/include/
 
 PLAT_BL_COMMON_SOURCES := lib/xlat_tables/aarch64/xlat_tables.c       \
@@ -44,6 +45,7 @@
                    ${MTK_PLAT}/common/mtk_plat_common.c                  \
                    ${MTK_PLAT}/common/drivers/pmic_wrap/pmic_wrap_init.c \
                    ${MTK_PLAT}/common/drivers/rtc/rtc_common.c           \
+                   ${MTK_PLAT}/common/drivers/uart/uart.c                \
                    ${MTK_PLAT}/common/params_setup.c                     \
                    ${MTK_PLAT_SOC}/aarch64/plat_helpers.S                \
                    ${MTK_PLAT_SOC}/aarch64/platform_common.c             \
@@ -57,7 +59,7 @@
                    ${MTK_PLAT_SOC}/drivers/spm/spm_pmic_wrap.c           \
                    ${MTK_PLAT_SOC}/drivers/spm/spm_suspend.c             \
                    ${MTK_PLAT_SOC}/drivers/gpio/mtgpio.c                 \
-                   ${MTK_PLAT_SOC}/drivers/uart/uart.c                   \
+                   ${MTK_PLAT_SOC}/drivers/timer/mt_timer.c              \
                    ${MTK_PLAT_SOC}/drivers/emi_mpu/emi_mpu.c             \
                    ${MTK_PLAT_SOC}/plat_pm.c                             \
                    ${MTK_PLAT_SOC}/plat_topology.c                       \
diff --git a/plat/mediatek/mt8192/aarch64/platform_common.c b/plat/mediatek/mt8192/aarch64/platform_common.c
index eb1bb44..fc98871 100644
--- a/plat/mediatek/mt8192/aarch64/platform_common.c
+++ b/plat/mediatek/mt8192/aarch64/platform_common.c
@@ -19,6 +19,16 @@
 			MT_DEVICE | MT_RW | MT_SECURE),
 	MAP_REGION_FLAT(MTK_DEV_RNG2_BASE, MTK_DEV_RNG2_SIZE,
 			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(MTK_MCDI_SRAM_BASE, MTK_MCDI_SRAM_MAP_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(APUSYS_SCTRL_REVISER_BASE, APUSYS_SCTRL_REVISER_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(APUSYS_APU_S_S_4_BASE, APUSYS_APU_S_S_4_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(APUSYS_APC_AO_WRAPPER_BASE, APUSYS_APC_AO_WRAPPER_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(APUSYS_NOC_DAPC_AO_BASE, APUSYS_NOC_DAPC_AO_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
 	{ 0 }
 };
 
diff --git a/plat/mediatek/mt8192/bl31_plat_setup.c b/plat/mediatek/mt8192/bl31_plat_setup.c
index 9a01bef..c3cb9a5 100644
--- a/plat/mediatek/mt8192/bl31_plat_setup.c
+++ b/plat/mediatek/mt8192/bl31_plat_setup.c
@@ -11,12 +11,18 @@
 #include <common/bl_common.h>
 #include <common/debug.h>
 #include <common/desc_image_load.h>
+#include <drivers/generic_delay_timer.h>
 #include <drivers/ti/uart/uart_16550.h>
 #include <lib/coreboot.h>
 
 /* Platform Includes */
+#include <devapc/devapc.h>
+#include <emi_mpu/emi_mpu.h>
 #include <gpio/mtgpio.h>
 #include <mt_gic_v3.h>
+#include <mt_spm.h>
+#include <mt_timer.h>
+#include <mtk_dcm.h>
 #include <plat_params.h>
 #include <plat_private.h>
 
@@ -81,10 +87,25 @@
  ******************************************************************************/
 void bl31_platform_setup(void)
 {
+	/* Set dcm on */
+	if (!dcm_set_default()) {
+		ERROR("Failed to set default dcm on!!\n");
+	}
+
+	/* MPU Init */
+	emi_mpu_init();
+
+	/* DAPC Init */
+	devapc_init();
+
 	/* Initialize the GIC driver, CPU and distributor interfaces */
 	mt_gic_driver_init();
 	mt_gic_init();
-	plat_mt8192_gpio_init();
+
+	mt_gpio_init();
+	mt_systimer_init();
+	generic_delay_timer_init();
+	spm_boot_init();
 }
 
 /*******************************************************************************
diff --git a/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.c b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.c
new file mode 100644
index 0000000..782aa5f
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.c
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/console.h>
+#include <lib/mmio.h>
+#include <mtk_apusys.h>
+#include <plat/common/platform.h>
+
+uint64_t apusys_kernel_ctrl(uint64_t x1, uint64_t x2, uint64_t x3, uint64_t x4,
+			    uint32_t *ret1)
+{
+	uint32_t request_ops;
+
+	request_ops = (uint32_t)x1;
+	INFO("[APUSYS] ops=0x%x\n", request_ops);
+
+	switch (request_ops) {
+	case MTK_SIP_APU_START_MCU:
+		/* setup addr[33:32] in reviser */
+		mmio_write_32(REVISER_SECUREFW_CTXT, 0U);
+		mmio_write_32(REVISER_USDRFW_CTXT, 0U);
+
+		/* setup secure sideband */
+		mmio_write_32(AO_SEC_FW,
+			      (SEC_FW_NON_SECURE << SEC_FW_SHIFT_NS) |
+			      (0U << SEC_FW_DOMAIN_SHIFT));
+
+		/* setup boot address */
+		mmio_write_32(AO_MD32_BOOT_CTRL, 0U);
+
+		/* setup pre-define region */
+		mmio_write_32(AO_MD32_PRE_DEFINE,
+			      (PRE_DEFINE_CACHE_TCM << PRE_DEFINE_SHIFT_0G) |
+			      (PRE_DEFINE_CACHE << PRE_DEFINE_SHIFT_1G) |
+			      (PRE_DEFINE_CACHE << PRE_DEFINE_SHIFT_2G) |
+			      (PRE_DEFINE_CACHE << PRE_DEFINE_SHIFT_3G));
+
+		/* release runstall */
+		mmio_write_32(AO_MD32_SYS_CTRL, SYS_CTRL_RUN);
+
+		INFO("[APUSYS] reviser_ctxt=%x,%x\n",
+		     mmio_read_32(REVISER_SECUREFW_CTXT),
+		     mmio_read_32(REVISER_USDRFW_CTXT));
+		INFO("[APUSYS]fw=0x%08x,boot=0x%08x,def=0x%08x,sys=0x%08x\n",
+		     mmio_read_32(AO_SEC_FW),
+		     mmio_read_32(AO_MD32_BOOT_CTRL),
+		     mmio_read_32(AO_MD32_PRE_DEFINE),
+		     mmio_read_32(AO_MD32_SYS_CTRL));
+		break;
+	case MTK_SIP_APU_STOP_MCU:
+		/* hold runstall */
+		mmio_write_32(AO_MD32_SYS_CTRL, SYS_CTRL_STALL);
+
+		INFO("[APUSYS] md32_boot_ctrl=0x%08x,runstall=0x%08x\n",
+		     mmio_read_32(AO_MD32_BOOT_CTRL),
+		     mmio_read_32(AO_MD32_SYS_CTRL));
+		break;
+	default:
+		ERROR("%s, unknown request_ops = %x\n", __func__, request_ops);
+		break;
+	}
+
+	return 0UL;
+}
diff --git a/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.h b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.h
new file mode 100644
index 0000000..95fac4a
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef __MTK_APUSYS_H__
+#define __MTK_APUSYS_H__
+
+#include <stdint.h>
+
+/* setup the SMC command ops */
+#define MTK_SIP_APU_START_MCU	0x00U
+#define MTK_SIP_APU_STOP_MCU	0x01U
+
+/* AO Register */
+#define AO_MD32_PRE_DEFINE	(APUSYS_APU_S_S_4_BASE + 0x00)
+#define AO_MD32_BOOT_CTRL	(APUSYS_APU_S_S_4_BASE + 0x04)
+#define AO_MD32_SYS_CTRL	(APUSYS_APU_S_S_4_BASE + 0x08)
+#define AO_SEC_FW		(APUSYS_APU_S_S_4_BASE + 0x10)
+
+#define PRE_DEFINE_CACHE_TCM	0x3U
+#define PRE_DEFINE_CACHE	0x2U
+#define PRE_DEFINE_SHIFT_0G	0U
+#define PRE_DEFINE_SHIFT_1G	2U
+#define PRE_DEFINE_SHIFT_2G	4U
+#define PRE_DEFINE_SHIFT_3G	6U
+
+#define SEC_FW_NON_SECURE	1U
+#define SEC_FW_SHIFT_NS		4U
+#define SEC_FW_DOMAIN_SHIFT	0U
+
+#define SYS_CTRL_RUN		0U
+#define SYS_CTRL_STALL		1U
+
+/* Reviser Register */
+#define REVISER_SECUREFW_CTXT     (APUSYS_SCTRL_REVISER_BASE + 0x300)
+#define REVISER_USDRFW_CTXT       (APUSYS_SCTRL_REVISER_BASE + 0x304)
+
+uint64_t apusys_kernel_ctrl(uint64_t x1, uint64_t x2, uint64_t x3, uint64_t x4,
+			    uint32_t *ret1);
+#endif /* __MTK_APUSYS_H__ */
diff --git a/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.c b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.c
new file mode 100644
index 0000000..245d512
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.c
@@ -0,0 +1,571 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <mtk_apusys_apc.h>
+#include <mtk_apusys_apc_def.h>
+#include <mtk_plat_common.h>
+#include <platform_def.h>
+
+static const struct APC_DOM_16 APUSYS_NOC_DAPC_AO[] = {
+/* 0~3 */
+APUSYS_APC_AO_ATTR("slv07-0",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv07-1",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv07-2",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv07-3",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+
+/* 16~18 */
+APUSYS_APC_AO_ATTR("slv01-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("slv01-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("slv01-2",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 19~21 */
+APUSYS_APC_AO_ATTR("slv00-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("slv00-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("slv00-2",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 22~26 */
+APUSYS_APC_AO_ATTR("slv02-0",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv02-1",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv02-2",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv02-3",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+APUSYS_APC_AO_ATTR("slv02-4",
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION,
+		NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION),
+};
+
+static int32_t set_slave_noc_dapc(uint32_t slave,
+				  enum APUSYS_APC_DOMAIN_ID domain_id,
+				  enum APUSYS_APC_PERM_TYPE perm)
+{
+	uint32_t apc_register_index;
+	uint32_t apc_set_index;
+	uintptr_t base;
+	uint32_t clr_bit;
+	uint32_t set_bit;
+	int32_t ret;
+
+	if (perm >= PERM_NUM) {
+		ERROR("[NOC_DAPC] perm type:0x%x is not supported!\n", perm);
+		ret = APUSYS_APC_ERR_PERMISSION_NOT_SUPPORTED;
+		goto exit;
+	}
+
+	apc_register_index = slave / APUSYS_NOC_DAPC_AO_SLAVE_NUM_IN_1_DOM;
+	apc_set_index = slave % APUSYS_NOC_DAPC_AO_SLAVE_NUM_IN_1_DOM;
+
+	clr_bit = 0xFFFFFFFF ^ (0x3U << (apc_set_index * 2));
+	set_bit = perm << (apc_set_index * 2);
+
+	if ((slave < APUSYS_NOC_DAPC_AO_SLAVE_NUM) &&
+	    (domain_id < APUSYS_NOC_DAPC_AO_DOM_NUM)) {
+		base = APUSYS_NOC_DAPC_AO_BASE +
+		       (domain_id * 0x40) + (apc_register_index * 4);
+		apuapc_writel(apuapc_readl(base) & clr_bit, base);
+		apuapc_writel(apuapc_readl(base) | set_bit, base);
+		ret = APUSYS_APC_OK;
+	} else {
+		ERROR("[NOC_DAPC] %s: %s, %s:0x%x, %s:0x%x\n",
+		      __func__, "out of boundary",
+		      "slave", slave,
+		      "domain_id", domain_id);
+		ret = APUSYS_APC_ERR_OUT_OF_BOUNDARY;
+	}
+
+exit:
+	return ret;
+}
+
+static void dump_apusys_noc_dapc(void)
+{
+	uint32_t reg_num;
+	uint32_t d, i;
+
+	reg_num = APUSYS_NOC_DAPC_AO_SLAVE_NUM /
+		  APUSYS_NOC_DAPC_AO_SLAVE_NUM_IN_1_DOM;
+	for (d = 0U; d < APUSYS_NOC_DAPC_AO_DOM_NUM; d++) {
+		for (i = 0U; i <= reg_num; i++) {
+			INFO("[NOCDAPC] D%d_APC_%d: 0x%x\n", d, i,
+			     apuapc_readl(APUSYS_NOC_DAPC_AO_BASE +
+			     (d * 0x40) + (i * 4)));
+		}
+	}
+
+	INFO("[NOCDAPC] APC_CON: 0x%x\n", apuapc_readl(APUSYS_NOC_DAPC_CON));
+}
+
+static const struct APC_DOM_16 APUSYS_AO_Devices[] = {
+
+/* 0 */
+APUSYS_APC_AO_ATTR("apusys_ao-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apusys_ao-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apusys_ao-2",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apusys_ao-3",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apusys_ao-4",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apusys_ao-5",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("md32_apb_s-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("md32_apb_s-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("md32_apb_s-2",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("md32_debug_apb",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+APUSYS_APC_AO_ATTR("apu_conn_config",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_sctrl_reviser",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_sema_stimer",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_emi_config",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_adl",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_edma_lite0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_edma_lite1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_edma0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_edma0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_dapc_ao",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+APUSYS_APC_AO_ATTR("apu_dapc",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("infra_bcrm",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apb_dbg_ctl",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("noc_dapc",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_noc_bcrm",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_noc_config",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vpu_core0_config-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vpu_core0_config-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vpu_core1_config-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vpu_core1_config-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+APUSYS_APC_AO_ATTR("mdla0_apb-0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("mdla0_apb-1",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("mdla0_apb-2",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("mdla0_apb-3",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_iommu0_r0",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_iommu0_r1",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_iommu0_r2",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_iommu0_r3",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_iommu0_r4",
+		SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("apu_rsi2_config",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+APUSYS_APC_AO_ATTR("apu_ssc2_config",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vp6_core0_debug_apb",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+APUSYS_APC_AO_ATTR("vp6_core1_debug_apb",
+		NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+		FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+};
+
+static int32_t set_slave_apc(uint32_t slave,
+			     enum APUSYS_APC_DOMAIN_ID domain_id,
+			     enum APUSYS_APC_PERM_TYPE perm)
+{
+	uint32_t apc_register_index;
+	uint32_t apc_set_index;
+	uintptr_t base;
+	uint32_t clr_bit;
+	uint32_t set_bit;
+	int32_t ret;
+
+	if (perm >= PERM_NUM) {
+		ERROR("[APUAPC] perm type:0x%x is not supported!\n", perm);
+		ret = APUSYS_APC_ERR_PERMISSION_NOT_SUPPORTED;
+		goto exit;
+	}
+
+	apc_register_index = slave / APUSYS_APC_SYS0_AO_SLAVE_NUM_IN_1_DOM;
+	apc_set_index = slave % APUSYS_APC_SYS0_AO_SLAVE_NUM_IN_1_DOM;
+
+	clr_bit = 0xFFFFFFFF ^ (0x3U << (apc_set_index * 2));
+	set_bit = perm << (apc_set_index * 2);
+
+	if ((slave < APUSYS_APC_SYS0_AO_SLAVE_NUM) &&
+	    (domain_id < APUSYS_APC_SYS0_AO_DOM_NUM)) {
+		base = APUSYS_APC_AO_BASE +
+		       (domain_id * 0x40) + (apc_register_index * 4);
+		apuapc_writel(apuapc_readl(base) & clr_bit, base);
+		apuapc_writel(apuapc_readl(base) | set_bit, base);
+		ret = APUSYS_APC_OK;
+	} else {
+		ERROR("[APUAPC] %s: %s, %s:0x%x, %s:0x%x\n",
+		      __func__, "out of boundary",
+		      "slave", slave,
+		      "domain_id", domain_id);
+		ret = APUSYS_APC_ERR_OUT_OF_BOUNDARY;
+	}
+
+exit:
+	return ret;
+}
+
+static void dump_apusys_ao_apc(void)
+{
+	uint32_t reg_num;
+	uint32_t d, i;
+
+	reg_num = APUSYS_APC_SYS0_AO_SLAVE_NUM /
+		  APUSYS_APC_SYS0_AO_SLAVE_NUM_IN_1_DOM;
+	for (d = 0U; d < APUSYS_APC_SYS0_AO_DOM_NUM; d++) {
+		for (i = 0U; i <= reg_num; i++) {
+			INFO("[APUAPC] D%d_APC_%d: 0x%x\n", d, i,
+			     apuapc_readl(APUSYS_APC_AO_BASE +
+			     (d * 0x40) + (i * 4)));
+		}
+	}
+	INFO("[APUAPC] APC_CON: 0x%x\n", apuapc_readl(APUSYS_APC_CON));
+}
+
+static int32_t set_apusys_noc_dapc(void)
+{
+	int32_t ret = 0;
+	uint32_t i;
+	uint32_t index;
+
+	for (i = 0U; i < ARRAY_SIZE(APUSYS_NOC_DAPC_AO); i++) {
+		if (i < APUSYS_NOC_DAPC_GAP_BOUNDARY) {
+			index = i;
+		} else {
+			index = i + APUSYS_NOC_DAPC_JUMP_GAP;
+		}
+		ret += set_slave_noc_dapc(index, DOMAIN_0,
+				APUSYS_NOC_DAPC_AO[i].d0_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_1,
+				APUSYS_NOC_DAPC_AO[i].d1_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_2,
+				APUSYS_NOC_DAPC_AO[i].d2_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_3,
+				APUSYS_NOC_DAPC_AO[i].d3_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_4,
+				APUSYS_NOC_DAPC_AO[i].d4_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_5,
+				APUSYS_NOC_DAPC_AO[i].d5_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_6,
+				APUSYS_NOC_DAPC_AO[i].d6_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_7,
+				APUSYS_NOC_DAPC_AO[i].d7_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_8,
+				APUSYS_NOC_DAPC_AO[i].d8_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_9,
+				APUSYS_NOC_DAPC_AO[i].d9_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_10,
+				APUSYS_NOC_DAPC_AO[i].d10_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_11,
+				APUSYS_NOC_DAPC_AO[i].d11_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_12,
+				APUSYS_NOC_DAPC_AO[i].d12_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_13,
+				APUSYS_NOC_DAPC_AO[i].d13_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_14,
+				APUSYS_NOC_DAPC_AO[i].d14_permission);
+		ret += set_slave_noc_dapc(index, DOMAIN_15,
+				APUSYS_NOC_DAPC_AO[i].d15_permission);
+	}
+
+	return ret;
+}
+
+static int32_t set_apusys_ao_apc(void)
+{
+	int32_t ret = 0;
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(APUSYS_AO_Devices); i++) {
+		ret += set_slave_apc(i, DOMAIN_0,
+				APUSYS_AO_Devices[i].d0_permission);
+		ret += set_slave_apc(i, DOMAIN_1,
+				APUSYS_AO_Devices[i].d1_permission);
+		ret += set_slave_apc(i, DOMAIN_2,
+				APUSYS_AO_Devices[i].d2_permission);
+		ret += set_slave_apc(i, DOMAIN_3,
+				APUSYS_AO_Devices[i].d3_permission);
+		ret += set_slave_apc(i, DOMAIN_4,
+				APUSYS_AO_Devices[i].d4_permission);
+		ret += set_slave_apc(i, DOMAIN_5,
+				APUSYS_AO_Devices[i].d5_permission);
+		ret += set_slave_apc(i, DOMAIN_6,
+				APUSYS_AO_Devices[i].d6_permission);
+		ret += set_slave_apc(i, DOMAIN_7,
+				APUSYS_AO_Devices[i].d7_permission);
+		ret += set_slave_apc(i, DOMAIN_8,
+				APUSYS_AO_Devices[i].d8_permission);
+		ret += set_slave_apc(i, DOMAIN_9,
+				APUSYS_AO_Devices[i].d9_permission);
+		ret += set_slave_apc(i, DOMAIN_10,
+				APUSYS_AO_Devices[i].d10_permission);
+		ret += set_slave_apc(i, DOMAIN_11,
+				APUSYS_AO_Devices[i].d11_permission);
+		ret += set_slave_apc(i, DOMAIN_12,
+				APUSYS_AO_Devices[i].d12_permission);
+		ret += set_slave_apc(i, DOMAIN_13,
+				APUSYS_AO_Devices[i].d13_permission);
+		ret += set_slave_apc(i, DOMAIN_14,
+				APUSYS_AO_Devices[i].d14_permission);
+		ret += set_slave_apc(i, DOMAIN_15,
+				APUSYS_AO_Devices[i].d15_permission);
+	}
+
+	return ret;
+}
+
+static void set_apusys_apc_lock(void)
+{
+	uint32_t set_bit = 1U << APUSYS_APC_SYS0_LOCK_BIT_APU_SCTRL_REVISER;
+
+	/* Lock apu_sctrl_reviser */
+	set_bit = set_bit | (1U << APUSYS_APC_SYS0_LOCK_BIT_APUSYS_AO_5);
+	apuapc_writel(set_bit, APUSYS_SYS0_APC_LOCK_0);
+}
+
+void set_apusys_apc(void)
+{
+	int32_t ret = 0;
+
+	/* Check violation status */
+	INFO("[APUAPC] vio %d\n", apuapc_readl(APUSYS_APC_CON) & 0x80000000);
+
+	/* Initial Permission */
+	ret = set_apusys_ao_apc();
+	INFO("[APUAPC] %s - %s!\n", "set_apusys_ao_apc",
+	     ret ? "FAILED" : "SUCCESS");
+
+	/* Lock */
+	set_apusys_apc_lock();
+
+	/* Initial NoC Permission */
+	ret = set_apusys_noc_dapc();
+	INFO("[APUAPC] %s - %s!\n", "set_apusys_noc_dapc",
+	     ret ? "FAILED" : "SUCCESS");
+
+	/* Dump Permission */
+	dump_apusys_ao_apc();
+	dump_apusys_noc_dapc();
+
+	INFO("[APUAPC] %s done\n", __func__);
+}
diff --git a/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.h b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.h
new file mode 100644
index 0000000..ff7a9fa
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef __MTK_APUSYS_APC_H__
+#define __MTK_APUSYS_APC_H__
+
+void set_apusys_apc(void);
+
+#endif /* __MTK_APUSYS_APC_H__ */
diff --git a/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc_def.h b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc_def.h
new file mode 100644
index 0000000..b392d6a
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/apusys/mtk_apusys_apc_def.h
@@ -0,0 +1,110 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef __MTK_APUSYS_APC_DEF_H__
+#define __MTK_APUSYS_APC_DEF_H__
+
+#include <lib/mmio.h>
+
+enum APUSYS_APC_ERR_STATUS {
+	APUSYS_APC_OK = 0x0,
+
+	APUSYS_APC_ERR_GENERIC = 0x1000,
+	APUSYS_APC_ERR_INVALID_CMD = 0x1001,
+	APUSYS_APC_ERR_SLAVE_TYPE_NOT_SUPPORTED = 0x1002,
+	APUSYS_APC_ERR_SLAVE_IDX_NOT_SUPPORTED = 0x1003,
+	APUSYS_APC_ERR_DOMAIN_NOT_SUPPORTED = 0x1004,
+	APUSYS_APC_ERR_PERMISSION_NOT_SUPPORTED = 0x1005,
+	APUSYS_APC_ERR_OUT_OF_BOUNDARY = 0x1006,
+	APUSYS_APC_ERR_REQ_TYPE_NOT_SUPPORTED = 0x1007,
+};
+
+enum APUSYS_APC_PERM_TYPE {
+	NO_PROTECTION = 0U,
+	SEC_RW_ONLY = 1U,
+	SEC_RW_NS_R = 2U,
+	FORBIDDEN = 3U,
+	PERM_NUM = 4U,
+};
+
+enum APUSYS_APC_DOMAIN_ID {
+	DOMAIN_0 = 0U,
+	DOMAIN_1 = 1U,
+	DOMAIN_2 = 2U,
+	DOMAIN_3 = 3U,
+	DOMAIN_4 = 4U,
+	DOMAIN_5 = 5U,
+	DOMAIN_6 = 6U,
+	DOMAIN_7 = 7U,
+	DOMAIN_8 = 8U,
+	DOMAIN_9 = 9U,
+	DOMAIN_10 = 10U,
+	DOMAIN_11 = 11U,
+	DOMAIN_12 = 12U,
+	DOMAIN_13 = 13U,
+	DOMAIN_14 = 14U,
+	DOMAIN_15 = 15U,
+};
+
+struct APC_DOM_16 {
+	unsigned char d0_permission;
+	unsigned char d1_permission;
+	unsigned char d2_permission;
+	unsigned char d3_permission;
+	unsigned char d4_permission;
+	unsigned char d5_permission;
+	unsigned char d6_permission;
+	unsigned char d7_permission;
+	unsigned char d8_permission;
+	unsigned char d9_permission;
+	unsigned char d10_permission;
+	unsigned char d11_permission;
+	unsigned char d12_permission;
+	unsigned char d13_permission;
+	unsigned char d14_permission;
+	unsigned char d15_permission;
+};
+
+#define APUSYS_APC_AO_ATTR(DEV_NAME, PERM_ATTR0, PERM_ATTR1, \
+		PERM_ATTR2, PERM_ATTR3, PERM_ATTR4, PERM_ATTR5, \
+		PERM_ATTR6, PERM_ATTR7, PERM_ATTR8, PERM_ATTR9, \
+		PERM_ATTR10, PERM_ATTR11, PERM_ATTR12, PERM_ATTR13, \
+		PERM_ATTR14, PERM_ATTR15) \
+	{(unsigned char)PERM_ATTR0, (unsigned char)PERM_ATTR1, \
+	(unsigned char)PERM_ATTR2, (unsigned char)PERM_ATTR3, \
+	(unsigned char)PERM_ATTR4, (unsigned char)PERM_ATTR5, \
+	(unsigned char)PERM_ATTR6, (unsigned char)PERM_ATTR7, \
+	(unsigned char)PERM_ATTR8, (unsigned char)PERM_ATTR9, \
+	(unsigned char)PERM_ATTR10, (unsigned char)PERM_ATTR11, \
+	(unsigned char)PERM_ATTR12, (unsigned char)PERM_ATTR13, \
+	(unsigned char)PERM_ATTR14, (unsigned char)PERM_ATTR15}
+
+#define apuapc_writel(VAL, REG)		mmio_write_32((uintptr_t)REG, VAL)
+#define apuapc_readl(REG)		mmio_read_32((uintptr_t)REG)
+
+/* APUSYS APC AO  Registers */
+#define APUSYS_APC_AO_BASE            APUSYS_APC_AO_WRAPPER_BASE
+#define APUSYS_APC_CON                (APUSYS_APC_AO_BASE + 0x00F00)
+#define APUSYS_SYS0_APC_LOCK_0        (APUSYS_APC_AO_BASE + 0x00700)
+
+/* APUSYS NOC_DPAC_AO Registers */
+#define APUSYS_NOC_DAPC_CON	      (APUSYS_NOC_DAPC_AO_BASE + 0x00F00)
+
+#define APUSYS_NOC_DAPC_GAP_BOUNDARY    4U
+#define APUSYS_NOC_DAPC_JUMP_GAP        12U
+
+#define APUSYS_APC_SYS0_AO_SLAVE_NUM_IN_1_DOM       16U
+#define APUSYS_APC_SYS0_AO_DOM_NUM                  16U
+#define APUSYS_APC_SYS0_AO_SLAVE_NUM                59U
+
+#define APUSYS_APC_SYS0_LOCK_BIT_APU_SCTRL_REVISER  11U
+#define APUSYS_APC_SYS0_LOCK_BIT_APUSYS_AO_5        5U
+
+#define APUSYS_NOC_DAPC_AO_SLAVE_NUM_IN_1_DOM       16U
+#define APUSYS_NOC_DAPC_AO_DOM_NUM                  16U
+#define APUSYS_NOC_DAPC_AO_SLAVE_NUM                27U
+
+#endif /* __MTK_APUSYS_APC_DEF_H__ */
diff --git a/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.c b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.c
new file mode 100644
index 0000000..dd8bf4e
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.c
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <mtk_dcm.h>
+#include <mtk_dcm_utils.h>
+
+static void dcm_armcore(bool mode)
+{
+	dcm_mp_cpusys_top_bus_pll_div_dcm(mode);
+	dcm_mp_cpusys_top_cpu_pll_div_0_dcm(mode);
+	dcm_mp_cpusys_top_cpu_pll_div_1_dcm(mode);
+}
+
+static void dcm_mcusys(bool on)
+{
+	dcm_mp_cpusys_top_adb_dcm(on);
+	dcm_mp_cpusys_top_apb_dcm(on);
+	dcm_mp_cpusys_top_cpubiu_dcm(on);
+	dcm_mp_cpusys_top_misc_dcm(on);
+	dcm_mp_cpusys_top_mp0_qdcm(on);
+	dcm_cpccfg_reg_emi_wfifo(on);
+	dcm_mp_cpusys_top_last_cor_idle_dcm(on);
+}
+
+static void dcm_stall(bool on)
+{
+	dcm_mp_cpusys_top_core_stall_dcm(on);
+	dcm_mp_cpusys_top_fcm_stall_dcm(on);
+}
+
+static bool check_dcm_state(void)
+{
+	bool ret = true;
+
+	ret &= dcm_mp_cpusys_top_bus_pll_div_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on();
+
+	ret &= dcm_mp_cpusys_top_adb_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_apb_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpubiu_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_misc_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_mp0_qdcm_is_on();
+	ret &= dcm_cpccfg_reg_emi_wfifo_is_on();
+	ret &= dcm_mp_cpusys_top_last_cor_idle_dcm_is_on();
+
+	ret &= dcm_mp_cpusys_top_core_stall_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_fcm_stall_dcm_is_on();
+
+	return ret;
+}
+
+bool dcm_set_default(void)
+{
+	dcm_armcore(true);
+	dcm_mcusys(true);
+	dcm_stall(true);
+
+	return check_dcm_state();
+}
diff --git a/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.h b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.h
new file mode 100644
index 0000000..ee98d0e
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_DCM_H
+#define MTK_DCM_H
+
+#include <stdbool.h>
+
+bool dcm_set_default(void);
+
+#endif /* #ifndef MTK_DCM_H */
diff --git a/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.c b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.c
new file mode 100644
index 0000000..15a700c
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.c
@@ -0,0 +1,562 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mtk_dcm_utils.h>
+
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_MASK (BIT(17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_MASK (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18) | \
+			BIT(21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_MASK (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18))
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_ON (BIT(17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_ON (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18) | \
+			BIT(21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_ON (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18))
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_OFF ((0x0 << 17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_OFF ((0x0 << 15) | \
+			(0x0 << 16) | \
+			(0x0 << 17) | \
+			(0x0 << 18) | \
+			(0x0 << 21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_OFF ((0x0 << 15) | \
+			(0x0 << 16) | \
+			(0x0 << 17) | \
+			(0x0 << 18))
+
+bool dcm_mp_cpusys_top_adb_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_ADB_DCM_CFG0) &
+		MP_CPUSYS_TOP_ADB_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG0_ON);
+	ret &= ((mmio_read_32(MP_ADB_DCM_CFG4) &
+		MP_CPUSYS_TOP_ADB_DCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG1_ON);
+	ret &= ((mmio_read_32(MCUSYS_DCM_CFG0) &
+		MP_CPUSYS_TOP_ADB_DCM_REG2_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG2_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_adb_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_adb_dcm'" */
+		mmio_clrsetbits_32(MP_ADB_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_ON);
+		mmio_clrsetbits_32(MP_ADB_DCM_CFG4,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_ON);
+		mmio_clrsetbits_32(MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_adb_dcm'" */
+		mmio_clrsetbits_32(MP_ADB_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_OFF);
+		mmio_clrsetbits_32(MP_ADB_DCM_CFG4,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_OFF);
+		mmio_clrsetbits_32(MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_APB_DCM_REG0_MASK (BIT(5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_MASK (BIT(8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_MASK (BIT(16))
+#define MP_CPUSYS_TOP_APB_DCM_REG0_ON (BIT(5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_ON (BIT(8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_ON (BIT(16))
+#define MP_CPUSYS_TOP_APB_DCM_REG0_OFF ((0x0 << 5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_OFF ((0x0 << 8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_OFF ((0x0 << 16))
+
+bool dcm_mp_cpusys_top_apb_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG0_ON);
+	ret &= ((mmio_read_32(MCUSYS_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG1_ON);
+	ret &= ((mmio_read_32(MP0_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG2_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG2_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_apb_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_apb_dcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG0_ON);
+		mmio_clrsetbits_32(MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG1_ON);
+		mmio_clrsetbits_32(MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG2_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_apb_dcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG0_OFF);
+		mmio_clrsetbits_32(MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG1_OFF);
+		mmio_clrsetbits_32(MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG2_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_bus_pll_div_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(BUS_PLLDIV_CFG) &
+		MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_bus_pll_div_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_bus_pll_div_dcm'" */
+		mmio_clrsetbits_32(BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_bus_pll_div_dcm'" */
+		mmio_clrsetbits_32(BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK (BIT(0))
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON (BIT(0))
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_OFF ((0x0 << 0))
+
+bool dcm_mp_cpusys_top_core_stall_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP0_DCM_CFG7) &
+		MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_core_stall_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_core_stall_dcm'" */
+		mmio_clrsetbits_32(MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_core_stall_dcm'" */
+		mmio_clrsetbits_32(MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK ((0xffff << 0))
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON ((0xffff << 0))
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_OFF ((0x0 << 0))
+
+bool dcm_mp_cpusys_top_cpubiu_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MCSI_DCM0) &
+		MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpubiu_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpubiu_dcm'" */
+		mmio_clrsetbits_32(MCSI_DCM0,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpubiu_dcm'" */
+		mmio_clrsetbits_32(MCSI_DCM0,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPU_PLLDIV_CFG0) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_0_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_0_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG0,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_0_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG0,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPU_PLLDIV_CFG1) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_1_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_1_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG1,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_1_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG1,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_2_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPU_PLLDIV_CFG2) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_2_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_2_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG2,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_2_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG2,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_2_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_3_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPU_PLLDIV_CFG3) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_3_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_3_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG3,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_3_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG3,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_3_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_MASK (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_ON (BIT(11))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_OFF ((0x0 << 11))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_4_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPU_PLLDIV_CFG4) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_4_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_4_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG4,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_4_dcm'" */
+		mmio_clrsetbits_32(CPU_PLLDIV_CFG4,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_4_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK (BIT(4))
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON (BIT(4))
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_OFF ((0x0 << 4))
+
+bool dcm_mp_cpusys_top_fcm_stall_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP0_DCM_CFG7) &
+		MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_fcm_stall_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_fcm_stall_dcm'" */
+		mmio_clrsetbits_32(MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_fcm_stall_dcm'" */
+		mmio_clrsetbits_32(MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK ((0x1U << 31))
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON ((0x1U << 31))
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_OFF ((0x0U << 31))
+
+bool dcm_mp_cpusys_top_last_cor_idle_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(BUS_PLLDIV_CFG) &
+		MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_last_cor_idle_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_last_cor_idle_dcm'" */
+		mmio_clrsetbits_32(BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_last_cor_idle_dcm'" */
+		mmio_clrsetbits_32(BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_MASK (BIT(1) | \
+			BIT(4))
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_ON (BIT(1) | \
+			BIT(4))
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_OFF ((0x0 << 1) | \
+			(0x0 << 4))
+
+bool dcm_mp_cpusys_top_misc_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_MISC_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MISC_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_misc_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_misc_dcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_misc_dcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK (BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_ON (BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_ON (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_OFF ((0x0 << 3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_OFF ((0x0 << 0) | \
+			(0x0 << 1) | \
+			(0x0 << 2) | \
+			(0x0 << 3))
+
+bool dcm_mp_cpusys_top_mp0_qdcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MP0_QDCM_REG0_ON);
+	ret &= ((mmio_read_32(MP0_DCM_CFG0) &
+		MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MP0_QDCM_REG1_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_mp0_qdcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_mp0_qdcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_ON);
+		mmio_clrsetbits_32(MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_mp0_qdcm'" */
+		mmio_clrsetbits_32(MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_OFF);
+		mmio_clrsetbits_32(MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_OFF);
+	}
+}
+
+#define CPCCFG_REG_EMI_WFIFO_REG0_MASK (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define CPCCFG_REG_EMI_WFIFO_REG0_ON (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define CPCCFG_REG_EMI_WFIFO_REG0_OFF ((0x0 << 0) | \
+			(0x0 << 1) | \
+			(0x0 << 2) | \
+			(0x0 << 3))
+
+bool dcm_cpccfg_reg_emi_wfifo_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(EMI_WFIFO) &
+		CPCCFG_REG_EMI_WFIFO_REG0_MASK) ==
+		(unsigned int) CPCCFG_REG_EMI_WFIFO_REG0_ON);
+
+	return ret;
+}
+
+void dcm_cpccfg_reg_emi_wfifo(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'cpccfg_reg_emi_wfifo'" */
+		mmio_clrsetbits_32(EMI_WFIFO,
+			CPCCFG_REG_EMI_WFIFO_REG0_MASK,
+			CPCCFG_REG_EMI_WFIFO_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'cpccfg_reg_emi_wfifo'" */
+		mmio_clrsetbits_32(EMI_WFIFO,
+			CPCCFG_REG_EMI_WFIFO_REG0_MASK,
+			CPCCFG_REG_EMI_WFIFO_REG0_OFF);
+	}
+}
+
diff --git a/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.h b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.h
new file mode 100644
index 0000000..1cf7834
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dcm/mtk_dcm_utils.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_DCM_UTILS_H
+#define MTK_DCM_UTILS_H
+
+#include <stdbool.h>
+
+#include <mtk_dcm.h>
+#include <platform_def.h>
+
+/* Base */
+#define MP_CPUSYS_TOP_BASE	(MCUCFG_BASE + 0x8000)
+#define CPCCFG_REG_BASE		(MCUCFG_BASE + 0xA800)
+
+/* Register Definition */
+#define CPU_PLLDIV_CFG0		(MP_CPUSYS_TOP_BASE + 0x22a0)
+#define CPU_PLLDIV_CFG1		(MP_CPUSYS_TOP_BASE + 0x22a4)
+#define CPU_PLLDIV_CFG2		(MP_CPUSYS_TOP_BASE + 0x22a8)
+#define CPU_PLLDIV_CFG3		(MP_CPUSYS_TOP_BASE + 0x22ac)
+#define CPU_PLLDIV_CFG4		(MP_CPUSYS_TOP_BASE + 0x22b0)
+#define BUS_PLLDIV_CFG		(MP_CPUSYS_TOP_BASE + 0x22e0)
+#define MCSI_DCM0		(MP_CPUSYS_TOP_BASE + 0x2440)
+#define MP_ADB_DCM_CFG0		(MP_CPUSYS_TOP_BASE + 0x2500)
+#define MP_ADB_DCM_CFG4		(MP_CPUSYS_TOP_BASE + 0x2510)
+#define MP_MISC_DCM_CFG0	(MP_CPUSYS_TOP_BASE + 0x2518)
+#define MCUSYS_DCM_CFG0		(MP_CPUSYS_TOP_BASE + 0x25c0)
+#define EMI_WFIFO		(CPCCFG_REG_BASE + 0x100)
+#define MP0_DCM_CFG0		(MP_CPUSYS_TOP_BASE + 0x4880)
+#define MP0_DCM_CFG7		(MP_CPUSYS_TOP_BASE + 0x489c)
+
+/* MP_CPUSYS_TOP */
+bool dcm_mp_cpusys_top_adb_dcm_is_on(void);
+void dcm_mp_cpusys_top_adb_dcm(bool on);
+bool dcm_mp_cpusys_top_apb_dcm_is_on(void);
+void dcm_mp_cpusys_top_apb_dcm(bool on);
+bool dcm_mp_cpusys_top_bus_pll_div_dcm_is_on(void);
+void dcm_mp_cpusys_top_bus_pll_div_dcm(bool on);
+bool dcm_mp_cpusys_top_core_stall_dcm_is_on(void);
+void dcm_mp_cpusys_top_core_stall_dcm(bool on);
+bool dcm_mp_cpusys_top_cpubiu_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpubiu_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_0_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_1_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_2_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_2_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_3_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_3_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_4_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_4_dcm(bool on);
+bool dcm_mp_cpusys_top_fcm_stall_dcm_is_on(void);
+void dcm_mp_cpusys_top_fcm_stall_dcm(bool on);
+bool dcm_mp_cpusys_top_last_cor_idle_dcm_is_on(void);
+void dcm_mp_cpusys_top_last_cor_idle_dcm(bool on);
+bool dcm_mp_cpusys_top_misc_dcm_is_on(void);
+void dcm_mp_cpusys_top_misc_dcm(bool on);
+bool dcm_mp_cpusys_top_mp0_qdcm_is_on(void);
+void dcm_mp_cpusys_top_mp0_qdcm(bool on);
+/* CPCCFG_REG */
+bool dcm_cpccfg_reg_emi_wfifo_is_on(void);
+void dcm_cpccfg_reg_emi_wfifo(bool on);
+
+#endif
diff --git a/plat/mediatek/mt8192/drivers/devapc/devapc.c b/plat/mediatek/mt8192/drivers/devapc/devapc.c
new file mode 100644
index 0000000..b11f272
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/devapc/devapc.c
@@ -0,0 +1,2847 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <drivers/console.h>
+#include <lib/mmio.h>
+
+#include <devapc.h>
+#include <mtk_apusys_apc.h>
+
+/* Infra_ao */
+static const struct APC_INFRA_PERI_DOM_16 INFRA_AO_SYS0_Devices[] = {
+
+/* 0 */
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-5",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-6",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-7",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MFG_S_S-8",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S-4",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("APU_S_S-5",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MCUSYS_CFGREG_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MCUSYS_CFGREG_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MCUSYS_CFGREG_APB_S-2",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MCUSYS_CFGREG_APB_S-3",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("MCUSYS_CFGREG_APB_S-4",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_INFRA_AO_SYS0_ATTR("L3C_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("L3C_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS0_ATTR("PCIE_AXI_S",
+			NO_PROTECTION, NO_PROTECTION, FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+static const struct APC_INFRA_PERI_DOM_4 INFRA_AO_SYS1_Devices[] = {
+
+/* 0 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-5",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-6",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-7",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-8",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-9",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-10",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-11",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-12",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-13",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-14",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-15",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-16",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-17",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-18",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-19",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-20",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-21",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-22",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-23",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-24",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-25",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-26",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-27",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-28",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-29",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-30",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-31",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-32",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-33",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-34",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-35",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-36",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-37",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-38",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-39",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-100",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-101",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-102",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-103",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-104",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-105",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-106",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-107",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-108",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-109",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 50 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-110",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-111",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-112",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-113",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-114",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-115",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-116",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-117",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-118",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-119",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 60 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-120",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-121",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-122",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-123",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-124",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-125",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-126",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-127",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-128",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-129",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 70 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-130",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-131",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-132",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-133",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-134",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-135",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-136",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-137",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-138",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-139",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 80 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-140",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-141",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-142",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-143",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-200",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     NO_PROTECTION),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-201",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     NO_PROTECTION),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-202",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-203",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     NO_PROTECTION),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-204",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-205",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 90 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-206",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-207",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-300",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-301",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-302",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     NO_PROTECTION),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-303",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-304",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-305",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-306",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-307",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 100 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-400",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-401",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-402",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-403",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-404",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-405",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-406",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-407",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-408",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-409",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 110 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-410",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-411",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-412",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-413",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-414",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-415",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-416",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-417",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-418",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-419",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 120 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-420",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-421",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-422",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-423",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-424",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-425",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-426",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-427",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-428",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-429",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 130 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-430",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-431",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-432",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-433",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-434",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-435",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-436",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-437",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-438",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-439",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 140 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-440",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-441",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-442",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-443",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-444",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-445",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-446",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-447",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-448",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-449",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 150 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-450",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-451",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-452",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-453",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-454",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-455",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-456",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-457",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-458",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-459",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 160 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-460",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-461",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-462",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-463",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-464",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-465",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-466",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-467",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-468",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-469",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 170 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-470",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-471",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-472",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-473",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-474",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-475",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-476",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-477",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-478",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-479",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 180 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-480",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-481",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-482",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-483",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-484",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-485",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-486",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-487",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-488",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-489",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 190 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-490",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-491",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-492",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-493",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-494",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-495",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-496",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-497",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-498",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-499",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 200 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-500",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-501",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-502",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-503",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-504",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-505",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-506",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-507",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-508",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-509",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 210 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-510",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-511",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-512",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-513",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-514",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-515",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-516",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-517",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-518",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-519",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 220 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-520",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-521",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-522",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-523",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-524",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-525",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-526",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-527",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-528",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-529",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 230 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-530",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-531",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-532",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-533",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-534",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-535",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-536",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-537",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-538",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-539",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 240 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-540",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-541",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-542",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-543",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-544",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-545",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-546",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-547",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-548",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-549",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 250 */
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-550",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-551",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-552",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-553",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-554",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS1_ATTR("MM_S_S-555",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+static const struct APC_INFRA_PERI_DOM_4 INFRA_AO_SYS2_Devices[] = {
+
+/* 0 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-556",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-557",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-558",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-559",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-560",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-561",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-562",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-563",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-564",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-565",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-566",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-567",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-568",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-569",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-570",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-571",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-572",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-573",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-574",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-575",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-576",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-577",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-578",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-579",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-580",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-581",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-582",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-583",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-584",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-585",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-586",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-587",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-588",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-589",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-590",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-591",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-592",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-593",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-594",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-595",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-600",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-601",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-602",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-603",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-604",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-605",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-606",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-607",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-608",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-609",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 50 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-610",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-611",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-700",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-701",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-702",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-703",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-704",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-705",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-706",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-707",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 60 */
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-708",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-709",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-710",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-711",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-712",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-713",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-714",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-715",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-716",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_INFRA_AO_SYS2_ATTR("MM_S_S-717",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+/* Peri_ao */
+static const struct APC_INFRA_PERI_DOM_16 PERI_AO_SYS0_Devices[] = {
+
+/* 0 */
+DAPC_PERI_AO_SYS0_ATTR("SPM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SPM_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SPM_APB_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SPM_APB_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SPM_APB_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("APMIXEDSYS_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, NO_PROTECTION,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("APMIXEDSYS_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("TOPCKGEN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, NO_PROTECTION,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("INFRACFG_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("INFRACFG_AO_MEM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_PERI_AO_SYS0_ATTR("PERICFG_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("GPIO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     NO_PROTECTION,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("TOPRGU_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("RESERVED_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_APC_INFRA_AO_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("BCRM_INFRA_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEBUG_CTRL_INFRA_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_APC_PERI_AO_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("BCRM_PERI_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEBUG_CTRL_PERI_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_PERI_AO_SYS0_ATTR("AP_CIRQ_EINT_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PMIC_WRAP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_APC_AO_MM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("KP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("TOP_MISC_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DVFSRC_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("MBIST_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DPMAIF_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_MPU_AO_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SYS_TIMER_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+DAPC_PERI_AO_SYS0_ATTR("MODEM_TEMP_SHARE_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_APC_AO_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PMIF1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PMICSPI_MST_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("TIA_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("TOPCKGEN_INFRA_CFG_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRM_DEBUG_TOP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-3",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-5",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-6",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-7",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-8",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-9",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PWR_MD32_S-10",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("AUDIO_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("AUDIO_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 50 */
+DAPC_PERI_AO_SYS0_ATTR("SSUSB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SSUSB_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SSUSB_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("UFS_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("UFS_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("UFS_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("UFS_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEBUGSYS_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_MD32_S0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_MD32_S0_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 60 */
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_MD32_S1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_MD32_S1_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("NOR_AXI_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("PCIE_AHB_S",
+			NO_PROTECTION, NO_PROTECTION, FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP3_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP4_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP5_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 70 */
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH0_TOP6_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP3_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP4_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP5_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH1_TOP6_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 80 */
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP3_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP4_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP5_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH2_TOP6_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP3_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP4_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 90 */
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP5_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DRAMC_CH3_TOP6_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF2_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF2_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF3_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF3_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF4_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF4_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("INFRA_BUS_TRACE_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("CCIF5_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 100 */
+DAPC_PERI_AO_SYS0_ATTR("CCIF5_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SSC_INFRA_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SSC_INFRA_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("SSC_INFRA_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS0_ATTR("DEVICE_MPU_ACP_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+static const struct APC_INFRA_PERI_DOM_8 PERI_AO_SYS1_Devices[] = {
+
+/* 0 */
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-5",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-6",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-7",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-8",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-9",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-10",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-11",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-12",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-13",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-14",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-15",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-16",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-17",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-18",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-19",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-20",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-21",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("TINSYS_S-22",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-4",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-5",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-6",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-7",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-8",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-9",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-10",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-11",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-12",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-13",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-14",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-15",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-16",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-17",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-18",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-19",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-20",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-21",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-22",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-23",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-24",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-25",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-26",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 50 */
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-27",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-28",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-29",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-30",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-31",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-32",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-33",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-34",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-35",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-36",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 60 */
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-37",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-38",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-39",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-40",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-41",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO_SYS1_ATTR("MD_AP_S-42",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+static const struct APC_INFRA_PERI_DOM_4 PERI_AO_SYS2_Devices[] = {
+
+/* 0 */
+DAPC_PERI_AO_SYS2_ATTR("CONN_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+/* Peri_ao2 */
+static const struct APC_INFRA_PERI_DOM_16 PERI_AO2_SYS0_Devices[] = {
+
+/* 0 */
+DAPC_PERI_AO2_SYS0_ATTR("EFUSE_DEBUG_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("APXGPT_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SEJ_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("AES_TOP0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SECURITY_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_APC_PERI_AO2_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_PERI_AO2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEBUG_CTRL_PERI_AO2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SPMI_MST_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEBUG_CTRL_FMEM_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_FMEM_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_APC_FMEM_AO_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("PWM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("GCE_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("GCE_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("GCE_APB_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("GCE_APB_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DPMAIF_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DPMAIF_PDN_APB_S-1",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DPMAIF_PDN_APB_S-2",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_PERI_AO2_SYS0_ATTR("DPMAIF_PDN_APB_S-3",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     SEC_RW_NS_R,   FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB5_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB6_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB7_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB8_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 30 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB9_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB10_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB11_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB12_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB13_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB14_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_APB15_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 40 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB5_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB6_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_WEST_APB7_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 50 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB5_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB6_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB7_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB8_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB9_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB10_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB11_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB12_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB13_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB14_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 60 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_NORTH_APB15_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB5_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB6_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB7_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB8_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 70 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB9_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB10_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB11_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB12_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB13_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB14_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_SOUTH_APB15_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 80 */
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB5_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB6_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BND_EAST_NORTH_APB7_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SYS_CIRQ_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("EFUSE_DEBUG_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_APC_INFRA_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEBUG_TRACKER_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("CCIF0_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 90 */
+DAPC_PERI_AO2_SYS0_ATTR("CCIF0_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("CCIF1_AP_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("CCIF1_MD_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("MBIST_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("INFRACFG_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("TRNG_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DX_CC_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("CQ_DMA_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SRAMROM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("INFRACFG_MEM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 100 */
+DAPC_PERI_AO2_SYS0_ATTR("RESERVED_DVFS_PROC_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SYS_CIRQ1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("SYS_CIRQ2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEBUG_TRACKER_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("EMI_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("EMI_MPU_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_MPU_PDN_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("APDMA_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEBUG_TRACKER_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_INFRA_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 110 */
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_PERI_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_PERI_PDN2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_APC_PERI_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("DEVICE_APC_PERI_PDN2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_AO2_SYS0_ATTR("BCRM_FMEM_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+/* Peri_par_ao */
+static const struct APC_INFRA_PERI_DOM_16 PERI_PAR_AO_SYS0_Devices[] = {
+
+/* 0 */
+DAPC_PERI_PAR_AO_SYS0_ATTR("AUXADC_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("UART0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("UART1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("UART2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("IIC_P2P_REMAP_APB4_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI0_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("PTP_THERM_CTRL_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("BTIF_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("DISP_PWM_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI1_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 10 */
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI3_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("IIC_P2P_REMAP_APB0_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("IIC_P2P_REMAP_APB1_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI4_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI5_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("IIC_P2P_REMAP_APB2_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("IIC_P2P_REMAP_APB3_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI6_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("SPI7_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+/* 20 */
+DAPC_PERI_PAR_AO_SYS0_ATTR("BCRM_PERI_PAR_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("DEVICE_APC_PERI_PAR_PDN_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("PTP_THERM_CTRL2_APB_S",
+			NO_PROTECTION, FORBIDDEN,     NO_PROTECTION, FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("NOR_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("DEVICE_APC_PERI_PAR_AO_APB_S",
+			SEC_RW_ONLY,   FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("DEBUG_CTRL_PERI_PAR_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+DAPC_PERI_PAR_AO_SYS0_ATTR("BCRM_PERI_PAR_AO_APB_S",
+			NO_PROTECTION, FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN,
+			FORBIDDEN,     FORBIDDEN,     FORBIDDEN,     FORBIDDEN),
+
+};
+
+static void set_module_apc(enum DEVAPC_SLAVE_TYPE slave_type,
+		uint32_t module, enum DOMAIN_ID domain_id,
+		enum DEVAPC_PERM_TYPE perm)
+{
+	uint32_t apc_register_index;
+	uint32_t apc_set_index;
+	uintptr_t base = 0, reg;
+	uint32_t clr_bit;
+	uint32_t set_bit;
+
+	apc_register_index = module / MOD_NO_IN_1_DEVAPC;
+	apc_set_index = module % MOD_NO_IN_1_DEVAPC;
+
+	clr_bit = (0x3U << (apc_set_index * 2));
+	set_bit = (uint32_t)perm << (apc_set_index * 2);
+
+	/* infra_ao */
+	if ((slave_type == SLAVE_TYPE_INFRA_AO_SYS0) &&
+		(module < SLAVE_NUM_INFRA_AO_SYS0) &&
+		(domain_id < (uint32_t)DOM_NUM_INFRA_AO_SYS0)) {
+		base = DEVAPC_INFRA_AO_SYS0_D0_APC_0;
+
+	} else if ((slave_type == SLAVE_TYPE_INFRA_AO_SYS1) &&
+		(module < SLAVE_NUM_INFRA_AO_SYS1) &&
+		(domain_id < (uint32_t)DOM_NUM_INFRA_AO_SYS1)) {
+		base = DEVAPC_INFRA_AO_SYS1_D0_APC_0;
+
+	} else if ((slave_type == SLAVE_TYPE_INFRA_AO_SYS2) &&
+		(module < SLAVE_NUM_INFRA_AO_SYS2) &&
+		(domain_id < (uint32_t)DOM_NUM_INFRA_AO_SYS2)) {
+		base = DEVAPC_INFRA_AO_SYS2_D0_APC_0;
+	/* peri_ao */
+	} else if ((slave_type == SLAVE_TYPE_PERI_AO_SYS0) &&
+		(module < SLAVE_NUM_PERI_AO_SYS0) &&
+		(domain_id < (uint32_t)DOM_NUM_PERI_AO_SYS0)) {
+		base = DEVAPC_PERI_AO_SYS0_D0_APC_0;
+
+	} else if ((slave_type == SLAVE_TYPE_PERI_AO_SYS1) &&
+		(module < SLAVE_NUM_PERI_AO_SYS1) &&
+		(domain_id <= (uint32_t)DOM_NUM_PERI_AO_SYS1)) {
+		base = DEVAPC_PERI_AO_SYS1_D0_APC_0;
+
+	} else if ((slave_type == SLAVE_TYPE_PERI_AO_SYS2) &&
+		(module < SLAVE_NUM_PERI_AO_SYS2) &&
+		(domain_id < (uint32_t)DOM_NUM_PERI_AO_SYS2)) {
+		base = DEVAPC_PERI_AO_SYS2_D0_APC_0;
+	/* peri_ao2 */
+	} else if ((slave_type == SLAVE_TYPE_PERI_AO2_SYS0) &&
+		(module < SLAVE_NUM_PERI_AO2_SYS0) &&
+		(domain_id < (uint32_t)DOM_NUM_PERI_AO2_SYS0)) {
+		base = DEVAPC_PERI_AO2_SYS0_D0_APC_0;
+
+	/* peri_par_ao */
+	} else if ((slave_type == SLAVE_TYPE_PERI_PAR_AO_SYS0) &&
+		(module < SLAVE_NUM_PERI_PAR_AO_SYS0) &&
+		(domain_id < (uint32_t)DOM_NUM_PERI_PAR_AO_SYS0)) {
+		base = DEVAPC_PERI_PAR_AO_SYS0_D0_APC_0;
+
+	} else {
+		ERROR("[DEVAPC] %s: %s, %s:0x%x, %s:0x%x, %s:0x%x\n",
+				__func__, "out of boundary",
+				"slave_type", slave_type,
+				"module", module,
+				"domain_id", domain_id);
+	}
+
+	if (base != 0U) {
+		reg = base + domain_id * 0x40 + apc_register_index * 4;
+		mmio_clrsetbits_32(reg, clr_bit, set_bit);
+	}
+}
+
+static void dump_infra_ao_apc(void)
+{
+	int reg_num;
+	int d, i;
+
+	reg_num = (SLAVE_NUM_INFRA_AO_SYS0 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_INFRA_AO_SYS0; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (INFRA_AO_SYS0)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_INFRA_AO_SYS0_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	reg_num = (SLAVE_NUM_INFRA_AO_SYS1 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_INFRA_AO_SYS1; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (INFRA_AO_SYS1)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_INFRA_AO_SYS1_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	reg_num = (SLAVE_NUM_INFRA_AO_SYS2 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_INFRA_AO_SYS2; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (INFRA_AO_SYS2)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_INFRA_AO_SYS2_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	INFO("[DEVAPC] (INFRA_AO)MAS_SEC_0: 0x%x\n",
+		devapc_readl(DEVAPC_INFRA_AO_MAS_SEC_0));
+}
+
+static void dump_peri_ao_apc(void)
+{
+	int reg_num;
+	int d, i;
+
+	reg_num = (SLAVE_NUM_PERI_AO_SYS0 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_PERI_AO_SYS0; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (PERI_AO_SYS0)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_PERI_AO_SYS0_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	reg_num = (SLAVE_NUM_PERI_AO_SYS1 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_PERI_AO_SYS1; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (PERI_AO_SYS1)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_PERI_AO_SYS1_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	reg_num = (SLAVE_NUM_PERI_AO_SYS2 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_PERI_AO_SYS2; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (PERI_AO_SYS2)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_PERI_AO_SYS2_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	INFO("[DEVAPC] (PERI_AO)MAS_SEC_0: 0x%x\n",
+		devapc_readl(DEVAPC_PERI_AO_MAS_SEC_0));
+}
+
+static void dump_peri_ao2_apc(void)
+{
+	int reg_num;
+	int d, i;
+
+	reg_num = (SLAVE_NUM_PERI_AO2_SYS0 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_PERI_AO2_SYS0; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (PERI_AO2_SYS0)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_PERI_AO2_SYS0_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+}
+
+static void dump_peri_par_ao_apc(void)
+{
+	int reg_num;
+	int d, i;
+
+	reg_num = (SLAVE_NUM_PERI_PAR_AO_SYS0 - 1) / MOD_NO_IN_1_DEVAPC;
+	for (d = 0; d < DOM_NUM_PERI_PAR_AO_SYS0; d++) {
+		for (i = 0; i <= reg_num; i++) {
+			INFO("[DEVAPC] (PERI_PAR_AO_SYS0)D%d_APC_%d: 0x%x\n",
+					d, i, devapc_readl(
+					DEVAPC_PERI_PAR_AO_SYS0_D0_APC_0 +
+					d * 0x40 + i * 4)
+			);
+		}
+	}
+
+	INFO("[DEVAPC] (PERI_PAR_AO)MAS_SEC_0: 0x%x\n",
+		devapc_readl(DEVAPC_PERI_PAR_AO_MAS_SEC_0));
+}
+
+static void set_infra_ao_apc(void)
+{
+	uint32_t infra_ao_size;
+	uint32_t i;
+
+	infra_ao_size = ARRAY_SIZE(INFRA_AO_SYS0_Devices);
+
+	for (i = 0; i < infra_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_0,
+				INFRA_AO_SYS0_Devices[i].d0_permission);		/* APMCU */
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_1,
+				INFRA_AO_SYS0_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_2,
+				INFRA_AO_SYS0_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_3,
+				INFRA_AO_SYS0_Devices[i].d3_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_4,
+				INFRA_AO_SYS0_Devices[i].d4_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_5,
+				INFRA_AO_SYS0_Devices[i].d5_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_6,
+				INFRA_AO_SYS0_Devices[i].d6_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_7,
+				INFRA_AO_SYS0_Devices[i].d7_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_8,
+				INFRA_AO_SYS0_Devices[i].d8_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_9,
+				INFRA_AO_SYS0_Devices[i].d9_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_10,
+				INFRA_AO_SYS0_Devices[i].d10_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_11,
+				INFRA_AO_SYS0_Devices[i].d11_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_12,
+				INFRA_AO_SYS0_Devices[i].d12_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_13,
+				INFRA_AO_SYS0_Devices[i].d13_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_14,
+				INFRA_AO_SYS0_Devices[i].d14_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS0, i, DOMAIN_15,
+				INFRA_AO_SYS0_Devices[i].d15_permission);
+	}
+
+	infra_ao_size = ARRAY_SIZE(INFRA_AO_SYS1_Devices);
+
+	for (i = 0; i < infra_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS1, i, DOMAIN_0,
+				INFRA_AO_SYS1_Devices[i].d0_permission);		/* APMCU */
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS1, i, DOMAIN_1,
+				INFRA_AO_SYS1_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS1, i, DOMAIN_2,
+				INFRA_AO_SYS1_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS1, i, DOMAIN_3,
+				INFRA_AO_SYS1_Devices[i].d3_permission);
+	}
+
+	infra_ao_size = ARRAY_SIZE(INFRA_AO_SYS2_Devices);
+
+	for (i = 0; i < infra_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS2, i, DOMAIN_0,
+				INFRA_AO_SYS2_Devices[i].d0_permission);		/* APMCU */
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS2, i, DOMAIN_1,
+				INFRA_AO_SYS2_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS2, i, DOMAIN_2,
+				INFRA_AO_SYS2_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_INFRA_AO_SYS2, i, DOMAIN_3,
+				INFRA_AO_SYS2_Devices[i].d3_permission);
+	}
+}
+
+static void set_peri_ao_apc(void)
+{
+	uint32_t peri_ao_size;
+	uint32_t i;
+
+	peri_ao_size = ARRAY_SIZE(PERI_AO_SYS0_Devices);
+
+	for (i = 0; i < peri_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_0,
+				PERI_AO_SYS0_Devices[i].d0_permission);			/* APMCU */
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_1,
+				PERI_AO_SYS0_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_2,
+				PERI_AO_SYS0_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_3,
+				PERI_AO_SYS0_Devices[i].d3_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_4,
+				PERI_AO_SYS0_Devices[i].d4_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_5,
+				PERI_AO_SYS0_Devices[i].d5_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_6,
+				PERI_AO_SYS0_Devices[i].d6_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_7,
+				PERI_AO_SYS0_Devices[i].d7_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_8,
+				PERI_AO_SYS0_Devices[i].d8_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_9,
+				PERI_AO_SYS0_Devices[i].d9_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_10,
+				PERI_AO_SYS0_Devices[i].d10_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_11,
+				PERI_AO_SYS0_Devices[i].d11_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_12,
+				PERI_AO_SYS0_Devices[i].d12_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_13,
+				PERI_AO_SYS0_Devices[i].d13_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_14,
+				PERI_AO_SYS0_Devices[i].d14_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, i, DOMAIN_15,
+				PERI_AO_SYS0_Devices[i].d15_permission);
+	}
+
+	peri_ao_size = ARRAY_SIZE(PERI_AO_SYS1_Devices);
+
+	for (i = 0; i < peri_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_0,
+				PERI_AO_SYS1_Devices[i].d0_permission);			/* APMCU */
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_1,
+				PERI_AO_SYS1_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_2,
+				PERI_AO_SYS1_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_3,
+				PERI_AO_SYS1_Devices[i].d3_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_4,
+				PERI_AO_SYS1_Devices[i].d4_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_5,
+				PERI_AO_SYS1_Devices[i].d5_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_6,
+				PERI_AO_SYS1_Devices[i].d6_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS1, i, DOMAIN_7,
+				PERI_AO_SYS1_Devices[i].d7_permission);
+	}
+
+	peri_ao_size = ARRAY_SIZE(PERI_AO_SYS2_Devices);
+
+	for (i = 0; i < peri_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS2, i, DOMAIN_0,
+				PERI_AO_SYS2_Devices[i].d0_permission);			/* APMCU */
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS2, i, DOMAIN_1,
+				PERI_AO_SYS2_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS2, i, DOMAIN_2,
+				PERI_AO_SYS2_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO_SYS2, i, DOMAIN_3,
+				PERI_AO_SYS2_Devices[i].d3_permission);
+	}
+}
+
+static void set_peri_ao2_apc(void)
+{
+	uint32_t peri_ao2_size;
+	uint32_t i;
+
+	peri_ao2_size = ARRAY_SIZE(PERI_AO2_SYS0_Devices);
+
+	for (i = 0; i < peri_ao2_size; i++) {
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_0,
+				PERI_AO2_SYS0_Devices[i].d0_permission);		/* APMCU */
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_1,
+				PERI_AO2_SYS0_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_2,
+				PERI_AO2_SYS0_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_3,
+				PERI_AO2_SYS0_Devices[i].d3_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_4,
+				PERI_AO2_SYS0_Devices[i].d4_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_5,
+				PERI_AO2_SYS0_Devices[i].d5_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_6,
+				PERI_AO2_SYS0_Devices[i].d6_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_7,
+				PERI_AO2_SYS0_Devices[i].d7_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_8,
+				PERI_AO2_SYS0_Devices[i].d8_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_9,
+				PERI_AO2_SYS0_Devices[i].d9_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_10,
+				PERI_AO2_SYS0_Devices[i].d10_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_11,
+				PERI_AO2_SYS0_Devices[i].d11_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_12,
+				PERI_AO2_SYS0_Devices[i].d12_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_13,
+				PERI_AO2_SYS0_Devices[i].d13_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_14,
+				PERI_AO2_SYS0_Devices[i].d14_permission);
+		set_module_apc(SLAVE_TYPE_PERI_AO2_SYS0, i, DOMAIN_15,
+				PERI_AO2_SYS0_Devices[i].d15_permission);
+	}
+}
+
+static void set_peri_par_ao_apc(void)
+{
+	uint32_t peri_par_ao_size;
+	uint32_t i;
+
+	peri_par_ao_size = ARRAY_SIZE(PERI_PAR_AO_SYS0_Devices);
+
+	for (i = 0; i < peri_par_ao_size; i++) {
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_0,
+				PERI_PAR_AO_SYS0_Devices[i].d0_permission);		/* APMCU */
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_1,
+				PERI_PAR_AO_SYS0_Devices[i].d1_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_2,
+				PERI_PAR_AO_SYS0_Devices[i].d2_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_3,
+				PERI_PAR_AO_SYS0_Devices[i].d3_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_4,
+				PERI_PAR_AO_SYS0_Devices[i].d4_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_5,
+				PERI_PAR_AO_SYS0_Devices[i].d5_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_6,
+				PERI_PAR_AO_SYS0_Devices[i].d6_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_7,
+				PERI_PAR_AO_SYS0_Devices[i].d7_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_8,
+				PERI_PAR_AO_SYS0_Devices[i].d8_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_9,
+				PERI_PAR_AO_SYS0_Devices[i].d9_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_10,
+				PERI_PAR_AO_SYS0_Devices[i].d10_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_11,
+				PERI_PAR_AO_SYS0_Devices[i].d11_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_12,
+				PERI_PAR_AO_SYS0_Devices[i].d12_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_13,
+				PERI_PAR_AO_SYS0_Devices[i].d13_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_14,
+				PERI_PAR_AO_SYS0_Devices[i].d14_permission);
+		set_module_apc(SLAVE_TYPE_PERI_PAR_AO_SYS0, i, DOMAIN_15,
+				PERI_PAR_AO_SYS0_Devices[i].d15_permission);
+	}
+}
+
+static void set_extra_apc(void)
+{
+#ifdef MTK_DEBUGSYS_LOCK
+	/* Block debugsys to avoid privilege escalation (user load only) */
+	set_module_apc(SLAVE_TYPE_PERI_AO_SYS0, DEVAPC_DEBUGSYS_INDEX,
+			DOMAIN_0, SEC_RW_NS_R);
+#endif
+}
+
+void devapc_init(void)
+{
+	/* Initial Permission */
+	set_infra_ao_apc();
+	set_peri_ao_apc();
+	set_peri_ao2_apc();
+	set_peri_par_ao_apc();
+
+	/* Extra Permission */
+	set_extra_apc();
+
+	/* Dump Permission */
+	dump_infra_ao_apc();
+	dump_peri_ao_apc();
+	dump_peri_ao2_apc();
+	dump_peri_par_ao_apc();
+
+	/* Setup APUSYS Permission */
+	set_apusys_apc();
+
+	INFO("[DEVAPC] %s done\n", __func__);
+}
diff --git a/plat/mediatek/mt8192/drivers/devapc/devapc.h b/plat/mediatek/mt8192/drivers/devapc/devapc.h
new file mode 100644
index 0000000..9033a0f
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/devapc/devapc.h
@@ -0,0 +1,211 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef DEVAPC_H
+#define DEVAPC_H
+
+#include <stdint.h>
+#include <platform_def.h>
+
+/******************************************************************************
+ * FUNCTION DEFINITION
+ ******************************************************************************/
+void devapc_init(void);
+
+/******************************************************************************
+ * STRUCTURE DEFINITION
+ ******************************************************************************/
+enum DEVAPC_PERM_TYPE {
+	NO_PROTECTION = 0,
+	SEC_RW_ONLY,
+	SEC_RW_NS_R,
+	FORBIDDEN,
+	PERM_NUM,
+};
+
+enum DOMAIN_ID {
+	DOMAIN_0 = 0,
+	DOMAIN_1,
+	DOMAIN_2,
+	DOMAIN_3,
+	DOMAIN_4,
+	DOMAIN_5,
+	DOMAIN_6,
+	DOMAIN_7,
+	DOMAIN_8,
+	DOMAIN_9,
+	DOMAIN_10,
+	DOMAIN_11,
+	DOMAIN_12,
+	DOMAIN_13,
+	DOMAIN_14,
+	DOMAIN_15,
+};
+
+/* Slave Type */
+enum DEVAPC_SLAVE_TYPE_SIMPLE {
+	SLAVE_TYPE_INFRA = 0,
+	SLAVE_TYPE_PERI,
+	SLAVE_TYPE_PERI2,
+	SLAVE_TYPE_PERI_PAR,
+};
+
+enum DEVAPC_SYS_INDEX {
+	DEVAPC_SYS0 = 0,
+	DEVAPC_SYS1,
+	DEVAPC_SYS2,
+};
+
+enum DEVAPC_SLAVE_TYPE {
+	SLAVE_TYPE_INFRA_AO_SYS0 = 0,
+	SLAVE_TYPE_INFRA_AO_SYS1,
+	SLAVE_TYPE_INFRA_AO_SYS2,
+	SLAVE_TYPE_PERI_AO_SYS0,
+	SLAVE_TYPE_PERI_AO_SYS1,
+	SLAVE_TYPE_PERI_AO_SYS2,
+	SLAVE_TYPE_PERI_AO2_SYS0,
+	SLAVE_TYPE_PERI_PAR_AO_SYS0,
+};
+
+/* Slave Num */
+enum DEVAPC_SLAVE_NUM {
+	SLAVE_NUM_INFRA_AO_SYS0 = 23,
+	SLAVE_NUM_INFRA_AO_SYS1 = 256,
+	SLAVE_NUM_INFRA_AO_SYS2 = 70,
+	SLAVE_NUM_PERI_AO_SYS0 = 105,
+	SLAVE_NUM_PERI_AO_SYS1 = 66,
+	SLAVE_NUM_PERI_AO_SYS2 = 1,
+	SLAVE_NUM_PERI_AO2_SYS0 = 115,
+	SLAVE_NUM_PERI_PAR_AO_SYS0 = 27,
+};
+
+enum DEVAPC_SYS_DOM_NUM {
+	DOM_NUM_INFRA_AO_SYS0 = 16,
+	DOM_NUM_INFRA_AO_SYS1 = 4,
+	DOM_NUM_INFRA_AO_SYS2 = 4,
+	DOM_NUM_PERI_AO_SYS0 = 16,
+	DOM_NUM_PERI_AO_SYS1 = 8,
+	DOM_NUM_PERI_AO_SYS2 = 4,
+	DOM_NUM_PERI_AO2_SYS0 = 16,
+	DOM_NUM_PERI_PAR_AO_SYS0 = 16,
+};
+
+enum DEVAPC_CFG_INDEX {
+	DEVAPC_DEBUGSYS_INDEX = 57,
+};
+
+struct APC_INFRA_PERI_DOM_16 {
+	unsigned char d0_permission;
+	unsigned char d1_permission;
+	unsigned char d2_permission;
+	unsigned char d3_permission;
+	unsigned char d4_permission;
+	unsigned char d5_permission;
+	unsigned char d6_permission;
+	unsigned char d7_permission;
+	unsigned char d8_permission;
+	unsigned char d9_permission;
+	unsigned char d10_permission;
+	unsigned char d11_permission;
+	unsigned char d12_permission;
+	unsigned char d13_permission;
+	unsigned char d14_permission;
+	unsigned char d15_permission;
+};
+
+struct APC_INFRA_PERI_DOM_8 {
+	unsigned char d0_permission;
+	unsigned char d1_permission;
+	unsigned char d2_permission;
+	unsigned char d3_permission;
+	unsigned char d4_permission;
+	unsigned char d5_permission;
+	unsigned char d6_permission;
+	unsigned char d7_permission;
+};
+
+struct APC_INFRA_PERI_DOM_4 {
+	unsigned char d0_permission;
+	unsigned char d1_permission;
+	unsigned char d2_permission;
+	unsigned char d3_permission;
+};
+
+#define DAPC_INFRA_AO_SYS0_ATTR(DEV_NAME, PERM_ATTR0, PERM_ATTR1, \
+		PERM_ATTR2, PERM_ATTR3, PERM_ATTR4, PERM_ATTR5, \
+		PERM_ATTR6, PERM_ATTR7, PERM_ATTR8, PERM_ATTR9, \
+		PERM_ATTR10, PERM_ATTR11, PERM_ATTR12, PERM_ATTR13, \
+		PERM_ATTR14, PERM_ATTR15) \
+	{(unsigned char)PERM_ATTR0, (unsigned char)PERM_ATTR1, \
+	(unsigned char)PERM_ATTR2, (unsigned char)PERM_ATTR3, \
+	(unsigned char)PERM_ATTR4, (unsigned char)PERM_ATTR5, \
+	(unsigned char)PERM_ATTR6, (unsigned char)PERM_ATTR7, \
+	(unsigned char)PERM_ATTR8, (unsigned char)PERM_ATTR9, \
+	(unsigned char)PERM_ATTR10, (unsigned char)PERM_ATTR11, \
+	(unsigned char)PERM_ATTR12, (unsigned char)PERM_ATTR13, \
+	(unsigned char)PERM_ATTR14, (unsigned char)PERM_ATTR15}
+
+#define DAPC_INFRA_AO_SYS1_ATTR(DEV_NAME, PERM_ATTR0, PERM_ATTR1, \
+		PERM_ATTR2, PERM_ATTR3) \
+	{(unsigned char)PERM_ATTR0, (unsigned char)PERM_ATTR1, \
+	(unsigned char)PERM_ATTR2, (unsigned char)PERM_ATTR3}
+
+#define DAPC_PERI_AO_SYS1_ATTR(DEV_NAME, PERM_ATTR0, PERM_ATTR1, \
+		PERM_ATTR2, PERM_ATTR3, PERM_ATTR4, PERM_ATTR5, \
+		PERM_ATTR6, PERM_ATTR7) \
+	{(unsigned char)PERM_ATTR0, (unsigned char)PERM_ATTR1, \
+	(unsigned char)PERM_ATTR2, (unsigned char)PERM_ATTR3, \
+	(unsigned char)PERM_ATTR4, (unsigned char)PERM_ATTR5, \
+	(unsigned char)PERM_ATTR6, (unsigned char)PERM_ATTR7}
+
+#define DAPC_INFRA_AO_SYS2_ATTR(...)	DAPC_INFRA_AO_SYS1_ATTR(__VA_ARGS__)
+#define DAPC_PERI_AO_SYS0_ATTR(...)	DAPC_INFRA_AO_SYS0_ATTR(__VA_ARGS__)
+#define DAPC_PERI_AO_SYS2_ATTR(...)	DAPC_INFRA_AO_SYS1_ATTR(__VA_ARGS__)
+#define DAPC_PERI_AO2_SYS0_ATTR(...)	DAPC_INFRA_AO_SYS0_ATTR(__VA_ARGS__)
+#define DAPC_PERI_PAR_AO_SYS0_ATTR(...)	DAPC_INFRA_AO_SYS0_ATTR(__VA_ARGS__)
+
+/******************************************************************************
+ * UTILITY DEFINITION
+ ******************************************************************************/
+#define devapc_writel(VAL, REG)		mmio_write_32((uintptr_t)REG, VAL)
+#define devapc_readl(REG)		mmio_read_32((uintptr_t)REG)
+
+/******************************************************************************/
+/* Device APC AO for INFRA AO */
+#define DEVAPC_INFRA_AO_SYS0_D0_APC_0		(DEVAPC_INFRA_AO_BASE + 0x0000)
+#define DEVAPC_INFRA_AO_SYS1_D0_APC_0		(DEVAPC_INFRA_AO_BASE + 0x1000)
+#define DEVAPC_INFRA_AO_SYS2_D0_APC_0		(DEVAPC_INFRA_AO_BASE + 0x2000)
+
+#define DEVAPC_INFRA_AO_MAS_SEC_0		(DEVAPC_INFRA_AO_BASE + 0x0A00)
+
+/******************************************************************************/
+/* Device APC AO for PERI AO */
+#define DEVAPC_PERI_AO_SYS0_D0_APC_0		(DEVAPC_PERI_AO_BASE + 0x0000)
+#define DEVAPC_PERI_AO_SYS1_D0_APC_0		(DEVAPC_PERI_AO_BASE + 0x1000)
+#define DEVAPC_PERI_AO_SYS2_D0_APC_0		(DEVAPC_PERI_AO_BASE + 0x2000)
+
+#define DEVAPC_PERI_AO_MAS_SEC_0		(DEVAPC_PERI_AO_BASE + 0x0A00)
+
+/******************************************************************************/
+/* Device APC AO for PERI AO2 */
+#define DEVAPC_PERI_AO2_SYS0_D0_APC_0		(DEVAPC_PERI_AO2_BASE + 0x0000)
+
+/******************************************************************************/
+/* Device APC AO for PERI PAR AO */
+#define DEVAPC_PERI_PAR_AO_SYS0_D0_APC_0	(DEVAPC_PERI_PAR_AO_BASE + 0x0000)
+
+#define DEVAPC_PERI_PAR_AO_MAS_SEC_0		(DEVAPC_PERI_PAR_AO_BASE + 0x0A00)
+
+/******************************************************************************/
+
+
+/******************************************************************************
+ * Variable DEFINITION
+ ******************************************************************************/
+#define MOD_NO_IN_1_DEVAPC              16
+
+#endif /* DEVAPC_H */
+
diff --git a/plat/mediatek/mt8192/drivers/dfd/plat_dfd.c b/plat/mediatek/mt8192/drivers/dfd/plat_dfd.c
new file mode 100644
index 0000000..69c395e
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dfd/plat_dfd.c
@@ -0,0 +1,139 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mtk_sip_svc.h>
+#include <plat_dfd.h>
+
+static bool dfd_enabled;
+static uint64_t dfd_base_addr;
+static uint64_t dfd_chain_length;
+static uint64_t dfd_cache_dump;
+
+static void dfd_setup(uint64_t base_addr, uint64_t chain_length,
+		      uint64_t cache_dump)
+{
+	/* bit[0]: rg_rw_dfd_internal_dump_en -> 1 */
+	/* bit[2]: rg_rw_dfd_clock_stop_en -> 1 */
+	sync_writel(DFD_INTERNAL_CTL, 0x5);
+
+	/* bit[13]: xreset_b_update_disable */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x1 << 13);
+
+	/*
+	 * bit[10:3]: DFD trigger selection mask
+	 * bit[3]: rg_rw_dfd_trigger_sel[0] = 1(enable wdt trigger)
+	 * bit[4]: rg_rw_dfd_trigger_sel[1] = 1(enable HW trigger)
+	 * bit[5]: rg_rw_dfd_trigger_sel[2] = 1(enable SW trigger)
+	 * bit[6]: rg_rw_dfd_trigger_sel[3] = 1(enable SW non-security trigger)
+	 * bit[7]: rg_rw_dfd_trigger_sel[4] = 1(enable timer trigger)
+	 */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x1 << 3);
+
+	/* bit[20:19]: rg_dfd_armpll_div_mux_sel switch to PLL2 for DFD */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x3 << 19);
+
+	/*
+	 * bit[0]: rg_rw_dfd_auto_power_on = 1
+	 * bit[2:1]: rg_rw_dfd_auto_power_on_dely = 1(10us)
+	 * bit[4:2]: rg_rw_dfd_power_on_wait_time = 1(20us)
+	 */
+	mmio_write_32(DFD_INTERNAL_PWR_ON, 0xB);
+
+	/* longest scan chain length */
+	mmio_write_32(DFD_CHAIN_LENGTH0, chain_length);
+
+	/* bit[1:0]: rg_rw_dfd_shift_clock_ratio */
+	mmio_write_32(DFD_INTERNAL_SHIFT_CLK_RATIO, 0x0);
+
+	/* rg_dfd_test_so_over_64 */
+	mmio_write_32(DFD_INTERNAL_TEST_SO_OVER_64, 0x1);
+
+	/* DFD3.0 */
+	mmio_write_32(DFD_TEST_SI_0, DFD_TEST_SI_0_CACHE_DIS_VAL);
+	mmio_write_32(DFD_TEST_SI_1, DFD_TEST_SI_1_VAL);
+	mmio_write_32(DFD_TEST_SI_2, DFD_TEST_SI_2_VAL);
+	mmio_write_32(DFD_TEST_SI_3, DFD_TEST_SI_3_VAL);
+
+	/* for iLDO feature */
+	sync_writel(DFD_POWER_CTL, 0xF9);
+
+	/* set base address */
+	mmio_write_32(DFD_O_SET_BASEADDR_REG, base_addr >> 24);
+
+	/*
+	 * disable sleep protect of DFD
+	 * 10001220[8]: protect_en_reg[8]
+	 * 10001a3c[2]: infra_mcu_pwr_ctl_mask[2]
+	 */
+	mmio_clrbits_32(DFD_O_PROTECT_EN_REG, 1 << 8);
+	mmio_clrbits_32(DFD_O_INTRF_MCU_PWR_CTL_MASK, 1 << 2);
+
+	/* clean DFD trigger status */
+	sync_writel(DFD_CLEAN_STATUS, 0x1);
+	sync_writel(DFD_CLEAN_STATUS, 0x0);
+
+	/* DFD-3.0 */
+	sync_writel(DFD_V30_CTL, 0x1);
+
+	/* setup global variables for suspend and resume */
+	dfd_enabled = true;
+	dfd_base_addr = base_addr;
+	dfd_chain_length = chain_length;
+	dfd_cache_dump = cache_dump;
+
+	if ((cache_dump & DFD_CACHE_DUMP_ENABLE) != 0UL) {
+		/* DFD3.5 */
+		mmio_write_32(DFD_TEST_SI_0, DFD_TEST_SI_0_CACHE_EN_VAL);
+		sync_writel(DFD_V35_ENALBE, 0x1);
+		sync_writel(DFD_V35_TAP_NUMBER, 0xB);
+		sync_writel(DFD_V35_TAP_EN, DFD_V35_TAP_EN_VAL);
+		sync_writel(DFD_V35_SEQ0_0, DFD_V35_SEQ0_0_VAL);
+
+		if (cache_dump & DFD_PARITY_ERR_TRIGGER) {
+			sync_writel(DFD_HW_TRIGGER_MASK, 0xC);
+			mmio_setbits_32(DFD_INTERNAL_CTL, 0x1 << 4);
+		}
+	}
+	dsbsy();
+}
+
+void dfd_resume(void)
+{
+	if (dfd_enabled == true) {
+		dfd_setup(dfd_base_addr, dfd_chain_length, dfd_cache_dump);
+	}
+}
+
+uint64_t dfd_smc_dispatcher(uint64_t arg0, uint64_t arg1,
+			    uint64_t arg2, uint64_t arg3)
+{
+	uint64_t ret = 0L;
+
+	switch (arg0) {
+	case PLAT_MTK_DFD_SETUP_MAGIC:
+		dfd_setup(arg1, arg2, arg3);
+		break;
+	case PLAT_MTK_DFD_READ_MAGIC:
+		/* only allow to access DFD register base + 0x200 */
+		if (arg1 <= 0x200) {
+			ret = mmio_read_32(MISC1_CFG_BASE + arg1);
+		}
+		break;
+	case PLAT_MTK_DFD_WRITE_MAGIC:
+		/* only allow to access DFD register base + 0x200 */
+		if (arg1 <= 0x200) {
+			sync_writel(MISC1_CFG_BASE + arg1, arg2);
+		}
+		break;
+	default:
+		ret = MTK_SIP_E_INVALID_PARAM;
+		break;
+	}
+
+	return ret;
+}
diff --git a/plat/mediatek/mt8192/drivers/dfd/plat_dfd.h b/plat/mediatek/mt8192/drivers/dfd/plat_dfd.h
new file mode 100644
index 0000000..7f0f4b5
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/dfd/plat_dfd.h
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_DFD_H
+#define PLAT_DFD_H
+
+#include <arch_helpers.h>
+#include <lib/mmio.h>
+#include <platform_def.h>
+
+#define sync_writel(addr, val)	do { mmio_write_32((addr), (val)); \
+				dsbsy(); \
+				} while (0)
+
+#define PLAT_MTK_DFD_SETUP_MAGIC		(0x99716150)
+#define PLAT_MTK_DFD_READ_MAGIC			(0x99716151)
+#define PLAT_MTK_DFD_WRITE_MAGIC		(0x99716152)
+
+#define MCU_BIU_BASE				(MCUCFG_BASE)
+#define MISC1_CFG_BASE				(MCU_BIU_BASE + 0xE040)
+#define DFD_INTERNAL_CTL			(MISC1_CFG_BASE + 0x00)
+#define DFD_INTERNAL_PWR_ON			(MISC1_CFG_BASE + 0x08)
+#define DFD_CHAIN_LENGTH0			(MISC1_CFG_BASE + 0x0C)
+#define DFD_INTERNAL_SHIFT_CLK_RATIO		(MISC1_CFG_BASE + 0x10)
+#define DFD_CHAIN_LENGTH1			(MISC1_CFG_BASE + 0x1C)
+#define DFD_CHAIN_LENGTH2			(MISC1_CFG_BASE + 0x20)
+#define DFD_CHAIN_LENGTH3			(MISC1_CFG_BASE + 0x24)
+#define DFD_INTERNAL_TEST_SO_0			(MISC1_CFG_BASE + 0x28)
+#define DFD_INTERNAL_NUM_OF_TEST_SO_GROUP	(MISC1_CFG_BASE + 0x30)
+#define DFD_INTERNAL_TEST_SO_OVER_64		(MISC1_CFG_BASE + 0x34)
+#define DFD_V30_CTL				(MISC1_CFG_BASE + 0x48)
+#define DFD_V30_BASE_ADDR			(MISC1_CFG_BASE + 0x4C)
+#define DFD_POWER_CTL				(MISC1_CFG_BASE + 0x50)
+#define DFD_TEST_SI_0				(MISC1_CFG_BASE + 0x58)
+#define DFD_TEST_SI_1				(MISC1_CFG_BASE + 0x5C)
+#define DFD_CLEAN_STATUS			(MISC1_CFG_BASE + 0x60)
+#define DFD_TEST_SI_2				(MISC1_CFG_BASE + 0x1D8)
+#define DFD_TEST_SI_3				(MISC1_CFG_BASE + 0x1DC)
+#define DFD_HW_TRIGGER_MASK			(MISC1_CFG_BASE + 0xBC)
+
+#define DFD_V35_ENALBE				(MCU_BIU_BASE + 0xE0A8)
+#define DFD_V35_TAP_NUMBER			(MCU_BIU_BASE + 0xE0AC)
+#define DFD_V35_TAP_EN				(MCU_BIU_BASE + 0xE0B0)
+#define DFD_V35_CTL				(MCU_BIU_BASE + 0xE0B4)
+#define DFD_V35_SEQ0_0				(MCU_BIU_BASE + 0xE0C0)
+#define DFD_V35_SEQ0_1				(MCU_BIU_BASE + 0xE0C4)
+
+#define DFD_O_PROTECT_EN_REG			(0x10001220)
+#define DFD_O_INTRF_MCU_PWR_CTL_MASK		(0x10001A3C)
+#define DFD_O_SET_BASEADDR_REG			(0x10043034)
+
+#define DFD_CACHE_DUMP_ENABLE			1U
+#define DFD_PARITY_ERR_TRIGGER			2U
+
+#define DFD_TEST_SI_0_CACHE_DIS_VAL		(0x1E000202)
+#define DFD_TEST_SI_0_CACHE_EN_VAL		(0x1E000002)
+#define DFD_TEST_SI_1_VAL			(0x20408100)
+#define DFD_TEST_SI_2_VAL			(0x10101000)
+#define DFD_TEST_SI_3_VAL			(0x00000010)
+#define	DFD_V35_TAP_EN_VAL			(0x43FF)
+#define	DFD_V35_SEQ0_0_VAL			(0x63668820)
+
+void dfd_resume(void);
+uint64_t dfd_smc_dispatcher(uint64_t arg0, uint64_t arg1,
+			    uint64_t arg2, uint64_t arg3);
+
+#endif /* PLAT_DFD_H */
diff --git a/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.c b/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.c
new file mode 100644
index 0000000..26bed29
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.c
@@ -0,0 +1,144 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <emi_mpu.h>
+#include <lib/mmio.h>
+
+/*
+ * emi_mpu_set_region_protection: protect a region.
+ * @start: start address of the region
+ * @end: end address of the region
+ * @access_permission: EMI MPU access permission
+ * Return 0 for success, otherwise negative status code.
+ */
+static int _emi_mpu_set_protection(
+	unsigned long start, unsigned long end,
+	unsigned int apc)
+{
+	unsigned int dgroup;
+	unsigned int region;
+
+	region = (start >> 24) & 0xFF;
+	start &= 0x00FFFFFF;
+	dgroup = (end >> 24) & 0xFF;
+	end &= 0x00FFFFFF;
+
+	if  ((region >= EMI_MPU_REGION_NUM) || (dgroup > EMI_MPU_DGROUP_NUM)) {
+		WARN("Region:%u or dgroup:%u is wrong!\n", region, dgroup);
+		return -1;
+	}
+
+	apc &= 0x80FFFFFF;
+
+	if ((start >= DRAM_OFFSET) && (end >= start)) {
+		start -= DRAM_OFFSET;
+		end -= DRAM_OFFSET;
+	} else {
+		WARN("start:0x%lx or end:0x%lx address is wrong!\n",
+		     start, end);
+		return -2;
+	}
+
+	mmio_write_32(EMI_MPU_SA(region), start);
+	mmio_write_32(EMI_MPU_EA(region), end);
+	mmio_write_32(EMI_MPU_APC(region, dgroup), apc);
+
+	return 0;
+}
+
+void dump_emi_mpu_regions(void)
+{
+	unsigned long apc[EMI_MPU_DGROUP_NUM], sa, ea;
+
+	int region, i;
+
+	/* Only dump 8 regions(max: EMI_MPU_REGION_NUM --> 32) */
+	for (region = 0; region < 8; ++region) {
+		for (i = 0; i < EMI_MPU_DGROUP_NUM; ++i)
+			apc[i] = mmio_read_32(EMI_MPU_APC(region, i));
+		sa = mmio_read_32(EMI_MPU_SA(region));
+		ea = mmio_read_32(EMI_MPU_EA(region));
+
+		WARN("region %d:\n", region);
+		WARN("\tsa:0x%lx, ea:0x%lx, apc0: 0x%lx apc1: 0x%lx\n",
+		     sa, ea, apc[0], apc[1]);
+	}
+}
+
+int emi_mpu_set_protection(struct emi_region_info_t *region_info)
+{
+	unsigned long start, end;
+	int i;
+
+	if (region_info->region >= EMI_MPU_REGION_NUM)
+		return -1;
+
+	start = (unsigned long)(region_info->start >> EMI_MPU_ALIGN_BITS) |
+		(region_info->region << 24);
+
+	for (i = EMI_MPU_DGROUP_NUM - 1; i >= 0; i--) {
+		end = (unsigned long)(region_info->end >> EMI_MPU_ALIGN_BITS) |
+			(i << 24);
+		_emi_mpu_set_protection(start, end, region_info->apc[i]);
+	}
+
+	return 0;
+}
+
+void emi_mpu_init(void)
+{
+	struct emi_region_info_t region_info;
+
+	/* reserve region 0 for future use */
+
+	/* PCI-e protect address(64MB) */
+	region_info.start = 0xC0000000ULL;
+	region_info.end = 0xC3FF0000ULL;
+	region_info.region = 1;
+	SET_ACCESS_PERMISSION(region_info.apc, 1,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, NO_PROT, NO_PROT);
+	emi_mpu_set_protection(&region_info);
+
+	/* SCP protect address */
+	region_info.start = 0x50000000ULL;
+	region_info.end = 0x513F0000ULL;
+	region_info.region = 2;
+	SET_ACCESS_PERMISSION(region_info.apc, 1,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      NO_PROT, FORBIDDEN, FORBIDDEN, NO_PROT);
+	emi_mpu_set_protection(&region_info);
+
+	/* DSP protect address */
+	region_info.start = 0x40000000ULL;	/* dram base addr */
+	region_info.end = 0x1FFFF0000ULL;
+	region_info.region = 3;
+	SET_ACCESS_PERMISSION(region_info.apc, 1,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROT);
+	emi_mpu_set_protection(&region_info);
+
+	/* Forbidden All */
+	region_info.start = 0x40000000ULL;	/* dram base addr */
+	region_info.end = 0x1FFFF0000ULL;
+	region_info.region = 4;
+	SET_ACCESS_PERMISSION(region_info.apc, 1,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN,
+			      FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROT);
+	emi_mpu_set_protection(&region_info);
+
+	dump_emi_mpu_regions();
+}
+
diff --git a/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.h b/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.h
new file mode 100644
index 0000000..0b15431
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/emi_mpu/emi_mpu.h
@@ -0,0 +1,102 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMI_MPU_H
+#define EMI_MPU_H
+
+#include <platform_def.h>
+
+#define EMI_MPUP		(EMI_BASE + 0x01D8)
+#define EMI_MPUQ		(EMI_BASE + 0x01E0)
+#define EMI_MPUR		(EMI_BASE + 0x01E8)
+#define EMI_MPUS		(EMI_BASE + 0x01F0)
+#define EMI_MPUT		(EMI_BASE + 0x01F8)
+#define EMI_MPUY		(EMI_BASE + 0x0220)
+#define EMI_MPU_CTRL		(EMI_MPU_BASE + 0x0000)
+#define EMI_MPUD0_ST		(EMI_BASE + 0x0160)
+#define EMI_MPUD1_ST		(EMI_BASE + 0x0164)
+#define EMI_MPUD2_ST		(EMI_BASE + 0x0168)
+#define EMI_MPUD3_ST		(EMI_BASE + 0x016C)
+#define EMI_MPUD0_ST2		(EMI_BASE + 0x0200)
+#define EMI_MPUD1_ST2		(EMI_BASE + 0x0204)
+#define EMI_MPUD2_ST2		(EMI_BASE + 0x0208)
+#define EMI_MPUD3_ST2		(EMI_BASE + 0x020C)
+
+#define EMI_PHY_OFFSET		(0x40000000UL)
+
+#define NO_PROT 		(0)
+#define SEC_RW			(1)
+#define SEC_RW_NSEC_R		(2)
+#define SEC_RW_NSEC_W		(3)
+#define SEC_R_NSEC_R		(4)
+#define FORBIDDEN		(5)
+#define SEC_R_NSEC_RW		(6)
+
+#define SECURE_OS_MPU_REGION_ID	(0)
+#define ATF_MPU_REGION_ID	(1)
+
+#define EMI_MPU_SA0		(EMI_MPU_BASE + 0x100)
+#define EMI_MPU_EA0		(EMI_MPU_BASE + 0x200)
+#define EMI_MPU_SA(region)	(EMI_MPU_SA0 + (region) * 4)
+#define EMI_MPU_EA(region)	(EMI_MPU_EA0 + (region) * 4)
+
+#define EMI_MPU_APC0			(EMI_MPU_BASE + 0x300)
+#define EMI_MPU_APC(region, dgroup)	(EMI_MPU_APC0 + (region) * 4 + \
+					(dgroup) * 0x100)
+
+#define EMI_MPU_CTRL_D0		(EMI_MPU_BASE + 0x800)
+#define EMI_MPU_CTRL_D(domain)	(EMI_MPU_CTRL_D0 + domain * 4)
+#define EMI_RG_MASK_D0		(EMI_MPU_BASE + 0x900)
+#define EMI_RG_MASK_D(domain)	(EMI_RG_MASK_D0 + domain * 4)
+
+#define EMI_MPU_DOMAIN_NUM	16
+#define EMI_MPU_REGION_NUM	32
+#define EMI_MPU_ALIGN_BITS	16
+#define DRAM_OFFSET		(0x40000000 >> EMI_MPU_ALIGN_BITS)
+
+#define EMI_MPU_DGROUP_NUM	(EMI_MPU_DOMAIN_NUM / 8)
+
+#if (EMI_MPU_DGROUP_NUM == 1)
+#define SET_ACCESS_PERMISSION(apc_ary, lock, d7, d6, d5, d4, d3, d2, d1, d0) \
+do { \
+	apc_ary[0] = 0; \
+	apc_ary[0] = \
+		(((unsigned int)    d7) << 21) | (((unsigned int)  d6) << 18) \
+		| (((unsigned int)  d5) << 15) | (((unsigned int)  d4) << 12) \
+		| (((unsigned int)  d3) <<  9) | (((unsigned int)  d2) <<  6) \
+		| (((unsigned int)  d1) <<  3) | ((unsigned int)   d0) \
+		| (((unsigned int) lock) << 31); \
+} while (0)
+#elif (EMI_MPU_DGROUP_NUM == 2)
+#define SET_ACCESS_PERMISSION(apc_ary, lock, d15, d14, d13, d12, d11, d10, \
+			      d9, d8, d7, d6, d5, d4, d3, d2, d1, d0) \
+do { \
+	apc_ary[1] = \
+		(((unsigned int)   d15) << 21) | (((unsigned int) d14) << 18) \
+		| (((unsigned int) d13) << 15) | (((unsigned int) d12) << 12) \
+		| (((unsigned int) d11) <<  9) | (((unsigned int) d10) <<  6) \
+		| (((unsigned int)  d9) <<  3) |  ((unsigned int)  d8); \
+	apc_ary[0] = \
+		(((unsigned int)    d7) << 21) | (((unsigned int)  d6) << 18) \
+		| (((unsigned int)  d5) << 15) | (((unsigned int)  d4) << 12) \
+		| (((unsigned int)  d3) <<  9) | (((unsigned int)  d2) <<  6) \
+		| (((unsigned int)  d1) <<  3) |  ((unsigned int)  d0) \
+		| (((unsigned int) lock) << 31); \
+} while (0)
+#endif
+
+struct emi_region_info_t {
+	unsigned long long	start;
+	unsigned long long	end;
+	unsigned int		region;
+	unsigned long		apc[EMI_MPU_DGROUP_NUM];
+};
+
+void emi_mpu_init(void);
+int emi_mpu_set_protection(struct emi_region_info_t *region_info);
+void dump_emi_mpu_regions(void);
+
+#endif  /* __EMI_MPU_H */
diff --git a/plat/mediatek/mt8192/drivers/gpio/mtgpio.c b/plat/mediatek/mt8192/drivers/gpio/mtgpio.c
index e07b75a..c78332d 100644
--- a/plat/mediatek/mt8192/drivers/gpio/mtgpio.c
+++ b/plat/mediatek/mt8192/drivers/gpio/mtgpio.c
@@ -5,94 +5,17 @@
  */
 
 #include <assert.h>
-#include <common/debug.h>
-#include <drivers/delay_timer.h>
-#include <drivers/gpio.h>
-#include <lib/mmio.h>
 #include <mtgpio.h>
 #include <platform_def.h>
 
-/******************************************************************************
- *Macro Definition
- ******************************************************************************/
-#define GPIO_MODE_BITS		4
-#define MAX_GPIO_MODE_PER_REG	8
-#define MAX_GPIO_REG_BITS	32
-#define DIR_BASE		(GPIO_BASE + 0x000)
-#define DOUT_BASE		(GPIO_BASE + 0x100)
-#define DIN_BASE		(GPIO_BASE + 0x200)
-#define MODE_BASE		(GPIO_BASE + 0x300)
-#define SET			0x4
-#define CLR			0x8
-
-static void mt_set_gpio_dir_chip(uint32_t pin, int dir)
-{
-	uint32_t pos, bit;
-
-	assert(pin < MAX_GPIO_PIN);
-	assert(dir < MT_GPIO_DIR_MAX);
-
-	pos = pin / MAX_GPIO_REG_BITS;
-	bit = pin % MAX_GPIO_REG_BITS;
-
-	if (dir == MT_GPIO_DIR_IN) {
-		mmio_write_32(DIR_BASE + 0x10U * pos + CLR, 1U << bit);
-	} else {
-		mmio_write_32(DIR_BASE + 0x10U * pos + SET, 1U << bit);
-	}
-}
-
-static int mt_get_gpio_dir_chip(uint32_t pin)
-{
-	uint32_t pos, bit;
-	uint32_t reg;
-
-	assert(pin < MAX_GPIO_PIN);
-
-	pos = pin / MAX_GPIO_REG_BITS;
-	bit = pin % MAX_GPIO_REG_BITS;
-
-	reg = mmio_read_32(DIR_BASE + 0x10U * pos);
-	return (((reg & (1U << bit)) != 0U) ? MT_GPIO_DIR_OUT : MT_GPIO_DIR_IN);
-}
-
-static void mt_set_gpio_out_chip(uint32_t pin, int output)
-{
-	uint32_t pos, bit;
-
-	assert(pin < MAX_GPIO_PIN);
-	assert(output < MT_GPIO_OUT_MAX);
-
-	pos = pin / MAX_GPIO_REG_BITS;
-	bit = pin % MAX_GPIO_REG_BITS;
-
-	if (output == MT_GPIO_OUT_ZERO) {
-		mmio_write_32(DOUT_BASE + 0x10U * pos + CLR, 1U << bit);
-	} else {
-		mmio_write_32(DOUT_BASE + 0x10U * pos + SET, 1U << bit);
-	}
-}
-
-static int mt_get_gpio_in_chip(uint32_t pin)
-{
-	uint32_t pos, bit;
-	uint32_t reg;
-
-	assert(pin < MAX_GPIO_PIN);
-
-	pos = pin / MAX_GPIO_REG_BITS;
-	bit = pin % MAX_GPIO_REG_BITS;
-
-	reg = mmio_read_32(DIN_BASE + 0x10U * pos);
-	return (((reg & (1U << bit)) != 0U) ? 1 : 0);
-}
-
-static uintptr_t mt_gpio_find_reg_addr(uint32_t pin)
+uintptr_t mt_gpio_find_reg_addr(uint32_t pin)
 {
 	uintptr_t reg_addr = 0U;
 	struct mt_pin_info gpio_info;
 
-	gpio_info = mt8192_pin_infos[pin];
+	assert(pin < MAX_GPIO_PIN);
+
+	gpio_info = mt_pin_infos[pin];
 
 	switch (gpio_info.base & 0x0f) {
 	case 0:
@@ -128,213 +51,3 @@
 
 	return reg_addr;
 }
-
-static void mt_gpio_set_spec_pull_pupd(uint32_t pin, int enable,
-			       int select)
-{
-	uintptr_t reg1;
-	uintptr_t reg2;
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	uint32_t bit = gpio_info.bit;
-
-	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
-	reg2 = reg1 + (gpio_info.base & 0xf0);
-	if (enable == MT_GPIO_PULL_ENABLE) {
-		mmio_write_32(reg2 + SET, (1U << bit));
-		if (select == MT_GPIO_PULL_DOWN) {
-			mmio_write_32(reg1 + SET, (1U << bit));
-		} else {
-			mmio_write_32(reg1 + CLR, (1U << bit));
-		}
-	} else {
-		mmio_write_32(reg2 + CLR, (1U << bit));
-		mmio_write_32((reg2 + 0x010U) + CLR, (1U << bit));
-	}
-}
-
-static void mt_gpio_set_pull_pu_pd(uint32_t pin, int enable,
-				 int select)
-{
-	uintptr_t reg1;
-	uintptr_t reg2;
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	uint32_t bit = gpio_info.bit;
-
-	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
-	reg2 = reg1 - (gpio_info.base & 0xf0);
-
-	if (enable == MT_GPIO_PULL_ENABLE) {
-		if (select == MT_GPIO_PULL_DOWN) {
-			mmio_write_32(reg1 + CLR, (1U << bit));
-			mmio_write_32(reg2 + SET, (1U << bit));
-		} else {
-			mmio_write_32(reg2 + CLR, (1U << bit));
-			mmio_write_32(reg1 + SET, (1U << bit));
-		}
-	} else {
-		mmio_write_32(reg1 + CLR, (1U << bit));
-		mmio_write_32(reg2 + CLR, (1U << bit));
-	}
-}
-
-static void mt_gpio_set_pull_chip(uint32_t pin, int enable,
-		   int select)
-{
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	if (gpio_info.flag) {
-		mt_gpio_set_spec_pull_pupd(pin, enable, select);
-	} else {
-		mt_gpio_set_pull_pu_pd(pin, enable, select);
-	}
-}
-
-static int mt_gpio_get_spec_pull_pupd(uint32_t pin)
-{
-	uintptr_t reg1;
-	uintptr_t reg2;
-	uint32_t r0;
-	uint32_t r1;
-
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	uint32_t bit = gpio_info.bit;
-
-	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
-	reg2 = reg1 + (gpio_info.base & 0xf0);
-
-	r0 = (mmio_read_32(reg2) >> bit) & 1U;
-	r1 = (mmio_read_32(reg2 + 0x010) >> bit) & 1U;
-	if (r0 == 0U && r1 == 0U) {
-		return MT_GPIO_PULL_NONE;
-	} else {
-		if (mmio_read_32(reg1) & (1U << bit)) {
-			return MT_GPIO_PULL_DOWN;
-		} else {
-			return MT_GPIO_PULL_UP;
-		}
-	}
-}
-
-static int mt_gpio_get_pull_pu_pd(uint32_t pin)
-{
-	uintptr_t reg1;
-	uintptr_t reg2;
-	uint32_t pu;
-	uint32_t pd;
-
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	uint32_t bit = gpio_info.bit;
-
-	reg1 = mt_gpio_find_reg_addr(pin) + gpio_info.offset;
-	reg2 = reg1 - (gpio_info.base & 0xf0);
-	pu = (mmio_read_32(reg1) >> bit) & 1U;
-	pd = (mmio_read_32(reg2) >> bit) & 1U;
-	if (pu == 1U) {
-		return MT_GPIO_PULL_UP;
-	} else if (pd == 1U) {
-		return MT_GPIO_PULL_DOWN;
-	} else {
-		return MT_GPIO_PULL_NONE;
-	}
-}
-
-static int mt_gpio_get_pull_chip(uint32_t pin)
-{
-	struct mt_pin_info gpio_info;
-
-	gpio_info = mt8192_pin_infos[pin];
-	if (gpio_info.flag) {
-		return mt_gpio_get_spec_pull_pupd(pin);
-	} else {
-		return mt_gpio_get_pull_pu_pd(pin);
-	}
-}
-
-static void mt_set_gpio_pull_select_chip(uint32_t pin, int sel)
-{
-	assert(pin < MAX_GPIO_PIN);
-
-	if (sel == MT_GPIO_PULL_NONE) {
-		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_DISABLE, MT_GPIO_PULL_DOWN);
-	} else if (sel == MT_GPIO_PULL_UP) {
-		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_ENABLE, MT_GPIO_PULL_UP);
-	} else if (sel == MT_GPIO_PULL_DOWN) {
-		mt_gpio_set_pull_chip(pin, MT_GPIO_PULL_ENABLE, MT_GPIO_PULL_DOWN);
-	}
-}
-
-/* get pull-up or pull-down, regardless of resistor value */
-static int mt_get_gpio_pull_select_chip(uint32_t pin)
-{
-	assert(pin < MAX_GPIO_PIN);
-
-	return mt_gpio_get_pull_chip(pin);
-}
-
-static void mt_set_gpio_dir(int gpio, int direction)
-{
-	mt_set_gpio_dir_chip((uint32_t)gpio, direction);
-}
-
-static int mt_get_gpio_dir(int gpio)
-{
-	uint32_t pin;
-
-	pin = (uint32_t)gpio;
-	return mt_get_gpio_dir_chip(pin);
-}
-
-static void mt_set_gpio_pull(int gpio, int pull)
-{
-	uint32_t pin;
-
-	pin = (uint32_t)gpio;
-	mt_set_gpio_pull_select_chip(pin, pull);
-}
-
-static int mt_get_gpio_pull(int gpio)
-{
-	uint32_t pin;
-
-	pin = (uint32_t)gpio;
-	return mt_get_gpio_pull_select_chip(pin);
-}
-
-static void mt_set_gpio_out(int gpio, int value)
-{
-	uint32_t pin;
-
-	pin = (uint32_t)gpio;
-	mt_set_gpio_out_chip(pin, value);
-}
-
-static int mt_get_gpio_in(int gpio)
-{
-	uint32_t pin;
-
-	pin = (uint32_t)gpio;
-	return mt_get_gpio_in_chip(pin);
-}
-
-const gpio_ops_t mtgpio_ops = {
-	 .get_direction = mt_get_gpio_dir,
-	 .set_direction = mt_set_gpio_dir,
-	 .get_value = mt_get_gpio_in,
-	 .set_value = mt_set_gpio_out,
-	 .set_pull = mt_set_gpio_pull,
-	 .get_pull = mt_get_gpio_pull,
-};
-
-void plat_mt8192_gpio_init(void)
-{
-	gpio_init(&mtgpio_ops);
-}
diff --git a/plat/mediatek/mt8192/drivers/gpio/mtgpio.h b/plat/mediatek/mt8192/drivers/gpio/mtgpio.h
index ca0c964..d3aa24d 100644
--- a/plat/mediatek/mt8192/drivers/gpio/mtgpio.h
+++ b/plat/mediatek/mt8192/drivers/gpio/mtgpio.h
@@ -7,17 +7,7 @@
 #ifndef MT_GPIO_H
 #define MT_GPIO_H
 
-#include <stdbool.h>
-#include <stdint.h>
-
-#include <plat/common/common_def.h>
-
-/*  Error Code No. */
-#define RSUCCESS        0
-#define ERACCESS        1
-#define ERINVAL         2
-#define ERWRAPPER       3
-#define MAX_GPIO_PIN    MT_GPIO_BASE_MAX
+#include <mtgpio_common.h>
 
 /* Enumeration for GPIO pin */
 typedef enum GPIO_PIN {
@@ -54,110 +44,7 @@
 	MT_GPIO_BASE_MAX
 } GPIO_PIN;
 
-/* GPIO MODE CONTROL VALUE*/
-typedef enum {
-	GPIO_MODE_UNSUPPORTED = -1,
-	GPIO_MODE_GPIO  = 0,
-	GPIO_MODE_00    = 0,
-	GPIO_MODE_01,
-	GPIO_MODE_02,
-	GPIO_MODE_03,
-	GPIO_MODE_04,
-	GPIO_MODE_05,
-	GPIO_MODE_06,
-	GPIO_MODE_07,
-
-	GPIO_MODE_MAX,
-	GPIO_MODE_DEFAULT = GPIO_MODE_00,
-} GPIO_MODE;
-
-/* GPIO DIRECTION */
-typedef enum {
-	MT_GPIO_DIR_UNSUPPORTED = -1,
-	MT_GPIO_DIR_OUT    = 0,
-	MT_GPIO_DIR_IN     = 1,
-	MT_GPIO_DIR_MAX,
-	MT_GPIO_DIR_DEFAULT = MT_GPIO_DIR_IN,
-} GPIO_DIR;
-
-/* GPIO PULL ENABLE*/
-typedef enum {
-	MT_GPIO_PULL_EN_UNSUPPORTED = -1,
-	MT_GPIO_PULL_DISABLE   = 0,
-	MT_GPIO_PULL_ENABLE    = 1,
-	MT_GPIO_PULL_ENABLE_R0 = 2,
-	MT_GPIO_PULL_ENABLE_R1 = 3,
-	MT_GPIO_PULL_ENABLE_R0R1 = 4,
-
-	MT_GPIO_PULL_EN_MAX,
-	MT_GPIO_PULL_EN_DEFAULT = MT_GPIO_PULL_ENABLE,
-} GPIO_PULL_EN;
-
-/* GPIO PULL-UP/PULL-DOWN*/
-typedef enum {
-	MT_GPIO_PULL_UNSUPPORTED = -1,
-	MT_GPIO_PULL_NONE        = 0,
-	MT_GPIO_PULL_UP          = 1,
-	MT_GPIO_PULL_DOWN        = 2,
-	MT_GPIO_PULL_MAX,
-	MT_GPIO_PULL_DEFAULT = MT_GPIO_PULL_DOWN
-} GPIO_PULL;
-
-/* GPIO OUTPUT */
-typedef enum {
-	MT_GPIO_OUT_UNSUPPORTED = -1,
-	MT_GPIO_OUT_ZERO = 0,
-	MT_GPIO_OUT_ONE  = 1,
-
-	MT_GPIO_OUT_MAX,
-	MT_GPIO_OUT_DEFAULT = MT_GPIO_OUT_ZERO,
-	MT_GPIO_DATA_OUT_DEFAULT = MT_GPIO_OUT_ZERO,  /*compatible with DCT*/
-} GPIO_OUT;
-
-/* GPIO INPUT */
-typedef enum {
-	MT_GPIO_IN_UNSUPPORTED = -1,
-	MT_GPIO_IN_ZERO = 0,
-	MT_GPIO_IN_ONE  = 1,
-
-	MT_GPIO_IN_MAX,
-} GPIO_IN;
-
-typedef struct {
-	uint32_t val;
-	uint32_t set;
-	uint32_t rst;
-	uint32_t _align1;
-} VAL_REGS;
-
-typedef struct {
-	VAL_REGS dir[7];
-	uint8_t rsv00[144];
-	VAL_REGS dout[7];
-	uint8_t rsv01[144];
-	VAL_REGS din[7];
-	uint8_t rsv02[144];
-	VAL_REGS mode[28];
-} GPIO_REGS;
-
-
-#define PIN(_id, _flag, _bit, _base, _offset) {		\
-		.id = _id,				\
-		.flag = _flag,				\
-		.bit = _bit,				\
-		.base = _base,				\
-		.offset = _offset,			\
-	}
-
-struct mt_pin_info {
-	uint8_t id;
-	uint8_t flag;
-	uint8_t bit;
-	uint16_t base;
-	uint16_t offset;
-};
-
-static const struct mt_pin_info mt8192_pin_infos[] = {
+static const struct mt_pin_info mt_pin_infos[] = {
 	PIN(0, 0, 9, 0x23, 0xb0),
 	PIN(1, 0, 10, 0x23, 0xb0),
 	PIN(2, 0, 11, 0x23, 0xb0),
@@ -379,6 +266,4 @@
 	PIN(218, 0, 1, 0x14, 0x50),
 	PIN(219, 0, 2, 0x14, 0x50),
 };
-
-void plat_mt8192_gpio_init(void);
 #endif /* MT_GPIO_H */
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm.c b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm.c
new file mode 100644
index 0000000..b483c36
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm.c
@@ -0,0 +1,149 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <lib/psci/psci.h>
+#include <lib/spinlock.h>
+
+#include <mt_cpu_pm_cpc.h>
+#include <mt_lp_irqremain.h>
+#include <mt_lp_rm.h>
+#include <mt_mcdi.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+
+DEFINE_SYSREG_RW_FUNCS(dbgprcr_el1);
+
+static int plat_mt_lp_cpu_rc;
+
+static int pwr_state_prompt(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_state_reflect(unsigned int cpu, const psci_power_state_t *state)
+{
+	mtk_cpc_core_on_hint_clr(cpu);
+
+	if (IS_SYSTEM_SUSPEND_STATE(state)) {
+		mtk_cpc_time_sync();
+	}
+
+	return 0;
+}
+
+static int pwr_cpu_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_cpu_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	/* clear DBGPRCR.CORENPDRQ to allow CPU power down  */
+	write_dbgprcr_el1(0ULL);
+
+	return 0;
+}
+
+static int pwr_cluster_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_cluster_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_mcusys_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	if (!IS_MCUSYS_OFF_STATE(state) || (plat_mt_lp_cpu_rc < 0)) {
+		return -1;
+	}
+
+	mtk_cpc_mcusys_off_reflect();
+
+	return 0;
+}
+
+static int pwr_mcusys_pwron_finished(unsigned int cpu,
+					const psci_power_state_t *state)
+{
+	int state_id = state->pwr_domain_state[MTK_AFFLVL_MCUSYS];
+
+	if (!IS_MCUSYS_OFF_STATE(state) || (plat_mt_lp_cpu_rc < 0)) {
+		return -1;
+	}
+
+	mt_lp_rm_reset_constraint(plat_mt_lp_cpu_rc, cpu, state_id);
+	mt_lp_irqremain_release();
+
+	return 0;
+}
+
+static int pwr_mcusys_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	int state_id = state->pwr_domain_state[MTK_AFFLVL_MCUSYS];
+
+	if (!IS_MCUSYS_OFF_STATE(state)) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	if (mcdi_try_init() != 0) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	if (mtk_cpc_mcusys_off_prepare() != CPC_SUCCESS) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	plat_mt_lp_cpu_rc =
+		mt_lp_rm_find_and_run_constraint(0, cpu, state_id, NULL);
+
+	if (plat_mt_lp_cpu_rc < 0) {
+		goto mt_pwr_mcusysoff_reflect;
+	}
+
+	mt_lp_irqremain_aquire();
+
+	return 0;
+
+mt_pwr_mcusysoff_reflect:
+	mtk_cpc_mcusys_off_reflect();
+
+mt_pwr_mcusysoff_break:
+	plat_mt_lp_cpu_rc = -1;
+
+	return -1;
+}
+
+static const struct mt_lpm_tz plat_pm = {
+	.pwr_prompt			= pwr_state_prompt,
+	.pwr_reflect			= pwr_state_reflect,
+	.pwr_cpu_on			= pwr_cpu_pwron,
+	.pwr_cpu_dwn			= pwr_cpu_pwrdwn,
+	.pwr_cluster_on			= pwr_cluster_pwron,
+	.pwr_cluster_dwn		= pwr_cluster_pwrdwn,
+	.pwr_mcusys_dwn			= pwr_mcusys_pwrdwn,
+	.pwr_mcusys_on			= pwr_mcusys_pwron,
+	.pwr_mcusys_on_finished		= pwr_mcusys_pwron_finished
+};
+
+const struct mt_lpm_tz *mt_plat_cpu_pm_init(void)
+{
+	mtk_cpc_init();
+
+	if (mcdi_try_init() == 0) {
+		INFO("MCDI init done.\n");
+	}
+
+	mt_lp_irqremain_init();
+
+	return &plat_pm;
+}
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.c b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.c
new file mode 100644
index 0000000..f8c51a1
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.c
@@ -0,0 +1,269 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <drivers/delay_timer.h>
+
+#include <mt_cpu_pm_cpc.h>
+#include <mt_timer.h>
+
+struct mtk_cpc_dev {
+	int auto_off;
+	unsigned int auto_thres_tick;
+};
+
+static struct mtk_cpc_dev cpc;
+
+static int mtk_cpc_last_core_prot(uint32_t prot_req,
+				uint32_t resp_reg, uint32_t resp_ofs)
+{
+	uint32_t sta, retry;
+
+	retry = 0U;
+
+	while (retry++ < RETRY_CNT_MAX) {
+
+		mmio_write_32(CPC_MCUSYS_LAST_CORE_REQ, prot_req);
+
+		udelay(1U);
+
+		sta = (mmio_read_32(resp_reg) >> resp_ofs) & CPC_PROT_RESP_MASK;
+
+		if (sta == PROT_SUCCESS) {
+			return CPC_SUCCESS;
+		} else if (sta == PROT_GIVEUP) {
+			return CPC_ERR_FAIL;
+		}
+	}
+
+	return CPC_ERR_TIMEOUT;
+}
+
+int mtk_cpu_pm_mcusys_prot_aquire(void)
+{
+	return mtk_cpc_last_core_prot(
+			MCUSYS_PROT_SET,
+			CPC_MCUSYS_LAST_CORE_RESP,
+			MCUSYS_RESP_OFS);
+}
+
+void mtk_cpu_pm_mcusys_prot_release(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_ON_MASK, MCUSYS_PROT_CLR);
+}
+
+int mtk_cpu_pm_cluster_prot_aquire(unsigned int cluster)
+{
+	return mtk_cpc_last_core_prot(
+			CPUSYS_PROT_SET,
+			CPC_MCUSYS_MP_LAST_CORE_RESP,
+			CPUSYS_RESP_OFS);
+}
+
+void mtk_cpu_pm_cluster_prot_release(unsigned int cluster)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_ON_MASK, CPUSYS_PROT_CLR);
+}
+
+static void mtk_cpc_cluster_cnt_backup(void)
+{
+	uint32_t backup_cnt;
+	uint32_t curr_cnt;
+	uint32_t cnt_mask = GENMASK(14, 0);
+	uint32_t clr_mask = GENMASK(1, 0);
+
+	/* Single Cluster */
+	backup_cnt = mmio_read_32(CPC_CLUSTER_CNT_BACKUP);
+	curr_cnt = mmio_read_32(CPC_MCUSYS_CLUSTER_COUNTER);
+
+	/* Get off count if dormant count is 0 */
+	if ((curr_cnt & cnt_mask) == 0U) {
+		curr_cnt = (curr_cnt >> 16) & cnt_mask;
+	} else {
+		curr_cnt = curr_cnt & cnt_mask;
+	}
+
+	mmio_write_32(CPC_CLUSTER_CNT_BACKUP, backup_cnt + curr_cnt);
+	mmio_write_32(CPC_MCUSYS_CLUSTER_COUNTER_CLR, clr_mask);
+}
+
+static inline void mtk_cpc_mcusys_off_en(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_CTRL, 1U);
+}
+
+static inline void mtk_cpc_mcusys_off_dis(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_CTRL, 0U);
+}
+
+void mtk_cpc_mcusys_off_reflect(void)
+{
+	mtk_cpc_mcusys_off_dis();
+	mtk_cpu_pm_mcusys_prot_release();
+}
+
+int mtk_cpc_mcusys_off_prepare(void)
+{
+	if (mtk_cpu_pm_mcusys_prot_aquire() != CPC_SUCCESS) {
+		return CPC_ERR_FAIL;
+	}
+
+	mtk_cpc_cluster_cnt_backup();
+	mtk_cpc_mcusys_off_en();
+
+	return CPC_SUCCESS;
+}
+
+void mtk_cpc_core_on_hint_set(unsigned int cpu)
+{
+	mmio_write_32(CPC_MCUSYS_CPU_ON_SW_HINT_SET, BIT(cpu));
+}
+
+void mtk_cpc_core_on_hint_clr(unsigned int cpu)
+{
+	mmio_write_32(CPC_MCUSYS_CPU_ON_SW_HINT_CLR, BIT(cpu));
+}
+
+static void mtk_cpc_dump_timestamp(void)
+{
+	uint32_t id;
+
+	for (id = 0U; id < CPC_TRACE_ID_NUM; id++) {
+		mmio_write_32(CPC_MCUSYS_TRACE_SEL, id);
+
+		memcpy((void *)(uintptr_t)CPC_TRACE_SRAM(id),
+				(const void *)(uintptr_t)CPC_MCUSYS_TRACE_DATA,
+				CPC_TRACE_SIZE);
+	}
+}
+
+void mtk_cpc_time_sync(void)
+{
+	uint64_t kt;
+	uint32_t systime_l, systime_h;
+
+	kt = sched_clock();
+	systime_l = mmio_read_32(CNTSYS_L_REG);
+	systime_h = mmio_read_32(CNTSYS_H_REG);
+
+	/* sync kernel timer to cpc */
+	mmio_write_32(CPC_MCUSYS_CPC_KERNEL_TIME_L_BASE, (uint32_t)kt);
+	mmio_write_32(CPC_MCUSYS_CPC_KERNEL_TIME_H_BASE, (uint32_t)(kt >> 32));
+	/* sync system timer to cpc */
+	mmio_write_32(CPC_MCUSYS_CPC_SYSTEM_TIME_L_BASE, systime_l);
+	mmio_write_32(CPC_MCUSYS_CPC_SYSTEM_TIME_H_BASE, systime_h);
+}
+
+static void mtk_cpc_config(uint32_t cfg, uint32_t data)
+{
+	uint32_t val;
+	uint32_t reg = 0U;
+
+	switch (cfg) {
+	case CPC_SMC_CONFIG_PROF:
+		reg = CPC_MCUSYS_CPC_DBG_SETTING;
+		val = mmio_read_32(reg);
+		val = (data != 0U) ? (val | CPC_PROF_EN) : (val & ~CPC_PROF_EN);
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF:
+		reg = CPC_MCUSYS_CPC_FLOW_CTRL_CFG;
+		val = mmio_read_32(reg);
+		if (data != 0U) {
+			val |= CPC_AUTO_OFF_EN;
+			cpc.auto_off = 1;
+		} else {
+			val &= ~CPC_AUTO_OFF_EN;
+			cpc.auto_off = 0;
+		}
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF_THRES:
+		reg = CPC_MCUSYS_CPC_OFF_THRES;
+		cpc.auto_thres_tick = us_to_ticks(data);
+		val = cpc.auto_thres_tick;
+		break;
+	case CPC_SMC_CONFIG_CNT_CLR:
+		reg = CPC_MCUSYS_CLUSTER_COUNTER_CLR;
+		val = GENMASK(1, 0);	/* clr_mask */
+		break;
+	case CPC_SMC_CONFIG_TIME_SYNC:
+		mtk_cpc_time_sync();
+		break;
+	default:
+		break;
+	}
+
+	if (reg != 0U) {
+		mmio_write_32(reg, val);
+	}
+}
+
+static uint32_t mtk_cpc_read_config(uint32_t cfg)
+{
+	uint32_t res = 0U;
+
+	switch (cfg) {
+	case CPC_SMC_CONFIG_PROF:
+		res = (mmio_read_32(CPC_MCUSYS_CPC_DBG_SETTING) & CPC_PROF_EN) ?
+			1U : 0U;
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF:
+		res = cpc.auto_off;
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF_THRES:
+		res = ticks_to_us(cpc.auto_thres_tick);
+		break;
+	case CPC_SMC_CONFIG_CNT_CLR:
+		break;
+	default:
+		break;
+	}
+
+	return res;
+}
+
+uint64_t mtk_cpc_handler(uint64_t act, uint64_t arg1, uint64_t arg2)
+{
+	uint64_t res = 0ULL;
+
+	switch (act) {
+	case CPC_SMC_EVENT_DUMP_TRACE_DATA:
+		mtk_cpc_dump_timestamp();
+		break;
+	case CPC_SMC_EVENT_GIC_DPG_SET:
+		/* isolated_status = x2; */
+		break;
+	case CPC_SMC_EVENT_CPC_CONFIG:
+		mtk_cpc_config((uint32_t)arg1, (uint32_t)arg2);
+		break;
+	case CPC_SMC_EVENT_READ_CONFIG:
+		res = mtk_cpc_read_config((uint32_t)arg1);
+		break;
+	default:
+		break;
+	}
+
+	return res;
+}
+
+void mtk_cpc_init(void)
+{
+	mmio_write_32(CPC_MCUSYS_CPC_DBG_SETTING,
+			mmio_read_32(CPC_MCUSYS_CPC_DBG_SETTING)
+			| CPC_DBG_EN
+			| CPC_CALC_EN);
+
+	cpc.auto_off = 1;
+	cpc.auto_thres_tick = us_to_ticks(8000);
+
+	mmio_write_32(CPC_MCUSYS_CPC_FLOW_CTRL_CFG,
+			mmio_read_32(CPC_MCUSYS_CPC_FLOW_CTRL_CFG)
+			| CPC_OFF_PRE_EN
+			| (cpc.auto_off ? CPC_AUTO_OFF_EN : 0U));
+
+	mmio_write_32(CPC_MCUSYS_CPC_OFF_THRES, cpc.auto_thres_tick);
+}
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.h b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.h
new file mode 100644
index 0000000..19dd6a2
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_cpu_pm_cpc.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_CPU_PM_CPC_H
+#define MT_CPU_PM_CPC_H
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mcucfg.h>
+#include <platform_def.h>
+
+#define NEED_CPUSYS_PROT_WORKAROUND	1
+
+/* system sram registers */
+#define CPUIDLE_SRAM_REG(r)	(uint32_t)(MTK_MCDI_SRAM_BASE + (r))
+
+/* db dump */
+#define CPC_TRACE_SIZE		U(0x20)
+#define CPC_TRACE_ID_NUM	U(10)
+#define CPC_TRACE_SRAM(id)	(CPUIDLE_SRAM_REG(0x10) + (id) * CPC_TRACE_SIZE)
+
+/* buckup off count */
+#define CPC_CLUSTER_CNT_BACKUP	CPUIDLE_SRAM_REG(0x1F0)
+#define CPC_MCUSYS_CNT		CPUIDLE_SRAM_REG(0x1F4)
+
+/* CPC_MCUSYS_CPC_FLOW_CTRL_CFG(0xA814): debug setting */
+#define CPC_PWR_ON_SEQ_DIS	BIT(1)
+#define CPC_PWR_ON_PRIORITY	BIT(2)
+#define CPC_AUTO_OFF_EN		BIT(5)
+#define CPC_DORMANT_WAIT_EN	BIT(14)
+#define CPC_CTRL_EN		BIT(16)
+#define CPC_OFF_PRE_EN		BIT(29)
+
+/* CPC_MCUSYS_LAST_CORE_REQ(0xA818) : last core protection */
+#define CPUSYS_PROT_SET		BIT(0)
+#define MCUSYS_PROT_SET		BIT(8)
+#define CPUSYS_PROT_CLR		BIT(8)
+#define MCUSYS_PROT_CLR		BIT(9)
+
+#define CPC_PROT_RESP_MASK	U(0x3)
+#define CPUSYS_RESP_OFS		U(16)
+#define MCUSYS_RESP_OFS		U(30)
+
+#define cpusys_resp(r)		(((r) >> CPUSYS_RESP_OFS) & CPC_PROT_RESP_MASK)
+#define mcusys_resp(r)		(((r) >> MCUSYS_RESP_OFS) & CPC_PROT_RESP_MASK)
+
+#define RETRY_CNT_MAX		U(1000)
+
+#define PROT_RETRY		U(0)
+#define PROT_SUCCESS		U(1)
+#define PROT_GIVEUP		U(2)
+
+/* CPC_MCUSYS_CPC_DBG_SETTING(0xAB00): debug setting */
+#define CPC_PROF_EN		BIT(0)
+#define CPC_DBG_EN		BIT(1)
+#define CPC_FREEZE		BIT(2)
+#define CPC_CALC_EN		BIT(3)
+
+enum {
+	CPC_SUCCESS = 0,
+
+	CPC_ERR_FAIL,
+	CPC_ERR_TIMEOUT,
+
+	NF_CPC_ERR
+};
+
+enum {
+	CPC_SMC_EVENT_DUMP_TRACE_DATA,
+	CPC_SMC_EVENT_GIC_DPG_SET,
+	CPC_SMC_EVENT_CPC_CONFIG,
+	CPC_SMC_EVENT_READ_CONFIG,
+
+	NF_CPC_SMC_EVENT
+};
+
+enum {
+	CPC_SMC_CONFIG_PROF,
+	CPC_SMC_CONFIG_AUTO_OFF,
+	CPC_SMC_CONFIG_AUTO_OFF_THRES,
+	CPC_SMC_CONFIG_CNT_CLR,
+	CPC_SMC_CONFIG_TIME_SYNC,
+
+	NF_CPC_SMC_CONFIG
+};
+
+#define us_to_ticks(us)		((us) * 13)
+#define ticks_to_us(tick)	((tick) / 13)
+
+int mtk_cpu_pm_cluster_prot_aquire(unsigned int cluster);
+void mtk_cpu_pm_cluster_prot_release(unsigned int cluster);
+
+void mtk_cpc_mcusys_off_reflect(void);
+int mtk_cpc_mcusys_off_prepare(void);
+
+void mtk_cpc_core_on_hint_set(unsigned int cpu);
+void mtk_cpc_core_on_hint_clr(unsigned int cpu);
+void mtk_cpc_time_sync(void);
+
+uint64_t mtk_cpc_handler(uint64_t act, uint64_t arg1, uint64_t arg2);
+void mtk_cpc_init(void);
+
+#endif /* MT_CPU_PM_CPC_H */
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.c b/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.c
new file mode 100644
index 0000000..e74d3e7
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.c
@@ -0,0 +1,150 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <mt_lp_rm.h>
+#include <mt_lp_irqremain.h>
+#include <mtk_cirq.h>
+#include <plat_mtk_lpm.h>
+
+#define EDMA0_IRQ_ID		U(448)
+#define MDLA_IRQ_ID		U(446)
+#define MALI4_IRQ_ID		U(399)
+#define MALI3_IRQ_ID		U(398)
+#define MALI2_IRQ_ID		U(397)
+#define MALI1_IRQ_ID		U(396)
+#define MALI0_IRQ_ID		U(395)
+#define VPU_CORE1_IRQ_ID	U(453)
+#define VPU_CORE0_IRQ_ID	U(452)
+#define MD_WDT_IRQ_ID		U(110)
+#define KEYPAD_IRQ_ID		U(106)
+
+#define MD_WDT_WAKESRC		0x2000000
+#define KEYPAD_WAKESRC		0x4
+
+static struct mt_irqremain remain_irqs;
+
+int mt_lp_irqremain_submit(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	set_wakeup_sources(remain_irqs.irqs, remain_irqs.count);
+	mt_lp_rm_do_update(-1, PLAT_RC_UPDATE_REMAIN_IRQS, &remain_irqs);
+
+	return 0;
+}
+
+int mt_lp_irqremain_aquire(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	mt_cirq_sw_reset();
+	mt_cirq_clone_gic();
+	mt_cirq_enable();
+
+	return 0;
+}
+
+int mt_lp_irqremain_release(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	mt_cirq_flush();
+	mt_cirq_disable();
+
+	return 0;
+}
+
+void mt_lp_irqremain_init(void)
+{
+	uint32_t idx;
+
+	remain_irqs.count = 0;
+
+	/* level edma0 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = EDMA0_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mdla */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MDLA_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mali4 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MALI4_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mali3 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MALI3_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mali2 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MALI2_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mali1 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MALI1_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level mali0 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MALI0_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level vpu core1 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = VPU_CORE1_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* level vpu core0 */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = VPU_CORE0_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = 0;
+	remain_irqs.count++;
+
+	/* edge mdwdt */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = MD_WDT_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = MD_WDT_WAKESRC;
+	remain_irqs.count++;
+
+	/* edge keypad */
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = KEYPAD_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = KEYPAD_WAKESRC;
+	remain_irqs.count++;
+
+	mt_lp_irqremain_submit();
+}
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.h b/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.h
new file mode 100644
index 0000000..cbed967
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_lp_irqremain.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_LP_IRQREMAIN_H
+#define MT_LP_IRQREMAIN_H
+
+extern int mt_lp_irqremain_submit(void);
+extern int mt_lp_irqremain_aquire(void);
+extern int mt_lp_irqremain_release(void);
+extern void mt_lp_irqremain_init(void);
+#endif /* MT_LP_IRQREMAIN_H */
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.c b/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.c
new file mode 100644
index 0000000..1635b67
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.c
@@ -0,0 +1,151 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <cdefs.h>
+#include <common/debug.h>
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mt_mcdi.h>
+
+/* Read/Write */
+#define APMCU_MCUPM_MBOX_AP_READY	U(0)
+#define APMCU_MCUPM_MBOX_RESERVED_1	U(1)
+#define APMCU_MCUPM_MBOX_RESERVED_2	U(2)
+#define APMCU_MCUPM_MBOX_RESERVED_3	U(3)
+#define APMCU_MCUPM_MBOX_PWR_CTRL_EN	U(4)
+#define APMCU_MCUPM_MBOX_L3_CACHE_MODE	U(5)
+#define APMCU_MCUPM_MBOX_BUCK_MODE	U(6)
+#define APMCU_MCUPM_MBOX_ARMPLL_MODE	U(7)
+/* Read only */
+#define APMCU_MCUPM_MBOX_TASK_STA	U(8)
+#define APMCU_MCUPM_MBOX_RESERVED_9	U(9)
+#define APMCU_MCUPM_MBOX_RESERVED_10	U(10)
+#define APMCU_MCUPM_MBOX_RESERVED_11	U(11)
+
+/* CPC mode - Read/Write */
+#define APMCU_MCUPM_MBOX_WAKEUP_CPU	U(12)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_PWR_CTRL_EN */
+#define MCUPM_MCUSYS_CTRL		BIT(0)
+#define MCUPM_BUCK_CTRL			BIT(1)
+#define MCUPM_ARMPLL_CTRL		BIT(2)
+#define MCUPM_CM_CTRL			BIT(3)
+#define MCUPM_PWR_CTRL_MASK		GENMASK(3, 0)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_BUCK_MODE */
+#define MCUPM_BUCK_NORMAL_MODE		U(0) /* default */
+#define MCUPM_BUCK_LP_MODE		U(1)
+#define MCUPM_BUCK_OFF_MODE		U(2)
+#define NF_MCUPM_BUCK_MODE		U(3)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_ARMPLL_MODE */
+#define MCUPM_ARMPLL_ON			U(0) /* default */
+#define MCUPM_ARMPLL_GATING		U(1)
+#define MCUPM_ARMPLL_OFF		U(2)
+#define NF_MCUPM_ARMPLL_MODE		U(3)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_TASK_STA */
+#define MCUPM_TASK_UNINIT		U(0)
+#define MCUPM_TASK_INIT			U(1)
+#define MCUPM_TASK_INIT_FINISH		U(2)
+#define MCUPM_TASK_WAIT			U(3)
+#define MCUPM_TASK_RUN			U(4)
+#define MCUPM_TASK_PAUSE		U(5)
+
+#define SSPM_MBOX_3_BASE		U(0x0c55fce0)
+
+#define MCDI_NOT_INIT			0
+#define MCDI_INIT_1			1
+#define MCDI_INIT_2			2
+#define MCDI_INIT_DONE			3
+
+static int mcdi_init_status __section("tzfw_coherent_mem");
+
+static inline uint32_t mcdi_mbox_read(uint32_t id)
+{
+	return mmio_read_32(SSPM_MBOX_3_BASE + (id << 2));
+}
+
+static inline void mcdi_mbox_write(uint32_t id, uint32_t val)
+{
+	mmio_write_32(SSPM_MBOX_3_BASE + (id << 2), val);
+}
+
+static void mtk_mcupm_pwr_ctrl_setting(uint32_t dev)
+{
+	mcdi_mbox_write(APMCU_MCUPM_MBOX_PWR_CTRL_EN, dev);
+}
+
+static void mtk_set_mcupm_pll_mode(uint32_t mode)
+{
+	if (mode < NF_MCUPM_ARMPLL_MODE) {
+		mcdi_mbox_write(APMCU_MCUPM_MBOX_ARMPLL_MODE, mode);
+	}
+}
+
+static void mtk_set_mcupm_buck_mode(uint32_t mode)
+{
+	if (mode < NF_MCUPM_BUCK_MODE) {
+		mcdi_mbox_write(APMCU_MCUPM_MBOX_BUCK_MODE, mode);
+	}
+}
+
+static int mtk_mcupm_is_ready(void)
+{
+	unsigned int sta = mcdi_mbox_read(APMCU_MCUPM_MBOX_TASK_STA);
+
+	return (sta == MCUPM_TASK_WAIT) || (sta == MCUPM_TASK_INIT_FINISH);
+}
+
+static int mcdi_init_1(void)
+{
+	unsigned int sta = mcdi_mbox_read(APMCU_MCUPM_MBOX_TASK_STA);
+
+	if (sta != MCUPM_TASK_INIT) {
+		return -1;
+	}
+
+	mtk_set_mcupm_pll_mode(MCUPM_ARMPLL_OFF);
+	mtk_set_mcupm_buck_mode(MCUPM_BUCK_OFF_MODE);
+
+	mtk_mcupm_pwr_ctrl_setting(
+			 MCUPM_MCUSYS_CTRL |
+			 MCUPM_BUCK_CTRL |
+			 MCUPM_ARMPLL_CTRL);
+
+	mcdi_mbox_write(APMCU_MCUPM_MBOX_AP_READY, 1);
+
+	return 0;
+}
+
+static int mcdi_init_2(void)
+{
+	return mtk_mcupm_is_ready() ? 0 : -1;
+}
+
+int mcdi_try_init(void)
+{
+	if (mcdi_init_status == MCDI_INIT_DONE) {
+		return 0;
+	}
+
+	if (mcdi_init_status == MCDI_NOT_INIT) {
+		mcdi_init_status = MCDI_INIT_1;
+	}
+
+	if (mcdi_init_status == MCDI_INIT_1 && mcdi_init_1() == 0) {
+		mcdi_init_status = MCDI_INIT_2;
+	}
+
+	if (mcdi_init_status == MCDI_INIT_2 && mcdi_init_2() == 0) {
+		mcdi_init_status = MCDI_INIT_DONE;
+	}
+
+	INFO("mcdi ready for mcusys-off-idle and system suspend\n");
+
+	return (mcdi_init_status == MCDI_INIT_DONE) ? 0 : mcdi_init_status;
+}
diff --git a/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.h b/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.h
new file mode 100644
index 0000000..f3545aa
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/mcdi/mt_mcdi.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_MCDI_H
+#define MT_MCDI_H
+
+int mcdi_try_init(void);
+
+#endif /* MT_MCDI_H */
diff --git a/plat/mediatek/mt8192/drivers/pmic/pmic.c b/plat/mediatek/mt8192/drivers/pmic/pmic.c
new file mode 100644
index 0000000..cca4413
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/pmic/pmic.c
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <pmic.h>
+#include <pmic_wrap_init.h>
+
+void pmic_power_off(void)
+{
+	pwrap_write(PMIC_PWRHOLD, 0x0);
+}
diff --git a/plat/mediatek/mt8192/drivers/pmic/pmic.h b/plat/mediatek/mt8192/drivers/pmic/pmic.h
new file mode 100644
index 0000000..aac22af
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/pmic/pmic.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PMIC_H
+#define PMIC_H
+
+#define PMIC_PWRHOLD 0xa08
+
+/* external API */
+void pmic_power_off(void);
+
+#endif /* PMIC_H */
diff --git a/plat/mediatek/mt8192/drivers/pmic/pmic_wrap_init.h b/plat/mediatek/mt8192/drivers/pmic/pmic_wrap_init.h
new file mode 100644
index 0000000..ae892ed
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/pmic/pmic_wrap_init.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PMIC_WRAP_INIT_H
+#define PMIC_WRAP_INIT_H
+
+#include <stdint.h>
+
+#include "platform_def.h"
+
+/* external API */
+int32_t pwrap_read(uint32_t adr, uint32_t *rdata);
+int32_t pwrap_write(uint32_t adr, uint32_t wdata);
+
+static struct mt8192_pmic_wrap_regs *const mtk_pwrap = (void *)PMIC_WRAP_BASE;
+
+/* PMIC_WRAP registers */
+struct mt8192_pmic_wrap_regs {
+	uint32_t init_done;
+	uint32_t reserved[799];
+	uint32_t wacs2_cmd;
+	uint32_t wacs2_wdata;
+	uint32_t reserved1[3];
+	uint32_t wacs2_rdata;
+	uint32_t reserved2[3];
+	uint32_t wacs2_vldclr;
+	uint32_t wacs2_sta;
+};
+
+#define GET_WACS_FSM(x)	((x >> 1) & 0x7)
+
+/* macro for SWINF_FSM */
+#define SWINF_FSM_IDLE		(0x00)
+#define SWINF_FSM_REQ		(0x02)
+#define SWINF_FSM_WFDLE		(0x04)
+#define SWINF_FSM_WFVLDCLR	(0x06)
+#define SWINF_INIT_DONE		(0x01)
+
+/* timeout setting */
+#define PWRAP_READ_US	1000
+#define PWRAP_WAIT_IDLE_US	1000
+
+/* error information flag */
+enum pwrap_errno {
+	E_PWR_INVALID_ARG             = 1,
+	E_PWR_INVALID_RW              = 2,
+	E_PWR_INVALID_ADDR            = 3,
+	E_PWR_INVALID_WDAT            = 4,
+	E_PWR_INVALID_OP_MANUAL       = 5,
+	E_PWR_NOT_IDLE_STATE          = 6,
+	E_PWR_NOT_INIT_DONE           = 7,
+	E_PWR_NOT_INIT_DONE_READ      = 8,
+	E_PWR_WAIT_IDLE_TIMEOUT       = 9,
+	E_PWR_WAIT_IDLE_TIMEOUT_READ  = 10,
+	E_PWR_INIT_SIDLY_FAIL         = 11,
+	E_PWR_RESET_TIMEOUT           = 12,
+	E_PWR_TIMEOUT                 = 13,
+	E_PWR_INIT_RESET_SPI          = 20,
+	E_PWR_INIT_SIDLY              = 21,
+	E_PWR_INIT_REG_CLOCK          = 22,
+	E_PWR_INIT_ENABLE_PMIC        = 23,
+	E_PWR_INIT_DIO                = 24,
+	E_PWR_INIT_CIPHER             = 25,
+	E_PWR_INIT_WRITE_TEST         = 26,
+	E_PWR_INIT_ENABLE_CRC         = 27,
+	E_PWR_INIT_ENABLE_DEWRAP      = 28,
+	E_PWR_INIT_ENABLE_EVENT       = 29,
+	E_PWR_READ_TEST_FAIL          = 30,
+	E_PWR_WRITE_TEST_FAIL         = 31,
+	E_PWR_SWITCH_DIO              = 32
+};
+
+#endif /* PMIC_WRAP_INIT_H */
diff --git a/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_common.h b/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_common.h
new file mode 100644
index 0000000..92c71bc
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_common.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_PTP3_H
+#define MTK_PTP3_H
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+
+/************************************************
+ * BIT Operation and REG r/w
+ ************************************************/
+#define ptp3_read(addr)		mmio_read_32((uintptr_t)addr)
+#define ptp3_write(addr, val)	mmio_write_32((uintptr_t)addr, val)
+
+/************************************************
+ * CPU info
+ ************************************************/
+#define NR_PTP3_CFG1_CPU	U(8)
+#define PTP3_CFG1_CPU_START_ID	U(0)
+#define PTP3_CFG1_MASK		0x00100000
+
+#define NR_PTP3_CFG2_CPU	U(4)
+#define PTP3_CFG2_CPU_START_ID	U(4)
+
+#define NR_PTP3_CFG3_CPU	U(4)
+#define PTP3_CFG3_CPU_START_ID	U(4)
+
+/************************************************
+ * config enum
+ ************************************************/
+enum PTP3_CFG {
+	PTP3_CFG_ADDR,
+	PTP3_CFG_VALUE,
+	NR_PTP3_CFG,
+};
+
+/************************************
+ * prototype
+ ************************************/
+/* init trigger for ptp3 feature */
+extern void ptp3_init(unsigned int core);
+extern void ptp3_deinit(unsigned int core);
+
+#endif /* MTK_PTP3_H */
diff --git a/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_main.c b/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_main.c
new file mode 100644
index 0000000..f1d8493
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/ptp3/mtk_ptp3_main.c
@@ -0,0 +1,84 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved. \
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include "mtk_ptp3_common.h"
+
+/************************************************
+ * Central control: turn on sysPi protection
+ ************************************************/
+static unsigned int ptp3_cfg1[NR_PTP3_CFG1_CPU][NR_PTP3_CFG] = {
+	{0x0C530610, 0x110842},
+	{0x0C530E10, 0x110842},
+	{0x0C531610, 0x110842},
+	{0x0C531E10, 0x110842},
+	{0x0C532610, 0x110842},
+	{0x0C532E10, 0x110842},
+	{0x0C533610, 0x110842},
+	{0x0C533E10, 0x110842}
+};
+static unsigned int ptp3_cfg2[NR_PTP3_CFG2_CPU][NR_PTP3_CFG] = {
+	{0x0C53B830, 0x68000},
+	{0x0C53BA30, 0x68000},
+	{0x0C53BC30, 0x68000},
+	{0x0C53BE30, 0x68000}
+};
+static unsigned int ptp3_cfg3[NR_PTP3_CFG3_CPU][NR_PTP3_CFG] = {
+	{0x0C532480, 0x7C607C6},
+	{0x0C532C80, 0x7C607C6},
+	{0x0C533480, 0x7C607C6},
+	{0x0C533C80, 0x7C607C6}
+};
+
+/************************************************
+ * API
+ ************************************************/
+void ptp3_init(unsigned int core)
+{
+	unsigned int _core;
+
+	/* Apply ptp3_cfg1 for core 0 to 7 */
+	if (core < NR_PTP3_CFG1_CPU) {
+		/* update ptp3_cfg1 */
+		ptp3_write(
+			ptp3_cfg1[core][PTP3_CFG_ADDR],
+			ptp3_cfg1[core][PTP3_CFG_VALUE]);
+	}
+
+	/* Apply ptp3_cfg2 for core 4 to 7 */
+	if (core >= PTP3_CFG2_CPU_START_ID) {
+		_core = core - PTP3_CFG2_CPU_START_ID;
+
+		if (_core < NR_PTP3_CFG2_CPU) {
+			/* update ptp3_cfg2 */
+			ptp3_write(
+				ptp3_cfg2[_core][PTP3_CFG_ADDR],
+				ptp3_cfg2[_core][PTP3_CFG_VALUE]);
+		}
+	}
+
+	/* Apply ptp3_cfg3 for core 4 to 7 */
+	if (core >= PTP3_CFG3_CPU_START_ID) {
+		_core = core - PTP3_CFG3_CPU_START_ID;
+
+		if (_core < NR_PTP3_CFG3_CPU) {
+			/* update ptp3_cfg3 */
+			ptp3_write(
+				ptp3_cfg3[_core][PTP3_CFG_ADDR],
+				ptp3_cfg3[_core][PTP3_CFG_VALUE]);
+		}
+	}
+}
+
+void ptp3_deinit(unsigned int core)
+{
+	if (core < NR_PTP3_CFG1_CPU) {
+		/* update ptp3_cfg1 */
+		ptp3_write(
+			ptp3_cfg1[core][PTP3_CFG_ADDR],
+			ptp3_cfg1[core][PTP3_CFG_VALUE] &
+				 ~PTP3_CFG1_MASK);
+	}
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/build.mk b/plat/mediatek/mt8192/drivers/spm/build.mk
new file mode 100644
index 0000000..4153603
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/build.mk
@@ -0,0 +1,68 @@
+#
+# Copyright (c) 2020, MediaTek Inc. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Enable or disable spm feature
+MT_SPM_FEATURE_SUPPORT = yes
+
+# Enable or disable cirq restore
+MT_SPM_CIRQ_FEATURE_SUPPORT = yes
+
+# sspm notifier support
+MT_SPM_SSPM_NOTIFIER_SUPPORT = yes
+
+CUR_SPM_FOLDER = ${MTK_PLAT_SOC}/drivers/spm
+
+# spm common files
+PLAT_SPM_SOURCE_FILES_COMMON +=			\
+	${CUR_SPM_FOLDER}/mt_spm.c		\
+	${CUR_SPM_FOLDER}/mt_spm_conservation.c	\
+	${CUR_SPM_FOLDER}/mt_spm_internal.c	\
+	${CUR_SPM_FOLDER}/mt_spm_pmic_wrap.c	\
+	${CUR_SPM_FOLDER}/mt_spm_vcorefs.c
+
+# spm platform dependcy files
+PLAT_SPM_SOURCE_FILES +=					\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_bus26m.c	\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_cpu_buck_ldo.c	\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_dram.c		\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_syspll.c	\
+	${CUR_SPM_FOLDER}/mt_spm_cond.c				\
+	${CUR_SPM_FOLDER}/mt_spm_suspend.c			\
+	${CUR_SPM_FOLDER}/mt_spm_idle.c
+
+ifeq (${MT_SPM_FEATURE_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_SPM_UNSUPPORT
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES += ${PLAT_SPM_SOURCE_FILES_COMMON}
+else
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES +=	\
+	${PLAT_SPM_SOURCE_FILES_COMMON} \
+	${PLAT_SPM_SOURCE_FILES}
+endif
+
+ifeq (${MT_SPM_CIRQ_FEATURE_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_CIRQ_UNSUPPORT
+endif
+
+ifeq (${MT_SPM_SSPM_NOTIFIER_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+else
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES +=	\
+	${CUR_SPM_FOLDER}/notifier/mt_spm_sspm_notifier.c
+endif
+
+$(info --------------------------------------)
+$(info SPM build flags: ${PLAT_SPM_DEBUG_CFLAGS})
+$(info SPM build files: ${BL31_MT_LPM_PLAT_SPM_SOURCE_FILES})
+$(info --------------------------------------)
+
+# Common makefile for platform.mk
+PLAT_INCLUDES +=				\
+	${PLAT_SPM_DEBUG_CFLAGS}		\
+	-I${CUR_SPM_FOLDER}/			\
+	-I${CUR_SPM_FOLDER}/constraints/	\
+	-I${CUR_SPM_FOLDER}/notifier/
+
+PLAT_BL_COMMON_SOURCES += ${BL31_MT_LPM_PLAT_SPM_SOURCE_FILES}
diff --git a/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_bus26m.c b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_bus26m.c
new file mode 100644
index 0000000..f66b8ec
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_bus26m.c
@@ -0,0 +1,230 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#ifndef ATF_PLAT_CIRQ_UNSUPPORT
+#include <mt_gic_v3.h>
+#include <mtk_cirq.h>
+#endif
+
+#define CONSTRAINT_BUS26M_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S0 |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_VCORE_LP |	\
+	 MT_RM_CONSTRAINT_ALLOW_LVTS_STATE |	\
+	 MT_RM_CONSTRAINT_ALLOW_BUS26M_OFF)
+
+#define CONSTRAINT_BUS26M_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_ENABLE_TIA_WORKAROUND |	\
+	 SPM_FLAG_ENABLE_LVTS_WORKAROUND |	\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH)
+
+#define CONSTRAINT_BUS26M_PCM_FLAG1		\
+	(SPM_FLAG1_DISABLE_MD26M_CK_OFF)
+
+#define CONSTRAINT_BUS26M_RESOURCE_REQ		0U
+
+static unsigned int bus26m_ext_opand;
+static struct mt_irqremain *refer2remain_irq;
+static struct mt_spm_cond_tables cond_bus26m = {
+	.name = "bus26m",
+	.table_cg = {
+		0x07CBF1FC,	/* MTCMOS1 */
+		0x0A0D8856,	/* INFRA0  */
+		0x03AF9A00,	/* INFRA1  */
+		0x86000650,	/* INFRA2  */
+		0xC800C000,	/* INFRA3  */
+		0x00000000,     /* INFRA4  */
+		0x4000007C,     /* INFRA5  */
+		0x280E0800,	/* MMSYS0  */
+		0x00000001,     /* MMSYS1  */
+		0x00000000,	/* MMSYS2  */
+	},
+	.table_pll = (PLL_BIT_UNIVPLL | PLL_BIT_MFGPLL |
+		      PLL_BIT_MSDCPLL | PLL_BIT_TVDPLL |
+		      PLL_BIT_MMPLL),
+};
+
+static struct mt_spm_cond_tables cond_bus26m_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_BUS26M,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_bus26m_res,
+};
+
+/*
+ * Cirq will take the place of gic when gic is off.
+ * However, cirq cannot work if 26m clk is turned off when system idle/suspend.
+ * Therefore, we need to set irq pending for specific wakeup source.
+ */
+#ifdef ATF_PLAT_CIRQ_UNSUPPORT
+#define do_irqs_delivery()
+#else
+static void mt_spm_irq_remain_dump(struct mt_irqremain *irqs,
+				   unsigned int irq_index,
+				   struct wake_status *wakeup)
+{
+	INFO("[SPM] r12 = 0x%08x(0x%08x), flag = 0x%08x 0x%08x 0x%08x\n",
+	     wakeup->tr.comm.r12, wakeup->md32pcm_wakeup_sta,
+	     wakeup->tr.comm.debug_flag, wakeup->tr.comm.b_sw_flag0,
+	     wakeup->tr.comm.b_sw_flag1);
+
+	INFO("irq:%u(0x%08x) set pending\n",
+	     irqs->wakeupsrc[irq_index], irqs->irqs[irq_index]);
+}
+
+static void do_irqs_delivery(void)
+{
+	unsigned int idx;
+	int res = 0;
+	struct wake_status *wakeup = NULL;
+	struct mt_irqremain *irqs = refer2remain_irq;
+
+	res = spm_conservation_get_result(&wakeup);
+
+	if ((res != 0) && (irqs == NULL)) {
+		return;
+	}
+
+	for (idx = 0U; idx < irqs->count; ++idx) {
+		if (((wakeup->tr.comm.r12 & irqs->wakeupsrc[idx]) != 0U) ||
+		    ((wakeup->raw_sta & irqs->wakeupsrc[idx]) != 0U)) {
+			if ((irqs->wakeupsrc_cat[idx] &
+			     MT_IRQ_REMAIN_CAT_LOG) != 0U) {
+				mt_spm_irq_remain_dump(irqs, idx, wakeup);
+			}
+
+			mt_irq_set_pending(irqs->irqs[idx]);
+		}
+	}
+}
+#endif
+
+static void spm_bus26m_conduct(struct spm_lp_scen *spm_lp,
+			       unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_BUS26M_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_BUS26M_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_BUS26M_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_bus26m(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_bus26m(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_bus26m;
+
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_bus26m_res : NULL);
+	} else if (type == PLAT_RC_UPDATE_REMAIN_IRQS) {
+		refer2remain_irq = (struct mt_irqremain *)val;
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_bus26m(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_BUS26M_ALLOW;
+}
+
+int spm_run_rc_bus26m(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, CONSTRAINT_BUS26M_ALLOW |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_HW_S1_DETECT |
+				      bus26m_ext_opand),
+				     CONSTRAINT_BUS26M_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, MT_SPM_EX_OP_HW_S1_DETECT,
+					  spm_bus26m_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_bus26m(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, 0U);
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		ext_op |= (bus26m_ext_opand | MT_SPM_EX_OP_SET_WDT);
+		mt_spm_suspend_resume(state_id, ext_op, NULL);
+		bus26m_ext_opand = 0U;
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	do_irqs_delivery();
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c
new file mode 100644
index 0000000..9618f3b
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c
@@ -0,0 +1,104 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+
+#define CONSTRAINT_CPU_BUCK_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH)
+
+#define CONSTRAINT_CPU_BUCK_PCM_FLAG1		0U
+
+#define CONSTRAINT_CPU_BUCK_RESOURCE_REQ	\
+	(MT_SPM_DRAM_S1 |			\
+	 MT_SPM_DRAM_S0 |			\
+	 MT_SPM_SYSPLL |			\
+	 MT_SPM_INFRA |				\
+	 MT_SPM_26M |				\
+	 MT_SPM_XO_FPM)
+
+
+static unsigned int cpubuckldo_status = MT_SPM_RC_VALID_SW;
+static unsigned int cpubuckldo_enter_cnt;
+
+static void spm_cpu_bcuk_ldo_conduct(struct spm_lp_scen *spm_lp,
+				     unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_CPU_BUCK_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_CPU_BUCK_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_CPU_BUCK_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return IS_MT_RM_RC_READY(cpubuckldo_status);
+}
+
+unsigned int spm_allow_rc_cpu_buck_ldo(int state_id)
+{
+	(void)state_id;
+
+	return MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF;
+}
+
+int spm_run_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER,
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     MT_SPM_EX_OP_SET_WDT,
+				     CONSTRAINT_CPU_BUCK_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, 0U,
+					  spm_cpu_bcuk_ldo_conduct);
+	}
+
+	cpubuckldo_enter_cnt++;
+
+	return 0;
+}
+
+int spm_reset_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, 0U);
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id, MT_SPM_EX_OP_SET_WDT, NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, 0U, NULL);
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_dram.c b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_dram.c
new file mode 100644
index 0000000..34293c4
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_dram.c
@@ -0,0 +1,191 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#define CONSTRAINT_DRAM_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_DRAM_S0	|	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF)
+
+#define CONSTRAINT_DRAM_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH)
+
+#define CONSTRAINT_DRAM_PCM_FLAG1		0U
+
+#define CONSTRAINT_DRAM_RESOURCE_REQ		\
+	(MT_SPM_SYSPLL |			\
+	 MT_SPM_INFRA |				\
+	 MT_SPM_26M)
+
+static struct mt_spm_cond_tables cond_dram = {
+	.name = "dram",
+	.table_cg = {
+		0x078BF1FC,	/* MTCMOS1 */
+		0x080D8856,	/* INFRA0  */
+		0x03AF9A00,	/* INFRA1  */
+		0x86000640,	/* INFRA2  */
+		0xC800C000,	/* INFRA3  */
+		0x00000000,     /* INFRA4  */
+		0x00000000,     /* INFRA5  */
+		0x200C0000,	/* MMSYS0  */
+		0x00000000,     /* MMSYS1  */
+		0x00000000,	/* MMSYS2  */
+	},
+	.table_pll = 0U,
+};
+
+static struct mt_spm_cond_tables cond_dram_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_DRAM,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH |
+		  MT_SPM_RC_VALID_XSOC_BBLPM),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_dram_res,
+};
+
+static void spm_dram_conduct(struct spm_lp_scen *spm_lp,
+			     unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_DRAM_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_DRAM_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_DRAM_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_dram(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_dram(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_dram;
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_dram_res : NULL);
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_dram(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_DRAM_ALLOW;
+}
+
+int spm_run_rc_dram(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_DRAM_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, allows |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_HW_S1_DETECT),
+				     CONSTRAINT_DRAM_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, ext_op, spm_dram_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_dram(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_DRAM_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, allows);
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id,
+				      (MT_SPM_EX_OP_SET_WDT |
+				       MT_SPM_EX_OP_HW_S1_DETECT),
+				      NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_internal.h b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_internal.h
new file mode 100644
index 0000000..aeb778a
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_internal.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_RC_INTERNAL_H
+#define MT_SPM_RC_INTERNAL_H
+
+#include <stdbool.h>
+
+#define SPM_FLAG_SRAM_SLEEP_CTRL			\
+	(SPM_FLAG_DISABLE_SSPM_SRAM_SLEEP |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |	\
+	 SPM_FLAG_DISABLE_SYSRAM_SLEEP |		\
+	 SPM_FLAG_DISABLE_MCUPM_SRAM_SLEEP |		\
+	 SPM_FLAG_DISABLE_SRAM_EVENT)
+
+/* cpu buck/ldo constraint function */
+bool spm_is_valid_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+unsigned int spm_allow_rc_cpu_buck_ldo(int state_id);
+int spm_run_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+int spm_reset_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+
+/* spm resource dram constraint function */
+bool spm_is_valid_rc_dram(unsigned int cpu, int state_id);
+int spm_update_rc_dram(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_dram(int state_id);
+int spm_run_rc_dram(unsigned int cpu, int state_id);
+int spm_reset_rc_dram(unsigned int cpu, int state_id);
+
+/* spm resource syspll constraint function */
+bool spm_is_valid_rc_syspll(unsigned int cpu, int state_id);
+int spm_update_rc_syspll(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_syspll(int state_id);
+int spm_run_rc_syspll(unsigned int cpu, int state_id);
+int spm_reset_rc_syspll(unsigned int cpu, int state_id);
+
+/* spm resource bus26m constraint function */
+bool spm_is_valid_rc_bus26m(unsigned int cpu, int state_id);
+int spm_update_rc_bus26m(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_bus26m(int state_id);
+int spm_run_rc_bus26m(unsigned int cpu, int state_id);
+int spm_reset_rc_bus26m(unsigned int cpu, int state_id);
+#endif /* MT_SPM_RC_INTERNAL_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_syspll.c b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_syspll.c
new file mode 100644
index 0000000..8d76d63
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/constraints/mt_spm_rc_syspll.c
@@ -0,0 +1,192 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#define CONSTRAINT_SYSPLL_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S0 |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_VCORE_LP)
+
+#define CONSTRAINT_SYSPLL_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |	\
+	 SPM_FLAG_ENABLE_6315_CTRL |		\
+	 SPM_FLAG_USE_SRCCLKENO2)
+
+#define CONSTRAINT_SYSPLL_PCM_FLAG1		0U
+#define CONSTRAINT_SYSPLL_RESOURCE_REQ		\
+	(MT_SPM_26M)
+
+static struct mt_spm_cond_tables cond_syspll = {
+	.name = "syspll",
+	.table_cg = {
+		0x078BF1FC,	/* MTCMOS1 */
+		0x080D8856,	/* INFRA0  */
+		0x03AF9A00,	/* INFRA1  */
+		0x86000640,	/* INFRA2  */
+		0xC800C000,	/* INFRA3  */
+		0x00000000,     /* INFRA4  */
+		0x0000007C,     /* INFRA5  */
+		0x280E0800,	/* MMSYS0  */
+		0x00000001,     /* MMSYS1  */
+		0x00000000,	/* MMSYS2  */
+	},
+	.table_pll = 0U,
+};
+
+static struct mt_spm_cond_tables cond_syspll_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_SYSPLL,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH |
+		  MT_SPM_RC_VALID_XSOC_BBLPM),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_syspll_res,
+};
+
+static void spm_syspll_conduct(struct spm_lp_scen *spm_lp,
+			       unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_SYSPLL_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_SYSPLL_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_SYSPLL_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_syspll(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_syspll(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_syspll;
+
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_syspll_res : NULL);
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_syspll(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_SYSPLL_ALLOW;
+}
+
+int spm_run_rc_syspll(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_SYSPLL_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, allows |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_HW_S1_DETECT |
+				      MT_SPM_EX_OP_SET_SUSPEND_MODE),
+				     CONSTRAINT_SYSPLL_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, ext_op, spm_syspll_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_syspll(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_SYSPLL_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, allows);
+#else
+	(void)allows;
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id,
+				      (MT_SPM_EX_OP_SET_SUSPEND_MODE |
+				       MT_SPM_EX_OP_SET_WDT |
+				       MT_SPM_EX_OP_HW_S1_DETECT),
+				      NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm.c b/plat/mediatek/mt8192/drivers/spm/mt_spm.c
new file mode 100644
index 0000000..f4505b6
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm.c
@@ -0,0 +1,104 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+#include <string.h>
+#include <common/debug.h>
+#include <lib/bakery_lock.h>
+#include <lib/mmio.h>
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <mtk_plat_common.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+#include <sleep_def.h>
+
+#ifdef MT_SPM_USING_BAKERY_LOCK
+DEFINE_BAKERY_LOCK(spm_lock);
+#define plat_spm_lock_init() bakery_lock_init(&spm_lock)
+#else
+spinlock_t spm_lock;
+#define plat_spm_lock_init()
+#endif
+
+/* CLK_SCP_CFG_0 */
+#define CLK_SCP_CFG_0		(TOPCKGEN_BASE + 0x200)
+#define SPM_CK_CONTROL_EN	0x3FF
+
+/* CLK_SCP_CFG_1 */
+#define CLK_SCP_CFG_1		(TOPCKGEN_BASE + 0x210)
+#define CLK_SCP_CFG_1_MASK	0x100C
+#define CLK_SCP_CFG_1_SPM	0x3
+
+struct mt_resource_constraint plat_constraint_bus26m = {
+	.is_valid = spm_is_valid_rc_bus26m,
+	.update = spm_update_rc_bus26m,
+	.allow = spm_allow_rc_bus26m,
+	.run = spm_run_rc_bus26m,
+	.reset = spm_reset_rc_bus26m,
+};
+
+struct mt_resource_constraint plat_constraint_syspll = {
+	.is_valid = spm_is_valid_rc_syspll,
+	.update = spm_update_rc_syspll,
+	.allow = spm_allow_rc_syspll,
+	.run = spm_run_rc_syspll,
+	.reset = spm_reset_rc_syspll,
+};
+
+struct mt_resource_constraint plat_constraint_dram = {
+	.is_valid = spm_is_valid_rc_dram,
+	.update = spm_update_rc_dram,
+	.allow = spm_allow_rc_dram,
+	.run = spm_run_rc_dram,
+	.reset = spm_reset_rc_dram,
+};
+
+struct mt_resource_constraint plat_constraint_cpu = {
+	.is_valid = spm_is_valid_rc_cpu_buck_ldo,
+	.update = NULL,
+	.allow = spm_allow_rc_cpu_buck_ldo,
+	.run = spm_run_rc_cpu_buck_ldo,
+	.reset = spm_reset_rc_cpu_buck_ldo,
+};
+
+struct mt_resource_constraint *plat_constraints[] = {
+	&plat_constraint_bus26m,
+	&plat_constraint_syspll,
+	&plat_constraint_dram,
+	&plat_constraint_cpu,
+	NULL,
+};
+
+struct mt_resource_manager plat_mt8192_rm = {
+	.update = mt_spm_cond_update,
+	.consts = plat_constraints,
+};
+
+void spm_boot_init(void)
+{
+	/* switch ck_off/axi_26m control to SPM */
+	mmio_setbits_32(CLK_SCP_CFG_0, SPM_CK_CONTROL_EN);
+	mmio_clrsetbits_32(CLK_SCP_CFG_1, CLK_SCP_CFG_1_MASK,
+			   CLK_SCP_CFG_1_SPM);
+
+	plat_spm_lock_init();
+	mt_spm_pmic_wrap_set_phase(PMIC_WRAP_PHASE_ALLINONE);
+	mt_lp_rm_register(&plat_mt8192_rm);
+	mt_spm_idle_generic_init();
+	mt_spm_suspend_init();
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm.h b/plat/mediatek/mt8192/drivers/spm/mt_spm.h
new file mode 100644
index 0000000..b147fe2
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_H
+#define MT_SPM_H
+
+#include <lib/bakery_lock.h>
+#include <lib/spinlock.h>
+
+#include <plat_mtk_lpm.h>
+
+/*
+ * ARM v8.2, the cache will turn off automatically when cpu
+ * power down. So, there is no doubt to use the spin_lock here
+ */
+#if !HW_ASSISTED_COHERENCY
+#define MT_SPM_USING_BAKERY_LOCK
+#endif
+
+#ifdef MT_SPM_USING_BAKERY_LOCK
+DECLARE_BAKERY_LOCK(spm_lock);
+#define plat_spm_lock() bakery_lock_get(&spm_lock)
+#define plat_spm_unlock() bakery_lock_release(&spm_lock)
+#else
+extern spinlock_t spm_lock;
+#define plat_spm_lock() spin_lock(&spm_lock)
+#define plat_spm_unlock() spin_unlock(&spm_lock)
+#endif
+
+#define MT_SPM_USING_SRCLKEN_RC
+
+/* spm extern operand definition */
+#define MT_SPM_EX_OP_CLR_26M_RECORD			(1U << 0)
+#define MT_SPM_EX_OP_SET_WDT				(1U << 1)
+#define MT_SPM_EX_OP_NON_GENERIC_RESOURCE_REQ		(1U << 2)
+#define MT_SPM_EX_OP_SET_SUSPEND_MODE			(1U << 3)
+#define MT_SPM_EX_OP_SET_IS_ADSP			(1U << 4)
+#define MT_SPM_EX_OP_SRCLKEN_RC_BBLPM			(1U << 5)
+#define MT_SPM_EX_OP_HW_S1_DETECT			(1U << 6)
+
+typedef enum {
+	WR_NONE = 0,
+	WR_UART_BUSY = 1,
+	WR_ABORT = 2,
+	WR_PCM_TIMER = 3,
+	WR_WAKE_SRC = 4,
+	WR_DVFSRC = 5,
+	WR_TWAM = 6,
+	WR_PMSR = 7,
+	WR_SPM_ACK_CHK = 8,
+	WR_UNKNOWN = 9,
+} wake_reason_t;
+
+static inline void spm_lock_get(void)
+{
+	plat_spm_lock();
+}
+
+static inline void spm_lock_release(void)
+{
+	plat_spm_unlock();
+}
+
+extern void spm_boot_init(void);
+#endif /* MT_SPM_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.c
new file mode 100644
index 0000000..2d67fdf
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.c
@@ -0,0 +1,219 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm_cond.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_constraint.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+
+#define MT_LP_TZ_INFRA_REG(ofs)		(INFRACFG_AO_BASE + ofs)
+#define MT_LP_TZ_MM_REG(ofs)		(MMSYS_BASE + ofs)
+#define MT_LP_TZ_SPM_REG(ofs)		(SPM_BASE + ofs)
+#define MT_LP_TZ_TOPCK_REG(ofs)		(TOPCKGEN_BASE + ofs)
+#define MT_LP_TZ_APMIXEDSYS(ofs)	(APMIXEDSYS + ofs)
+
+#define SPM_PWR_STATUS			MT_LP_TZ_SPM_REG(0x016C)
+#define SPM_PWR_STATUS_2ND		MT_LP_TZ_SPM_REG(0x0170)
+#define	INFRA_SW_CG0			MT_LP_TZ_INFRA_REG(0x0094)
+#define	INFRA_SW_CG1			MT_LP_TZ_INFRA_REG(0x0090)
+#define	INFRA_SW_CG2			MT_LP_TZ_INFRA_REG(0x00AC)
+#define	INFRA_SW_CG3			MT_LP_TZ_INFRA_REG(0x00C8)
+#define INFRA_SW_CG4                    MT_LP_TZ_INFRA_REG(0x00D8)
+#define INFRA_SW_CG5                    MT_LP_TZ_INFRA_REG(0x00E8)
+#define MMSYS_CG_CON0			MT_LP_TZ_MM_REG(0x100)
+#define MMSYS_CG_CON1			MT_LP_TZ_MM_REG(0x110)
+#define MMSYS_CG_CON2                   MT_LP_TZ_MM_REG(0x1A0)
+
+/***********************************************************
+ * Check clkmux registers
+ ***********************************************************/
+#define CLK_CFG(id)	MT_LP_TZ_TOPCK_REG(0x20 + id * 0x10)
+#define PDN_CHECK	BIT(7)
+#define CLK_CHECK	BIT(31)
+
+enum {
+	CLKMUX_DISP = 0,
+	CLKMUX_MDP  = 1,
+	CLKMUX_IMG1 = 2,
+	CLKMUX_IMG2 = 3,
+	NF_CLKMUX,
+};
+
+static bool is_clkmux_pdn(unsigned int clkmux_id)
+{
+	unsigned int reg, val, idx;
+
+	if ((clkmux_id & CLK_CHECK) != 0U) {
+		clkmux_id = (clkmux_id & ~CLK_CHECK);
+		reg = clkmux_id / 4U;
+		val = mmio_read_32(CLK_CFG(reg));
+		idx = clkmux_id % 4U;
+		val = (val >> (idx * 8U)) & PDN_CHECK;
+		return (val != 0U);
+	}
+
+	return false;
+}
+
+static struct mt_spm_cond_tables spm_cond_t;
+
+struct idle_cond_info {
+	unsigned int subsys_mask;
+	uintptr_t addr;
+	bool bBitflip;
+	unsigned int clkmux_id;
+};
+
+#define IDLE_CG(mask, addr, bitflip, clkmux)	\
+	{mask, (uintptr_t)addr, bitflip, clkmux}
+
+static struct idle_cond_info idle_cg_info[PLAT_SPM_COND_MAX] = {
+	IDLE_CG(0xffffffff, SPM_PWR_STATUS, false, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG0, true, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG1, true, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG2, true, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG3, true, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG4, true, 0U),
+	IDLE_CG(0x00000200, INFRA_SW_CG5, true, 0U),
+	IDLE_CG(0x00100000, MMSYS_CG_CON0, true, (CLK_CHECK | CLKMUX_DISP)),
+	IDLE_CG(0x00100000, MMSYS_CG_CON1, true, (CLK_CHECK | CLKMUX_DISP)),
+	IDLE_CG(0x00100000, MMSYS_CG_CON2, true, (CLK_CHECK | CLKMUX_DISP)),
+};
+
+/***********************************************************
+ * Check pll idle condition
+ ***********************************************************/
+#define PLL_MFGPLL	MT_LP_TZ_APMIXEDSYS(0x268)
+#define PLL_MMPLL	MT_LP_TZ_APMIXEDSYS(0x360)
+#define PLL_UNIVPLL	MT_LP_TZ_APMIXEDSYS(0x308)
+#define PLL_MSDCPLL	MT_LP_TZ_APMIXEDSYS(0x350)
+#define PLL_TVDPLL	MT_LP_TZ_APMIXEDSYS(0x380)
+
+unsigned int mt_spm_cond_check(int state_id,
+			       const struct mt_spm_cond_tables *src,
+			       const struct mt_spm_cond_tables *dest,
+			       struct mt_spm_cond_tables *res)
+{
+	unsigned int blocked = 0U, i;
+	bool is_system_suspend = IS_PLAT_SUSPEND_ID(state_id);
+
+	if ((src == NULL) || (dest == NULL)) {
+		return SPM_COND_CHECK_FAIL;
+	}
+
+	for (i = 0U; i < PLAT_SPM_COND_MAX; i++) {
+		if (res != NULL) {
+			res->table_cg[i] =
+				(src->table_cg[i] & dest->table_cg[i]);
+
+			if (is_system_suspend && (res->table_cg[i] != 0U)) {
+				INFO("suspend: %s block[%u](0x%lx) = 0x%08x\n",
+				     dest->name, i, idle_cg_info[i].addr,
+				     res->table_cg[i]);
+			}
+
+			if (res->table_cg[i] != 0U) {
+				blocked |= (1U << i);
+			}
+		} else if ((src->table_cg[i] & dest->table_cg[i]) != 0U) {
+			blocked |= (1U << i);
+			break;
+		}
+	}
+
+	if (res != NULL) {
+		res->table_pll = (src->table_pll & dest->table_pll);
+
+		if (res->table_pll != 0U) {
+			blocked |=
+				(res->table_pll << SPM_COND_BLOCKED_PLL_IDX) |
+				 SPM_COND_CHECK_BLOCKED_PLL;
+		}
+	} else if ((src->table_pll & dest->table_pll) != 0U) {
+		blocked |= SPM_COND_CHECK_BLOCKED_PLL;
+	}
+
+	if (is_system_suspend && (blocked != 0U)) {
+		INFO("suspend: %s total blocked = 0x%08x\n",
+		     dest->name, blocked);
+	}
+
+	return blocked;
+}
+
+#define IS_MT_SPM_PWR_OFF(mask)					\
+	(((mmio_read_32(SPM_PWR_STATUS) & mask) == 0U) &&	\
+	 ((mmio_read_32(SPM_PWR_STATUS_2ND) & mask) == 0U))
+
+int mt_spm_cond_update(struct mt_resource_constraint **con,
+		       int stateid, void *priv)
+{
+	int res;
+	uint32_t i;
+	struct mt_resource_constraint *const *rc;
+
+	/* read all cg state */
+	for (i = 0U; i < PLAT_SPM_COND_MAX; i++) {
+		spm_cond_t.table_cg[i] = 0U;
+
+		/* check mtcmos, if off set idle_value and clk to 0 disable */
+		if (IS_MT_SPM_PWR_OFF(idle_cg_info[i].subsys_mask)) {
+			continue;
+		}
+
+		/* check clkmux */
+		if (is_clkmux_pdn(idle_cg_info[i].clkmux_id)) {
+			continue;
+		}
+
+		spm_cond_t.table_cg[i] = idle_cg_info[i].bBitflip ?
+					 ~mmio_read_32(idle_cg_info[i].addr) :
+					 mmio_read_32(idle_cg_info[i].addr);
+	}
+
+	spm_cond_t.table_pll = 0U;
+	if ((mmio_read_32(PLL_MFGPLL) & 0x1) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MFGPLL;
+	}
+
+	if ((mmio_read_32(PLL_MMPLL) & 0x1) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MMPLL;
+	}
+
+	if ((mmio_read_32(PLL_UNIVPLL) & 0x1) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_UNIVPLL;
+	}
+
+	if ((mmio_read_32(PLL_MSDCPLL) & 0x1) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MSDCPLL;
+	}
+
+	if ((mmio_read_32(PLL_TVDPLL) & 0x1) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_TVDPLL;
+	}
+
+	spm_cond_t.priv = priv;
+	for (rc = con; *rc != NULL; rc++) {
+		if (((*rc)->update) == NULL) {
+			continue;
+		}
+
+		res = (*rc)->update(stateid, PLAT_RC_UPDATE_CONDITION,
+				    (void const *)&spm_cond_t);
+		if (res != MT_RM_STATUS_OK) {
+			break;
+		}
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.h
new file mode 100644
index 0000000..91ebdd9
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_cond.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONDIT_H
+#define MT_SPM_CONDIT_H
+
+#include <mt_lp_rm.h>
+
+enum PLAT_SPM_COND {
+	PLAT_SPM_COND_MTCMOS1 = 0,
+	PLAT_SPM_COND_CG_INFRA_0,
+	PLAT_SPM_COND_CG_INFRA_1,
+	PLAT_SPM_COND_CG_INFRA_2,
+	PLAT_SPM_COND_CG_INFRA_3,
+	PLAT_SPM_COND_CG_INFRA_4,
+	PLAT_SPM_COND_CG_INFRA_5,
+	PLAT_SPM_COND_CG_MMSYS_0,
+	PLAT_SPM_COND_CG_MMSYS_1,
+	PLAT_SPM_COND_CG_MMSYS_2,
+	PLAT_SPM_COND_MAX,
+};
+
+#define PLL_BIT_UNIVPLL	BIT(0)
+#define PLL_BIT_MFGPLL	BIT(1)
+#define PLL_BIT_MSDCPLL	BIT(2)
+#define PLL_BIT_TVDPLL	BIT(3)
+#define PLL_BIT_MMPLL	BIT(4)
+
+/* Definition about SPM_COND_CHECK_BLOCKED
+ * bit [00 ~ 15]: cg blocking index
+ * bit [16 ~ 29]: pll blocking index
+ * bit [30]     : pll blocking information
+ * bit [31]	: idle condition check fail
+ */
+#define SPM_COND_BLOCKED_CG_IDX		U(0)
+#define SPM_COND_BLOCKED_PLL_IDX	U(16)
+#define SPM_COND_CHECK_BLOCKED_PLL	BIT(30)
+#define SPM_COND_CHECK_FAIL		BIT(31)
+
+struct mt_spm_cond_tables {
+	char *name;
+	unsigned int table_cg[PLAT_SPM_COND_MAX];
+	unsigned int table_pll;
+	void *priv;
+};
+
+extern unsigned int mt_spm_cond_check(int state_id,
+				      const struct mt_spm_cond_tables *src,
+				      const struct mt_spm_cond_tables *dest,
+				      struct mt_spm_cond_tables *res);
+extern int mt_spm_cond_update(struct mt_resource_constraint **con,
+			      int stateid, void *priv);
+#endif /* MT_SPM_CONDIT_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.c
new file mode 100644
index 0000000..f9e6654
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.c
@@ -0,0 +1,155 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_vcorefs.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+struct wake_status spm_wakesta; /* record last wakesta */
+
+static int go_to_spm_before_wfi(int state_id, unsigned int ext_opand,
+				struct spm_lp_scen *spm_lp,
+				unsigned int resource_req)
+{
+	int ret = 0;
+	struct pwr_ctrl *pwrctrl;
+	uint32_t cpu = plat_my_core_pos();
+
+	pwrctrl = spm_lp->pwrctrl;
+
+	__spm_set_cpu_status(cpu);
+	__spm_set_power_control(pwrctrl);
+	__spm_set_wakeup_event(pwrctrl);
+	__spm_sync_vcore_dvfs_power_control(pwrctrl, __spm_vcorefs.pwrctrl);
+	__spm_set_pcm_flags(pwrctrl);
+	__spm_src_req_update(pwrctrl, resource_req);
+
+	if ((ext_opand & MT_SPM_EX_OP_SET_WDT) != 0U) {
+		__spm_set_pcm_wdt(1);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_SRCLKEN_RC_BBLPM) != 0U) {
+		__spm_xo_soc_bblpm(1);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_HW_S1_DETECT) != 0U) {
+		spm_hw_s1_state_monitor_resume();
+	}
+
+	/* Disable auto resume by PCM in system suspend stage */
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		__spm_disable_pcm_timer();
+		__spm_set_pcm_wdt(0);
+	}
+
+	__spm_send_cpu_wakeup_event();
+
+	INFO("cpu%d: wakesrc = 0x%x, settle = 0x%x, sec = %u\n",
+	     cpu, pwrctrl->wake_src, mmio_read_32(SPM_CLK_SETTLE),
+	     mmio_read_32(PCM_TIMER_VAL) / 32768);
+	INFO("sw_flag = 0x%x 0x%x, req = 0x%x, pwr = 0x%x 0x%x\n",
+	     pwrctrl->pcm_flags, pwrctrl->pcm_flags1,
+	     mmio_read_32(SPM_SRC_REQ), mmio_read_32(PWR_STATUS),
+	     mmio_read_32(PWR_STATUS_2ND));
+
+	return ret;
+}
+
+static void go_to_spm_after_wfi(int state_id, unsigned int ext_opand,
+				struct spm_lp_scen *spm_lp,
+				struct wake_status **status)
+{
+	unsigned int ext_status = 0U;
+
+	/* system watchdog will be resumed at kernel stage */
+	if ((ext_opand & MT_SPM_EX_OP_SET_WDT) != 0U) {
+		__spm_set_pcm_wdt(0);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_SRCLKEN_RC_BBLPM) != 0U) {
+		__spm_xo_soc_bblpm(0);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_HW_S1_DETECT) != 0U) {
+		spm_hw_s1_state_monitor_pause(&ext_status);
+	}
+
+	__spm_ext_int_wakeup_req_clr();
+	__spm_get_wakeup_status(&spm_wakesta, ext_status);
+
+	if (status != NULL) {
+		*status = &spm_wakesta;
+	}
+
+	__spm_clean_after_wakeup();
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		__spm_output_wake_reason(state_id, &spm_wakesta);
+	}
+}
+
+int spm_conservation(int state_id, unsigned int ext_opand,
+		     struct spm_lp_scen *spm_lp, unsigned int resource_req)
+{
+	if (spm_lp == NULL) {
+		return -1;
+	}
+
+	spm_lock_get();
+	go_to_spm_before_wfi(state_id, ext_opand, spm_lp, resource_req);
+	spm_lock_release();
+
+	return 0;
+}
+
+void spm_conservation_finish(int state_id, unsigned int ext_opand,
+			     struct spm_lp_scen *spm_lp,
+			     struct wake_status **status)
+{
+	spm_lock_get();
+	go_to_spm_after_wfi(state_id, ext_opand, spm_lp, status);
+	spm_lock_release();
+}
+
+int spm_conservation_get_result(struct wake_status **res)
+{
+	if (res == NULL) {
+		return -1;
+	}
+
+	*res = &spm_wakesta;
+
+	return 0;
+}
+
+#define GPIO_BANK	(GPIO_BASE + 0x6F0)
+#define TRAP_UFS_FIRST	BIT(11) /* bit 11, 0: UFS, 1: eMMC */
+
+void spm_conservation_pwrctrl_init(struct pwr_ctrl *pwrctrl)
+{
+	if (pwrctrl == NULL) {
+		return;
+	}
+
+	/* For ufs, emmc storage type */
+	if ((mmio_read_32(GPIO_BANK) & TRAP_UFS_FIRST) != 0U) {
+		/* If eMMC is used, mask UFS req */
+		pwrctrl->reg_ufs_srcclkena_mask_b = 0;
+		pwrctrl->reg_ufs_infra_req_mask_b = 0;
+		pwrctrl->reg_ufs_apsrc_req_mask_b = 0;
+		pwrctrl->reg_ufs_vrf18_req_mask_b = 0;
+		pwrctrl->reg_ufs_ddr_en_mask_b = 0;
+	}
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.h
new file mode 100644
index 0000000..c5e97db
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_conservation.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONSERVATION_H
+#define MT_SPM_CONSERVATION_H
+
+#include <mt_spm_internal.h>
+
+extern int spm_conservation(int state_id, unsigned int ext_opand,
+			    struct spm_lp_scen *spm_lp,
+			    unsigned int resource_req);
+extern void spm_conservation_finish(int state_id, unsigned int ext_opand,
+				    struct spm_lp_scen *spm_lp,
+				    struct wake_status **status);
+extern int spm_conservation_get_result(struct wake_status **res);
+extern void spm_conservation_pwrctrl_init(struct pwr_ctrl *pwrctrl);
+#endif /* MT_SPM_CONSERVATION_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_constraint.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_constraint.h
new file mode 100644
index 0000000..a3409f7
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_constraint.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONSTRAINT_H
+#define MT_SPM_CONSTRAINT_H
+
+#include <mt_lp_rm.h>
+
+#define MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF	(1U << 0)
+#define MT_RM_CONSTRAINT_ALLOW_DRAM_S0		(1U << 1)
+#define MT_RM_CONSTRAINT_ALLOW_DRAM_S1		(1U << 2)
+#define MT_RM_CONSTRAINT_ALLOW_VCORE_LP		(1U << 3)
+#define MT_RM_CONSTRAINT_ALLOW_INFRA_PDN	(1U << 4)
+#define MT_RM_CONSTRAINT_ALLOW_BUS26M_OFF	(1U << 5)
+#define MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND	(1U << 6)
+#define MT_RM_CONSTRAINT_ALLOW_BBLPM		(1U << 7)
+#define MT_RM_CONSTRAINT_ALLOW_XO_UFS		(1U << 8)
+#define MT_RM_CONSTRAINT_ALLOW_GPS_STATE	(1U << 9)
+#define MT_RM_CONSTRAINT_ALLOW_LVTS_STATE	(1U << 10)
+
+#define MT_SPM_RC_INVALID		0x0
+#define MT_SPM_RC_VALID_SW		(1U << 0)
+#define MT_SPM_RC_VALID_FW		(1U << 1)
+#define MT_SPM_RC_VALID_RESIDNECY	(1U << 2)
+#define MT_SPM_RC_VALID_COND_CHECK	(1U << 3)
+#define MT_SPM_RC_VALID_COND_LATCH	(1U << 4)
+#define MT_SPM_RC_VALID_UFS_H8		(1U << 5)
+#define MT_SPM_RC_VALID_FLIGHTMODE	(1U << 6)
+#define MT_SPM_RC_VALID_XSOC_BBLPM	(1U << 7)
+#define MT_SPM_RC_VALID_TRACE_EVENT	(1U << 8)
+
+#define MT_SPM_RC_VALID	(MT_SPM_RC_VALID_SW)
+
+#define IS_MT_RM_RC_READY(status)	\
+	((status & MT_SPM_RC_VALID) == MT_SPM_RC_VALID)
+
+#define MT_SPM_RC_BBLPM_MODE		\
+	(MT_SPM_RC_VALID_UFS_H8 |	\
+	 MT_SPM_RC_VALID_FLIGHTMODE |	\
+	 MT_SPM_RC_VALID_XSOC_BBLPM)
+
+#define IS_MT_SPM_RC_BBLPM_MODE(st)	\
+	((st & (MT_SPM_RC_BBLPM_MODE)) == MT_SPM_RC_BBLPM_MODE)
+
+struct constraint_status {
+	uint16_t id;
+	uint16_t valid;
+	uint32_t cond_block;
+	uint32_t enter_cnt;
+	struct mt_spm_cond_tables *cond_res;
+};
+
+enum MT_SPM_RM_RC_TYPE {
+	MT_RM_CONSTRAINT_ID_BUS26M,
+	MT_RM_CONSTRAINT_ID_SYSPLL,
+	MT_RM_CONSTRAINT_ID_DRAM,
+	MT_RM_CONSTRAINT_ID_CPU_BUCK_LDO,
+	MT_RM_CONSTRAINT_ID_ALL,
+};
+#endif /* MT_SPM_CONSTRAINT_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.c
new file mode 100644
index 0000000..3540ec2
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.c
@@ -0,0 +1,249 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <plat_pm.h>
+
+#define __WAKE_SRC_FOR_IDLE_COMMON__	\
+	(R12_PCM_TIMER |		\
+	 R12_KP_IRQ_B |			\
+	 R12_APWDT_EVENT_B |		\
+	 R12_APXGPT1_EVENT_B |		\
+	 R12_CONN2AP_SPM_WAKEUP_B |	\
+	 R12_EINT_EVENT_B |		\
+	 R12_CONN_WDT_IRQ_B |		\
+	 R12_CCIF0_EVENT_B |		\
+	 R12_SSPM2SPM_WAKEUP_B |	\
+	 R12_SCP2SPM_WAKEUP_B |		\
+	 R12_ADSP2SPM_WAKEUP_B |	\
+	 R12_USBX_CDSC_B |		\
+	 R12_USBX_POWERDWN_B |		\
+	 R12_SYS_TIMER_EVENT_B |	\
+	 R12_EINT_EVENT_SECURE_B |	\
+	 R12_CCIF1_EVENT_B |		\
+	 R12_AFE_IRQ_MCU_B |		\
+	 R12_SYS_CIRQ_IRQ_B |		\
+	 R12_MD2AP_PEER_EVENT_B |	\
+	 R12_MD1_WDT_B |		\
+	 R12_CLDMA_EVENT_B |		\
+	 R12_REG_CPU_WAKEUP |		\
+	 R12_APUSYS_WAKE_HOST_B |	\
+	 R12_PCIE_BRIDGE_IRQ |		\
+	 R12_PCIE_IRQ)
+
+#if defined(CFG_MICROTRUST_TEE_SUPPORT)
+#define WAKE_SRC_FOR_IDLE (__WAKE_SRC_FOR_IDLE_COMMON__)
+#else
+#define WAKE_SRC_FOR_IDLE		\
+	(__WAKE_SRC_FOR_IDLE_COMMON__ |	\
+	  R12_SEJ_EVENT_B)
+#endif
+
+static struct pwr_ctrl idle_spm_pwr = {
+	.timer_val = 0x28000,
+	.wake_src = WAKE_SRC_FOR_IDLE,
+
+	/* Auto-gen Start */
+
+	/* SPM_AP_STANDBY_CON */
+	.reg_wfi_op = 0,
+	.reg_wfi_type = 0,
+	.reg_mp0_cputop_idle_mask = 0,
+	.reg_mp1_cputop_idle_mask = 0,
+	.reg_mcusys_idle_mask = 0,
+	.reg_md_apsrc_1_sel = 0,
+	.reg_md_apsrc_0_sel = 0,
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC6_MASK */
+	.reg_dpmaif_srcclkena_mask_b = 1,
+	.reg_dpmaif_infra_req_mask_b = 1,
+	.reg_dpmaif_apsrc_req_mask_b = 1,
+	.reg_dpmaif_vrf18_req_mask_b = 1,
+	.reg_dpmaif_ddr_en_mask_b    = 1,
+
+	/* SPM_SRC_REQ */
+	.reg_spm_apsrc_req = 1,
+	.reg_spm_f26m_req = 1,
+	.reg_spm_infra_req = 1,
+	.reg_spm_vrf18_req = 1,
+	.reg_spm_ddr_en_req = 1,
+	.reg_spm_dvfs_req = 0,
+	.reg_spm_sw_mailbox_req = 0,
+	.reg_spm_sspm_mailbox_req = 0,
+	.reg_spm_adsp_mailbox_req = 0,
+	.reg_spm_scp_mailbox_req = 0,
+
+	/* SPM_SRC_MASK */
+	.reg_md_srcclkena_0_mask_b = 1,
+	.reg_md_srcclkena2infra_req_0_mask_b = 0,
+	.reg_md_apsrc2infra_req_0_mask_b = 1,
+	.reg_md_apsrc_req_0_mask_b = 1,
+	.reg_md_vrf18_req_0_mask_b = 1,
+	.reg_md_ddr_en_0_mask_b = 1,
+	.reg_md_srcclkena_1_mask_b = 0,
+	.reg_md_srcclkena2infra_req_1_mask_b = 0,
+	.reg_md_apsrc2infra_req_1_mask_b = 0,
+	.reg_md_apsrc_req_1_mask_b = 0,
+	.reg_md_vrf18_req_1_mask_b = 0,
+	.reg_md_ddr_en_1_mask_b = 0,
+	.reg_conn_srcclkena_mask_b = 1,
+	.reg_conn_srcclkenb_mask_b = 0,
+	.reg_conn_infra_req_mask_b = 1,
+	.reg_conn_apsrc_req_mask_b = 1,
+	.reg_conn_vrf18_req_mask_b = 1,
+	.reg_conn_ddr_en_mask_b = 1,
+	.reg_conn_vfe28_mask_b = 0,
+	.reg_srcclkeni0_srcclkena_mask_b = 1,
+	.reg_srcclkeni0_infra_req_mask_b = 1,
+	.reg_srcclkeni1_srcclkena_mask_b = 0,
+	.reg_srcclkeni1_infra_req_mask_b = 0,
+	.reg_srcclkeni2_srcclkena_mask_b = 0,
+	.reg_srcclkeni2_infra_req_mask_b = 0,
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	.reg_infrasys_ddr_en_mask_b = 1,
+	.reg_md32_srcclkena_mask_b = 1,
+	.reg_md32_infra_req_mask_b = 1,
+	.reg_md32_apsrc_req_mask_b = 1,
+	.reg_md32_vrf18_req_mask_b = 1,
+	.reg_md32_ddr_en_mask_b = 1,
+
+	/* SPM_SRC2_MASK */
+	.reg_scp_srcclkena_mask_b = 1,
+	.reg_scp_infra_req_mask_b = 1,
+	.reg_scp_apsrc_req_mask_b = 1,
+	.reg_scp_vrf18_req_mask_b = 1,
+	.reg_scp_ddr_en_mask_b = 1,
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	.reg_ufs_srcclkena_mask_b = 1,
+	.reg_ufs_infra_req_mask_b = 1,
+	.reg_ufs_apsrc_req_mask_b = 1,
+	.reg_ufs_vrf18_req_mask_b = 1,
+	.reg_ufs_ddr_en_mask_b = 1,
+	.reg_disp0_apsrc_req_mask_b = 1,
+	.reg_disp0_ddr_en_mask_b = 1,
+	.reg_disp1_apsrc_req_mask_b = 1,
+	.reg_disp1_ddr_en_mask_b = 1,
+	.reg_gce_infra_req_mask_b = 1,
+	.reg_gce_apsrc_req_mask_b = 1,
+	.reg_gce_vrf18_req_mask_b = 1,
+	.reg_gce_ddr_en_mask_b = 1,
+	.reg_apu_srcclkena_mask_b = 1,
+	.reg_apu_infra_req_mask_b = 1,
+	.reg_apu_apsrc_req_mask_b = 1,
+	.reg_apu_vrf18_req_mask_b = 1,
+	.reg_apu_ddr_en_mask_b = 1,
+	.reg_cg_check_srcclkena_mask_b = 0,
+	.reg_cg_check_apsrc_req_mask_b = 0,
+	.reg_cg_check_vrf18_req_mask_b = 0,
+	.reg_cg_check_ddr_en_mask_b = 0,
+
+	/* SPM_SRC3_MASK */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+	.reg_sw2spm_int0_mask_b = 0,
+	.reg_sw2spm_int1_mask_b = 0,
+	.reg_sw2spm_int2_mask_b = 0,
+	.reg_sw2spm_int3_mask_b = 0,
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	.reg_csyspwrreq_mask = 1,
+	.reg_spm_srcclkena_reserved_mask_b = 0,
+	.reg_spm_infra_req_reserved_mask_b = 0,
+	.reg_spm_apsrc_req_reserved_mask_b = 0,
+	.reg_spm_vrf18_req_reserved_mask_b = 0,
+	.reg_spm_ddr_en_reserved_mask_b = 0,
+	.reg_mcupm_srcclkena_mask_b = 1,
+	.reg_mcupm_infra_req_mask_b = 1,
+	.reg_mcupm_apsrc_req_mask_b = 1,
+	.reg_mcupm_vrf18_req_mask_b = 1,
+	.reg_mcupm_ddr_en_mask_b = 1,
+	.reg_msdc0_srcclkena_mask_b = 1,
+	.reg_msdc0_infra_req_mask_b = 1,
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	.reg_msdc0_ddr_en_mask_b = 1,
+	.reg_msdc1_srcclkena_mask_b = 1,
+	.reg_msdc1_infra_req_mask_b = 1,
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	.reg_msdc1_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	.ccif_event_mask_b = 0xFFF,
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	.reg_bak_psri_infra_req_mask_b = 0,
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	.reg_bak_psri_ddr_en_mask_b = 0,
+	.reg_dramc0_md32_infra_req_mask_b = 1,
+	.reg_dramc0_md32_vrf18_req_mask_b = 0,
+	.reg_dramc1_md32_infra_req_mask_b = 1,
+	.reg_dramc1_md32_vrf18_req_mask_b = 0,
+	.reg_conn_srcclkenb2pwrap_mask_b = 0,
+	.reg_dramc0_md32_wakeup_mask = 1,
+	.reg_dramc1_md32_wakeup_mask = 1,
+
+	/* SPM_SRC5_MASK */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x11,
+	.reg_mcusys_merge_ddr_en_mask_b = 0x11,
+	.reg_msdc2_srcclkena_mask_b = 1,
+	.reg_msdc2_infra_req_mask_b = 1,
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	.reg_msdc2_ddr_en_mask_b = 1,
+	.reg_pcie_srcclkena_mask_b = 1,
+	.reg_pcie_infra_req_mask_b = 1,
+	.reg_pcie_apsrc_req_mask_b = 1,
+	.reg_pcie_vrf18_req_mask_b = 1,
+	.reg_pcie_ddr_en_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	.reg_wakeup_event_mask = 0x01282202,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+
+	/* Auto-gen End */
+};
+
+struct spm_lp_scen idle_spm_lp = {
+	.pwrctrl = &idle_spm_pwr,
+};
+
+int mt_spm_idle_generic_enter(int state_id, unsigned int ext_opand,
+			      spm_idle_conduct fn)
+{
+	unsigned int src_req = 0;
+
+	if (fn != NULL) {
+		fn(&idle_spm_lp, &src_req);
+	}
+
+	return spm_conservation(state_id, ext_opand, &idle_spm_lp, src_req);
+}
+void mt_spm_idle_generic_resume(int state_id, unsigned int ext_opand,
+				struct wake_status **status)
+{
+	spm_conservation_finish(state_id, ext_opand, &idle_spm_lp, status);
+}
+
+void mt_spm_idle_generic_init(void)
+{
+	spm_conservation_pwrctrl_init(idle_spm_lp.pwrctrl);
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.h
new file mode 100644
index 0000000..3d42cf1
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_idle.h
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_IDLE_H
+#define MT_SPM_IDLE_H
+
+typedef void (*spm_idle_conduct)(struct spm_lp_scen *spm_lp,
+				 unsigned int *resource_req);
+int mt_spm_idle_generic_enter(int state_id, unsigned int ext_opand,
+			      spm_idle_conduct fn);
+void mt_spm_idle_generic_resume(int state_id, unsigned int ext_opand,
+				struct wake_status **status);
+void mt_spm_idle_generic_init(void);
+#endif /* MT_SPM_IDLE_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.c
new file mode 100644
index 0000000..40be027
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.c
@@ -0,0 +1,588 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <assert.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <platform_def.h>
+#include <plat_pm.h>
+
+/**************************************
+ * Define and Declare
+ **************************************/
+#define ROOT_CORE_ADDR_OFFSET			0x20000000
+#define SPM_WAKEUP_EVENT_MASK_CLEAN_MASK	0xefffffff
+#define	SPM_INIT_DONE_US			20
+
+static unsigned int mt_spm_bblpm_cnt;
+
+const char *wakeup_src_str[32] = {
+	[0] = "R12_PCM_TIMER",
+	[1] = "R12_RESERVED_DEBUG_B",
+	[2] = "R12_KP_IRQ_B",
+	[3] = "R12_APWDT_EVENT_B",
+	[4] = "R12_APXGPT1_EVENT_B",
+	[5] = "R12_CONN2AP_SPM_WAKEUP_B",
+	[6] = "R12_EINT_EVENT_B",
+	[7] = "R12_CONN_WDT_IRQ_B",
+	[8] = "R12_CCIF0_EVENT_B",
+	[9] = "R12_LOWBATTERY_IRQ_B",
+	[10] = "R12_SC_SSPM2SPM_WAKEUP_B",
+	[11] = "R12_SC_SCP2SPM_WAKEUP_B",
+	[12] = "R12_SC_ADSP2SPM_WAKEUP_B",
+	[13] = "R12_PCM_WDT_WAKEUP_B",
+	[14] = "R12_USB_CDSC_B",
+	[15] = "R12_USB_POWERDWN_B",
+	[16] = "R12_SYS_TIMER_EVENT_B",
+	[17] = "R12_EINT_EVENT_SECURE_B",
+	[18] = "R12_CCIF1_EVENT_B",
+	[19] = "R12_UART0_IRQ_B",
+	[20] = "R12_AFE_IRQ_MCU_B",
+	[21] = "R12_THERM_CTRL_EVENT_B",
+	[22] = "R12_SYS_CIRQ_IRQ_B",
+	[23] = "R12_MD2AP_PEER_EVENT_B",
+	[24] = "R12_CSYSPWREQ_B",
+	[25] = "R12_MD1_WDT_B",
+	[26] = "R12_AP2AP_PEER_WAKEUPEVENT_B",
+	[27] = "R12_SEJ_EVENT_B",
+	[28] = "R12_SPM_CPU_WAKEUPEVENT_B",
+	[29] = "R12_APUSYS",
+	[30] = "R12_PCIE_BRIDGE_IRQ",
+	[31] = "R12_PCIE_IRQ",
+};
+
+/**************************************
+ * Function and API
+ **************************************/
+
+wake_reason_t __spm_output_wake_reason(int state_id,
+				       const struct wake_status *wakesta)
+{
+	uint32_t i, bk_vtcxo_dur, spm_26m_off_pct = 0U;
+	wake_reason_t wr = WR_UNKNOWN;
+
+	if (wakesta == NULL) {
+		return WR_UNKNOWN;
+	}
+
+	if (wakesta->abort != 0U) {
+		ERROR("spmfw flow is aborted: 0x%x, timer_out = %u\n",
+		      wakesta->abort, wakesta->timer_out);
+	} else {
+		for (i = 0U; i < 32U; i++) {
+			if ((wakesta->r12 & (1U << i)) != 0U) {
+				INFO("wake up by %s, timer_out = %u\n",
+				     wakeup_src_str[i], wakesta->timer_out);
+				wr = WR_WAKE_SRC;
+				break;
+			}
+		}
+	}
+
+	INFO("r12 = 0x%x, r12_ext = 0x%x, r13 = 0x%x, debug_flag = 0x%x 0x%x\n",
+	     wakesta->r12, wakesta->r12_ext, wakesta->r13, wakesta->debug_flag,
+	     wakesta->debug_flag1);
+	INFO("raw_sta = 0x%x 0x%x 0x%x, idle_sta = 0x%x, cg_check_sta = 0x%x\n",
+	     wakesta->raw_sta, wakesta->md32pcm_wakeup_sta,
+	     wakesta->md32pcm_event_sta, wakesta->idle_sta,
+	     wakesta->cg_check_sta);
+	INFO("req_sta = 0x%x 0x%x 0x%x 0x%x 0x%x, isr = 0x%x\n",
+	     wakesta->req_sta0, wakesta->req_sta1, wakesta->req_sta2,
+	     wakesta->req_sta3, wakesta->req_sta4, wakesta->isr);
+	INFO("rt_req_sta0 = 0x%x, rt_req_sta1 = 0x%x, rt_req_sta2 = 0x%x\n",
+	     wakesta->rt_req_sta0, wakesta->rt_req_sta1, wakesta->rt_req_sta2);
+	INFO("rt_req_sta3 = 0x%x, dram_sw_con_3 = 0x%x, raw_ext_sta = 0x%x\n",
+	     wakesta->rt_req_sta3, wakesta->rt_req_sta4, wakesta->raw_ext_sta);
+	INFO("wake_misc = 0x%x, pcm_flag = 0x%x 0x%x 0x%x 0x%x, req = 0x%x\n",
+	     wakesta->wake_misc, wakesta->sw_flag0, wakesta->sw_flag1,
+	     wakesta->b_sw_flag0, wakesta->b_sw_flag1, wakesta->src_req);
+	INFO("clk_settle = 0x%x, wlk_cntcv_l = 0x%x, wlk_cntcv_h = 0x%x\n",
+	     wakesta->clk_settle, mmio_read_32(SYS_TIMER_VALUE_L),
+	     mmio_read_32(SYS_TIMER_VALUE_H));
+
+	if (wakesta->timer_out != 0U) {
+		bk_vtcxo_dur = mmio_read_32(SPM_BK_VTCXO_DUR);
+		spm_26m_off_pct = (100 * bk_vtcxo_dur) / wakesta->timer_out;
+		INFO("spm_26m_off_pct = %u\n", spm_26m_off_pct);
+	}
+
+	return wr;
+}
+
+void __spm_set_cpu_status(unsigned int cpu)
+{
+	uint32_t root_core_addr;
+
+	if (cpu < 8U) {
+		mmio_write_32(ROOT_CPUTOP_ADDR, (1U << cpu));
+		root_core_addr = SPM_CPU0_PWR_CON + (cpu * 0x4);
+		root_core_addr += ROOT_CORE_ADDR_OFFSET;
+		mmio_write_32(ROOT_CORE_ADDR, root_core_addr);
+		/* Notify MCUPM that preferred cpu wakeup */
+		mmio_write_32(MCUPM_MBOX_WAKEUP_CPU, cpu);
+	} else {
+		ERROR("%s: error cpu number %d\n", __func__, cpu);
+	}
+}
+
+void __spm_src_req_update(const struct pwr_ctrl *pwrctrl,
+			  unsigned int resource_usage)
+{
+	uint8_t apsrc_req = ((resource_usage & MT_SPM_DRAM_S0) != 0U) ?
+			    1 : pwrctrl->reg_spm_apsrc_req;
+	uint8_t ddr_en_req = ((resource_usage & MT_SPM_DRAM_S1) != 0U) ?
+			     1 : pwrctrl->reg_spm_ddr_en_req;
+	uint8_t vrf18_req = ((resource_usage & MT_SPM_SYSPLL) != 0U) ?
+			    1 : pwrctrl->reg_spm_vrf18_req;
+	uint8_t infra_req = ((resource_usage & MT_SPM_INFRA) != 0U) ?
+			    1 : pwrctrl->reg_spm_infra_req;
+	uint8_t f26m_req  = ((resource_usage &
+			      (MT_SPM_26M | MT_SPM_XO_FPM)) != 0U) ?
+			    1 : pwrctrl->reg_spm_f26m_req;
+
+	mmio_write_32(SPM_SRC_REQ,
+		      ((apsrc_req & 0x1) << 0) |
+		      ((f26m_req & 0x1) << 1) |
+		      ((infra_req & 0x1) << 3) |
+		      ((vrf18_req & 0x1) << 4) |
+		      ((ddr_en_req & 0x1) << 7) |
+		      ((pwrctrl->reg_spm_dvfs_req & 0x1) << 8) |
+		      ((pwrctrl->reg_spm_sw_mailbox_req & 0x1) << 9) |
+		      ((pwrctrl->reg_spm_sspm_mailbox_req & 0x1) << 10) |
+		      ((pwrctrl->reg_spm_adsp_mailbox_req & 0x1) << 11) |
+		      ((pwrctrl->reg_spm_scp_mailbox_req & 0x1) << 12));
+}
+
+void __spm_set_power_control(const struct pwr_ctrl *pwrctrl)
+{
+	/* Auto-gen Start */
+
+	/* SPM_AP_STANDBY_CON */
+	mmio_write_32(SPM_AP_STANDBY_CON,
+		((pwrctrl->reg_wfi_op & 0x1) << 0) |
+		((pwrctrl->reg_wfi_type & 0x1) << 1) |
+		((pwrctrl->reg_mp0_cputop_idle_mask & 0x1) << 2) |
+		((pwrctrl->reg_mp1_cputop_idle_mask & 0x1) << 3) |
+		((pwrctrl->reg_mcusys_idle_mask & 0x1) << 4) |
+		((pwrctrl->reg_md_apsrc_1_sel & 0x1) << 25) |
+		((pwrctrl->reg_md_apsrc_0_sel & 0x1) << 26) |
+		((pwrctrl->reg_conn_apsrc_sel & 0x1) << 29));
+
+	/* SPM_SRC6_MASK */
+	mmio_write_32(SPM_SRC6_MASK,
+		((pwrctrl->reg_dpmaif_srcclkena_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_dpmaif_infra_req_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_dpmaif_apsrc_req_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_dpmaif_vrf18_req_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_dpmaif_ddr_en_mask_b & 0x1) << 4));
+
+	/* SPM_SRC_REQ */
+	mmio_write_32(SPM_SRC_REQ,
+		((pwrctrl->reg_spm_apsrc_req & 0x1) << 0) |
+		((pwrctrl->reg_spm_f26m_req & 0x1) << 1) |
+		((pwrctrl->reg_spm_infra_req & 0x1) << 3) |
+		((pwrctrl->reg_spm_vrf18_req & 0x1) << 4) |
+		((pwrctrl->reg_spm_ddr_en_req & 0x1) << 7) |
+		((pwrctrl->reg_spm_dvfs_req & 0x1) << 8) |
+		((pwrctrl->reg_spm_sw_mailbox_req & 0x1) << 9) |
+		((pwrctrl->reg_spm_sspm_mailbox_req & 0x1) << 10) |
+		((pwrctrl->reg_spm_adsp_mailbox_req & 0x1) << 11) |
+		((pwrctrl->reg_spm_scp_mailbox_req & 0x1) << 12));
+
+	/* SPM_SRC_MASK */
+	mmio_write_32(SPM_SRC_MASK,
+		((pwrctrl->reg_md_srcclkena_0_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_md_srcclkena2infra_req_0_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_md_apsrc2infra_req_0_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_md_apsrc_req_0_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_md_vrf18_req_0_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_md_ddr_en_0_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_md_srcclkena_1_mask_b & 0x1) << 6) |
+		((pwrctrl->reg_md_srcclkena2infra_req_1_mask_b & 0x1) << 7) |
+		((pwrctrl->reg_md_apsrc2infra_req_1_mask_b & 0x1) << 8) |
+		((pwrctrl->reg_md_apsrc_req_1_mask_b & 0x1) << 9) |
+		((pwrctrl->reg_md_vrf18_req_1_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_md_ddr_en_1_mask_b & 0x1) << 11) |
+		((pwrctrl->reg_conn_srcclkena_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_conn_srcclkenb_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_conn_infra_req_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_conn_apsrc_req_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_conn_vrf18_req_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_conn_ddr_en_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_conn_vfe28_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_srcclkeni0_srcclkena_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_srcclkeni0_infra_req_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_srcclkeni1_srcclkena_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_srcclkeni1_infra_req_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_srcclkeni2_srcclkena_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_srcclkeni2_infra_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_infrasys_apsrc_req_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_infrasys_ddr_en_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_md32_srcclkena_mask_b & 0x1) << 27) |
+		((pwrctrl->reg_md32_infra_req_mask_b & 0x1) << 28) |
+		((pwrctrl->reg_md32_apsrc_req_mask_b & 0x1) << 29) |
+		((pwrctrl->reg_md32_vrf18_req_mask_b & 0x1) << 30) |
+		((pwrctrl->reg_md32_ddr_en_mask_b & 0x1) << 31));
+
+	/* SPM_SRC2_MASK */
+	mmio_write_32(SPM_SRC2_MASK,
+		((pwrctrl->reg_scp_srcclkena_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_scp_infra_req_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_scp_apsrc_req_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_scp_vrf18_req_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_scp_ddr_en_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_audio_dsp_srcclkena_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_audio_dsp_infra_req_mask_b & 0x1) << 6) |
+		((pwrctrl->reg_audio_dsp_apsrc_req_mask_b & 0x1) << 7) |
+		((pwrctrl->reg_audio_dsp_vrf18_req_mask_b & 0x1) << 8) |
+		((pwrctrl->reg_audio_dsp_ddr_en_mask_b & 0x1) << 9) |
+		((pwrctrl->reg_ufs_srcclkena_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_ufs_infra_req_mask_b & 0x1) << 11) |
+		((pwrctrl->reg_ufs_apsrc_req_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_ufs_vrf18_req_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_ufs_ddr_en_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_disp0_apsrc_req_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_disp0_ddr_en_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_disp1_apsrc_req_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_disp1_ddr_en_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_gce_infra_req_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_gce_apsrc_req_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_gce_vrf18_req_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_gce_ddr_en_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_apu_srcclkena_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_apu_infra_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_apu_apsrc_req_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_apu_vrf18_req_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_apu_ddr_en_mask_b & 0x1) << 27) |
+		((pwrctrl->reg_cg_check_srcclkena_mask_b & 0x1) << 28) |
+		((pwrctrl->reg_cg_check_apsrc_req_mask_b & 0x1) << 29) |
+		((pwrctrl->reg_cg_check_vrf18_req_mask_b & 0x1) << 30) |
+		((pwrctrl->reg_cg_check_ddr_en_mask_b & 0x1) << 31));
+
+	/* SPM_SRC3_MASK */
+	mmio_write_32(SPM_SRC3_MASK,
+		((pwrctrl->reg_dvfsrc_event_trigger_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_sw2spm_int0_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_sw2spm_int1_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_sw2spm_int2_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_sw2spm_int3_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_sc_adsp2spm_wakeup_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_sc_sspm2spm_wakeup_mask_b & 0xf) << 6) |
+		((pwrctrl->reg_sc_scp2spm_wakeup_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_csyspwrreq_mask & 0x1) << 11) |
+		((pwrctrl->reg_spm_srcclkena_reserved_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_spm_infra_req_reserved_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_spm_apsrc_req_reserved_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_spm_vrf18_req_reserved_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_spm_ddr_en_reserved_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_mcupm_srcclkena_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_mcupm_infra_req_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_mcupm_apsrc_req_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_mcupm_vrf18_req_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_mcupm_ddr_en_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_msdc0_srcclkena_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_msdc0_infra_req_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_msdc0_apsrc_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_msdc0_vrf18_req_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_msdc0_ddr_en_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_msdc1_srcclkena_mask_b & 0x1) << 27) |
+		((pwrctrl->reg_msdc1_infra_req_mask_b & 0x1) << 28) |
+		((pwrctrl->reg_msdc1_apsrc_req_mask_b & 0x1) << 29) |
+		((pwrctrl->reg_msdc1_vrf18_req_mask_b & 0x1) << 30) |
+		((pwrctrl->reg_msdc1_ddr_en_mask_b & 0x1) << 31));
+
+	/* SPM_SRC4_MASK */
+	mmio_write_32(SPM_SRC4_MASK,
+		((pwrctrl->ccif_event_mask_b & 0xffff) << 0) |
+		((pwrctrl->reg_bak_psri_srcclkena_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_bak_psri_infra_req_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_bak_psri_apsrc_req_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_bak_psri_vrf18_req_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_bak_psri_ddr_en_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_dramc0_md32_infra_req_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_dramc0_md32_vrf18_req_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_dramc1_md32_infra_req_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_dramc1_md32_vrf18_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_conn_srcclkenb2pwrap_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_dramc0_md32_wakeup_mask & 0x1) << 26) |
+		((pwrctrl->reg_dramc1_md32_wakeup_mask & 0x1) << 27));
+
+	/* SPM_SRC5_MASK */
+	mmio_write_32(SPM_SRC5_MASK,
+		((pwrctrl->reg_mcusys_merge_apsrc_req_mask_b & 0x1ff) << 0) |
+		((pwrctrl->reg_mcusys_merge_ddr_en_mask_b & 0x1ff) << 9) |
+		((pwrctrl->reg_msdc2_srcclkena_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_msdc2_infra_req_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_msdc2_apsrc_req_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_msdc2_vrf18_req_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_msdc2_ddr_en_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_pcie_srcclkena_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_pcie_infra_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_pcie_apsrc_req_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_pcie_vrf18_req_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_pcie_ddr_en_mask_b & 0x1) << 27));
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK,
+		((pwrctrl->reg_wakeup_event_mask & 0xffffffff) << 0));
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	mmio_write_32(SPM_WAKEUP_EVENT_EXT_MASK,
+		((pwrctrl->reg_ext_wakeup_event_mask & 0xffffffff) << 0));
+
+	/* Auto-gen End */
+}
+
+void __spm_disable_pcm_timer(void)
+{
+	mmio_clrsetbits_32(PCM_CON1, RG_PCM_TIMER_EN_LSB, SPM_REGWR_CFG_KEY);
+}
+
+void __spm_set_wakeup_event(const struct pwr_ctrl *pwrctrl)
+{
+	uint32_t val, mask;
+
+	/* toggle event counter clear */
+	mmio_setbits_32(PCM_CON1,
+			SPM_REGWR_CFG_KEY | SPM_EVENT_COUNTER_CLR_LSB);
+
+	/* toggle for reset SYS TIMER start point */
+	mmio_setbits_32(SYS_TIMER_CON, SYS_TIMER_START_EN_LSB);
+
+	if (pwrctrl->timer_val_cust == 0U) {
+		val = pwrctrl->timer_val;
+	} else {
+		val = pwrctrl->timer_val_cust;
+	}
+
+	mmio_write_32(PCM_TIMER_VAL, val);
+	mmio_setbits_32(PCM_CON1, SPM_REGWR_CFG_KEY | RG_PCM_TIMER_EN_LSB);
+
+	/* unmask AP wakeup source */
+	if (pwrctrl->wake_src_cust == 0U) {
+		mask = pwrctrl->wake_src;
+	} else {
+		mask = pwrctrl->wake_src_cust;
+	}
+
+	if (pwrctrl->reg_csyspwrreq_mask != 0U) {
+		mask &= ~R12_CSYSPWREQ_B;
+	}
+
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK, ~mask);
+
+	/* unmask SPM ISR (keep TWAM setting) */
+	mmio_setbits_32(SPM_IRQ_MASK, ISRM_RET_IRQ_AUX);
+
+	/* toggle event counter clear */
+	mmio_clrsetbits_32(PCM_CON1, SPM_EVENT_COUNTER_CLR_LSB,
+			   SPM_REGWR_CFG_KEY);
+	/* toggle for reset SYS TIMER start point */
+	mmio_clrbits_32(SYS_TIMER_CON, SYS_TIMER_START_EN_LSB);
+}
+
+void __spm_set_pcm_flags(struct pwr_ctrl *pwrctrl)
+{
+	/* set PCM flags and data */
+	if (pwrctrl->pcm_flags_cust_clr != 0U) {
+		pwrctrl->pcm_flags &= ~pwrctrl->pcm_flags_cust_clr;
+	}
+
+	if (pwrctrl->pcm_flags_cust_set != 0U) {
+		pwrctrl->pcm_flags |= pwrctrl->pcm_flags_cust_set;
+	}
+
+	if (pwrctrl->pcm_flags1_cust_clr != 0U) {
+		pwrctrl->pcm_flags1 &= ~pwrctrl->pcm_flags1_cust_clr;
+	}
+
+	if (pwrctrl->pcm_flags1_cust_set != 0U) {
+		pwrctrl->pcm_flags1 |= pwrctrl->pcm_flags1_cust_set;
+	}
+
+	mmio_write_32(SPM_SW_FLAG_0, pwrctrl->pcm_flags);
+	mmio_write_32(SPM_SW_FLAG_1, pwrctrl->pcm_flags1);
+	mmio_write_32(SPM_SW_RSV_7, pwrctrl->pcm_flags);
+	mmio_write_32(SPM_SW_RSV_8, pwrctrl->pcm_flags1);
+}
+
+void __spm_get_wakeup_status(struct wake_status *wakesta,
+			     unsigned int ext_status)
+{
+	wakesta->tr.comm.r12 = mmio_read_32(SPM_BK_WAKE_EVENT);
+	wakesta->tr.comm.timer_out = mmio_read_32(SPM_BK_PCM_TIMER);
+	wakesta->tr.comm.r13 = mmio_read_32(PCM_REG13_DATA);
+	wakesta->tr.comm.req_sta0 = mmio_read_32(SRC_REQ_STA_0);
+	wakesta->tr.comm.req_sta1 = mmio_read_32(SRC_REQ_STA_1);
+	wakesta->tr.comm.req_sta2 = mmio_read_32(SRC_REQ_STA_2);
+	wakesta->tr.comm.req_sta3 = mmio_read_32(SRC_REQ_STA_3);
+	wakesta->tr.comm.req_sta4 = mmio_read_32(SRC_REQ_STA_4);
+	wakesta->tr.comm.debug_flag = mmio_read_32(PCM_WDT_LATCH_SPARE_0);
+	wakesta->tr.comm.debug_flag1 = mmio_read_32(PCM_WDT_LATCH_SPARE_1);
+
+	if ((ext_status & SPM_INTERNAL_STATUS_HW_S1) != 0U) {
+		wakesta->tr.comm.debug_flag |= (SPM_DBG_DEBUG_IDX_DDREN_WAKE |
+						SPM_DBG_DEBUG_IDX_DDREN_SLEEP);
+		mmio_write_32(PCM_WDT_LATCH_SPARE_0,
+			      wakesta->tr.comm.debug_flag);
+	}
+
+	wakesta->tr.comm.b_sw_flag0 = mmio_read_32(SPM_SW_RSV_7);
+	wakesta->tr.comm.b_sw_flag1 = mmio_read_32(SPM_SW_RSV_8);
+
+	/* record below spm info for debug */
+	wakesta->r12 = mmio_read_32(SPM_BK_WAKE_EVENT);
+	wakesta->r12_ext = mmio_read_32(SPM_WAKEUP_STA);
+	wakesta->raw_sta = mmio_read_32(SPM_WAKEUP_STA);
+	wakesta->raw_ext_sta = mmio_read_32(SPM_WAKEUP_EXT_STA);
+	wakesta->md32pcm_wakeup_sta = mmio_read_32(MD32PCM_WAKEUP_STA);
+	wakesta->md32pcm_event_sta = mmio_read_32(MD32PCM_EVENT_STA);
+	wakesta->src_req = mmio_read_32(SPM_SRC_REQ);
+
+	/* backup of SPM_WAKEUP_MISC */
+	wakesta->wake_misc = mmio_read_32(SPM_BK_WAKE_MISC);
+
+	/* get sleep time, backup of PCM_TIMER_OUT */
+	wakesta->timer_out = mmio_read_32(SPM_BK_PCM_TIMER);
+
+	/* get other SYS and co-clock status */
+	wakesta->r13 = mmio_read_32(PCM_REG13_DATA);
+	wakesta->idle_sta = mmio_read_32(SUBSYS_IDLE_STA);
+	wakesta->req_sta0 = mmio_read_32(SRC_REQ_STA_0);
+	wakesta->req_sta1 = mmio_read_32(SRC_REQ_STA_1);
+	wakesta->req_sta2 = mmio_read_32(SRC_REQ_STA_2);
+	wakesta->req_sta3 = mmio_read_32(SRC_REQ_STA_3);
+	wakesta->req_sta4 = mmio_read_32(SRC_REQ_STA_4);
+
+	/* get HW CG check status */
+	wakesta->cg_check_sta = mmio_read_32(SPM_CG_CHECK_STA);
+
+	/* get debug flag for PCM execution check */
+	wakesta->debug_flag = mmio_read_32(PCM_WDT_LATCH_SPARE_0);
+	wakesta->debug_flag1 = mmio_read_32(PCM_WDT_LATCH_SPARE_1);
+
+	/* get backup SW flag status */
+	wakesta->b_sw_flag0 = mmio_read_32(SPM_SW_RSV_7);
+	wakesta->b_sw_flag1 = mmio_read_32(SPM_SW_RSV_8);
+
+	wakesta->rt_req_sta0 = mmio_read_32(SPM_SW_RSV_2);
+	wakesta->rt_req_sta1 = mmio_read_32(SPM_SW_RSV_3);
+	wakesta->rt_req_sta2 = mmio_read_32(SPM_SW_RSV_4);
+	wakesta->rt_req_sta3 = mmio_read_32(SPM_SW_RSV_5);
+	wakesta->rt_req_sta4 = mmio_read_32(SPM_SW_RSV_6);
+
+	/* get ISR status */
+	wakesta->isr = mmio_read_32(SPM_IRQ_STA);
+
+	/* get SW flag status */
+	wakesta->sw_flag0 = mmio_read_32(SPM_SW_FLAG_0);
+	wakesta->sw_flag1 = mmio_read_32(SPM_SW_FLAG_1);
+
+	/* get CLK SETTLE */
+	wakesta->clk_settle = mmio_read_32(SPM_CLK_SETTLE);
+
+	/* check abort */
+	wakesta->abort = (wakesta->debug_flag & DEBUG_ABORT_MASK) |
+			 (wakesta->debug_flag1 & DEBUG_ABORT_MASK_1);
+}
+
+void __spm_clean_after_wakeup(void)
+{
+	mmio_write_32(SPM_BK_WAKE_EVENT,
+		      mmio_read_32(SPM_WAKEUP_STA) |
+		      mmio_read_32(SPM_BK_WAKE_EVENT));
+	mmio_write_32(SPM_CPU_WAKEUP_EVENT, 0);
+
+	/*
+	 * clean wakeup event raw status (for edge trigger event)
+	 * bit[28] for cpu wake up event
+	 */
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK, SPM_WAKEUP_EVENT_MASK_CLEAN_MASK);
+
+	/* clean ISR status (except TWAM) */
+	mmio_setbits_32(SPM_IRQ_MASK, ISRM_ALL_EXC_TWAM);
+	mmio_write_32(SPM_IRQ_STA, ISRC_ALL_EXC_TWAM);
+	mmio_write_32(SPM_SWINT_CLR, PCM_SW_INT_ALL);
+}
+
+void __spm_set_pcm_wdt(int en)
+{
+	mmio_clrsetbits_32(PCM_CON1, RG_PCM_WDT_EN_LSB,
+			   SPM_REGWR_CFG_KEY);
+
+	if (en == 1) {
+		mmio_clrsetbits_32(PCM_CON1, RG_PCM_WDT_WAKE_LSB,
+				   SPM_REGWR_CFG_KEY);
+
+		if (mmio_read_32(PCM_TIMER_VAL) > PCM_TIMER_MAX) {
+			mmio_write_32(PCM_TIMER_VAL, PCM_TIMER_MAX);
+		}
+
+		mmio_write_32(PCM_WDT_VAL,
+			      mmio_read_32(PCM_TIMER_VAL) + PCM_WDT_TIMEOUT);
+		mmio_setbits_32(PCM_CON1,
+				SPM_REGWR_CFG_KEY | RG_PCM_WDT_EN_LSB);
+	}
+}
+
+void __spm_send_cpu_wakeup_event(void)
+{
+	/* SPM will clear SPM_CPU_WAKEUP_EVENT */
+	mmio_write_32(SPM_CPU_WAKEUP_EVENT, 1);
+}
+
+void __spm_ext_int_wakeup_req_clr(void)
+{
+	mmio_write_32(EXT_INT_WAKEUP_REQ_CLR, mmio_read_32(ROOT_CPUTOP_ADDR));
+
+	/* Clear spm2mcupm wakeup interrupt status */
+	mmio_write_32(SPM2MCUPM_CON, 0);
+}
+
+void __spm_xo_soc_bblpm(int en)
+{
+	if (en == 1) {
+		mmio_clrsetbits_32(RC_M00_SRCLKEN_CFG,
+				   RC_SW_SRCLKEN_FPM, RC_SW_SRCLKEN_RC);
+		assert(mt_spm_bblpm_cnt == 0);
+		mt_spm_bblpm_cnt += 1;
+	} else {
+		mmio_clrsetbits_32(RC_M00_SRCLKEN_CFG,
+				   RC_SW_SRCLKEN_RC, RC_SW_SRCLKEN_FPM);
+		mt_spm_bblpm_cnt -= 1;
+	}
+}
+
+void __spm_hw_s1_state_monitor(int en, unsigned int *status)
+{
+	unsigned int reg;
+
+	reg = mmio_read_32(SPM_ACK_CHK_CON_3);
+
+	if (en == 1) {
+		reg &= ~SPM_ACK_CHK_3_CON_CLR_ALL;
+		mmio_write_32(SPM_ACK_CHK_CON_3, reg);
+		reg |= SPM_ACK_CHK_3_CON_EN;
+		mmio_write_32(SPM_ACK_CHK_CON_3, reg);
+	} else {
+		if (((reg & SPM_ACK_CHK_3_CON_RESULT) != 0U) &&
+		    (status != NULL)) {
+			*status |= SPM_INTERNAL_STATUS_HW_S1;
+		}
+
+		mmio_clrsetbits_32(SPM_ACK_CHK_CON_3, SPM_ACK_CHK_3_CON_EN,
+				   SPM_ACK_CHK_3_CON_HW_MODE_TRIG |
+				   SPM_ACK_CHK_3_CON_CLR_ALL);
+	}
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.h
new file mode 100644
index 0000000..1d0f783
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_internal.h
@@ -0,0 +1,637 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_INTERNAL_H
+#define MT_SPM_INTERNAL_H
+
+#include "mt_spm.h"
+
+/**************************************
+ * Config and Parameter
+ **************************************/
+#define POWER_ON_VAL0_DEF	0x0000F100
+#define POWER_ON_VAL1_DEF	0x80015860
+#define PCM_WDT_TIMEOUT		(30 * 32768)	/* 30s */
+#define PCM_TIMER_MAX		(0xffffffff - PCM_WDT_TIMEOUT)
+
+/**************************************
+ * Define and Declare
+ **************************************/
+/* PCM_PWR_IO_EN */
+#define PCM_PWRIO_EN_R0		(1U << 0)
+#define PCM_PWRIO_EN_R7		(1U << 7)
+#define PCM_RF_SYNC_R0		(1U << 16)
+#define PCM_RF_SYNC_R6		(1U << 22)
+#define PCM_RF_SYNC_R7		(1U << 23)
+
+/* SPM_SWINT */
+#define PCM_SW_INT0		(1U << 0)
+#define PCM_SW_INT1		(1U << 1)
+#define PCM_SW_INT2		(1U << 2)
+#define PCM_SW_INT3		(1U << 3)
+#define PCM_SW_INT4		(1U << 4)
+#define PCM_SW_INT5		(1U << 5)
+#define PCM_SW_INT6		(1U << 6)
+#define PCM_SW_INT7		(1U << 7)
+#define PCM_SW_INT8		(1U << 8)
+#define PCM_SW_INT9		(1U << 9)
+#define PCM_SW_INT_ALL		(PCM_SW_INT9 | PCM_SW_INT8 | PCM_SW_INT7 | \
+				 PCM_SW_INT6 | PCM_SW_INT5 | PCM_SW_INT4 | \
+				 PCM_SW_INT3 | PCM_SW_INT2 | PCM_SW_INT1 | \
+				 PCM_SW_INT0)
+
+/* SPM_AP_STANDBY_CON */
+#define WFI_OP_AND		1
+#define WFI_OP_OR		0
+
+/* SPM_IRQ_MASK */
+#define ISRM_TWAM		(1U << 2)
+#define ISRM_PCM_RETURN		(1U << 3)
+#define ISRM_RET_IRQ0		(1U << 8)
+#define ISRM_RET_IRQ1		(1U << 9)
+#define ISRM_RET_IRQ2		(1U << 10)
+#define ISRM_RET_IRQ3		(1U << 11)
+#define ISRM_RET_IRQ4		(1U << 12)
+#define ISRM_RET_IRQ5		(1U << 13)
+#define ISRM_RET_IRQ6		(1U << 14)
+#define ISRM_RET_IRQ7		(1U << 15)
+#define ISRM_RET_IRQ8		(1U << 16)
+#define ISRM_RET_IRQ9		(1U << 17)
+#define ISRM_RET_IRQ_AUX	((ISRM_RET_IRQ9) | (ISRM_RET_IRQ8) | \
+				 (ISRM_RET_IRQ7) | (ISRM_RET_IRQ6) | \
+				 (ISRM_RET_IRQ5) | (ISRM_RET_IRQ4) | \
+				 (ISRM_RET_IRQ3) | (ISRM_RET_IRQ2) | \
+				 (ISRM_RET_IRQ1))
+#define ISRM_ALL_EXC_TWAM	(ISRM_RET_IRQ_AUX)
+#define ISRM_ALL		(ISRM_ALL_EXC_TWAM | ISRM_TWAM)
+
+/* SPM_IRQ_STA */
+#define ISRS_TWAM		(1U << 2)
+#define ISRS_PCM_RETURN		(1U << 3)
+#define ISRC_TWAM		ISRS_TWAM
+#define ISRC_ALL_EXC_TWAM	ISRS_PCM_RETURN
+#define ISRC_ALL		(ISRC_ALL_EXC_TWAM | ISRC_TWAM)
+
+/* SPM_WAKEUP_MISC */
+#define WAKE_MISC_GIC_WAKEUP             0x3FF
+#define WAKE_MISC_DVFSRC_IRQ	         DVFSRC_IRQ_LSB
+#define WAKE_MISC_REG_CPU_WAKEUP         SPM_WAKEUP_MISC_REG_CPU_WAKEUP_LSB
+#define WAKE_MISC_PCM_TIMER_EVENT        PCM_TIMER_EVENT_LSB
+#define WAKE_MISC_PMIC_OUT_B		 ((1U << 19) | (1U << 20))
+#define WAKE_MISC_TWAM_IRQ_B             TWAM_IRQ_B_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET0        PMSR_IRQ_B_SET0_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET1        PMSR_IRQ_B_SET1_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET2        PMSR_IRQ_B_SET2_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_0   SPM_ACK_CHK_WAKEUP_0_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_1	 SPM_ACK_CHK_WAKEUP_1_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_2	 SPM_ACK_CHK_WAKEUP_2_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_3	 SPM_ACK_CHK_WAKEUP_3_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_ALL SPM_ACK_CHK_WAKEUP_ALL_LSB
+#define WAKE_MISC_PMIC_IRQ_ACK           PMIC_IRQ_ACK_LSB
+#define WAKE_MISC_PMIC_SCP_IRQ           PMIC_SCP_IRQ_LSB
+
+/* ABORT MASK for DEBUG FOORTPRINT */
+#define DEBUG_ABORT_MASK				\
+	(SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_APSRC |	\
+	 SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_DDREN)
+
+#define DEBUG_ABORT_MASK_1					\
+	(SPM_DBG1_DEBUG_IDX_VRCXO_SLEEP_ABORT |			\
+	 SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_LOW_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_HIGH_ABORT |	\
+	 SPM_DBG1_DEBUG_IDX_EMI_SLP_IDLE_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_LOW_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_HIGH_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SPM_DVFS_CMD_RDY_ABORT)
+
+#define MCUPM_MBOX_WAKEUP_CPU		0x0C55FD10
+
+struct pwr_ctrl {
+	uint32_t pcm_flags;
+	uint32_t pcm_flags_cust;
+	uint32_t pcm_flags_cust_set;
+	uint32_t pcm_flags_cust_clr;
+	uint32_t pcm_flags1;
+	uint32_t pcm_flags1_cust;
+	uint32_t pcm_flags1_cust_set;
+	uint32_t pcm_flags1_cust_clr;
+	uint32_t timer_val;
+	uint32_t timer_val_cust;
+	uint32_t timer_val_ramp_en;
+	uint32_t timer_val_ramp_en_sec;
+	uint32_t wake_src;
+	uint32_t wake_src_cust;
+	uint32_t wakelock_timer_val;
+	uint8_t wdt_disable;
+
+	/* Auto-gen Start */
+
+	/* SPM_CLK_CON */
+	uint8_t reg_srcclken0_ctl;
+	uint8_t reg_srcclken1_ctl;
+	uint8_t reg_spm_lock_infra_dcm;
+	uint8_t reg_srcclken_mask;
+	uint8_t reg_md1_c32rm_en;
+	uint8_t reg_md2_c32rm_en;
+	uint8_t reg_clksq0_sel_ctrl;
+	uint8_t reg_clksq1_sel_ctrl;
+	uint8_t reg_srcclken0_en;
+	uint8_t reg_srcclken1_en;
+	uint32_t reg_sysclk0_src_mask_b;
+	uint32_t reg_sysclk1_src_mask_b;
+
+	/* SPM_AP_STANDBY_CON */
+	uint8_t reg_wfi_op;
+	uint8_t reg_wfi_type;
+	uint8_t reg_mp0_cputop_idle_mask;
+	uint8_t reg_mp1_cputop_idle_mask;
+	uint8_t reg_mcusys_idle_mask;
+	uint8_t reg_md_apsrc_1_sel;
+	uint8_t reg_md_apsrc_0_sel;
+	uint8_t reg_conn_apsrc_sel;
+
+	/* SPM_SRC6_MASK */
+	uint8_t reg_dpmaif_srcclkena_mask_b;
+	uint8_t reg_dpmaif_infra_req_mask_b;
+	uint8_t reg_dpmaif_apsrc_req_mask_b;
+	uint8_t reg_dpmaif_vrf18_req_mask_b;
+	uint8_t reg_dpmaif_ddr_en_mask_b;
+	/* SPM_SRC_REQ */
+	uint8_t reg_spm_apsrc_req;
+	uint8_t reg_spm_f26m_req;
+	uint8_t reg_spm_infra_req;
+	uint8_t reg_spm_vrf18_req;
+	uint8_t reg_spm_ddr_en_req;
+	uint8_t reg_spm_dvfs_req;
+	uint8_t reg_spm_sw_mailbox_req;
+	uint8_t reg_spm_sspm_mailbox_req;
+	uint8_t reg_spm_adsp_mailbox_req;
+	uint8_t reg_spm_scp_mailbox_req;
+
+	/* SPM_SRC_MASK */
+	uint8_t reg_md_srcclkena_0_mask_b;
+	uint8_t reg_md_srcclkena2infra_req_0_mask_b;
+	uint8_t reg_md_apsrc2infra_req_0_mask_b;
+	uint8_t reg_md_apsrc_req_0_mask_b;
+	uint8_t reg_md_vrf18_req_0_mask_b;
+	uint8_t reg_md_ddr_en_0_mask_b;
+	uint8_t reg_md_srcclkena_1_mask_b;
+	uint8_t reg_md_srcclkena2infra_req_1_mask_b;
+	uint8_t reg_md_apsrc2infra_req_1_mask_b;
+	uint8_t reg_md_apsrc_req_1_mask_b;
+	uint8_t reg_md_vrf18_req_1_mask_b;
+	uint8_t reg_md_ddr_en_1_mask_b;
+	uint8_t reg_conn_srcclkena_mask_b;
+	uint8_t reg_conn_srcclkenb_mask_b;
+	uint8_t reg_conn_infra_req_mask_b;
+	uint8_t reg_conn_apsrc_req_mask_b;
+	uint8_t reg_conn_vrf18_req_mask_b;
+	uint8_t reg_conn_ddr_en_mask_b;
+	uint8_t reg_conn_vfe28_mask_b;
+	uint8_t reg_srcclkeni0_srcclkena_mask_b;
+	uint8_t reg_srcclkeni0_infra_req_mask_b;
+	uint8_t reg_srcclkeni1_srcclkena_mask_b;
+	uint8_t reg_srcclkeni1_infra_req_mask_b;
+	uint8_t reg_srcclkeni2_srcclkena_mask_b;
+	uint8_t reg_srcclkeni2_infra_req_mask_b;
+	uint8_t reg_infrasys_apsrc_req_mask_b;
+	uint8_t reg_infrasys_ddr_en_mask_b;
+	uint8_t reg_md32_srcclkena_mask_b;
+	uint8_t reg_md32_infra_req_mask_b;
+	uint8_t reg_md32_apsrc_req_mask_b;
+	uint8_t reg_md32_vrf18_req_mask_b;
+	uint8_t reg_md32_ddr_en_mask_b;
+
+	/* SPM_SRC2_MASK */
+	uint8_t reg_scp_srcclkena_mask_b;
+	uint8_t reg_scp_infra_req_mask_b;
+	uint8_t reg_scp_apsrc_req_mask_b;
+	uint8_t reg_scp_vrf18_req_mask_b;
+	uint8_t reg_scp_ddr_en_mask_b;
+	uint8_t reg_audio_dsp_srcclkena_mask_b;
+	uint8_t reg_audio_dsp_infra_req_mask_b;
+	uint8_t reg_audio_dsp_apsrc_req_mask_b;
+	uint8_t reg_audio_dsp_vrf18_req_mask_b;
+	uint8_t reg_audio_dsp_ddr_en_mask_b;
+	uint8_t reg_ufs_srcclkena_mask_b;
+	uint8_t reg_ufs_infra_req_mask_b;
+	uint8_t reg_ufs_apsrc_req_mask_b;
+	uint8_t reg_ufs_vrf18_req_mask_b;
+	uint8_t reg_ufs_ddr_en_mask_b;
+	uint8_t reg_disp0_apsrc_req_mask_b;
+	uint8_t reg_disp0_ddr_en_mask_b;
+	uint8_t reg_disp1_apsrc_req_mask_b;
+	uint8_t reg_disp1_ddr_en_mask_b;
+	uint8_t reg_gce_infra_req_mask_b;
+	uint8_t reg_gce_apsrc_req_mask_b;
+	uint8_t reg_gce_vrf18_req_mask_b;
+	uint8_t reg_gce_ddr_en_mask_b;
+	uint8_t reg_apu_srcclkena_mask_b;
+	uint8_t reg_apu_infra_req_mask_b;
+	uint8_t reg_apu_apsrc_req_mask_b;
+	uint8_t reg_apu_vrf18_req_mask_b;
+	uint8_t reg_apu_ddr_en_mask_b;
+	uint8_t reg_cg_check_srcclkena_mask_b;
+	uint8_t reg_cg_check_apsrc_req_mask_b;
+	uint8_t reg_cg_check_vrf18_req_mask_b;
+	uint8_t reg_cg_check_ddr_en_mask_b;
+
+	/* SPM_SRC3_MASK */
+	uint8_t reg_dvfsrc_event_trigger_mask_b;
+	uint8_t reg_sw2spm_int0_mask_b;
+	uint8_t reg_sw2spm_int1_mask_b;
+	uint8_t reg_sw2spm_int2_mask_b;
+	uint8_t reg_sw2spm_int3_mask_b;
+	uint8_t reg_sc_adsp2spm_wakeup_mask_b;
+	uint8_t reg_sc_sspm2spm_wakeup_mask_b;
+	uint8_t reg_sc_scp2spm_wakeup_mask_b;
+	uint8_t reg_csyspwrreq_mask;
+	uint8_t reg_spm_srcclkena_reserved_mask_b;
+	uint8_t reg_spm_infra_req_reserved_mask_b;
+	uint8_t reg_spm_apsrc_req_reserved_mask_b;
+	uint8_t reg_spm_vrf18_req_reserved_mask_b;
+	uint8_t reg_spm_ddr_en_reserved_mask_b;
+	uint8_t reg_mcupm_srcclkena_mask_b;
+	uint8_t reg_mcupm_infra_req_mask_b;
+	uint8_t reg_mcupm_apsrc_req_mask_b;
+	uint8_t reg_mcupm_vrf18_req_mask_b;
+	uint8_t reg_mcupm_ddr_en_mask_b;
+	uint8_t reg_msdc0_srcclkena_mask_b;
+	uint8_t reg_msdc0_infra_req_mask_b;
+	uint8_t reg_msdc0_apsrc_req_mask_b;
+	uint8_t reg_msdc0_vrf18_req_mask_b;
+	uint8_t reg_msdc0_ddr_en_mask_b;
+	uint8_t reg_msdc1_srcclkena_mask_b;
+	uint8_t reg_msdc1_infra_req_mask_b;
+	uint8_t reg_msdc1_apsrc_req_mask_b;
+	uint8_t reg_msdc1_vrf18_req_mask_b;
+	uint8_t reg_msdc1_ddr_en_mask_b;
+
+	/* SPM_SRC4_MASK */
+	uint32_t ccif_event_mask_b;
+	uint8_t reg_bak_psri_srcclkena_mask_b;
+	uint8_t reg_bak_psri_infra_req_mask_b;
+	uint8_t reg_bak_psri_apsrc_req_mask_b;
+	uint8_t reg_bak_psri_vrf18_req_mask_b;
+	uint8_t reg_bak_psri_ddr_en_mask_b;
+	uint8_t reg_dramc0_md32_infra_req_mask_b;
+	uint8_t reg_dramc0_md32_vrf18_req_mask_b;
+	uint8_t reg_dramc1_md32_infra_req_mask_b;
+	uint8_t reg_dramc1_md32_vrf18_req_mask_b;
+	uint8_t reg_conn_srcclkenb2pwrap_mask_b;
+	uint8_t reg_dramc0_md32_wakeup_mask;
+	uint8_t reg_dramc1_md32_wakeup_mask;
+
+	/* SPM_SRC5_MASK */
+	uint32_t reg_mcusys_merge_apsrc_req_mask_b;
+	uint32_t reg_mcusys_merge_ddr_en_mask_b;
+	uint8_t reg_msdc2_srcclkena_mask_b;
+	uint8_t reg_msdc2_infra_req_mask_b;
+	uint8_t reg_msdc2_apsrc_req_mask_b;
+	uint8_t reg_msdc2_vrf18_req_mask_b;
+	uint8_t reg_msdc2_ddr_en_mask_b;
+	uint8_t reg_pcie_srcclkena_mask_b;
+	uint8_t reg_pcie_infra_req_mask_b;
+	uint8_t reg_pcie_apsrc_req_mask_b;
+	uint8_t reg_pcie_vrf18_req_mask_b;
+	uint8_t reg_pcie_ddr_en_mask_b;
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	uint32_t reg_wakeup_event_mask;
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	uint32_t reg_ext_wakeup_event_mask;
+
+	/* Auto-gen End */
+};
+
+/* code gen by spm_pwr_ctrl_atf.pl, need struct pwr_ctrl */
+enum pwr_ctrl_enum {
+	PW_PCM_FLAGS,
+	PW_PCM_FLAGS_CUST,
+	PW_PCM_FLAGS_CUST_SET,
+	PW_PCM_FLAGS_CUST_CLR,
+	PW_PCM_FLAGS1,
+	PW_PCM_FLAGS1_CUST,
+	PW_PCM_FLAGS1_CUST_SET,
+	PW_PCM_FLAGS1_CUST_CLR,
+	PW_TIMER_VAL,
+	PW_TIMER_VAL_CUST,
+	PW_TIMER_VAL_RAMP_EN,
+	PW_TIMER_VAL_RAMP_EN_SEC,
+	PW_WAKE_SRC,
+	PW_WAKE_SRC_CUST,
+	PW_WAKELOCK_TIMER_VAL,
+	PW_WDT_DISABLE,
+
+	/* SPM_CLK_CON */
+	PW_REG_SRCCLKEN0_CTL,
+	PW_REG_SRCCLKEN1_CTL,
+	PW_REG_SPM_LOCK_INFRA_DCM,
+	PW_REG_SRCCLKEN_MASK,
+	PW_REG_MD1_C32RM_EN,
+	PW_REG_MD2_C32RM_EN,
+	PW_REG_CLKSQ0_SEL_CTRL,
+	PW_REG_CLKSQ1_SEL_CTRL,
+	PW_REG_SRCCLKEN0_EN,
+	PW_REG_SRCCLKEN1_EN,
+	PW_REG_SYSCLK0_SRC_MASK_B,
+	PW_REG_SYSCLK1_SRC_MASK_B,
+
+	/* SPM_AP_STANDBY_CON */
+	PW_REG_WFI_OP,
+	PW_REG_WFI_TYPE,
+	PW_REG_MP0_CPUTOP_IDLE_MASK,
+	PW_REG_MP1_CPUTOP_IDLE_MASK,
+	PW_REG_MCUSYS_IDLE_MASK,
+	PW_REG_MD_APSRC_1_SEL,
+	PW_REG_MD_APSRC_0_SEL,
+	PW_REG_CONN_APSRC_SEL,
+
+	/* SPM_SRC6_MASK */
+	PW_REG_DPMAIF_SRCCLKENA_MASK_B,
+	PW_REG_DPMAIF_INFRA_REQ_MASK_B,
+	PW_REG_DPMAIF_APSRC_REQ_MASK_B,
+	PW_REG_DPMAIF_VRF18_REQ_MASK_B,
+	PW_REG_DPMAIF_DDR_EN_MASK_B,
+
+	/* SPM_SRC_REQ */
+	PW_REG_SPM_APSRC_REQ,
+	PW_REG_SPM_F26M_REQ,
+	PW_REG_SPM_INFRA_REQ,
+	PW_REG_SPM_VRF18_REQ,
+	PW_REG_SPM_DDR_EN_REQ,
+	PW_REG_SPM_DVFS_REQ,
+	PW_REG_SPM_SW_MAILBOX_REQ,
+	PW_REG_SPM_SSPM_MAILBOX_REQ,
+	PW_REG_SPM_ADSP_MAILBOX_REQ,
+	PW_REG_SPM_SCP_MAILBOX_REQ,
+
+	/* SPM_SRC_MASK */
+	PW_REG_MD_SRCCLKENA_0_MASK_B,
+	PW_REG_MD_SRCCLKENA2INFRA_REQ_0_MASK_B,
+	PW_REG_MD_APSRC2INFRA_REQ_0_MASK_B,
+	PW_REG_MD_APSRC_REQ_0_MASK_B,
+	PW_REG_MD_VRF18_REQ_0_MASK_B,
+	PW_REG_MD_DDR_EN_0_MASK_B,
+	PW_REG_MD_SRCCLKENA_1_MASK_B,
+	PW_REG_MD_SRCCLKENA2INFRA_REQ_1_MASK_B,
+	PW_REG_MD_APSRC2INFRA_REQ_1_MASK_B,
+	PW_REG_MD_APSRC_REQ_1_MASK_B,
+	PW_REG_MD_VRF18_REQ_1_MASK_B,
+	PW_REG_MD_DDR_EN_1_MASK_B,
+	PW_REG_CONN_SRCCLKENA_MASK_B,
+	PW_REG_CONN_SRCCLKENB_MASK_B,
+	PW_REG_CONN_INFRA_REQ_MASK_B,
+	PW_REG_CONN_APSRC_REQ_MASK_B,
+	PW_REG_CONN_VRF18_REQ_MASK_B,
+	PW_REG_CONN_DDR_EN_MASK_B,
+	PW_REG_CONN_VFE28_MASK_B,
+	PW_REG_SRCCLKENI0_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI0_INFRA_REQ_MASK_B,
+	PW_REG_SRCCLKENI1_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI1_INFRA_REQ_MASK_B,
+	PW_REG_SRCCLKENI2_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI2_INFRA_REQ_MASK_B,
+	PW_REG_INFRASYS_APSRC_REQ_MASK_B,
+	PW_REG_INFRASYS_DDR_EN_MASK_B,
+	PW_REG_MD32_SRCCLKENA_MASK_B,
+	PW_REG_MD32_INFRA_REQ_MASK_B,
+	PW_REG_MD32_APSRC_REQ_MASK_B,
+	PW_REG_MD32_VRF18_REQ_MASK_B,
+	PW_REG_MD32_DDR_EN_MASK_B,
+
+	/* SPM_SRC2_MASK */
+	PW_REG_SCP_SRCCLKENA_MASK_B,
+	PW_REG_SCP_INFRA_REQ_MASK_B,
+	PW_REG_SCP_APSRC_REQ_MASK_B,
+	PW_REG_SCP_VRF18_REQ_MASK_B,
+	PW_REG_SCP_DDR_EN_MASK_B,
+	PW_REG_AUDIO_DSP_SRCCLKENA_MASK_B,
+	PW_REG_AUDIO_DSP_INFRA_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_APSRC_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_VRF18_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_DDR_EN_MASK_B,
+	PW_REG_UFS_SRCCLKENA_MASK_B,
+	PW_REG_UFS_INFRA_REQ_MASK_B,
+	PW_REG_UFS_APSRC_REQ_MASK_B,
+	PW_REG_UFS_VRF18_REQ_MASK_B,
+	PW_REG_UFS_DDR_EN_MASK_B,
+	PW_REG_DISP0_APSRC_REQ_MASK_B,
+	PW_REG_DISP0_DDR_EN_MASK_B,
+	PW_REG_DISP1_APSRC_REQ_MASK_B,
+	PW_REG_DISP1_DDR_EN_MASK_B,
+	PW_REG_GCE_INFRA_REQ_MASK_B,
+	PW_REG_GCE_APSRC_REQ_MASK_B,
+	PW_REG_GCE_VRF18_REQ_MASK_B,
+	PW_REG_GCE_DDR_EN_MASK_B,
+	PW_REG_APU_SRCCLKENA_MASK_B,
+	PW_REG_APU_INFRA_REQ_MASK_B,
+	PW_REG_APU_APSRC_REQ_MASK_B,
+	PW_REG_APU_VRF18_REQ_MASK_B,
+	PW_REG_APU_DDR_EN_MASK_B,
+	PW_REG_CG_CHECK_SRCCLKENA_MASK_B,
+	PW_REG_CG_CHECK_APSRC_REQ_MASK_B,
+	PW_REG_CG_CHECK_VRF18_REQ_MASK_B,
+	PW_REG_CG_CHECK_DDR_EN_MASK_B,
+
+	/* SPM_SRC3_MASK */
+	PW_REG_DVFSRC_EVENT_TRIGGER_MASK_B,
+	PW_REG_SW2SPM_INT0_MASK_B,
+	PW_REG_SW2SPM_INT1_MASK_B,
+	PW_REG_SW2SPM_INT2_MASK_B,
+	PW_REG_SW2SPM_INT3_MASK_B,
+	PW_REG_SC_ADSP2SPM_WAKEUP_MASK_B,
+	PW_REG_SC_SSPM2SPM_WAKEUP_MASK_B,
+	PW_REG_SC_SCP2SPM_WAKEUP_MASK_B,
+	PW_REG_CSYSPWRREQ_MASK,
+	PW_REG_SPM_SRCCLKENA_RESERVED_MASK_B,
+	PW_REG_SPM_INFRA_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_APSRC_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_VRF18_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_DDR_EN_RESERVED_MASK_B,
+	PW_REG_MCUPM_SRCCLKENA_MASK_B,
+	PW_REG_MCUPM_INFRA_REQ_MASK_B,
+	PW_REG_MCUPM_APSRC_REQ_MASK_B,
+	PW_REG_MCUPM_VRF18_REQ_MASK_B,
+	PW_REG_MCUPM_DDR_EN_MASK_B,
+	PW_REG_MSDC0_SRCCLKENA_MASK_B,
+	PW_REG_MSDC0_INFRA_REQ_MASK_B,
+	PW_REG_MSDC0_APSRC_REQ_MASK_B,
+	PW_REG_MSDC0_VRF18_REQ_MASK_B,
+	PW_REG_MSDC0_DDR_EN_MASK_B,
+	PW_REG_MSDC1_SRCCLKENA_MASK_B,
+	PW_REG_MSDC1_INFRA_REQ_MASK_B,
+	PW_REG_MSDC1_APSRC_REQ_MASK_B,
+	PW_REG_MSDC1_VRF18_REQ_MASK_B,
+	PW_REG_MSDC1_DDR_EN_MASK_B,
+
+	/* SPM_SRC4_MASK */
+	PW_CCIF_EVENT_MASK_B,
+	PW_REG_BAK_PSRI_SRCCLKENA_MASK_B,
+	PW_REG_BAK_PSRI_INFRA_REQ_MASK_B,
+	PW_REG_BAK_PSRI_APSRC_REQ_MASK_B,
+	PW_REG_BAK_PSRI_VRF18_REQ_MASK_B,
+	PW_REG_BAK_PSRI_DDR_EN_MASK_B,
+	PW_REG_DRAMC0_MD32_INFRA_REQ_MASK_B,
+	PW_REG_DRAMC0_MD32_VRF18_REQ_MASK_B,
+	PW_REG_DRAMC1_MD32_INFRA_REQ_MASK_B,
+	PW_REG_DRAMC1_MD32_VRF18_REQ_MASK_B,
+	PW_REG_CONN_SRCCLKENB2PWRAP_MASK_B,
+	PW_REG_DRAMC0_MD32_WAKEUP_MASK,
+	PW_REG_DRAMC1_MD32_WAKEUP_MASK,
+
+	/* SPM_SRC5_MASK */
+	PW_REG_MCUSYS_MERGE_APSRC_REQ_MASK_B,
+	PW_REG_MCUSYS_MERGE_DDR_EN_MASK_B,
+	PW_REG_MSDC2_SRCCLKENA_MASK_B,
+	PW_REG_MSDC2_INFRA_REQ_MASK_B,
+	PW_REG_MSDC2_APSRC_REQ_MASK_B,
+	PW_REG_MSDC2_VRF18_REQ_MASK_B,
+	PW_REG_MSDC2_DDR_EN_MASK_B,
+	PW_REG_PCIE_SRCCLKENA_MASK_B,
+	PW_REG_PCIE_INFRA_REQ_MASK_B,
+	PW_REG_PCIE_APSRC_REQ_MASK_B,
+	PW_REG_PCIE_VRF18_REQ_MASK_B,
+	PW_REG_PCIE_DDR_EN_MASK_B,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	PW_REG_WAKEUP_EVENT_MASK,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	PW_REG_EXT_WAKEUP_EVENT_MASK,
+
+	PW_MAX_COUNT,
+};
+
+#define SPM_INTERNAL_STATUS_HW_S1	(1U << 0)
+#define SPM_ACK_CHK_3_SEL_HW_S1		0x00350098
+#define SPM_ACK_CHK_3_HW_S1_CNT		1
+#define SPM_ACK_CHK_3_CON_HW_MODE_TRIG	0x800
+#define SPM_ACK_CHK_3_CON_EN		0x110
+#define SPM_ACK_CHK_3_CON_CLR_ALL	0x2
+#define SPM_ACK_CHK_3_CON_RESULT	0x8000
+
+struct wake_status_trace_comm {
+	uint32_t debug_flag;	/* PCM_WDT_LATCH_SPARE_0 */
+	uint32_t debug_flag1;	/* PCM_WDT_LATCH_SPARE_1 */
+	uint32_t timer_out;	/* SPM_SW_RSV_6*/
+	uint32_t b_sw_flag0;	/* SPM_SW_RSV_7 */
+	uint32_t b_sw_flag1;	/* SPM_SW_RSV_7 */
+	uint32_t r12;		/* SPM_SW_RSV_0 */
+	uint32_t r13;		/* PCM_REG13_DATA */
+	uint32_t req_sta0;	/* SRC_REQ_STA_0 */
+	uint32_t req_sta1;	/* SRC_REQ_STA_1 */
+	uint32_t req_sta2;	/* SRC_REQ_STA_2 */
+	uint32_t req_sta3;	/* SRC_REQ_STA_3 */
+	uint32_t req_sta4;	/* SRC_REQ_STA_4 */
+};
+
+struct wake_status_trace {
+	struct wake_status_trace_comm comm;
+};
+
+struct wake_status {
+	struct wake_status_trace tr;
+	uint32_t r12;			/* SPM_BK_WAKE_EVENT */
+	uint32_t r12_ext;		/* SPM_WAKEUP_EXT_STA */
+	uint32_t raw_sta;		/* SPM_WAKEUP_STA */
+	uint32_t raw_ext_sta;		/* SPM_WAKEUP_EXT_STA */
+	uint32_t md32pcm_wakeup_sta;	/* MD32CPM_WAKEUP_STA */
+	uint32_t md32pcm_event_sta;	/* MD32PCM_EVENT_STA */
+	uint32_t wake_misc;		/* SPM_BK_WAKE_MISC */
+	uint32_t timer_out;		/* SPM_BK_PCM_TIMER */
+	uint32_t r13;			/* PCM_REG13_DATA */
+	uint32_t idle_sta;		/* SUBSYS_IDLE_STA */
+	uint32_t req_sta0;		/* SRC_REQ_STA_0 */
+	uint32_t req_sta1;		/* SRC_REQ_STA_1 */
+	uint32_t req_sta2;		/* SRC_REQ_STA_2 */
+	uint32_t req_sta3;		/* SRC_REQ_STA_3 */
+	uint32_t req_sta4;		/* SRC_REQ_STA_4 */
+	uint32_t cg_check_sta;		/* SPM_CG_CHECK_STA */
+	uint32_t debug_flag;		/* PCM_WDT_LATCH_SPARE_0 */
+	uint32_t debug_flag1;		/* PCM_WDT_LATCH_SPARE_1 */
+	uint32_t b_sw_flag0;		/* SPM_SW_RSV_7 */
+	uint32_t b_sw_flag1;		/* SPM_SW_RSV_8 */
+	uint32_t isr;			/* SPM_IRQ_STA */
+	uint32_t sw_flag0;		/* SPM_SW_FLAG_0 */
+	uint32_t sw_flag1;		/* SPM_SW_FLAG_1 */
+	uint32_t clk_settle;		/* SPM_CLK_SETTLE */
+	uint32_t src_req;		/* SPM_SRC_REQ */
+	uint32_t log_index;
+	uint32_t abort;
+	uint32_t rt_req_sta0;		/* SPM_SW_RSV_2 */
+	uint32_t rt_req_sta1;		/* SPM_SW_RSV_3 */
+	uint32_t rt_req_sta2;		/* SPM_SW_RSV_4 */
+	uint32_t rt_req_sta3;		/* SPM_SW_RSV_5 */
+	uint32_t rt_req_sta4;		/* SPM_SW_RSV_6 */
+	uint32_t mcupm_req_sta;
+};
+
+struct spm_lp_scen {
+	struct pcm_desc *pcmdesc;
+	struct pwr_ctrl *pwrctrl;
+};
+
+extern struct spm_lp_scen __spm_vcorefs;
+extern void __spm_set_cpu_status(unsigned int cpu);
+extern void __spm_reset_and_init_pcm(const struct pcm_desc *pcmdesc);
+extern void __spm_kick_im_to_fetch(const struct pcm_desc *pcmdesc);
+extern void __spm_init_pcm_register(void);
+extern void __spm_src_req_update(const struct pwr_ctrl *pwrctrl,
+				 unsigned int resource_usage);
+extern void __spm_set_power_control(const struct pwr_ctrl *pwrctrl);
+extern void __spm_disable_pcm_timer(void);
+extern void __spm_set_wakeup_event(const struct pwr_ctrl *pwrctrl);
+extern void __spm_kick_pcm_to_run(struct pwr_ctrl *pwrctrl);
+extern void __spm_set_pcm_flags(struct pwr_ctrl *pwrctrl);
+extern void __spm_send_cpu_wakeup_event(void);
+extern void __spm_get_wakeup_status(struct wake_status *wakesta,
+				    unsigned int ext_status);
+extern void __spm_clean_after_wakeup(void);
+extern wake_reason_t
+__spm_output_wake_reason(int state_id, const struct wake_status *wakesta);
+extern void
+__spm_sync_vcore_dvfs_power_control(struct pwr_ctrl *dest_pwr_ctrl,
+				    const struct pwr_ctrl *src_pwr_ctrl);
+extern void __spm_set_pcm_wdt(int en);
+extern uint32_t _spm_get_wake_period(int pwake_time, wake_reason_t last_wr);
+extern void __spm_set_fw_resume_option(struct pwr_ctrl *pwrctrl);
+extern void __spm_ext_int_wakeup_req_clr(void);
+extern void __spm_xo_soc_bblpm(int en);
+
+static inline void set_pwrctrl_pcm_flags(struct pwr_ctrl *pwrctrl,
+					 uint32_t flags)
+{
+	if (pwrctrl->pcm_flags_cust == 0U) {
+		pwrctrl->pcm_flags = flags;
+	} else {
+		pwrctrl->pcm_flags = pwrctrl->pcm_flags_cust;
+	}
+}
+
+static inline void set_pwrctrl_pcm_flags1(struct pwr_ctrl *pwrctrl,
+					  uint32_t flags)
+{
+	if (pwrctrl->pcm_flags1_cust == 0U) {
+		pwrctrl->pcm_flags1 = flags;
+	} else {
+		pwrctrl->pcm_flags1 = pwrctrl->pcm_flags1_cust;
+	}
+}
+
+extern void __spm_hw_s1_state_monitor(int en, unsigned int *status);
+
+static inline void spm_hw_s1_state_monitor_resume(void)
+{
+	__spm_hw_s1_state_monitor(1, NULL);
+}
+
+static inline void spm_hw_s1_state_monitor_pause(unsigned int *status)
+{
+	__spm_hw_s1_state_monitor(0, status);
+}
+#endif /* MT_SPM_INTERNAL_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.c
new file mode 100644
index 0000000..4e5f6a0
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.c
@@ -0,0 +1,159 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_reg.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+
+/* PMIC_WRAP MT6359 */
+#define VCORE_BASE_UV		40000
+#define VOLT_TO_PMIC_VAL(volt)	(((volt) - VCORE_BASE_UV + 625 - 1) / 625)
+#define PMIC_VAL_TO_VOLT(pmic)	(((pmic) * 625) + VCORE_BASE_UV)
+
+#define NR_PMIC_WRAP_CMD	(NR_IDX_ALL)
+#define SPM_DATA_SHIFT		16
+
+#define BUCK_VGPU11_ELR0	0x15B4
+#define TOP_SPI_CON0		0x0456
+#define BUCK_TOP_CON1		0x1443
+#define TOP_CON			0x0013
+#define TOP_DIG_WPK		0x03a9
+#define TOP_CON_LOCK		0x03a8
+#define TOP_CLK_CON0		0x0134
+
+struct pmic_wrap_cmd {
+	unsigned long cmd_addr;
+	unsigned long cmd_wdata;
+};
+
+struct pmic_wrap_setting {
+	enum pmic_wrap_phase_id phase;
+	struct pmic_wrap_cmd addr[NR_PMIC_WRAP_CMD];
+	struct {
+		struct {
+			unsigned long cmd_addr;
+			unsigned long cmd_wdata;
+		} _[NR_PMIC_WRAP_CMD];
+		const int nr_idx;
+	} set[NR_PMIC_WRAP_PHASE];
+};
+
+static struct pmic_wrap_setting pw = {
+	.phase = NR_PMIC_WRAP_PHASE,    /* invalid setting for init */
+	.addr = { {0UL, 0UL} },
+	.set[PMIC_WRAP_PHASE_ALLINONE] = {
+		._[CMD_0]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(72500),},
+		._[CMD_1]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(65000),},
+		._[CMD_2]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(60000),},
+		._[CMD_3]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(57500),},
+		._[CMD_4]	= {TOP_SPI_CON0, 0x1,},
+		._[CMD_5]	= {TOP_SPI_CON0, 0x0,},
+		._[CMD_6]	= {BUCK_TOP_CON1, 0x0,},
+		._[CMD_7]	= {BUCK_TOP_CON1, 0xf,},
+		._[CMD_8]	= {TOP_CON, 0x3,},
+		._[CMD_9]	= {TOP_CON, 0x0,},
+		._[CMD_10]	= {TOP_DIG_WPK, 0x63,},
+		._[CMD_11]	= {TOP_CON_LOCK, 0x15,},
+		._[CMD_12]	= {TOP_DIG_WPK, 0x0,},
+		._[CMD_13]	= {TOP_CON_LOCK, 0x0,},
+		._[CMD_14]	= {TOP_CLK_CON0, 0x40,},
+		._[CMD_15]	= {TOP_CLK_CON0, 0x0,},
+		.nr_idx = NR_IDX_ALL,
+	},
+};
+
+void _mt_spm_pmic_table_init(void)
+{
+	struct pmic_wrap_cmd pwrap_cmd_default[NR_PMIC_WRAP_CMD] = {
+		{(uint32_t)SPM_DVFS_CMD0, (uint32_t)SPM_DVFS_CMD0,},
+		{(uint32_t)SPM_DVFS_CMD1, (uint32_t)SPM_DVFS_CMD1,},
+		{(uint32_t)SPM_DVFS_CMD2, (uint32_t)SPM_DVFS_CMD2,},
+		{(uint32_t)SPM_DVFS_CMD3, (uint32_t)SPM_DVFS_CMD3,},
+		{(uint32_t)SPM_DVFS_CMD4, (uint32_t)SPM_DVFS_CMD4,},
+		{(uint32_t)SPM_DVFS_CMD5, (uint32_t)SPM_DVFS_CMD5,},
+		{(uint32_t)SPM_DVFS_CMD6, (uint32_t)SPM_DVFS_CMD6,},
+		{(uint32_t)SPM_DVFS_CMD7, (uint32_t)SPM_DVFS_CMD7,},
+		{(uint32_t)SPM_DVFS_CMD8, (uint32_t)SPM_DVFS_CMD8,},
+		{(uint32_t)SPM_DVFS_CMD9, (uint32_t)SPM_DVFS_CMD9,},
+		{(uint32_t)SPM_DVFS_CMD10, (uint32_t)SPM_DVFS_CMD10,},
+		{(uint32_t)SPM_DVFS_CMD11, (uint32_t)SPM_DVFS_CMD11,},
+		{(uint32_t)SPM_DVFS_CMD12, (uint32_t)SPM_DVFS_CMD12,},
+		{(uint32_t)SPM_DVFS_CMD13, (uint32_t)SPM_DVFS_CMD13,},
+		{(uint32_t)SPM_DVFS_CMD14, (uint32_t)SPM_DVFS_CMD14,},
+		{(uint32_t)SPM_DVFS_CMD15, (uint32_t)SPM_DVFS_CMD15,},
+	};
+
+	memcpy(pw.addr, pwrap_cmd_default, sizeof(pwrap_cmd_default));
+}
+
+void mt_spm_pmic_wrap_set_phase(enum pmic_wrap_phase_id phase)
+{
+	uint32_t idx, addr, data;
+
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return;
+	}
+
+	if (pw.phase == phase) {
+		return;
+	}
+
+	if (pw.addr[0].cmd_addr == 0UL) {
+		_mt_spm_pmic_table_init();
+	}
+
+	pw.phase = phase;
+	mmio_write_32(POWERON_CONFIG_EN, SPM_REGWR_CFG_KEY | BCLK_CG_EN_LSB);
+
+	for (idx = 0U; idx < pw.set[phase].nr_idx; idx++) {
+		addr = pw.set[phase]._[idx].cmd_addr << SPM_DATA_SHIFT;
+		data = pw.set[phase]._[idx].cmd_wdata;
+		mmio_write_32(pw.addr[idx].cmd_addr, addr | data);
+	}
+}
+
+void mt_spm_pmic_wrap_set_cmd(enum pmic_wrap_phase_id phase, uint32_t idx,
+			      uint32_t cmd_wdata)
+{
+	uint32_t addr;
+
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return;
+	}
+
+	if (idx >= pw.set[phase].nr_idx) {
+		return;
+	}
+
+	pw.set[phase]._[idx].cmd_wdata = cmd_wdata;
+	mmio_write_32(POWERON_CONFIG_EN, SPM_REGWR_CFG_KEY | BCLK_CG_EN_LSB);
+
+	if (pw.phase == phase) {
+		addr = pw.set[phase]._[idx].cmd_addr << SPM_DATA_SHIFT;
+		mmio_write_32(pw.addr[idx].cmd_addr, addr | cmd_wdata);
+	}
+}
+
+uint64_t mt_spm_pmic_wrap_get_cmd(enum pmic_wrap_phase_id phase, uint32_t idx)
+{
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return 0UL;
+	}
+
+	if (idx >= pw.set[phase].nr_idx) {
+		return 0UL;
+	}
+
+	return pw.set[phase]._[idx].cmd_wdata;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.h
new file mode 100644
index 0000000..6e20916
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_pmic_wrap.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/****************************************************************
+ * Auto generated by DE, please DO NOT modify this file directly.
+ *****************************************************************/
+#ifndef MT_SPM_PMIC_WRAP_H
+#define MT_SPM_PMIC_WRAP_H
+
+enum pmic_wrap_phase_id {
+	PMIC_WRAP_PHASE_ALLINONE,
+	NR_PMIC_WRAP_PHASE,
+};
+
+/* IDX mapping, PMIC_WRAP_PHASE_ALLINONE */
+enum {
+	CMD_0,        /* 0x0 */
+	CMD_1,        /* 0x1 */
+	CMD_2,        /* 0x2 */
+	CMD_3,        /* 0x3 */
+	CMD_4,        /* 0x4 */
+	CMD_5,        /* 0x5 */
+	CMD_6,        /* 0x6 */
+	CMD_7,        /* 0x7 */
+	CMD_8,        /* 0x8 */
+	CMD_9,        /* 0x9 */
+	CMD_10,        /* 0xA */
+	CMD_11,        /* 0xB */
+	CMD_12,        /* 0xC */
+	CMD_13,        /* 0xD */
+	CMD_14,        /* 0xE */
+	CMD_15,        /* 0xF */
+	NR_IDX_ALL,
+};
+
+/* APIs */
+extern void mt_spm_pmic_wrap_set_phase(enum pmic_wrap_phase_id phase);
+extern void mt_spm_pmic_wrap_set_cmd(enum pmic_wrap_phase_id phase,
+				     uint32_t idx, uint32_t cmd_wdata);
+extern uint64_t mt_spm_pmic_wrap_get_cmd(enum pmic_wrap_phase_id phase,
+					 uint32_t idx);
+#endif /* MT_SPM_PMIC_WRAP_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_reg.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_reg.h
new file mode 100644
index 0000000..fba011d
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_reg.h
@@ -0,0 +1,2919 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/****************************************************************
+ * Auto generated by DE, please DO NOT modify this file directly.
+ *****************************************************************/
+#ifndef MT_SPM_REG
+#define MT_SPM_REG
+
+#include "pcm_def.h"
+#include <platform_def.h>
+#include "sleep_def.h"
+
+/**************************************
+ * Define and Declare
+ **************************************/
+#define POWERON_CONFIG_EN              (SPM_BASE + 0x000)
+#define SPM_POWER_ON_VAL0              (SPM_BASE + 0x004)
+#define SPM_POWER_ON_VAL1              (SPM_BASE + 0x008)
+#define SPM_CLK_CON                    (SPM_BASE + 0x00C)
+#define SPM_CLK_SETTLE                 (SPM_BASE + 0x010)
+#define SPM_AP_STANDBY_CON             (SPM_BASE + 0x014)
+#define PCM_CON0                       (SPM_BASE + 0x018)
+#define PCM_CON1                       (SPM_BASE + 0x01C)
+#define SPM_POWER_ON_VAL2              (SPM_BASE + 0x020)
+#define SPM_POWER_ON_VAL3              (SPM_BASE + 0x024)
+#define PCM_REG_DATA_INI               (SPM_BASE + 0x028)
+#define PCM_PWR_IO_EN                  (SPM_BASE + 0x02C)
+#define PCM_TIMER_VAL                  (SPM_BASE + 0x030)
+#define PCM_WDT_VAL                    (SPM_BASE + 0x034)
+#define SPM_SRC6_MASK                  (SPM_BASE + 0x038)
+#define SPM_SW_RST_CON                 (SPM_BASE + 0x040)
+#define SPM_SW_RST_CON_SET             (SPM_BASE + 0x044)
+#define SPM_SW_RST_CON_CLR             (SPM_BASE + 0x048)
+#define VS1_PSR_MASK_B                 (SPM_BASE + 0x04C)
+#define VS2_PSR_MASK_B                 (SPM_BASE + 0x050)
+#define MD32_CLK_CON                   (SPM_BASE + 0x084)
+#define SPM_SRAM_RSV_CON               (SPM_BASE + 0x088)
+#define SPM_SWINT                      (SPM_BASE + 0x08C)
+#define SPM_SWINT_SET                  (SPM_BASE + 0x090)
+#define SPM_SWINT_CLR                  (SPM_BASE + 0x094)
+#define SPM_SCP_MAILBOX                (SPM_BASE + 0x098)
+#define SCP_SPM_MAILBOX                (SPM_BASE + 0x09C)
+#define SPM_TWAM_CON                   (SPM_BASE + 0x0A0)
+#define SPM_TWAM_WINDOW_LEN            (SPM_BASE + 0x0A4)
+#define SPM_TWAM_IDLE_SEL              (SPM_BASE + 0x0A8)
+#define SPM_SCP_IRQ                    (SPM_BASE + 0x0AC)
+#define SPM_CPU_WAKEUP_EVENT           (SPM_BASE + 0x0B0)
+#define SPM_IRQ_MASK                   (SPM_BASE + 0x0B4)
+#define SPM_SRC_REQ                    (SPM_BASE + 0x0B8)
+#define SPM_SRC_MASK                   (SPM_BASE + 0x0BC)
+#define SPM_SRC2_MASK                  (SPM_BASE + 0x0C0)
+#define SPM_SRC3_MASK                  (SPM_BASE + 0x0C4)
+#define SPM_SRC4_MASK                  (SPM_BASE + 0x0C8)
+#define SPM_SRC5_MASK                  (SPM_BASE + 0x0CC)
+#define SPM_WAKEUP_EVENT_MASK          (SPM_BASE + 0x0D0)
+#define SPM_WAKEUP_EVENT_EXT_MASK      (SPM_BASE + 0x0D4)
+#define SPM_TWAM_EVENT_CLEAR           (SPM_BASE + 0x0D8)
+#define SCP_CLK_CON                    (SPM_BASE + 0x0DC)
+#define PCM_DEBUG_CON                  (SPM_BASE + 0x0E0)
+#define AHB_BUS_CON                    (SPM_BASE + 0x0E4)
+#define DDR_EN_DBC_CON0                (SPM_BASE + 0x0E8)
+#define DDR_EN_DBC_CON1                (SPM_BASE + 0x0EC)
+#define SPM_RESOURCE_ACK_CON0          (SPM_BASE + 0x0F0)
+#define SPM_RESOURCE_ACK_CON1          (SPM_BASE + 0x0F4)
+#define SPM_RESOURCE_ACK_CON2          (SPM_BASE + 0x0F8)
+#define SPM_RESOURCE_ACK_CON3          (SPM_BASE + 0x0FC)
+#define PCM_REG0_DATA                  (SPM_BASE + 0x100)
+#define PCM_REG2_DATA                  (SPM_BASE + 0x104)
+#define PCM_REG6_DATA                  (SPM_BASE + 0x108)
+#define PCM_REG7_DATA                  (SPM_BASE + 0x10C)
+#define PCM_REG13_DATA                 (SPM_BASE + 0x110)
+#define SRC_REQ_STA_0                  (SPM_BASE + 0x114)
+#define SRC_REQ_STA_1                  (SPM_BASE + 0x118)
+#define SRC_REQ_STA_2                  (SPM_BASE + 0x11C)
+#define PCM_TIMER_OUT                  (SPM_BASE + 0x120)
+#define PCM_WDT_OUT                    (SPM_BASE + 0x124)
+#define SPM_IRQ_STA                    (SPM_BASE + 0x128)
+#define SRC_REQ_STA_4                  (SPM_BASE + 0x12C)
+#define MD32PCM_WAKEUP_STA             (SPM_BASE + 0x130)
+#define MD32PCM_EVENT_STA              (SPM_BASE + 0x134)
+#define SPM_WAKEUP_STA                 (SPM_BASE + 0x138)
+#define SPM_WAKEUP_EXT_STA             (SPM_BASE + 0x13C)
+#define SPM_WAKEUP_MISC                (SPM_BASE + 0x140)
+#define MM_DVFS_HALT                   (SPM_BASE + 0x144)
+#define BUS_PROTECT_RDY                (SPM_BASE + 0x150)
+#define BUS_PROTECT1_RDY               (SPM_BASE + 0x154)
+#define BUS_PROTECT2_RDY               (SPM_BASE + 0x158)
+#define BUS_PROTECT3_RDY               (SPM_BASE + 0x15C)
+#define SUBSYS_IDLE_STA                (SPM_BASE + 0x160)
+#define PCM_STA                        (SPM_BASE + 0x164)
+#define SRC_REQ_STA_3                  (SPM_BASE + 0x168)
+#define PWR_STATUS                     (SPM_BASE + 0x16C)
+#define PWR_STATUS_2ND                 (SPM_BASE + 0x170)
+#define CPU_PWR_STATUS                 (SPM_BASE + 0x174)
+#define OTHER_PWR_STATUS               (SPM_BASE + 0x178)
+#define SPM_VTCXO_EVENT_COUNT_STA      (SPM_BASE + 0x17C)
+#define SPM_INFRA_EVENT_COUNT_STA      (SPM_BASE + 0x180)
+#define SPM_VRF18_EVENT_COUNT_STA      (SPM_BASE + 0x184)
+#define SPM_APSRC_EVENT_COUNT_STA      (SPM_BASE + 0x188)
+#define SPM_DDREN_EVENT_COUNT_STA      (SPM_BASE + 0x18C)
+#define MD32PCM_STA                    (SPM_BASE + 0x190)
+#define MD32PCM_PC                     (SPM_BASE + 0x194)
+#define DVFSRC_EVENT_STA               (SPM_BASE + 0x1A4)
+#define BUS_PROTECT4_RDY               (SPM_BASE + 0x1A8)
+#define BUS_PROTECT5_RDY               (SPM_BASE + 0x1AC)
+#define BUS_PROTECT6_RDY               (SPM_BASE + 0x1B0)
+#define BUS_PROTECT7_RDY               (SPM_BASE + 0x1B4)
+#define BUS_PROTECT8_RDY               (SPM_BASE + 0x1B8)
+#define SPM_TWAM_LAST_STA0             (SPM_BASE + 0x1D0)
+#define SPM_TWAM_LAST_STA1             (SPM_BASE + 0x1D4)
+#define SPM_TWAM_LAST_STA2             (SPM_BASE + 0x1D8)
+#define SPM_TWAM_LAST_STA3             (SPM_BASE + 0x1DC)
+#define SPM_TWAM_CURR_STA0             (SPM_BASE + 0x1E0)
+#define SPM_TWAM_CURR_STA1             (SPM_BASE + 0x1E4)
+#define SPM_TWAM_CURR_STA2             (SPM_BASE + 0x1E8)
+#define SPM_TWAM_CURR_STA3             (SPM_BASE + 0x1EC)
+#define SPM_TWAM_TIMER_OUT             (SPM_BASE + 0x1F0)
+#define SPM_CG_CHECK_STA               (SPM_BASE + 0x1F4)
+#define SPM_DVFS_STA                   (SPM_BASE + 0x1F8)
+#define SPM_DVFS_OPP_STA               (SPM_BASE + 0x1FC)
+#define SPM_MCUSYS_PWR_CON             (SPM_BASE + 0x200)
+#define SPM_CPUTOP_PWR_CON             (SPM_BASE + 0x204)
+#define SPM_CPU0_PWR_CON               (SPM_BASE + 0x208)
+#define SPM_CPU1_PWR_CON               (SPM_BASE + 0x20C)
+#define SPM_CPU2_PWR_CON               (SPM_BASE + 0x210)
+#define SPM_CPU3_PWR_CON               (SPM_BASE + 0x214)
+#define SPM_CPU4_PWR_CON               (SPM_BASE + 0x218)
+#define SPM_CPU5_PWR_CON               (SPM_BASE + 0x21C)
+#define SPM_CPU6_PWR_CON               (SPM_BASE + 0x220)
+#define SPM_CPU7_PWR_CON               (SPM_BASE + 0x224)
+#define ARMPLL_CLK_CON                 (SPM_BASE + 0x22C)
+#define MCUSYS_IDLE_STA                (SPM_BASE + 0x230)
+#define GIC_WAKEUP_STA                 (SPM_BASE + 0x234)
+#define CPU_SPARE_CON                  (SPM_BASE + 0x238)
+#define CPU_SPARE_CON_SET              (SPM_BASE + 0x23C)
+#define CPU_SPARE_CON_CLR              (SPM_BASE + 0x240)
+#define ARMPLL_CLK_SEL                 (SPM_BASE + 0x244)
+#define EXT_INT_WAKEUP_REQ             (SPM_BASE + 0x248)
+#define EXT_INT_WAKEUP_REQ_SET         (SPM_BASE + 0x24C)
+#define EXT_INT_WAKEUP_REQ_CLR         (SPM_BASE + 0x250)
+#define MP0_CPU0_IRQ_MASK              (SPM_BASE + 0x260)
+#define MP0_CPU1_IRQ_MASK              (SPM_BASE + 0x264)
+#define MP0_CPU2_IRQ_MASK              (SPM_BASE + 0x268)
+#define MP0_CPU3_IRQ_MASK              (SPM_BASE + 0x26C)
+#define MP1_CPU0_IRQ_MASK              (SPM_BASE + 0x270)
+#define MP1_CPU1_IRQ_MASK              (SPM_BASE + 0x274)
+#define MP1_CPU2_IRQ_MASK              (SPM_BASE + 0x278)
+#define MP1_CPU3_IRQ_MASK              (SPM_BASE + 0x27C)
+#define MP0_CPU0_WFI_EN                (SPM_BASE + 0x280)
+#define MP0_CPU1_WFI_EN                (SPM_BASE + 0x284)
+#define MP0_CPU2_WFI_EN                (SPM_BASE + 0x288)
+#define MP0_CPU3_WFI_EN                (SPM_BASE + 0x28C)
+#define MP0_CPU4_WFI_EN                (SPM_BASE + 0x290)
+#define MP0_CPU5_WFI_EN                (SPM_BASE + 0x294)
+#define MP0_CPU6_WFI_EN                (SPM_BASE + 0x298)
+#define MP0_CPU7_WFI_EN                (SPM_BASE + 0x29C)
+#define ROOT_CPUTOP_ADDR               (SPM_BASE + 0x2A0)
+#define ROOT_CORE_ADDR                 (SPM_BASE + 0x2A4)
+#define SPM2SW_MAILBOX_0               (SPM_BASE + 0x2D0)
+#define SPM2SW_MAILBOX_1               (SPM_BASE + 0x2D4)
+#define SPM2SW_MAILBOX_2               (SPM_BASE + 0x2D8)
+#define SPM2SW_MAILBOX_3               (SPM_BASE + 0x2DC)
+#define SW2SPM_INT                     (SPM_BASE + 0x2E0)
+#define SW2SPM_INT_SET                 (SPM_BASE + 0x2E4)
+#define SW2SPM_INT_CLR                 (SPM_BASE + 0x2E8)
+#define SW2SPM_MAILBOX_0               (SPM_BASE + 0x2EC)
+#define SW2SPM_MAILBOX_1               (SPM_BASE + 0x2F0)
+#define SW2SPM_MAILBOX_2               (SPM_BASE + 0x2F4)
+#define SW2SPM_MAILBOX_3               (SPM_BASE + 0x2F8)
+#define SW2SPM_CFG                     (SPM_BASE + 0x2FC)
+#define MD1_PWR_CON                    (SPM_BASE + 0x300)
+#define CONN_PWR_CON                   (SPM_BASE + 0x304)
+#define MFG0_PWR_CON                   (SPM_BASE + 0x308)
+#define MFG1_PWR_CON                   (SPM_BASE + 0x30C)
+#define MFG2_PWR_CON                   (SPM_BASE + 0x310)
+#define MFG3_PWR_CON                   (SPM_BASE + 0x314)
+#define MFG4_PWR_CON                   (SPM_BASE + 0x318)
+#define MFG5_PWR_CON                   (SPM_BASE + 0x31C)
+#define MFG6_PWR_CON                   (SPM_BASE + 0x320)
+#define IFR_PWR_CON                    (SPM_BASE + 0x324)
+#define IFR_SUB_PWR_CON                (SPM_BASE + 0x328)
+#define DPY_PWR_CON                    (SPM_BASE + 0x32C)
+#define ISP_PWR_CON                    (SPM_BASE + 0x330)
+#define ISP2_PWR_CON                   (SPM_BASE + 0x334)
+#define IPE_PWR_CON                    (SPM_BASE + 0x338)
+#define VDE_PWR_CON                    (SPM_BASE + 0x33C)
+#define VDE2_PWR_CON                   (SPM_BASE + 0x340)
+#define VEN_PWR_CON                    (SPM_BASE + 0x344)
+#define VEN_CORE1_PWR_CON              (SPM_BASE + 0x348)
+#define MDP_PWR_CON                    (SPM_BASE + 0x34C)
+#define DIS_PWR_CON                    (SPM_BASE + 0x350)
+#define AUDIO_PWR_CON                  (SPM_BASE + 0x354)
+#define ADSP_PWR_CON                   (SPM_BASE + 0x358)
+#define CAM_PWR_CON                    (SPM_BASE + 0x35C)
+#define CAM_RAWA_PWR_CON               (SPM_BASE + 0x360)
+#define CAM_RAWB_PWR_CON               (SPM_BASE + 0x364)
+#define CAM_RAWC_PWR_CON               (SPM_BASE + 0x368)
+#define SYSRAM_CON                     (SPM_BASE + 0x36C)
+#define SYSROM_CON                     (SPM_BASE + 0x370)
+#define SSPM_SRAM_CON                  (SPM_BASE + 0x374)
+#define SCP_SRAM_CON                   (SPM_BASE + 0x378)
+#define DPY_SHU_SRAM_CON               (SPM_BASE + 0x37C)
+#define UFS_SRAM_CON                   (SPM_BASE + 0x380)
+#define DEVAPC_IFR_SRAM_CON            (SPM_BASE + 0x384)
+#define DEVAPC_SUBIFR_SRAM_CON         (SPM_BASE + 0x388)
+#define DEVAPC_ACP_SRAM_CON            (SPM_BASE + 0x38C)
+#define USB_SRAM_CON                   (SPM_BASE + 0x390)
+#define DUMMY_SRAM_CON                 (SPM_BASE + 0x394)
+#define MD_EXT_BUCK_ISO_CON            (SPM_BASE + 0x398)
+#define EXT_BUCK_ISO                   (SPM_BASE + 0x39C)
+#define DXCC_SRAM_CON                  (SPM_BASE + 0x3A0)
+#define MSDC_SRAM_CON                  (SPM_BASE + 0x3A4)
+#define DEBUGTOP_SRAM_CON              (SPM_BASE + 0x3A8)
+#define DP_TX_PWR_CON                  (SPM_BASE + 0x3AC)
+#define DPMAIF_SRAM_CON                (SPM_BASE + 0x3B0)
+#define DPY_SHU2_SRAM_CON              (SPM_BASE + 0x3B4)
+#define DRAMC_MCU2_SRAM_CON            (SPM_BASE + 0x3B8)
+#define DRAMC_MCU_SRAM_CON             (SPM_BASE + 0x3BC)
+#define MCUPM_SRAM_CON                 (SPM_BASE + 0x3C0)
+#define DPY2_PWR_CON                   (SPM_BASE + 0x3C4)
+#define PERI_PWR_CON                   (SPM_BASE + 0x3C8)
+#define SPM_MEM_CK_SEL                 (SPM_BASE + 0x400)
+#define SPM_BUS_PROTECT_MASK_B         (SPM_BASE + 0x404)
+#define SPM_BUS_PROTECT1_MASK_B        (SPM_BASE + 0x408)
+#define SPM_BUS_PROTECT2_MASK_B        (SPM_BASE + 0x40C)
+#define SPM_BUS_PROTECT3_MASK_B        (SPM_BASE + 0x410)
+#define SPM_BUS_PROTECT4_MASK_B        (SPM_BASE + 0x414)
+#define SPM_EMI_BW_MODE                (SPM_BASE + 0x418)
+#define AP2MD_PEER_WAKEUP              (SPM_BASE + 0x41C)
+#define ULPOSC_CON                     (SPM_BASE + 0x420)
+#define SPM2MM_CON                     (SPM_BASE + 0x424)
+#define SPM_BUS_PROTECT5_MASK_B        (SPM_BASE + 0x428)
+#define SPM2MCUPM_CON                  (SPM_BASE + 0x42C)
+#define AP_MDSRC_REQ                   (SPM_BASE + 0x430)
+#define SPM2EMI_ENTER_ULPM             (SPM_BASE + 0x434)
+#define SPM2MD_DVFS_CON                (SPM_BASE + 0x438)
+#define MD2SPM_DVFS_CON                (SPM_BASE + 0x43C)
+#define SPM_BUS_PROTECT6_MASK_B        (SPM_BASE + 0x440)
+#define SPM_BUS_PROTECT7_MASK_B        (SPM_BASE + 0x444)
+#define SPM_BUS_PROTECT8_MASK_B        (SPM_BASE + 0x448)
+#define SPM_PLL_CON                    (SPM_BASE + 0x44C)
+#define CPU_DVFS_REQ                   (SPM_BASE + 0x450)
+#define SPM_DRAM_MCU_SW_CON_0          (SPM_BASE + 0x454)
+#define SPM_DRAM_MCU_SW_CON_1          (SPM_BASE + 0x458)
+#define SPM_DRAM_MCU_SW_CON_2          (SPM_BASE + 0x45C)
+#define SPM_DRAM_MCU_SW_CON_3          (SPM_BASE + 0x460)
+#define SPM_DRAM_MCU_SW_CON_4          (SPM_BASE + 0x464)
+#define SPM_DRAM_MCU_STA_0             (SPM_BASE + 0x468)
+#define SPM_DRAM_MCU_STA_1             (SPM_BASE + 0x46C)
+#define SPM_DRAM_MCU_STA_2             (SPM_BASE + 0x470)
+#define SPM_DRAM_MCU_SW_SEL_0          (SPM_BASE + 0x474)
+#define RELAY_DVFS_LEVEL               (SPM_BASE + 0x478)
+#define DRAMC_DPY_CLK_SW_CON_0         (SPM_BASE + 0x480)
+#define DRAMC_DPY_CLK_SW_CON_1         (SPM_BASE + 0x484)
+#define DRAMC_DPY_CLK_SW_CON_2         (SPM_BASE + 0x488)
+#define DRAMC_DPY_CLK_SW_CON_3         (SPM_BASE + 0x48C)
+#define DRAMC_DPY_CLK_SW_SEL_0         (SPM_BASE + 0x490)
+#define DRAMC_DPY_CLK_SW_SEL_1         (SPM_BASE + 0x494)
+#define DRAMC_DPY_CLK_SW_SEL_2         (SPM_BASE + 0x498)
+#define DRAMC_DPY_CLK_SW_SEL_3         (SPM_BASE + 0x49C)
+#define DRAMC_DPY_CLK_SPM_CON          (SPM_BASE + 0x4A0)
+#define SPM_DVFS_LEVEL                 (SPM_BASE + 0x4A4)
+#define SPM_CIRQ_CON                   (SPM_BASE + 0x4A8)
+#define SPM_DVFS_MISC                  (SPM_BASE + 0x4AC)
+#define SPM_VS1_VS2_RC_CON             (SPM_BASE + 0x4B0)
+#define RG_MODULE_SW_CG_0_MASK_REQ_0   (SPM_BASE + 0x4B4)
+#define RG_MODULE_SW_CG_0_MASK_REQ_1   (SPM_BASE + 0x4B8)
+#define RG_MODULE_SW_CG_0_MASK_REQ_2   (SPM_BASE + 0x4BC)
+#define RG_MODULE_SW_CG_1_MASK_REQ_0   (SPM_BASE + 0x4C0)
+#define RG_MODULE_SW_CG_1_MASK_REQ_1   (SPM_BASE + 0x4C4)
+#define RG_MODULE_SW_CG_1_MASK_REQ_2   (SPM_BASE + 0x4C8)
+#define RG_MODULE_SW_CG_2_MASK_REQ_0   (SPM_BASE + 0x4CC)
+#define RG_MODULE_SW_CG_2_MASK_REQ_1   (SPM_BASE + 0x4D0)
+#define RG_MODULE_SW_CG_2_MASK_REQ_2   (SPM_BASE + 0x4D4)
+#define RG_MODULE_SW_CG_3_MASK_REQ_0   (SPM_BASE + 0x4D8)
+#define RG_MODULE_SW_CG_3_MASK_REQ_1   (SPM_BASE + 0x4DC)
+#define RG_MODULE_SW_CG_3_MASK_REQ_2   (SPM_BASE + 0x4E0)
+#define PWR_STATUS_MASK_REQ_0          (SPM_BASE + 0x4E4)
+#define PWR_STATUS_MASK_REQ_1          (SPM_BASE + 0x4E8)
+#define PWR_STATUS_MASK_REQ_2          (SPM_BASE + 0x4EC)
+#define SPM_CG_CHECK_CON               (SPM_BASE + 0x4F0)
+#define SPM_SRC_RDY_STA                (SPM_BASE + 0x4F4)
+#define SPM_DVS_DFS_LEVEL              (SPM_BASE + 0x4F8)
+#define SPM_FORCE_DVFS                 (SPM_BASE + 0x4FC)
+#define SRCLKEN_RC_CFG                 (SPM_BASE + 0x500)
+#define RC_CENTRAL_CFG1                (SPM_BASE + 0x504)
+#define RC_CENTRAL_CFG2                (SPM_BASE + 0x508)
+#define RC_CMD_ARB_CFG                 (SPM_BASE + 0x50C)
+#define RC_PMIC_RCEN_ADDR              (SPM_BASE + 0x510)
+#define RC_PMIC_RCEN_SET_CLR_ADDR      (SPM_BASE + 0x514)
+#define RC_DCXO_FPM_CFG                (SPM_BASE + 0x518)
+#define RC_CENTRAL_CFG3                (SPM_BASE + 0x51C)
+#define RC_M00_SRCLKEN_CFG             (SPM_BASE + 0x520)
+#define RC_M01_SRCLKEN_CFG             (SPM_BASE + 0x524)
+#define RC_M02_SRCLKEN_CFG             (SPM_BASE + 0x528)
+#define RC_M03_SRCLKEN_CFG             (SPM_BASE + 0x52C)
+#define RC_M04_SRCLKEN_CFG             (SPM_BASE + 0x530)
+#define RC_M05_SRCLKEN_CFG             (SPM_BASE + 0x534)
+#define RC_M06_SRCLKEN_CFG             (SPM_BASE + 0x538)
+#define RC_M07_SRCLKEN_CFG             (SPM_BASE + 0x53C)
+#define RC_M08_SRCLKEN_CFG             (SPM_BASE + 0x540)
+#define RC_M09_SRCLKEN_CFG             (SPM_BASE + 0x544)
+#define RC_M10_SRCLKEN_CFG             (SPM_BASE + 0x548)
+#define RC_M11_SRCLKEN_CFG             (SPM_BASE + 0x54C)
+#define RC_M12_SRCLKEN_CFG             (SPM_BASE + 0x550)
+#define RC_SRCLKEN_SW_CON_CFG          (SPM_BASE + 0x554)
+#define RC_CENTRAL_CFG4                (SPM_BASE + 0x558)
+#define RC_PROTOCOL_CHK_CFG            (SPM_BASE + 0x560)
+#define RC_DEBUG_CFG                   (SPM_BASE + 0x564)
+#define RC_MISC_0                      (SPM_BASE + 0x5B4)
+#define RC_SPM_CTRL                    (SPM_BASE + 0x5B8)
+#define SUBSYS_INTF_CFG                (SPM_BASE + 0x5BC)
+#define PCM_WDT_LATCH_25               (SPM_BASE + 0x5C0)
+#define PCM_WDT_LATCH_26               (SPM_BASE + 0x5C4)
+#define PCM_WDT_LATCH_27               (SPM_BASE + 0x5C8)
+#define PCM_WDT_LATCH_28               (SPM_BASE + 0x5CC)
+#define PCM_WDT_LATCH_29               (SPM_BASE + 0x5D0)
+#define PCM_WDT_LATCH_30               (SPM_BASE + 0x5D4)
+#define PCM_WDT_LATCH_31               (SPM_BASE + 0x5D8)
+#define PCM_WDT_LATCH_32               (SPM_BASE + 0x5DC)
+#define PCM_WDT_LATCH_33               (SPM_BASE + 0x5E0)
+#define PCM_WDT_LATCH_34               (SPM_BASE + 0x5E4)
+#define PCM_WDT_LATCH_35               (SPM_BASE + 0x5EC)
+#define PCM_WDT_LATCH_36               (SPM_BASE + 0x5F0)
+#define PCM_WDT_LATCH_37               (SPM_BASE + 0x5F4)
+#define PCM_WDT_LATCH_38               (SPM_BASE + 0x5F8)
+#define PCM_WDT_LATCH_39               (SPM_BASE + 0x5FC)
+#define SPM_SW_FLAG_0                  (SPM_BASE + 0x600)
+#define SPM_SW_DEBUG_0                 (SPM_BASE + 0x604)
+#define SPM_SW_FLAG_1                  (SPM_BASE + 0x608)
+#define SPM_SW_DEBUG_1                 (SPM_BASE + 0x60C)
+#define SPM_SW_RSV_0                   (SPM_BASE + 0x610)
+#define SPM_SW_RSV_1                   (SPM_BASE + 0x614)
+#define SPM_SW_RSV_2                   (SPM_BASE + 0x618)
+#define SPM_SW_RSV_3                   (SPM_BASE + 0x61C)
+#define SPM_SW_RSV_4                   (SPM_BASE + 0x620)
+#define SPM_SW_RSV_5                   (SPM_BASE + 0x624)
+#define SPM_SW_RSV_6                   (SPM_BASE + 0x628)
+#define SPM_SW_RSV_7                   (SPM_BASE + 0x62C)
+#define SPM_SW_RSV_8                   (SPM_BASE + 0x630)
+#define SPM_BK_WAKE_EVENT              (SPM_BASE + 0x634)
+#define SPM_BK_VTCXO_DUR               (SPM_BASE + 0x638)
+#define SPM_BK_WAKE_MISC               (SPM_BASE + 0x63C)
+#define SPM_BK_PCM_TIMER               (SPM_BASE + 0x640)
+#define SPM_RSV_CON_0                  (SPM_BASE + 0x650)
+#define SPM_RSV_CON_1                  (SPM_BASE + 0x654)
+#define SPM_RSV_STA_0                  (SPM_BASE + 0x658)
+#define SPM_RSV_STA_1                  (SPM_BASE + 0x65C)
+#define SPM_SPARE_CON                  (SPM_BASE + 0x660)
+#define SPM_SPARE_CON_SET              (SPM_BASE + 0x664)
+#define SPM_SPARE_CON_CLR              (SPM_BASE + 0x668)
+#define SPM_CROSS_WAKE_M00_REQ         (SPM_BASE + 0x66C)
+#define SPM_CROSS_WAKE_M01_REQ         (SPM_BASE + 0x670)
+#define SPM_CROSS_WAKE_M02_REQ         (SPM_BASE + 0x674)
+#define SPM_CROSS_WAKE_M03_REQ         (SPM_BASE + 0x678)
+#define SCP_VCORE_LEVEL                (SPM_BASE + 0x67C)
+#define SC_MM_CK_SEL_CON               (SPM_BASE + 0x680)
+#define SPARE_ACK_MASK                 (SPM_BASE + 0x684)
+#define SPM_CROSS_WAKE_M04_REQ         (SPM_BASE + 0x688)
+#define SPM_DV_CON_0                   (SPM_BASE + 0x68C)
+#define SPM_DV_CON_1                   (SPM_BASE + 0x690)
+#define SPM_DV_STA                     (SPM_BASE + 0x694)
+#define CONN_XOWCN_DEBUG_EN            (SPM_BASE + 0x698)
+#define SPM_SEMA_M0                    (SPM_BASE + 0x69C)
+#define SPM_SEMA_M1                    (SPM_BASE + 0x6A0)
+#define SPM_SEMA_M2                    (SPM_BASE + 0x6A4)
+#define SPM_SEMA_M3                    (SPM_BASE + 0x6A8)
+#define SPM_SEMA_M4                    (SPM_BASE + 0x6AC)
+#define SPM_SEMA_M5                    (SPM_BASE + 0x6B0)
+#define SPM_SEMA_M6                    (SPM_BASE + 0x6B4)
+#define SPM_SEMA_M7                    (SPM_BASE + 0x6B8)
+#define SPM2ADSP_MAILBOX               (SPM_BASE + 0x6BC)
+#define ADSP2SPM_MAILBOX               (SPM_BASE + 0x6C0)
+#define SPM_ADSP_IRQ                   (SPM_BASE + 0x6C4)
+#define SPM_MD32_IRQ                   (SPM_BASE + 0x6C8)
+#define SPM2PMCU_MAILBOX_0             (SPM_BASE + 0x6CC)
+#define SPM2PMCU_MAILBOX_1             (SPM_BASE + 0x6D0)
+#define SPM2PMCU_MAILBOX_2             (SPM_BASE + 0x6D4)
+#define SPM2PMCU_MAILBOX_3             (SPM_BASE + 0x6D8)
+#define PMCU2SPM_MAILBOX_0             (SPM_BASE + 0x6DC)
+#define PMCU2SPM_MAILBOX_1             (SPM_BASE + 0x6E0)
+#define PMCU2SPM_MAILBOX_2             (SPM_BASE + 0x6E4)
+#define PMCU2SPM_MAILBOX_3             (SPM_BASE + 0x6E8)
+#define UFS_PSRI_SW                    (SPM_BASE + 0x6EC)
+#define UFS_PSRI_SW_SET                (SPM_BASE + 0x6F0)
+#define UFS_PSRI_SW_CLR                (SPM_BASE + 0x6F4)
+#define SPM_AP_SEMA                    (SPM_BASE + 0x6F8)
+#define SPM_SPM_SEMA                   (SPM_BASE + 0x6FC)
+#define SPM_DVFS_CON                   (SPM_BASE + 0x700)
+#define SPM_DVFS_CON_STA               (SPM_BASE + 0x704)
+#define SPM_PMIC_SPMI_CON              (SPM_BASE + 0x708)
+#define SPM_DVFS_CMD0                  (SPM_BASE + 0x710)
+#define SPM_DVFS_CMD1                  (SPM_BASE + 0x714)
+#define SPM_DVFS_CMD2                  (SPM_BASE + 0x718)
+#define SPM_DVFS_CMD3                  (SPM_BASE + 0x71C)
+#define SPM_DVFS_CMD4                  (SPM_BASE + 0x720)
+#define SPM_DVFS_CMD5                  (SPM_BASE + 0x724)
+#define SPM_DVFS_CMD6                  (SPM_BASE + 0x728)
+#define SPM_DVFS_CMD7                  (SPM_BASE + 0x72C)
+#define SPM_DVFS_CMD8                  (SPM_BASE + 0x730)
+#define SPM_DVFS_CMD9                  (SPM_BASE + 0x734)
+#define SPM_DVFS_CMD10                 (SPM_BASE + 0x738)
+#define SPM_DVFS_CMD11                 (SPM_BASE + 0x73C)
+#define SPM_DVFS_CMD12                 (SPM_BASE + 0x740)
+#define SPM_DVFS_CMD13                 (SPM_BASE + 0x744)
+#define SPM_DVFS_CMD14                 (SPM_BASE + 0x748)
+#define SPM_DVFS_CMD15                 (SPM_BASE + 0x74C)
+#define SPM_DVFS_CMD16                 (SPM_BASE + 0x750)
+#define SPM_DVFS_CMD17                 (SPM_BASE + 0x754)
+#define SPM_DVFS_CMD18                 (SPM_BASE + 0x758)
+#define SPM_DVFS_CMD19                 (SPM_BASE + 0x75C)
+#define SPM_DVFS_CMD20                 (SPM_BASE + 0x760)
+#define SPM_DVFS_CMD21                 (SPM_BASE + 0x764)
+#define SPM_DVFS_CMD22                 (SPM_BASE + 0x768)
+#define SPM_DVFS_CMD23                 (SPM_BASE + 0x76C)
+#define SYS_TIMER_VALUE_L              (SPM_BASE + 0x770)
+#define SYS_TIMER_VALUE_H              (SPM_BASE + 0x774)
+#define SYS_TIMER_START_L              (SPM_BASE + 0x778)
+#define SYS_TIMER_START_H              (SPM_BASE + 0x77C)
+#define SYS_TIMER_LATCH_L_00           (SPM_BASE + 0x780)
+#define SYS_TIMER_LATCH_H_00           (SPM_BASE + 0x784)
+#define SYS_TIMER_LATCH_L_01           (SPM_BASE + 0x788)
+#define SYS_TIMER_LATCH_H_01           (SPM_BASE + 0x78C)
+#define SYS_TIMER_LATCH_L_02           (SPM_BASE + 0x790)
+#define SYS_TIMER_LATCH_H_02           (SPM_BASE + 0x794)
+#define SYS_TIMER_LATCH_L_03           (SPM_BASE + 0x798)
+#define SYS_TIMER_LATCH_H_03           (SPM_BASE + 0x79C)
+#define SYS_TIMER_LATCH_L_04           (SPM_BASE + 0x7A0)
+#define SYS_TIMER_LATCH_H_04           (SPM_BASE + 0x7A4)
+#define SYS_TIMER_LATCH_L_05           (SPM_BASE + 0x7A8)
+#define SYS_TIMER_LATCH_H_05           (SPM_BASE + 0x7AC)
+#define SYS_TIMER_LATCH_L_06           (SPM_BASE + 0x7B0)
+#define SYS_TIMER_LATCH_H_06           (SPM_BASE + 0x7B4)
+#define SYS_TIMER_LATCH_L_07           (SPM_BASE + 0x7B8)
+#define SYS_TIMER_LATCH_H_07           (SPM_BASE + 0x7BC)
+#define SYS_TIMER_LATCH_L_08           (SPM_BASE + 0x7C0)
+#define SYS_TIMER_LATCH_H_08           (SPM_BASE + 0x7C4)
+#define SYS_TIMER_LATCH_L_09           (SPM_BASE + 0x7C8)
+#define SYS_TIMER_LATCH_H_09           (SPM_BASE + 0x7CC)
+#define SYS_TIMER_LATCH_L_10           (SPM_BASE + 0x7D0)
+#define SYS_TIMER_LATCH_H_10           (SPM_BASE + 0x7D4)
+#define SYS_TIMER_LATCH_L_11           (SPM_BASE + 0x7D8)
+#define SYS_TIMER_LATCH_H_11           (SPM_BASE + 0x7DC)
+#define SYS_TIMER_LATCH_L_12           (SPM_BASE + 0x7E0)
+#define SYS_TIMER_LATCH_H_12           (SPM_BASE + 0x7E4)
+#define SYS_TIMER_LATCH_L_13           (SPM_BASE + 0x7E8)
+#define SYS_TIMER_LATCH_H_13           (SPM_BASE + 0x7EC)
+#define SYS_TIMER_LATCH_L_14           (SPM_BASE + 0x7F0)
+#define SYS_TIMER_LATCH_H_14           (SPM_BASE + 0x7F4)
+#define SYS_TIMER_LATCH_L_15           (SPM_BASE + 0x7F8)
+#define SYS_TIMER_LATCH_H_15           (SPM_BASE + 0x7FC)
+#define PCM_WDT_LATCH_0                (SPM_BASE + 0x800)
+#define PCM_WDT_LATCH_1                (SPM_BASE + 0x804)
+#define PCM_WDT_LATCH_2                (SPM_BASE + 0x808)
+#define PCM_WDT_LATCH_3                (SPM_BASE + 0x80C)
+#define PCM_WDT_LATCH_4                (SPM_BASE + 0x810)
+#define PCM_WDT_LATCH_5                (SPM_BASE + 0x814)
+#define PCM_WDT_LATCH_6                (SPM_BASE + 0x818)
+#define PCM_WDT_LATCH_7                (SPM_BASE + 0x81C)
+#define PCM_WDT_LATCH_8                (SPM_BASE + 0x820)
+#define PCM_WDT_LATCH_9                (SPM_BASE + 0x824)
+#define PCM_WDT_LATCH_10               (SPM_BASE + 0x828)
+#define PCM_WDT_LATCH_11               (SPM_BASE + 0x82C)
+#define PCM_WDT_LATCH_12               (SPM_BASE + 0x830)
+#define PCM_WDT_LATCH_13               (SPM_BASE + 0x834)
+#define PCM_WDT_LATCH_14               (SPM_BASE + 0x838)
+#define PCM_WDT_LATCH_15               (SPM_BASE + 0x83C)
+#define PCM_WDT_LATCH_16               (SPM_BASE + 0x840)
+#define PCM_WDT_LATCH_17               (SPM_BASE + 0x844)
+#define PCM_WDT_LATCH_18               (SPM_BASE + 0x848)
+#define PCM_WDT_LATCH_SPARE_0          (SPM_BASE + 0x84C)
+#define PCM_WDT_LATCH_SPARE_1          (SPM_BASE + 0x850)
+#define PCM_WDT_LATCH_SPARE_2          (SPM_BASE + 0x854)
+#define PCM_WDT_LATCH_CONN_0           (SPM_BASE + 0x870)
+#define PCM_WDT_LATCH_CONN_1           (SPM_BASE + 0x874)
+#define PCM_WDT_LATCH_CONN_2           (SPM_BASE + 0x878)
+#define DRAMC_GATING_ERR_LATCH_CH0_0   (SPM_BASE + 0x8A0)
+#define DRAMC_GATING_ERR_LATCH_CH0_1   (SPM_BASE + 0x8A4)
+#define DRAMC_GATING_ERR_LATCH_CH0_2   (SPM_BASE + 0x8A8)
+#define DRAMC_GATING_ERR_LATCH_CH0_3   (SPM_BASE + 0x8AC)
+#define DRAMC_GATING_ERR_LATCH_CH0_4   (SPM_BASE + 0x8B0)
+#define DRAMC_GATING_ERR_LATCH_CH0_5   (SPM_BASE + 0x8B4)
+#define DRAMC_GATING_ERR_LATCH_CH0_6   (SPM_BASE + 0x8B8)
+#define DRAMC_GATING_ERR_LATCH_SPARE_0 (SPM_BASE + 0x8F4)
+#define SPM_ACK_CHK_CON_0              (SPM_BASE + 0x900)
+#define SPM_ACK_CHK_PC_0               (SPM_BASE + 0x904)
+#define SPM_ACK_CHK_SEL_0              (SPM_BASE + 0x908)
+#define SPM_ACK_CHK_TIMER_0            (SPM_BASE + 0x90C)
+#define SPM_ACK_CHK_STA_0              (SPM_BASE + 0x910)
+#define SPM_ACK_CHK_SWINT_0            (SPM_BASE + 0x914)
+#define SPM_ACK_CHK_CON_1              (SPM_BASE + 0x920)
+#define SPM_ACK_CHK_PC_1               (SPM_BASE + 0x924)
+#define SPM_ACK_CHK_SEL_1              (SPM_BASE + 0x928)
+#define SPM_ACK_CHK_TIMER_1            (SPM_BASE + 0x92C)
+#define SPM_ACK_CHK_STA_1              (SPM_BASE + 0x930)
+#define SPM_ACK_CHK_SWINT_1            (SPM_BASE + 0x934)
+#define SPM_ACK_CHK_CON_2              (SPM_BASE + 0x940)
+#define SPM_ACK_CHK_PC_2               (SPM_BASE + 0x944)
+#define SPM_ACK_CHK_SEL_2              (SPM_BASE + 0x948)
+#define SPM_ACK_CHK_TIMER_2            (SPM_BASE + 0x94C)
+#define SPM_ACK_CHK_STA_2              (SPM_BASE + 0x950)
+#define SPM_ACK_CHK_SWINT_2            (SPM_BASE + 0x954)
+#define SPM_ACK_CHK_CON_3              (SPM_BASE + 0x960)
+#define SPM_ACK_CHK_PC_3               (SPM_BASE + 0x964)
+#define SPM_ACK_CHK_SEL_3              (SPM_BASE + 0x968)
+#define SPM_ACK_CHK_TIMER_3            (SPM_BASE + 0x96C)
+#define SPM_ACK_CHK_STA_3              (SPM_BASE + 0x970)
+#define SPM_ACK_CHK_SWINT_3            (SPM_BASE + 0x974)
+#define SPM_COUNTER_0                  (SPM_BASE + 0x978)
+#define SPM_COUNTER_1                  (SPM_BASE + 0x97C)
+#define SPM_COUNTER_2                  (SPM_BASE + 0x980)
+#define SYS_TIMER_CON                  (SPM_BASE + 0x98C)
+#define RC_FSM_STA_0                   (SPM_BASE + 0xE00)
+#define RC_CMD_STA_0                   (SPM_BASE + 0xE04)
+#define RC_CMD_STA_1                   (SPM_BASE + 0xE08)
+#define RC_SPI_STA_0                   (SPM_BASE + 0xE0C)
+#define RC_PI_PO_STA_0                 (SPM_BASE + 0xE10)
+#define RC_M00_REQ_STA_0               (SPM_BASE + 0xE14)
+#define RC_M01_REQ_STA_0               (SPM_BASE + 0xE1C)
+#define RC_M02_REQ_STA_0               (SPM_BASE + 0xE20)
+#define RC_M03_REQ_STA_0               (SPM_BASE + 0xE24)
+#define RC_M04_REQ_STA_0               (SPM_BASE + 0xE28)
+#define RC_M05_REQ_STA_0               (SPM_BASE + 0xE2C)
+#define RC_M06_REQ_STA_0               (SPM_BASE + 0xE30)
+#define RC_M07_REQ_STA_0               (SPM_BASE + 0xE34)
+#define RC_M08_REQ_STA_0               (SPM_BASE + 0xE38)
+#define RC_M09_REQ_STA_0               (SPM_BASE + 0xE3C)
+#define RC_M10_REQ_STA_0               (SPM_BASE + 0xE40)
+#define RC_M11_REQ_STA_0               (SPM_BASE + 0xE44)
+#define RC_M12_REQ_STA_0               (SPM_BASE + 0xE48)
+#define RC_DEBUG_STA_0                 (SPM_BASE + 0xE4C)
+#define RC_DEBUG_TRACE_0_LSB           (SPM_BASE + 0xE50)
+#define RC_DEBUG_TRACE_0_MSB           (SPM_BASE + 0xE54)
+#define RC_DEBUG_TRACE_1_LSB           (SPM_BASE + 0xE5C)
+#define RC_DEBUG_TRACE_1_MSB           (SPM_BASE + 0xE60)
+#define RC_DEBUG_TRACE_2_LSB           (SPM_BASE + 0xE64)
+#define RC_DEBUG_TRACE_2_MSB           (SPM_BASE + 0xE6C)
+#define RC_DEBUG_TRACE_3_LSB           (SPM_BASE + 0xE70)
+#define RC_DEBUG_TRACE_3_MSB           (SPM_BASE + 0xE74)
+#define RC_DEBUG_TRACE_4_LSB           (SPM_BASE + 0xE78)
+#define RC_DEBUG_TRACE_4_MSB           (SPM_BASE + 0xE7C)
+#define RC_DEBUG_TRACE_5_LSB           (SPM_BASE + 0xE80)
+#define RC_DEBUG_TRACE_5_MSB           (SPM_BASE + 0xE84)
+#define RC_DEBUG_TRACE_6_LSB           (SPM_BASE + 0xE88)
+#define RC_DEBUG_TRACE_6_MSB           (SPM_BASE + 0xE8C)
+#define RC_DEBUG_TRACE_7_LSB           (SPM_BASE + 0xE90)
+#define RC_DEBUG_TRACE_7_MSB           (SPM_BASE + 0xE94)
+#define RC_SYS_TIMER_LATCH_0_LSB       (SPM_BASE + 0xE98)
+#define RC_SYS_TIMER_LATCH_0_MSB       (SPM_BASE + 0xE9C)
+#define RC_SYS_TIMER_LATCH_1_LSB       (SPM_BASE + 0xEA0)
+#define RC_SYS_TIMER_LATCH_1_MSB       (SPM_BASE + 0xEA4)
+#define RC_SYS_TIMER_LATCH_2_LSB       (SPM_BASE + 0xEA8)
+#define RC_SYS_TIMER_LATCH_2_MSB       (SPM_BASE + 0xEAC)
+#define RC_SYS_TIMER_LATCH_3_LSB       (SPM_BASE + 0xEB0)
+#define RC_SYS_TIMER_LATCH_3_MSB       (SPM_BASE + 0xEB4)
+#define RC_SYS_TIMER_LATCH_4_LSB       (SPM_BASE + 0xEB8)
+#define RC_SYS_TIMER_LATCH_4_MSB       (SPM_BASE + 0xEBC)
+#define RC_SYS_TIMER_LATCH_5_LSB       (SPM_BASE + 0xEC0)
+#define RC_SYS_TIMER_LATCH_5_MSB       (SPM_BASE + 0xEC4)
+#define RC_SYS_TIMER_LATCH_6_LSB       (SPM_BASE + 0xEC8)
+#define RC_SYS_TIMER_LATCH_6_MSB       (SPM_BASE + 0xECC)
+#define RC_SYS_TIMER_LATCH_7_LSB       (SPM_BASE + 0xED0)
+#define RC_SYS_TIMER_LATCH_7_MSB       (SPM_BASE + 0xED4)
+#define PCM_WDT_LATCH_19               (SPM_BASE + 0xED8)
+#define PCM_WDT_LATCH_20               (SPM_BASE + 0xEDC)
+#define PCM_WDT_LATCH_21               (SPM_BASE + 0xEE0)
+#define PCM_WDT_LATCH_22               (SPM_BASE + 0xEE4)
+#define PCM_WDT_LATCH_23               (SPM_BASE + 0xEE8)
+#define PCM_WDT_LATCH_24               (SPM_BASE + 0xEEC)
+#define PMSR_LAST_DAT                  (SPM_BASE + 0xF00)
+#define PMSR_LAST_CNT                  (SPM_BASE + 0xF04)
+#define PMSR_LAST_ACK                  (SPM_BASE + 0xF08)
+#define SPM_PMSR_SEL_CON0              (SPM_BASE + 0xF10)
+#define SPM_PMSR_SEL_CON1              (SPM_BASE + 0xF14)
+#define SPM_PMSR_SEL_CON2              (SPM_BASE + 0xF18)
+#define SPM_PMSR_SEL_CON3              (SPM_BASE + 0xF1C)
+#define SPM_PMSR_SEL_CON4              (SPM_BASE + 0xF20)
+#define SPM_PMSR_SEL_CON5              (SPM_BASE + 0xF24)
+#define SPM_PMSR_SEL_CON6              (SPM_BASE + 0xF28)
+#define SPM_PMSR_SEL_CON7              (SPM_BASE + 0xF2C)
+#define SPM_PMSR_SEL_CON8              (SPM_BASE + 0xF30)
+#define SPM_PMSR_SEL_CON9              (SPM_BASE + 0xF34)
+#define SPM_PMSR_SEL_CON10             (SPM_BASE + 0xF3C)
+#define SPM_PMSR_SEL_CON11             (SPM_BASE + 0xF40)
+#define SPM_PMSR_TIEMR_STA0            (SPM_BASE + 0xFB8)
+#define SPM_PMSR_TIEMR_STA1            (SPM_BASE + 0xFBC)
+#define SPM_PMSR_TIEMR_STA2            (SPM_BASE + 0xFC0)
+#define SPM_PMSR_GENERAL_CON0          (SPM_BASE + 0xFC4)
+#define SPM_PMSR_GENERAL_CON1          (SPM_BASE + 0xFC8)
+#define SPM_PMSR_GENERAL_CON2          (SPM_BASE + 0xFCC)
+#define SPM_PMSR_GENERAL_CON3          (SPM_BASE + 0xFD0)
+#define SPM_PMSR_GENERAL_CON4          (SPM_BASE + 0xFD4)
+#define SPM_PMSR_GENERAL_CON5          (SPM_BASE + 0xFD8)
+#define SPM_PMSR_SW_RESET              (SPM_BASE + 0xFDC)
+#define SPM_PMSR_MON_CON0              (SPM_BASE + 0xFE0)
+#define SPM_PMSR_MON_CON1              (SPM_BASE + 0xFE4)
+#define SPM_PMSR_MON_CON2              (SPM_BASE + 0xFE8)
+#define SPM_PMSR_LEN_CON0              (SPM_BASE + 0xFEC)
+#define SPM_PMSR_LEN_CON1              (SPM_BASE + 0xFF0)
+#define SPM_PMSR_LEN_CON2              (SPM_BASE + 0xFF4)
+
+/* POWERON_CONFIG_EN (0x10006000+0x000) */
+#define BCLK_CG_EN_LSB                      (1U << 0)       /* 1b */
+#define PROJECT_CODE_LSB                    (1U << 16)      /* 16b */
+/* SPM_POWER_ON_VAL0 (0x10006000+0x004) */
+#define POWER_ON_VAL0_LSB                   (1U << 0)       /* 32b */
+/* SPM_POWER_ON_VAL1 (0x10006000+0x008) */
+#define POWER_ON_VAL1_LSB                   (1U << 0)       /* 32b */
+/* SPM_CLK_CON (0x10006000+0x00C) */
+#define REG_SRCCLKEN0_CTL_LSB               (1U << 0)       /* 2b */
+#define REG_SRCCLKEN1_CTL_LSB               (1U << 2)       /* 2b */
+#define SYS_SETTLE_SEL_LSB                  (1U << 4)       /* 1b */
+#define REG_SPM_LOCK_INFRA_DCM_LSB          (1U << 5)       /* 1b */
+#define REG_SRCCLKEN_MASK_LSB               (1U << 6)       /* 3b */
+#define REG_MD1_C32RM_EN_LSB                (1U << 9)       /* 1b */
+#define REG_MD2_C32RM_EN_LSB                (1U << 10)      /* 1b */
+#define REG_CLKSQ0_SEL_CTRL_LSB             (1U << 11)      /* 1b */
+#define REG_CLKSQ1_SEL_CTRL_LSB             (1U << 12)      /* 1b */
+#define REG_SRCCLKEN0_EN_LSB                (1U << 13)      /* 1b */
+#define REG_SRCCLKEN1_EN_LSB                (1U << 14)      /* 1b */
+#define SCP_DCM_EN_LSB                      (1U << 15)      /* 1b */
+#define REG_SYSCLK0_SRC_MASK_B_LSB          (1U << 16)      /* 8b */
+#define REG_SYSCLK1_SRC_MASK_B_LSB          (1U << 24)      /* 8b */
+/* SPM_CLK_SETTLE (0x10006000+0x010) */
+#define SYSCLK_SETTLE_LSB                   (1U << 0)       /* 28b */
+/* SPM_AP_STANDBY_CON (0x10006000+0x014) */
+#define REG_WFI_OP_LSB                      (1U << 0)       /* 1b */
+#define REG_WFI_TYPE_LSB                    (1U << 1)       /* 1b */
+#define REG_MP0_CPUTOP_IDLE_MASK_LSB        (1U << 2)       /* 1b */
+#define REG_MP1_CPUTOP_IDLE_MASK_LSB        (1U << 3)       /* 1b */
+#define REG_MCUSYS_IDLE_MASK_LSB            (1U << 4)       /* 1b */
+#define REG_MD_APSRC_1_SEL_LSB              (1U << 25)      /* 1b */
+#define REG_MD_APSRC_0_SEL_LSB              (1U << 26)      /* 1b */
+#define REG_CONN_APSRC_SEL_LSB              (1U << 29)      /* 1b */
+/* PCM_CON0 (0x10006000+0x018) */
+#define PCM_CK_EN_LSB                       (1U << 2)       /* 1b */
+#define RG_EN_IM_SLEEP_DVS_LSB              (1U << 3)       /* 1b */
+#define PCM_CK_FROM_CKSYS_LSB               (1U << 4)       /* 1b */
+#define PCM_SW_RESET_LSB                    (1U << 15)      /* 1b */
+#define PCM_CON0_PROJECT_CODE_LSB           (1U << 16)      /* 16b */
+/* PCM_CON1 (0x10006000+0x01C) */
+#define RG_IM_SLAVE_LSB                     (1U << 0)       /* 1b */
+#define RG_IM_SLEEP_LSB                     (1U << 1)       /* 1b */
+#define REG_SPM_SRAM_CTRL_MUX_LSB           (1U << 2)       /* 1b */
+#define RG_AHBMIF_APBEN_LSB                 (1U << 3)       /* 1b */
+#define RG_IM_PDN_LSB                       (1U << 4)       /* 1b */
+#define RG_PCM_TIMER_EN_LSB                 (1U << 5)       /* 1b */
+#define SPM_EVENT_COUNTER_CLR_LSB           (1U << 6)       /* 1b */
+#define RG_DIS_MIF_PROT_LSB                 (1U << 7)       /* 1b */
+#define RG_PCM_WDT_EN_LSB                   (1U << 8)       /* 1b */
+#define RG_PCM_WDT_WAKE_LSB                 (1U << 9)       /* 1b */
+#define REG_SPM_SRAM_SLEEP_B_LSB            (1U << 10)      /* 1b */
+#define REG_SPM_SRAM_ISOINT_B_LSB           (1U << 11)      /* 1b */
+#define REG_EVENT_LOCK_EN_LSB               (1U << 12)      /* 1b */
+#define REG_SRCCLKEN_FAST_RESP_LSB          (1U << 13)      /* 1b */
+#define REG_MD32_APB_INTERNAL_EN_LSB        (1U << 14)      /* 1b */
+#define RG_PCM_IRQ_MSK_LSB                  (1U << 15)      /* 1b */
+#define PCM_CON1_PROJECT_CODE_LSB           (1U << 16)      /* 16b */
+/* SPM_POWER_ON_VAL2 (0x10006000+0x020) */
+#define POWER_ON_VAL2_LSB                   (1U << 0)       /* 32b */
+/* SPM_POWER_ON_VAL3 (0x10006000+0x024) */
+#define POWER_ON_VAL3_LSB                   (1U << 0)       /* 32b */
+/* PCM_REG_DATA_INI (0x10006000+0x028) */
+#define PCM_REG_DATA_INI_LSB                (1U << 0)       /* 32b */
+/* PCM_PWR_IO_EN (0x10006000+0x02C) */
+#define PCM_PWR_IO_EN_LSB                   (1U << 0)       /* 8b */
+#define RG_RF_SYNC_EN_LSB                   (1U << 16)      /* 8b */
+/* PCM_TIMER_VAL (0x10006000+0x030) */
+#define REG_PCM_TIMER_VAL_LSB               (1U << 0)       /* 32b */
+/* PCM_WDT_VAL (0x10006000+0x034) */
+#define RG_PCM_WDT_VAL_LSB                  (1U << 0)       /* 32b */
+/* SPM_SRC6_MASK (0x10006000+0x038) */
+#define REG_DPMAIF_SRCCLKENA_MASK_B_LSB     (1U << 0)       /* 1b */
+#define REG_DPMAIF_INFRA_REQ_MASK_B_LSB     (1U << 1)       /* 1b */
+#define REG_DPMAIF_APSRC_REQ_MASK_B_LSB     (1U << 2)       /* 1b */
+#define REG_DPMAIF_VRF18_REQ_MASK_B_LSB     (1U << 3)       /* 1b */
+#define REG_DPMAIF_DDR_EN_MASK_B_LSB        (1U << 4)       /* 1b */
+/* SPM_SW_RST_CON (0x10006000+0x040) */
+#define SPM_SW_RST_CON_LSB                  (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_PROJECT_CODE_LSB     (1U << 16)      /* 16b */
+/* SPM_SW_RST_CON_SET (0x10006000+0x044) */
+#define SPM_SW_RST_CON_SET_LSB              (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_SET_PROJECT_CODE_LSB (1U << 16)      /* 16b */
+/* SPM_SW_RST_CON_CLR (0x10006000+0x048) */
+#define SPM_SW_RST_CON_CLR_LSB              (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_CLR_PROJECT_CODE_LSB (1U << 16)      /* 16b */
+/* VS1_PSR_MASK_B (0x10006000+0x04C) */
+#define VS1_OPP0_PSR_MASK_B_LSB             (1U << 0)       /* 8b */
+#define VS1_OPP1_PSR_MASK_B_LSB             (1U << 8)       /* 8b */
+/* VS2_PSR_MASK_B (0x10006000+0x050) */
+#define VS2_OPP0_PSR_MASK_B_LSB             (1U << 0)       /* 8b */
+#define VS2_OPP1_PSR_MASK_B_LSB             (1U << 8)       /* 8b */
+#define VS2_OPP2_PSR_MASK_B_LSB             (1U << 16)      /* 8b */
+/* MD32_CLK_CON (0x10006000+0x084) */
+#define REG_MD32_26M_CK_SEL_LSB             (1U << 0)       /* 1b */
+#define REG_MD32_DCM_EN_LSB                 (1U << 1)       /* 1b */
+/* SPM_SRAM_RSV_CON (0x10006000+0x088) */
+#define SPM_SRAM_SLEEP_B_ECO_EN_LSB         (1U << 0)       /* 1b */
+/* SPM_SWINT (0x10006000+0x08C) */
+#define SPM_SWINT_LSB                       (1U << 0)       /* 32b */
+/* SPM_SWINT_SET (0x10006000+0x090) */
+#define SPM_SWINT_SET_LSB                   (1U << 0)       /* 32b */
+/* SPM_SWINT_CLR (0x10006000+0x094) */
+#define SPM_SWINT_CLR_LSB                   (1U << 0)       /* 32b */
+/* SPM_SCP_MAILBOX (0x10006000+0x098) */
+#define SPM_SCP_MAILBOX_LSB                 (1U << 0)       /* 32b */
+/* SCP_SPM_MAILBOX (0x10006000+0x09C) */
+#define SCP_SPM_MAILBOX_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_CON (0x10006000+0x0A0) */
+#define REG_TWAM_ENABLE_LSB                 (1U << 0)       /* 1b */
+#define REG_TWAM_SPEED_MODE_EN_LSB          (1U << 1)       /* 1b */
+#define REG_TWAM_SW_RST_LSB                 (1U << 2)       /* 1b */
+#define REG_TWAM_IRQ_MASK_LSB               (1U << 3)       /* 1b */
+#define REG_TWAM_MON_TYPE_0_LSB             (1U << 4)       /* 2b */
+#define REG_TWAM_MON_TYPE_1_LSB             (1U << 6)       /* 2b */
+#define REG_TWAM_MON_TYPE_2_LSB             (1U << 8)       /* 2b */
+#define REG_TWAM_MON_TYPE_3_LSB             (1U << 10)      /* 2b */
+/* SPM_TWAM_WINDOW_LEN (0x10006000+0x0A4) */
+#define REG_TWAM_WINDOW_LEN_LSB             (1U << 0)       /* 32b */
+/* SPM_TWAM_IDLE_SEL (0x10006000+0x0A8) */
+#define REG_TWAM_SIG_SEL_0_LSB              (1U << 0)       /* 7b */
+#define REG_TWAM_SIG_SEL_1_LSB              (1U << 8)       /* 7b */
+#define REG_TWAM_SIG_SEL_2_LSB              (1U << 16)      /* 7b */
+#define REG_TWAM_SIG_SEL_3_LSB              (1U << 24)      /* 7b */
+/* SPM_SCP_IRQ (0x10006000+0x0AC) */
+#define SC_SPM2SCP_WAKEUP_LSB               (1U << 0)       /* 1b */
+#define SC_SCP2SPM_WAKEUP_LSB               (1U << 4)       /* 1b */
+/* SPM_CPU_WAKEUP_EVENT (0x10006000+0x0B0) */
+#define REG_CPU_WAKEUP_LSB                  (1U << 0)       /* 1b */
+/* SPM_IRQ_MASK (0x10006000+0x0B4) */
+#define REG_SPM_IRQ_MASK_LSB                (1U << 0)       /* 32b */
+/* SPM_SRC_REQ (0x10006000+0x0B8) */
+#define REG_SPM_APSRC_REQ_LSB               (1U << 0)       /* 1b */
+#define REG_SPM_F26M_REQ_LSB                (1U << 1)       /* 1b */
+#define REG_SPM_INFRA_REQ_LSB               (1U << 3)       /* 1b */
+#define REG_SPM_VRF18_REQ_LSB               (1U << 4)       /* 1b */
+#define REG_SPM_DDR_EN_REQ_LSB              (1U << 7)       /* 1b */
+#define REG_SPM_DVFS_REQ_LSB                (1U << 8)       /* 1b */
+#define REG_SPM_SW_MAILBOX_REQ_LSB          (1U << 9)       /* 1b */
+#define REG_SPM_SSPM_MAILBOX_REQ_LSB        (1U << 10)      /* 1b */
+#define REG_SPM_ADSP_MAILBOX_REQ_LSB        (1U << 11)      /* 1b */
+#define REG_SPM_SCP_MAILBOX_REQ_LSB         (1U << 12)      /* 1b */
+/* SPM_SRC_MASK (0x10006000+0x0BC) */
+#define REG_MD_SRCCLKENA_0_MASK_B_LSB       (1U << 0)       /* 1b */
+#define REG_MD_SRCCLKENA2INFRA_REQ_0_MASK_B_LSB (1U << 1)   /* 1b */
+#define REG_MD_APSRC2INFRA_REQ_0_MASK_B_LSB (1U << 2)       /* 1b */
+#define REG_MD_APSRC_REQ_0_MASK_B_LSB       (1U << 3)       /* 1b */
+#define REG_MD_VRF18_REQ_0_MASK_B_LSB       (1U << 4)       /* 1b */
+#define REG_MD_DDR_EN_0_MASK_B_LSB          (1U << 5)       /* 1b */
+#define REG_MD_SRCCLKENA_1_MASK_B_LSB       (1U << 6)       /* 1b */
+#define REG_MD_SRCCLKENA2INFRA_REQ_1_MASK_B_LSB (1U << 7)   /* 1b */
+#define REG_MD_APSRC2INFRA_REQ_1_MASK_B_LSB (1U << 8)       /* 1b */
+#define REG_MD_APSRC_REQ_1_MASK_B_LSB       (1U << 9)       /* 1b */
+#define REG_MD_VRF18_REQ_1_MASK_B_LSB       (1U << 10)      /* 1b */
+#define REG_MD_DDR_EN_1_MASK_B_LSB          (1U << 11)      /* 1b */
+#define REG_CONN_SRCCLKENA_MASK_B_LSB       (1U << 12)      /* 1b */
+#define REG_CONN_SRCCLKENB_MASK_B_LSB       (1U << 13)      /* 1b */
+#define REG_CONN_INFRA_REQ_MASK_B_LSB       (1U << 14)      /* 1b */
+#define REG_CONN_APSRC_REQ_MASK_B_LSB       (1U << 15)      /* 1b */
+#define REG_CONN_VRF18_REQ_MASK_B_LSB       (1U << 16)      /* 1b */
+#define REG_CONN_DDR_EN_MASK_B_LSB          (1U << 17)      /* 1b */
+#define REG_CONN_VFE28_MASK_B_LSB           (1U << 18)      /* 1b */
+#define REG_SRCCLKENI0_SRCCLKENA_MASK_B_LSB (1U << 19)      /* 1b */
+#define REG_SRCCLKENI0_INFRA_REQ_MASK_B_LSB (1U << 20)      /* 1b */
+#define REG_SRCCLKENI1_SRCCLKENA_MASK_B_LSB (1U << 21)      /* 1b */
+#define REG_SRCCLKENI1_INFRA_REQ_MASK_B_LSB (1U << 22)      /* 1b */
+#define REG_SRCCLKENI2_SRCCLKENA_MASK_B_LSB (1U << 23)      /* 1b */
+#define REG_SRCCLKENI2_INFRA_REQ_MASK_B_LSB (1U << 24)      /* 1b */
+#define REG_INFRASYS_APSRC_REQ_MASK_B_LSB   (1U << 25)      /* 1b */
+#define REG_INFRASYS_DDR_EN_MASK_B_LSB      (1U << 26)      /* 1b */
+#define REG_MD32_SRCCLKENA_MASK_B_LSB       (1U << 27)      /* 1b */
+#define REG_MD32_INFRA_REQ_MASK_B_LSB       (1U << 28)      /* 1b */
+#define REG_MD32_APSRC_REQ_MASK_B_LSB       (1U << 29)      /* 1b */
+#define REG_MD32_VRF18_REQ_MASK_B_LSB       (1U << 30)      /* 1b */
+#define REG_MD32_DDR_EN_MASK_B_LSB          (1U << 31)      /* 1b */
+/* SPM_SRC2_MASK (0x10006000+0x0C0) */
+#define REG_SCP_SRCCLKENA_MASK_B_LSB        (1U << 0)       /* 1b */
+#define REG_SCP_INFRA_REQ_MASK_B_LSB        (1U << 1)       /* 1b */
+#define REG_SCP_APSRC_REQ_MASK_B_LSB        (1U << 2)       /* 1b */
+#define REG_SCP_VRF18_REQ_MASK_B_LSB        (1U << 3)       /* 1b */
+#define REG_SCP_DDR_EN_MASK_B_LSB           (1U << 4)       /* 1b */
+#define REG_AUDIO_DSP_SRCCLKENA_MASK_B_LSB  (1U << 5)       /* 1b */
+#define REG_AUDIO_DSP_INFRA_REQ_MASK_B_LSB  (1U << 6)       /* 1b */
+#define REG_AUDIO_DSP_APSRC_REQ_MASK_B_LSB  (1U << 7)       /* 1b */
+#define REG_AUDIO_DSP_VRF18_REQ_MASK_B_LSB  (1U << 8)       /* 1b */
+#define REG_AUDIO_DSP_DDR_EN_MASK_B_LSB     (1U << 9)       /* 1b */
+#define REG_UFS_SRCCLKENA_MASK_B_LSB        (1U << 10)      /* 1b */
+#define REG_UFS_INFRA_REQ_MASK_B_LSB        (1U << 11)      /* 1b */
+#define REG_UFS_APSRC_REQ_MASK_B_LSB        (1U << 12)      /* 1b */
+#define REG_UFS_VRF18_REQ_MASK_B_LSB        (1U << 13)      /* 1b */
+#define REG_UFS_DDR_EN_MASK_B_LSB           (1U << 14)      /* 1b */
+#define REG_DISP0_APSRC_REQ_MASK_B_LSB      (1U << 15)      /* 1b */
+#define REG_DISP0_DDR_EN_MASK_B_LSB         (1U << 16)      /* 1b */
+#define REG_DISP1_APSRC_REQ_MASK_B_LSB      (1U << 17)      /* 1b */
+#define REG_DISP1_DDR_EN_MASK_B_LSB         (1U << 18)      /* 1b */
+#define REG_GCE_INFRA_REQ_MASK_B_LSB        (1U << 19)      /* 1b */
+#define REG_GCE_APSRC_REQ_MASK_B_LSB        (1U << 20)      /* 1b */
+#define REG_GCE_VRF18_REQ_MASK_B_LSB        (1U << 21)      /* 1b */
+#define REG_GCE_DDR_EN_MASK_B_LSB           (1U << 22)      /* 1b */
+#define REG_APU_SRCCLKENA_MASK_B_LSB        (1U << 23)      /* 1b */
+#define REG_APU_INFRA_REQ_MASK_B_LSB        (1U << 24)      /* 1b */
+#define REG_APU_APSRC_REQ_MASK_B_LSB        (1U << 25)      /* 1b */
+#define REG_APU_VRF18_REQ_MASK_B_LSB        (1U << 26)      /* 1b */
+#define REG_APU_DDR_EN_MASK_B_LSB           (1U << 27)      /* 1b */
+#define REG_CG_CHECK_SRCCLKENA_MASK_B_LSB   (1U << 28)      /* 1b */
+#define REG_CG_CHECK_APSRC_REQ_MASK_B_LSB   (1U << 29)      /* 1b */
+#define REG_CG_CHECK_VRF18_REQ_MASK_B_LSB   (1U << 30)      /* 1b */
+#define REG_CG_CHECK_DDR_EN_MASK_B_LSB      (1U << 31)      /* 1b */
+/* SPM_SRC3_MASK (0x10006000+0x0C4) */
+#define REG_DVFSRC_EVENT_TRIGGER_MASK_B_LSB (1U << 0)       /* 1b */
+#define REG_SW2SPM_INT0_MASK_B_LSB          (1U << 1)       /* 1b */
+#define REG_SW2SPM_INT1_MASK_B_LSB          (1U << 2)       /* 1b */
+#define REG_SW2SPM_INT2_MASK_B_LSB          (1U << 3)       /* 1b */
+#define REG_SW2SPM_INT3_MASK_B_LSB          (1U << 4)       /* 1b */
+#define REG_SC_ADSP2SPM_WAKEUP_MASK_B_LSB   (1U << 5)       /* 1b */
+#define REG_SC_SSPM2SPM_WAKEUP_MASK_B_LSB   (1U << 6)       /* 4b */
+#define REG_SC_SCP2SPM_WAKEUP_MASK_B_LSB    (1U << 10)      /* 1b */
+#define REG_CSYSPWRREQ_MASK_LSB             (1U << 11)      /* 1b */
+#define REG_SPM_SRCCLKENA_RESERVED_MASK_B_LSB (1U << 12)    /* 1b */
+#define REG_SPM_INFRA_REQ_RESERVED_MASK_B_LSB (1U << 13)    /* 1b */
+#define REG_SPM_APSRC_REQ_RESERVED_MASK_B_LSB (1U << 14)    /* 1b */
+#define REG_SPM_VRF18_REQ_RESERVED_MASK_B_LSB (1U << 15)    /* 1b */
+#define REG_SPM_DDR_EN_RESERVED_MASK_B_LSB  (1U << 16)      /* 1b */
+#define REG_MCUPM_SRCCLKENA_MASK_B_LSB      (1U << 17)      /* 1b */
+#define REG_MCUPM_INFRA_REQ_MASK_B_LSB      (1U << 18)      /* 1b */
+#define REG_MCUPM_APSRC_REQ_MASK_B_LSB      (1U << 19)      /* 1b */
+#define REG_MCUPM_VRF18_REQ_MASK_B_LSB      (1U << 20)      /* 1b */
+#define REG_MCUPM_DDR_EN_MASK_B_LSB         (1U << 21)      /* 1b */
+#define REG_MSDC0_SRCCLKENA_MASK_B_LSB      (1U << 22)      /* 1b */
+#define REG_MSDC0_INFRA_REQ_MASK_B_LSB      (1U << 23)      /* 1b */
+#define REG_MSDC0_APSRC_REQ_MASK_B_LSB      (1U << 24)      /* 1b */
+#define REG_MSDC0_VRF18_REQ_MASK_B_LSB      (1U << 25)      /* 1b */
+#define REG_MSDC0_DDR_EN_MASK_B_LSB         (1U << 26)      /* 1b */
+#define REG_MSDC1_SRCCLKENA_MASK_B_LSB      (1U << 27)      /* 1b */
+#define REG_MSDC1_INFRA_REQ_MASK_B_LSB      (1U << 28)      /* 1b */
+#define REG_MSDC1_APSRC_REQ_MASK_B_LSB      (1U << 29)      /* 1b */
+#define REG_MSDC1_VRF18_REQ_MASK_B_LSB      (1U << 30)      /* 1b */
+#define REG_MSDC1_DDR_EN_MASK_B_LSB         (1U << 31)      /* 1b */
+/* SPM_SRC4_MASK (0x10006000+0x0C8) */
+#define CCIF_EVENT_MASK_B_LSB               (1U << 0)       /* 16b */
+#define REG_BAK_PSRI_SRCCLKENA_MASK_B_LSB   (1U << 16)      /* 1b */
+#define REG_BAK_PSRI_INFRA_REQ_MASK_B_LSB   (1U << 17)      /* 1b */
+#define REG_BAK_PSRI_APSRC_REQ_MASK_B_LSB   (1U << 18)      /* 1b */
+#define REG_BAK_PSRI_VRF18_REQ_MASK_B_LSB   (1U << 19)      /* 1b */
+#define REG_BAK_PSRI_DDR_EN_MASK_B_LSB      (1U << 20)      /* 1b */
+#define REG_DRAMC0_MD32_INFRA_REQ_MASK_B_LSB (1U << 21)     /* 1b */
+#define REG_DRAMC0_MD32_VRF18_REQ_MASK_B_LSB (1U << 22)     /* 1b */
+#define REG_DRAMC1_MD32_INFRA_REQ_MASK_B_LSB (1U << 23)     /* 1b */
+#define REG_DRAMC1_MD32_VRF18_REQ_MASK_B_LSB (1U << 24)     /* 1b */
+#define REG_CONN_SRCCLKENB2PWRAP_MASK_B_LSB (1U << 25)      /* 1b */
+#define REG_DRAMC0_MD32_WAKEUP_MASK_LSB     (1U << 26)      /* 1b */
+#define REG_DRAMC1_MD32_WAKEUP_MASK_LSB     (1U << 27)      /* 1b */
+/* SPM_SRC5_MASK (0x10006000+0x0CC) */
+#define REG_MCUSYS_MERGE_APSRC_REQ_MASK_B_LSB (1U << 0)     /* 9b */
+#define REG_MCUSYS_MERGE_DDR_EN_MASK_B_LSB  (1U << 9)       /* 9b */
+#define REG_MSDC2_SRCCLKENA_MASK_B_LSB      (1U << 18)      /* 1b */
+#define REG_MSDC2_INFRA_REQ_MASK_B_LSB      (1U << 19)      /* 1b */
+#define REG_MSDC2_APSRC_REQ_MASK_B_LSB      (1U << 20)      /* 1b */
+#define REG_MSDC2_VRF18_REQ_MASK_B_LSB      (1U << 21)      /* 1b */
+#define REG_MSDC2_DDR_EN_MASK_B_LSB         (1U << 22)      /* 1b */
+#define REG_PCIE_SRCCLKENA_MASK_B_LSB       (1U << 23)      /* 1b */
+#define REG_PCIE_INFRA_REQ_MASK_B_LSB       (1U << 24)      /* 1b */
+#define REG_PCIE_APSRC_REQ_MASK_B_LSB       (1U << 25)      /* 1b */
+#define REG_PCIE_VRF18_REQ_MASK_B_LSB       (1U << 26)      /* 1b */
+#define REG_PCIE_DDR_EN_MASK_B_LSB          (1U << 27)      /* 1b */
+/* SPM_WAKEUP_EVENT_MASK (0x10006000+0x0D0) */
+#define REG_WAKEUP_EVENT_MASK_LSB           (1U << 0)       /* 32b */
+/* SPM_WAKEUP_EVENT_EXT_MASK (0x10006000+0x0D4) */
+#define REG_EXT_WAKEUP_EVENT_MASK_LSB       (1U << 0)       /* 32b */
+/* SPM_TWAM_EVENT_CLEAR (0x10006000+0x0D8) */
+#define SPM_TWAM_EVENT_CLEAR_LSB            (1U << 0)       /* 1b */
+/* SCP_CLK_CON (0x10006000+0x0DC) */
+#define REG_SCP_26M_CK_SEL_LSB              (1U << 0)       /* 1b */
+#define REG_SCP_DCM_EN_LSB                  (1U << 1)       /* 1b */
+#define SCP_SECURE_V_REQ_MASK_LSB           (1U << 2)       /* 1b */
+#define SCP_SLP_REQ_LSB                     (1U << 3)       /* 1b */
+#define SCP_SLP_ACK_LSB                     (1U << 4)       /* 1b */
+/* PCM_DEBUG_CON (0x10006000+0x0E0) */
+#define PCM_DEBUG_OUT_ENABLE_LSB            (1U << 0)       /* 1b */
+/* AHB_BUS_CON (0x10006000+0x0E4) */
+#define AHB_HADDR_EXT_LSB                   (1U << 0)       /* 2b */
+#define REG_AHB_LOCK_LSB                    (1U << 8)       /* 1b */
+/* DDR_EN_DBC_CON0 (0x10006000+0x0E8) */
+#define REG_ALL_DDR_EN_DBC_LEN_LSB          (1U << 0)       /* 10b */
+#define REG_MD_DDR_EN_0_DBC_LEN_LSB         (1U << 10)      /* 10b */
+#define REG_HW_S1_DBC_LEN_LSB               (1U << 20)      /* 10b */
+/* DDR_EN_DBC_CON1 (0x10006000+0x0EC) */
+#define REG_ALL_DDR_EN_DBC_EN_LSB           (1U << 0)       /* 1b */
+#define REG_MD_DDR_EN_0_DBC_EN_LSB          (1U << 1)       /* 1b */
+#define REG_HW_S1_DBC_EN_LSB                (1U << 2)       /* 1b */
+/* SPM_RESOURCE_ACK_CON0 (0x10006000+0x0F0) */
+#define REG_MD_SRCCLKENA_ACK_0_MASK_LSB     (1U << 0)       /* 1b */
+#define REG_MD_INFRA_ACK_0_MASK_LSB         (1U << 1)       /* 1b */
+#define REG_MD_APSRC_ACK_0_MASK_LSB         (1U << 2)       /* 1b */
+#define REG_MD_VRF18_ACK_0_MASK_LSB         (1U << 3)       /* 1b */
+#define REG_MD_DDR_EN_ACK_0_MASK_LSB        (1U << 4)       /* 1b */
+#define REG_MD_SRCCLKENA_ACK_1_MASK_LSB     (1U << 5)       /* 1b */
+#define REG_MD_INFRA_ACK_1_MASK_LSB         (1U << 6)       /* 1b */
+#define REG_MD_APSRC_ACK_1_MASK_LSB         (1U << 7)       /* 1b */
+#define REG_MD_VRF18_ACK_1_MASK_LSB         (1U << 8)       /* 1b */
+#define REG_MD_DDR_EN_ACK_1_MASK_LSB        (1U << 9)       /* 1b */
+#define REG_CONN_SRCCLKENA_ACK_MASK_LSB     (1U << 10)      /* 1b */
+#define REG_CONN_INFRA_ACK_MASK_LSB         (1U << 11)      /* 1b */
+#define REG_CONN_APSRC_ACK_MASK_LSB         (1U << 12)      /* 1b */
+#define REG_CONN_VRF18_ACK_MASK_LSB         (1U << 13)      /* 1b */
+#define REG_CONN_DDR_EN_ACK_MASK_LSB        (1U << 14)      /* 1b */
+#define REG_MD32_SRCCLKENA_ACK_MASK_LSB     (1U << 15)      /* 1b */
+#define REG_MD32_INFRA_ACK_MASK_LSB         (1U << 16)      /* 1b */
+#define REG_MD32_APSRC_ACK_MASK_LSB         (1U << 17)      /* 1b */
+#define REG_MD32_VRF18_ACK_MASK_LSB         (1U << 18)      /* 1b */
+#define REG_MD32_DDR_EN_ACK_MASK_LSB        (1U << 19)      /* 1b */
+#define REG_SCP_SRCCLKENA_ACK_MASK_LSB      (1U << 20)      /* 1b */
+#define REG_SCP_INFRA_ACK_MASK_LSB          (1U << 21)      /* 1b */
+#define REG_SCP_APSRC_ACK_MASK_LSB          (1U << 22)      /* 1b */
+#define REG_SCP_VRF18_ACK_MASK_LSB          (1U << 23)      /* 1b */
+#define REG_SCP_DDR_EN_ACK_MASK_LSB         (1U << 24)      /* 1b */
+#define REG_AUDIO_DSP_SRCCLKENA_ACK_MASK_LSB (1U << 25)     /* 1b */
+#define REG_AUDIO_DSP_INFRA_ACK_MASK_LSB    (1U << 26)      /* 1b */
+#define REG_AUDIO_DSP_APSRC_ACK_MASK_LSB    (1U << 27)      /* 1b */
+#define REG_AUDIO_DSP_VRF18_ACK_MASK_LSB    (1U << 28)      /* 1b */
+#define REG_AUDIO_DSP_DDR_EN_ACK_MASK_LSB   (1U << 29)      /* 1b */
+#define REG_DISP0_DDR_EN_ACK_MASK_LSB       (1U << 30)      /* 1b */
+#define REG_DISP1_APSRC_ACK_MASK_LSB        (1U << 31)      /* 1b */
+/* SPM_RESOURCE_ACK_CON1 (0x10006000+0x0F4) */
+#define REG_UFS_SRCCLKENA_ACK_MASK_LSB      (1U << 0)       /* 1b */
+#define REG_UFS_INFRA_ACK_MASK_LSB          (1U << 1)       /* 1b */
+#define REG_UFS_APSRC_ACK_MASK_LSB          (1U << 2)       /* 1b */
+#define REG_UFS_VRF18_ACK_MASK_LSB          (1U << 3)       /* 1b */
+#define REG_UFS_DDR_EN_ACK_MASK_LSB         (1U << 4)       /* 1b */
+#define REG_APU_SRCCLKENA_ACK_MASK_LSB      (1U << 5)       /* 1b */
+#define REG_APU_INFRA_ACK_MASK_LSB          (1U << 6)       /* 1b */
+#define REG_APU_APSRC_ACK_MASK_LSB          (1U << 7)       /* 1b */
+#define REG_APU_VRF18_ACK_MASK_LSB          (1U << 8)       /* 1b */
+#define REG_APU_DDR_EN_ACK_MASK_LSB         (1U << 9)       /* 1b */
+#define REG_MCUPM_SRCCLKENA_ACK_MASK_LSB    (1U << 10)      /* 1b */
+#define REG_MCUPM_INFRA_ACK_MASK_LSB        (1U << 11)      /* 1b */
+#define REG_MCUPM_APSRC_ACK_MASK_LSB        (1U << 12)      /* 1b */
+#define REG_MCUPM_VRF18_ACK_MASK_LSB        (1U << 13)      /* 1b */
+#define REG_MCUPM_DDR_EN_ACK_MASK_LSB       (1U << 14)      /* 1b */
+#define REG_MSDC0_SRCCLKENA_ACK_MASK_LSB    (1U << 15)      /* 1b */
+#define REG_MSDC0_INFRA_ACK_MASK_LSB        (1U << 16)      /* 1b */
+#define REG_MSDC0_APSRC_ACK_MASK_LSB        (1U << 17)      /* 1b */
+#define REG_MSDC0_VRF18_ACK_MASK_LSB        (1U << 18)      /* 1b */
+#define REG_MSDC0_DDR_EN_ACK_MASK_LSB       (1U << 19)      /* 1b */
+#define REG_MSDC1_SRCCLKENA_ACK_MASK_LSB    (1U << 20)      /* 1b */
+#define REG_MSDC1_INFRA_ACK_MASK_LSB        (1U << 21)      /* 1b */
+#define REG_MSDC1_APSRC_ACK_MASK_LSB        (1U << 22)      /* 1b */
+#define REG_MSDC1_VRF18_ACK_MASK_LSB        (1U << 23)      /* 1b */
+#define REG_MSDC1_DDR_EN_ACK_MASK_LSB       (1U << 24)      /* 1b */
+#define REG_DISP0_APSRC_ACK_MASK_LSB        (1U << 25)      /* 1b */
+#define REG_DISP1_DDR_EN_ACK_MASK_LSB       (1U << 26)      /* 1b */
+#define REG_GCE_INFRA_ACK_MASK_LSB          (1U << 27)      /* 1b */
+#define REG_GCE_APSRC_ACK_MASK_LSB          (1U << 28)      /* 1b */
+#define REG_GCE_VRF18_ACK_MASK_LSB          (1U << 29)      /* 1b */
+#define REG_GCE_DDR_EN_ACK_MASK_LSB         (1U << 30)      /* 1b */
+/* SPM_RESOURCE_ACK_CON2 (0x10006000+0x0F8) */
+#define SPM_F26M_ACK_WAIT_CYCLE_LSB         (1U << 0)       /* 8b */
+#define SPM_INFRA_ACK_WAIT_CYCLE_LSB        (1U << 8)       /* 8b */
+#define SPM_APSRC_ACK_WAIT_CYCLE_LSB        (1U << 16)      /* 8b */
+#define SPM_VRF18_ACK_WAIT_CYCLE_LSB        (1U << 24)      /* 8b */
+/* SPM_RESOURCE_ACK_CON3 (0x10006000+0x0FC) */
+#define SPM_DDR_EN_ACK_WAIT_CYCLE_LSB       (1U << 0)       /* 8b */
+#define REG_BAK_PSRI_SRCCLKENA_ACK_MASK_LSB (1U << 8)       /* 1b */
+#define REG_BAK_PSRI_INFRA_ACK_MASK_LSB     (1U << 9)       /* 1b */
+#define REG_BAK_PSRI_APSRC_ACK_MASK_LSB     (1U << 10)      /* 1b */
+#define REG_BAK_PSRI_VRF18_ACK_MASK_LSB     (1U << 11)      /* 1b */
+#define REG_BAK_PSRI_DDR_EN_ACK_MASK_LSB    (1U << 12)      /* 1b */
+#define REG_MSDC2_SRCCLKENA_ACK_MASK_LSB    (1U << 13)      /* 1b */
+#define REG_MSDC2_INFRA_ACK_MASK_LSB        (1U << 14)      /* 1b */
+#define REG_MSDC2_APSRC_ACK_MASK_LSB        (1U << 15)      /* 1b */
+#define REG_MSDC2_VRF18_ACK_MASK_LSB        (1U << 16)      /* 1b */
+#define REG_MSDC2_DDR_EN_ACK_MASK_LSB       (1U << 17)      /* 1b */
+#define REG_PCIE_SRCCLKENA_ACK_MASK_LSB     (1U << 18)      /* 1b */
+#define REG_PCIE_INFRA_ACK_MASK_LSB         (1U << 19)      /* 1b */
+#define REG_PCIE_APSRC_ACK_MASK_LSB         (1U << 20)      /* 1b */
+#define REG_PCIE_VRF18_ACK_MASK_LSB         (1U << 21)      /* 1b */
+#define REG_PCIE_DDR_EN_ACK_MASK_LSB        (1U << 22)      /* 1b */
+#define REG_DPMAIF_SRCCLKENA_ACK_MASK_LSB   (1U << 23)      /* 1b */
+#define REG_DPMAIF_INFRA_ACK_MASK_LSB       (1U << 24)      /* 1b */
+#define REG_DPMAIF_APSRC_ACK_MASK_LSB       (1U << 25)      /* 1b */
+#define REG_DPMAIF_VRF18_ACK_MASK_LSB       (1U << 26)      /* 1b */
+#define REG_DPMAIF_DDR_EN_ACK_MASK_LSB      (1U << 27)      /* 1b */
+/* PCM_REG0_DATA (0x10006000+0x100) */
+#define PCM_REG0_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG2_DATA (0x10006000+0x104) */
+#define PCM_REG2_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG6_DATA (0x10006000+0x108) */
+#define PCM_REG6_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG7_DATA (0x10006000+0x10C) */
+#define PCM_REG7_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG13_DATA (0x10006000+0x110) */
+#define PCM_REG13_RF_LSB                    (1U << 0)       /* 32b */
+/* SRC_REQ_STA_0 (0x10006000+0x114) */
+#define MD_SRCCLKENA_0_LSB                  (1U << 0)       /* 1b */
+#define MD_SRCCLKENA2INFRA_REQ_0_LSB        (1U << 1)       /* 1b */
+#define MD_APSRC2INFRA_REQ_0_LSB            (1U << 2)       /* 1b */
+#define MD_APSRC_REQ_0_LSB                  (1U << 3)       /* 1b */
+#define MD_VRF18_REQ_0_LSB                  (1U << 4)       /* 1b */
+#define MD_DDR_EN_0_LSB                     (1U << 5)       /* 1b */
+#define MD_SRCCLKENA_1_LSB                  (1U << 6)       /* 1b */
+#define MD_SRCCLKENA2INFRA_REQ_1_LSB        (1U << 7)       /* 1b */
+#define MD_APSRC2INFRA_REQ_1_LSB            (1U << 8)       /* 1b */
+#define MD_APSRC_REQ_1_LSB                  (1U << 9)       /* 1b */
+#define MD_VRF18_REQ_1_LSB                  (1U << 10)      /* 1b */
+#define MD_DDR_EN_1_LSB                     (1U << 11)      /* 1b */
+#define CONN_SRCCLKENA_LSB                  (1U << 12)      /* 1b */
+#define CONN_SRCCLKENB_LSB                  (1U << 13)      /* 1b */
+#define CONN_INFRA_REQ_LSB                  (1U << 14)      /* 1b */
+#define CONN_APSRC_REQ_LSB                  (1U << 15)      /* 1b */
+#define CONN_VRF18_REQ_LSB                  (1U << 16)      /* 1b */
+#define CONN_DDR_EN_LSB                     (1U << 17)      /* 1b */
+#define SRCCLKENI_LSB                       (1U << 18)      /* 3b */
+#define MD32_SRCCLKENA_LSB                  (1U << 21)      /* 1b */
+#define MD32_INFRA_REQ_LSB                  (1U << 22)      /* 1b */
+#define MD32_APSRC_REQ_LSB                  (1U << 23)      /* 1b */
+#define MD32_VRF18_REQ_LSB                  (1U << 24)      /* 1b */
+#define MD32_DDR_EN_LSB                     (1U << 25)      /* 1b */
+#define DISP0_APSRC_REQ_LSB                 (1U << 26)      /* 1b */
+#define DISP0_DDR_EN_LSB                    (1U << 27)      /* 1b */
+#define DISP1_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define DISP1_DDR_EN_LSB                    (1U << 29)      /* 1b */
+#define DVFSRC_EVENT_TRIGGER_LSB            (1U << 30)      /* 1b */
+/* SRC_REQ_STA_1 (0x10006000+0x118) */
+#define SCP_SRCCLKENA_LSB                   (1U << 0)       /* 1b */
+#define SCP_INFRA_REQ_LSB                   (1U << 1)       /* 1b */
+#define SCP_APSRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define SCP_VRF18_REQ_LSB                   (1U << 3)       /* 1b */
+#define SCP_DDR_EN_LSB                      (1U << 4)       /* 1b */
+#define AUDIO_DSP_SRCCLKENA_LSB             (1U << 5)       /* 1b */
+#define AUDIO_DSP_INFRA_REQ_LSB             (1U << 6)       /* 1b */
+#define AUDIO_DSP_APSRC_REQ_LSB             (1U << 7)       /* 1b */
+#define AUDIO_DSP_VRF18_REQ_LSB             (1U << 8)       /* 1b */
+#define AUDIO_DSP_DDR_EN_LSB                (1U << 9)       /* 1b */
+#define UFS_SRCCLKENA_LSB                   (1U << 10)      /* 1b */
+#define UFS_INFRA_REQ_LSB                   (1U << 11)      /* 1b */
+#define UFS_APSRC_REQ_LSB                   (1U << 12)      /* 1b */
+#define UFS_VRF18_REQ_LSB                   (1U << 13)      /* 1b */
+#define UFS_DDR_EN_LSB                      (1U << 14)      /* 1b */
+#define GCE_INFRA_REQ_LSB                   (1U << 15)      /* 1b */
+#define GCE_APSRC_REQ_LSB                   (1U << 16)      /* 1b */
+#define GCE_VRF18_REQ_LSB                   (1U << 17)      /* 1b */
+#define GCE_DDR_EN_LSB                      (1U << 18)      /* 1b */
+#define INFRASYS_APSRC_REQ_LSB              (1U << 19)      /* 1b */
+#define INFRASYS_DDR_EN_LSB                 (1U << 20)      /* 1b */
+#define MSDC0_SRCCLKENA_LSB                 (1U << 21)      /* 1b */
+#define MSDC0_INFRA_REQ_LSB                 (1U << 22)      /* 1b */
+#define MSDC0_APSRC_REQ_LSB                 (1U << 23)      /* 1b */
+#define MSDC0_VRF18_REQ_LSB                 (1U << 24)      /* 1b */
+#define MSDC0_DDR_EN_LSB                    (1U << 25)      /* 1b */
+#define MSDC1_SRCCLKENA_LSB                 (1U << 26)      /* 1b */
+#define MSDC1_INFRA_REQ_LSB                 (1U << 27)      /* 1b */
+#define MSDC1_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define MSDC1_VRF18_REQ_LSB                 (1U << 29)      /* 1b */
+#define MSDC1_DDR_EN_LSB                    (1U << 30)      /* 1b */
+/* SRC_REQ_STA_2 (0x10006000+0x11C) */
+#define MCUSYS_MERGE_DDR_EN_LSB             (1U << 0)       /* 9b */
+#define EMI_SELF_REFRESH_CH_LSB             (1U << 9)       /* 2b */
+#define SW2SPM_INT_LSB                      (1U << 11)      /* 4b */
+#define SC_ADSP2SPM_WAKEUP_LSB              (1U << 15)      /* 1b */
+#define SC_SSPM2SPM_WAKEUP_LSB              (1U << 16)      /* 4b */
+#define SRC_REQ_STA_2_SC_SCP2SPM_WAKEUP_LSB (1U << 20)      /* 1b */
+#define SPM_SRCCLKENA_RESERVED_LSB          (1U << 21)      /* 1b */
+#define SPM_INFRA_REQ_RESERVED_LSB          (1U << 22)      /* 1b */
+#define SPM_APSRC_REQ_RESERVED_LSB          (1U << 23)      /* 1b */
+#define SPM_VRF18_REQ_RESERVED_LSB          (1U << 24)      /* 1b */
+#define SPM_DDR_EN_RESERVED_LSB             (1U << 25)      /* 1b */
+#define MCUPM_SRCCLKENA_LSB                 (1U << 26)      /* 1b */
+#define MCUPM_INFRA_REQ_LSB                 (1U << 27)      /* 1b */
+#define MCUPM_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define MCUPM_VRF18_REQ_LSB                 (1U << 29)      /* 1b */
+#define MCUPM_DDR_EN_LSB                    (1U << 30)      /* 1b */
+/* PCM_TIMER_OUT (0x10006000+0x120) */
+#define PCM_TIMER_LSB                       (1U << 0)       /* 32b */
+/* PCM_WDT_OUT (0x10006000+0x124) */
+#define PCM_WDT_TIMER_VAL_OUT_LSB           (1U << 0)       /* 32b */
+/* SPM_IRQ_STA (0x10006000+0x128) */
+#define TWAM_IRQ_LSB                        (1U << 2)       /* 1b */
+#define PCM_IRQ_LSB                         (1U << 3)       /* 1b */
+/* SRC_REQ_STA_4 (0x10006000+0x12C) */
+#define APU_SRCCLKENA_LSB                   (1U << 0)       /* 1b */
+#define APU_INFRA_REQ_LSB                   (1U << 1)       /* 1b */
+#define APU_APSRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define APU_VRF18_REQ_LSB                   (1U << 3)       /* 1b */
+#define APU_DDR_EN_LSB                      (1U << 4)       /* 1b */
+#define BAK_PSRI_SRCCLKENA_LSB              (1U << 5)       /* 1b */
+#define BAK_PSRI_INFRA_REQ_LSB              (1U << 6)       /* 1b */
+#define BAK_PSRI_APSRC_REQ_LSB              (1U << 7)       /* 1b */
+#define BAK_PSRI_VRF18_REQ_LSB              (1U << 8)       /* 1b */
+#define BAK_PSRI_DDR_EN_LSB                 (1U << 9)       /* 1b */
+#define MSDC2_SRCCLKENA_LSB                 (1U << 10)      /* 1b */
+#define MSDC2_INFRA_REQ_LSB                 (1U << 11)      /* 1b */
+#define MSDC2_APSRC_REQ_LSB                 (1U << 12)      /* 1b */
+#define MSDC2_VRF18_REQ_LSB                 (1U << 13)      /* 1b */
+#define MSDC2_DDR_EN_LSB                    (1U << 14)      /* 1b */
+#define PCIE_SRCCLKENA_LSB                  (1U << 15)      /* 1b */
+#define PCIE_INFRA_REQ_LSB                  (1U << 16)      /* 1b */
+#define PCIE_APSRC_REQ_LSB                  (1U << 17)      /* 1b */
+#define PCIE_VRF18_REQ_LSB                  (1U << 18)      /* 1b */
+#define PCIE_DDR_EN_LSB                     (1U << 19)      /* 1b */
+#define DPMAIF_SRCCLKENA_LSB                (1U << 20)      /* 1b */
+#define DPMAIF_INFRA_REQ_LSB                (1U << 21)      /* 1b */
+#define DPMAIF_APSRC_REQ_LSB                (1U << 22)      /* 1b */
+#define DPMAIF_VRF18_REQ_LSB                (1U << 23)      /* 1b */
+#define DPMAIF_DDR_EN_LSB                   (1U << 24)      /* 1b */
+/* MD32PCM_WAKEUP_STA (0x10006000+0x130) */
+#define MD32PCM_WAKEUP_STA_LSB              (1U << 0)       /* 32b */
+/* MD32PCM_EVENT_STA (0x10006000+0x134) */
+#define MD32PCM_EVENT_STA_LSB               (1U << 0)       /* 32b */
+/* SPM_WAKEUP_STA (0x10006000+0x138) */
+#define F32K_WAKEUP_EVENT_L_LSB             (1U << 0)       /* 16b */
+#define ASYN_WAKEUP_EVENT_L_LSB             (1U << 16)      /* 16b */
+/* SPM_WAKEUP_EXT_STA (0x10006000+0x13C) */
+#define EXT_WAKEUP_EVENT_LSB                (1U << 0)       /* 32b */
+/* SPM_WAKEUP_MISC (0x10006000+0x140) */
+#define GIC_WAKEUP_LSB                      (1U << 0)       /* 10b */
+#define DVFSRC_IRQ_LSB                      (1U << 16)      /* 1b */
+#define SPM_WAKEUP_MISC_REG_CPU_WAKEUP_LSB  (1U << 17)      /* 1b */
+#define PCM_TIMER_EVENT_LSB                 (1U << 18)      /* 1b */
+#define PMIC_EINT_OUT_B_LSB                 (1U << 19)      /* 2b */
+#define TWAM_IRQ_B_LSB                      (1U << 21)      /* 1b */
+#define PMSR_IRQ_B_SET0_LSB                 (1U << 22)      /* 1b */
+#define PMSR_IRQ_B_SET1_LSB                 (1U << 23)      /* 1b */
+#define PMSR_IRQ_B_SET2_LSB                 (1U << 24)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_0_LSB            (1U << 25)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_1_LSB            (1U << 26)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_2_LSB            (1U << 27)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_3_LSB            (1U << 28)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_ALL_LSB          (1U << 29)      /* 1b */
+#define PMIC_IRQ_ACK_LSB                    (1U << 30)      /* 1b */
+#define PMIC_SCP_IRQ_LSB                    (1U << 31)      /* 1b */
+/* MM_DVFS_HALT (0x10006000+0x144) */
+#define MM_DVFS_HALT_LSB                    (1U << 0)       /* 5b */
+/* BUS_PROTECT_RDY (0x10006000+0x150) */
+#define PROTECT_READY_LSB                   (1U << 0)       /* 32b */
+/* BUS_PROTECT1_RDY (0x10006000+0x154) */
+#define PROTECT1_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT2_RDY (0x10006000+0x158) */
+#define PROTECT2_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT3_RDY (0x10006000+0x15C) */
+#define PROTECT3_READY_LSB                  (1U << 0)       /* 32b */
+/* SUBSYS_IDLE_STA (0x10006000+0x160) */
+#define SUBSYS_IDLE_SIGNALS_LSB             (1U << 0)       /* 32b */
+/* PCM_STA (0x10006000+0x164) */
+#define PCM_CK_SEL_O_LSB                    (1U << 0)       /* 4b */
+#define EXT_SRC_STA_LSB                     (1U << 4)       /* 3b */
+/* SRC_REQ_STA_3 (0x10006000+0x168) */
+#define CCIF_EVENT_RAW_STATUS_LSB           (1U << 0)       /* 16b */
+#define F26M_STATE_LSB                      (1U << 16)      /* 1b */
+#define INFRA_STATE_LSB                     (1U << 17)      /* 1b */
+#define APSRC_STATE_LSB                     (1U << 18)      /* 1b */
+#define VRF18_STATE_LSB                     (1U << 19)      /* 1b */
+#define DDR_EN_STATE_LSB                    (1U << 20)      /* 1b */
+#define DVFS_STATE_LSB                      (1U << 21)      /* 1b */
+#define SW_MAILBOX_STATE_LSB                (1U << 22)      /* 1b */
+#define SSPM_MAILBOX_STATE_LSB              (1U << 23)      /* 1b */
+#define ADSP_MAILBOX_STATE_LSB              (1U << 24)      /* 1b */
+#define SCP_MAILBOX_STATE_LSB               (1U << 25)      /* 1b */
+/* PWR_STATUS (0x10006000+0x16C) */
+#define PWR_STATUS_LSB                      (1U << 0)       /* 32b */
+/* PWR_STATUS_2ND (0x10006000+0x170) */
+#define PWR_STATUS_2ND_LSB                  (1U << 0)       /* 32b */
+/* CPU_PWR_STATUS (0x10006000+0x174) */
+#define MP0_SPMC_PWR_ON_ACK_CPU0_LSB        (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU1_LSB        (1U << 1)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU2_LSB        (1U << 2)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU3_LSB        (1U << 3)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU4_LSB        (1U << 4)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU5_LSB        (1U << 5)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU6_LSB        (1U << 6)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU7_LSB        (1U << 7)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPUTOP_LSB      (1U << 8)       /* 1b */
+#define MCUSYS_SPMC_PWR_ON_ACK_LSB          (1U << 9)       /* 1b */
+/* OTHER_PWR_STATUS (0x10006000+0x178) */
+#define OTHER_PWR_STATUS_LSB                (1U << 0)       /* 32b */
+/* SPM_VTCXO_EVENT_COUNT_STA (0x10006000+0x17C) */
+#define SPM_VTCXO_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_VTCXO_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_INFRA_EVENT_COUNT_STA (0x10006000+0x180) */
+#define SPM_INFRA_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_INFRA_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_VRF18_EVENT_COUNT_STA (0x10006000+0x184) */
+#define SPM_VRF18_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_VRF18_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_APSRC_EVENT_COUNT_STA (0x10006000+0x188) */
+#define SPM_APSRC_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_APSRC_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_DDREN_EVENT_COUNT_STA (0x10006000+0x18C) */
+#define SPM_DDREN_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_DDREN_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* MD32PCM_STA (0x10006000+0x190) */
+#define MD32PCM_HALT_LSB                    (1U << 0)       /* 1b */
+#define MD32PCM_GATED_LSB                   (1U << 1)       /* 1b */
+/* MD32PCM_PC (0x10006000+0x194) */
+#define MON_PC_LSB                          (1U << 0)       /* 32b */
+/* DVFSRC_EVENT_STA (0x10006000+0x1A4) */
+#define DVFSRC_EVENT_LSB                    (1U << 0)       /* 32b */
+/* BUS_PROTECT4_RDY (0x10006000+0x1A8) */
+#define PROTECT4_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT5_RDY (0x10006000+0x1AC) */
+#define PROTECT5_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT6_RDY (0x10006000+0x1B0) */
+#define PROTECT6_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT7_RDY (0x10006000+0x1B4) */
+#define PROTECT7_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT8_RDY (0x10006000+0x1B8) */
+#define PROTECT8_READY_LSB                  (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA0 (0x10006000+0x1D0) */
+#define LAST_IDLE_CNT_0_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA1 (0x10006000+0x1D4) */
+#define LAST_IDLE_CNT_1_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA2 (0x10006000+0x1D8) */
+#define LAST_IDLE_CNT_2_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA3 (0x10006000+0x1DC) */
+#define LAST_IDLE_CNT_3_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA0 (0x10006000+0x1E0) */
+#define CURRENT_IDLE_CNT_0_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA1 (0x10006000+0x1E4) */
+#define CURRENT_IDLE_CNT_1_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA2 (0x10006000+0x1E8) */
+#define CURRENT_IDLE_CNT_2_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA3 (0x10006000+0x1EC) */
+#define CURRENT_IDLE_CNT_3_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_TIMER_OUT (0x10006000+0x1F0) */
+#define TWAM_TIMER_LSB                      (1U << 0)       /* 32b */
+/* SPM_CG_CHECK_STA (0x10006000+0x1F4) */
+#define SPM_CG_CHECK_SLEEP_REQ_0_LSB        (1U << 0)       /* 1b */
+#define SPM_CG_CHECK_SLEEP_REQ_1_LSB        (1U << 1)       /* 1b */
+#define SPM_CG_CHECK_SLEEP_REQ_2_LSB        (1U << 2)       /* 1b */
+/* SPM_DVFS_STA (0x10006000+0x1F8) */
+#define TARGET_DVFS_LEVEL_LSB               (1U << 0)       /* 32b */
+/* SPM_DVFS_OPP_STA (0x10006000+0x1FC) */
+#define TARGET_DVFS_OPP_LSB                 (1U << 0)       /* 5b */
+#define CURRENT_DVFS_OPP_LSB                (1U << 5)       /* 5b */
+#define RELAY_DVFS_OPP_LSB                  (1U << 10)      /* 5b */
+/* SPM_MCUSYS_PWR_CON (0x10006000+0x200) */
+#define MCUSYS_SPMC_PWR_RST_B_LSB           (1U << 0)       /* 1b */
+#define MCUSYS_SPMC_PWR_ON_LSB              (1U << 2)       /* 1b */
+#define MCUSYS_SPMC_PWR_CLK_DIS_LSB         (1U << 4)       /* 1b */
+#define MCUSYS_SPMC_RESETPWRON_CONFIG_LSB   (1U << 5)       /* 1b */
+#define MCUSYS_SPMC_DORMANT_EN_LSB          (1U << 6)       /* 1b */
+#define MCUSYS_VPROC_EXT_OFF_LSB            (1U << 7)       /* 1b */
+#define SPM_MCUSYS_PWR_CON_MCUSYS_SPMC_PWR_ON_ACK_LSB (1U << 31)      /* 1b */
+/* SPM_CPUTOP_PWR_CON (0x10006000+0x204) */
+#define MP0_SPMC_PWR_RST_B_CPUTOP_LSB       (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPUTOP_LSB          (1U << 2)       /* 1b */
+#define MP0_SPMC_PWR_CLK_DIS_CPUTOP_LSB     (1U << 4)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPUTOP_LSB (1U << 5)     /* 1b */
+#define MP0_SPMC_DORMANT_EN_CPUTOP_LSB      (1U << 6)       /* 1b */
+#define MP0_VPROC_EXT_OFF_LSB               (1U << 7)       /* 1b */
+#define MP0_VSRAM_EXT_OFF_LSB               (1U << 8)       /* 1b */
+#define SPM_CPUTOP_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPUTOP_LSB (1U << 31)  /* 1b */
+/* SPM_CPU0_PWR_CON (0x10006000+0x208) */
+#define MP0_SPMC_PWR_RST_B_CPU0_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU0_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU0_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU0_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU0_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU0_LSB (1U << 31)      /* 1b */
+/* SPM_CPU1_PWR_CON (0x10006000+0x20C) */
+#define MP0_SPMC_PWR_RST_B_CPU1_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU1_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU1_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU1_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU1_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU1_LSB (1U << 31)      /* 1b */
+/* SPM_CPU2_PWR_CON (0x10006000+0x210) */
+#define MP0_SPMC_PWR_RST_B_CPU2_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU2_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU2_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU2_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU2_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU2_LSB (1U << 31)      /* 1b */
+/* SPM_CPU3_PWR_CON (0x10006000+0x214) */
+#define MP0_SPMC_PWR_RST_B_CPU3_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU3_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU3_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU3_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU3_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU3_LSB (1U << 31)      /* 1b */
+/* SPM_CPU4_PWR_CON (0x10006000+0x218) */
+#define MP0_SPMC_PWR_RST_B_CPU4_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU4_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU4_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU4_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU4_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU4_LSB (1U << 31)      /* 1b */
+/* SPM_CPU5_PWR_CON (0x10006000+0x21C) */
+#define MP0_SPMC_PWR_RST_B_CPU5_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU5_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU5_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU5_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU5_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU5_LSB (1U << 31)      /* 1b */
+/* SPM_CPU6_PWR_CON (0x10006000+0x220) */
+#define MP0_SPMC_PWR_RST_B_CPU6_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU6_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU6_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU6_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU6_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU6_LSB (1U << 31)      /* 1b */
+/* SPM_CPU7_PWR_CON (0x10006000+0x224) */
+#define MP0_SPMC_PWR_RST_B_CPU7_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU7_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU7_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU7_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU7_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU7_LSB (1U << 31)      /* 1b */
+/* ARMPLL_CLK_CON (0x10006000+0x22C) */
+#define SC_ARM_FHC_PAUSE_LSB                (1U << 0)       /* 6b */
+#define SC_ARM_CK_OFF_LSB                   (1U << 6)       /* 6b */
+#define SC_ARMPLL_OFF_LSB                   (1U << 12)      /* 1b */
+#define SC_ARMBPLL_OFF_LSB                  (1U << 13)      /* 1b */
+#define SC_ARMBPLL1_OFF_LSB                 (1U << 14)      /* 1b */
+#define SC_ARMBPLL2_OFF_LSB                 (1U << 15)      /* 1b */
+#define SC_ARMBPLL3_OFF_LSB                 (1U << 16)      /* 1b */
+#define SC_CCIPLL_CKOFF_LSB                 (1U << 17)      /* 1b */
+#define SC_ARMDDS_OFF_LSB                   (1U << 18)      /* 1b */
+#define SC_ARMBPLL_S_OFF_LSB                (1U << 19)      /* 1b */
+#define SC_ARMBPLL1_S_OFF_LSB               (1U << 20)      /* 1b */
+#define SC_ARMBPLL2_S_OFF_LSB               (1U << 21)      /* 1b */
+#define SC_ARMBPLL3_S_OFF_LSB               (1U << 22)      /* 1b */
+#define SC_CCIPLL_PWROFF_LSB                (1U << 23)      /* 1b */
+#define SC_ARMPLLOUT_OFF_LSB                (1U << 24)      /* 1b */
+#define SC_ARMBPLLOUT_OFF_LSB               (1U << 25)      /* 1b */
+#define SC_ARMBPLLOUT1_OFF_LSB              (1U << 26)      /* 1b */
+#define SC_ARMBPLLOUT2_OFF_LSB              (1U << 27)      /* 1b */
+#define SC_ARMBPLLOUT3_OFF_LSB              (1U << 28)      /* 1b */
+#define SC_CCIPLL_OUT_OFF_LSB               (1U << 29)      /* 1b */
+/* MCUSYS_IDLE_STA (0x10006000+0x230) */
+#define ARMBUS_IDLE_TO_26M_LSB              (1U << 0)       /* 1b */
+#define MP0_CLUSTER_IDLE_TO_PWR_OFF_LSB     (1U << 1)       /* 1b */
+#define MCUSYS_DDR_EN_0_LSB                 (1U << 2)       /* 1b */
+#define MCUSYS_DDR_EN_1_LSB                 (1U << 3)       /* 1b */
+#define MCUSYS_DDR_EN_2_LSB                 (1U << 4)       /* 1b */
+#define MCUSYS_DDR_EN_3_LSB                 (1U << 5)       /* 1b */
+#define MCUSYS_DDR_EN_4_LSB                 (1U << 6)       /* 1b */
+#define MCUSYS_DDR_EN_5_LSB                 (1U << 7)       /* 1b */
+#define MCUSYS_DDR_EN_6_LSB                 (1U << 8)       /* 1b */
+#define MCUSYS_DDR_EN_7_LSB                 (1U << 9)       /* 1b */
+#define MP0_CPU_IDLE_TO_PWR_OFF_LSB         (1U << 16)      /* 8b */
+#define WFI_AF_SEL_LSB                      (1U << 24)      /* 8b */
+/* GIC_WAKEUP_STA (0x10006000+0x234) */
+#define GIC_WAKEUP_STA_GIC_WAKEUP_LSB       (1U << 10)      /* 10b */
+/* CPU_SPARE_CON (0x10006000+0x238) */
+#define CPU_SPARE_CON_LSB                   (1U << 0)       /* 32b */
+/* CPU_SPARE_CON_SET (0x10006000+0x23C) */
+#define CPU_SPARE_CON_SET_LSB               (1U << 0)       /* 32b */
+/* CPU_SPARE_CON_CLR (0x10006000+0x240) */
+#define CPU_SPARE_CON_CLR_LSB               (1U << 0)       /* 32b */
+/* ARMPLL_CLK_SEL (0x10006000+0x244) */
+#define ARMPLL_CLK_SEL_LSB                  (1U << 0)       /* 15b */
+/* EXT_INT_WAKEUP_REQ (0x10006000+0x248) */
+#define EXT_INT_WAKEUP_REQ_LSB              (1U << 0)       /* 10b */
+/* EXT_INT_WAKEUP_REQ_SET (0x10006000+0x24C) */
+#define EXT_INT_WAKEUP_REQ_SET_LSB          (1U << 0)       /* 10b */
+/* EXT_INT_WAKEUP_REQ_CLR (0x10006000+0x250) */
+#define EXT_INT_WAKEUP_REQ_CLR_LSB          (1U << 0)       /* 10b */
+/* MP0_CPU0_IRQ_MASK (0x10006000+0x260) */
+#define MP0_CPU0_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU0_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU1_IRQ_MASK (0x10006000+0x264) */
+#define MP0_CPU1_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU1_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU2_IRQ_MASK (0x10006000+0x268) */
+#define MP0_CPU2_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU2_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU3_IRQ_MASK (0x10006000+0x26C) */
+#define MP0_CPU3_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU3_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU0_IRQ_MASK (0x10006000+0x270) */
+#define MP1_CPU0_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU0_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU1_IRQ_MASK (0x10006000+0x274) */
+#define MP1_CPU1_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU1_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU2_IRQ_MASK (0x10006000+0x278) */
+#define MP1_CPU2_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU2_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU3_IRQ_MASK (0x10006000+0x27C) */
+#define MP1_CPU3_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU3_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU0_WFI_EN (0x10006000+0x280) */
+#define MP0_CPU0_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU1_WFI_EN (0x10006000+0x284) */
+#define MP0_CPU1_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU2_WFI_EN (0x10006000+0x288) */
+#define MP0_CPU2_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU3_WFI_EN (0x10006000+0x28C) */
+#define MP0_CPU3_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU4_WFI_EN (0x10006000+0x290) */
+#define MP0_CPU4_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU5_WFI_EN (0x10006000+0x294) */
+#define MP0_CPU5_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU6_WFI_EN (0x10006000+0x298) */
+#define MP0_CPU6_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU7_WFI_EN (0x10006000+0x29C) */
+#define MP0_CPU7_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* ROOT_CPUTOP_ADDR (0x10006000+0x2A0) */
+#define ROOT_CPUTOP_ADDR_LSB                (1U << 0)       /* 32b */
+/* ROOT_CORE_ADDR (0x10006000+0x2A4) */
+#define ROOT_CORE_ADDR_LSB                  (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_0 (0x10006000+0x2D0) */
+#define SPM2SW_MAILBOX_0_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_1 (0x10006000+0x2D4) */
+#define SPM2SW_MAILBOX_1_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_2 (0x10006000+0x2D8) */
+#define SPM2SW_MAILBOX_2_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_3 (0x10006000+0x2DC) */
+#define SPM2SW_MAILBOX_3_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_INT (0x10006000+0x2E0) */
+#define SW2SPM_INT_SW2SPM_INT_LSB           (1U << 0)       /* 4b */
+/* SW2SPM_INT_SET (0x10006000+0x2E4) */
+#define SW2SPM_INT_SET_LSB                  (1U << 0)       /* 4b */
+/* SW2SPM_INT_CLR (0x10006000+0x2E8) */
+#define SW2SPM_INT_CLR_LSB                  (1U << 0)       /* 4b */
+/* SW2SPM_MAILBOX_0 (0x10006000+0x2EC) */
+#define SW2SPM_MAILBOX_0_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_1 (0x10006000+0x2F0) */
+#define SW2SPM_MAILBOX_1_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_2 (0x10006000+0x2F4) */
+#define SW2SPM_MAILBOX_2_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_3 (0x10006000+0x2F8) */
+#define SW2SPM_MAILBOX_3_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_CFG (0x10006000+0x2FC) */
+#define SWU2SPM_INT_MASK_B_LSB              (1U << 0)       /* 4b */
+/* MD1_PWR_CON (0x10006000+0x300) */
+#define MD1_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define MD1_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define MD1_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define MD1_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define MD1_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define MD1_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_MD1_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* CONN_PWR_CON (0x10006000+0x304) */
+#define CONN_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define CONN_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define CONN_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define CONN_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define CONN_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+/* MFG0_PWR_CON (0x10006000+0x308) */
+#define MFG0_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG0_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG0_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG0_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG0_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG0_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG0_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG1_PWR_CON (0x10006000+0x30C) */
+#define MFG1_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG1_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG1_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG1_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG1_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG1_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG1_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG2_PWR_CON (0x10006000+0x310) */
+#define MFG2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG3_PWR_CON (0x10006000+0x314) */
+#define MFG3_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG3_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG3_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG3_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG3_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG3_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG3_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG4_PWR_CON (0x10006000+0x318) */
+#define MFG4_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG4_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG4_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG4_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG4_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG4_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG4_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG5_PWR_CON (0x10006000+0x31C) */
+#define MFG5_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG5_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG5_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG5_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG5_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG5_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG5_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG6_PWR_CON (0x10006000+0x320) */
+#define MFG6_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG6_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG6_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG6_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG6_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG6_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG6_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* IFR_PWR_CON (0x10006000+0x324) */
+#define IFR_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define IFR_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define IFR_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define IFR_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define IFR_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define IFR_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_IFR_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* IFR_SUB_PWR_CON (0x10006000+0x328) */
+#define IFR_SUB_PWR_RST_B_LSB               (1U << 0)       /* 1b */
+#define IFR_SUB_PWR_ISO_LSB                 (1U << 1)       /* 1b */
+#define IFR_SUB_PWR_ON_LSB                  (1U << 2)       /* 1b */
+#define IFR_SUB_PWR_ON_2ND_LSB              (1U << 3)       /* 1b */
+#define IFR_SUB_PWR_CLK_DIS_LSB             (1U << 4)       /* 1b */
+#define IFR_SUB_SRAM_PDN_LSB                (1U << 8)       /* 1b */
+#define SC_IFR_SUB_SRAM_PDN_ACK_LSB         (1U << 12)      /* 1b */
+/* DPY_PWR_CON (0x10006000+0x32C) */
+#define DPY_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define DPY_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define DPY_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define DPY_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define DPY_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define DPY_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_DPY_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* ISP_PWR_CON (0x10006000+0x330) */
+#define ISP_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define ISP_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define ISP_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define ISP_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define ISP_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define ISP_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_ISP_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* ISP2_PWR_CON (0x10006000+0x334) */
+#define ISP2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define ISP2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define ISP2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define ISP2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define ISP2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define ISP2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_ISP2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* IPE_PWR_CON (0x10006000+0x338) */
+#define IPE_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define IPE_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define IPE_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define IPE_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define IPE_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define IPE_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_IPE_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VDE_PWR_CON (0x10006000+0x33C) */
+#define VDE_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define VDE_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define VDE_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define VDE_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define VDE_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define VDE_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_VDE_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VDE2_PWR_CON (0x10006000+0x340) */
+#define VDE2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define VDE2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define VDE2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define VDE2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define VDE2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define VDE2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_VDE2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* VEN_PWR_CON (0x10006000+0x344) */
+#define VEN_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define VEN_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define VEN_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define VEN_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define VEN_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define VEN_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_VEN_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VEN_CORE1_PWR_CON (0x10006000+0x348) */
+#define VEN_CORE1_PWR_RST_B_LSB             (1U << 0)       /* 1b */
+#define VEN_CORE1_PWR_ISO_LSB               (1U << 1)       /* 1b */
+#define VEN_CORE1_PWR_ON_LSB                (1U << 2)       /* 1b */
+#define VEN_CORE1_PWR_ON_2ND_LSB            (1U << 3)       /* 1b */
+#define VEN_CORE1_PWR_CLK_DIS_LSB           (1U << 4)       /* 1b */
+#define VEN_CORE1_SRAM_PDN_LSB              (1U << 8)       /* 1b */
+#define SC_VEN_CORE1_SRAM_PDN_ACK_LSB       (1U << 12)      /* 1b */
+/* MDP_PWR_CON (0x10006000+0x34C) */
+#define MDP_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define MDP_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define MDP_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define MDP_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define MDP_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define MDP_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_MDP_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* DIS_PWR_CON (0x10006000+0x350) */
+#define DIS_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define DIS_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define DIS_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define DIS_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define DIS_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define DIS_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_DIS_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* AUDIO_PWR_CON (0x10006000+0x354) */
+#define AUDIO_PWR_RST_B_LSB                 (1U << 0)       /* 1b */
+#define AUDIO_PWR_ISO_LSB                   (1U << 1)       /* 1b */
+#define AUDIO_PWR_ON_LSB                    (1U << 2)       /* 1b */
+#define AUDIO_PWR_ON_2ND_LSB                (1U << 3)       /* 1b */
+#define AUDIO_PWR_CLK_DIS_LSB               (1U << 4)       /* 1b */
+#define AUDIO_SRAM_PDN_LSB                  (1U << 8)       /* 1b */
+#define SC_AUDIO_SRAM_PDN_ACK_LSB           (1U << 12)      /* 1b */
+/* ADSP_PWR_CON (0x10006000+0x358) */
+#define ADSP_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define ADSP_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define ADSP_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define ADSP_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define ADSP_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define ADSP_SRAM_CKISO_LSB                 (1U << 5)       /* 1b */
+#define ADSP_SRAM_ISOINT_B_LSB              (1U << 6)       /* 1b */
+#define ADSP_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define ADSP_SRAM_SLEEP_B_LSB               (1U << 9)       /* 1b */
+#define SC_ADSP_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+#define SC_ADSP_SRAM_SLEEP_B_ACK_LSB        (1U << 13)      /* 1b */
+/* CAM_PWR_CON (0x10006000+0x35C) */
+#define CAM_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define CAM_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define CAM_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define CAM_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define CAM_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define CAM_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_CAM_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* CAM_RAWA_PWR_CON (0x10006000+0x360) */
+#define CAM_RAWA_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWA_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWA_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWA_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWA_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWA_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWA_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* CAM_RAWB_PWR_CON (0x10006000+0x364) */
+#define CAM_RAWB_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWB_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWB_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWB_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWB_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWB_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWB_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* CAM_RAWC_PWR_CON (0x10006000+0x368) */
+#define CAM_RAWC_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWC_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWC_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWC_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWC_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWC_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWC_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* SYSRAM_CON (0x10006000+0x36C) */
+#define SYSRAM_SRAM_CKISO_LSB               (1U << 0)       /* 1b */
+#define SYSRAM_SRAM_ISOINT_B_LSB            (1U << 1)       /* 1b */
+#define SYSRAM_SRAM_SLEEP_B_LSB             (1U << 4)       /* 4b */
+#define SYSRAM_SRAM_PDN_LSB                 (1U << 16)      /* 4b */
+/* SYSROM_CON (0x10006000+0x370) */
+#define SYSROM_SRAM_PDN_LSB                 (1U << 0)       /* 6b */
+/* SSPM_SRAM_CON (0x10006000+0x374) */
+#define SSPM_SRAM_CKISO_LSB                 (1U << 0)       /* 1b */
+#define SSPM_SRAM_ISOINT_B_LSB              (1U << 1)       /* 1b */
+#define SSPM_SRAM_SLEEP_B_LSB               (1U << 4)       /* 1b */
+#define SSPM_SRAM_PDN_LSB                   (1U << 16)      /* 1b */
+/* SCP_SRAM_CON (0x10006000+0x378) */
+#define SCP_SRAM_CKISO_LSB                  (1U << 0)       /* 1b */
+#define SCP_SRAM_ISOINT_B_LSB               (1U << 1)       /* 1b */
+#define SCP_SRAM_SLEEP_B_LSB                (1U << 4)       /* 1b */
+#define SCP_SRAM_PDN_LSB                    (1U << 16)      /* 1b */
+/* DPY_SHU_SRAM_CON (0x10006000+0x37C) */
+#define DPY_SHU_SRAM_CKISO_LSB              (1U << 0)       /* 1b */
+#define DPY_SHU_SRAM_ISOINT_B_LSB           (1U << 1)       /* 1b */
+#define DPY_SHU_SRAM_SLEEP_B_LSB            (1U << 4)       /* 2b */
+#define DPY_SHU_SRAM_PDN_LSB                (1U << 16)      /* 2b */
+/* UFS_SRAM_CON (0x10006000+0x380) */
+#define UFS_SRAM_CKISO_LSB                  (1U << 0)       /* 1b */
+#define UFS_SRAM_ISOINT_B_LSB               (1U << 1)       /* 1b */
+#define UFS_SRAM_SLEEP_B_LSB                (1U << 4)       /* 5b */
+#define UFS_SRAM_PDN_LSB                    (1U << 16)      /* 5b */
+/* DEVAPC_IFR_SRAM_CON (0x10006000+0x384) */
+#define DEVAPC_IFR_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DEVAPC_IFR_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DEVAPC_IFR_SRAM_SLEEP_B_LSB         (1U << 4)       /* 6b */
+#define DEVAPC_IFR_SRAM_PDN_LSB             (1U << 16)      /* 6b */
+/* DEVAPC_SUBIFR_SRAM_CON (0x10006000+0x388) */
+#define DEVAPC_SUBIFR_SRAM_CKISO_LSB        (1U << 0)       /* 1b */
+#define DEVAPC_SUBIFR_SRAM_ISOINT_B_LSB     (1U << 1)       /* 1b */
+#define DEVAPC_SUBIFR_SRAM_SLEEP_B_LSB      (1U << 4)       /* 6b */
+#define DEVAPC_SUBIFR_SRAM_PDN_LSB          (1U << 16)      /* 6b */
+/* DEVAPC_ACP_SRAM_CON (0x10006000+0x38C) */
+#define DEVAPC_ACP_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DEVAPC_ACP_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DEVAPC_ACP_SRAM_SLEEP_B_LSB         (1U << 4)       /* 6b */
+#define DEVAPC_ACP_SRAM_PDN_LSB             (1U << 16)      /* 6b */
+/* USB_SRAM_CON (0x10006000+0x390) */
+#define USB_SRAM_PDN_LSB                    (1U << 0)       /* 7b */
+/* DUMMY_SRAM_CON (0x10006000+0x394) */
+#define DUMMY_SRAM_CKISO_LSB                (1U << 0)       /* 1b */
+#define DUMMY_SRAM_ISOINT_B_LSB             (1U << 1)       /* 1b */
+#define DUMMY_SRAM_SLEEP_B_LSB              (1U << 4)       /* 8b */
+#define DUMMY_SRAM_PDN_LSB                  (1U << 16)      /* 8b */
+/* MD_EXT_BUCK_ISO_CON (0x10006000+0x398) */
+#define VMODEM_EXT_BUCK_ISO_LSB             (1U << 0)       /* 1b */
+#define VMD_EXT_BUCK_ISO_LSB                (1U << 1)       /* 1b */
+/* EXT_BUCK_ISO (0x10006000+0x39C) */
+#define VIMVO_EXT_BUCK_ISO_LSB              (1U << 0)       /* 1b */
+#define GPU_EXT_BUCK_ISO_LSB                (1U << 1)       /* 1b */
+#define ADSP_EXT_BUCK_ISO_LSB               (1U << 2)       /* 1b */
+#define IPU_EXT_BUCK_ISO_LSB                (1U << 5)       /* 3b */
+/* DXCC_SRAM_CON (0x10006000+0x3A0) */
+#define DXCC_SRAM_CKISO_LSB                 (1U << 0)       /* 1b */
+#define DXCC_SRAM_ISOINT_B_LSB              (1U << 1)       /* 1b */
+#define DXCC_SRAM_SLEEP_B_LSB               (1U << 4)       /* 1b */
+#define DXCC_SRAM_PDN_LSB                   (1U << 16)      /* 1b */
+/* MSDC_SRAM_CON (0x10006000+0x3A4) */
+#define MSDC_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MSDC_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MSDC_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MSDC_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MSDC_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MSDC_SRAM_CKISO_LSB                 (1U << 5)       /* 1b */
+#define MSDC_SRAM_ISOINT_B_LSB              (1U << 6)       /* 1b */
+#define MSDC_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define MSDC_SRAM_SLEEP_B_LSB               (1U << 9)       /* 1b */
+#define SC_MSDC_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+#define SC_MSDC_SRAM_SLEEP_B_ACK_LSB        (1U << 13)      /* 1b */
+/* DEBUGTOP_SRAM_CON (0x10006000+0x3A8) */
+#define DEBUGTOP_SRAM_PDN_LSB               (1U << 0)       /* 1b */
+/* DP_TX_PWR_CON (0x10006000+0x3AC) */
+#define DP_TX_PWR_RST_B_LSB                 (1U << 0)       /* 1b */
+#define DP_TX_PWR_ISO_LSB                   (1U << 1)       /* 1b */
+#define DP_TX_PWR_ON_LSB                    (1U << 2)       /* 1b */
+#define DP_TX_PWR_ON_2ND_LSB                (1U << 3)       /* 1b */
+#define DP_TX_PWR_CLK_DIS_LSB               (1U << 4)       /* 1b */
+#define DP_TX_SRAM_PDN_LSB                  (1U << 8)       /* 1b */
+#define SC_DP_TX_SRAM_PDN_ACK_LSB           (1U << 12)      /* 1b */
+/* DPMAIF_SRAM_CON (0x10006000+0x3B0) */
+#define DPMAIF_SRAM_CKISO_LSB               (1U << 0)       /* 1b */
+#define DPMAIF_SRAM_ISOINT_B_LSB            (1U << 1)       /* 1b */
+#define DPMAIF_SRAM_SLEEP_B_LSB             (1U << 4)       /* 1b */
+#define DPMAIF_SRAM_PDN_LSB                 (1U << 16)      /* 1b */
+/* DPY_SHU2_SRAM_CON (0x10006000+0x3B4) */
+#define DPY_SHU2_SRAM_CKISO_LSB             (1U << 0)       /* 1b */
+#define DPY_SHU2_SRAM_ISOINT_B_LSB          (1U << 1)       /* 1b */
+#define DPY_SHU2_SRAM_SLEEP_B_LSB           (1U << 4)       /* 2b */
+#define DPY_SHU2_SRAM_PDN_LSB               (1U << 16)      /* 2b */
+/* DRAMC_MCU2_SRAM_CON (0x10006000+0x3B8) */
+#define DRAMC_MCU2_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DRAMC_MCU2_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DRAMC_MCU2_SRAM_SLEEP_B_LSB         (1U << 4)       /* 1b */
+#define DRAMC_MCU2_SRAM_PDN_LSB             (1U << 16)      /* 1b */
+/* DRAMC_MCU_SRAM_CON (0x10006000+0x3BC) */
+#define DRAMC_MCU_SRAM_CKISO_LSB            (1U << 0)       /* 1b */
+#define DRAMC_MCU_SRAM_ISOINT_B_LSB         (1U << 1)       /* 1b */
+#define DRAMC_MCU_SRAM_SLEEP_B_LSB          (1U << 4)       /* 1b */
+#define DRAMC_MCU_SRAM_PDN_LSB              (1U << 16)      /* 1b */
+/* MCUPM_SRAM_CON (0x10006000+0x3C0) */
+#define MCUPM_PWR_RST_B_LSB                 (1U << 0)       /* 1b */
+#define MCUPM_PWR_ISO_LSB                   (1U << 1)       /* 1b */
+#define MCUPM_PWR_ON_LSB                    (1U << 2)       /* 1b */
+#define MCUPM_PWR_ON_2ND_LSB                (1U << 3)       /* 1b */
+#define MCUPM_PWR_CLK_DIS_LSB               (1U << 4)       /* 1b */
+#define MCUPM_SRAM_CKISO_LSB                (1U << 5)       /* 1b */
+#define MCUPM_SRAM_ISOINT_B_LSB             (1U << 6)       /* 1b */
+#define MCUPM_SRAM_PDN_LSB                  (1U << 8)       /* 1b */
+#define MCUPM_SRAM_SLEEP_B_LSB              (1U << 9)       /* 1b */
+#define SC_MCUPM_SRAM_PDN_ACK_LSB           (1U << 12)      /* 1b */
+#define SC_MCUPM_SRAM_SLEEP_B_ACK_LSB       (1U << 13)      /* 1b */
+/* DPY2_PWR_CON (0x10006000+0x3C4) */
+#define DPY2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define DPY2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define DPY2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define DPY2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define DPY2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define DPY2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_DPY2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* PERI_PWR_CON (0x10006000+0x3C8) */
+#define PERI_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define PERI_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define PERI_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define PERI_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define PERI_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define PERI_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_PERI_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* SPM_MEM_CK_SEL (0x10006000+0x400) */
+#define SC_MEM_CK_SEL_LSB                   (1U << 0)       /* 1b */
+#define SPM2CKSYS_MEM_CK_MUX_UPDATE_LSB     (1U << 1)       /* 1b */
+/* SPM_BUS_PROTECT_MASK_B (0x10006000+0X404) */
+#define SPM_BUS_PROTECT_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT1_MASK_B (0x10006000+0x408) */
+#define SPM_BUS_PROTECT1_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT2_MASK_B (0x10006000+0x40C) */
+#define SPM_BUS_PROTECT2_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT3_MASK_B (0x10006000+0x410) */
+#define SPM_BUS_PROTECT3_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT4_MASK_B (0x10006000+0x414) */
+#define SPM_BUS_PROTECT4_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_EMI_BW_MODE (0x10006000+0x418) */
+#define EMI_BW_MODE_LSB                     (1U << 0)       /* 1b */
+#define EMI_BOOST_MODE_LSB                  (1U << 1)       /* 1b */
+#define EMI_BW_MODE_2_LSB                   (1U << 2)       /* 1b */
+#define EMI_BOOST_MODE_2_LSB                (1U << 3)       /* 1b */
+/* AP2MD_PEER_WAKEUP (0x10006000+0x41C) */
+#define AP2MD_PEER_WAKEUP_LSB               (1U << 0)       /* 1b */
+/* ULPOSC_CON (0x10006000+0x420) */
+#define ULPOSC_EN_LSB                       (1U << 0)       /* 1b */
+#define ULPOSC_RST_LSB                      (1U << 1)       /* 1b */
+#define ULPOSC_CG_EN_LSB                    (1U << 2)       /* 1b */
+#define ULPOSC_CLK_SEL_LSB                  (1U << 3)       /* 1b */
+/* SPM2MM_CON (0x10006000+0x424) */
+#define SPM2MM_FORCE_ULTRA_LSB              (1U << 0)       /* 1b */
+#define SPM2MM_DBL_OSTD_ACT_LSB             (1U << 1)       /* 1b */
+#define SPM2MM_ULTRAREQ_LSB                 (1U << 2)       /* 1b */
+#define SPM2MD_ULTRAREQ_LSB                 (1U << 3)       /* 1b */
+#define SPM2ISP_ULTRAREQ_LSB                (1U << 4)       /* 1b */
+#define MM2SPM_FORCE_ULTRA_ACK_D2T_LSB      (1U << 16)      /* 1b */
+#define MM2SPM_DBL_OSTD_ACT_ACK_D2T_LSB     (1U << 17)      /* 1b */
+#define SPM2ISP_ULTRAACK_D2T_LSB            (1U << 18)      /* 1b */
+#define SPM2MM_ULTRAACK_D2T_LSB             (1U << 19)      /* 1b */
+#define SPM2MD_ULTRAACK_D2T_LSB             (1U << 20)      /* 1b */
+/* SPM_BUS_PROTECT5_MASK_B (0x10006000+0x428) */
+#define SPM_BUS_PROTECT5_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM2MCUPM_CON (0x10006000+0x42C) */
+#define SPM2MCUPM_SW_RST_B_LSB              (1U << 0)       /* 1b */
+#define SPM2MCUPM_SW_INT_LSB                (1U << 1)       /* 1b */
+/* AP_MDSRC_REQ (0x10006000+0x430) */
+#define AP_MDSMSRC_REQ_LSB                  (1U << 0)       /* 1b */
+#define AP_L1SMSRC_REQ_LSB                  (1U << 1)       /* 1b */
+#define AP_MD2SRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define AP_MDSMSRC_ACK_LSB                  (1U << 4)       /* 1b */
+#define AP_L1SMSRC_ACK_LSB                  (1U << 5)       /* 1b */
+#define AP_MD2SRC_ACK_LSB                   (1U << 6)       /* 1b */
+/* SPM2EMI_ENTER_ULPM (0x10006000+0x434) */
+#define SPM2EMI_ENTER_ULPM_LSB              (1U << 0)       /* 1b */
+/* SPM2MD_DVFS_CON (0x10006000+0x438) */
+#define SPM2MD_DVFS_CON_LSB                 (1U << 0)       /* 32b */
+/* MD2SPM_DVFS_CON (0x10006000+0x43C) */
+#define MD2SPM_DVFS_CON_LSB                 (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT6_MASK_B (0x10006000+0X440) */
+#define SPM_BUS_PROTECT6_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT7_MASK_B (0x10006000+0x444) */
+#define SPM_BUS_PROTECT7_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT8_MASK_B (0x10006000+0x448) */
+#define SPM_BUS_PROTECT8_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_PLL_CON (0x10006000+0x44C) */
+#define SC_MAINPLLOUT_OFF_LSB               (1U << 0)       /* 1b */
+#define SC_UNIPLLOUT_OFF_LSB                (1U << 1)       /* 1b */
+#define SC_MAINPLL_OFF_LSB                  (1U << 4)       /* 1b */
+#define SC_UNIPLL_OFF_LSB                   (1U << 5)       /* 1b */
+#define SC_MAINPLL_S_OFF_LSB                (1U << 8)       /* 1b */
+#define SC_UNIPLL_S_OFF_LSB                 (1U << 9)       /* 1b */
+#define SC_SMI_CK_OFF_LSB                   (1U << 16)      /* 1b */
+#define SC_MD32K_CK_OFF_LSB                 (1U << 17)      /* 1b */
+#define SC_CKSQ1_OFF_LSB                    (1U << 18)      /* 1b */
+#define SC_AXI_MEM_CK_OFF_LSB               (1U << 19)      /* 1b */
+/* CPU_DVFS_REQ (0x10006000+0x450) */
+#define CPU_DVFS_REQ_LSB                    (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_0 (0x10006000+0x454) */
+#define SW_DDR_PST_REQ_LSB                  (1U << 0)       /* 2b */
+#define SW_DDR_PST_ABORT_REQ_LSB            (1U << 2)       /* 2b */
+/* SPM_DRAM_MCU_SW_CON_1 (0x10006000+0x458) */
+#define SW_DDR_PST_CH0_LSB                  (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_2 (0x10006000+0x45C) */
+#define SW_DDR_PST_CH1_LSB                  (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_3 (0x10006000+0x460) */
+#define SW_DDR_RESERVED_CH0_LSB             (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_4 (0x10006000+0x464) */
+#define SW_DDR_RESERVED_CH1_LSB             (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_STA_0 (0x10006000+0x468) */
+#define SC_DDR_PST_ACK_LSB                  (1U << 0)       /* 2b */
+#define SC_DDR_PST_ABORT_ACK_LSB            (1U << 2)       /* 2b */
+/* SPM_DRAM_MCU_STA_1 (0x10006000+0x46C) */
+#define SC_DDR_CUR_PST_STA_CH0_LSB          (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_STA_2 (0x10006000+0x470) */
+#define SC_DDR_CUR_PST_STA_CH1_LSB          (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_SEL_0 (0x10006000+0x474) */
+#define SW_DDR_PST_REQ_SEL_LSB              (1U << 0)       /* 2b */
+#define SW_DDR_PST_SEL_LSB                  (1U << 2)       /* 2b */
+#define SW_DDR_PST_ABORT_REQ_SEL_LSB        (1U << 4)       /* 2b */
+#define SW_DDR_RESERVED_SEL_LSB             (1U << 6)       /* 2b */
+#define SW_DDR_PST_ACK_SEL_LSB              (1U << 8)       /* 2b */
+#define SW_DDR_PST_ABORT_ACK_SEL_LSB        (1U << 10)      /* 2b */
+/* RELAY_DVFS_LEVEL (0x10006000+0x478) */
+#define RELAY_DVFS_LEVEL_LSB                (1U << 0)       /* 32b */
+/* DRAMC_DPY_CLK_SW_CON_0 (0x10006000+0x480) */
+#define SW_PHYPLL_EN_LSB                    (1U << 0)       /* 2b */
+#define SW_DPY_VREF_EN_LSB                  (1U << 2)       /* 2b */
+#define SW_DPY_DLL_CK_EN_LSB                (1U << 4)       /* 2b */
+#define SW_DPY_DLL_EN_LSB                   (1U << 6)       /* 2b */
+#define SW_DPY_2ND_DLL_EN_LSB               (1U << 8)       /* 2b */
+#define SW_MEM_CK_OFF_LSB                   (1U << 10)      /* 2b */
+#define SW_DMSUS_OFF_LSB                    (1U << 12)      /* 2b */
+#define SW_DPY_MODE_SW_LSB                  (1U << 14)      /* 2b */
+#define SW_EMI_CLK_OFF_LSB                  (1U << 16)      /* 2b */
+#define SW_DDRPHY_FB_CK_EN_LSB              (1U << 18)      /* 2b */
+#define SW_DR_GATE_RETRY_EN_LSB             (1U << 20)      /* 2b */
+#define SW_DPHY_PRECAL_UP_LSB               (1U << 24)      /* 2b */
+#define SW_DPY_BCLK_ENABLE_LSB              (1U << 26)      /* 2b */
+#define SW_TX_TRACKING_DIS_LSB              (1U << 28)      /* 2b */
+#define SW_DPHY_RXDLY_TRACKING_EN_LSB       (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_CON_1 (0x10006000+0x484) */
+#define SW_SHU_RESTORE_LSB                  (1U << 0)       /* 2b */
+#define SW_DMYRD_MOD_LSB                    (1U << 2)       /* 2b */
+#define SW_DMYRD_INTV_LSB                   (1U << 4)       /* 2b */
+#define SW_DMYRD_EN_LSB                     (1U << 6)       /* 2b */
+#define SW_DRS_DIS_REQ_LSB                  (1U << 8)       /* 2b */
+#define SW_DR_SRAM_LOAD_LSB                 (1U << 10)      /* 2b */
+#define SW_DR_SRAM_RESTORE_LSB              (1U << 12)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_LATCH_LSB      (1U << 14)      /* 2b */
+#define SW_TX_TRACK_RETRY_EN_LSB            (1U << 16)      /* 2b */
+#define SW_DPY_MIDPI_EN_LSB                 (1U << 18)      /* 2b */
+#define SW_DPY_PI_RESETB_EN_LSB             (1U << 20)      /* 2b */
+#define SW_DPY_MCK8X_EN_LSB                 (1U << 22)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_CH0_LSB        (1U << 24)      /* 4b */
+#define SW_DR_SHU_LEVEL_SRAM_CH1_LSB        (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SW_CON_2 (0x10006000+0x488) */
+#define SW_DR_SHU_LEVEL_LSB                 (1U << 0)       /* 2b */
+#define SW_DR_SHU_EN_LSB                    (1U << 2)       /* 1b */
+#define SW_DR_SHORT_QUEUE_LSB               (1U << 3)       /* 1b */
+#define SW_PHYPLL_MODE_SW_LSB               (1U << 4)       /* 1b */
+#define SW_PHYPLL2_MODE_SW_LSB              (1U << 5)       /* 1b */
+#define SW_PHYPLL_SHU_EN_LSB                (1U << 6)       /* 1b */
+#define SW_PHYPLL2_SHU_EN_LSB               (1U << 7)       /* 1b */
+#define SW_DR_RESERVED_0_LSB                (1U << 24)      /* 2b */
+#define SW_DR_RESERVED_1_LSB                (1U << 26)      /* 2b */
+#define SW_DR_RESERVED_2_LSB                (1U << 28)      /* 2b */
+#define SW_DR_RESERVED_3_LSB                (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_CON_3 (0x10006000+0x48C) */
+#define SC_DR_SHU_EN_ACK_LSB                (1U << 0)       /* 4b */
+#define SC_EMI_CLK_OFF_ACK_LSB              (1U << 4)       /* 4b */
+#define SC_DR_SHORT_QUEUE_ACK_LSB           (1U << 8)       /* 4b */
+#define SC_DRAMC_DFS_STA_LSB                (1U << 12)      /* 4b */
+#define SC_DRS_DIS_ACK_LSB                  (1U << 16)      /* 4b */
+#define SC_DR_SRAM_LOAD_ACK_LSB             (1U << 20)      /* 4b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_LSB         (1U << 24)      /* 4b */
+#define SC_DR_SRAM_RESTORE_ACK_LSB          (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SW_SEL_0 (0x10006000+0x490) */
+#define SW_PHYPLL_EN_SEL_LSB                (1U << 0)       /* 2b */
+#define SW_DPY_VREF_EN_SEL_LSB              (1U << 2)       /* 2b */
+#define SW_DPY_DLL_CK_EN_SEL_LSB            (1U << 4)       /* 2b */
+#define SW_DPY_DLL_EN_SEL_LSB               (1U << 6)       /* 2b */
+#define SW_DPY_2ND_DLL_EN_SEL_LSB           (1U << 8)       /* 2b */
+#define SW_MEM_CK_OFF_SEL_LSB               (1U << 10)      /* 2b */
+#define SW_DMSUS_OFF_SEL_LSB                (1U << 12)      /* 2b */
+#define SW_DPY_MODE_SW_SEL_LSB              (1U << 14)      /* 2b */
+#define SW_EMI_CLK_OFF_SEL_LSB              (1U << 16)      /* 2b */
+#define SW_DDRPHY_FB_CK_EN_SEL_LSB          (1U << 18)      /* 2b */
+#define SW_DR_GATE_RETRY_EN_SEL_LSB         (1U << 20)      /* 2b */
+#define SW_DPHY_PRECAL_UP_SEL_LSB           (1U << 24)      /* 2b */
+#define SW_DPY_BCLK_ENABLE_SEL_LSB          (1U << 26)      /* 2b */
+#define SW_TX_TRACKING_DIS_SEL_LSB          (1U << 28)      /* 2b */
+#define SW_DPHY_RXDLY_TRACKING_EN_SEL_LSB   (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_1 (0x10006000+0x494) */
+#define SW_SHU_RESTORE_SEL_LSB              (1U << 0)       /* 2b */
+#define SW_DMYRD_MOD_SEL_LSB                (1U << 2)       /* 2b */
+#define SW_DMYRD_INTV_SEL_LSB               (1U << 4)       /* 2b */
+#define SW_DMYRD_EN_SEL_LSB                 (1U << 6)       /* 2b */
+#define SW_DRS_DIS_REQ_SEL_LSB              (1U << 8)       /* 2b */
+#define SW_DR_SRAM_LOAD_SEL_LSB             (1U << 10)      /* 2b */
+#define SW_DR_SRAM_RESTORE_SEL_LSB          (1U << 12)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_LATCH_SEL_LSB  (1U << 14)      /* 2b */
+#define SW_TX_TRACK_RETRY_EN_SEL_LSB        (1U << 16)      /* 2b */
+#define SW_DPY_MIDPI_EN_SEL_LSB             (1U << 18)      /* 2b */
+#define SW_DPY_PI_RESETB_EN_SEL_LSB         (1U << 20)      /* 2b */
+#define SW_DPY_MCK8X_EN_SEL_LSB             (1U << 22)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_SEL_LSB        (1U << 24)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_2 (0x10006000+0x498) */
+#define SW_DR_SHU_LEVEL_SEL_LSB             (1U << 0)       /* 1b */
+#define SW_DR_SHU_EN_SEL_LSB                (1U << 2)       /* 1b */
+#define SW_DR_SHORT_QUEUE_SEL_LSB           (1U << 3)       /* 1b */
+#define SW_PHYPLL_MODE_SW_SEL_LSB           (1U << 4)       /* 1b */
+#define SW_PHYPLL2_MODE_SW_SEL_LSB          (1U << 5)       /* 1b */
+#define SW_PHYPLL_SHU_EN_SEL_LSB            (1U << 6)       /* 1b */
+#define SW_PHYPLL2_SHU_EN_SEL_LSB           (1U << 7)       /* 1b */
+#define SW_DR_RESERVED_0_SEL_LSB            (1U << 24)      /* 2b */
+#define SW_DR_RESERVED_1_SEL_LSB            (1U << 26)      /* 2b */
+#define SW_DR_RESERVED_2_SEL_LSB            (1U << 28)      /* 2b */
+#define SW_DR_RESERVED_3_SEL_LSB            (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_3 (0x10006000+0x49C) */
+#define SC_DR_SHU_EN_ACK_SEL_LSB            (1U << 0)       /* 4b */
+#define SC_EMI_CLK_OFF_ACK_SEL_LSB          (1U << 4)       /* 4b */
+#define SC_DR_SHORT_QUEUE_ACK_SEL_LSB       (1U << 8)       /* 4b */
+#define SC_DRAMC_DFS_STA_SEL_LSB            (1U << 12)      /* 4b */
+#define SC_DRS_DIS_ACK_SEL_LSB              (1U << 16)      /* 4b */
+#define SC_DR_SRAM_LOAD_ACK_SEL_LSB         (1U << 20)      /* 4b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_SEL_LSB     (1U << 24)      /* 4b */
+#define SC_DR_SRAM_RESTORE_ACK_SEL_LSB      (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SPM_CON (0x10006000+0x4A0) */
+#define SC_DMYRD_EN_MOD_SEL_PCM_LSB         (1U << 0)       /* 1b */
+#define SC_DMYRD_INTV_SEL_PCM_LSB           (1U << 1)       /* 1b */
+#define SC_DMYRD_EN_PCM_LSB                 (1U << 2)       /* 1b */
+#define SC_DRS_DIS_REQ_PCM_LSB              (1U << 3)       /* 1b */
+#define SC_DR_SHU_LEVEL_SRAM_PCM_LSB        (1U << 4)       /* 4b */
+#define SC_DR_GATE_RETRY_EN_PCM_LSB         (1U << 8)       /* 1b */
+#define SC_DR_SHORT_QUEUE_PCM_LSB           (1U << 9)       /* 1b */
+#define SC_DPY_MIDPI_EN_PCM_LSB             (1U << 10)      /* 1b */
+#define SC_DPY_PI_RESETB_EN_PCM_LSB         (1U << 11)      /* 1b */
+#define SC_DPY_MCK8X_EN_PCM_LSB             (1U << 12)      /* 1b */
+#define SC_DR_RESERVED_0_PCM_LSB            (1U << 13)      /* 1b */
+#define SC_DR_RESERVED_1_PCM_LSB            (1U << 14)      /* 1b */
+#define SC_DR_RESERVED_2_PCM_LSB            (1U << 15)      /* 1b */
+#define SC_DR_RESERVED_3_PCM_LSB            (1U << 16)      /* 1b */
+#define SC_DMDRAMCSHU_ACK_ALL_LSB           (1U << 24)      /* 1b */
+#define SC_EMI_CLK_OFF_ACK_ALL_LSB          (1U << 25)      /* 1b */
+#define SC_DR_SHORT_QUEUE_ACK_ALL_LSB       (1U << 26)      /* 1b */
+#define SC_DRAMC_DFS_STA_ALL_LSB            (1U << 27)      /* 1b */
+#define SC_DRS_DIS_ACK_ALL_LSB              (1U << 28)      /* 1b */
+#define SC_DR_SRAM_LOAD_ACK_ALL_LSB         (1U << 29)      /* 1b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_ALL_LSB     (1U << 30)      /* 1b */
+#define SC_DR_SRAM_RESTORE_ACK_ALL_LSB      (1U << 31)      /* 1b */
+/* SPM_DVFS_LEVEL (0x10006000+0x4A4) */
+#define SPM_DVFS_LEVEL_LSB                  (1U << 0)       /* 32b */
+/* SPM_CIRQ_CON (0x10006000+0x4A8) */
+#define CIRQ_CLK_SEL_LSB                    (1U << 0)       /* 1b */
+/* SPM_DVFS_MISC (0x10006000+0x4AC) */
+#define MSDC_DVFS_REQUEST_LSB               (1U << 0)       /* 1b */
+#define SPM2EMI_SLP_PROT_EN_LSB             (1U << 1)       /* 1b */
+#define SPM_DVFS_FORCE_ENABLE_LSB           (1U << 2)       /* 1b */
+#define FORCE_DVFS_WAKE_LSB                 (1U << 3)       /* 1b */
+#define SPM_DVFSRC_ENABLE_LSB               (1U << 4)       /* 1b */
+#define SPM_DVFS_DONE_LSB                   (1U << 5)       /* 1b */
+#define DVFSRC_IRQ_WAKEUP_EVENT_MASK_LSB    (1U << 6)       /* 1b */
+#define SPM2RC_EVENT_ABORT_LSB              (1U << 7)       /* 1b */
+#define EMI_SLP_IDLE_LSB                    (1U << 14)      /* 1b */
+#define SDIO_READY_TO_SPM_LSB               (1U << 15)      /* 1b */
+/* SPM_VS1_VS2_RC_CON (0x10006000+0x4B0) */
+#define VS1_INIT_LEVEL_LSB                  (1U << 0)       /* 2b */
+#define VS1_INIT_LSB                        (1U << 2)       /* 1b */
+#define VS1_CURR_LEVEL_LSB                  (1U << 3)       /* 2b */
+#define VS1_NEXT_LEVEL_LSB                  (1U << 5)       /* 2b */
+#define VS1_VOTE_LEVEL_LSB                  (1U << 7)       /* 2b */
+#define VS1_TRIGGER_LSB                     (1U << 9)       /* 1b */
+#define VS2_INIT_LEVEL_LSB                  (1U << 10)      /* 3b */
+#define VS2_INIT_LSB                        (1U << 13)      /* 1b */
+#define VS2_CURR_LEVEL_LSB                  (1U << 14)      /* 3b */
+#define VS2_NEXT_LEVEL_LSB                  (1U << 17)      /* 3b */
+#define VS2_VOTE_LEVEL_LSB                  (1U << 20)      /* 3b */
+#define VS2_TRIGGER_LSB                     (1U << 23)      /* 1b */
+#define VS1_FORCE_LSB                       (1U << 24)      /* 1b */
+#define VS2_FORCE_LSB                       (1U << 25)      /* 1b */
+#define VS1_VOTE_LEVEL_FORCE_LSB            (1U << 26)      /* 2b */
+#define VS2_VOTE_LEVEL_FORCE_LSB            (1U << 28)      /* 3b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_0 (0x10006000+0x4B4) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_1 (0x10006000+0x4B8) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_2 (0x10006000+0x4BC) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_0 (0x10006000+0x4C0) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_1 (0x10006000+0x4C4) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_2 (0x10006000+0x4C8) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_0 (0x10006000+0x4CC) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_1 (0x10006000+0x4D0) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_2 (0x10006000+0x4D4) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_0 (0x10006000+0x4D8) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_1 (0x10006000+0x4DC) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_2 (0x10006000+0x4E0) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_0 (0x10006000+0x4E4) */
+#define PWR_STATUS_MASK_REQ_0_LSB           (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_1 (0x10006000+0x4E8) */
+#define PWR_STATUS_MASK_REQ_1_LSB           (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_2 (0x10006000+0x4EC) */
+#define PWR_STATUS_MASK_REQ_2_LSB           (1U << 0)       /* 32b */
+/* SPM_CG_CHECK_CON (0x10006000+0x4F0) */
+#define APMIXEDSYS_BUSY_MASK_REQ_0_LSB      (1U << 0)       /* 5b */
+#define APMIXEDSYS_BUSY_MASK_REQ_1_LSB      (1U << 8)       /* 5b */
+#define APMIXEDSYS_BUSY_MASK_REQ_2_LSB      (1U << 16)      /* 5b */
+#define AUDIOSYS_BUSY_MASK_REQ_0_LSB        (1U << 24)      /* 1b */
+#define AUDIOSYS_BUSY_MASK_REQ_1_LSB        (1U << 25)      /* 1b */
+#define AUDIOSYS_BUSY_MASK_REQ_2_LSB        (1U << 26)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_0_LSB           (1U << 27)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_1_LSB           (1U << 28)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_2_LSB           (1U << 29)      /* 1b */
+/* SPM_SRC_RDY_STA (0x10006000+0x4F4) */
+#define SPM_INFRA_INTERNAL_ACK_LSB          (1U << 0)       /* 1b */
+#define SPM_VRF18_INTERNAL_ACK_LSB          (1U << 1)       /* 1b */
+/* SPM_DVS_DFS_LEVEL (0x10006000+0x4F8) */
+#define SPM_DFS_LEVEL_LSB                   (1U << 0)       /* 16b */
+#define SPM_DVS_LEVEL_LSB                   (1U << 16)      /* 16b */
+/* SPM_FORCE_DVFS (0x10006000+0x4FC) */
+#define FORCE_DVFS_LEVEL_LSB                (1U << 0)       /* 32b */
+/* SRCLKEN_RC_CFG (0x10006000+0x500) */
+#define SRCLKEN_RC_CFG_LSB                  (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG1 (0x10006000+0x504) */
+#define RC_CENTRAL_CFG1_LSB                 (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG2 (0x10006000+0x508) */
+#define RC_CENTRAL_CFG2_LSB                 (1U << 0)       /* 32b */
+/* RC_CMD_ARB_CFG (0x10006000+0x50C) */
+#define RC_CMD_ARB_CFG_LSB                  (1U << 0)       /* 32b */
+/* RC_PMIC_RCEN_ADDR (0x10006000+0x510) */
+#define RC_PMIC_RCEN_ADDR_LSB               (1U << 0)       /* 16b */
+#define RC_PMIC_RCEN_RESERVE_LSB            (1U << 16)      /* 16b */
+/* RC_PMIC_RCEN_SET_CLR_ADDR (0x10006000+0x514) */
+#define RC_PMIC_RCEN_SET_ADDR_LSB           (1U << 0)       /* 16b */
+#define RC_PMIC_RCEN_CLR_ADDR_LSB           (1U << 16)      /* 16b */
+/* RC_DCXO_FPM_CFG (0x10006000+0x518) */
+#define RC_DCXO_FPM_CFG_LSB                 (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG3 (0x10006000+0x51C) */
+#define RC_CENTRAL_CFG3_LSB                 (1U << 0)       /* 32b */
+/* RC_M00_SRCLKEN_CFG (0x10006000+0x520) */
+#define RC_M00_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+#define RC_SW_SRCLKEN_RC                    (1U << 3)       /* 1b */
+#define RC_SW_SRCLKEN_FPM                   (1U << 4)       /* 1b */
+/* RC_M01_SRCLKEN_CFG (0x10006000+0x524) */
+#define RC_M01_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M02_SRCLKEN_CFG (0x10006000+0x528) */
+#define RC_M02_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M03_SRCLKEN_CFG (0x10006000+0x52C) */
+#define RC_M03_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M04_SRCLKEN_CFG (0x10006000+0x530) */
+#define RC_M04_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M05_SRCLKEN_CFG (0x10006000+0x534) */
+#define RC_M05_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M06_SRCLKEN_CFG (0x10006000+0x538) */
+#define RC_M06_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M07_SRCLKEN_CFG (0x10006000+0x53C) */
+#define RC_M07_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M08_SRCLKEN_CFG (0x10006000+0x540) */
+#define RC_M08_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M09_SRCLKEN_CFG (0x10006000+0x544) */
+#define RC_M09_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M10_SRCLKEN_CFG (0x10006000+0x548) */
+#define RC_M10_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M11_SRCLKEN_CFG (0x10006000+0x54C) */
+#define RC_M11_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M12_SRCLKEN_CFG (0x10006000+0x550) */
+#define RC_M12_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_SRCLKEN_SW_CON_CFG (0x10006000+0x554) */
+#define RC_SRCLKEN_SW_CON_CFG_LSB           (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG4 (0x10006000+0x558) */
+#define RC_CENTRAL_CFG4_LSB                 (1U << 0)       /* 32b */
+/* RC_PROTOCOL_CHK_CFG (0x10006000+0x560) */
+#define RC_PROTOCOL_CHK_CFG_LSB             (1U << 0)       /* 32b */
+/* RC_DEBUG_CFG (0x10006000+0x564) */
+#define RC_DEBUG_CFG_LSB                    (1U << 0)       /* 32b */
+/* RC_MISC_0 (0x10006000+0x5B4) */
+#define SRCCLKENO_LSB                       (1U << 0)       /* 2b */
+#define PCM_SRCCLKENO_LSB                   (1U << 3)       /* 2b */
+#define RC_VREQ_LSB                         (1U << 5)       /* 1b */
+#define RC_SPM_SRCCLKENO_0_ACK_LSB          (1U << 6)       /* 1b */
+/* RC_SPM_CTRL (0x10006000+0x5B8) */
+#define SPM_AP_26M_RDY_LSB                  (1U << 0)       /* 1b */
+#define KEEP_RC_SPI_ACTIVE_LSB              (1U << 1)       /* 1b */
+#define SPM2RC_DMY_CTRL_LSB                 (1U << 2)       /* 6b */
+/* SUBSYS_INTF_CFG (0x10006000+0x5BC) */
+#define SRCLKEN_FPM_MASK_B_LSB              (1U << 0)       /* 13b */
+#define SRCLKEN_BBLPM_MASK_B_LSB            (1U << 16)      /* 13b */
+/* PCM_WDT_LATCH_25 (0x10006000+0x5C0) */
+#define PCM_WDT_LATCH_25_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_26 (0x10006000+0x5C4) */
+#define PCM_WDT_LATCH_26_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_27 (0x10006000+0x5C8) */
+#define PCM_WDT_LATCH_27_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_28 (0x10006000+0x5CC) */
+#define PCM_WDT_LATCH_28_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_29 (0x10006000+0x5D0) */
+#define PCM_WDT_LATCH_29_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_30 (0x10006000+0x5D4) */
+#define PCM_WDT_LATCH_30_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_31 (0x10006000+0x5D8) */
+#define PCM_WDT_LATCH_31_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_32 (0x10006000+0x5DC) */
+#define PCM_WDT_LATCH_32_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_33 (0x10006000+0x5E0) */
+#define PCM_WDT_LATCH_33_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_34 (0x10006000+0x5E4) */
+#define PCM_WDT_LATCH_34_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_35 (0x10006000+0x5EC) */
+#define PCM_WDT_LATCH_35_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_36 (0x10006000+0x5F0) */
+#define PCM_WDT_LATCH_36_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_37 (0x10006000+0x5F4) */
+#define PCM_WDT_LATCH_37_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_38 (0x10006000+0x5F8) */
+#define PCM_WDT_LATCH_38_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_39 (0x10006000+0x5FC) */
+#define PCM_WDT_LATCH_39_LSB                (1U << 0)       /* 32b */
+/* SPM_SW_FLAG_0 (0x10006000+0x600) */
+#define SPM_SW_FLAG_LSB                     (1U << 0)       /* 32b */
+/* SPM_SW_DEBUG_0 (0x10006000+0x604) */
+#define SPM_SW_DEBUG_0_LSB                  (1U << 0)       /* 32b */
+/* SPM_SW_FLAG_1 (0x10006000+0x608) */
+#define SPM_SW_FLAG_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_SW_DEBUG_1 (0x10006000+0x60C) */
+#define SPM_SW_DEBUG_1_LSB                  (1U << 0)       /* 32b */
+/* SPM_SW_RSV_0 (0x10006000+0x610) */
+#define SPM_SW_RSV_0_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_1 (0x10006000+0x614) */
+#define SPM_SW_RSV_1_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_2 (0x10006000+0x618) */
+#define SPM_SW_RSV_2_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_3 (0x10006000+0x61C) */
+#define SPM_SW_RSV_3_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_4 (0x10006000+0x620) */
+#define SPM_SW_RSV_4_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_5 (0x10006000+0x624) */
+#define SPM_SW_RSV_5_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_6 (0x10006000+0x628) */
+#define SPM_SW_RSV_6_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_7 (0x10006000+0x62C) */
+#define SPM_SW_RSV_7_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_8 (0x10006000+0x630) */
+#define SPM_SW_RSV_8_LSB                    (1U << 0)       /* 32b */
+/* SPM_BK_WAKE_EVENT (0x10006000+0x634) */
+#define SPM_BK_WAKE_EVENT_LSB               (1U << 0)       /* 32b */
+/* SPM_BK_VTCXO_DUR (0x10006000+0x638) */
+#define SPM_BK_VTCXO_DUR_LSB                (1U << 0)       /* 32b */
+/* SPM_BK_WAKE_MISC (0x10006000+0x63C) */
+#define SPM_BK_WAKE_MISC_LSB                (1U << 0)       /* 32b */
+/* SPM_BK_PCM_TIMER (0x10006000+0x640) */
+#define SPM_BK_PCM_TIMER_LSB                (1U << 0)       /* 32b */
+/* SPM_RSV_CON_0 (0x10006000+0x650) */
+#define SPM_RSV_CON_0_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_CON_1 (0x10006000+0x654) */
+#define SPM_RSV_CON_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_STA_0 (0x10006000+0x658) */
+#define SPM_RSV_STA_0_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_STA_1 (0x10006000+0x65C) */
+#define SPM_RSV_STA_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_SPARE_CON (0x10006000+0x660) */
+#define SPM_SPARE_CON_LSB                   (1U << 0)       /* 32b */
+/* SPM_SPARE_CON_SET (0x10006000+0x664) */
+#define SPM_SPARE_CON_SET_LSB               (1U << 0)       /* 32b */
+/* SPM_SPARE_CON_CLR (0x10006000+0x668) */
+#define SPM_SPARE_CON_CLR_LSB               (1U << 0)       /* 32b */
+/* SPM_CROSS_WAKE_M00_REQ (0x10006000+0x66C) */
+#define SPM_CROSS_WAKE_M00_REQ_LSB          (1U << 0)       /* 5b */
+#define SPM_CROSS_WAKE_M00_CHK_LSB          (1U << 8)       /* 5b */
+/* SPM_CROSS_WAKE_M01_REQ (0x10006000+0x670) */
+#define SPM_CROSS_WAKE_M01_REQ_LSB          (1U << 0)       /* 5b */
+#define SPM_CROSS_WAKE_M01_CHK_LSB          (1U << 8)       /* 5b */
+/* SPM_CROSS_WAKE_M02_REQ (0x10006000+0x674) */
+#define SPM_CROSS_WAKE_M02_REQ_LSB          (1U << 0)       /* 5b */
+#define SPM_CROSS_WAKE_M02_CHK_LSB          (1U << 8)       /* 5b */
+/* SPM_CROSS_WAKE_M03_REQ (0x10006000+0x678) */
+#define SPM_CROSS_WAKE_M03_REQ_LSB          (1U << 0)       /* 5b */
+#define SPM_CROSS_WAKE_M03_CHK_LSB          (1U << 8)       /* 5b */
+/* SCP_VCORE_LEVEL (0x10006000+0x67C) */
+#define SCP_VCORE_LEVEL_LSB                 (1U << 0)       /* 16b */
+/* SC_MM_CK_SEL_CON (0x10006000+0x680) */
+#define SC_MM_CK_SEL_LSB                    (1U << 0)       /* 4b */
+#define SC_MM_CK_SEL_EN_LSB                 (1U << 4)       /* 1b */
+/* SPARE_ACK_MASK (0x10006000+0x684) */
+#define SPARE_ACK_MASK_B_LSB                (1U << 0)       /* 32b */
+/* SPM_CROSS_WAKE_M04_REQ (0x10006000+0x688) */
+#define SPM_CROSS_WAKE_M04_REQ_LSB          (1U << 0)       /* 5b */
+#define SPM_CROSS_WAKE_M04_CHK_LSB          (1U << 8)       /* 5b */
+/* SPM_DV_CON_0 (0x10006000+0x68C) */
+#define SPM_DV_CON_0_LSB                    (1U << 0)       /* 32b */
+/* SPM_DV_CON_1 (0x10006000+0x690) */
+#define SPM_DV_CON_1_LSB                    (1U << 0)       /* 32b */
+/* SPM_DV_STA (0x10006000+0x694) */
+#define SPM_DV_STA_LSB                      (1U << 0)       /* 32b */
+/* CONN_XOWCN_DEBUG_EN (0x10006000+0x698) */
+#define CONN_XOWCN_DEBUG_EN_LSB             (1U << 0)       /* 1b */
+/* SPM_SEMA_M0 (0x10006000+0x69C) */
+#define SPM_SEMA_M0_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M1 (0x10006000+0x6A0) */
+#define SPM_SEMA_M1_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M2 (0x10006000+0x6A4) */
+#define SPM_SEMA_M2_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M3 (0x10006000+0x6A8) */
+#define SPM_SEMA_M3_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M4 (0x10006000+0x6AC) */
+#define SPM_SEMA_M4_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M5 (0x10006000+0x6B0) */
+#define SPM_SEMA_M5_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M6 (0x10006000+0x6B4) */
+#define SPM_SEMA_M6_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M7 (0x10006000+0x6B8) */
+#define SPM_SEMA_M7_LSB                     (1U << 0)       /* 8b */
+/* SPM2ADSP_MAILBOX (0x10006000+0x6BC) */
+#define SPM2ADSP_MAILBOX_LSB                (1U << 0)       /* 32b */
+/* ADSP2SPM_MAILBOX (0x10006000+0x6C0) */
+#define ADSP2SPM_MAILBOX_LSB                (1U << 0)       /* 32b */
+/* SPM_ADSP_IRQ (0x10006000+0x6C4) */
+#define SC_SPM2ADSP_WAKEUP_LSB              (1U << 0)       /* 1b */
+#define SPM_ADSP_IRQ_SC_ADSP2SPM_WAKEUP_LSB (1U << 4)       /* 1b */
+/* SPM_MD32_IRQ (0x10006000+0x6C8) */
+#define SC_SPM2SSPM_WAKEUP_LSB              (1U << 0)       /* 4b */
+#define SPM_MD32_IRQ_SC_SSPM2SPM_WAKEUP_LSB (1U << 4)       /* 4b */
+/* SPM2PMCU_MAILBOX_0 (0x10006000+0x6CC) */
+#define SPM2PMCU_MAILBOX_0_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_1 (0x10006000+0x6D0) */
+#define SPM2PMCU_MAILBOX_1_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_2 (0x10006000+0x6D4) */
+#define SPM2PMCU_MAILBOX_2_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_3 (0x10006000+0x6D8) */
+#define SPM2PMCU_MAILBOX_3_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_0 (0x10006000+0x6DC) */
+#define PMCU2SPM_MAILBOX_0_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_1 (0x10006000+0x6E0) */
+#define PMCU2SPM_MAILBOX_1_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_2 (0x10006000+0x6E4) */
+#define PMCU2SPM_MAILBOX_2_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_3 (0x10006000+0x6E8) */
+#define PMCU2SPM_MAILBOX_3_LSB              (1U << 0)       /* 32b */
+/* UFS_PSRI_SW (0x10006000+0x6EC) */
+#define UFS_PSRI_SW_LSB                     (1U << 0)       /* 1b */
+/* UFS_PSRI_SW_SET (0x10006000+0x6F0) */
+#define UFS_PSRI_SW_SET_LSB                 (1U << 0)       /* 1b */
+/* UFS_PSRI_SW_CLR (0x10006000+0x6F4) */
+#define UFS_PSRI_SW_CLR_LSB                 (1U << 0)       /* 1b */
+/* SPM_AP_SEMA (0x10006000+0x6F8) */
+#define SPM_AP_SEMA_LSB                     (1U << 0)       /* 1b */
+/* SPM_SPM_SEMA (0x10006000+0x6FC) */
+#define SPM_SPM_SEMA_LSB                    (1U << 0)       /* 1b */
+/* SPM_DVFS_CON (0x10006000+0x700) */
+#define SPM_DVFS_CON_LSB                    (1U << 0)       /* 32b */
+/* SPM_DVFS_CON_STA (0x10006000+0x704) */
+#define SPM_DVFS_CON_STA_LSB                (1U << 0)       /* 32b */
+/* SPM_PMIC_SPMI_CON (0x10006000+0x708) */
+#define SPM_PMIC_SPMI_CMD_LSB               (1U << 0)       /* 2b */
+#define SPM_PMIC_SPMI_SLAVEID_LSB           (1U << 2)       /* 4b */
+#define SPM_PMIC_SPMI_PMIFID_LSB            (1U << 6)       /* 1b */
+#define SPM_PMIC_SPMI_DBCNT_LSB             (1U << 7)       /* 1b */
+/* SPM_DVFS_CMD0 (0x10006000+0x710) */
+#define SPM_DVFS_CMD0_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD1 (0x10006000+0x714) */
+#define SPM_DVFS_CMD1_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD2 (0x10006000+0x718) */
+#define SPM_DVFS_CMD2_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD3 (0x10006000+0x71C) */
+#define SPM_DVFS_CMD3_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD4 (0x10006000+0x720) */
+#define SPM_DVFS_CMD4_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD5 (0x10006000+0x724) */
+#define SPM_DVFS_CMD5_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD6 (0x10006000+0x728) */
+#define SPM_DVFS_CMD6_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD7 (0x10006000+0x72C) */
+#define SPM_DVFS_CMD7_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD8 (0x10006000+0x730) */
+#define SPM_DVFS_CMD8_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD9 (0x10006000+0x734) */
+#define SPM_DVFS_CMD9_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD10 (0x10006000+0x738) */
+#define SPM_DVFS_CMD10_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD11 (0x10006000+0x73C) */
+#define SPM_DVFS_CMD11_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD12 (0x10006000+0x740) */
+#define SPM_DVFS_CMD12_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD13 (0x10006000+0x744) */
+#define SPM_DVFS_CMD13_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD14 (0x10006000+0x748) */
+#define SPM_DVFS_CMD14_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD15 (0x10006000+0x74C) */
+#define SPM_DVFS_CMD15_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD16 (0x10006000+0x750) */
+#define SPM_DVFS_CMD16_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD17 (0x10006000+0x754) */
+#define SPM_DVFS_CMD17_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD18 (0x10006000+0x758) */
+#define SPM_DVFS_CMD18_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD19 (0x10006000+0x75C) */
+#define SPM_DVFS_CMD19_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD20 (0x10006000+0x760) */
+#define SPM_DVFS_CMD20_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD21 (0x10006000+0x764) */
+#define SPM_DVFS_CMD21_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD22 (0x10006000+0x768) */
+#define SPM_DVFS_CMD22_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD23 (0x10006000+0x76C) */
+#define SPM_DVFS_CMD23_LSB                  (1U << 0)       /* 32b */
+/* SYS_TIMER_VALUE_L (0x10006000+0x770) */
+#define SYS_TIMER_VALUE_L_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_VALUE_H (0x10006000+0x774) */
+#define SYS_TIMER_VALUE_H_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_START_L (0x10006000+0x778) */
+#define SYS_TIMER_START_L_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_START_H (0x10006000+0x77C) */
+#define SYS_TIMER_START_H_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_00 (0x10006000+0x780) */
+#define SYS_TIMER_LATCH_L_00_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_00 (0x10006000+0x784) */
+#define SYS_TIMER_LATCH_H_00_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_01 (0x10006000+0x788) */
+#define SYS_TIMER_LATCH_L_01_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_01 (0x10006000+0x78C) */
+#define SYS_TIMER_LATCH_H_01_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_02 (0x10006000+0x790) */
+#define SYS_TIMER_LATCH_L_02_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_02 (0x10006000+0x794) */
+#define SYS_TIMER_LATCH_H_02_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_03 (0x10006000+0x798) */
+#define SYS_TIMER_LATCH_L_03_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_03 (0x10006000+0x79C) */
+#define SYS_TIMER_LATCH_H_03_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_04 (0x10006000+0x7A0) */
+#define SYS_TIMER_LATCH_L_04_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_04 (0x10006000+0x7A4) */
+#define SYS_TIMER_LATCH_H_04_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_05 (0x10006000+0x7A8) */
+#define SYS_TIMER_LATCH_L_05_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_05 (0x10006000+0x7AC) */
+#define SYS_TIMER_LATCH_H_05_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_06 (0x10006000+0x7B0) */
+#define SYS_TIMER_LATCH_L_06_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_06 (0x10006000+0x7B4) */
+#define SYS_TIMER_LATCH_H_06_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_07 (0x10006000+0x7B8) */
+#define SYS_TIMER_LATCH_L_07_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_07 (0x10006000+0x7BC) */
+#define SYS_TIMER_LATCH_H_07_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_08 (0x10006000+0x7C0) */
+#define SYS_TIMER_LATCH_L_08_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_08 (0x10006000+0x7C4) */
+#define SYS_TIMER_LATCH_H_08_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_09 (0x10006000+0x7C8) */
+#define SYS_TIMER_LATCH_L_09_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_09 (0x10006000+0x7CC) */
+#define SYS_TIMER_LATCH_H_09_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_10 (0x10006000+0x7D0) */
+#define SYS_TIMER_LATCH_L_10_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_10 (0x10006000+0x7D4) */
+#define SYS_TIMER_LATCH_H_10_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_11 (0x10006000+0x7D8) */
+#define SYS_TIMER_LATCH_L_11_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_11 (0x10006000+0x7DC) */
+#define SYS_TIMER_LATCH_H_11_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_12 (0x10006000+0x7E0) */
+#define SYS_TIMER_LATCH_L_12_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_12 (0x10006000+0x7E4) */
+#define SYS_TIMER_LATCH_H_12_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_13 (0x10006000+0x7E8) */
+#define SYS_TIMER_LATCH_L_13_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_13 (0x10006000+0x7EC) */
+#define SYS_TIMER_LATCH_H_13_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_14 (0x10006000+0x7F0) */
+#define SYS_TIMER_LATCH_L_14_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_14 (0x10006000+0x7F4) */
+#define SYS_TIMER_LATCH_H_14_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_15 (0x10006000+0x7F8) */
+#define SYS_TIMER_LATCH_L_15_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_15 (0x10006000+0x7FC) */
+#define SYS_TIMER_LATCH_H_15_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_0 (0x10006000+0x800) */
+#define PCM_WDT_LATCH_0_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_1 (0x10006000+0x804) */
+#define PCM_WDT_LATCH_1_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_2 (0x10006000+0x808) */
+#define PCM_WDT_LATCH_2_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_3 (0x10006000+0x80C) */
+#define PCM_WDT_LATCH_3_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_4 (0x10006000+0x810) */
+#define PCM_WDT_LATCH_4_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_5 (0x10006000+0x814) */
+#define PCM_WDT_LATCH_5_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_6 (0x10006000+0x818) */
+#define PCM_WDT_LATCH_6_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_7 (0x10006000+0x81C) */
+#define PCM_WDT_LATCH_7_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_8 (0x10006000+0x820) */
+#define PCM_WDT_LATCH_8_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_9 (0x10006000+0x824) */
+#define PCM_WDT_LATCH_9_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_10 (0x10006000+0x828) */
+#define PCM_WDT_LATCH_10_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_11 (0x10006000+0x82C) */
+#define PCM_WDT_LATCH_11_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_12 (0x10006000+0x830) */
+#define PCM_WDT_LATCH_12_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_13 (0x10006000+0x834) */
+#define PCM_WDT_LATCH_13_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_14 (0x10006000+0x838) */
+#define PCM_WDT_LATCH_14_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_15 (0x10006000+0x83C) */
+#define PCM_WDT_LATCH_15_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_16 (0x10006000+0x840) */
+#define PCM_WDT_LATCH_16_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_17 (0x10006000+0x844) */
+#define PCM_WDT_LATCH_17_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_18 (0x10006000+0x848) */
+#define PCM_WDT_LATCH_18_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_0 (0x10006000+0x84C) */
+#define PCM_WDT_LATCH_SPARE_0_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_1 (0x10006000+0x850) */
+#define PCM_WDT_LATCH_SPARE_1_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_2 (0x10006000+0x854) */
+#define PCM_WDT_LATCH_SPARE_2_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_0 (0x10006000+0x870) */
+#define PCM_WDT_LATCH_CONN_0_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_1 (0x10006000+0x874) */
+#define PCM_WDT_LATCH_CONN_1_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_2 (0x10006000+0x878) */
+#define PCM_WDT_LATCH_CONN_2_LSB            (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_0 (0x10006000+0x8A0) */
+#define DRAMC_GATING_ERR_LATCH_CH0_0_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_1 (0x10006000+0x8A4) */
+#define DRAMC_GATING_ERR_LATCH_CH0_1_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_2 (0x10006000+0x8A8) */
+#define DRAMC_GATING_ERR_LATCH_CH0_2_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_3 (0x10006000+0x8AC) */
+#define DRAMC_GATING_ERR_LATCH_CH0_3_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_4 (0x10006000+0x8B0) */
+#define DRAMC_GATING_ERR_LATCH_CH0_4_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_5 (0x10006000+0x8B4) */
+#define DRAMC_GATING_ERR_LATCH_CH0_5_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_6 (0x10006000+0x8B8) */
+#define DRAMC_GATING_ERR_LATCH_CH0_6_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_SPARE_0 (0x10006000+0x8F4) */
+#define DRAMC_GATING_ERR_LATCH_SPARE_0_LSB  (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_0 (0x10006000+0x900) */
+#define SPM_ACK_CHK_SW_EN_0_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_0_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_0_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_0_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_0_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_0_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_0_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_0_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_0_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_0_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_0_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_0 (0x10006000+0x904) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_0_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_0_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_0 (0x10006000+0x908) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_0_LSB (1U << 0)      /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_0_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_0_LSB (1U << 16)     /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_0_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_0 (0x10006000+0x90C) */
+#define SPM_ACK_CHK_TIMER_VAL_0_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_0_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_0 (0x10006000+0x910) */
+#define SPM_ACK_CHK_STA_0_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_0 (0x10006000+0x914) */
+#define SPM_ACK_CHK_SWINT_EN_0_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_1 (0x10006000+0x920) */
+#define SPM_ACK_CHK_SW_EN_1_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_1_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_1_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_1_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_1_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_1_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_1_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_1_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_1_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_1_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_1_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_1 (0x10006000+0x924) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_1_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_1_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_1 (0x10006000+0x928) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_1_LSB (1U << 0)      /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_1_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_1_LSB (1U << 16)     /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_1_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_1 (0x10006000+0x92C) */
+#define SPM_ACK_CHK_TIMER_VAL_1_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_1_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_1 (0x10006000+0x930) */
+#define SPM_ACK_CHK_STA_1_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_1 (0x10006000+0x934) */
+#define SPM_ACK_CHK_SWINT_EN_1_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_2 (0x10006000+0x940) */
+#define SPM_ACK_CHK_SW_EN_2_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_2_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_2_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_2_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_2_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_2_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_2_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_2_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_2_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_2_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_2_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_2 (0x10006000+0x944) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_2_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_2_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_2 (0x10006000+0x948) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_2_LSB (1U << 0)      /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_2_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_2_LSB (1U << 16)     /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_2_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_2 (0x10006000+0x94C) */
+#define SPM_ACK_CHK_TIMER_VAL_2_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_2_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_2 (0x10006000+0x950) */
+#define SPM_ACK_CHK_STA_2_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_2 (0x10006000+0x954) */
+#define SPM_ACK_CHK_SWINT_EN_2_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_3 (0x10006000+0x960) */
+#define SPM_ACK_CHK_SW_EN_3_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_3_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_3_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_3_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_3_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_3_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_3_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_3_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_3_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_3_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_3_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_3 (0x10006000+0x964) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_3_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_3_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_3 (0x10006000+0x968) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_3_LSB (1U << 0)      /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_3_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_3_LSB (1U << 16)     /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_3_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_3 (0x10006000+0x96C) */
+#define SPM_ACK_CHK_TIMER_VAL_3_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_3_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_3 (0x10006000+0x970) */
+#define SPM_ACK_CHK_STA_3_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_3 (0x10006000+0x974) */
+#define SPM_ACK_CHK_SWINT_EN_3_LSB          (1U << 0)       /* 32b */
+/* SPM_COUNTER_0 (0x10006000+0x978) */
+#define SPM_COUNTER_VAL_0_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_0_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_0_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_0_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_0_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_0_LSB         (1U << 31)      /* 1b */
+/* SPM_COUNTER_1 (0x10006000+0x97C) */
+#define SPM_COUNTER_VAL_1_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_1_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_1_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_1_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_1_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_1_LSB         (1U << 31)      /* 1b */
+/* SPM_COUNTER_2 (0x10006000+0x980) */
+#define SPM_COUNTER_VAL_2_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_2_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_2_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_2_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_2_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_2_LSB         (1U << 31)      /* 1b */
+/* SYS_TIMER_CON (0x10006000+0x98C) */
+#define SYS_TIMER_START_EN_LSB              (1U << 0)       /* 1b */
+#define SYS_TIMER_LATCH_EN_LSB              (1U << 1)       /* 1b */
+#define SYS_TIMER_ID_LSB                    (1U << 8)       /* 8b */
+#define SYS_TIMER_VALID_LSB                 (1U << 31)      /* 1b */
+/* RC_FSM_STA_0 (0x10006000+0xE00) */
+#define RC_FSM_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_CMD_STA_0 (0x10006000+0xE04) */
+#define RC_CMD_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_CMD_STA_1 (0x10006000+0xE08) */
+#define RC_CMD_STA_1_LSB                    (1U << 0)       /* 32b */
+/* RC_SPI_STA_0 (0x10006000+0xE0C) */
+#define RC_SPI_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_PI_PO_STA_0 (0x10006000+0xE10) */
+#define RC_PI_PO_STA_0_LSB                  (1U << 0)       /* 32b */
+/* RC_M00_REQ_STA_0 (0x10006000+0xE14) */
+#define RC_M00_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M01_REQ_STA_0 (0x10006000+0xE1C) */
+#define RC_M01_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M02_REQ_STA_0 (0x10006000+0xE20) */
+#define RC_M02_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M03_REQ_STA_0 (0x10006000+0xE24) */
+#define RC_M03_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M04_REQ_STA_0 (0x10006000+0xE28) */
+#define RC_M04_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M05_REQ_STA_0 (0x10006000+0xE2C) */
+#define RC_M05_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M06_REQ_STA_0 (0x10006000+0xE30) */
+#define RC_M06_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M07_REQ_STA_0 (0x10006000+0xE34) */
+#define RC_M07_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M08_REQ_STA_0 (0x10006000+0xE38) */
+#define RC_M08_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M09_REQ_STA_0 (0x10006000+0xE3C) */
+#define RC_M09_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M10_REQ_STA_0 (0x10006000+0xE40) */
+#define RC_M10_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M11_REQ_STA_0 (0x10006000+0xE44) */
+#define RC_M11_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M12_REQ_STA_0 (0x10006000+0xE48) */
+#define RC_M12_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_DEBUG_STA_0 (0x10006000+0xE4C) */
+#define RC_DEBUG_STA_0_LSB                  (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_0_LSB (0x10006000+0xE50) */
+#define RO_PMRC_TRACE_00_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_0_MSB (0x10006000+0xE54) */
+#define RO_PMRC_TRACE_00_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_1_LSB (0x10006000+0xE5C) */
+#define RO_PMRC_TRACE_01_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_1_MSB (0x10006000+0xE60) */
+#define RO_PMRC_TRACE_01_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_2_LSB (0x10006000+0xE64) */
+#define RO_PMRC_TRACE_02_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_2_MSB (0x10006000+0xE6C) */
+#define RO_PMRC_TRACE_02_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_3_LSB (0x10006000+0xE70) */
+#define RO_PMRC_TRACE_03_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_3_MSB (0x10006000+0xE74) */
+#define RO_PMRC_TRACE_03_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_4_LSB (0x10006000+0xE78) */
+#define RO_PMRC_TRACE_04_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_4_MSB (0x10006000+0xE7C) */
+#define RO_PMRC_TRACE_04_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_5_LSB (0x10006000+0xE80) */
+#define RO_PMRC_TRACE_05_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_5_MSB (0x10006000+0xE84) */
+#define RO_PMRC_TRACE_05_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_6_LSB (0x10006000+0xE88) */
+#define RO_PMRC_TRACE_06_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_6_MSB (0x10006000+0xE8C) */
+#define RO_PMRC_TRACE_06_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_7_LSB (0x10006000+0xE90) */
+#define RO_PMRC_TRACE_07_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_7_MSB (0x10006000+0xE94) */
+#define RO_PMRC_TRACE_07_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_0_LSB (0x10006000+0xE98) */
+#define RC_SYS_TIMER_LATCH_L_00_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_0_MSB (0x10006000+0xE9C) */
+#define RC_SYS_TIMER_LATCH_H_00_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_1_LSB (0x10006000+0xEA0) */
+#define RC_SYS_TIMER_LATCH_L_01_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_1_MSB (0x10006000+0xEA4) */
+#define RC_SYS_TIMER_LATCH_H_01_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_2_LSB (0x10006000+0xEA8) */
+#define RC_SYS_TIMER_LATCH_L_02_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_2_MSB (0x10006000+0xEAC) */
+#define RC_SYS_TIMER_LATCH_H_02_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_3_LSB (0x10006000+0xEB0) */
+#define RC_SYS_TIMER_LATCH_L_03_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_3_MSB (0x10006000+0xEB4) */
+#define RC_SYS_TIMER_LATCH_H_03_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_4_LSB (0x10006000+0xEB8) */
+#define RC_SYS_TIMER_LATCH_L_04_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_4_MSB (0x10006000+0xEBC) */
+#define RC_SYS_TIMER_LATCH_H_04_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_5_LSB (0x10006000+0xEC0) */
+#define RC_SYS_TIMER_LATCH_L_05_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_5_MSB (0x10006000+0xEC4) */
+#define RC_SYS_TIMER_LATCH_H_05_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_6_LSB (0x10006000+0xEC8) */
+#define RC_SYS_TIMER_LATCH_L_06_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_6_MSB (0x10006000+0xECC) */
+#define RC_SYS_TIMER_LATCH_H_06_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_7_LSB (0x10006000+0xED0) */
+#define RC_SYS_TIMER_LATCH_L_07_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_7_MSB (0x10006000+0xED4) */
+#define RC_SYS_TIMER_LATCH_H_07_LSB         (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_19 (0x10006000+0xED8) */
+#define PCM_WDT_LATCH_19_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_20 (0x10006000+0xEDC) */
+#define PCM_WDT_LATCH_20_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_21 (0x10006000+0xEE0) */
+#define PCM_WDT_LATCH_21_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_22 (0x10006000+0xEE4) */
+#define PCM_WDT_LATCH_22_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_23 (0x10006000+0xEE8) */
+#define PCM_WDT_LATCH_23_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_24 (0x10006000+0xEEC) */
+#define PCM_WDT_LATCH_24_LSB                (1U << 0)       /* 32b */
+/* PMSR_LAST_DAT (0x10006000+0xF00) */
+#define PMSR_LAST_DAT_LSB                   (1U << 0)       /* 32b */
+/* PMSR_LAST_CNT (0x10006000+0xF04) */
+#define PMSR_LAST_CMD_LSB                   (1U << 0)       /* 30b */
+#define PMSR_LAST_REQ_LSB                   (1U << 30)      /* 1b */
+/* PMSR_LAST_ACK (0x10006000+0xF08) */
+#define PMSR_LAST_ACK_LSB                   (1U << 0)       /* 1b */
+/* SPM_PMSR_SEL_CON0 (0x10006000+0xF10) */
+#define REG_PMSR_SIG_SEL_0_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_1_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_2_LSB              (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_3_LSB              (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON1 (0x10006000+0xF14) */
+#define REG_PMSR_SIG_SEL_4_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_5_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_6_LSB              (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_7_LSB              (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON2 (0x10006000+0xF18) */
+#define REG_PMSR_SIG_SEL_8_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_9_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_10_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_11_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON3 (0x10006000+0xF1C) */
+#define REG_PMSR_SIG_SEL_12_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_13_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_14_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_15_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON4 (0x10006000+0xF20) */
+#define REG_PMSR_SIG_SEL_16_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_17_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_18_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_19_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON5 (0x10006000+0xF24) */
+#define REG_PMSR_SIG_SEL_20_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_21_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_22_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_23_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON6 (0x10006000+0xF28) */
+#define REG_PMSR_SIG_SEL_24_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_25_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_26_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_27_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON7 (0x10006000+0xF2C) */
+#define REG_PMSR_SIG_SEL_28_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_29_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_30_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_31_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON8 (0x10006000+0xF30) */
+#define REG_PMSR_SIG_SEL_32_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_33_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_34_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_35_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON9 (0x10006000+0xF34) */
+#define REG_PMSR_SIG_SEL_36_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_37_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_38_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_39_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON10 (0x10006000+0xF3C) */
+#define REG_PMSR_SIG_SEL_40_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_41_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_42_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_43_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON11 (0x10006000+0xF40) */
+#define REG_PMSR_SIG_SEL_44_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_45_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_46_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_47_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_TIEMR_STA0 (0x10006000+0xFB8) */
+#define PMSR_TIMER_SET0_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_TIEMR_STA1 (0x10006000+0xFBC) */
+#define PMSR_TIMER_SET1_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_TIEMR_STA2 (0x10006000+0xFC0) */
+#define PMSR_TIMER_SET2_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON0 (0x10006000+0xFC4) */
+#define PMSR_ENABLE_SET0_LSB                (1U << 0)       /* 1b */
+#define PMSR_ENABLE_SET1_LSB                (1U << 1)       /* 1b */
+#define PMSR_ENABLE_SET2_LSB                (1U << 2)       /* 1b */
+#define PMSR_IRQ_CLR_SET0_LSB               (1U << 3)       /* 1b */
+#define PMSR_IRQ_CLR_SET1_LSB               (1U << 4)       /* 1b */
+#define PMSR_IRQ_CLR_SET2_LSB               (1U << 5)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET0_LSB         (1U << 6)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET1_LSB         (1U << 7)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET2_LSB         (1U << 8)       /* 1b */
+#define PMSR_EVENT_CLR_SET0_LSB             (1U << 9)       /* 1b */
+#define PMSR_EVENT_CLR_SET1_LSB             (1U << 10)      /* 1b */
+#define PMSR_EVENT_CLR_SET2_LSB             (1U << 11)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET0_LSB          (1U << 12)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET1_LSB          (1U << 13)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET2_LSB          (1U << 14)      /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET0_LSB (1U << 15)  /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET1_LSB (1U << 16)  /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET2_LSB (1U << 17)  /* 1b */
+#define PMSR_GEN_SW_RST_EN_LSB              (1U << 18)      /* 1b */
+#define PMSR_MODULE_ENABLE_LSB              (1U << 19)      /* 1b */
+#define PMSR_MODE_LSB                       (1U << 20)      /* 2b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET0_LSB (1U << 29)      /* 1b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET1_LSB (1U << 30)      /* 1b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET2_LSB (1U << 31)      /* 1b */
+/* SPM_PMSR_GENERAL_CON1 (0x10006000+0xFC8) */
+#define PMSR_COUNTER_THRES_LSB              (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON2 (0x10006000+0xFCC) */
+#define PMSR_DEBUG_IN_0_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON3 (0x10006000+0xFD0) */
+#define PMSR_DEBUG_IN_1_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON4 (0x10006000+0xFD4) */
+#define PMSR_DEBUG_IN_2_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON5 (0x10006000+0xFD8) */
+#define PMSR_DEBUG_IN_3_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_SW_RESET (0x10006000+0xFDC) */
+#define PMSR_SW_RST_EN_SET0_LSB             (1U << 0)       /* 1b */
+#define PMSR_SW_RST_EN_SET1_LSB             (1U << 1)       /* 1b */
+#define PMSR_SW_RST_EN_SET2_LSB             (1U << 2)       /* 1b */
+/* SPM_PMSR_MON_CON0 (0x10006000+0xFE0) */
+#define REG_PMSR_MON_TYPE_0_LSB             (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_1_LSB             (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_2_LSB             (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_3_LSB             (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_4_LSB             (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_5_LSB             (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_6_LSB             (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_7_LSB             (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_8_LSB             (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_9_LSB             (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_10_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_11_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_12_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_13_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_14_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_15_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_MON_CON1 (0x10006000+0xFE4) */
+#define REG_PMSR_MON_TYPE_16_LSB            (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_17_LSB            (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_18_LSB            (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_19_LSB            (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_20_LSB            (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_21_LSB            (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_22_LSB            (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_23_LSB            (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_24_LSB            (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_25_LSB            (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_26_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_27_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_28_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_29_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_30_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_31_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_MON_CON2 (0x10006000+0xFE8) */
+#define REG_PMSR_MON_TYPE_32_LSB            (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_33_LSB            (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_34_LSB            (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_35_LSB            (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_36_LSB            (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_37_LSB            (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_38_LSB            (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_39_LSB            (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_40_LSB            (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_41_LSB            (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_42_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_43_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_44_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_45_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_46_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_47_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_LEN_CON0 (0x10006000+0xFEC) */
+#define REG_PMSR_WINDOW_LEN_SET0_LSB        (1U << 0)       /* 32b */
+/* SPM_PMSR_LEN_CON1 (0x10006000+0xFF0) */
+#define REG_PMSR_WINDOW_LEN_SET1_LSB        (1U << 0)       /* 32b */
+/* SPM_PMSR_LEN_CON2 (0x10006000+0xFF4) */
+#define REG_PMSR_WINDOW_LEN_SET2_LSB        (1U << 0)       /* 32b */
+
+#define SPM_PROJECT_CODE	0xb16
+#define SPM_REGWR_CFG_KEY	(SPM_PROJECT_CODE << 16)
+#endif /* MT_SPM_REG */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_resource_req.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_resource_req.h
new file mode 100644
index 0000000..30194eb
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_resource_req.h
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_RESOURCE_REQ_H
+#define MT_SPM_RESOURCE_REQ_H
+
+/* SPM resource request internal bit */
+#define MT_SPM_BIT_XO_FPM	0
+#define MT_SPM_BIT_26M		1
+#define MT_SPM_BIT_INFRA	2
+#define MT_SPM_BIT_SYSPLL	3
+#define MT_SPM_BIT_DRAM_S0	4
+#define MT_SPM_BIT_DRAM_S1	5
+
+/* SPM resource request internal bit_mask */
+#define MT_SPM_XO_FPM	BIT(MT_SPM_BIT_XO_FPM)
+#define MT_SPM_26M	BIT(MT_SPM_BIT_26M)
+#define MT_SPM_INFRA	BIT(MT_SPM_BIT_INFRA)
+#define MT_SPM_SYSPLL	BIT(MT_SPM_BIT_SYSPLL)
+#define MT_SPM_DRAM_S0	BIT(MT_SPM_BIT_DRAM_S0)
+#define MT_SPM_DRAM_S1	BIT(MT_SPM_BIT_DRAM_S1)
+#endif /* MT_SPM_RESOURCE_REQ_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.c
new file mode 100644
index 0000000..3eb73d4
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.c
@@ -0,0 +1,303 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <uart.h>
+
+#define SPM_SUSPEND_SLEEP_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |	\
+	 SPM_FLAG_USE_SRCCLKENO2 |		\
+	 SPM_FLAG_ENABLE_MD_MUMTAS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL)
+
+#define SPM_SUSPEND_SLEEP_PCM_FLAG1		\
+	(SPM_FLAG1_DISABLE_MD26M_CK_OFF)
+
+#define SPM_SUSPEND_PCM_FLAG			\
+	(SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_ENABLE_TIA_WORKAROUND |	\
+	 SPM_FLAG_ENABLE_MD_MUMTAS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL)
+
+#define SPM_SUSPEND_PCM_FLAG1			\
+	(SPM_FLAG1_DISABLE_MD26M_CK_OFF)
+
+#define __WAKE_SRC_FOR_SUSPEND_COMMON__		\
+	(R12_PCM_TIMER |			\
+	 R12_KP_IRQ_B |				\
+	 R12_APWDT_EVENT_B |			\
+	 R12_APXGPT1_EVENT_B |			\
+	 R12_CONN2AP_SPM_WAKEUP_B |		\
+	 R12_EINT_EVENT_B |			\
+	 R12_CONN_WDT_IRQ_B |			\
+	 R12_CCIF0_EVENT_B |			\
+	 R12_SSPM2SPM_WAKEUP_B |		\
+	 R12_SCP2SPM_WAKEUP_B |			\
+	 R12_ADSP2SPM_WAKEUP_B |		\
+	 R12_USBX_CDSC_B |			\
+	 R12_USBX_POWERDWN_B |			\
+	 R12_SYS_TIMER_EVENT_B |		\
+	 R12_EINT_EVENT_SECURE_B |		\
+	 R12_CCIF1_EVENT_B |			\
+	 R12_SYS_CIRQ_IRQ_B |			\
+	 R12_MD2AP_PEER_EVENT_B |		\
+	 R12_MD1_WDT_B |			\
+	 R12_CLDMA_EVENT_B |			\
+	 R12_REG_CPU_WAKEUP |			\
+	 R12_APUSYS_WAKE_HOST_B |		\
+	 R12_PCIE_BRIDGE_IRQ |			\
+	 R12_PCIE_IRQ)
+
+#if defined(CFG_MICROTRUST_TEE_SUPPORT)
+#define WAKE_SRC_FOR_SUSPEND (__WAKE_SRC_FOR_SUSPEND_COMMON__)
+#else
+#define WAKE_SRC_FOR_SUSPEND			\
+	(__WAKE_SRC_FOR_SUSPEND_COMMON__ |	\
+	 R12_SEJ_EVENT_B)
+#endif
+
+static struct pwr_ctrl suspend_ctrl = {
+	.wake_src = WAKE_SRC_FOR_SUSPEND,
+	.pcm_flags = SPM_SUSPEND_PCM_FLAG | SPM_FLAG_DISABLE_INFRA_PDN,
+	.pcm_flags1 = SPM_SUSPEND_PCM_FLAG1,
+
+	/* Auto-gen Start */
+
+	/* SPM_AP_STANDBY_CON */
+	.reg_wfi_op = 0,
+	.reg_wfi_type = 0,
+	.reg_mp0_cputop_idle_mask = 0,
+	.reg_mp1_cputop_idle_mask = 0,
+	.reg_mcusys_idle_mask = 0,
+	.reg_md_apsrc_1_sel = 0,
+	.reg_md_apsrc_0_sel = 0,
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC6_MASK */
+	.reg_dpmaif_srcclkena_mask_b = 1,
+	.reg_dpmaif_infra_req_mask_b = 1,
+	.reg_dpmaif_apsrc_req_mask_b = 1,
+	.reg_dpmaif_vrf18_req_mask_b = 1,
+	.reg_dpmaif_ddr_en_mask_b    = 1,
+
+	/* SPM_SRC_REQ */
+	.reg_spm_apsrc_req = 0,
+	.reg_spm_f26m_req = 0,
+	.reg_spm_infra_req = 0,
+	.reg_spm_vrf18_req = 0,
+	.reg_spm_ddr_en_req = 0,
+	.reg_spm_dvfs_req = 0,
+	.reg_spm_sw_mailbox_req = 0,
+	.reg_spm_sspm_mailbox_req = 0,
+	.reg_spm_adsp_mailbox_req = 0,
+	.reg_spm_scp_mailbox_req = 0,
+
+	/* SPM_SRC_MASK */
+	.reg_md_srcclkena_0_mask_b = 1,
+	.reg_md_srcclkena2infra_req_0_mask_b = 0,
+	.reg_md_apsrc2infra_req_0_mask_b = 1,
+	.reg_md_apsrc_req_0_mask_b = 1,
+	.reg_md_vrf18_req_0_mask_b = 1,
+	.reg_md_ddr_en_0_mask_b = 1,
+	.reg_md_srcclkena_1_mask_b = 0,
+	.reg_md_srcclkena2infra_req_1_mask_b = 0,
+	.reg_md_apsrc2infra_req_1_mask_b = 0,
+	.reg_md_apsrc_req_1_mask_b = 0,
+	.reg_md_vrf18_req_1_mask_b = 0,
+	.reg_md_ddr_en_1_mask_b = 0,
+	.reg_conn_srcclkena_mask_b = 1,
+	.reg_conn_srcclkenb_mask_b = 0,
+	.reg_conn_infra_req_mask_b = 1,
+	.reg_conn_apsrc_req_mask_b = 1,
+	.reg_conn_vrf18_req_mask_b = 1,
+	.reg_conn_ddr_en_mask_b = 1,
+	.reg_conn_vfe28_mask_b = 0,
+	.reg_srcclkeni0_srcclkena_mask_b = 1,
+	.reg_srcclkeni0_infra_req_mask_b = 1,
+	.reg_srcclkeni1_srcclkena_mask_b = 0,
+	.reg_srcclkeni1_infra_req_mask_b = 0,
+	.reg_srcclkeni2_srcclkena_mask_b = 0,
+	.reg_srcclkeni2_infra_req_mask_b = 0,
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	.reg_infrasys_ddr_en_mask_b = 1,
+	.reg_md32_srcclkena_mask_b = 1,
+	.reg_md32_infra_req_mask_b = 1,
+	.reg_md32_apsrc_req_mask_b = 1,
+	.reg_md32_vrf18_req_mask_b = 1,
+	.reg_md32_ddr_en_mask_b = 1,
+
+	/* SPM_SRC2_MASK */
+	.reg_scp_srcclkena_mask_b = 1,
+	.reg_scp_infra_req_mask_b = 1,
+	.reg_scp_apsrc_req_mask_b = 1,
+	.reg_scp_vrf18_req_mask_b = 1,
+	.reg_scp_ddr_en_mask_b = 1,
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	.reg_ufs_srcclkena_mask_b = 1,
+	.reg_ufs_infra_req_mask_b = 1,
+	.reg_ufs_apsrc_req_mask_b = 1,
+	.reg_ufs_vrf18_req_mask_b = 1,
+	.reg_ufs_ddr_en_mask_b = 1,
+	.reg_disp0_apsrc_req_mask_b = 1,
+	.reg_disp0_ddr_en_mask_b = 1,
+	.reg_disp1_apsrc_req_mask_b = 1,
+	.reg_disp1_ddr_en_mask_b = 1,
+	.reg_gce_infra_req_mask_b = 1,
+	.reg_gce_apsrc_req_mask_b = 1,
+	.reg_gce_vrf18_req_mask_b = 1,
+	.reg_gce_ddr_en_mask_b = 1,
+	.reg_apu_srcclkena_mask_b = 1,
+	.reg_apu_infra_req_mask_b = 1,
+	.reg_apu_apsrc_req_mask_b = 1,
+	.reg_apu_vrf18_req_mask_b = 1,
+	.reg_apu_ddr_en_mask_b = 1,
+	.reg_cg_check_srcclkena_mask_b = 0,
+	.reg_cg_check_apsrc_req_mask_b = 0,
+	.reg_cg_check_vrf18_req_mask_b = 0,
+	.reg_cg_check_ddr_en_mask_b = 0,
+
+	/* SPM_SRC3_MASK */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+	.reg_sw2spm_int0_mask_b = 0,
+	.reg_sw2spm_int1_mask_b = 0,
+	.reg_sw2spm_int2_mask_b = 0,
+	.reg_sw2spm_int3_mask_b = 0,
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	.reg_csyspwrreq_mask = 1,
+	.reg_spm_srcclkena_reserved_mask_b = 0,
+	.reg_spm_infra_req_reserved_mask_b = 0,
+	.reg_spm_apsrc_req_reserved_mask_b = 0,
+	.reg_spm_vrf18_req_reserved_mask_b = 0,
+	.reg_spm_ddr_en_reserved_mask_b = 0,
+	.reg_mcupm_srcclkena_mask_b = 1,
+	.reg_mcupm_infra_req_mask_b = 1,
+	.reg_mcupm_apsrc_req_mask_b = 1,
+	.reg_mcupm_vrf18_req_mask_b = 1,
+	.reg_mcupm_ddr_en_mask_b = 1,
+	.reg_msdc0_srcclkena_mask_b = 1,
+	.reg_msdc0_infra_req_mask_b = 1,
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	.reg_msdc0_ddr_en_mask_b = 1,
+	.reg_msdc1_srcclkena_mask_b = 1,
+	.reg_msdc1_infra_req_mask_b = 1,
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	.reg_msdc1_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	.ccif_event_mask_b = 0xFFF,
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	.reg_bak_psri_infra_req_mask_b = 0,
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	.reg_bak_psri_ddr_en_mask_b = 0,
+	.reg_dramc0_md32_infra_req_mask_b = 1,
+	.reg_dramc0_md32_vrf18_req_mask_b = 0,
+	.reg_dramc1_md32_infra_req_mask_b = 1,
+	.reg_dramc1_md32_vrf18_req_mask_b = 0,
+	.reg_conn_srcclkenb2pwrap_mask_b = 0,
+	.reg_dramc0_md32_wakeup_mask = 1,
+	.reg_dramc1_md32_wakeup_mask = 1,
+
+	/* SPM_SRC5_MASK */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x11,
+	.reg_mcusys_merge_ddr_en_mask_b = 0x11,
+	.reg_msdc2_srcclkena_mask_b = 1,
+	.reg_msdc2_infra_req_mask_b = 1,
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	.reg_msdc2_ddr_en_mask_b = 1,
+	.reg_pcie_srcclkena_mask_b = 1,
+	.reg_pcie_infra_req_mask_b = 1,
+	.reg_pcie_apsrc_req_mask_b = 1,
+	.reg_pcie_vrf18_req_mask_b = 1,
+	.reg_pcie_ddr_en_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	.reg_wakeup_event_mask = 0x01382202,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+
+	/* Auto-gen End */
+};
+
+struct spm_lp_scen __spm_suspend = {
+	.pwrctrl = &suspend_ctrl,
+};
+
+int mt_spm_suspend_mode_set(int mode)
+{
+	if (mode == MT_SPM_SUSPEND_SLEEP) {
+		suspend_ctrl.pcm_flags = SPM_SUSPEND_SLEEP_PCM_FLAG;
+		suspend_ctrl.pcm_flags1 = SPM_SUSPEND_SLEEP_PCM_FLAG1;
+	} else {
+		suspend_ctrl.pcm_flags = SPM_SUSPEND_PCM_FLAG;
+		suspend_ctrl.pcm_flags1 = SPM_SUSPEND_PCM_FLAG1;
+	}
+
+	return 0;
+}
+
+int mt_spm_suspend_enter(int state_id, unsigned int ext_opand,
+			 unsigned int resource_req)
+{
+	/* If FMAudio / ADSP is active, change to sleep suspend mode */
+	if ((ext_opand & MT_SPM_EX_OP_SET_SUSPEND_MODE) != 0U) {
+		mt_spm_suspend_mode_set(MT_SPM_SUSPEND_SLEEP);
+	}
+
+	/* Notify MCUPM that device is going suspend flow */
+	mmio_write_32(MCUPM_MBOX_OFFSET_PDN, MCUPM_POWER_DOWN);
+
+	/* Notify UART to sleep */
+	mt_uart_save();
+
+	return spm_conservation(state_id, ext_opand,
+				&__spm_suspend, resource_req);
+}
+
+void mt_spm_suspend_resume(int state_id, unsigned int ext_opand,
+			   struct wake_status **status)
+{
+	spm_conservation_finish(state_id, ext_opand, &__spm_suspend, status);
+
+	/* Notify UART to wakeup */
+	mt_uart_restore();
+
+	/* Notify MCUPM that device leave suspend */
+	mmio_write_32(MCUPM_MBOX_OFFSET_PDN, 0);
+
+	/* If FMAudio / ADSP is active, change back to suspend mode */
+	if ((ext_opand & MT_SPM_EX_OP_SET_SUSPEND_MODE) != 0U) {
+		mt_spm_suspend_mode_set(MT_SPM_SUSPEND_SYSTEM_PDN);
+	}
+}
+
+void mt_spm_suspend_init(void)
+{
+	spm_conservation_pwrctrl_init(__spm_suspend.pwrctrl);
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.h
new file mode 100644
index 0000000..08bbad2
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_suspend.h
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SUSPEND_H
+#define MT_SPM_SUSPEND_H
+
+#include <mt_spm_internal.h>
+
+#define MCUPM_MBOX_OFFSET_PDN	0x0C55FDA8
+#define MCUPM_POWER_DOWN	0x4D50444E
+
+enum MT_SPM_SUSPEND_MODE {
+	MT_SPM_SUSPEND_SYSTEM_PDN,
+	MT_SPM_SUSPEND_SLEEP,
+};
+
+extern int mt_spm_suspend_mode_set(int mode);
+extern int mt_spm_suspend_enter(int state_id, unsigned int ext_opand,
+				unsigned int reosuce_req);
+extern void mt_spm_suspend_resume(int state_id, unsigned int ext_opand,
+				  struct wake_status **status);
+extern void mt_spm_suspend_init(void);
+#endif /* MT_SPM_SUSPEND_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.c b/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.c
new file mode 100644
index 0000000..f74ea80
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.c
@@ -0,0 +1,405 @@
+/*
+ * Copyright(C)2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+#include <stdio.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+#include <plat/common/platform.h>
+#include <lib/utils_def.h>
+
+#include <mtk_sip_svc.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+
+#include "mt_spm.h"
+#include "mt_spm_internal.h"
+#include "mt_spm_reg.h"
+#include "mt_spm_vcorefs.h"
+#include "mt_spm_pmic_wrap.h"
+
+#define VCORE_CT_ENABLE (1U << 5)
+#define SW_REQ5_INIT_VAL (6U << 12)
+#define V_VMODE_SHIFT 0
+#define VCORE_HV 105
+#define VCORE_LV 95
+#define PMIC_STEP_UV 6250
+
+static const struct reg_config dvfsrc_init_configs[] = {
+	/* Setup opp table */
+	{ DVFSRC_LEVEL_LABEL_0_1, 0x50436053 },
+	{ DVFSRC_LEVEL_LABEL_2_3, 0x40335042 },
+	{ DVFSRC_LEVEL_LABEL_4_5, 0x40314032 },
+	{ DVFSRC_LEVEL_LABEL_6_7, 0x30223023 },
+	{ DVFSRC_LEVEL_LABEL_8_9, 0x20133021 },
+	{ DVFSRC_LEVEL_LABEL_10_11, 0x20112012 },
+	{ DVFSRC_LEVEL_LABEL_12_13, 0x10032010 },
+	{ DVFSRC_LEVEL_LABEL_14_15, 0x10011002 },
+	{ DVFSRC_LEVEL_LABEL_16_17, 0x00131000 },
+	{ DVFSRC_LEVEL_LABEL_18_19, 0x00110012 },
+	{ DVFSRC_LEVEL_LABEL_20_21, 0x00000010 },
+
+	/* Setup hw emi qos policy */
+	{ DVFSRC_DDR_REQUEST, 0x00004321 },
+	{ DVFSRC_DDR_REQUEST3, 0x00000065 },
+
+	/* Setup up for PCIe */
+	{ DVFSRC_PCIE_VCORE_REQ, 0x0A298001 },
+
+	/* Setup up HRT QOS policy */
+	{ DVFSRC_HRT_BW_BASE, 0x00000004 },
+	{ DVFSRC_HRT_REQ_UNIT, 0x0000001E },
+	{ DVFSRC_HRT_HIGH_3, 0x18A618A6 },
+	{ DVFSRC_HRT_HIGH_2, 0x18A61183 },
+	{ DVFSRC_HRT_HIGH_1, 0x0D690B80 },
+	{ DVFSRC_HRT_HIGH, 0x070804B0 },
+	{ DVFSRC_HRT_LOW_3, 0x18A518A5 },
+	{ DVFSRC_HRT_LOW_2, 0x18A51182 },
+	{ DVFSRC_HRT_LOW_1, 0x0D680B7F },
+	{ DVFSRC_HRT_LOW, 0x070704AF },
+	{ DVFSRC_HRT_REQUEST, 0x66654321 },
+	/* Setup up SRT QOS policy */
+	{ DVFSRC_QOS_EN, 0x0011007C },
+	{ DVFSRC_DDR_QOS0, 0x00000019 },
+	{ DVFSRC_DDR_QOS1, 0x00000026 },
+	{ DVFSRC_DDR_QOS2, 0x00000033 },
+	{ DVFSRC_DDR_QOS3, 0x0000003B },
+	{ DVFSRC_DDR_QOS4, 0x0000004C },
+	{ DVFSRC_DDR_QOS5, 0x00000066 },
+	{ DVFSRC_DDR_QOS6, 0x00000066 },
+	{ DVFSRC_DDR_REQUEST5, 0x54321000 },
+	{ DVFSRC_DDR_REQUEST7, 0x66000000 },
+	/* Setup up hifi request policy */
+	{ DVFSRC_DDR_REQUEST6, 0x66543210 },
+	/* Setup up hw request vcore policy */
+	{ DVFSRC_VCORE_USER_REQ, 0x00010A29 },
+
+	/* Setup misc*/
+	{ DVFSRC_TIMEOUT_NEXTREQ, 0x00000015 },
+	{ DVFSRC_RSRV_5, 0x00000001 },
+	{ DVFSRC_INT_EN, 0x00000002 },
+	/* Init opp and enable dvfsrc*/
+	{ DVFSRC_CURRENT_FORCE, 0x00000001 },
+	{ DVFSRC_BASIC_CONTROL, 0x0298444B },
+	{ DVFSRC_BASIC_CONTROL, 0x0298054B },
+	{ DVFSRC_CURRENT_FORCE, 0x00000000 },
+};
+
+static struct pwr_ctrl vcorefs_ctrl = {
+	.wake_src = R12_REG_CPU_WAKEUP,
+
+	/* default VCORE DVFS is disabled */
+	.pcm_flags = (SPM_FLAG_RUN_COMMON_SCENARIO |
+			SPM_FLAG_DISABLE_VCORE_DVS |
+			SPM_FLAG_DISABLE_VCORE_DFS),
+
+	/* Auto-gen Start */
+
+	/* SPM_AP_STANDBY_CON */
+	.reg_wfi_op = 0,
+	.reg_wfi_type = 0,
+	.reg_mp0_cputop_idle_mask = 0,
+	.reg_mp1_cputop_idle_mask = 0,
+	.reg_mcusys_idle_mask = 0,
+	.reg_md_apsrc_1_sel = 0,
+	.reg_md_apsrc_0_sel = 0,
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC_REQ */
+	.reg_spm_apsrc_req = 0,
+	.reg_spm_f26m_req = 0,
+	.reg_spm_infra_req = 0,
+	.reg_spm_vrf18_req = 0,
+	.reg_spm_ddr_en_req = 1,
+	.reg_spm_dvfs_req = 0,
+	.reg_spm_sw_mailbox_req = 0,
+	.reg_spm_sspm_mailbox_req = 0,
+	.reg_spm_adsp_mailbox_req = 0,
+	.reg_spm_scp_mailbox_req = 0,
+
+	/* SPM_SRC6_MASK */
+	.reg_dpmaif_srcclkena_mask_b = 1,
+	.reg_dpmaif_infra_req_mask_b = 1,
+	.reg_dpmaif_apsrc_req_mask_b = 1,
+	.reg_dpmaif_vrf18_req_mask_b = 1,
+	.reg_dpmaif_ddr_en_mask_b    = 1,
+
+	/* SPM_SRC_MASK */
+	.reg_md_srcclkena_0_mask_b = 1,
+	.reg_md_srcclkena2infra_req_0_mask_b = 0,
+	.reg_md_apsrc2infra_req_0_mask_b = 1,
+	.reg_md_apsrc_req_0_mask_b = 1,
+	.reg_md_vrf18_req_0_mask_b = 1,
+	.reg_md_ddr_en_0_mask_b = 1,
+	.reg_md_srcclkena_1_mask_b = 0,
+	.reg_md_srcclkena2infra_req_1_mask_b = 0,
+	.reg_md_apsrc2infra_req_1_mask_b = 0,
+	.reg_md_apsrc_req_1_mask_b = 0,
+	.reg_md_vrf18_req_1_mask_b = 0,
+	.reg_md_ddr_en_1_mask_b = 0,
+	.reg_conn_srcclkena_mask_b = 1,
+	.reg_conn_srcclkenb_mask_b = 0,
+	.reg_conn_infra_req_mask_b = 1,
+	.reg_conn_apsrc_req_mask_b = 1,
+	.reg_conn_vrf18_req_mask_b = 1,
+	.reg_conn_ddr_en_mask_b = 1,
+	.reg_conn_vfe28_mask_b = 0,
+	.reg_srcclkeni0_srcclkena_mask_b = 1,
+	.reg_srcclkeni0_infra_req_mask_b = 1,
+	.reg_srcclkeni1_srcclkena_mask_b = 0,
+	.reg_srcclkeni1_infra_req_mask_b = 0,
+	.reg_srcclkeni2_srcclkena_mask_b = 0,
+	.reg_srcclkeni2_infra_req_mask_b = 0,
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	.reg_infrasys_ddr_en_mask_b = 1,
+	.reg_md32_srcclkena_mask_b = 1,
+	.reg_md32_infra_req_mask_b = 1,
+	.reg_md32_apsrc_req_mask_b = 1,
+	.reg_md32_vrf18_req_mask_b = 1,
+	.reg_md32_ddr_en_mask_b = 1,
+
+	/* SPM_SRC2_MASK */
+	.reg_scp_srcclkena_mask_b = 1,
+	.reg_scp_infra_req_mask_b = 1,
+	.reg_scp_apsrc_req_mask_b = 1,
+	.reg_scp_vrf18_req_mask_b = 1,
+	.reg_scp_ddr_en_mask_b = 1,
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	.reg_ufs_srcclkena_mask_b = 1,
+	.reg_ufs_infra_req_mask_b = 1,
+	.reg_ufs_apsrc_req_mask_b = 1,
+	.reg_ufs_vrf18_req_mask_b = 1,
+	.reg_ufs_ddr_en_mask_b = 1,
+	.reg_disp0_apsrc_req_mask_b = 1,
+	.reg_disp0_ddr_en_mask_b = 1,
+	.reg_disp1_apsrc_req_mask_b = 1,
+	.reg_disp1_ddr_en_mask_b = 1,
+	.reg_gce_infra_req_mask_b = 1,
+	.reg_gce_apsrc_req_mask_b = 1,
+	.reg_gce_vrf18_req_mask_b = 1,
+	.reg_gce_ddr_en_mask_b = 1,
+	.reg_apu_srcclkena_mask_b = 1,
+	.reg_apu_infra_req_mask_b = 1,
+	.reg_apu_apsrc_req_mask_b = 1,
+	.reg_apu_vrf18_req_mask_b = 1,
+	.reg_apu_ddr_en_mask_b = 1,
+	.reg_cg_check_srcclkena_mask_b = 0,
+	.reg_cg_check_apsrc_req_mask_b = 0,
+	.reg_cg_check_vrf18_req_mask_b = 0,
+	.reg_cg_check_ddr_en_mask_b = 0,
+
+	/* SPM_SRC3_MASK */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+	.reg_sw2spm_int0_mask_b = 0,
+	.reg_sw2spm_int1_mask_b = 0,
+	.reg_sw2spm_int2_mask_b = 0,
+	.reg_sw2spm_int3_mask_b = 0,
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	.reg_csyspwrreq_mask = 1,
+	.reg_spm_srcclkena_reserved_mask_b = 0,
+	.reg_spm_infra_req_reserved_mask_b = 0,
+	.reg_spm_apsrc_req_reserved_mask_b = 0,
+	.reg_spm_vrf18_req_reserved_mask_b = 0,
+	.reg_spm_ddr_en_reserved_mask_b = 0,
+	.reg_mcupm_srcclkena_mask_b = 1,
+	.reg_mcupm_infra_req_mask_b = 1,
+	.reg_mcupm_apsrc_req_mask_b = 1,
+	.reg_mcupm_vrf18_req_mask_b = 1,
+	.reg_mcupm_ddr_en_mask_b = 1,
+	.reg_msdc0_srcclkena_mask_b = 1,
+	.reg_msdc0_infra_req_mask_b = 1,
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	.reg_msdc0_ddr_en_mask_b = 1,
+	.reg_msdc1_srcclkena_mask_b = 1,
+	.reg_msdc1_infra_req_mask_b = 1,
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	.reg_msdc1_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	.ccif_event_mask_b = 0xFFF,
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	.reg_bak_psri_infra_req_mask_b = 0,
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	.reg_bak_psri_ddr_en_mask_b = 0,
+	.reg_dramc0_md32_infra_req_mask_b = 1,
+	.reg_dramc0_md32_vrf18_req_mask_b = 0,
+	.reg_dramc1_md32_infra_req_mask_b = 1,
+	.reg_dramc1_md32_vrf18_req_mask_b = 0,
+	.reg_conn_srcclkenb2pwrap_mask_b = 0,
+	.reg_dramc0_md32_wakeup_mask = 1,
+	.reg_dramc1_md32_wakeup_mask = 1,
+
+	/* SPM_SRC5_MASK */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x11,
+	.reg_mcusys_merge_ddr_en_mask_b = 0x11,
+	.reg_msdc2_srcclkena_mask_b = 1,
+	.reg_msdc2_infra_req_mask_b = 1,
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	.reg_msdc2_ddr_en_mask_b = 1,
+	.reg_pcie_srcclkena_mask_b = 1,
+	.reg_pcie_infra_req_mask_b = 1,
+	.reg_pcie_apsrc_req_mask_b = 1,
+	.reg_pcie_vrf18_req_mask_b = 1,
+	.reg_pcie_ddr_en_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	.reg_wakeup_event_mask = 0xEFFFFFFF,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+
+	/* Auto-gen End */
+};
+
+struct spm_lp_scen __spm_vcorefs = {
+	.pwrctrl	= &vcorefs_ctrl,
+};
+
+static void spm_vcorefs_pwarp_cmd(uint64_t cmd, uint64_t val)
+{
+	if (cmd < NR_IDX_ALL) {
+		mt_spm_pmic_wrap_set_cmd(PMIC_WRAP_PHASE_ALLINONE, cmd, val);
+	} else {
+		INFO("cmd out of range!\n");
+	}
+}
+
+void spm_dvfsfw_init(uint64_t boot_up_opp, uint64_t dram_issue)
+{
+	mmio_clrsetbits_32(SPM_DVFS_MISC, SPM_DVFS_FORCE_ENABLE_LSB,
+		SPM_DVFSRC_ENABLE_LSB);
+
+	mmio_write_32(SPM_DVFS_LEVEL, 0x00000001);
+	mmio_write_32(SPM_DVS_DFS_LEVEL, 0x00010001);
+}
+
+void __spm_sync_vcore_dvfs_power_control(struct pwr_ctrl *dest_pwr_ctrl,
+					 const struct pwr_ctrl *src_pwr_ctrl)
+{
+	uint32_t dvfs_mask = SPM_FLAG_DISABLE_VCORE_DVS |
+			     SPM_FLAG_DISABLE_VCORE_DFS |
+			     SPM_FLAG_ENABLE_VOLTAGE_BIN;
+
+	dest_pwr_ctrl->pcm_flags = (dest_pwr_ctrl->pcm_flags & (~dvfs_mask)) |
+					(src_pwr_ctrl->pcm_flags & dvfs_mask);
+
+	if (dest_pwr_ctrl->pcm_flags_cust > 0U) {
+		dest_pwr_ctrl->pcm_flags_cust =
+			(dest_pwr_ctrl->pcm_flags_cust & (~dvfs_mask)) |
+			(src_pwr_ctrl->pcm_flags & dvfs_mask);
+	}
+}
+
+static void spm_go_to_vcorefs(void)
+{
+	__spm_set_power_control(__spm_vcorefs.pwrctrl);
+	__spm_set_wakeup_event(__spm_vcorefs.pwrctrl);
+	__spm_set_pcm_flags(__spm_vcorefs.pwrctrl);
+	__spm_send_cpu_wakeup_event();
+}
+
+static void dvfsrc_init(void)
+{
+	uint32_t i;
+
+	for (i = 0U; i < ARRAY_SIZE(dvfsrc_init_configs); i++) {
+		mmio_write_32(dvfsrc_init_configs[i].offset,
+			dvfsrc_init_configs[i].val);
+	}
+}
+
+static uint32_t spm_vcorefs_get_efuse_data(void)
+{
+	return mmio_read_32(VCORE_VB_EFUSE);
+}
+
+static uint32_t is_rising_need(void)
+{
+	return ((spm_vcorefs_get_efuse_data() & 0xF) == 11U) ? 1U : 0U;
+}
+
+static void spm_vcorefs_vcore_setting(uint64_t flag)
+{
+	uint32_t dvfs_v_mode, dvfsrc_rsrv, i;
+	uint32_t opp_uv[] = {725000U, 650000U, 600000U, 575000U};
+
+	dvfsrc_rsrv = mmio_read_32(DVFSRC_RSRV_4);
+
+	dvfs_v_mode = (dvfsrc_rsrv >> V_VMODE_SHIFT) & 0x3;
+
+	if (is_rising_need() != 0U) {
+		opp_uv[2] = 625000U;
+		opp_uv[3] = 600000U;
+	}
+
+	for (i = 0; i < ARRAY_SIZE(opp_uv); i++) {
+		if (dvfs_v_mode == 3U) {
+			/* LV */
+			opp_uv[i] = round_down((opp_uv[i] * VCORE_LV) / 100U,
+					      PMIC_STEP_UV);
+		} else if (dvfs_v_mode == 1U) {
+			/* HV */
+			opp_uv[i] = round_up((opp_uv[i] * VCORE_HV) / 100U,
+					    PMIC_STEP_UV);
+		}
+		spm_vcorefs_pwarp_cmd(i, __vcore_uv_to_pmic(opp_uv[i]));
+	}
+}
+
+uint64_t spm_vcorefs_args(uint64_t x1, uint64_t x2, uint64_t x3, uint64_t *x4)
+{
+	uint64_t cmd = x1;
+	uint64_t spm_flags;
+
+	switch (cmd) {
+	case VCOREFS_SMC_CMD_INIT:
+		/* vcore_dvfs init + kick */
+		mmio_write_32(DVFSRC_SW_REQ5, SW_REQ5_INIT_VAL);
+		spm_dvfsfw_init(0ULL, 0ULL);
+		spm_vcorefs_vcore_setting(x3 & 0xF);
+		spm_flags = SPM_FLAG_RUN_COMMON_SCENARIO;
+		if ((x2 & 0x1) > 0U) {
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DVS;
+		}
+
+		if ((x2 & 0x2) > 0U) {
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DFS;
+		}
+
+		if ((mmio_read_32(DVFSRC_RSRV_4) & VCORE_CT_ENABLE) > 0U) {
+			spm_flags |= SPM_FLAG_ENABLE_VOLTAGE_BIN;
+		}
+
+		set_pwrctrl_pcm_flags(__spm_vcorefs.pwrctrl, spm_flags);
+		spm_go_to_vcorefs();
+		dvfsrc_init();
+
+		*x4 = 0U;
+		mmio_write_32(DVFSRC_SW_REQ5, 0U);
+		break;
+	case VCOREFS_SMC_CMD_KICK:
+		mmio_write_32(DVFSRC_SW_REQ5, 0U);
+		break;
+	default:
+		break;
+	}
+
+	return 0ULL;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.h b/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.h
new file mode 100644
index 0000000..f4e0c48
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/mt_spm_vcorefs.h
@@ -0,0 +1,135 @@
+/*
+ * Copyright(C)2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_VCOREFS_H
+#define MT_SPM_VCOREFS_H
+
+uint64_t spm_vcorefs_args(uint64_t x1, uint64_t x2, uint64_t x3, uint64_t *x4);
+
+enum vcorefs_smc_cmd {
+	VCOREFS_SMC_CMD_0,
+	VCOREFS_SMC_CMD_1,
+	VCOREFS_SMC_CMD_2,
+	VCOREFS_SMC_CMD_3,
+	VCOREFS_SMC_CMD_4,
+	/* check spmfw status */
+	VCOREFS_SMC_CMD_5,
+
+	/* get spmfw type */
+	VCOREFS_SMC_CMD_6,
+
+	/* get spm reg status */
+	VCOREFS_SMC_CMD_7,
+
+	NUM_VCOREFS_SMC_CMD,
+};
+
+enum vcorefs_smc_cmd_new {
+	VCOREFS_SMC_CMD_INIT = 0,
+	VCOREFS_SMC_CMD_KICK = 1,
+};
+
+#define _VCORE_BASE_UV		400000
+#define _VCORE_STEP_UV		6250
+
+/* PMIC */
+#define __vcore_pmic_to_uv(pmic)	\
+	(((pmic) * _VCORE_STEP_UV) + _VCORE_BASE_UV)
+
+#define __vcore_uv_to_pmic(uv)	/* pmic >= uv */	\
+	((((uv) - _VCORE_BASE_UV) + (_VCORE_STEP_UV - 1)) / _VCORE_STEP_UV)
+
+struct reg_config {
+	uint32_t offset;
+	uint32_t val;
+};
+
+#define DVFSRC_BASIC_CONTROL             (DVFSRC_BASE + 0x0)
+#define DVFSRC_SW_REQ5                   (DVFSRC_BASE + 0x14)
+#define DVFSRC_INT_EN                    (DVFSRC_BASE + 0xC8)
+#define DVFSRC_MD_TURBO                  (DVFSRC_BASE + 0xDC)
+#define DVFSRC_PCIE_VCORE_REQ            (DVFSRC_BASE + 0xE0)
+#define DVFSRC_VCORE_USER_REQ            (DVFSRC_BASE + 0xE4)
+#define DVFSRC_TIMEOUT_NEXTREQ           (DVFSRC_BASE + 0xF8)
+#define DVFSRC_LEVEL_LABEL_0_1           (DVFSRC_BASE + 0x100)
+#define DVFSRC_LEVEL_LABEL_2_3           (DVFSRC_BASE + 0x104)
+#define DVFSRC_LEVEL_LABEL_4_5           (DVFSRC_BASE + 0x108)
+#define DVFSRC_LEVEL_LABEL_6_7           (DVFSRC_BASE + 0x10C)
+#define DVFSRC_LEVEL_LABEL_8_9           (DVFSRC_BASE + 0x110)
+#define DVFSRC_LEVEL_LABEL_10_11         (DVFSRC_BASE + 0x114)
+#define DVFSRC_LEVEL_LABEL_12_13         (DVFSRC_BASE + 0x118)
+#define DVFSRC_LEVEL_LABEL_14_15         (DVFSRC_BASE + 0x11C)
+#define DVFSRC_QOS_EN                    (DVFSRC_BASE + 0x280)
+#define DVFSRC_HRT_BW_BASE               (DVFSRC_BASE + 0x294)
+#define DVFSRC_RSRV_4                    (DVFSRC_BASE + 0x610)
+#define DVFSRC_RSRV_5                    (DVFSRC_BASE + 0x614)
+#define DVFSRC_DDR_REQUEST               (DVFSRC_BASE + 0xA00)
+#define DVFSRC_DDR_REQUEST2              (DVFSRC_BASE + 0xA04)
+#define DVFSRC_DDR_REQUEST3              (DVFSRC_BASE + 0xA08)
+#define DVFSRC_DDR_REQUEST4              (DVFSRC_BASE + 0xA0C)
+#define DVFSRC_DDR_REQUEST5              (DVFSRC_BASE + 0xA10)
+#define DVFSRC_DDR_REQUEST6              (DVFSRC_BASE + 0xA14)
+#define DVFSRC_DDR_REQUEST7              (DVFSRC_BASE + 0xA18)
+#define DVFSRC_DDR_QOS0                  (DVFSRC_BASE + 0xA34)
+#define DVFSRC_DDR_QOS1                  (DVFSRC_BASE + 0xA38)
+#define DVFSRC_DDR_QOS2                  (DVFSRC_BASE + 0xA3C)
+#define DVFSRC_DDR_QOS3                  (DVFSRC_BASE + 0xA40)
+#define DVFSRC_DDR_QOS4                  (DVFSRC_BASE + 0xA44)
+#define DVFSRC_HRT_REQ_UNIT              (DVFSRC_BASE + 0xA60)
+#define DVFSRC_HRT_REQUEST               (DVFSRC_BASE + 0xAC4)
+#define DVFSRC_HRT_HIGH_2                (DVFSRC_BASE + 0xAC8)
+#define DVFSRC_HRT_HIGH_1                (DVFSRC_BASE + 0xACC)
+#define DVFSRC_HRT_HIGH                  (DVFSRC_BASE + 0xAD0)
+#define DVFSRC_HRT_LOW_2                 (DVFSRC_BASE + 0xAD4)
+#define DVFSRC_HRT_LOW_1                 (DVFSRC_BASE + 0xAD8)
+#define DVFSRC_HRT_LOW                   (DVFSRC_BASE + 0xADC)
+#define DVFSRC_DDR_ADD_REQUEST           (DVFSRC_BASE + 0xAE0)
+#define DVFSRC_LAST                      (DVFSRC_BASE + 0xAE4)
+#define DVFSRC_LAST_L                    (DVFSRC_BASE + 0xAE8)
+#define DVFSRC_MD_SCENARIO               (DVFSRC_BASE + 0xAEC)
+#define DVFSRC_RECORD_0_0                (DVFSRC_BASE + 0xAF0)
+#define DVFSRC_RECORD_0_1                (DVFSRC_BASE + 0xAF4)
+#define DVFSRC_RECORD_0_2                (DVFSRC_BASE + 0xAF8)
+#define DVFSRC_RECORD_0_3                (DVFSRC_BASE + 0xAFC)
+#define DVFSRC_RECORD_0_4                (DVFSRC_BASE + 0xB00)
+#define DVFSRC_RECORD_0_5                (DVFSRC_BASE + 0xB04)
+#define DVFSRC_RECORD_0_6                (DVFSRC_BASE + 0xB08)
+#define DVFSRC_RECORD_0_7                (DVFSRC_BASE + 0xB0C)
+#define DVFSRC_RECORD_0_L_0              (DVFSRC_BASE + 0xBF0)
+#define DVFSRC_RECORD_0_L_1              (DVFSRC_BASE + 0xBF4)
+#define DVFSRC_RECORD_0_L_2              (DVFSRC_BASE + 0xBF8)
+#define DVFSRC_RECORD_0_L_3              (DVFSRC_BASE + 0xBFC)
+#define DVFSRC_RECORD_0_L_4              (DVFSRC_BASE + 0xC00)
+#define DVFSRC_RECORD_0_L_5              (DVFSRC_BASE + 0xC04)
+#define DVFSRC_RECORD_0_L_6              (DVFSRC_BASE + 0xC08)
+#define DVFSRC_RECORD_0_L_7              (DVFSRC_BASE + 0xC0C)
+#define DVFSRC_EMI_REQUEST8              (DVFSRC_BASE + 0xCF0)
+#define DVFSRC_DDR_REQUEST8              (DVFSRC_BASE + 0xCF4)
+#define DVFSRC_EMI_HRT_2                 (DVFSRC_BASE + 0xCF8)
+#define DVFSRC_EMI_HRT2_2                (DVFSRC_BASE + 0xCFC)
+#define DVFSRC_EMI_HRT3_2                (DVFSRC_BASE + 0xD00)
+#define DVFSRC_EMI_QOS5                  (DVFSRC_BASE + 0xD04)
+#define DVFSRC_EMI_QOS6                  (DVFSRC_BASE + 0xD08)
+#define DVFSRC_DDR_HRT_2                 (DVFSRC_BASE + 0xD0C)
+#define DVFSRC_DDR_HRT2_2                (DVFSRC_BASE + 0xD10)
+#define DVFSRC_DDR_HRT3_2                (DVFSRC_BASE + 0xD14)
+#define DVFSRC_DDR_QOS5                  (DVFSRC_BASE + 0xD18)
+#define DVFSRC_DDR_QOS6                  (DVFSRC_BASE + 0xD1C)
+#define DVFSRC_HRT_HIGH_3                (DVFSRC_BASE + 0xD38)
+#define DVFSRC_HRT_LOW_3                 (DVFSRC_BASE + 0xD3C)
+#define DVFSRC_LEVEL_LABEL_16_17         (DVFSRC_BASE + 0xD4C)
+#define DVFSRC_LEVEL_LABEL_18_19         (DVFSRC_BASE + 0xD50)
+#define DVFSRC_LEVEL_LABEL_20_21         (DVFSRC_BASE + 0xD54)
+#define DVFSRC_LEVEL_LABEL_22_23         (DVFSRC_BASE + 0xD58)
+#define DVFSRC_LEVEL_LABEL_24_25         (DVFSRC_BASE + 0xD5C)
+#define DVFSRC_LEVEL_LABEL_26_27         (DVFSRC_BASE + 0xD60)
+#define DVFSRC_LEVEL_LABEL_28_29         (DVFSRC_BASE + 0xD64)
+#define DVFSRC_LEVEL_LABEL_30_31         (DVFSRC_BASE + 0xD68)
+#define DVFSRC_CURRENT_FORCE             (DVFSRC_BASE + 0xD6C)
+
+#define VCORE_VB_EFUSE	(0x11C105E8)
+
+#endif /* MT_SPM_VCOREFS_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_notifier.h b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_notifier.h
new file mode 100644
index 0000000..66be7ee
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_notifier.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SSPM_NOTIFIER_H
+#define MT_SPM_SSPM_NOTIFIER_H
+
+enum MT_SPM_SSPM_NOTIFY_ID {
+	MT_SPM_NOTIFY_LP_ENTER,
+	MT_SPM_NOTIFY_LP_LEAVE,
+};
+
+int mt_spm_sspm_notify(int type, unsigned int lp_mode);
+
+static inline int mt_spm_sspm_notify_u32(int type, unsigned int lp_mode)
+{
+	return mt_spm_sspm_notify(type, lp_mode);
+}
+#endif /* MT_SPM_SSPM_NOTIFIER_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_intc.h b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_intc.h
new file mode 100644
index 0000000..452ae90
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_intc.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SSPM_INTC_H
+#define MT_SPM_SSPM_INTC_H
+
+#include <mt_spm_reg.h>
+
+#define MT_SPM_SSPM_INTC_SEL_0		0x10
+#define MT_SPM_SSPM_INTC_SEL_1		0x20
+#define MT_SPM_SSPM_INTC_SEL_2		0x40
+#define MT_SPM_SSPM_INTC_SEL_3		0x80
+
+#define MT_SPM_SSPM_INTC_TRIGGER(id, sg) \
+	(((0x10 << id) | (sg << id)) & 0xff)
+
+#define MT_SPM_SSPM_INTC0_HIGH	MT_SPM_SSPM_INTC_TRIGGER(0, 1)
+#define MT_SPM_SSPM_INTC0_LOW	MT_SPM_SSPM_INTC_TRIGGER(0, 0)
+#define MT_SPM_SSPM_INTC1_HIGH	MT_SPM_SSPM_INTC_TRIGGER(1, 1)
+#define MT_SPM_SSPM_INTC1_LOW	MT_SPM_SSPM_INTC_TRIGGER(1, 0)
+#define MT_SPM_SSPM_INTC2_HIGH	MT_SPM_SSPM_INTC_TRIGGER(2, 1)
+#define MT_SPM_SSPM_INTC2_LOW	MT_SPM_SSPM_INTC_TRIGGER(2, 0)
+#define MT_SPM_SSPM_INTC3_HIGH	MT_SPM_SSPM_INTC_TRIGGER(3, 1)
+#define MT_SPM_SSPM_INTC3_LOW	MT_SPM_SSPM_INTC_TRIGGER(3, 0)
+
+#define DO_SPM_SSPM_LP_SUSPEND()	\
+	mmio_write_32(SPM_MD32_IRQ, MT_SPM_SSPM_INTC0_HIGH)
+#define DO_SPM_SSPM_LP_RESUME()		\
+	mmio_write_32(SPM_MD32_IRQ, MT_SPM_SSPM_INTC0_LOW)
+#endif /* MT_SPM_SSPM_INTC_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_notifier.c b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_notifier.c
new file mode 100644
index 0000000..e0ba037
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/notifier/mt_spm_sspm_notifier.c
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <lib/mmio.h>
+
+#include <mt_spm_notifier.h>
+#include <mt_spm_sspm_intc.h>
+
+#define MT_SPM_SSPM_MBOX_OFF(x)		(SSPM_MBOX_BASE + x)
+#define MT_SPM_MBOX(slot)		MT_SPM_SSPM_MBOX_OFF((slot << 2UL))
+
+#define SSPM_MBOX_SPM_LP_LOOKUP1	MT_SPM_MBOX(0)
+#define SSPM_MBOX_SPM_LP_LOOKUP2	MT_SPM_MBOX(1)
+#define SSPM_MBOX_SPM_LP1		MT_SPM_MBOX(2)
+#define SSPM_MBOX_SPM_LP2		MT_SPM_MBOX(3)
+
+#define MCUPM_MBOX_OFFSET_LP		0x0C55FDA4
+#define MCUPM_MBOX_ENTER_LP		0x454e0000
+#define MCUPM_MBOX_LEAVE_LP		0x4c450000
+#define MCUPM_MBOX_SLEEP_MASK		0x0000FFFF
+
+int mt_spm_sspm_notify(int type, unsigned int lp_mode)
+{
+	switch (type) {
+	case MT_SPM_NOTIFY_LP_ENTER:
+		mmio_write_32(SSPM_MBOX_SPM_LP1, lp_mode);
+		mmio_write_32(MCUPM_MBOX_OFFSET_LP, MCUPM_MBOX_ENTER_LP |
+			      (lp_mode & MCUPM_MBOX_SLEEP_MASK));
+		DO_SPM_SSPM_LP_SUSPEND();
+		break;
+	case MT_SPM_NOTIFY_LP_LEAVE:
+		mmio_write_32(SSPM_MBOX_SPM_LP1, lp_mode);
+		mmio_write_32(MCUPM_MBOX_OFFSET_LP, MCUPM_MBOX_LEAVE_LP |
+			      (lp_mode & MCUPM_MBOX_SLEEP_MASK));
+		DO_SPM_SSPM_LP_RESUME();
+		break;
+	default:
+		break;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8192/drivers/spm/pcm_def.h b/plat/mediatek/mt8192/drivers/spm/pcm_def.h
new file mode 100644
index 0000000..ab46b86
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/pcm_def.h
@@ -0,0 +1,179 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PCM_DEF_H
+#define PCM_DEF_H
+
+/*
+ * Auto generated by DE, please DO NOT modify this file directly.
+ */
+
+/* --- R0 Define --- */
+#define R0_SC_26M_CK_OFF			(1U << 0)
+#define R0_SC_TX_TRACK_RETRY_EN			(1U << 1)
+#define R0_SC_MEM_CK_OFF			(1U << 2)
+#define R0_SC_AXI_CK_OFF			(1U << 3)
+#define R0_SC_DR_SRAM_LOAD			(1U << 4)
+#define R0_SC_MD26M_CK_OFF			(1U << 5)
+#define R0_SC_DPY_MODE_SW			(1U << 6)
+#define R0_SC_DMSUS_OFF				(1U << 7)
+#define R0_SC_DPY_2ND_DLL_EN			(1U << 8)
+#define R0_SC_DR_SRAM_RESTORE			(1U << 9)
+#define R0_SC_MPLLOUT_OFF			(1U << 10)
+#define R0_SC_TX_TRACKING_DIS			(1U << 11)
+#define R0_SC_DPY_DLL_EN			(1U << 12)
+#define R0_SC_DPY_DLL_CK_EN			(1U << 13)
+#define R0_SC_DPY_VREF_EN			(1U << 14)
+#define R0_SC_PHYPLL_EN				(1U << 15)
+#define R0_SC_DDRPHY_FB_CK_EN			(1U << 16)
+#define R0_SC_DPY_BCLK_ENABLE			(1U << 17)
+#define R0_SC_MPLL_OFF				(1U << 18)
+#define R0_SC_SHU_RESTORE			(1U << 19)
+#define R0_SC_CKSQ0_OFF				(1U << 20)
+#define R0_SC_DR_SHU_LEVEL_SRAM_LATCH		(1U << 21)
+#define R0_SC_DR_SHU_EN				(1U << 22)
+#define R0_SC_DPHY_PRECAL_UP			(1U << 23)
+#define R0_SC_MPLL_S_OFF			(1U << 24)
+#define R0_SC_DPHY_RXDLY_TRACKING_EN		(1U << 25)
+#define R0_SC_PHYPLL_SHU_EN			(1U << 26)
+#define R0_SC_PHYPLL2_SHU_EN			(1U << 27)
+#define R0_SC_PHYPLL_MODE_SW			(1U << 28)
+#define R0_SC_PHYPLL2_MODE_SW			(1U << 29)
+#define R0_SC_DR_SHU_LEVEL0			(1U << 30)
+#define R0_SC_DR_SHU_LEVEL1			(1U << 31)
+/* --- R7 Define --- */
+#define R7_PWRAP_SLEEP_REQ			(1U << 0)
+#define R7_EMI_CLK_OFF_REQ			(1U << 1)
+#define R7_PCM_BUS_PROTECT_REQ			(1U << 2)
+#define R7_SPM_CK_UPDATE			(1U << 3)
+#define R7_SPM_CK_SEL0				(1U << 4)
+#define R7_SPM_CK_SEL1				(1U << 5)
+#define R7_SPM_LEAVE_DEEPIDLE_REQ		(1U << 6)
+#define R7_SC_FHC_PAUSE_MPLL			(1U << 7)
+#define R7_SC_26M_CK_SEL			(1U << 8)
+#define R7_PCM_TIMER_SET			(1U << 9)
+#define R7_PCM_TIMER_CLR			(1U << 10)
+#define R7_SPM_LEAVE_SUSPEND_REQ		(1U << 11)
+#define R7_CSYSPWRUPACK				(1U << 12)
+#define R7_PCM_IM_SLP_EN			(1U << 13)
+#define R7_SRCCLKENO0				(1U << 14)
+#define R7_FORCE_DDR_EN_WAKE			(1U << 15)
+#define R7_SPM_APSRC_INTERNAL_ACK		(1U << 16)
+#define R7_CPU_SYS_TIMER_CLK_SEL		(1U << 17)
+#define R7_SC_AXI_DCM_DIS			(1U << 18)
+#define R7_SC_FHC_PAUSE_MEM			(1U << 19)
+#define R7_SC_FHC_PAUSE_MAIN			(1U << 20)
+#define R7_SRCCLKENO1				(1U << 21)
+#define R7_PCM_WDT_KICK_P			(1U << 22)
+#define R7_SPM2EMI_S1_MODE_ASYNC		(1U << 23)
+#define R7_SC_DDR_PST_REQ_PCM			(1U << 24)
+#define R7_SC_DDR_PST_ABORT_REQ_PCM		(1U << 25)
+#define R7_PMIC_IRQ_REQ_EN			(1U << 26)
+#define R7_FORCE_F26M_WAKE			(1U << 27)
+#define R7_FORCE_APSRC_WAKE			(1U << 28)
+#define R7_FORCE_INFRA_WAKE			(1U << 29)
+#define R7_FORCE_VRF18_WAKE			(1U << 30)
+#define R7_SPM_DDR_EN_INTERNAL_ACK		(1U << 31)
+/* --- R12 Define --- */
+#define R12_PCM_TIMER				(1U << 0)
+#define R12_TWAM_IRQ_B				(1U << 1)
+#define R12_KP_IRQ_B				(1U << 2)
+#define R12_APWDT_EVENT_B			(1U << 3)
+#define R12_APXGPT1_EVENT_B			(1U << 4)
+#define R12_CONN2AP_SPM_WAKEUP_B		(1U << 5)
+#define R12_EINT_EVENT_B			(1U << 6)
+#define R12_CONN_WDT_IRQ_B			(1U << 7)
+#define R12_CCIF0_EVENT_B			(1U << 8)
+#define R12_LOWBATTERY_IRQ_B			(1U << 9)
+#define R12_SSPM2SPM_WAKEUP_B			(1U << 10)
+#define R12_SCP2SPM_WAKEUP_B			(1U << 11)
+#define R12_ADSP2SPM_WAKEUP_B			(1U << 12)
+#define R12_PCM_WDT_WAKEUP_B			(1U << 13)
+#define R12_USBX_CDSC_B				(1U << 14)
+#define R12_USBX_POWERDWN_B			(1U << 15)
+#define R12_SYS_TIMER_EVENT_B			(1U << 16)
+#define R12_EINT_EVENT_SECURE_B			(1U << 17)
+#define R12_CCIF1_EVENT_B			(1U << 18)
+#define R12_UART0_IRQ_B				(1U << 19)
+#define R12_AFE_IRQ_MCU_B			(1U << 20)
+#define R12_THERM_CTRL_EVENT_B			(1U << 21)
+#define R12_SYS_CIRQ_IRQ_B			(1U << 22)
+#define R12_MD2AP_PEER_EVENT_B			(1U << 23)
+#define R12_CSYSPWREQ_B				(1U << 24)
+#define R12_MD1_WDT_B				(1U << 25)
+#define R12_CLDMA_EVENT_B			(1U << 26)
+#define R12_SEJ_EVENT_B				(1U << 27)
+#define R12_REG_CPU_WAKEUP			(1U << 28)
+#define R12_APUSYS_WAKE_HOST_B			(1U << 29)
+#define R12_PCIE_BRIDGE_IRQ			(1U << 30)
+#define R12_PCIE_IRQ				(1U << 31)
+/* --- R12ext Define --- */
+#define R12EXT_26M_WAKE				(1U << 0)
+#define R12EXT_26M_SLEEP			(1U << 1)
+#define R12EXT_INFRA_WAKE			(1U << 2)
+#define R12EXT_INFRA_SLEEP			(1U << 3)
+#define R12EXT_APSRC_WAKE			(1U << 4)
+#define R12EXT_APSRC_SLEEP			(1U << 5)
+#define R12EXT_VRF18_WAKE			(1U << 6)
+#define R12EXT_VRF18_SLEEP			(1U << 7)
+#define R12EXT_DVFS_WAKE			(1U << 8)
+#define R12EXT_DDREN_WAKE			(1U << 9)
+#define R12EXT_DDREN_SLEEP			(1U << 10)
+#define R12EXT_MCU_PM_WFI			(1U << 11)
+#define R12EXT_SSPM_IDLE			(1U << 12)
+#define R12EXT_CONN_SRCCLKENB			(1U << 13)
+#define R12EXT_DRAMC_SSPM_WFI_MERGE		(1U << 14)
+#define R12EXT_SW_MAILBOX_WAKE			(1U << 15)
+#define R12EXT_SSPM_MAILBOX_WAKE		(1U << 16)
+#define R12EXT_ADSP_MAILBOX_WAKE		(1U << 17)
+#define R12EXT_SCP_MAILBOX_WAKE			(1U << 18)
+#define R12EXT_SPM_LEAVE_SUSPEND_ACK		(1U << 19)
+#define R12EXT_SPM_LEAVE_DEEPIDLE_ACK		(1U << 20)
+#define R12EXT_VS1_TRIGGER			(1U << 21)
+#define R12EXT_VS2_TRIGGER			(1U << 22)
+#define R12EXT_COROSS_REQ_APU			(1U << 23)
+#define R12EXT_CROSS_REQ_L3			(1U << 24)
+#define R12EXT_DDR_PST_ACK			(1U << 25)
+#define R12EXT_BIT26				(1U << 26)
+#define R12EXT_BIT27				(1U << 27)
+#define R12EXT_BIT28				(1U << 28)
+#define R12EXT_BIT29				(1U << 29)
+#define R12EXT_BIT30				(1U << 30)
+#define R12EXT_BIT31				(1U << 31)
+/* --- R13 Define --- */
+#define R13_SRCCLKENI0				(1U << 0)
+#define R13_SRCCLKENI1				(1U << 1)
+#define R13_MD_SRCCLKENA_0			(1U << 2)
+#define R13_MD_APSRC_REQ_0			(1U << 3)
+#define R13_CONN_DDR_EN				(1U << 4)
+#define R13_MD_SRCCLKENA_1			(1U << 5)
+#define R13_SSPM_SRCCLKENA			(1U << 6)
+#define R13_SSPM_APSRC_REQ			(1U << 7)
+#define R13_MD1_STATE				(1U << 8)
+#define R13_BIT9				(1U << 9)
+#define R13_MM_STATE				(1U << 10)
+#define R13_SSPM_STATE				(1U << 11)
+#define R13_MD_DDR_EN_0				(1U << 12)
+#define R13_CONN_STATE				(1U << 13)
+#define R13_CONN_SRCCLKENA			(1U << 14)
+#define R13_CONN_APSRC_REQ			(1U << 15)
+#define R13_SC_DDR_PST_ACK_ALL			(1U << 16)
+#define R13_SC_DDR_PST_ABORT_ACK_ALL		(1U << 17)
+#define R13_SCP_STATE				(1U << 18)
+#define R13_CSYSPWRUPREQ			(1U << 19)
+#define R13_PWRAP_SLEEP_ACK			(1U << 20)
+#define R13_SC_EMI_CLK_OFF_ACK_ALL		(1U << 21)
+#define R13_AUDIO_DSP_STATE			(1U << 22)
+#define R13_SC_DMDRAMCSHU_ACK_ALL		(1U << 23)
+#define R13_CONN_SRCCLKENB			(1U << 24)
+#define R13_SC_DR_SRAM_LOAD_ACK_ALL		(1U << 25)
+#define R13_SUBSYS_IDLE_SIGNALS0		(1U << 26)
+#define R13_DVFS_STATE				(1U << 27)
+#define R13_SC_DR_SRAM_PLL_LOAD_ACK_ALL		(1U << 28)
+#define R13_SC_DR_SRAM_RESTORE_ACK_ALL		(1U << 29)
+#define R13_MD_VRF18_REQ_0			(1U << 30)
+#define R13_DDR_EN_STATE			(1U << 31)
+#endif /* PCM_DEF_H */
diff --git a/plat/mediatek/mt8192/drivers/spm/sleep_def.h b/plat/mediatek/mt8192/drivers/spm/sleep_def.h
new file mode 100644
index 0000000..6c5cbed
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spm/sleep_def.h
@@ -0,0 +1,151 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SLEEP_DEF_H
+#define SLEEP_DEF_H
+
+/*
+ * Auto generated by DE, please DO NOT modify this file directly.
+ */
+
+/* --- SPM Flag Define --- */
+#define SPM_FLAG_DISABLE_CPU_PDN			(1U << 0)
+#define SPM_FLAG_DISABLE_INFRA_PDN			(1U << 1)
+#define SPM_FLAG_DISABLE_DDRPHY_PDN			(1U << 2)
+#define SPM_FLAG_DISABLE_VCORE_DVS			(1U << 3)
+#define SPM_FLAG_DISABLE_VCORE_DFS			(1U << 4)
+#define SPM_FLAG_DISABLE_COMMON_SCENARIO		(1U << 5)
+#define SPM_FLAG_DISABLE_BUS_CLK_OFF			(1U << 6)
+#define SPM_FLAG_DISABLE_ARMPLL_OFF			(1U << 7)
+#define SPM_FLAG_KEEP_CSYSPWRACK_HIGH			(1U << 8)
+#define SPM_FLAG_ENABLE_LVTS_WORKAROUND			(1U << 9)
+#define SPM_FLAG_RUN_COMMON_SCENARIO			(1U << 10)
+#define SPM_FLAG_RESERVED_BIT11				(1U << 11)
+#define SPM_FLAG_ENABLE_SPM_DBG_WDT_DUMP		(1U << 12)
+#define SPM_FLAG_USE_SRCCLKENO2				(1U << 13)
+#define SPM_FLAG_ENABLE_6315_CTRL			(1U << 14)
+#define SPM_FLAG_ENABLE_TIA_WORKAROUND			(1U << 15)
+#define SPM_FLAG_DISABLE_SYSRAM_SLEEP			(1U << 16)
+#define SPM_FLAG_DISABLE_SSPM_SRAM_SLEEP		(1U << 17)
+#define SPM_FLAG_DISABLE_MCUPM_SRAM_SLEEP		(1U << 18)
+#define SPM_FLAG_ENABLE_MD_MUMTAS			(1U << 19)
+#define SPM_FLAG_ENABLE_VOLTAGE_BIN			(1U << 20)
+#define SPM_FLAG_RESERVED_BIT21				(1U << 21)
+#define SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP		(1U << 22)
+#define SPM_FLAG_DISABLE_SRAM_EVENT			(1U << 23)
+#define SPM_FLAG_RESERVED_BIT24				(1U << 24)
+#define SPM_FLAG_RESERVED_BIT25				(1U << 25)
+#define SPM_FLAG_RESERVED_BIT26				(1U << 26)
+#define SPM_FLAG_VTCXO_STATE				(1U << 27)
+#define SPM_FLAG_INFRA_STATE				(1U << 28)
+#define SPM_FLAG_APSRC_STATE				(1U << 29)
+#define SPM_FLAG_VRF18_STATE				(1U << 30)
+#define SPM_FLAG_DDREN_STATE				(1U << 31)
+/* --- SPM Flag1 Define --- */
+#define SPM_FLAG1_DISABLE_AXI_BUS_TO_26M		(1U << 0)
+#define SPM_FLAG1_DISABLE_SYSPLL_OFF			(1U << 1)
+#define SPM_FLAG1_DISABLE_PWRAP_CLK_SWITCH		(1U << 2)
+#define SPM_FLAG1_DISABLE_ULPOSC_OFF			(1U << 3)
+#define SPM_FLAG1_FW_SET_ULPOSC_ON			(1U << 4)
+#define SPM_FLAG1_RESERVED_BIT5				(1U << 5)
+#define SPM_FLAG1_ENABLE_REKICK				(1U << 6)
+#define SPM_FLAG1_DISABLE_MD26M_CK_OFF			(1U << 7)
+#define SPM_FLAG1_RESERVED_BIT8				(1U << 8)
+#define SPM_FLAG1_RESERVED_BIT9				(1U << 9)
+#define SPM_FLAG1_DISABLE_SRCLKEN_LOW			(1U << 10)
+#define SPM_FLAG1_DISABLE_SCP_CLK_SWITCH		(1U << 11)
+#define SPM_FLAG1_RESERVED_BIT12			(1U << 12)
+#define SPM_FLAG1_RESERVED_BIT13			(1U << 13)
+#define SPM_FLAG1_RESERVED_BIT14			(1U << 14)
+#define SPM_FLAG1_RESERVED_BIT15			(1U << 15)
+#define SPM_FLAG1_RESERVED_BIT16			(1U << 16)
+#define SPM_FLAG1_RESERVED_BIT17			(1U << 17)
+#define SPM_FLAG1_RESERVED_BIT18			(1U << 18)
+#define SPM_FLAG1_RESERVED_BIT19			(1U << 19)
+#define SPM_FLAG1_DISABLE_DEVAPC_SRAM_SLEEP		(1U << 20)
+#define SPM_FLAG1_RESERVED_BIT21			(1U << 21)
+#define SPM_FLAG1_ENABLE_VS1_VOTER			(1U << 22)
+#define SPM_FLAG1_ENABLE_VS2_VOTER			(1U << 23)
+#define SPM_FLAG1_DISABLE_SCP_VREQ_MASK_CONTROL		(1U << 24)
+#define SPM_FLAG1_RESERVED_BIT25			(1U << 25)
+#define SPM_FLAG1_RESERVED_BIT26			(1U << 26)
+#define SPM_FLAG1_RESERVED_BIT27			(1U << 27)
+#define SPM_FLAG1_RESERVED_BIT28			(1U << 28)
+#define SPM_FLAG1_RESERVED_BIT29			(1U << 29)
+#define SPM_FLAG1_RESERVED_BIT30			(1U << 30)
+#define SPM_FLAG1_DISABLE_CPUEB_OFF			(1U << 31)
+/* --- SPM DEBUG Define --- */
+#define SPM_DBG_DEBUG_IDX_26M_WAKE			(1U << 0)
+#define SPM_DBG_DEBUG_IDX_26M_SLEEP			(1U << 1)
+#define SPM_DBG_DEBUG_IDX_INFRA_WAKE			(1U << 2)
+#define SPM_DBG_DEBUG_IDX_INFRA_SLEEP			(1U << 3)
+#define SPM_DBG_DEBUG_IDX_APSRC_WAKE			(1U << 4)
+#define SPM_DBG_DEBUG_IDX_APSRC_SLEEP			(1U << 5)
+#define SPM_DBG_DEBUG_IDX_VRF18_WAKE			(1U << 6)
+#define SPM_DBG_DEBUG_IDX_VRF18_SLEEP			(1U << 7)
+#define SPM_DBG_DEBUG_IDX_DDREN_WAKE			(1U << 8)
+#define SPM_DBG_DEBUG_IDX_DDREN_SLEEP			(1U << 9)
+#define SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_APSRC	(1U << 10)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_STATE		(1U << 11)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_STATE		(1U << 12)
+#define SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_DDREN	(1U << 13)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_STATE		(1U << 14)
+#define SPM_DBG_DEBUG_IDX_SYSRAM_SLP			(1U << 15)
+#define SPM_DBG_DEBUG_IDX_SYSRAM_ON			(1U << 16)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_SLP		(1U << 17)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_ON			(1U << 18)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_SLP			(1U << 19)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_ON			(1U << 20)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_SLP		(1U << 21)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_ON		(1U << 22)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P575V		(1U << 23)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P600V		(1U << 24)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P650V		(1U << 25)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P725V		(1U << 26)
+#define SPM_DBG_DEBUG_IDX_SPM_GO_WAKEUP_NOW		(1U << 27)
+#define SPM_DBG_DEBUG_IDX_VTCXO_STATE			(1U << 28)
+#define SPM_DBG_DEBUG_IDX_INFRA_STATE			(1U << 29)
+#define SPM_DBG_DEBUG_IDX_VRR18_STATE			(1U << 30)
+#define SPM_DBG_DEBUG_IDX_APSRC_STATE			(1U << 31)
+/* --- SPM DEBUG1 Define --- */
+#define SPM_DBG1_DEBUG_IDX_CURRENT_IS_LP		(1U << 0)
+#define SPM_DBG1_DEBUG_IDX_VCORE_DVFS_START		(1U << 1)
+#define SPM_DBG1_DEBUG_IDX_SYSPLL_OFF			(1U << 2)
+#define SPM_DBG1_DEBUG_IDX_SYSPLL_ON			(1U << 3)
+#define SPM_DBG1_DEBUG_IDX_CURRENT_IS_VCORE_DVFS	(1U << 4)
+#define SPM_DBG1_DEBUG_IDX_INFRA_MTCMOS_OFF		(1U << 5)
+#define SPM_DBG1_DEBUG_IDX_INFRA_MTCMOS_ON		(1U << 6)
+#define SPM_DBG1_DEBUG_IDX_VRCXO_SLEEP_ABORT		(1U << 7)
+#define SPM_DBG1_RESERVED_BIT8				(1U << 8)
+#define SPM_DBG1_DEBUG_IDX_INFRA_SUB_MTCMOS_OFF		(1U << 9)
+#define SPM_DBG1_DEBUG_IDX_INFRA_SUB_MTCMOS_ON		(1U << 10)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_CLK_TO_ULPOSC		(1U << 11)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_CLK_TO_26M		(1U << 12)
+#define SPM_DBG1_DEBUG_IDX_SCP_CLK_TO_32K		(1U << 13)
+#define SPM_DBG1_DEBUG_IDX_SCP_CLK_TO_26M		(1U << 14)
+#define SPM_DBG1_DEBUG_IDX_BUS_CLK_OFF			(1U << 15)
+#define SPM_DBG1_DEBUG_IDX_BUS_CLK_ON			(1U << 16)
+#define SPM_DBG1_DEBUG_IDX_SRCLKEN2_LOW			(1U << 17)
+#define SPM_DBG1_DEBUG_IDX_SRCLKEN2_HIGH		(1U << 18)
+#define SPM_DBG1_RESERVED_BIT19				(1U << 19)
+#define SPM_DBG1_DEBUG_IDX_ULPOSC_IS_OFF_BUT_SHOULD_ON	(1U << 20)
+#define SPM_DBG1_DEBUG_IDX_6315_LOW			(1U << 21)
+#define SPM_DBG1_DEBUG_IDX_6315_HIGH			(1U << 22)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_LOW_ABORT	(1U << 23)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_HIGH_ABORT	(1U << 24)
+#define SPM_DBG1_DEBUG_IDX_EMI_SLP_IDLE_ABORT		(1U << 25)
+#define SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_LOW_ABORT	(1U << 26)
+#define SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_HIGH_ABORT	(1U << 27)
+#define SPM_DBG1_DEBUG_IDX_SPM_DVFS_CMD_RDY_ABORT	(1U << 28)
+#define SPM_DBG1_RESERVED_BIT29				(1U << 29)
+#define SPM_DBG1_RESERVED_BIT30				(1U << 30)
+#define SPM_DBG1_DEBUG_DISABLE_CPUEB_OFF		(1U << 31)
+
+ /* Macro and Inline */
+#define is_cpu_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_CPU_PDN) == 0U)
+#define is_infra_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_INFRA_PDN) == 0U)
+#define is_ddrphy_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_DDRPHY_PDN) == 0U)
+#endif /* SLEEP_DEF_H */
diff --git a/plat/mediatek/mt8192/drivers/spmc/mtspmc.c b/plat/mediatek/mt8192/drivers/spmc/mtspmc.c
new file mode 100644
index 0000000..7ccebd6
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spmc/mtspmc.c
@@ -0,0 +1,177 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include <mcucfg.h>
+#include <mtspmc.h>
+#include <mtspmc_private.h>
+
+
+void mcucfg_disable_gic_wakeup(uint32_t cluster, uint32_t cpu)
+{
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(cpu));
+}
+
+void mcucfg_enable_gic_wakeup(uint32_t cluster, uint32_t cpu)
+{
+	mmio_clrbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(cpu));
+}
+
+void mcucfg_set_bootaddr(uint32_t cluster, uint32_t cpu, uintptr_t bootaddr)
+{
+	assert(cluster == 0U);
+
+	mmio_write_32(per_cpu(cluster, cpu, MCUCFG_BOOTADDR), bootaddr);
+}
+
+uintptr_t mcucfg_get_bootaddr(uint32_t cluster, uint32_t cpu)
+{
+	assert(cluster == 0U);
+
+	return (uintptr_t)mmio_read_32(per_cpu(cluster, cpu, MCUCFG_BOOTADDR));
+}
+
+void mcucfg_init_archstate(uint32_t cluster, uint32_t cpu, bool arm64)
+{
+	uint32_t reg;
+
+	assert(cluster == 0U);
+
+	reg = per_cluster(cluster, MCUCFG_INITARCH);
+
+	if (arm64) {
+		mmio_setbits_32(reg, MCUCFG_INITARCH_CPU_BIT(cpu));
+	} else {
+		mmio_clrbits_32(reg, MCUCFG_INITARCH_CPU_BIT(cpu));
+	}
+}
+
+/**
+ * Return subsystem's power state.
+ *
+ * @mask: mask to SPM_CPU_PWR_STATUS to query the power state
+ *        of one subsystem.
+ * RETURNS:
+ * 0 (the subsys was powered off)
+ * 1 (the subsys was powered on)
+ */
+bool spm_get_powerstate(uint32_t mask)
+{
+	return (mmio_read_32(SPM_CPU_PWR_STATUS) & mask) != 0U;
+}
+
+bool spm_get_cluster_powerstate(uint32_t cluster)
+{
+	assert(cluster == 0U);
+
+	return spm_get_powerstate(MP0_CPUTOP);
+}
+
+bool spm_get_cpu_powerstate(uint32_t cluster, uint32_t cpu)
+{
+	uint32_t mask = BIT(cpu);
+
+	assert(cluster == 0U);
+
+	return spm_get_powerstate(mask);
+}
+
+int spmc_init(void)
+{
+	INFO("SPM: enable CPC mode\n");
+
+	mmio_write_32(SPM_POWERON_CONFIG_EN, PROJECT_CODE | BCLK_CG_EN);
+
+	mmio_setbits_32(per_cpu(0, 1, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 2, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 3, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 4, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 5, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 6, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 7, SPM_CPU_PWR), PWR_RST_B);
+
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(1));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(2));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(3));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(4));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(5));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(6));
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(7));
+
+	mmio_clrbits_32(SPM_MCUSYS_PWR_CON, RESETPWRON_CONFIG);
+	mmio_clrbits_32(SPM_MP0_CPUTOP_PWR_CON, RESETPWRON_CONFIG);
+	mmio_clrbits_32(per_cpu(0, 0, SPM_CPU_PWR), RESETPWRON_CONFIG);
+
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, CPC_CTRL_ENABLE);
+
+	return 0;
+}
+
+/**
+ * Power on a core with specified cluster and core index
+ *
+ * @cluster: the cluster ID of the CPU which to be powered on
+ * @cpu: the CPU ID of the CPU which to be powered on
+ */
+void spm_poweron_cpu(uint32_t cluster, uint32_t cpu)
+{
+	/* set to 0 after BIG VPROC bulk on & before B-core power on seq. */
+	if (cpu >= 4U) {
+		mmio_write_32(DREQ20_BIG_VPROC_ISO, 0U);
+	}
+
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, SSPM_ALL_PWR_CTRL_EN);
+	mmio_setbits_32(per_cpu(cluster, cpu, SPM_CPU_PWR), PWR_ON);
+
+	while (!spm_get_cpu_powerstate(cluster, cpu)) {
+	}
+
+	mmio_clrbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, SSPM_ALL_PWR_CTRL_EN);
+
+	/* Enable Big CPU Last PC */
+	if (cpu >= 4U) {
+		mmio_clrbits_32(LAST_PC_REG(cpu), BIT(3));
+	}
+}
+
+/**
+ * Power off a core with specified cluster and core index
+ *
+ * @cluster: the cluster ID of the CPU which to be powered off
+ * @cpu: the CPU ID of the CPU which to be powered off
+ */
+void spm_poweroff_cpu(uint32_t cluster, uint32_t cpu)
+{
+	/* Set mp0_spmc_pwr_on_cpuX = 0 */
+	mmio_clrbits_32(per_cpu(cluster, cpu, SPM_CPU_PWR), PWR_ON);
+}
+
+/**
+ * Power off a cluster with specified index
+ *
+ * @cluster: the cluster index which to be powered off
+ */
+void spm_poweroff_cluster(uint32_t cluster)
+{
+	/* No need to power on/off cluster on single cluster platform */
+	assert(false);
+}
+
+/**
+ * Power on a cluster with specified index
+ *
+ * @cluster: the cluster index which to be powered on
+ */
+void spm_poweron_cluster(uint32_t cluster)
+{
+	/* No need to power on/off cluster on single cluster platform */
+	assert(false);
+}
diff --git a/plat/mediatek/mt8192/drivers/spmc/mtspmc.h b/plat/mediatek/mt8192/drivers/spmc/mtspmc.h
new file mode 100644
index 0000000..7ed2e62
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spmc/mtspmc.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTSPMC_H
+#define MTSPMC_H
+
+#include <stdint.h>
+
+int spmc_init(void);
+
+void spm_poweron_cpu(uint32_t cluster, uint32_t cpu);
+void spm_poweroff_cpu(uint32_t cluster, uint32_t cpu);
+
+void spm_poweroff_cluster(uint32_t cluster);
+void spm_poweron_cluster(uint32_t cluster);
+
+bool spm_get_cpu_powerstate(uint32_t cluster, uint32_t cpu);
+bool spm_get_cluster_powerstate(uint32_t cluster);
+bool spm_get_powerstate(uint32_t mask);
+
+void mcucfg_init_archstate(uint32_t cluster, uint32_t cpu, bool arm64);
+void mcucfg_set_bootaddr(uint32_t cluster, uint32_t cpu, uintptr_t bootaddr);
+uintptr_t mcucfg_get_bootaddr(uint32_t cluster, uint32_t cpu);
+
+void mcucfg_disable_gic_wakeup(uint32_t cluster, uint32_t cpu);
+void mcucfg_enable_gic_wakeup(uint32_t cluster, uint32_t cpu);
+
+#endif /* MTSPMC_H */
diff --git a/plat/mediatek/mt8192/drivers/spmc/mtspmc_private.h b/plat/mediatek/mt8192/drivers/spmc/mtspmc_private.h
new file mode 100644
index 0000000..ad78295
--- /dev/null
+++ b/plat/mediatek/mt8192/drivers/spmc/mtspmc_private.h
@@ -0,0 +1,184 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTSPMC_PRIVATE_H
+#define MTSPMC_PRIVATE_H
+
+#include <lib/utils_def.h>
+#include <platform_def.h>
+
+unsigned long read_cpuectlr(void);
+void write_cpuectlr(unsigned long cpuectlr);
+
+unsigned long read_cpupwrctlr_el1(void);
+void write_cpupwrctlr_el1(unsigned long cpuectlr);
+
+/*
+ * per_cpu/cluster helper
+ */
+struct per_cpu_reg {
+	unsigned int cluster_addr;
+	unsigned int cpu_stride;
+};
+
+#define per_cpu(cluster, cpu, reg)	\
+	(reg[cluster].cluster_addr + (cpu << reg[cluster].cpu_stride))
+
+#define per_cluster(cluster, reg)	(reg[cluster].cluster_addr)
+
+#define SPM_REG(ofs)			(uint32_t)(SPM_BASE + (ofs))
+#define MCUCFG_REG(ofs)			(uint32_t)(MCUCFG_BASE + (ofs))
+#define INFRACFG_AO_REG(ofs)		(uint32_t)(INFRACFG_AO_BASE + (ofs))
+
+/* === SPMC related registers */
+#define SPM_POWERON_CONFIG_EN		SPM_REG(0x000)
+/* bit-fields of SPM_POWERON_CONFIG_EN */
+#define PROJECT_CODE			(U(0xb16) << 16)
+#define BCLK_CG_EN			BIT(0)
+
+#define SPM_PWR_STATUS			SPM_REG(0x16c)
+#define SPM_PWR_STATUS_2ND		SPM_REG(0x170)
+#define SPM_CPU_PWR_STATUS		SPM_REG(0x174)
+
+/* bit-fields of SPM_PWR_STATUS */
+#define MD				BIT(0)
+#define CONN				BIT(1)
+#define DDRPHY				BIT(2)
+#define DISP				BIT(3)
+#define MFG				BIT(4)
+#define ISP				BIT(5)
+#define INFRA				BIT(6)
+#define VDEC				BIT(7)
+#define MP0_CPUTOP			BIT(8)
+#define MP0_CPU0			BIT(9)
+#define MP0_CPU1			BIT(10)
+#define MP0_CPU2			BIT(11)
+#define MP0_CPU3			BIT(12)
+#define MCUSYS				BIT(14)
+#define MP0_CPU4			BIT(15)
+#define MP0_CPU5			BIT(16)
+#define MP0_CPU6			BIT(17)
+#define MP0_CPU7			BIT(18)
+#define VEN				BIT(21)
+
+/* === SPMC related registers */
+#define SPM_MCUSYS_PWR_CON		MCUCFG_REG(0xd200)
+#define SPM_MP0_CPUTOP_PWR_CON		MCUCFG_REG(0xd204)
+#define SPM_MP0_CPU0_PWR_CON		MCUCFG_REG(0xd208)
+#define SPM_MP0_CPU1_PWR_CON		MCUCFG_REG(0xd20c)
+#define SPM_MP0_CPU2_PWR_CON		MCUCFG_REG(0xd210)
+#define SPM_MP0_CPU3_PWR_CON		MCUCFG_REG(0xd214)
+#define SPM_MP0_CPU4_PWR_CON		MCUCFG_REG(0xd218)
+#define SPM_MP0_CPU5_PWR_CON		MCUCFG_REG(0xd21c)
+#define SPM_MP0_CPU6_PWR_CON		MCUCFG_REG(0xd220)
+#define SPM_MP0_CPU7_PWR_CON		MCUCFG_REG(0xd224)
+
+/* bit fields of SPM_*_PWR_CON */
+#define PWR_ON_ACK			BIT(31)
+#define VPROC_EXT_OFF			BIT(7)
+#define DORMANT_EN			BIT(6)
+#define RESETPWRON_CONFIG		BIT(5)
+#define PWR_CLK_DIS			BIT(4)
+#define PWR_ON				BIT(2)
+#define PWR_RST_B			BIT(0)
+
+/**** per_cpu registers for SPM_MP0_CPU?_PWR_CON */
+static const struct per_cpu_reg SPM_CPU_PWR[] = {
+	{ .cluster_addr = SPM_MP0_CPU0_PWR_CON, .cpu_stride = 2U }
+};
+
+/**** per_cluster registers for SPM_MP0_CPUTOP_PWR_CON */
+static const struct per_cpu_reg SPM_CLUSTER_PWR[] = {
+	{ .cluster_addr = SPM_MP0_CPUTOP_PWR_CON, .cpu_stride = 0U }
+};
+
+/* === MCUCFG related registers */
+/* aa64naa32 */
+#define MCUCFG_MP0_CLUSTER_CFG5		MCUCFG_REG(0xc8e4)
+/* reset vectors */
+#define MCUCFG_MP0_CLUSTER_CFG8		MCUCFG_REG(0xc900)
+#define MCUCFG_MP0_CLUSTER_CFG10	MCUCFG_REG(0xc908)
+#define MCUCFG_MP0_CLUSTER_CFG12	MCUCFG_REG(0xc910)
+#define MCUCFG_MP0_CLUSTER_CFG14	MCUCFG_REG(0xc918)
+#define MCUCFG_MP0_CLUSTER_CFG16	MCUCFG_REG(0xc920)
+#define MCUCFG_MP0_CLUSTER_CFG18	MCUCFG_REG(0xc928)
+#define MCUCFG_MP0_CLUSTER_CFG20	MCUCFG_REG(0xc930)
+#define MCUCFG_MP0_CLUSTER_CFG22	MCUCFG_REG(0xc938)
+
+/* MCUSYS DREQ BIG VPROC ISO control */
+#define DREQ20_BIG_VPROC_ISO		MCUCFG_REG(0xad8c)
+
+/**** per_cpu registers for MCUCFG_MP0_CLUSTER_CFG? */
+static const struct per_cpu_reg MCUCFG_BOOTADDR[] = {
+	{ .cluster_addr = MCUCFG_MP0_CLUSTER_CFG8, .cpu_stride = 3U }
+};
+
+/**** per_cpu registers for MCUCFG_MP0_CLUSTER_CFG5 */
+static const struct per_cpu_reg MCUCFG_INITARCH[] = {
+	{ .cluster_addr = MCUCFG_MP0_CLUSTER_CFG5, .cpu_stride = 0U }
+};
+
+#define MCUCFG_INITARCH_CPU_BIT(cpu)	BIT(16U + cpu)
+#define LAST_PC_REG(cpu)		(MCUCFG_REG(0x308) + (cpu * 0x800))
+
+/* === CPC control */
+#define MCUCFG_CPC_FLOW_CTRL_CFG	MCUCFG_REG(0xa814)
+#define MCUCFG_CPC_SPMC_PWR_STATUS	MCUCFG_REG(0xa840)
+
+/* bit fields of CPC_FLOW_CTRL_CFG */
+#define CPC_CTRL_ENABLE			BIT(16)
+#define SSPM_ALL_PWR_CTRL_EN		BIT(13) /* for cpu-hotplug */
+#define GIC_WAKEUP_IGNORE(cpu)		BIT(21 + cpu)
+
+/* bit fields of CPC_SPMC_PWR_STATUS */
+#define CORE_SPMC_PWR_ON_ACK		GENMASK(15, 0)
+
+/* === APB Module infracfg_ao */
+#define INFRA_TOPAXI_PROTECTEN		INFRACFG_AO_REG(0x0220)
+#define INFRA_TOPAXI_PROTECTEN_STA0	INFRACFG_AO_REG(0x0224)
+#define INFRA_TOPAXI_PROTECTEN_STA1	INFRACFG_AO_REG(0x0228)
+#define INFRA_TOPAXI_PROTECTEN_SET	INFRACFG_AO_REG(0x02a0)
+#define INFRA_TOPAXI_PROTECTEN_CLR	INFRACFG_AO_REG(0x02a4)
+#define INFRA_TOPAXI_PROTECTEN_1	INFRACFG_AO_REG(0x0250)
+#define INFRA_TOPAXI_PROTECTEN_STA0_1	INFRACFG_AO_REG(0x0254)
+#define INFRA_TOPAXI_PROTECTEN_STA1_1	INFRACFG_AO_REG(0x0258)
+#define INFRA_TOPAXI_PROTECTEN_1_SET	INFRACFG_AO_REG(0x02a8)
+#define INFRA_TOPAXI_PROTECTEN_1_CLR	INFRACFG_AO_REG(0x02ac)
+
+/* bit fields of INFRA_TOPAXI_PROTECTEN */
+#define MP0_SPMC_PROT_STEP1_0_MASK	BIT(12)
+#define MP0_SPMC_PROT_STEP1_1_MASK	(BIT(26) | BIT(12))
+
+/* === SPARK */
+#define VOLTAGE_04			U(0x40)
+#define VOLTAGE_05			U(0x60)
+
+#define PTP3_CPU0_SPMC_SW_CFG		MCUCFG_REG(0x200)
+#define CPU0_ILDO_CONTROL5		MCUCFG_REG(0x334)
+#define CPU0_ILDO_CONTROL8		MCUCFG_REG(0x340)
+
+/* bit fields of CPU0_ILDO_CONTROL5 */
+#define ILDO_RET_VOSEL			GENMASK(7, 0)
+
+/* bit fields of PTP3_CPU_SPMC_SW_CFG */
+#define SW_SPARK_EN			BIT(0)
+
+/* bit fields of CPU0_ILDO_CONTROL8 */
+#define ILDO_BYPASS_B			BIT(0)
+
+static const struct per_cpu_reg MCUCFG_SPARK[] = {
+	{ .cluster_addr = PTP3_CPU0_SPMC_SW_CFG, .cpu_stride = 11U }
+};
+
+static const struct per_cpu_reg ILDO_CONTROL5[] = {
+	{ .cluster_addr = CPU0_ILDO_CONTROL5, .cpu_stride = 11U }
+};
+
+static const struct per_cpu_reg ILDO_CONTROL8[] = {
+	{ .cluster_addr = CPU0_ILDO_CONTROL8, .cpu_stride = 11U }
+};
+
+#endif /* MTSPMC_PRIVATE_H */
diff --git a/plat/mediatek/mt8192/drivers/timer/mt_timer.c b/plat/mediatek/mt8192/drivers/timer/mt_timer.c
deleted file mode 100644
index 781f940..0000000
--- a/plat/mediatek/mt8192/drivers/timer/mt_timer.c
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (c) 2020, MediaTek Inc. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch_helpers.h>
-#include <mt_timer.h>
-#include <platform_def.h>
-
-
-uint64_t normal_time_base;
-uint64_t atf_time_base;
-
-void sched_clock_init(uint64_t normal_base, uint64_t atf_base)
-{
-	normal_time_base += normal_base;
-	atf_time_base = atf_base;
-}
-
-uint64_t sched_clock(void)
-{
-	uint64_t cval;
-	uint64_t rel_base;
-
-	rel_base = read_cntpct_el0() - atf_time_base;
-	cval = ((rel_base * 1000U) / SYS_COUNTER_FREQ_IN_MHZ)
-		- normal_time_base;
-	return cval;
-}
diff --git a/plat/mediatek/mt8192/drivers/timer/mt_timer.h b/plat/mediatek/mt8192/drivers/timer/mt_timer.h
deleted file mode 100644
index 7aca4a3..0000000
--- a/plat/mediatek/mt8192/drivers/timer/mt_timer.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (c) 2020, MediaTek Inc. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef MT_TIMER_H
-#define MT_TIMER_H
-
-#define SYSTIMER_BASE       (0x10017000)
-#define CNTCR_REG           (SYSTIMER_BASE + 0x0)
-#define CNTSR_REG           (SYSTIMER_BASE + 0x4)
-#define CNTSYS_L_REG        (SYSTIMER_BASE + 0x8)
-#define CNTSYS_H_REG        (SYSTIMER_BASE + 0xc)
-
-#define TIEO_EN             (1 << 3)
-#define COMP_15_EN          (1 << 10)
-#define COMP_20_EN          (1 << 11)
-#define COMP_25_EN          (1 << 12)
-
-#define COMP_FEATURE_MASK (COMP_15_EN | COMP_20_EN | COMP_25_EN | TIEO_EN)
-#define COMP_15_MASK (COMP_15_EN)
-#define COMP_20_MASK (COMP_20_EN | TIEO_EN)
-#define COMP_25_MASK (COMP_20_EN | COMP_25_EN)
-
-
-void sched_clock_init(uint64_t normal_base, uint64_t atf_base);
-uint64_t sched_clock(void);
-
-#endif /* MT_TIMER_H */
diff --git a/plat/mediatek/mt8192/include/mcucfg.h b/plat/mediatek/mt8192/include/mcucfg.h
new file mode 100644
index 0000000..046cf73
--- /dev/null
+++ b/plat/mediatek/mt8192/include/mcucfg.h
@@ -0,0 +1,257 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MCUCFG_H
+#define MCUCFG_H
+
+#ifndef __ASSEMBLER__
+#include <stdint.h>
+#endif /* __ASSEMBLER__ */
+
+#include <platform_def.h>
+
+#define MCUCFG_REG(ofs)			(uint32_t)(MCUCFG_BASE + (ofs))
+
+#define MP2_MISC_CONFIG_BOOT_ADDR_L(cpu) (MCUCFG_REG(0x2290) + ((cpu) * 8))
+#define MP2_MISC_CONFIG_BOOT_ADDR_H(cpu) (MCUCFG_REG(0x2294) + ((cpu) * 8))
+
+#define MP2_CPUCFG			MCUCFG_REG(0x2208)
+
+#define MP2_CPU0_STANDBYWFE		BIT(4)
+#define MP2_CPU1_STANDBYWFE		BIT(5)
+
+#define MP0_CPUTOP_SPMC_CTL		MCUCFG_REG(0x788)
+#define MP1_CPUTOP_SPMC_CTL		MCUCFG_REG(0x78C)
+#define MP1_CPUTOP_SPMC_SRAM_CTL	MCUCFG_REG(0x790)
+
+#define sw_spark_en			BIT(0)
+#define sw_no_wait_for_q_channel	BIT(1)
+#define sw_fsm_override			BIT(2)
+#define sw_logic_pre1_pdb		BIT(3)
+#define sw_logic_pre2_pdb		BIT(4)
+#define sw_logic_pdb			BIT(5)
+#define sw_iso				BIT(6)
+#define sw_sram_sleepb			(U(0x3F) << 7)
+#define sw_sram_isointb			BIT(13)
+#define sw_clk_dis			BIT(14)
+#define sw_ckiso			BIT(15)
+#define sw_pd				(U(0x3F) << 16)
+#define sw_hot_plug_reset		BIT(22)
+#define sw_pwr_on_override_en		BIT(23)
+#define sw_pwr_on			BIT(24)
+#define sw_coq_dis			BIT(25)
+#define logic_pdbo_all_off_ack		BIT(26)
+#define logic_pdbo_all_on_ack		BIT(27)
+#define logic_pre2_pdbo_all_on_ack	BIT(28)
+#define logic_pre1_pdbo_all_on_ack	BIT(29)
+
+
+#define CPUSYSx_CPUx_SPMC_CTL(cluster, cpu) \
+	(MCUCFG_REG(0x1c30) + cluster * 0x2000 + cpu * 4)
+
+#define CPUSYS0_CPU0_SPMC_CTL		MCUCFG_REG(0x1c30)
+#define CPUSYS0_CPU1_SPMC_CTL		MCUCFG_REG(0x1c34)
+#define CPUSYS0_CPU2_SPMC_CTL		MCUCFG_REG(0x1c38)
+#define CPUSYS0_CPU3_SPMC_CTL		MCUCFG_REG(0x1c3C)
+
+#define CPUSYS1_CPU0_SPMC_CTL		MCUCFG_REG(0x3c30)
+#define CPUSYS1_CPU1_SPMC_CTL		MCUCFG_REG(0x3c34)
+#define CPUSYS1_CPU2_SPMC_CTL		MCUCFG_REG(0x3c38)
+#define CPUSYS1_CPU3_SPMC_CTL		MCUCFG_REG(0x3c3C)
+
+#define cpu_sw_spark_en			BIT(0)
+#define cpu_sw_no_wait_for_q_channel	BIT(1)
+#define cpu_sw_fsm_override		BIT(2)
+#define cpu_sw_logic_pre1_pdb		BIT(3)
+#define cpu_sw_logic_pre2_pdb		BIT(4)
+#define cpu_sw_logic_pdb		BIT(5)
+#define cpu_sw_iso			BIT(6)
+#define cpu_sw_sram_sleepb		BIT(7)
+#define cpu_sw_sram_isointb		BIT(8)
+#define cpu_sw_clk_dis			BIT(9)
+#define cpu_sw_ckiso			BIT(10)
+#define cpu_sw_pd			(U(0x1F) << 11)
+#define cpu_sw_hot_plug_reset		BIT(16)
+#define cpu_sw_powr_on_override_en	BIT(17)
+#define cpu_sw_pwr_on			BIT(18)
+#define cpu_spark2ldo_allswoff		BIT(19)
+#define cpu_pdbo_all_on_ack		BIT(20)
+#define cpu_pre2_pdbo_allon_ack		BIT(21)
+#define cpu_pre1_pdbo_allon_ack		BIT(22)
+
+/* CPC related registers */
+#define CPC_MCUSYS_CPC_OFF_THRES	MCUCFG_REG(0xa714)
+#define CPC_MCUSYS_PWR_CTRL		MCUCFG_REG(0xa804)
+#define CPC_MCUSYS_CPC_FLOW_CTRL_CFG	MCUCFG_REG(0xa814)
+#define CPC_MCUSYS_LAST_CORE_REQ	MCUCFG_REG(0xa818)
+#define CPC_MCUSYS_MP_LAST_CORE_RESP	MCUCFG_REG(0xa81c)
+#define CPC_MCUSYS_LAST_CORE_RESP	MCUCFG_REG(0xa824)
+#define CPC_MCUSYS_PWR_ON_MASK		MCUCFG_REG(0xa828)
+#define CPC_MCUSYS_CPU_ON_SW_HINT_SET	MCUCFG_REG(0xa8a8)
+#define CPC_MCUSYS_CPU_ON_SW_HINT_CLR	MCUCFG_REG(0xa8ac)
+#define CPC_MCUSYS_CPC_DBG_SETTING	MCUCFG_REG(0xab00)
+#define CPC_MCUSYS_CPC_KERNEL_TIME_L_BASE	MCUCFG_REG(0xab04)
+#define CPC_MCUSYS_CPC_KERNEL_TIME_H_BASE	MCUCFG_REG(0xab08)
+#define CPC_MCUSYS_CPC_SYSTEM_TIME_L_BASE	MCUCFG_REG(0xab0c)
+#define CPC_MCUSYS_CPC_SYSTEM_TIME_H_BASE	MCUCFG_REG(0xab10)
+#define CPC_MCUSYS_TRACE_SEL		MCUCFG_REG(0xab14)
+#define CPC_MCUSYS_TRACE_DATA		MCUCFG_REG(0xab20)
+#define CPC_MCUSYS_CLUSTER_COUNTER	MCUCFG_REG(0xab70)
+#define CPC_MCUSYS_CLUSTER_COUNTER_CLR	MCUCFG_REG(0xab74)
+
+#define SPARK2LDO			MCUCFG_REG(0x2700)
+/* APB Module mcucfg */
+#define MP0_CA7_CACHE_CONFIG		MCUCFG_REG(0x000)
+#define MP0_AXI_CONFIG			MCUCFG_REG(0x02C)
+#define MP0_MISC_CONFIG0		MCUCFG_REG(0x030)
+#define MP0_MISC_CONFIG1		MCUCFG_REG(0x034)
+#define MP0_MISC_CONFIG2		MCUCFG_REG(0x038)
+#define MP0_MISC_CONFIG_BOOT_ADDR(cpu)	(MP0_MISC_CONFIG2 + ((cpu) * 8))
+#define MP0_MISC_CONFIG3		MCUCFG_REG(0x03C)
+#define MP0_MISC_CONFIG9		MCUCFG_REG(0x054)
+#define MP0_CA7_MISC_CONFIG		MCUCFG_REG(0x064)
+
+#define MP0_RW_RSVD0			MCUCFG_REG(0x06C)
+
+
+#define MP1_CA7_CACHE_CONFIG		MCUCFG_REG(0x200)
+#define MP1_AXI_CONFIG			MCUCFG_REG(0x22C)
+#define MP1_MISC_CONFIG0		MCUCFG_REG(0x230)
+#define MP1_MISC_CONFIG1		MCUCFG_REG(0x234)
+#define MP1_MISC_CONFIG2		MCUCFG_REG(0x238)
+#define MP1_MISC_CONFIG_BOOT_ADDR(cpu)	(MP1_MISC_CONFIG2 + ((cpu) * 8))
+#define MP1_MISC_CONFIG3		MCUCFG_REG(0x23C)
+#define MP1_MISC_CONFIG9		MCUCFG_REG(0x254)
+#define MP1_CA7_MISC_CONFIG		MCUCFG_REG(0x264)
+
+#define CCI_ADB400_DCM_CONFIG		MCUCFG_REG(0x740)
+#define SYNC_DCM_CONFIG			MCUCFG_REG(0x744)
+
+#define MP0_CLUSTER_CFG0		MCUCFG_REG(0xC8D0)
+
+#define MP0_SPMC			MCUCFG_REG(0x788)
+#define MP1_SPMC			MCUCFG_REG(0x78C)
+#define MP2_AXI_CONFIG			MCUCFG_REG(0x220C)
+#define MP2_AXI_CONFIG_ACINACTM		BIT(0)
+#define MP2_AXI_CONFIG_AINACTS		BIT(4)
+
+#define MPx_AXI_CONFIG_ACINACTM		BIT(4)
+#define MPx_AXI_CONFIG_AINACTS		BIT(5)
+
+#define MPx_CA7_MISC_CONFIG_standbywfil2	BIT(28)
+
+#define MP0_CPU0_STANDBYWFE		BIT(20)
+#define MP0_CPU1_STANDBYWFE		BIT(21)
+#define MP0_CPU2_STANDBYWFE		BIT(22)
+#define MP0_CPU3_STANDBYWFE		BIT(23)
+
+#define MP1_CPU0_STANDBYWFE		BIT(20)
+#define MP1_CPU1_STANDBYWFE		BIT(21)
+#define MP1_CPU2_STANDBYWFE		BIT(22)
+#define MP1_CPU3_STANDBYWFE		BIT(23)
+
+#define CPUSYS0_SPARKVRETCNTRL		MCUCFG_REG(0x1c00)
+#define CPUSYS0_SPARKEN			MCUCFG_REG(0x1c04)
+#define CPUSYS0_AMUXSEL			MCUCFG_REG(0x1c08)
+#define CPUSYS1_SPARKVRETCNTRL		MCUCFG_REG(0x3c00)
+#define CPUSYS1_SPARKEN			MCUCFG_REG(0x3c04)
+#define CPUSYS1_AMUXSEL			MCUCFG_REG(0x3c08)
+
+#define MP2_PWR_RST_CTL			MCUCFG_REG(0x2008)
+#define MP2_PTP3_CPUTOP_SPMC0		MCUCFG_REG(0x22A0)
+#define MP2_PTP3_CPUTOP_SPMC1		MCUCFG_REG(0x22A4)
+
+#define MP2_COQ				MCUCFG_REG(0x22BC)
+#define MP2_COQ_SW_DIS			BIT(0)
+
+#define MP2_CA15M_MON_SEL		MCUCFG_REG(0x2400)
+#define MP2_CA15M_MON_L			MCUCFG_REG(0x2404)
+
+#define CPUSYS2_CPU0_SPMC_CTL		MCUCFG_REG(0x2430)
+#define CPUSYS2_CPU1_SPMC_CTL		MCUCFG_REG(0x2438)
+#define CPUSYS2_CPU0_SPMC_STA		MCUCFG_REG(0x2434)
+#define CPUSYS2_CPU1_SPMC_STA		MCUCFG_REG(0x243C)
+
+#define MP0_CA7L_DBG_PWR_CTRL		MCUCFG_REG(0x068)
+#define MP1_CA7L_DBG_PWR_CTRL		MCUCFG_REG(0x268)
+#define BIG_DBG_PWR_CTRL		MCUCFG_REG(0x75C)
+
+#define MP2_SW_RST_B			BIT(0)
+#define MP2_TOPAON_APB_MASK		BIT(1)
+
+#define B_SW_HOT_PLUG_RESET		BIT(30)
+
+#define B_SW_PD_OFFSET			18U
+#define B_SW_PD				(U(0x3f) << B_SW_PD_OFFSET)
+
+#define B_SW_SRAM_SLEEPB_OFFSET		12U
+#define B_SW_SRAM_SLEEPB		(U(0x3f) << B_SW_SRAM_SLEEPB_OFFSET)
+
+#define B_SW_SRAM_ISOINTB		BIT(9)
+#define B_SW_ISO			BIT(8)
+#define B_SW_LOGIC_PDB			BIT(7)
+#define B_SW_LOGIC_PRE2_PDB		BIT(6)
+#define B_SW_LOGIC_PRE1_PDB		BIT(5)
+#define B_SW_FSM_OVERRIDE		BIT(4)
+#define B_SW_PWR_ON			BIT(3)
+#define B_SW_PWR_ON_OVERRIDE_EN		BIT(2)
+
+#define B_FSM_STATE_OUT_OFFSET		(6U)
+#define B_FSM_STATE_OUT_MASK		(U(0x1f) << B_FSM_STATE_OUT_OFFSET)
+#define B_SW_LOGIC_PDBO_ALL_OFF_ACK	BIT(5)
+#define B_SW_LOGIC_PDBO_ALL_ON_ACK	BIT(4)
+#define B_SW_LOGIC_PRE2_PDBO_ALL_ON_ACK	BIT(3)
+#define B_SW_LOGIC_PRE1_PDBO_ALL_ON_ACK	BIT(2)
+
+#define B_FSM_OFF			(0U << B_FSM_STATE_OUT_OFFSET)
+#define B_FSM_ON			(1U << B_FSM_STATE_OUT_OFFSET)
+#define B_FSM_RET			(2U << B_FSM_STATE_OUT_OFFSET)
+
+#ifndef __ASSEMBLER__
+/* cpu boot mode */
+enum {
+	MP0_CPUCFG_64BIT_SHIFT = 12U,
+	MP1_CPUCFG_64BIT_SHIFT = 28U,
+	MP0_CPUCFG_64BIT = U(0xf) << MP0_CPUCFG_64BIT_SHIFT,
+	MP1_CPUCFG_64BIT = U(0xf) << MP1_CPUCFG_64BIT_SHIFT
+};
+
+enum {
+	MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK_SHIFT = 0U,
+	MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK_SHIFT = 4U,
+	MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK_SHIFT = 8U,
+	MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK_SHIFT = 12U,
+	MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK_SHIFT = 16U,
+
+	MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK_SHIFT
+};
+
+enum {
+	MP1_AINACTS_SHIFT = 4U,
+	MP1_AINACTS = 1U << MP1_AINACTS_SHIFT
+};
+
+enum {
+	MP1_SW_CG_GEN_SHIFT = 12U,
+	MP1_SW_CG_GEN = 1U << MP1_SW_CG_GEN_SHIFT
+};
+
+enum {
+	MP1_L2RSTDISABLE_SHIFT = 14U,
+	MP1_L2RSTDISABLE = 1U << MP1_L2RSTDISABLE_SHIFT
+};
+#endif /* __ASSEMBLER__ */
+
+#endif  /* MCUCFG_H */
diff --git a/plat/mediatek/mt8192/include/plat_mt_cirq.h b/plat/mediatek/mt8192/include/plat_mt_cirq.h
deleted file mode 100644
index 5818601..0000000
--- a/plat/mediatek/mt8192/include/plat_mt_cirq.h
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (c) 2020, MediaTek Inc. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PLAT_MT_CIRQ_H
-#define PLAT_MT_CIRQ_H
-
-#define SYS_CIRQ_BASE        U(0x10204000)
-#define CIRQ_IRQ_NUM         U(439)
-#define CIRQ_SPI_START       U(96)
-/*
- * Define hardware register
- */
-#define  CIRQ_STA_BASE         U(0x000)
-#define  CIRQ_ACK_BASE         U(0x080)
-#define  CIRQ_MASK_BASE        U(0x100)
-#define  CIRQ_MASK_SET_BASE    U(0x180)
-#define  CIRQ_MASK_CLR_BASE    U(0x200)
-#define  CIRQ_SENS_BASE        U(0x280)
-#define  CIRQ_SENS_SET_BASE    U(0x300)
-#define  CIRQ_SENS_CLR_BASE    U(0x380)
-#define  CIRQ_POL_BASE         U(0x400)
-#define  CIRQ_POL_SET_BASE     U(0x480)
-#define  CIRQ_POL_CLR_BASE     U(0x500)
-#define  CIRQ_CON              U(0x600)
-
-/*
- * Register placement
- */
-#define  CIRQ_CON_EN_BITS           U(0)
-#define  CIRQ_CON_EDGE_ONLY_BITS    U(1)
-#define  CIRQ_CON_FLUSH_BITS        U(2)
-#define  CIRQ_CON_EVENT_BITS        U(31)
-#define  CIRQ_CON_SW_RST_BITS       U(20)
-#define  CIRQ_CON_BITS_MASK         U(0x7)
-
-/*
- * Register setting
- */
-#define  CIRQ_CON_EN            U(0x1)
-#define  CIRQ_CON_EDGE_ONLY     U(0x1)
-#define  CIRQ_SW_RESET          U(0x1)
-#define  CIRQ_CON_FLUSH         U(0x1)
-
-/*
- * Define constant
- */
-#define  CIRQ_CTRL_REG_NUM      ((CIRQ_IRQ_NUM + 31U) / 32U)
-#define  MT_CIRQ_POL_NEG               U(0)
-#define  MT_CIRQ_POL_POS               U(1)
-#define  MT_CIRQ_EDGE_SENSITIVE        U(0)
-#define  MT_CIRQ_LEVEL_SENSITIVE       U(1)
-
-/*
- * Define macro
- */
-#define  IRQ_TO_CIRQ_NUM(irq)       ((irq) - (CIRQ_SPI_START))
-#define  CIRQ_TO_IRQ_NUM(cirq)      ((cirq) + (CIRQ_SPI_START))
-
-/*
- * Define cirq events
- */
-struct cirq_events {
-	uint32_t spi_start;
-	uint32_t num_of_events;
-	uint32_t *wakeup_events;
-};
-
-/*
- * Define function prototypes.
- */
-void mt_cirq_enable(void);
-void mt_cirq_disable(void);
-void mt_cirq_clone_gic(void);
-void mt_cirq_flush(void);
-void mt_cirq_sw_reset(void);
-void set_wakeup_sources(uint32_t *list, uint32_t num_of_events);
-void mt_cirq_dump_reg(void);
-
-#endif  /* PLAT_MT_CIRQ_H */
diff --git a/plat/mediatek/mt8192/include/plat_mtk_lpm.h b/plat/mediatek/mt8192/include/plat_mtk_lpm.h
new file mode 100644
index 0000000..deaac97
--- /dev/null
+++ b/plat/mediatek/mt8192/include/plat_mtk_lpm.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_MTK_LPM_H
+#define PLAT_MTK_LPM_H
+
+#include <lib/psci/psci.h>
+#include <lib/utils_def.h>
+
+#define MT_IRQ_REMAIN_MAX	U(32)
+#define MT_IRQ_REMAIN_CAT_LOG	BIT(31)
+
+struct mt_irqremain {
+	unsigned int count;
+	unsigned int irqs[MT_IRQ_REMAIN_MAX];
+	unsigned int wakeupsrc_cat[MT_IRQ_REMAIN_MAX];
+	unsigned int wakeupsrc[MT_IRQ_REMAIN_MAX];
+};
+
+#define PLAT_RC_STATUS_READY		BIT(0)
+#define PLAT_RC_STATUS_FEATURE_EN	BIT(1)
+#define PLAT_RC_STATUS_UART_NONSLEEP	BIT(31)
+
+struct mt_lpm_tz {
+	int (*pwr_prompt)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_reflect)(unsigned int cpu, const psci_power_state_t *state);
+
+	int (*pwr_cpu_on)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_cpu_dwn)(unsigned int cpu, const psci_power_state_t *state);
+
+	int (*pwr_cluster_on)(unsigned int cpu,
+					const psci_power_state_t *state);
+	int (*pwr_cluster_dwn)(unsigned int cpu,
+					const psci_power_state_t *state);
+
+	int (*pwr_mcusys_on)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_mcusys_on_finished)(unsigned int cpu,
+					const psci_power_state_t *state);
+	int (*pwr_mcusys_dwn)(unsigned int cpu,
+					const psci_power_state_t *state);
+};
+
+const struct mt_lpm_tz *mt_plat_cpu_pm_init(void);
+
+#endif /* PLAT_MTK_LPM_H */
diff --git a/plat/mediatek/mt8192/include/plat_pm.h b/plat/mediatek/mt8192/include/plat_pm.h
new file mode 100644
index 0000000..a2881ce
--- /dev/null
+++ b/plat/mediatek/mt8192/include/plat_pm.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_PM_H
+#define PLAT_PM_H
+
+#include <lib/utils_def.h>
+
+#define MT_PLAT_PWR_STATE_CPU			U(1)
+#define MT_PLAT_PWR_STATE_CLUSTER		U(2)
+#define MT_PLAT_PWR_STATE_MCUSYS		U(3)
+#define MT_PLAT_PWR_STATE_SUSPEND2IDLE		U(8)
+#define MT_PLAT_PWR_STATE_SYSTEM_SUSPEND	U(9)
+
+#define MTK_LOCAL_STATE_RUN			U(0)
+#define MTK_LOCAL_STATE_RET			U(1)
+#define MTK_LOCAL_STATE_OFF			U(2)
+
+#define MTK_AFFLVL_CPU				U(0)
+#define MTK_AFFLVL_CLUSTER			U(1)
+#define MTK_AFFLVL_MCUSYS			U(2)
+#define MTK_AFFLVL_SYSTEM			U(3)
+
+#define IS_CLUSTER_OFF_STATE(s)		\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_CLUSTER])
+#define IS_MCUSYS_OFF_STATE(s)		\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_MCUSYS])
+#define IS_SYSTEM_SUSPEND_STATE(s)	\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_SYSTEM])
+
+#define IS_PLAT_SUSPEND_ID(stateid)\
+		((stateid == MT_PLAT_PWR_STATE_SUSPEND2IDLE)	\
+		|| (stateid == MT_PLAT_PWR_STATE_SYSTEM_SUSPEND))
+
+#endif /* PLAT_PM_H */
diff --git a/plat/mediatek/mt8192/include/plat_sip_calls.h b/plat/mediatek/mt8192/include/plat_sip_calls.h
new file mode 100644
index 0000000..f68a4ea
--- /dev/null
+++ b/plat/mediatek/mt8192/include/plat_sip_calls.h
@@ -0,0 +1,19 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_SIP_CALLS_H
+#define PLAT_SIP_CALLS_H
+
+/*******************************************************************************
+ * Plat SiP function constants
+ ******************************************************************************/
+#define MTK_PLAT_SIP_NUM_CALLS    2
+
+/* DFD */
+#define MTK_SIP_KERNEL_DFD_AARCH32		0x82000205
+#define MTK_SIP_KERNEL_DFD_AARCH64		0xC2000205
+
+#endif /* PLAT_SIP_CALLS_H */
diff --git a/plat/mediatek/mt8192/include/platform_def.h b/plat/mediatek/mt8192/include/platform_def.h
index 768e7cf..ec377b5 100644
--- a/plat/mediatek/mt8192/include/platform_def.h
+++ b/plat/mediatek/mt8192/include/platform_def.h
@@ -23,17 +23,43 @@
 #define MTK_DEV_RNG1_SIZE    0x10000000
 #define MTK_DEV_RNG2_BASE    0x0c000000
 #define MTK_DEV_RNG2_SIZE    0x600000
+#define MTK_MCDI_SRAM_BASE      0x11B000
+#define MTK_MCDI_SRAM_MAP_SIZE  0x1000
 
-#define GPIO_BASE        (IO_PHYS + 0x00005000)
-#define IOCFG_RM_BASE    (IO_PHYS + 0x01C20000)
-#define IOCFG_BM_BASE    (IO_PHYS + 0x01D10000)
-#define IOCFG_BL_BASE    (IO_PHYS + 0x01D30000)
-#define IOCFG_BR_BASE    (IO_PHYS + 0x01D40000)
-#define IOCFG_LM_BASE    (IO_PHYS + 0x01E20000)
-#define IOCFG_LB_BASE    (IO_PHYS + 0x01E70000)
-#define IOCFG_RT_BASE    (IO_PHYS + 0x01EA0000)
-#define IOCFG_LT_BASE    (IO_PHYS + 0x01F20000)
-#define IOCFG_TL_BASE    (IO_PHYS + 0x01F30000)
+#define APUSYS_BASE                   0x19000000
+#define APUSYS_SCTRL_REVISER_BASE     0x19021000
+#define APUSYS_SCTRL_REVISER_SIZE     0x1000
+#define APUSYS_APU_S_S_4_BASE         0x190F2000
+#define APUSYS_APU_S_S_4_SIZE         0x1000
+#define APUSYS_APC_AO_WRAPPER_BASE    0x190F8000
+#define APUSYS_APC_AO_WRAPPER_SIZE    0x1000
+#define APUSYS_NOC_DAPC_AO_BASE       0x190FC000
+#define APUSYS_NOC_DAPC_AO_SIZE       0x1000
+
+#define TOPCKGEN_BASE            (IO_PHYS + 0x00000000)
+#define INFRACFG_AO_BASE         (IO_PHYS + 0x00001000)
+#define GPIO_BASE                (IO_PHYS + 0x00005000)
+#define SPM_BASE                 (IO_PHYS + 0x00006000)
+#define APMIXEDSYS               (IO_PHYS + 0x0000C000)
+#define DVFSRC_BASE              (IO_PHYS + 0x00012000)
+#define PMIC_WRAP_BASE           (IO_PHYS + 0x00026000)
+#define DEVAPC_INFRA_AO_BASE     (IO_PHYS + 0x00030000)
+#define DEVAPC_PERI_AO_BASE      (IO_PHYS + 0x00034000)
+#define DEVAPC_PERI_AO2_BASE     (IO_PHYS + 0x00038000)
+#define DEVAPC_PERI_PAR_AO_BASE  (IO_PHYS + 0x0003C000)
+#define EMI_BASE                 (IO_PHYS + 0x00219000)
+#define EMI_MPU_BASE             (IO_PHYS + 0x00226000)
+#define SSPM_MBOX_BASE           (IO_PHYS + 0x00480000)
+#define IOCFG_RM_BASE            (IO_PHYS + 0x01C20000)
+#define IOCFG_BM_BASE            (IO_PHYS + 0x01D10000)
+#define IOCFG_BL_BASE            (IO_PHYS + 0x01D30000)
+#define IOCFG_BR_BASE            (IO_PHYS + 0x01D40000)
+#define IOCFG_LM_BASE            (IO_PHYS + 0x01E20000)
+#define IOCFG_LB_BASE            (IO_PHYS + 0x01E70000)
+#define IOCFG_RT_BASE            (IO_PHYS + 0x01EA0000)
+#define IOCFG_LT_BASE            (IO_PHYS + 0x01F20000)
+#define IOCFG_TL_BASE            (IO_PHYS + 0x01F30000)
+#define MMSYS_BASE               (IO_PHYS + 0x04000000)
 /*******************************************************************************
  * UART related constants
  ******************************************************************************/
@@ -49,13 +75,19 @@
 #define SYS_COUNTER_FREQ_IN_MHZ      13
 
 /*******************************************************************************
- * GIC-400 & interrupt handling related constants
+ * GIC-600 & interrupt handling related constants
  ******************************************************************************/
 
 /* Base MTK_platform compatible GIC memory map */
 #define BASE_GICD_BASE        MT_GIC_BASE
 #define MT_GIC_RDIST_BASE     (MT_GIC_BASE + 0x40000)
 
+#define SYS_CIRQ_BASE         (IO_PHYS + 0x204000)
+#define CIRQ_REG_NUM          14
+#define CIRQ_IRQ_NUM          439
+#define CIRQ_SPI_START        64
+#define MD_WDT_IRQ_BIT_ID     110
+
 /*******************************************************************************
  * Platform binary types for linking
  ******************************************************************************/
@@ -67,11 +99,12 @@
  ******************************************************************************/
 #define PLATFORM_STACK_SIZE    0x800
 
-#define PLAT_MAX_PWR_LVL        U(2)
+#define PLAT_MAX_PWR_LVL        U(3)
 #define PLAT_MAX_RET_STATE      U(1)
-#define PLAT_MAX_OFF_STATE      U(2)
+#define PLAT_MAX_OFF_STATE      U(9)
 
 #define PLATFORM_SYSTEM_COUNT           U(1)
+#define PLATFORM_MCUSYS_COUNT           U(1)
 #define PLATFORM_CLUSTER_COUNT          U(1)
 #define PLATFORM_CLUSTER0_CORE_COUNT    U(8)
 #define PLATFORM_CORE_COUNT             (PLATFORM_CLUSTER0_CORE_COUNT)
diff --git a/plat/mediatek/mt8192/include/rtc.h b/plat/mediatek/mt8192/include/rtc.h
new file mode 100644
index 0000000..a9c7bc8
--- /dev/null
+++ b/plat/mediatek/mt8192/include/rtc.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RTC_H
+#define RTC_H
+
+#include <rtc_mt6359p.h>
+
+#endif  /* RTC_H */
diff --git a/plat/mediatek/mt8192/plat_mt_cirq.c b/plat/mediatek/mt8192/plat_mt_cirq.c
deleted file mode 100644
index 7fc0607..0000000
--- a/plat/mediatek/mt8192/plat_mt_cirq.c
+++ /dev/null
@@ -1,494 +0,0 @@
-/*
- * Copyright (c) 2020, MediaTek Inc. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <drivers/arm/gic_common.h>
-#include <drivers/console.h>
-#include <lib/mmio.h>
-
-#include <mt_gic_v3.h>
-#include <mtk_plat_common.h>
-#include <plat_mt_cirq.h>
-#include <platform_def.h>
-
-static struct cirq_events cirq_all_events = {
-	.spi_start = CIRQ_SPI_START
-};
-
-static inline void  mt_cirq_write32(uint32_t val, uint32_t addr)
-{
-	mmio_write_32(addr + SYS_CIRQ_BASE, val);
-}
-
-static inline uint32_t mt_cirq_read32(uint32_t addr)
-{
-	return mmio_read_32(addr + SYS_CIRQ_BASE);
-}
-
-/*
- * cirq_clone_flush_check_store:
- * set 1 if we need to enable clone/flush value's check
- */
-static int32_t cirq_clone_flush_check_val;
-
-/*
- * cirq_pattern_clone_flush_check_show:  set 1 if we need to do pattern test.
- */
-static int32_t cirq_pattern_clone_flush_check_val;
-
-/*
- * cirq_pattern_clone_flush_check_show:  set 1 if we need to do pattern test.
- */
-static int32_t cirq_pattern_list;
-
-/*
- * mt_cirq_ack_all: Ack all the interrupt on SYS_CIRQ
- */
-void mt_cirq_ack_all(void)
-{
-	unsigned int i;
-
-	for (i = 0U; i < CIRQ_CTRL_REG_NUM; i++) {
-		mt_cirq_write32(0xFFFFFFFF, CIRQ_ACK_BASE + (i * 4U));
-	}
-	/* make sure all cirq setting take effect before doing other things */
-	dmbsy();
-}
-
-/*
- * mt_cirq_enable: Enable SYS_CIRQ
- */
-void mt_cirq_enable(void)
-{
-	uint32_t st;
-
-	mt_cirq_ack_all();
-
-	st = mt_cirq_read32(CIRQ_CON);
-	st |= (CIRQ_CON_EN << CIRQ_CON_EN_BITS) |
-			(CIRQ_CON_EDGE_ONLY << CIRQ_CON_EDGE_ONLY_BITS);
-
-	mt_cirq_write32((st & CIRQ_CON_BITS_MASK), CIRQ_CON);
-}
-
-/*
- * mt_cirq_disable: Disable SYS_CIRQ
- */
-void mt_cirq_disable(void)
-{
-	uint32_t st;
-
-	st = mt_cirq_read32(CIRQ_CON);
-	st &= ~(CIRQ_CON_EN << CIRQ_CON_EN_BITS);
-
-	mt_cirq_write32((st & CIRQ_CON_BITS_MASK), CIRQ_CON);
-}
-
-/*
- * mt_cirq_get_mask: Get the specified SYS_CIRQ mask
- * @cirq_num: the SYS_CIRQ number to get
- * @return:
- *    1: this cirq is masked
- *    0: this cirq is umasked
- *    2: cirq num is out of range
- */
-__attribute__((weak)) unsigned int mt_cirq_get_mask(uint32_t cirq_num)
-{
-	uint32_t st;
-	unsigned int val;
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return 2;
-	}
-
-	st = mt_cirq_read32((cirq_num / 32U) * 4U + CIRQ_MASK_BASE);
-	val = (st >> (cirq_num % 32U)) & 1U;
-	return val;
-}
-
-/*
- * mt_cirq_mask_all: Mask all interrupts on SYS_CIRQ.
- */
-void mt_cirq_mask_all(void)
-{
-	unsigned int i;
-
-	for (i = 0U; i < CIRQ_CTRL_REG_NUM; i++) {
-		mt_cirq_write32(0xFFFFFFFF, CIRQ_MASK_SET_BASE + (i * 4U));
-	}
-	/* make sure all cirq setting take effect before doing other things */
-	dmbsy();
-}
-
-/*
- * mt_cirq_unmask_all: Unmask all interrupts on SYS_CIRQ.
- */
-void mt_cirq_unmask_all(void)
-{
-	unsigned int i;
-
-	for (i = 0U; i < CIRQ_CTRL_REG_NUM; i++) {
-		mt_cirq_write32(0xFFFFFFFF, CIRQ_MASK_CLR_BASE + (i * 4U));
-	}
-	/* make sure all cirq setting take effect before doing other things */
-	dmbsy();
-}
-
-/*
- * mt_cirq_mask: Mask the specified SYS_CIRQ.
- * @cirq_num: the SYS_CIRQ number to mask
- * @return:
- *    0: mask success
- *   -1: cirq num is out of range
- */
-static int mt_cirq_mask(uint32_t cirq_num)
-{
-	uint32_t bit = 1U << (cirq_num % 32U);
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return -1;
-	}
-
-	mt_cirq_write32(bit, (cirq_num / 32U) * 4U + CIRQ_MASK_SET_BASE);
-	return 0;
-}
-
-/*
- * mt_cirq_unmask: Unmask the specified SYS_CIRQ.
- * @cirq_num: the SYS_CIRQ number to unmask
- * @return:
- *    0: umask success
- *   -1: cirq num is out of range
- */
-static int mt_cirq_unmask(uint32_t cirq_num)
-{
-	uint32_t bit = 1U << (cirq_num % 32U);
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return -1;
-	}
-
-	mt_cirq_write32(bit, (cirq_num / 32U) * 4U + CIRQ_MASK_CLR_BASE);
-	return 0;
-}
-
-/*
- * mt_cirq_set_sens: Set the sensitivity for the specified SYS_CIRQ number.
- * @cirq_num: the SYS_CIRQ number to set
- * @sens: sensitivity to set
- * @return:
- *    0: set sens success
- *   -1: cirq num is out of range
- */
-static int mt_cirq_set_sens(uint32_t cirq_num, uint32_t sens)
-{
-	uint32_t base;
-	uint32_t bit = 1U << (cirq_num % 32U);
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return -1;
-	}
-
-	if (sens == MT_CIRQ_EDGE_SENSITIVE) {
-		base = (cirq_num / 32U) * 4U + CIRQ_SENS_CLR_BASE;
-	} else if (sens == MT_CIRQ_LEVEL_SENSITIVE) {
-		base = (cirq_num / 32U) * 4U + CIRQ_SENS_SET_BASE;
-	} else {
-		ERROR("[CIRQ] set_sens invalid sen value %u\n", sens);
-		return -1;
-	}
-
-	mt_cirq_write32(bit, base);
-	return 0;
-}
-
-/*
- * mt_cirq_get_sens: Get the specified SYS_CIRQ sensitivity
- * @cirq_num: the SYS_CIRQ number to get
- * @return:
- *    1: this cirq is MT_LEVEL_SENSITIVE
- *    0: this cirq is MT_EDGE_SENSITIVE
- *    2: cirq num is out of range
- */
-__attribute__((weak)) unsigned int mt_cirq_get_sens(uint32_t cirq_num)
-{
-	uint32_t st;
-	unsigned int val;
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return 2;
-	}
-
-	st = mt_cirq_read32((cirq_num / 32U) * 4U + CIRQ_SENS_BASE);
-	val = (st >> (cirq_num % 32U)) & 1U;
-	return val;
-}
-
-/*
- * mt_cirq_set_pol: Set the polarity for the specified SYS_CIRQ number.
- * @cirq_num: the SYS_CIRQ number to set
- * @pol: polarity to set
- * @return:
- *    0: set pol success
- *   -1: cirq num is out of range
- */
-static int mt_cirq_set_pol(uint32_t cirq_num, uint32_t pol)
-{
-	uint32_t base;
-	uint32_t bit = 1U << (cirq_num % 32U);
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return -1;
-	}
-
-	if (pol == MT_CIRQ_POL_NEG) {
-		base = (cirq_num / 32U) * 4U + CIRQ_POL_CLR_BASE;
-	} else if (pol == MT_CIRQ_POL_POS) {
-		base = (cirq_num / 32U) * 4U + CIRQ_POL_SET_BASE;
-	} else {
-		ERROR("[CIRQ] set_pol invalid polarity value %u\n", pol);
-		return -1;
-	}
-
-	mt_cirq_write32(bit, base);
-	return 0;
-}
-
-/*
- * mt_cirq_get_pol: Get the specified SYS_CIRQ polarity
- * @cirq_num: the SYS_CIRQ number to get
- * @return:
- *    1: this cirq is MT_CIRQ_POL_POS
- *    0: this cirq is MT_CIRQ_POL_NEG
- *    2: cirq num is out of range
- */
-__attribute__((weak)) unsigned int mt_cirq_get_pol(uint32_t cirq_num)
-{
-	uint32_t st;
-	unsigned int val;
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return 2;
-	}
-
-	st = mt_cirq_read32((cirq_num / 32U) * 4U + CIRQ_POL_BASE);
-	val = (st >> (cirq_num % 32U)) & 1U;
-	return val;
-}
-
-/*
- * mt_cirq_get_pending: Get the specified SYS_CIRQ pending
- * @cirq_num: the SYS_CIRQ number to get
- * @return:
- *    1: this cirq is pending
- *    0: this cirq is not pending
- *    2: cirq num is out of range
- */
-static unsigned int mt_cirq_get_pending(uint32_t cirq_num)
-{
-	uint32_t st;
-	unsigned int val;
-
-	if (cirq_num >= CIRQ_IRQ_NUM) {
-		ERROR("[CIRQ] %s: invalid cirq %u\n", __func__, cirq_num);
-		return 2;
-	}
-
-	st = mt_cirq_read32((cirq_num / 32U) * 4U + CIRQ_STA_BASE);
-	val = (st >> (cirq_num % 32U)) & 1U;
-	return val;
-}
-
-/*
- * mt_cirq_clone_pol: Copy the polarity setting from GIC to SYS_CIRQ
- */
-void mt_cirq_clone_pol(void)
-{
-	uint32_t cirq_num;
-
-	for (cirq_num = 0U; cirq_num < CIRQ_IRQ_NUM; cirq_num++) {
-		mt_cirq_set_pol(cirq_num, MT_CIRQ_POL_POS);
-	}
-}
-
-/*
- * mt_cirq_clone_sens: Copy the sensitivity setting from GIC to SYS_CIRQ
- */
-void mt_cirq_clone_sens(void)
-{
-	uint32_t cirq_num, irq_num;
-	uint32_t st, val;
-
-	for (cirq_num = 0U; cirq_num < CIRQ_IRQ_NUM; cirq_num++) {
-		irq_num = CIRQ_TO_IRQ_NUM(cirq_num);
-
-		if ((cirq_num == 0U) || (irq_num % 16U == 0U)) {
-			st = mmio_read_32(BASE_GICD_BASE + GICD_ICFGR +
-				(irq_num / 16U * 4U));
-		}
-
-		val = (st >> ((irq_num % 16U) * 2U)) & 0x2U;
-
-		if (val) {
-			mt_cirq_set_sens(cirq_num, MT_CIRQ_EDGE_SENSITIVE);
-		} else {
-			mt_cirq_set_sens(cirq_num, MT_CIRQ_LEVEL_SENSITIVE);
-		}
-	}
-}
-
-/*
- * mt_cirq_clone_mask: Copy the mask setting from GIC to SYS_CIRQ
- */
-void mt_cirq_clone_mask(void)
-{
-	uint32_t cirq_num, irq_num;
-	uint32_t st, val;
-
-	for (cirq_num = 0U; cirq_num < CIRQ_IRQ_NUM; cirq_num++) {
-		irq_num = CIRQ_TO_IRQ_NUM(cirq_num);
-
-		if ((cirq_num == 0U) || (irq_num % 32U == 0U)) {
-			st = mmio_read_32(BASE_GICD_BASE +
-				GICD_ISENABLER + (irq_num / 32U * 4U));
-		}
-
-		val = (st >> (irq_num % 32)) & 1U;
-
-		if (val) {
-			mt_cirq_unmask(cirq_num);
-		} else {
-			mt_cirq_mask(cirq_num);
-		}
-	}
-}
-
-/*
- * mt_cirq_clone_gic: Copy the setting from GIC to SYS_CIRQ
- */
-void mt_cirq_clone_gic(void)
-{
-	mt_cirq_clone_sens();
-	mt_cirq_clone_mask();
-}
-
-/*
- * mt_cirq_disable: Flush interrupt from SYS_CIRQ to GIC
- */
-void mt_cirq_flush(void)
-{
-	unsigned int i;
-	unsigned char cirq_p_val = 0U;
-	unsigned char irq_p_val = 0U;
-	uint32_t irq_p = 0U;
-	unsigned char pass = 1U;
-	uint32_t first_cirq_found = 0U;
-	uint32_t first_flushed_cirq;
-	uint32_t first_irq_flushedto;
-	uint32_t last_fluashed_cirq;
-	uint32_t last_irq_flushedto;
-
-	if (cirq_pattern_clone_flush_check_val == 1U) {
-		if (cirq_pattern_list < CIRQ_IRQ_NUM) {
-			mt_cirq_unmask(cirq_pattern_list);
-			mt_cirq_set_sens(cirq_pattern_list,
-				MT_CIRQ_EDGE_SENSITIVE);
-			mt_cirq_set_pol(cirq_pattern_list, MT_CIRQ_POL_NEG);
-			mt_cirq_set_pol(cirq_pattern_list, MT_CIRQ_POL_POS);
-			mt_cirq_set_pol(cirq_pattern_list, MT_CIRQ_POL_NEG);
-		} else {
-			ERROR("[CIRQ] no pattern to test,");
-			ERROR("input pattern first\n");
-		}
-		ERROR("[CIRQ] cirq_pattern %u, cirq_p %u,",
-				cirq_pattern_list,
-				mt_cirq_get_pending(cirq_pattern_list));
-		ERROR("cirq_s %u, cirq_con 0x%x\n",
-				mt_cirq_get_sens(cirq_pattern_list),
-				mt_cirq_read32(CIRQ_CON));
-	}
-
-	mt_cirq_unmask_all();
-
-	for (i = 0U; i < CIRQ_IRQ_NUM; i++) {
-		cirq_p_val = mt_cirq_get_pending(i);
-		if (cirq_p_val) {
-			mt_irq_set_pending(CIRQ_TO_IRQ_NUM(i));
-		}
-
-		if (cirq_clone_flush_check_val == 1U) {
-			if (cirq_p_val == 0U) {
-				continue;
-		}
-			irq_p = CIRQ_TO_IRQ_NUM(i);
-			irq_p_val = mt_irq_get_pending(irq_p);
-			if (cirq_p_val != irq_p_val) {
-				ERROR("[CIRQ] CIRQ Flush Failed ");
-				ERROR("%u(cirq %d)!= %u(gic %d)\n",
-					cirq_p_val, i, irq_p_val,
-					CIRQ_TO_IRQ_NUM(i));
-				pass = 0;
-			} else {
-				ERROR("[CIRQ] CIRQ Flush Pass ");
-				ERROR("%u(cirq %d) = %u(gic %d)\n",
-					cirq_p_val, i, irq_p_val,
-					CIRQ_TO_IRQ_NUM(i));
-			}
-			if (!first_cirq_found) {
-				first_flushed_cirq = i;
-				first_irq_flushedto = irq_p;
-				first_cirq_found = 1U;
-			}
-			last_fluashed_cirq = i;
-			last_irq_flushedto = irq_p;
-		}
-	}
-
-	if (cirq_clone_flush_check_val == 1U) {
-		if (first_cirq_found) {
-			ERROR("[CIRQ] The first flush : CIRQ%u to IRQ%u\n",
-				first_flushed_cirq, first_irq_flushedto);
-			ERROR("[CIRQ] The last flush : CIRQ%u to IRQ%u\n",
-				last_fluashed_cirq, last_irq_flushedto);
-		} else {
-			ERROR("[CIRQ] There are no pending ");
-			ERROR("interrupt in CIRQ\n");
-			ERROR("[CIRQ] so no flush operation happened\n");
-		}
-		ERROR("[CIRQ] The Flush Max Range : CIRQ");
-		ERROR("%d to IRQ%d ~ CIRQ%d to IRQ%d\n", 0U,
-			CIRQ_TO_IRQ_NUM(0U), CIRQ_IRQ_NUM - 1U,
-			CIRQ_TO_IRQ_NUM(CIRQ_IRQ_NUM - 1U));
-		ERROR("[CIRQ] Flush Check %s, Confirm:SPI_START_OFFSET:%d\n",
-			pass == 1 ? "Pass" : "Failed", CIRQ_SPI_START);
-	}
-	mt_cirq_mask_all();
-	mt_cirq_ack_all();
-}
-
-void mt_cirq_sw_reset(void)
-{
-	uint32_t st;
-
-	st = mt_cirq_read32(CIRQ_CON);
-	st |= (CIRQ_SW_RESET << CIRQ_CON_SW_RST_BITS);
-
-	mt_cirq_write32(st, CIRQ_CON);
-}
-
-void set_wakeup_sources(uint32_t *list, uint32_t num_of_events)
-{
-	cirq_all_events.num_of_events = num_of_events;
-	cirq_all_events.wakeup_events = list;
-}
diff --git a/plat/mediatek/mt8192/plat_pm.c b/plat/mediatek/mt8192/plat_pm.c
index becf5d3..018e418 100644
--- a/plat/mediatek/mt8192/plat_pm.c
+++ b/plat/mediatek/mt8192/plat_pm.c
@@ -5,17 +5,352 @@
  */
 
 /* common headers */
+#include <assert.h>
+
 #include <arch_helpers.h>
 #include <common/debug.h>
 #include <drivers/gpio.h>
 #include <lib/psci/psci.h>
 
-/* mediatek platform specific headers */
+/* platform specific headers */
+#include <mt_gic_v3.h>
+#include <mtk_ptp3_common.h>
+#include <mtspmc.h>
+#include <plat/common/platform.h>
+#include <plat_dfd.h>
+#include <plat_mtk_lpm.h>
 #include <plat_params.h>
+#include <plat_pm.h>
+#include <pmic.h>
+#include <rtc.h>
 
-/*******************************************************************************
- * MTK handlers to shutdown/reboot the system
- ******************************************************************************/
+/*
+ * Cluster state request:
+ * [0] : The CPU requires cluster power down
+ * [1] : The CPU requires cluster power on
+ */
+#define coordinate_cluster(onoff)	write_clusterpwrdn_el1(onoff)
+#define coordinate_cluster_pwron()	coordinate_cluster(1)
+#define coordinate_cluster_pwroff()	coordinate_cluster(0)
+
+/* platform secure entry point */
+static uintptr_t secure_entrypoint;
+/* per-CPU power state */
+static unsigned int plat_power_state[PLATFORM_CORE_COUNT];
+
+/* platform CPU power domain - ops */
+static const struct mt_lpm_tz *plat_mt_pm;
+
+#define plat_mt_pm_invoke(_name, _cpu, _state) ({ \
+	int ret = -1; \
+	if (plat_mt_pm != NULL && plat_mt_pm->_name != NULL) { \
+		ret = plat_mt_pm->_name(_cpu, _state); \
+	} \
+	ret; })
+
+#define plat_mt_pm_invoke_no_check(_name, _cpu, _state) ({ \
+	if (plat_mt_pm != NULL && plat_mt_pm->_name != NULL) { \
+		(void) plat_mt_pm->_name(_cpu, _state); \
+	} \
+	})
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * CPU in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_cpu_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	plat_mt_pm_invoke_no_check(pwr_cpu_dwn, cpu, state);
+
+	if ((psci_get_pstate_pwrlvl(req_pstate) >= MTK_AFFLVL_CLUSTER) ||
+			(req_pstate == 0U)) { /* hotplug off */
+		coordinate_cluster_pwroff();
+	}
+
+	/* Prevent interrupts from spuriously waking up this CPU */
+	mt_gic_rdistif_save();
+	gicv3_cpuif_disable(cpu);
+	gicv3_rdistif_off(cpu);
+	/* PTP3 config */
+	ptp3_deinit(cpu);
+}
+
+static void plat_cpu_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	plat_mt_pm_invoke_no_check(pwr_cpu_on, cpu, state);
+
+	coordinate_cluster_pwron();
+
+	/*
+	 * If mcusys does power down before then restore
+	 * all CPUs' GIC Redistributors
+	 */
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		mt_gic_rdistif_restore_all();
+	} else {
+		gicv3_rdistif_on(cpu);
+		gicv3_cpuif_enable(cpu);
+		mt_gic_rdistif_init();
+		mt_gic_rdistif_restore();
+	}
+
+	/* PTP3 config */
+	ptp3_init(cpu);
+}
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * cluster in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_cluster_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_cluster_dwn, cpu, state) != 0) {
+		coordinate_cluster_pwron();
+
+		/* TODO: return on fail.
+		 *       Add a 'return' here before adding any code following
+		 *       the if-block.
+		 */
+	}
+}
+
+static void plat_cluster_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_cluster_on, cpu, state) != 0) {
+		/* TODO: return on fail.
+		 *       Add a 'return' here before adding any code following
+		 *       the if-block.
+		 */
+	}
+}
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * mcusys in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_mcusys_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_mcusys_dwn, cpu, state) != 0) {
+		return;		/* return on fail */
+	}
+
+	mt_gic_distif_save();
+	gic_sgi_save_all();
+}
+
+static void plat_mcusys_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_mcusys_on, cpu, state) != 0) {
+		return;		/* return on fail */
+	}
+
+	mt_gic_init();
+	mt_gic_distif_restore();
+	gic_sgi_restore_all();
+
+	dfd_resume();
+
+	plat_mt_pm_invoke_no_check(pwr_mcusys_on_finished, cpu, state);
+}
+
+/*
+ * plat_psci_ops implementation
+ */
+
+static void plat_cpu_standby(plat_local_state_t cpu_state)
+{
+	uint64_t scr;
+
+	scr = read_scr_el3();
+	write_scr_el3(scr | SCR_IRQ_BIT | SCR_FIQ_BIT);
+
+	isb();
+	dsb();
+	wfi();
+
+	write_scr_el3(scr);
+}
+
+static int plat_power_domain_on(u_register_t mpidr)
+{
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+	unsigned int cluster = 0U;
+
+	if (cpu >= PLATFORM_CORE_COUNT) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	if (!spm_get_cluster_powerstate(cluster)) {
+		spm_poweron_cluster(cluster);
+	}
+
+	/* init CPU reset arch as AARCH64 */
+	mcucfg_init_archstate(cluster, cpu, true);
+	mcucfg_set_bootaddr(cluster, cpu, secure_entrypoint);
+	spm_poweron_cpu(cluster, cpu);
+
+	return PSCI_E_SUCCESS;
+}
+
+static void plat_power_domain_on_finish(const psci_power_state_t *state)
+{
+	unsigned long mpidr = read_mpidr_el1();
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	/* Allow IRQs to wakeup this core in IDLE flow */
+	mcucfg_enable_gic_wakeup(0U, cpu);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		plat_cluster_pwron_common(cpu, state, 0U);
+	}
+
+	plat_cpu_pwron_common(cpu, state, 0U);
+}
+
+static void plat_power_domain_off(const psci_power_state_t *state)
+{
+	unsigned long mpidr = read_mpidr_el1();
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	plat_cpu_pwrdwn_common(cpu, state, 0U);
+	spm_poweroff_cpu(0U, cpu);
+
+	/* prevent unintended IRQs from waking up the hot-unplugged core */
+	mcucfg_disable_gic_wakeup(0U, cpu);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		plat_cluster_pwrdwn_common(cpu, state, 0U);
+	}
+}
+
+static void plat_power_domain_suspend(const psci_power_state_t *state)
+{
+	unsigned int cpu = plat_my_core_pos();
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	plat_mt_pm_invoke_no_check(pwr_prompt, cpu, state);
+
+	/* Perform the common CPU specific operations */
+	plat_cpu_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		/* Perform the common cluster specific operations */
+		plat_cluster_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		/* Perform the common mcusys specific operations */
+		plat_mcusys_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+	}
+}
+
+static void plat_power_domain_suspend_finish(const psci_power_state_t *state)
+{
+	unsigned int cpu = plat_my_core_pos();
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		/* Perform the common mcusys specific operations */
+		plat_mcusys_pwron_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		/* Perform the common cluster specific operations */
+		plat_cluster_pwron_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	/* Perform the common CPU specific operations */
+	plat_cpu_pwron_common(cpu, state, plat_power_state[cpu]);
+
+	plat_mt_pm_invoke_no_check(pwr_reflect, cpu, state);
+}
+
+static int plat_validate_power_state(unsigned int power_state,
+					psci_power_state_t *req_state)
+{
+	unsigned int pstate = psci_get_pstate_type(power_state);
+	unsigned int aff_lvl = psci_get_pstate_pwrlvl(power_state);
+	unsigned int cpu = plat_my_core_pos();
+
+	if (pstate == PSTATE_TYPE_STANDBY) {
+		req_state->pwr_domain_state[0] = PLAT_MAX_RET_STATE;
+	} else {
+		unsigned int i;
+		unsigned int pstate_id = psci_get_pstate_id(power_state);
+		plat_local_state_t s = MTK_LOCAL_STATE_OFF;
+
+		/* Use pstate_id to be power domain state */
+		if (pstate_id > s) {
+			s = (plat_local_state_t)pstate_id;
+		}
+
+		for (i = 0U; i <= aff_lvl; i++) {
+			req_state->pwr_domain_state[i] = s;
+		}
+	}
+
+	plat_power_state[cpu] = power_state;
+	return PSCI_E_SUCCESS;
+}
+
+static void plat_get_sys_suspend_power_state(psci_power_state_t *req_state)
+{
+	unsigned int lv;
+	unsigned int cpu = plat_my_core_pos();
+
+	for (lv = PSCI_CPU_PWR_LVL; lv <= PLAT_MAX_PWR_LVL; lv++) {
+		req_state->pwr_domain_state[lv] = PLAT_MAX_OFF_STATE;
+	}
+
+	plat_power_state[cpu] =
+			psci_make_powerstate(
+				MT_PLAT_PWR_STATE_SYSTEM_SUSPEND,
+				PSTATE_TYPE_POWERDOWN, PLAT_MAX_PWR_LVL);
+
+	flush_dcache_range((uintptr_t)
+			&plat_power_state[cpu],
+			sizeof(plat_power_state[cpu]));
+}
+
+static void __dead2 plat_mtk_system_off(void)
+{
+	INFO("MTK System Off\n");
+
+	rtc_power_off_sequence();
+	pmic_power_off();
+
+	wfi();
+	ERROR("MTK System Off: operation not handled.\n");
+	panic();
+}
+
 static void __dead2 plat_mtk_system_reset(void)
 {
 	struct bl_aux_gpio_info *gpio_reset = plat_get_mtk_gpio_reset();
@@ -29,18 +364,35 @@
 	panic();
 }
 
-/*******************************************************************************
- * MTK_platform handler called when an affinity instance is about to be turned
- * on. The level and mpidr determine the affinity instance.
- ******************************************************************************/
-static const plat_psci_ops_t plat_plat_pm_ops = {
-	.system_reset         = plat_mtk_system_reset,
+static const plat_psci_ops_t plat_psci_ops = {
+	.system_reset			= plat_mtk_system_reset,
+	.cpu_standby			= plat_cpu_standby,
+	.pwr_domain_on			= plat_power_domain_on,
+	.pwr_domain_on_finish		= plat_power_domain_on_finish,
+	.pwr_domain_off			= plat_power_domain_off,
+	.pwr_domain_suspend		= plat_power_domain_suspend,
+	.pwr_domain_suspend_finish	= plat_power_domain_suspend_finish,
+	.system_off			= plat_mtk_system_off,
+	.validate_power_state		= plat_validate_power_state,
+	.get_sys_suspend_power_state	= plat_get_sys_suspend_power_state
 };
 
 int plat_setup_psci_ops(uintptr_t sec_entrypoint,
 			const plat_psci_ops_t **psci_ops)
 {
-	*psci_ops = &plat_plat_pm_ops;
+	*psci_ops = &plat_psci_ops;
+	secure_entrypoint = sec_entrypoint;
+
+	/*
+	 * init the warm reset config for boot CPU
+	 * reset arch as AARCH64
+	 * reset addr as function bl31_warm_entrypoint()
+	 */
+	mcucfg_init_archstate(0U, 0U, true);
+	mcucfg_set_bootaddr(0U, 0U, secure_entrypoint);
+
+	spmc_init();
+	plat_mt_pm = mt_plat_cpu_pm_init();
 
 	return 0;
 }
diff --git a/plat/mediatek/mt8192/plat_sip_calls.c b/plat/mediatek/mt8192/plat_sip_calls.c
new file mode 100644
index 0000000..353faf8
--- /dev/null
+++ b/plat/mediatek/mt8192/plat_sip_calls.c
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <mtk_apusys.h>
+#include <mtk_sip_svc.h>
+#include <mt_spm_vcorefs.h>
+#include <plat_dfd.h>
+#include "plat_sip_calls.h"
+
+uintptr_t mediatek_plat_sip_handler(uint32_t smc_fid,
+				u_register_t x1,
+				u_register_t x2,
+				u_register_t x3,
+				u_register_t x4,
+				void *cookie,
+				void *handle,
+				u_register_t flags)
+{
+	uint64_t ret;
+	uint32_t rnd_val0 = 0U;
+
+	switch (smc_fid) {
+	case MTK_SIP_VCORE_CONTROL_ARCH32:
+	case MTK_SIP_VCORE_CONTROL_ARCH64:
+		ret = spm_vcorefs_args(x1, x2, x3, (uint64_t *)&x4);
+		SMC_RET2(handle, ret, x4);
+		break;
+	case MTK_SIP_APUSYS_CONTROL_AARCH32:
+	case MTK_SIP_APUSYS_CONTROL_AARCH64:
+		ret = apusys_kernel_ctrl(x1, x2, x3, x4, &rnd_val0);
+		SMC_RET2(handle, ret, rnd_val0);
+		break;
+	case MTK_SIP_KERNEL_DFD_AARCH32:
+	case MTK_SIP_KERNEL_DFD_AARCH64:
+		ret = dfd_smc_dispatcher(x1, x2, x3, x4);
+		SMC_RET1(handle, ret);
+		break;
+	default:
+		ERROR("%s: unhandled SMC (0x%x)\n", __func__, smc_fid);
+		break;
+	}
+
+	SMC_RET1(handle, SMC_UNK);
+}
diff --git a/plat/mediatek/mt8192/plat_topology.c b/plat/mediatek/mt8192/plat_topology.c
index aa4975e..8c1231a 100644
--- a/plat/mediatek/mt8192/plat_topology.c
+++ b/plat/mediatek/mt8192/plat_topology.c
@@ -17,6 +17,8 @@
 	/* Number of root nodes */
 	PLATFORM_SYSTEM_COUNT,
 	/* Number of children for the root node */
+	PLATFORM_MCUSYS_COUNT,
+	/* Number of children for the mcusys node */
 	PLATFORM_CLUSTER_COUNT,
 	/* Number of children for the first cluster node */
 	PLATFORM_CLUSTER0_CORE_COUNT,
diff --git a/plat/mediatek/mt8192/platform.mk b/plat/mediatek/mt8192/platform.mk
index 7544b26..cbdaadd 100644
--- a/plat/mediatek/mt8192/platform.mk
+++ b/plat/mediatek/mt8192/platform.mk
@@ -8,10 +8,24 @@
 MTK_PLAT_SOC  := ${MTK_PLAT}/${PLAT}
 
 PLAT_INCLUDES := -I${MTK_PLAT}/common/                            \
+                 -I${MTK_PLAT}/common/drivers/gic600/             \
+                 -I${MTK_PLAT}/common/drivers/gpio/               \
+                 -I${MTK_PLAT}/common/drivers/rtc/                \
+                 -I${MTK_PLAT}/common/drivers/timer/              \
+                 -I${MTK_PLAT}/common/drivers/uart/               \
+                 -I${MTK_PLAT}/common/lpm/                        \
                  -I${MTK_PLAT_SOC}/include/                       \
                  -I${MTK_PLAT_SOC}/drivers/                       \
+                 -I${MTK_PLAT_SOC}/drivers/apusys/                \
+                 -I${MTK_PLAT_SOC}/drivers/dcm                    \
+                 -I${MTK_PLAT_SOC}/drivers/devapc                 \
+                 -I${MTK_PLAT_SOC}/drivers/dfd                    \
+                 -I${MTK_PLAT_SOC}/drivers/emi_mpu/               \
                  -I${MTK_PLAT_SOC}/drivers/gpio/                  \
-                 -I${MTK_PLAT_SOC}/drivers/timer/
+                 -I${MTK_PLAT_SOC}/drivers/mcdi/                  \
+                 -I${MTK_PLAT_SOC}/drivers/pmic/                  \
+                 -I${MTK_PLAT_SOC}/drivers/ptp3/                  \
+                 -I${MTK_PLAT_SOC}/drivers/spmc/
 
 GICV3_SUPPORT_GIC600        :=      1
 include drivers/arm/gic/v3/gicv3.mk
@@ -23,24 +37,50 @@
                           plat/common/plat_psci_common.c
 
 BL31_SOURCES    += common/desc_image_load.c                              \
+                   drivers/delay_timer/delay_timer.c                     \
+                   drivers/delay_timer/generic_delay_timer.c             \
                    drivers/ti/uart/aarch64/16550_console.S               \
                    drivers/gpio/gpio.c                                   \
                    lib/bl_aux_params/bl_aux_params.c                     \
                    lib/cpus/aarch64/cortex_a55.S                         \
                    lib/cpus/aarch64/cortex_a76.S                         \
                    plat/common/plat_gicv3.c                              \
+                   ${MTK_PLAT}/common/drivers/gic600/mt_gic_v3.c         \
+                   ${MTK_PLAT}/common/drivers/gpio/mtgpio_common.c       \
+                   ${MTK_PLAT}/common/drivers/pmic_wrap/pmic_wrap_init_v2.c \
+                   ${MTK_PLAT}/common/drivers/rtc/rtc_common.c           \
+                   ${MTK_PLAT}/common/drivers/rtc/rtc_mt6359p.c          \
+                   ${MTK_PLAT}/common/drivers/timer/mt_timer.c           \
+                   ${MTK_PLAT}/common/drivers/uart/uart.c                \
+                   ${MTK_PLAT}/common/lpm/mt_lp_rm.c                     \
+                   ${MTK_PLAT}/common/mtk_cirq.c                         \
                    ${MTK_PLAT}/common/mtk_plat_common.c                  \
+                   ${MTK_PLAT}/common/mtk_sip_svc.c                      \
                    ${MTK_PLAT}/common/params_setup.c                     \
                    ${MTK_PLAT_SOC}/aarch64/platform_common.c             \
                    ${MTK_PLAT_SOC}/aarch64/plat_helpers.S                \
                    ${MTK_PLAT_SOC}/bl31_plat_setup.c                     \
+                   ${MTK_PLAT_SOC}/drivers/pmic/pmic.c                   \
                    ${MTK_PLAT_SOC}/plat_pm.c                             \
                    ${MTK_PLAT_SOC}/plat_topology.c                       \
-                   ${MTK_PLAT_SOC}/plat_mt_gic.c                         \
-                   ${MTK_PLAT_SOC}/plat_mt_cirq.c                        \
+                   ${MTK_PLAT_SOC}/plat_sip_calls.c                      \
+                   ${MTK_PLAT_SOC}/drivers/apusys/mtk_apusys.c           \
+                   ${MTK_PLAT_SOC}/drivers/apusys/mtk_apusys_apc.c       \
+                   ${MTK_PLAT_SOC}/drivers/dcm/mtk_dcm.c                 \
+                   ${MTK_PLAT_SOC}/drivers/dcm/mtk_dcm_utils.c           \
+                   ${MTK_PLAT_SOC}/drivers/devapc/devapc.c               \
+                   ${MTK_PLAT_SOC}/drivers/dfd/plat_dfd.c                \
+                   ${MTK_PLAT_SOC}/drivers/emi_mpu/emi_mpu.c             \
                    ${MTK_PLAT_SOC}/drivers/gpio/mtgpio.c                 \
-                   ${MTK_PLAT_SOC}/drivers/timer/mt_timer.c
+                   ${MTK_PLAT_SOC}/drivers/mcdi/mt_cpu_pm.c              \
+                   ${MTK_PLAT_SOC}/drivers/mcdi/mt_cpu_pm_cpc.c          \
+                   ${MTK_PLAT_SOC}/drivers/mcdi/mt_lp_irqremain.c        \
+                   ${MTK_PLAT_SOC}/drivers/mcdi/mt_mcdi.c                \
+                   ${MTK_PLAT_SOC}/drivers/ptp3/mtk_ptp3_main.c          \
+                   ${MTK_PLAT_SOC}/drivers/spmc/mtspmc.c
 
+# Build SPM drivers
+include ${MTK_PLAT_SOC}/drivers/spm/build.mk
 
 # Configs for A76 and A55
 HW_ASSISTED_COHERENCY := 1
diff --git a/plat/mediatek/mt8195/aarch64/plat_helpers.S b/plat/mediatek/mt8195/aarch64/plat_helpers.S
new file mode 100644
index 0000000..a973f4d
--- /dev/null
+++ b/plat/mediatek/mt8195/aarch64/plat_helpers.S
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <platform_def.h>
+
+	.globl plat_is_my_cpu_primary
+	.globl plat_my_core_pos
+	.globl plat_mediatek_calc_core_pos
+
+func plat_is_my_cpu_primary
+	mrs	x0, mpidr_el1
+	and	x0, x0, #(MPIDR_CLUSTER_MASK | MPIDR_CPU_MASK)
+	cmp	x0, #PLAT_PRIMARY_CPU
+	cset	x0, eq
+	ret
+endfunc plat_is_my_cpu_primary
+
+	/* -----------------------------------------------------
+	 *  unsigned int plat_my_core_pos(void)
+	 *  This function uses the plat_mediatek_calc_core_pos()
+	 *  definition to get the index of the calling CPU.
+	 * -----------------------------------------------------
+	 */
+func plat_my_core_pos
+	mrs	x0, mpidr_el1
+	b	plat_mediatek_calc_core_pos
+endfunc plat_my_core_pos
+
+	/* -----------------------------------------------------
+	 * unsigned int plat_mediatek_calc_core_pos(u_register_t mpidr);
+	 *
+	 * In ARMv8.2, AFF2 is cluster id, AFF1 is core id and
+	 * AFF0 is thread id. There is only one cluster in ARMv8.2
+	 * and one thread in current implementation.
+	 *
+	 * With this function: CorePos = CoreID (AFF1)
+	 * we do it with x0 = (x0 >> 8) & 0xff
+	 * -----------------------------------------------------
+	 */
+func plat_mediatek_calc_core_pos
+	mov	x1, #MPIDR_AFFLVL_MASK
+	and	x0, x1, x0, lsr #MPIDR_AFF1_SHIFT
+	ret
+endfunc plat_mediatek_calc_core_pos
diff --git a/plat/mediatek/mt8195/aarch64/platform_common.c b/plat/mediatek/mt8195/aarch64/platform_common.c
new file mode 100644
index 0000000..4792746
--- /dev/null
+++ b/plat/mediatek/mt8195/aarch64/platform_common.c
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#include <platform_def.h>
+
+/* Table of regions to map using the MMU.  */
+const mmap_region_t plat_mmap[] = {
+	/* for TF text, RO, RW */
+	MAP_REGION_FLAT(MTK_DEV_RNG0_BASE, MTK_DEV_RNG0_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(MTK_DEV_RNG2_BASE, MTK_DEV_RNG2_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(MTK_MCDI_SRAM_BASE, MTK_MCDI_SRAM_MAP_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(DP_SEC_BASE, DP_SEC_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(eDP_SEC_BASE, eDP_SEC_SIZE,
+			MT_DEVICE | MT_RW | MT_SECURE),
+	{ 0 }
+};
+
+/*******************************************************************************
+ * Macro generating the code for the function setting up the pagetables as per
+ * the platform memory map & initialize the mmu, for the given exception level
+ ******************************************************************************/
+void plat_configure_mmu_el3(uintptr_t total_base,
+			    uintptr_t total_size,
+			    uintptr_t ro_start,
+			    uintptr_t ro_limit)
+{
+	mmap_add_region(total_base, total_base, total_size,
+			MT_RW_DATA | MT_SECURE);
+	mmap_add_region(ro_start, ro_start, ro_limit - ro_start,
+			MT_CODE | MT_SECURE);
+	mmap_add(plat_mmap);
+	init_xlat_tables();
+	enable_mmu_el3(0);
+}
+
+unsigned int plat_get_syscnt_freq2(void)
+{
+	return SYS_COUNTER_FREQ_IN_TICKS;
+}
diff --git a/plat/mediatek/mt8195/bl31_plat_setup.c b/plat/mediatek/mt8195/bl31_plat_setup.c
new file mode 100644
index 0000000..dff6670
--- /dev/null
+++ b/plat/mediatek/mt8195/bl31_plat_setup.c
@@ -0,0 +1,117 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/* System Includes */
+#include <assert.h>
+
+/* Project Includes */
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <common/desc_image_load.h>
+#include <drivers/generic_delay_timer.h>
+#include <drivers/ti/uart/uart_16550.h>
+#include <lib/coreboot.h>
+
+/* Platform Includes */
+#include <emi_mpu.h>
+#include <mt_gic_v3.h>
+#include <mt_spm.h>
+#include <mt_timer.h>
+#include <mtk_dcm.h>
+#include <mtgpio.h>
+#include <plat_params.h>
+#include <plat_private.h>
+
+static entry_point_info_t bl32_ep_info;
+static entry_point_info_t bl33_ep_info;
+
+/*******************************************************************************
+ * Return a pointer to the 'entry_point_info' structure of the next image for
+ * the security state specified. BL33 corresponds to the non-secure image type
+ * while BL32 corresponds to the secure image type. A NULL pointer is returned
+ * if the image does not exist.
+ ******************************************************************************/
+entry_point_info_t *bl31_plat_get_next_image_ep_info(uint32_t type)
+{
+	entry_point_info_t *next_image_info;
+
+	next_image_info = (type == NON_SECURE) ? &bl33_ep_info : &bl32_ep_info;
+	assert(next_image_info->h.type == PARAM_EP);
+
+	/* None of the images on this platform can have 0x0 as the entrypoint */
+	if (next_image_info->pc) {
+		return next_image_info;
+	} else {
+		return NULL;
+	}
+}
+
+/*******************************************************************************
+ * Perform any BL31 early platform setup. Here is an opportunity to copy
+ * parameters passed by the calling EL (S-EL1 in BL2 & S-EL3 in BL1) before they
+ * are lost (potentially). This needs to be done before the MMU is initialized
+ * so that the memory layout can be used while creating page tables.
+ * BL2 has flushed this information to memory, so we are guaranteed to pick up
+ * good data.
+ ******************************************************************************/
+void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
+				u_register_t arg2, u_register_t arg3)
+{
+	static console_t console;
+
+	params_early_setup(arg1);
+
+#if COREBOOT
+	if (coreboot_serial.type) {
+		console_16550_register(coreboot_serial.baseaddr,
+				       coreboot_serial.input_hertz,
+				       coreboot_serial.baud,
+				       &console);
+	}
+#else
+	console_16550_register(UART0_BASE, UART_CLOCK, UART_BAUDRATE, &console);
+#endif
+
+	NOTICE("MT8195 bl31_setup\n");
+
+	bl31_params_parse_helper(arg0, &bl32_ep_info, &bl33_ep_info);
+}
+
+
+/*******************************************************************************
+ * Perform any BL31 platform setup code
+ ******************************************************************************/
+void bl31_platform_setup(void)
+{
+	/* Set dcm on */
+	if (!dcm_set_default()) {
+		ERROR("Failed to set default dcm on!!\n");
+	}
+
+	/* Initialize EMI MPU */
+	emi_mpu_init();
+
+	/* Initialize the GIC driver, CPU and distributor interfaces */
+	mt_gic_driver_init();
+	mt_gic_init();
+
+	mt_gpio_init();
+	mt_systimer_init();
+	generic_delay_timer_init();
+	spm_boot_init();
+}
+
+/*******************************************************************************
+ * Perform the very early platform specific architectural setup here. At the
+ * moment this is only intializes the mmu in a quick and dirty way.
+ ******************************************************************************/
+void bl31_plat_arch_setup(void)
+{
+	plat_configure_mmu_el3(BL31_START,
+			       BL31_END - BL31_START,
+			       BL_CODE_BASE,
+			       BL_CODE_END);
+}
diff --git a/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.c b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.c
new file mode 100644
index 0000000..aed0833
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.c
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <mtk_dcm.h>
+#include <mtk_dcm_utils.h>
+
+static void dcm_armcore(bool mode)
+{
+	dcm_mp_cpusys_top_bus_pll_div_dcm(mode);
+	dcm_mp_cpusys_top_cpu_pll_div_0_dcm(mode);
+	dcm_mp_cpusys_top_cpu_pll_div_1_dcm(mode);
+}
+
+static void dcm_mcusys(bool on)
+{
+	dcm_mp_cpusys_top_adb_dcm(on);
+	dcm_mp_cpusys_top_apb_dcm(on);
+	dcm_mp_cpusys_top_cpubiu_dcm(on);
+	dcm_mp_cpusys_top_misc_dcm(on);
+	dcm_mp_cpusys_top_mp0_qdcm(on);
+	dcm_cpccfg_reg_emi_wfifo(on);
+	dcm_mp_cpusys_top_last_cor_idle_dcm(on);
+}
+
+static void dcm_stall(bool on)
+{
+	dcm_mp_cpusys_top_core_stall_dcm(on);
+	dcm_mp_cpusys_top_fcm_stall_dcm(on);
+}
+
+static bool check_dcm_state(void)
+{
+	bool ret = true;
+
+	ret &= dcm_mp_cpusys_top_bus_pll_div_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on();
+
+	ret &= dcm_mp_cpusys_top_adb_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_apb_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_cpubiu_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_misc_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_mp0_qdcm_is_on();
+	ret &= dcm_cpccfg_reg_emi_wfifo_is_on();
+	ret &= dcm_mp_cpusys_top_last_cor_idle_dcm_is_on();
+
+	ret &= dcm_mp_cpusys_top_core_stall_dcm_is_on();
+	ret &= dcm_mp_cpusys_top_fcm_stall_dcm_is_on();
+
+	return ret;
+}
+
+bool dcm_set_default(void)
+{
+	dcm_armcore(true);
+	dcm_mcusys(true);
+	dcm_stall(true);
+
+	return check_dcm_state();
+}
diff --git a/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.h b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.h
new file mode 100644
index 0000000..cb65b85
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_DCM_H
+#define MTK_DCM_H
+
+#include <stdbool.h>
+
+bool dcm_set_default(void);
+
+#endif /* #ifndef MTK_DCM_H */
diff --git a/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.c b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.c
new file mode 100644
index 0000000..a1a3720
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.c
@@ -0,0 +1,483 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mtk_dcm_utils.h>
+
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_MASK (BIT(17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_MASK (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18) | \
+			BIT(21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_MASK (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18))
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_ON (BIT(17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_ON (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18) | \
+			BIT(21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_ON (BIT(15) | \
+			BIT(16) | \
+			BIT(17) | \
+			BIT(18))
+#define MP_CPUSYS_TOP_ADB_DCM_REG0_OFF ((0x0 << 17))
+#define MP_CPUSYS_TOP_ADB_DCM_REG1_OFF ((0x0 << 15) | \
+			(0x0 << 16) | \
+			(0x0 << 17) | \
+			(0x0 << 18) | \
+			(0x0 << 21))
+#define MP_CPUSYS_TOP_ADB_DCM_REG2_OFF ((0x0 << 15) | \
+			(0x0 << 16) | \
+			(0x0 << 17) | \
+			(0x0 << 18))
+
+bool dcm_mp_cpusys_top_adb_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG0) &
+		MP_CPUSYS_TOP_ADB_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG0_ON);
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG4) &
+		MP_CPUSYS_TOP_ADB_DCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG1_ON);
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0) &
+		MP_CPUSYS_TOP_ADB_DCM_REG2_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_ADB_DCM_REG2_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_adb_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_adb_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_ON);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG4,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_ON);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_adb_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG0_OFF);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_ADB_DCM_CFG4,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG1_OFF);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_ADB_DCM_REG2_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_APB_DCM_REG0_MASK (BIT(5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_MASK (BIT(8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_MASK (BIT(16))
+#define MP_CPUSYS_TOP_APB_DCM_REG0_ON (BIT(5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_ON (BIT(8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_ON (BIT(16))
+#define MP_CPUSYS_TOP_APB_DCM_REG0_OFF ((0x0 << 5))
+#define MP_CPUSYS_TOP_APB_DCM_REG1_OFF ((0x0 << 8))
+#define MP_CPUSYS_TOP_APB_DCM_REG2_OFF ((0x0 << 16))
+
+bool dcm_mp_cpusys_top_apb_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG0_ON);
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG1_ON);
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP0_DCM_CFG0) &
+		MP_CPUSYS_TOP_APB_DCM_REG2_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_APB_DCM_REG2_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_apb_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_apb_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG0_ON);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG1_ON);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG2_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_apb_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG0_OFF);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCUSYS_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG1_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG1_OFF);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_APB_DCM_REG2_MASK,
+			MP_CPUSYS_TOP_APB_DCM_REG2_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK (BIT(11) | \
+			BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON (BIT(11) | \
+			BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_OFF ((0x0 << 11) | \
+			(0x0 << 24) | \
+			(0x0 << 25))
+
+bool dcm_mp_cpusys_top_bus_pll_div_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG) &
+		MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_bus_pll_div_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_bus_pll_div_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_bus_pll_div_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_BUS_PLL_DIV_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK (BIT(0))
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON (BIT(0))
+#define MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_OFF ((0x0 << 0))
+
+bool dcm_mp_cpusys_top_core_stall_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP0_DCM_CFG7) &
+		MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_core_stall_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_core_stall_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_core_stall_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CORE_STALL_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK ((0xffff << 0))
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON ((0xffff << 0))
+#define MP_CPUSYS_TOP_CPUBIU_DCM_REG0_OFF ((0x0 << 0))
+
+bool dcm_mp_cpusys_top_cpubiu_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MCSIC_DCM0) &
+		MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpubiu_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpubiu_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCSIC_DCM0,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpubiu_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MCSIC_DCM0,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPUBIU_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK (BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON (BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_OFF ((0x0 << 24) | \
+			(0x0 << 25))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG0) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_0_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_0_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG0,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_0_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG0,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_0_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK (BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON (BIT(24) | \
+			BIT(25))
+#define MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_OFF ((0x0 << 24) | \
+			(0x0 << 25))
+
+bool dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG1) &
+		MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_cpu_pll_div_1_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_cpu_pll_div_1_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG1,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_cpu_pll_div_1_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_CPU_PLLDIV_CFG1,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_CPU_PLL_DIV_1_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK (BIT(4))
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON (BIT(4))
+#define MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_OFF ((0x0 << 4))
+
+bool dcm_mp_cpusys_top_fcm_stall_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP0_DCM_CFG7) &
+		MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_fcm_stall_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_fcm_stall_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_fcm_stall_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG7,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_FCM_STALL_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK ((0x1U << 31))
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON ((0x1U << 31))
+#define MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_OFF ((0x0U << 31))
+
+bool dcm_mp_cpusys_top_last_cor_idle_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG) &
+		MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_last_cor_idle_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_last_cor_idle_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_last_cor_idle_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_BUS_PLLDIV_CFG,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_LAST_COR_IDLE_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_MASK (BIT(1) | \
+			BIT(4))
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_ON (BIT(1) | \
+			BIT(4))
+#define MP_CPUSYS_TOP_MISC_DCM_REG0_OFF ((0x0 << 1) | \
+			(0x0 << 4))
+
+bool dcm_mp_cpusys_top_misc_dcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_MISC_DCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MISC_DCM_REG0_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_misc_dcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_misc_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_misc_dcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_MASK,
+			MP_CPUSYS_TOP_MISC_DCM_REG0_OFF);
+	}
+}
+
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK (BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_ON (BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_ON (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG0_OFF ((0x0 << 3))
+#define MP_CPUSYS_TOP_MP0_QDCM_REG1_OFF ((0x0 << 0) | \
+			(0x0 << 1) | \
+			(0x0 << 2) | \
+			(0x0 << 3))
+
+bool dcm_mp_cpusys_top_mp0_qdcm_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0) &
+		MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MP0_QDCM_REG0_ON);
+	ret &= ((mmio_read_32(MP_CPUSYS_TOP_MP0_DCM_CFG0) &
+		MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK) ==
+		(unsigned int) MP_CPUSYS_TOP_MP0_QDCM_REG1_ON);
+
+	return ret;
+}
+
+void dcm_mp_cpusys_top_mp0_qdcm(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'mp_cpusys_top_mp0_qdcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_ON);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'mp_cpusys_top_mp0_qdcm'" */
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP_MISC_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG0_OFF);
+		mmio_clrsetbits_32(MP_CPUSYS_TOP_MP0_DCM_CFG0,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_MASK,
+			MP_CPUSYS_TOP_MP0_QDCM_REG1_OFF);
+	}
+}
+
+#define CPCCFG_REG_EMI_WFIFO_REG0_MASK (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define CPCCFG_REG_EMI_WFIFO_REG0_ON (BIT(0) | \
+			BIT(1) | \
+			BIT(2) | \
+			BIT(3))
+#define CPCCFG_REG_EMI_WFIFO_REG0_OFF ((0x0 << 0) | \
+			(0x0 << 1) | \
+			(0x0 << 2) | \
+			(0x0 << 3))
+
+bool dcm_cpccfg_reg_emi_wfifo_is_on(void)
+{
+	bool ret = true;
+
+	ret &= ((mmio_read_32(CPCCFG_REG_EMI_WFIFO) &
+		CPCCFG_REG_EMI_WFIFO_REG0_MASK) ==
+		(unsigned int) CPCCFG_REG_EMI_WFIFO_REG0_ON);
+
+	return ret;
+}
+
+void dcm_cpccfg_reg_emi_wfifo(bool on)
+{
+	if (on) {
+		/* TINFO = "Turn ON DCM 'cpccfg_reg_emi_wfifo'" */
+		mmio_clrsetbits_32(CPCCFG_REG_EMI_WFIFO,
+			CPCCFG_REG_EMI_WFIFO_REG0_MASK,
+			CPCCFG_REG_EMI_WFIFO_REG0_ON);
+	} else {
+		/* TINFO = "Turn OFF DCM 'cpccfg_reg_emi_wfifo'" */
+		mmio_clrsetbits_32(CPCCFG_REG_EMI_WFIFO,
+			CPCCFG_REG_EMI_WFIFO_REG0_MASK,
+			CPCCFG_REG_EMI_WFIFO_REG0_OFF);
+	}
+}
diff --git a/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.h b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.h
new file mode 100644
index 0000000..e5743af
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dcm/mtk_dcm_utils.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_DCM_UTILS_H
+#define MTK_DCM_UTILS_H
+
+#include <stdbool.h>
+
+#include <mtk_dcm.h>
+#include <platform_def.h>
+
+/* Base */
+#define MP_CPUSYS_TOP_BASE	(MCUCFG_BASE + 0x8000)
+#define CPCCFG_REG_BASE		(MCUCFG_BASE + 0xA800)
+
+/* Register Definition */
+#define MP_CPUSYS_TOP_CPU_PLLDIV_CFG0 (MP_CPUSYS_TOP_BASE + 0x22a0)
+#define MP_CPUSYS_TOP_CPU_PLLDIV_CFG1 (MP_CPUSYS_TOP_BASE + 0x22a4)
+#define MP_CPUSYS_TOP_BUS_PLLDIV_CFG (MP_CPUSYS_TOP_BASE + 0x22e0)
+#define MP_CPUSYS_TOP_MCSIC_DCM0 (MP_CPUSYS_TOP_BASE + 0x2440)
+#define MP_CPUSYS_TOP_MP_ADB_DCM_CFG0 (MP_CPUSYS_TOP_BASE + 0x2500)
+#define MP_CPUSYS_TOP_MP_ADB_DCM_CFG4 (MP_CPUSYS_TOP_BASE + 0x2510)
+#define MP_CPUSYS_TOP_MP_MISC_DCM_CFG0 (MP_CPUSYS_TOP_BASE + 0x2518)
+#define MP_CPUSYS_TOP_MCUSYS_DCM_CFG0 (MP_CPUSYS_TOP_BASE + 0x25c0)
+#define CPCCFG_REG_EMI_WFIFO (CPCCFG_REG_BASE + 0x100)
+#define MP_CPUSYS_TOP_MP0_DCM_CFG0 (MP_CPUSYS_TOP_BASE + 0x4880)
+#define MP_CPUSYS_TOP_MP0_DCM_CFG7 (MP_CPUSYS_TOP_BASE + 0x489c)
+
+/* MP_CPUSYS_TOP */
+bool dcm_mp_cpusys_top_adb_dcm_is_on(void);
+void dcm_mp_cpusys_top_adb_dcm(bool on);
+bool dcm_mp_cpusys_top_apb_dcm_is_on(void);
+void dcm_mp_cpusys_top_apb_dcm(bool on);
+bool dcm_mp_cpusys_top_bus_pll_div_dcm_is_on(void);
+void dcm_mp_cpusys_top_bus_pll_div_dcm(bool on);
+bool dcm_mp_cpusys_top_core_stall_dcm_is_on(void);
+void dcm_mp_cpusys_top_core_stall_dcm(bool on);
+bool dcm_mp_cpusys_top_cpubiu_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpubiu_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_0_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_0_dcm(bool on);
+bool dcm_mp_cpusys_top_cpu_pll_div_1_dcm_is_on(void);
+void dcm_mp_cpusys_top_cpu_pll_div_1_dcm(bool on);
+bool dcm_mp_cpusys_top_fcm_stall_dcm_is_on(void);
+void dcm_mp_cpusys_top_fcm_stall_dcm(bool on);
+bool dcm_mp_cpusys_top_last_cor_idle_dcm_is_on(void);
+void dcm_mp_cpusys_top_last_cor_idle_dcm(bool on);
+bool dcm_mp_cpusys_top_misc_dcm_is_on(void);
+void dcm_mp_cpusys_top_misc_dcm(bool on);
+bool dcm_mp_cpusys_top_mp0_qdcm_is_on(void);
+void dcm_mp_cpusys_top_mp0_qdcm(bool on);
+/* CPCCFG_REG */
+bool dcm_cpccfg_reg_emi_wfifo_is_on(void);
+void dcm_cpccfg_reg_emi_wfifo(bool on);
+
+#endif
diff --git a/plat/mediatek/mt8195/drivers/dfd/plat_dfd.c b/plat/mediatek/mt8195/drivers/dfd/plat_dfd.c
new file mode 100644
index 0000000..c083318
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dfd/plat_dfd.c
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mtk_sip_svc.h>
+#include <plat_dfd.h>
+
+static bool dfd_enabled;
+static uint64_t dfd_base_addr;
+static uint64_t dfd_chain_length;
+static uint64_t dfd_cache_dump;
+
+static void dfd_setup(uint64_t base_addr, uint64_t chain_length,
+		      uint64_t cache_dump)
+{
+	mmio_write_32(MTK_WDT_LATCH_CTL2, MTK_WDT_LATCH_CTL2_VAL);
+	mmio_write_32(MTK_WDT_INTERVAL, MTK_WDT_INTERVAL_VAL);
+	mmio_write_32(MTK_DRM_LATCH_CTL2, MTK_DRM_LATCH_CTL2_VAL);
+	mmio_write_32(MTK_DRM_LATCH_CTL1, MTK_DRM_LATCH_CTL1_VAL);
+
+	/* Bit[2] = 0 (default=1), disable dfd apb bus protect_en */
+	mmio_clrbits_32(DFD_O_INTRF_MCU_PWR_CTL_MASK, 0x1 << 2);
+
+	/* Bit[0] : enable?mcusys_vproc?external_off?dfd?trigger -> 1 */
+	mmio_setbits_32(DFD_V50_GROUP_0_63_DIFF, 0x1);
+
+	/* bit[0]: rg_rw_dfd_internal_dump_en -> 1 */
+	/* bit[2]: rg_rw_dfd_clock_stop_en -> 1 */
+	sync_writel(DFD_INTERNAL_CTL, 0x5);
+
+	/* bit[13]: xreset_b_update_disable */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x1 << 13);
+
+	/*
+	 * bit[10:3]: DFD trigger selection mask
+	 * bit[3]: rg_rw_dfd_trigger_sel[0] = 1(enable wdt trigger)
+	 * bit[4]: rg_rw_dfd_trigger_sel[1] = 1(enable HW trigger)
+	 * bit[5]: rg_rw_dfd_trigger_sel[2] = 1(enable SW trigger)
+	 * bit[6]: rg_rw_dfd_trigger_sel[3] = 1(enable SW non-security trigger)
+	 * bit[7]: rg_rw_dfd_trigger_sel[4] = 1(enable timer trigger)
+	 */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x1F << 3);
+
+	/*
+	 * bit[9]  : rg_rw_dfd_trigger_sel[6] = 1(cpu_eb_sw_dfd_trigger)
+	 * bit[10] : rg_rw_dfd_trigger_sel[7] = 1(cpu_eb_wdt_dfd_trigger)
+	 */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x3 << 9);
+
+	/* bit[20:19]: rg_dfd_armpll_div_mux_sel switch to PLL2 for DFD */
+	mmio_setbits_32(DFD_INTERNAL_CTL, 0x3 << 19);
+
+	/*
+	 * bit[0]: rg_rw_dfd_auto_power_on = 1
+	 * bit[2:1]: rg_rw_dfd_auto_power_on_dely = 1(10us)
+	 * bit[4:2]: rg_rw_dfd_power_on_wait_time = 1(20us)
+	 */
+	mmio_write_32(DFD_INTERNAL_PWR_ON, 0xB);
+
+	/* longest scan chain length */
+	mmio_write_32(DFD_CHAIN_LENGTH0, chain_length);
+
+	/* bit[1:0]: rg_rw_dfd_shift_clock_ratio */
+	mmio_write_32(DFD_INTERNAL_SHIFT_CLK_RATIO, 0x0);
+
+	/* rg_dfd_test_so_over_64 */
+	mmio_write_32(DFD_INTERNAL_TEST_SO_OVER_64, 0x1);
+
+	/* DFD3.0 */
+	mmio_write_32(DFD_TEST_SI_0, 0x0);
+	mmio_write_32(DFD_TEST_SI_1, 0x0);
+	mmio_write_32(DFD_TEST_SI_2, 0x0);
+	mmio_write_32(DFD_TEST_SI_3, 0x0);
+
+	/* for iLDO feature */
+	sync_writel(DFD_POWER_CTL, 0xF9);
+
+	/* read offset */
+	sync_writel(DFD_READ_ADDR, DFD_READ_ADDR_VAL);
+
+	/* for DFD-3.0 setup */
+	sync_writel(DFD_V30_CTL, 0xD);
+
+	/* set base address */
+	mmio_write_32(DFD_O_SET_BASEADDR_REG, base_addr >> 24);
+	mmio_write_32(DFD_O_REG_0, 0);
+
+	/* setup global variables for suspend and resume */
+	dfd_enabled = true;
+	dfd_base_addr = base_addr;
+	dfd_chain_length = chain_length;
+	dfd_cache_dump = cache_dump;
+
+	if ((cache_dump & DFD_CACHE_DUMP_ENABLE) != 0UL) {
+		mmio_write_32(MTK_DRM_LATCH_CTL2, MTK_DRM_LATCH_CTL2_CACHE_VAL);
+		sync_writel(DFD_V35_ENABLE, 0x1);
+		sync_writel(DFD_V35_TAP_NUMBER, 0xB);
+		sync_writel(DFD_V35_TAP_EN, DFD_V35_TAP_EN_VAL);
+		sync_writel(DFD_V35_SEQ0_0, DFD_V35_SEQ0_0_VAL);
+
+		/* Cache dump only mode */
+		sync_writel(DFD_V35_CTL, 0x1);
+		mmio_write_32(DFD_INTERNAL_NUM_OF_TEST_SO_GROUP, 0xF);
+		mmio_write_32(DFD_CHAIN_LENGTH0, DFD_CHAIN_LENGTH_VAL);
+		mmio_write_32(DFD_CHAIN_LENGTH1, DFD_CHAIN_LENGTH_VAL);
+		mmio_write_32(DFD_CHAIN_LENGTH2, DFD_CHAIN_LENGTH_VAL);
+		mmio_write_32(DFD_CHAIN_LENGTH3, DFD_CHAIN_LENGTH_VAL);
+
+		if ((cache_dump & DFD_PARITY_ERR_TRIGGER) != 0UL) {
+			sync_writel(DFD_HW_TRIGGER_MASK, 0xC);
+			mmio_setbits_32(DFD_INTERNAL_CTL, 0x1 << 4);
+		}
+	}
+	dsbsy();
+}
+
+void dfd_resume(void)
+{
+	if (dfd_enabled == true) {
+		dfd_setup(dfd_base_addr, dfd_chain_length, dfd_cache_dump);
+	}
+}
+
+uint64_t dfd_smc_dispatcher(uint64_t arg0, uint64_t arg1,
+			    uint64_t arg2, uint64_t arg3)
+{
+	uint64_t ret = 0L;
+
+	switch (arg0) {
+	case PLAT_MTK_DFD_SETUP_MAGIC:
+		INFO("[%s] DFD setup call from kernel\n", __func__);
+		dfd_setup(arg1, arg2, arg3);
+		break;
+	case PLAT_MTK_DFD_READ_MAGIC:
+		/* only allow to access DFD register base + 0x200 */
+		if (arg1 <= 0x200) {
+			ret = mmio_read_32(MISC1_CFG_BASE + arg1);
+		}
+		break;
+	case PLAT_MTK_DFD_WRITE_MAGIC:
+		/* only allow to access DFD register base + 0x200 */
+		if (arg1 <= 0x200) {
+			sync_writel(MISC1_CFG_BASE + arg1, arg2);
+		}
+		break;
+	default:
+		ret = MTK_SIP_E_INVALID_PARAM;
+		break;
+	}
+
+	return ret;
+}
diff --git a/plat/mediatek/mt8195/drivers/dfd/plat_dfd.h b/plat/mediatek/mt8195/drivers/dfd/plat_dfd.h
new file mode 100644
index 0000000..2a7e979
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dfd/plat_dfd.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_DFD_H
+#define PLAT_DFD_H
+
+#include <arch_helpers.h>
+#include <lib/mmio.h>
+#include <platform_def.h>
+
+#define sync_writel(addr, val)	do { mmio_write_32((addr), (val)); \
+				dsbsy(); \
+				} while (0)
+
+#define PLAT_MTK_DFD_SETUP_MAGIC		(0x99716150)
+#define PLAT_MTK_DFD_READ_MAGIC			(0x99716151)
+#define PLAT_MTK_DFD_WRITE_MAGIC		(0x99716152)
+
+#define MTK_DRM_LATCH_CTL1                      (DRM_BASE + 0x40)
+#define MTK_DRM_LATCH_CTL2			(DRM_BASE + 0x44)
+
+#define MTK_WDT_BASE				(RGU_BASE)
+#define MTK_WDT_INTERVAL			(MTK_WDT_BASE + 0x10)
+#define MTK_WDT_LATCH_CTL2			(MTK_WDT_BASE + 0x48)
+
+#define MCU_BIU_BASE				(MCUCFG_BASE)
+#define MISC1_CFG_BASE				(MCU_BIU_BASE + 0xE040)
+#define DFD_INTERNAL_CTL			(MISC1_CFG_BASE + 0x00)
+#define DFD_INTERNAL_PWR_ON			(MISC1_CFG_BASE + 0x08)
+#define DFD_CHAIN_LENGTH0			(MISC1_CFG_BASE + 0x0C)
+#define DFD_INTERNAL_SHIFT_CLK_RATIO		(MISC1_CFG_BASE + 0x10)
+#define DFD_CHAIN_LENGTH1			(MISC1_CFG_BASE + 0x1C)
+#define DFD_CHAIN_LENGTH2			(MISC1_CFG_BASE + 0x20)
+#define DFD_CHAIN_LENGTH3			(MISC1_CFG_BASE + 0x24)
+#define DFD_INTERNAL_TEST_SO_0			(MISC1_CFG_BASE + 0x28)
+#define DFD_INTERNAL_NUM_OF_TEST_SO_GROUP	(MISC1_CFG_BASE + 0x30)
+#define DFD_INTERNAL_TEST_SO_OVER_64		(MISC1_CFG_BASE + 0x34)
+#define DFD_INTERNAL_SW_NS_TRIGGER		(MISC1_CFG_BASE + 0x3c)
+#define DFD_V30_CTL				(MISC1_CFG_BASE + 0x48)
+#define DFD_V30_BASE_ADDR			(MISC1_CFG_BASE + 0x4C)
+#define DFD_POWER_CTL				(MISC1_CFG_BASE + 0x50)
+#define DFD_TEST_SI_0				(MISC1_CFG_BASE + 0x58)
+#define DFD_TEST_SI_1				(MISC1_CFG_BASE + 0x5C)
+#define DFD_CLEAN_STATUS			(MISC1_CFG_BASE + 0x60)
+#define DFD_TEST_SI_2				(MISC1_CFG_BASE + 0x1D8)
+#define DFD_TEST_SI_3				(MISC1_CFG_BASE + 0x1DC)
+#define DFD_READ_ADDR				(MISC1_CFG_BASE + 0x1E8)
+#define DFD_HW_TRIGGER_MASK			(MISC1_CFG_BASE + 0xBC)
+
+#define DFD_V35_ENABLE				(MCU_BIU_BASE + 0xE0A8)
+#define DFD_V35_TAP_NUMBER			(MCU_BIU_BASE + 0xE0AC)
+#define DFD_V35_TAP_EN				(MCU_BIU_BASE + 0xE0B0)
+#define DFD_V35_CTL				(MCU_BIU_BASE + 0xE0B4)
+#define DFD_V35_SEQ0_0				(MCU_BIU_BASE + 0xE0C0)
+#define DFD_V35_SEQ0_1				(MCU_BIU_BASE + 0xE0C4)
+#define DFD_V50_GROUP_0_63_DIFF			(MCU_BIU_BASE + 0xE2AC)
+
+#define DFD_O_PROTECT_EN_REG			(0x10001220)
+#define DFD_O_INTRF_MCU_PWR_CTL_MASK		(0x10001A3C)
+#define DFD_O_SET_BASEADDR_REG			(0x10043000)
+#define DFD_O_REG_0				(0x10001390)
+
+#define DFD_CACHE_DUMP_ENABLE			1U
+#define DFD_PARITY_ERR_TRIGGER			2U
+
+#define	DFD_V35_TAP_EN_VAL			(0x43FF)
+#define	DFD_V35_SEQ0_0_VAL			(0x63668820)
+#define DFD_READ_ADDR_VAL			(0x40000008)
+#define DFD_CHAIN_LENGTH_VAL			(0xFFFFFFFF)
+
+#define MTK_WDT_LATCH_CTL2_VAL			(0x9507FFFF)
+#define MTK_WDT_INTERVAL_VAL			(0x6600000A)
+#define MTK_DRM_LATCH_CTL2_VAL			(0x950600C8)
+#define MTK_DRM_LATCH_CTL2_CACHE_VAL		(0x95065DC0)
+
+#define MTK_DRM_LATCH_CTL1_VAL			(0x95000013)
+
+void dfd_resume(void);
+uint64_t dfd_smc_dispatcher(uint64_t arg0, uint64_t arg1,
+			    uint64_t arg2, uint64_t arg3);
+
+#endif /* PLAT_DFD_H */
diff --git a/plat/mediatek/mt8195/drivers/dp/mt_dp.c b/plat/mediatek/mt8195/drivers/dp/mt_dp.c
new file mode 100644
index 0000000..5930cd5
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dp/mt_dp.c
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <inttypes.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mt_dp.h>
+#include <mtk_sip_svc.h>
+#include <platform_def.h>
+
+static uint32_t dp_write_sec_reg(uint32_t is_edp, uint32_t offset,
+				uint32_t value, uint32_t mask)
+{
+	uint32_t reg = (is_edp != 0U) ? eDP_SEC_BASE : DP_SEC_BASE;
+
+	mmio_clrsetbits_32(reg + offset, mask, value);
+
+	return mmio_read_32(reg + offset);
+}
+
+int32_t dp_secure_handler(uint64_t cmd, uint64_t para, uint32_t *val)
+{
+	int32_t ret = 0L;
+	uint32_t is_edp = 0UL;
+	uint32_t regval = 0UL;
+	uint32_t regmsk = 0UL;
+	uint32_t fldmask = 0UL;
+
+	if ((cmd > DP_ATF_CMD_COUNT) || (val == NULL)) {
+		INFO("dp_secure_handler error cmd 0x%" PRIx64 "\n", cmd);
+		return MTK_SIP_E_INVALID_PARAM;
+	}
+
+	switch (cmd) {
+	case DP_ATF_DP_VIDEO_UNMUTE:
+		INFO("[%s] DP_ATF_DP_VIDEO_UNMUTE\n", __func__);
+		is_edp = DP_ATF_TYPE_DP;
+		ret = MTK_SIP_E_SUCCESS;
+		break;
+	case DP_ATF_EDP_VIDEO_UNMUTE:
+		INFO("[%s] DP_ATF_EDP_VIDEO_UNMUTE\n", __func__);
+		is_edp = DP_ATF_TYPE_EDP;
+		ret = MTK_SIP_E_SUCCESS;
+		break;
+	default:
+		ret = MTK_SIP_E_INVALID_PARAM;
+		break;
+	}
+
+	if (ret == MTK_SIP_E_SUCCESS) {
+		regmsk = (VIDEO_MUTE_SEL_SECURE_FLDMASK |
+				VIDEO_MUTE_SW_SECURE_FLDMASK);
+		if (para > 0U) {
+			fldmask = VIDEO_MUTE_SW_SECURE_FLDMASK;
+		} else {
+			fldmask = 0;
+		}
+
+		regval = (VIDEO_MUTE_SEL_SECURE_FLDMASK | fldmask);
+		*val = dp_write_sec_reg(is_edp, DP_TX_SECURE_REG11,
+					regval, regmsk);
+	}
+
+	return ret;
+}
diff --git a/plat/mediatek/mt8195/drivers/dp/mt_dp.h b/plat/mediatek/mt8195/drivers/dp/mt_dp.h
new file mode 100644
index 0000000..8157598
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/dp/mt_dp.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_DP_H
+#define MT_DP_H
+
+#define DP_TX_SECURE_REG11		(0x2c)
+
+#define VIDEO_MUTE_SEL_SECURE_FLDMASK	(0x10)
+#define VIDEO_MUTE_SW_SECURE_FLDMASK	(0x8)
+
+enum DP_ATF_HW_TYPE {
+	DP_ATF_TYPE_DP = 0,
+	DP_ATF_TYPE_EDP = 1
+};
+
+enum DP_ATF_CMD {
+	DP_ATF_DP_VIDEO_UNMUTE = 0x20,
+	DP_ATF_EDP_VIDEO_UNMUTE,
+	DP_ATF_CMD_COUNT
+};
+
+int32_t dp_secure_handler(uint64_t cmd, uint64_t para, uint32_t *val);
+
+#endif
diff --git a/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.c b/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.c
new file mode 100644
index 0000000..4330b77
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.c
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <emi_mpu.h>
+
+#if ENABLE_EMI_MPU_SW_LOCK
+static unsigned char region_lock_state[EMI_MPU_REGION_NUM];
+#endif
+
+#define EMI_MPU_START_MASK		(0x00FFFFFF)
+#define EMI_MPU_END_MASK		(0x00FFFFFF)
+#define EMI_MPU_APC_SW_LOCK_MASK	(0x00FFFFFF)
+#define EMI_MPU_APC_HW_LOCK_MASK	(0x80FFFFFF)
+
+static int _emi_mpu_set_protection(unsigned int start, unsigned int end,
+					unsigned int apc)
+{
+	unsigned int dgroup;
+	unsigned int region;
+
+	region = (start >> 24) & 0xFF;
+	start &= EMI_MPU_START_MASK;
+	dgroup = (end >> 24) & 0xFF;
+	end &= EMI_MPU_END_MASK;
+
+	if  ((region >= EMI_MPU_REGION_NUM) || (dgroup > EMI_MPU_DGROUP_NUM)) {
+		WARN("invalid region, domain\n");
+		return -1;
+	}
+
+#if ENABLE_EMI_MPU_SW_LOCK
+	if (region_lock_state[region] == 1) {
+		WARN("invalid region\n");
+		return -1;
+	}
+
+	if ((dgroup == 0) && ((apc >> 31) & 0x1)) {
+		region_lock_state[region] = 1;
+	}
+
+	apc &= EMI_MPU_APC_SW_LOCK_MASK;
+#else
+	apc &= EMI_MPU_APC_HW_LOCK_MASK;
+#endif
+
+	if ((start >= DRAM_OFFSET) && (end >= start)) {
+		start -= DRAM_OFFSET;
+		end -= DRAM_OFFSET;
+	} else {
+		WARN("invalid range\n");
+		return -1;
+	}
+
+	mmio_write_32(EMI_MPU_SA(region), start);
+	mmio_write_32(EMI_MPU_EA(region), end);
+	mmio_write_32(EMI_MPU_APC(region, dgroup), apc);
+
+#if defined(SUB_EMI_MPU_BASE)
+	mmio_write_32(SUB_EMI_MPU_SA(region), start);
+	mmio_write_32(SUB_EMI_MPU_EA(region), end);
+	mmio_write_32(SUB_EMI_MPU_APC(region, dgroup), apc);
+#endif
+	return 1;
+}
+
+int emi_mpu_set_protection(struct emi_region_info_t *region_info)
+{
+	unsigned int start, end;
+	int i;
+
+	if (region_info->region >= EMI_MPU_REGION_NUM) {
+		WARN("invalid region\n");
+		return -1;
+	}
+
+	start = (unsigned int)(region_info->start >> EMI_MPU_ALIGN_BITS) |
+		(region_info->region << 24);
+
+	for (i = EMI_MPU_DGROUP_NUM - 1; i >= 0; i--) {
+		end = (unsigned int)(region_info->end >> EMI_MPU_ALIGN_BITS) |
+			(i << 24);
+		_emi_mpu_set_protection(start, end, region_info->apc[i]);
+	}
+
+	return 0;
+}
+
+void emi_mpu_init(void)
+{
+	/* TODO: more setting for EMI MPU. */
+}
diff --git a/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.h b/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.h
new file mode 100644
index 0000000..415146e
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/emi_mpu/emi_mpu.h
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef EMI_MPU_H
+#define EMI_MPU_H
+
+#include <platform_def.h>
+
+#define ENABLE_EMI_MPU_SW_LOCK		1
+
+#define EMI_MPU_CTRL			(EMI_MPU_BASE + 0x000)
+#define EMI_MPU_DBG			(EMI_MPU_BASE + 0x004)
+#define EMI_MPU_SA0			(EMI_MPU_BASE + 0x100)
+#define EMI_MPU_EA0			(EMI_MPU_BASE + 0x200)
+#define EMI_MPU_SA(region)		(EMI_MPU_SA0 + (region * 4))
+#define EMI_MPU_EA(region)		(EMI_MPU_EA0 + (region * 4))
+#define EMI_MPU_APC0			(EMI_MPU_BASE + 0x300)
+#define EMI_MPU_APC(region, dgroup)	(EMI_MPU_APC0 + (region * 4) + (dgroup * 0x100))
+#define EMI_MPU_CTRL_D0			(EMI_MPU_BASE + 0x800)
+#define EMI_MPU_CTRL_D(domain)		(EMI_MPU_CTRL_D0 + (domain * 4))
+#define EMI_RG_MASK_D0			(EMI_MPU_BASE + 0x900)
+#define EMI_RG_MASK_D(domain)		(EMI_RG_MASK_D0 + (domain * 4))
+#define EMI_MPU_START			(0x000)
+#define EMI_MPU_END			(0x93C)
+
+#define SUB_EMI_MPU_CTRL		(SUB_EMI_MPU_BASE + 0x000)
+#define SUB_EMI_MPU_DBG			(SUB_EMI_MPU_BASE + 0x004)
+#define SUB_EMI_MPU_SA0			(SUB_EMI_MPU_BASE + 0x100)
+#define SUB_EMI_MPU_EA0			(SUB_EMI_MPU_BASE + 0x200)
+#define SUB_EMI_MPU_SA(region)		(SUB_EMI_MPU_SA0 + (region * 4))
+#define SUB_EMI_MPU_EA(region)		(SUB_EMI_MPU_EA0 + (region * 4))
+#define SUB_EMI_MPU_APC0		(SUB_EMI_MPU_BASE + 0x300)
+#define SUB_EMI_MPU_APC(region, dgroup)	(SUB_EMI_MPU_APC0 + (region * 4) + (dgroup * 0x100))
+#define SUB_EMI_MPU_CTRL_D0		(SUB_EMI_MPU_BASE + 0x800)
+#define SUB_EMI_MPU_CTRL_D(domain)	(SUB_EMI_MPU_CTRL_D0 + (domain * 4))
+#define SUB_EMI_RG_MASK_D0		(SUB_EMI_MPU_BASE + 0x900)
+#define SUB_EMI_RG_MASK_D(domain)	(SUB_EMI_RG_MASK_D0 + (domain * 4))
+
+#define EMI_MPU_DOMAIN_NUM		(16)
+#define EMI_MPU_REGION_NUM		(32)
+#define EMI_MPU_ALIGN_BITS		(16)
+#define DRAM_OFFSET			(0x40000000 >> EMI_MPU_ALIGN_BITS)
+
+#define NO_PROTECTION			0
+#define SEC_RW				1
+#define SEC_RW_NSEC_R			2
+#define SEC_RW_NSEC_W			3
+#define SEC_R_NSEC_R			4
+#define FORBIDDEN			5
+#define SEC_R_NSEC_RW			6
+
+#define LOCK				1
+#define UNLOCK				0
+
+#define EMI_MPU_DGROUP_NUM		(EMI_MPU_DOMAIN_NUM / 8)
+
+#if (EMI_MPU_DGROUP_NUM == 1)
+#define SET_ACCESS_PERMISSION(apc_ary, lock, d7, d6, d5, d4, d3, d2, d1, d0) \
+do { \
+	apc_ary[1] = 0; \
+	apc_ary[0] = \
+		(((unsigned int)  d7) << 21) | (((unsigned int)  d6) << 18) | \
+		(((unsigned int)  d5) << 15) | (((unsigned int)  d4) << 12) | \
+		(((unsigned int)  d3) <<  9) | (((unsigned int)  d2) <<  6) | \
+		(((unsigned int)  d1) <<  3) |  ((unsigned int)  d0) | \
+		((unsigned int) lock << 31); \
+} while (0)
+#elif (EMI_MPU_DGROUP_NUM == 2)
+#define SET_ACCESS_PERMISSION(apc_ary, lock, d15, d14, d13, d12, d11, d10, \
+				d9, d8, d7, d6, d5, d4, d3, d2, d1, d0) \
+do { \
+	apc_ary[1] = \
+		(((unsigned int) d15) << 21) | (((unsigned int) d14) << 18) | \
+		(((unsigned int) d13) << 15) | (((unsigned int) d12) << 12) | \
+		(((unsigned int) d11) <<  9) | (((unsigned int) d10) <<  6) | \
+		(((unsigned int)  d9) <<  3) |  ((unsigned int)  d8); \
+	apc_ary[0] = \
+		(((unsigned int)  d7) << 21) | (((unsigned int)  d6) << 18) | \
+		(((unsigned int)  d5) << 15) | (((unsigned int)  d4) << 12) | \
+		(((unsigned int)  d3) <<  9) | (((unsigned int)  d2) <<  6) | \
+		(((unsigned int)  d1) <<  3) |  ((unsigned int)  d0) | \
+		((unsigned int) lock << 31); \
+} while (0)
+#endif
+
+struct emi_region_info_t {
+	unsigned long long start;
+	unsigned long long end;
+	unsigned int region;
+	unsigned int apc[EMI_MPU_DGROUP_NUM];
+};
+
+void emi_mpu_init(void);
+
+#endif
diff --git a/plat/mediatek/mt8195/drivers/gpio/mtgpio.c b/plat/mediatek/mt8195/drivers/gpio/mtgpio.c
new file mode 100644
index 0000000..daab84c
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/gpio/mtgpio.c
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <mtgpio.h>
+#include <platform_def.h>
+
+uintptr_t mt_gpio_find_reg_addr(uint32_t pin)
+{
+	uintptr_t reg_addr = 0U;
+	struct mt_pin_info gpio_info;
+
+	assert(pin < MAX_GPIO_PIN);
+
+	gpio_info = mt_pin_infos[pin];
+
+	switch (gpio_info.base & 0x0f) {
+	case 0:
+		reg_addr = IOCFG_BM_BASE;
+		break;
+	case 1:
+		reg_addr = IOCFG_BL_BASE;
+		break;
+	case 2:
+		reg_addr = IOCFG_BR_BASE;
+		break;
+	case 3:
+		reg_addr = IOCFG_LM_BASE;
+		break;
+	case 4:
+		reg_addr = IOCFG_RB_BASE;
+		break;
+	case 5:
+		reg_addr = IOCFG_TL_BASE;
+		break;
+	default:
+		break;
+	}
+
+	return reg_addr;
+}
diff --git a/plat/mediatek/mt8195/drivers/gpio/mtgpio.h b/plat/mediatek/mt8195/drivers/gpio/mtgpio.h
new file mode 100644
index 0000000..88b4706
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/gpio/mtgpio.h
@@ -0,0 +1,183 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_GPIO_H
+#define MT_GPIO_H
+
+#include <mtgpio_common.h>
+
+/* Enumeration for GPIO pin */
+typedef enum GPIO_PIN {
+	GPIO_UNSUPPORTED = -1,
+
+	GPIO0, GPIO1, GPIO2, GPIO3, GPIO4, GPIO5, GPIO6, GPIO7,
+	GPIO8, GPIO9, GPIO10, GPIO11, GPIO12, GPIO13, GPIO14, GPIO15,
+	GPIO16, GPIO17, GPIO18, GPIO19, GPIO20, GPIO21, GPIO22, GPIO23,
+	GPIO24, GPIO25, GPIO26, GPIO27, GPIO28, GPIO29, GPIO30, GPIO31,
+	GPIO32, GPIO33, GPIO34, GPIO35, GPIO36, GPIO37, GPIO38, GPIO39,
+	GPIO40, GPIO41, GPIO42, GPIO43, GPIO44, GPIO45, GPIO46, GPIO47,
+	GPIO48, GPIO49, GPIO50, GPIO51, GPIO52, GPIO53, GPIO54, GPIO55,
+	GPIO56, GPIO57, GPIO58, GPIO59, GPIO60, GPIO61, GPIO62, GPIO63,
+	GPIO64, GPIO65, GPIO66, GPIO67, GPIO68, GPIO69, GPIO70, GPIO71,
+	GPIO72, GPIO73, GPIO74, GPIO75, GPIO76, GPIO77, GPIO78, GPIO79,
+	GPIO80, GPIO81, GPIO82, GPIO83, GPIO84, GPIO85, GPIO86, GPIO87,
+	GPIO88, GPIO89, GPIO90, GPIO91, GPIO92, GPIO93, GPIO94, GPIO95,
+	GPIO96, GPIO97, GPIO98, GPIO99, GPIO100, GPIO101, GPIO102, GPIO103,
+	GPIO104, GPIO105, GPIO106, GPIO107, GPIO108, GPIO109, GPIO110, GPIO111,
+	GPIO112, GPIO113, GPIO114, GPIO115, GPIO116, GPIO117, GPIO118, GPIO119,
+	GPIO120, GPIO121, GPIO122, GPIO123, GPIO124, GPIO125, GPIO126, GPIO127,
+	GPIO128, GPIO129, GPIO130, GPIO131, GPIO132, GPIO133, GPIO134, GPIO135,
+	GPIO136, GPIO137, GPIO138, GPIO139, GPIO140, GPIO141, GPIO142, GPIO143,
+	MT_GPIO_BASE_MAX
+} GPIO_PIN;
+
+static const struct mt_pin_info mt_pin_infos[] = {
+	PIN(0, 1, 0, 0x23, 0x60),
+	PIN(1, 1, 1, 0x23, 0x60),
+	PIN(2, 1, 2, 0x23, 0x60),
+	PIN(3, 1, 3, 0x23, 0x60),
+	PIN(4, 1, 4, 0x23, 0x60),
+	PIN(5, 1, 5, 0x23, 0x60),
+	PIN(6, 0, 6, 0x23, 0x70),
+	PIN(7, 0, 7, 0x23, 0x70),
+	PIN(8, 0, 13, 0x23, 0x70),
+	PIN(9, 0, 8, 0x23, 0x70),
+	PIN(10, 0, 14, 0x23, 0x70),
+	PIN(11, 0, 9, 0x23, 0x70),
+	PIN(12, 0, 15, 0x23, 0x70),
+	PIN(13, 0, 10, 0x23, 0x70),
+	PIN(14, 0, 16, 0x23, 0x70),
+	PIN(15, 0, 11, 0x23, 0x70),
+	PIN(16, 0, 17, 0x23, 0x70),
+	PIN(17, 0, 12, 0x23, 0x70),
+	PIN(18, 0, 5, 0x10, 0x60),
+	PIN(19, 0, 12, 0x10, 0x60),
+	PIN(20, 0, 11, 0x10, 0x60),
+	PIN(21, 0, 10, 0x10, 0x60),
+	PIN(22, 0, 0, 0x10, 0x60),
+	PIN(23, 0, 1, 0x10, 0x60),
+	PIN(24, 0, 2, 0x10, 0x60),
+	PIN(25, 0, 4, 0x10, 0x60),
+	PIN(26, 0, 3, 0x10, 0x60),
+	PIN(27, 0, 6, 0x10, 0x60),
+	PIN(28, 0, 7, 0x10, 0x60),
+	PIN(29, 0, 8, 0x10, 0x60),
+	PIN(30, 0, 9, 0x10, 0x60),
+	PIN(31, 0, 13, 0x21, 0xa0),
+	PIN(32, 0, 12, 0x21, 0xa0),
+	PIN(33, 0, 11, 0x21, 0xa0),
+	PIN(34, 0, 14, 0x21, 0xa0),
+	PIN(35, 0, 15, 0x21, 0xa0),
+	PIN(36, 0, 3, 0x21, 0xb0),
+	PIN(37, 0, 6, 0x21, 0xb0),
+	PIN(38, 0, 4, 0x21, 0xb0),
+	PIN(39, 0, 5, 0x21, 0xb0),
+	PIN(40, 0, 8, 0x21, 0xb0),
+	PIN(41, 0, 7, 0x21, 0xb0),
+	PIN(42, 0, 10, 0x21, 0xb0),
+	PIN(43, 0, 9, 0x21, 0xb0),
+	PIN(44, 0, 20, 0x21, 0xb0),
+	PIN(45, 0, 21, 0x21, 0xb0),
+	PIN(46, 0, 18, 0x21, 0xa0),
+	PIN(47, 0, 16, 0x21, 0xa0),
+	PIN(48, 0, 19, 0x21, 0xa0),
+	PIN(49, 0, 17, 0x21, 0xa0),
+	PIN(50, 0, 25, 0x21, 0xa0),
+	PIN(51, 0, 20, 0x21, 0xa0),
+	PIN(52, 0, 26, 0x21, 0xa0),
+	PIN(53, 0, 21, 0x21, 0xa0),
+	PIN(54, 0, 22, 0x21, 0xa0),
+	PIN(55, 0, 23, 0x21, 0xa0),
+	PIN(56, 0, 24, 0x21, 0xa0),
+	PIN(57, 0, 29, 0x21, 0xa0),
+	PIN(58, 0, 27, 0x21, 0xa0),
+	PIN(59, 0, 30, 0x21, 0xa0),
+	PIN(60, 0, 28, 0x21, 0xa0),
+	PIN(61, 0, 8, 0x21, 0xa0),
+	PIN(62, 0, 7, 0x21, 0xa0),
+	PIN(63, 0, 10, 0x21, 0xa0),
+	PIN(64, 0, 9, 0x21, 0xa0),
+	PIN(65, 0, 1, 0x21, 0xb0),
+	PIN(66, 0, 31, 0x21, 0xa0),
+	PIN(67, 0, 0, 0x21, 0xb0),
+	PIN(68, 0, 2, 0x21, 0xb0),
+	PIN(69, 0, 0, 0x21, 0xa0),
+	PIN(70, 0, 6, 0x21, 0xa0),
+	PIN(71, 0, 4, 0x21, 0xa0),
+	PIN(72, 0, 5, 0x21, 0xa0),
+	PIN(73, 0, 1, 0x21, 0xa0),
+	PIN(74, 0, 2, 0x21, 0xa0),
+	PIN(75, 0, 3, 0x21, 0xa0),
+	PIN(76, 0, 11, 0x21, 0xb0),
+	PIN(77, 1, 1, 0x22, 0x60),
+	PIN(78, 1, 2, 0x22, 0x60),
+	PIN(79, 1, 9, 0x22, 0x60),
+	PIN(80, 1, 10, 0x22, 0x60),
+	PIN(81, 1, 11, 0x22, 0x60),
+	PIN(82, 1, 12, 0x22, 0x60),
+	PIN(83, 1, 13, 0x22, 0x60),
+	PIN(84, 1, 14, 0x22, 0x60),
+	PIN(85, 1, 15, 0x22, 0x60),
+	PIN(86, 1, 16, 0x22, 0x60),
+	PIN(87, 1, 3, 0x22, 0x60),
+	PIN(88, 1, 4, 0x22, 0x60),
+	PIN(89, 1, 5, 0x22, 0x60),
+	PIN(90, 1, 6, 0x22, 0x60),
+	PIN(91, 1, 7, 0x22, 0x60),
+	PIN(92, 1, 8, 0x22, 0x60),
+	PIN(93, 1, 18, 0x22, 0x60),
+	PIN(94, 1, 19, 0x22, 0x60),
+	PIN(95, 1, 17, 0x22, 0x60),
+	PIN(96, 1, 0, 0x22, 0x60),
+	PIN(97, 0, 20, 0x22, 0x70),
+	PIN(98, 0, 28, 0x22, 0x70),
+	PIN(99, 0, 27, 0x22, 0x70),
+	PIN(100, 0, 30, 0x22, 0x70),
+	PIN(101, 0, 29, 0x22, 0x70),
+	PIN(102, 0, 0, 0x22, 0x70),
+	PIN(103, 0, 31, 0x22, 0x70),
+	PIN(104, 1, 25, 0x22, 0x60),
+	PIN(105, 1, 26, 0x22, 0x60),
+	PIN(106, 1, 23, 0x22, 0x60),
+	PIN(107, 1, 24, 0x22, 0x60),
+	PIN(108, 0, 22, 0x22, 0x70),
+	PIN(109, 0, 21, 0x22, 0x70),
+	PIN(110, 1, 1, 0x14, 0x20),
+	PIN(111, 1, 0, 0x14, 0x20),
+	PIN(112, 1, 2, 0x14, 0x20),
+	PIN(113, 1, 3, 0x14, 0x20),
+	PIN(114, 1, 4, 0x14, 0x20),
+	PIN(115, 1, 5, 0x14, 0x20),
+	PIN(116, 1, 9, 0x25, 0x50),
+	PIN(117, 1, 8, 0x25, 0x50),
+	PIN(118, 1, 7, 0x25, 0x50),
+	PIN(119, 1, 6, 0x25, 0x50),
+	PIN(120, 1, 11, 0x25, 0x50),
+	PIN(121, 1, 1, 0x25, 0x50),
+	PIN(122, 1, 0, 0x25, 0x50),
+	PIN(123, 1, 5, 0x25, 0x50),
+	PIN(124, 1, 4, 0x25, 0x50),
+	PIN(125, 1, 3, 0x25, 0x50),
+	PIN(126, 1, 2, 0x25, 0x50),
+	PIN(127, 1, 10, 0x25, 0x50),
+	PIN(128, 0, 3, 0x22, 0x70),
+	PIN(129, 0, 1, 0x22, 0x70),
+	PIN(130, 0, 4, 0x22, 0x70),
+	PIN(131, 0, 2, 0x22, 0x70),
+	PIN(132, 0, 13, 0x25, 0x60),
+	PIN(133, 0, 12, 0x25, 0x60),
+	PIN(134, 0, 15, 0x25, 0x60),
+	PIN(135, 0, 14, 0x25, 0x60),
+	PIN(136, 0, 13, 0x21, 0xb0),
+	PIN(137, 0, 12, 0x21, 0xb0),
+	PIN(138, 0, 15, 0x21, 0xb0),
+	PIN(139, 0, 14, 0x21, 0xb0),
+	PIN(140, 0, 17, 0x21, 0xb0),
+	PIN(141, 0, 16, 0x21, 0xb0),
+	PIN(142, 0, 19, 0x21, 0xb0),
+	PIN(143, 0, 18, 0x21, 0xb0),
+};
+#endif /* MT_GPIO_H */
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm.c b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm.c
new file mode 100644
index 0000000..5a80d95
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm.c
@@ -0,0 +1,150 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <lib/psci/psci.h>
+#include <lib/spinlock.h>
+
+#include <mt_cpu_pm_cpc.h>
+#include <mt_lp_irqremain.h>
+#include <mt_lp_rm.h>
+#include <mt_mcdi.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+
+DEFINE_SYSREG_RW_FUNCS(dbgprcr_el1);
+
+static int plat_mt_lp_cpu_rc;
+
+static int pwr_state_prompt(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_state_reflect(unsigned int cpu, const psci_power_state_t *state)
+{
+	mtk_cpc_core_on_hint_clr(cpu);
+
+	if (IS_SYSTEM_SUSPEND_STATE(state)) {
+		mtk_cpc_time_sync();
+	}
+
+	return 0;
+}
+
+static int pwr_cpu_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_cpu_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	/* clear DBGPRCR.CORENPDRQ to allow CPU power down  */
+	write_dbgprcr_el1(0ULL);
+
+	return 0;
+}
+
+static int pwr_cluster_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_cluster_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	return 0;
+}
+
+static int pwr_mcusys_pwron(unsigned int cpu, const psci_power_state_t *state)
+{
+	if (!IS_MCUSYS_OFF_STATE(state) || (plat_mt_lp_cpu_rc < 0)) {
+		return -1;
+	}
+
+	mtk_cpc_mcusys_off_reflect();
+
+	return 0;
+}
+
+static int pwr_mcusys_pwron_finished(unsigned int cpu,
+					const psci_power_state_t *state)
+{
+	int state_id = state->pwr_domain_state[MTK_AFFLVL_MCUSYS];
+
+	if (!IS_MCUSYS_OFF_STATE(state) || (plat_mt_lp_cpu_rc < 0)) {
+		return -1;
+	}
+
+	mt_lp_rm_reset_constraint(plat_mt_lp_cpu_rc, cpu, state_id);
+	mt_lp_irqremain_release();
+
+	return 0;
+}
+
+static int pwr_mcusys_pwrdwn(unsigned int cpu, const psci_power_state_t *state)
+{
+	int state_id = state->pwr_domain_state[MTK_AFFLVL_MCUSYS];
+
+	if (!IS_MCUSYS_OFF_STATE(state)) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	if (mcdi_try_init() != 0) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	if (mtk_cpc_mcusys_off_prepare() != CPC_SUCCESS) {
+		goto mt_pwr_mcusysoff_break;
+	}
+
+	plat_mt_lp_cpu_rc =
+		mt_lp_rm_find_and_run_constraint(0, cpu, state_id, NULL);
+
+	if (plat_mt_lp_cpu_rc < 0) {
+		goto mt_pwr_mcusysoff_reflect;
+	}
+
+	mt_lp_irqremain_aquire();
+
+	return 0;
+
+mt_pwr_mcusysoff_reflect:
+	mtk_cpc_mcusys_off_reflect();
+
+mt_pwr_mcusysoff_break:
+
+	plat_mt_lp_cpu_rc = -1;
+
+	return -1;
+}
+
+static const struct mt_lpm_tz plat_pm = {
+	.pwr_prompt			= pwr_state_prompt,
+	.pwr_reflect			= pwr_state_reflect,
+	.pwr_cpu_on			= pwr_cpu_pwron,
+	.pwr_cpu_dwn			= pwr_cpu_pwrdwn,
+	.pwr_cluster_on			= pwr_cluster_pwron,
+	.pwr_cluster_dwn		= pwr_cluster_pwrdwn,
+	.pwr_mcusys_dwn			= pwr_mcusys_pwrdwn,
+	.pwr_mcusys_on			= pwr_mcusys_pwron,
+	.pwr_mcusys_on_finished		= pwr_mcusys_pwron_finished
+};
+
+const struct mt_lpm_tz *mt_plat_cpu_pm_init(void)
+{
+	mtk_cpc_init();
+
+	if (mcdi_try_init() == 0) {
+		INFO("MCDI init done.\n");
+	}
+
+	mt_lp_irqremain_init();
+
+	return &plat_pm;
+}
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.c b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.c
new file mode 100644
index 0000000..f8c51a1
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.c
@@ -0,0 +1,269 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <drivers/delay_timer.h>
+
+#include <mt_cpu_pm_cpc.h>
+#include <mt_timer.h>
+
+struct mtk_cpc_dev {
+	int auto_off;
+	unsigned int auto_thres_tick;
+};
+
+static struct mtk_cpc_dev cpc;
+
+static int mtk_cpc_last_core_prot(uint32_t prot_req,
+				uint32_t resp_reg, uint32_t resp_ofs)
+{
+	uint32_t sta, retry;
+
+	retry = 0U;
+
+	while (retry++ < RETRY_CNT_MAX) {
+
+		mmio_write_32(CPC_MCUSYS_LAST_CORE_REQ, prot_req);
+
+		udelay(1U);
+
+		sta = (mmio_read_32(resp_reg) >> resp_ofs) & CPC_PROT_RESP_MASK;
+
+		if (sta == PROT_SUCCESS) {
+			return CPC_SUCCESS;
+		} else if (sta == PROT_GIVEUP) {
+			return CPC_ERR_FAIL;
+		}
+	}
+
+	return CPC_ERR_TIMEOUT;
+}
+
+int mtk_cpu_pm_mcusys_prot_aquire(void)
+{
+	return mtk_cpc_last_core_prot(
+			MCUSYS_PROT_SET,
+			CPC_MCUSYS_LAST_CORE_RESP,
+			MCUSYS_RESP_OFS);
+}
+
+void mtk_cpu_pm_mcusys_prot_release(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_ON_MASK, MCUSYS_PROT_CLR);
+}
+
+int mtk_cpu_pm_cluster_prot_aquire(unsigned int cluster)
+{
+	return mtk_cpc_last_core_prot(
+			CPUSYS_PROT_SET,
+			CPC_MCUSYS_MP_LAST_CORE_RESP,
+			CPUSYS_RESP_OFS);
+}
+
+void mtk_cpu_pm_cluster_prot_release(unsigned int cluster)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_ON_MASK, CPUSYS_PROT_CLR);
+}
+
+static void mtk_cpc_cluster_cnt_backup(void)
+{
+	uint32_t backup_cnt;
+	uint32_t curr_cnt;
+	uint32_t cnt_mask = GENMASK(14, 0);
+	uint32_t clr_mask = GENMASK(1, 0);
+
+	/* Single Cluster */
+	backup_cnt = mmio_read_32(CPC_CLUSTER_CNT_BACKUP);
+	curr_cnt = mmio_read_32(CPC_MCUSYS_CLUSTER_COUNTER);
+
+	/* Get off count if dormant count is 0 */
+	if ((curr_cnt & cnt_mask) == 0U) {
+		curr_cnt = (curr_cnt >> 16) & cnt_mask;
+	} else {
+		curr_cnt = curr_cnt & cnt_mask;
+	}
+
+	mmio_write_32(CPC_CLUSTER_CNT_BACKUP, backup_cnt + curr_cnt);
+	mmio_write_32(CPC_MCUSYS_CLUSTER_COUNTER_CLR, clr_mask);
+}
+
+static inline void mtk_cpc_mcusys_off_en(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_CTRL, 1U);
+}
+
+static inline void mtk_cpc_mcusys_off_dis(void)
+{
+	mmio_write_32(CPC_MCUSYS_PWR_CTRL, 0U);
+}
+
+void mtk_cpc_mcusys_off_reflect(void)
+{
+	mtk_cpc_mcusys_off_dis();
+	mtk_cpu_pm_mcusys_prot_release();
+}
+
+int mtk_cpc_mcusys_off_prepare(void)
+{
+	if (mtk_cpu_pm_mcusys_prot_aquire() != CPC_SUCCESS) {
+		return CPC_ERR_FAIL;
+	}
+
+	mtk_cpc_cluster_cnt_backup();
+	mtk_cpc_mcusys_off_en();
+
+	return CPC_SUCCESS;
+}
+
+void mtk_cpc_core_on_hint_set(unsigned int cpu)
+{
+	mmio_write_32(CPC_MCUSYS_CPU_ON_SW_HINT_SET, BIT(cpu));
+}
+
+void mtk_cpc_core_on_hint_clr(unsigned int cpu)
+{
+	mmio_write_32(CPC_MCUSYS_CPU_ON_SW_HINT_CLR, BIT(cpu));
+}
+
+static void mtk_cpc_dump_timestamp(void)
+{
+	uint32_t id;
+
+	for (id = 0U; id < CPC_TRACE_ID_NUM; id++) {
+		mmio_write_32(CPC_MCUSYS_TRACE_SEL, id);
+
+		memcpy((void *)(uintptr_t)CPC_TRACE_SRAM(id),
+				(const void *)(uintptr_t)CPC_MCUSYS_TRACE_DATA,
+				CPC_TRACE_SIZE);
+	}
+}
+
+void mtk_cpc_time_sync(void)
+{
+	uint64_t kt;
+	uint32_t systime_l, systime_h;
+
+	kt = sched_clock();
+	systime_l = mmio_read_32(CNTSYS_L_REG);
+	systime_h = mmio_read_32(CNTSYS_H_REG);
+
+	/* sync kernel timer to cpc */
+	mmio_write_32(CPC_MCUSYS_CPC_KERNEL_TIME_L_BASE, (uint32_t)kt);
+	mmio_write_32(CPC_MCUSYS_CPC_KERNEL_TIME_H_BASE, (uint32_t)(kt >> 32));
+	/* sync system timer to cpc */
+	mmio_write_32(CPC_MCUSYS_CPC_SYSTEM_TIME_L_BASE, systime_l);
+	mmio_write_32(CPC_MCUSYS_CPC_SYSTEM_TIME_H_BASE, systime_h);
+}
+
+static void mtk_cpc_config(uint32_t cfg, uint32_t data)
+{
+	uint32_t val;
+	uint32_t reg = 0U;
+
+	switch (cfg) {
+	case CPC_SMC_CONFIG_PROF:
+		reg = CPC_MCUSYS_CPC_DBG_SETTING;
+		val = mmio_read_32(reg);
+		val = (data != 0U) ? (val | CPC_PROF_EN) : (val & ~CPC_PROF_EN);
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF:
+		reg = CPC_MCUSYS_CPC_FLOW_CTRL_CFG;
+		val = mmio_read_32(reg);
+		if (data != 0U) {
+			val |= CPC_AUTO_OFF_EN;
+			cpc.auto_off = 1;
+		} else {
+			val &= ~CPC_AUTO_OFF_EN;
+			cpc.auto_off = 0;
+		}
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF_THRES:
+		reg = CPC_MCUSYS_CPC_OFF_THRES;
+		cpc.auto_thres_tick = us_to_ticks(data);
+		val = cpc.auto_thres_tick;
+		break;
+	case CPC_SMC_CONFIG_CNT_CLR:
+		reg = CPC_MCUSYS_CLUSTER_COUNTER_CLR;
+		val = GENMASK(1, 0);	/* clr_mask */
+		break;
+	case CPC_SMC_CONFIG_TIME_SYNC:
+		mtk_cpc_time_sync();
+		break;
+	default:
+		break;
+	}
+
+	if (reg != 0U) {
+		mmio_write_32(reg, val);
+	}
+}
+
+static uint32_t mtk_cpc_read_config(uint32_t cfg)
+{
+	uint32_t res = 0U;
+
+	switch (cfg) {
+	case CPC_SMC_CONFIG_PROF:
+		res = (mmio_read_32(CPC_MCUSYS_CPC_DBG_SETTING) & CPC_PROF_EN) ?
+			1U : 0U;
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF:
+		res = cpc.auto_off;
+		break;
+	case CPC_SMC_CONFIG_AUTO_OFF_THRES:
+		res = ticks_to_us(cpc.auto_thres_tick);
+		break;
+	case CPC_SMC_CONFIG_CNT_CLR:
+		break;
+	default:
+		break;
+	}
+
+	return res;
+}
+
+uint64_t mtk_cpc_handler(uint64_t act, uint64_t arg1, uint64_t arg2)
+{
+	uint64_t res = 0ULL;
+
+	switch (act) {
+	case CPC_SMC_EVENT_DUMP_TRACE_DATA:
+		mtk_cpc_dump_timestamp();
+		break;
+	case CPC_SMC_EVENT_GIC_DPG_SET:
+		/* isolated_status = x2; */
+		break;
+	case CPC_SMC_EVENT_CPC_CONFIG:
+		mtk_cpc_config((uint32_t)arg1, (uint32_t)arg2);
+		break;
+	case CPC_SMC_EVENT_READ_CONFIG:
+		res = mtk_cpc_read_config((uint32_t)arg1);
+		break;
+	default:
+		break;
+	}
+
+	return res;
+}
+
+void mtk_cpc_init(void)
+{
+	mmio_write_32(CPC_MCUSYS_CPC_DBG_SETTING,
+			mmio_read_32(CPC_MCUSYS_CPC_DBG_SETTING)
+			| CPC_DBG_EN
+			| CPC_CALC_EN);
+
+	cpc.auto_off = 1;
+	cpc.auto_thres_tick = us_to_ticks(8000);
+
+	mmio_write_32(CPC_MCUSYS_CPC_FLOW_CTRL_CFG,
+			mmio_read_32(CPC_MCUSYS_CPC_FLOW_CTRL_CFG)
+			| CPC_OFF_PRE_EN
+			| (cpc.auto_off ? CPC_AUTO_OFF_EN : 0U));
+
+	mmio_write_32(CPC_MCUSYS_CPC_OFF_THRES, cpc.auto_thres_tick);
+}
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.h b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.h
new file mode 100644
index 0000000..19dd6a2
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_cpu_pm_cpc.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_CPU_PM_CPC_H
+#define MT_CPU_PM_CPC_H
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mcucfg.h>
+#include <platform_def.h>
+
+#define NEED_CPUSYS_PROT_WORKAROUND	1
+
+/* system sram registers */
+#define CPUIDLE_SRAM_REG(r)	(uint32_t)(MTK_MCDI_SRAM_BASE + (r))
+
+/* db dump */
+#define CPC_TRACE_SIZE		U(0x20)
+#define CPC_TRACE_ID_NUM	U(10)
+#define CPC_TRACE_SRAM(id)	(CPUIDLE_SRAM_REG(0x10) + (id) * CPC_TRACE_SIZE)
+
+/* buckup off count */
+#define CPC_CLUSTER_CNT_BACKUP	CPUIDLE_SRAM_REG(0x1F0)
+#define CPC_MCUSYS_CNT		CPUIDLE_SRAM_REG(0x1F4)
+
+/* CPC_MCUSYS_CPC_FLOW_CTRL_CFG(0xA814): debug setting */
+#define CPC_PWR_ON_SEQ_DIS	BIT(1)
+#define CPC_PWR_ON_PRIORITY	BIT(2)
+#define CPC_AUTO_OFF_EN		BIT(5)
+#define CPC_DORMANT_WAIT_EN	BIT(14)
+#define CPC_CTRL_EN		BIT(16)
+#define CPC_OFF_PRE_EN		BIT(29)
+
+/* CPC_MCUSYS_LAST_CORE_REQ(0xA818) : last core protection */
+#define CPUSYS_PROT_SET		BIT(0)
+#define MCUSYS_PROT_SET		BIT(8)
+#define CPUSYS_PROT_CLR		BIT(8)
+#define MCUSYS_PROT_CLR		BIT(9)
+
+#define CPC_PROT_RESP_MASK	U(0x3)
+#define CPUSYS_RESP_OFS		U(16)
+#define MCUSYS_RESP_OFS		U(30)
+
+#define cpusys_resp(r)		(((r) >> CPUSYS_RESP_OFS) & CPC_PROT_RESP_MASK)
+#define mcusys_resp(r)		(((r) >> MCUSYS_RESP_OFS) & CPC_PROT_RESP_MASK)
+
+#define RETRY_CNT_MAX		U(1000)
+
+#define PROT_RETRY		U(0)
+#define PROT_SUCCESS		U(1)
+#define PROT_GIVEUP		U(2)
+
+/* CPC_MCUSYS_CPC_DBG_SETTING(0xAB00): debug setting */
+#define CPC_PROF_EN		BIT(0)
+#define CPC_DBG_EN		BIT(1)
+#define CPC_FREEZE		BIT(2)
+#define CPC_CALC_EN		BIT(3)
+
+enum {
+	CPC_SUCCESS = 0,
+
+	CPC_ERR_FAIL,
+	CPC_ERR_TIMEOUT,
+
+	NF_CPC_ERR
+};
+
+enum {
+	CPC_SMC_EVENT_DUMP_TRACE_DATA,
+	CPC_SMC_EVENT_GIC_DPG_SET,
+	CPC_SMC_EVENT_CPC_CONFIG,
+	CPC_SMC_EVENT_READ_CONFIG,
+
+	NF_CPC_SMC_EVENT
+};
+
+enum {
+	CPC_SMC_CONFIG_PROF,
+	CPC_SMC_CONFIG_AUTO_OFF,
+	CPC_SMC_CONFIG_AUTO_OFF_THRES,
+	CPC_SMC_CONFIG_CNT_CLR,
+	CPC_SMC_CONFIG_TIME_SYNC,
+
+	NF_CPC_SMC_CONFIG
+};
+
+#define us_to_ticks(us)		((us) * 13)
+#define ticks_to_us(tick)	((tick) / 13)
+
+int mtk_cpu_pm_cluster_prot_aquire(unsigned int cluster);
+void mtk_cpu_pm_cluster_prot_release(unsigned int cluster);
+
+void mtk_cpc_mcusys_off_reflect(void);
+int mtk_cpc_mcusys_off_prepare(void);
+
+void mtk_cpc_core_on_hint_set(unsigned int cpu);
+void mtk_cpc_core_on_hint_clr(unsigned int cpu);
+void mtk_cpc_time_sync(void);
+
+uint64_t mtk_cpc_handler(uint64_t act, uint64_t arg1, uint64_t arg2);
+void mtk_cpc_init(void);
+
+#endif /* MT_CPU_PM_CPC_H */
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.c b/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.c
new file mode 100644
index 0000000..4147184
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.c
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <mt_lp_rm.h>
+#include <mt_lp_irqremain.h>
+#include <mtk_cirq.h>
+#include <plat_mtk_lpm.h>
+
+
+#define KEYPAD_IRQ_ID		U(138)
+
+#define KEYPAD_WAKESRC		0x4
+
+static struct mt_irqremain remain_irqs;
+
+int mt_lp_irqremain_submit(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	set_wakeup_sources(remain_irqs.irqs, remain_irqs.count);
+	mt_lp_rm_do_update(-1, PLAT_RC_UPDATE_REMAIN_IRQS, &remain_irqs);
+
+	return 0;
+}
+
+int mt_lp_irqremain_aquire(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	mt_cirq_sw_reset();
+	mt_cirq_clone_gic();
+	mt_cirq_enable();
+
+	return 0;
+}
+
+int mt_lp_irqremain_release(void)
+{
+	if (remain_irqs.count == 0) {
+		return -1;
+	}
+
+	mt_cirq_flush();
+	mt_cirq_disable();
+
+	return 0;
+}
+
+void mt_lp_irqremain_init(void)
+{
+	uint32_t idx;
+
+	remain_irqs.count = 0;
+
+	/*edge keypad*/
+	idx = remain_irqs.count;
+	remain_irqs.irqs[idx] = KEYPAD_IRQ_ID;
+	remain_irqs.wakeupsrc_cat[idx] = 0;
+	remain_irqs.wakeupsrc[idx] = KEYPAD_WAKESRC;
+	remain_irqs.count++;
+
+	mt_lp_irqremain_submit();
+}
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.h b/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.h
new file mode 100644
index 0000000..b86e17e
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_lp_irqremain.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_LP_IRQREMAIN_H
+#define MT_LP_IRQREMAIN_H
+
+extern int mt_lp_irqremain_submit(void);
+extern int mt_lp_irqremain_aquire(void);
+extern int mt_lp_irqremain_release(void);
+extern void mt_lp_irqremain_init(void);
+#endif /* MT_LP_IRQREMAIN_H */
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.c b/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.c
new file mode 100644
index 0000000..c14e83b
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.c
@@ -0,0 +1,151 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <cdefs.h>
+#include <common/debug.h>
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+#include <mt_mcdi.h>
+
+/* Read/Write */
+#define APMCU_MCUPM_MBOX_AP_READY	U(0)
+#define APMCU_MCUPM_MBOX_RESERVED_1	U(1)
+#define APMCU_MCUPM_MBOX_RESERVED_2	U(2)
+#define APMCU_MCUPM_MBOX_RESERVED_3	U(3)
+#define APMCU_MCUPM_MBOX_PWR_CTRL_EN	U(4)
+#define APMCU_MCUPM_MBOX_L3_CACHE_MODE	U(5)
+#define APMCU_MCUPM_MBOX_BUCK_MODE	U(6)
+#define APMCU_MCUPM_MBOX_ARMPLL_MODE	U(7)
+/* Read only */
+#define APMCU_MCUPM_MBOX_TASK_STA	U(8)
+#define APMCU_MCUPM_MBOX_RESERVED_9	U(9)
+#define APMCU_MCUPM_MBOX_RESERVED_10	U(10)
+#define APMCU_MCUPM_MBOX_RESERVED_11	U(11)
+
+/* CPC mode - Read/Write */
+#define APMCU_MCUPM_MBOX_WAKEUP_CPU	U(12)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_PWR_CTRL_EN */
+#define MCUPM_MCUSYS_CTRL		BIT(0)
+#define MCUPM_BUCK_CTRL			BIT(1)
+#define MCUPM_ARMPLL_CTRL		BIT(2)
+#define MCUPM_CM_CTRL			BIT(3)
+#define MCUPM_PWR_CTRL_MASK		GENMASK(3, 0)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_BUCK_MODE */
+#define MCUPM_BUCK_NORMAL_MODE		U(0) /* default */
+#define MCUPM_BUCK_LP_MODE		U(1)
+#define MCUPM_BUCK_OFF_MODE		U(2)
+#define NF_MCUPM_BUCK_MODE		U(3)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_ARMPLL_MODE */
+#define MCUPM_ARMPLL_ON			U(0) /* default */
+#define MCUPM_ARMPLL_GATING		U(1)
+#define MCUPM_ARMPLL_OFF		U(2)
+#define NF_MCUPM_ARMPLL_MODE		U(3)
+
+/* Mbox Slot: APMCU_MCUPM_MBOX_TASK_STA */
+#define MCUPM_TASK_UNINIT		U(0)
+#define MCUPM_TASK_INIT			U(1)
+#define MCUPM_TASK_INIT_FINISH		U(2)
+#define MCUPM_TASK_WAIT			U(3)
+#define MCUPM_TASK_RUN			U(4)
+#define MCUPM_TASK_PAUSE		U(5)
+
+#define SSPM_MBOX_3_BASE		U(0x0c55fce0)
+
+#define MCDI_NOT_INIT			0
+#define MCDI_INIT_1			1
+#define MCDI_INIT_2			2
+#define MCDI_INIT_DONE			3
+
+static int mcdi_init_status __section("tzfw_coherent_mem");
+
+static inline uint32_t mcdi_mbox_read(uint32_t id)
+{
+	return mmio_read_32(SSPM_MBOX_3_BASE + (id << 2));
+}
+
+static inline void mcdi_mbox_write(uint32_t id, uint32_t val)
+{
+	mmio_write_32(SSPM_MBOX_3_BASE + (id << 2), val);
+}
+
+static void mtk_mcupm_pwr_ctrl_setting(uint32_t dev)
+{
+	mcdi_mbox_write(APMCU_MCUPM_MBOX_PWR_CTRL_EN, dev);
+}
+
+static void mtk_set_mcupm_pll_mode(uint32_t mode)
+{
+	if (mode < NF_MCUPM_ARMPLL_MODE) {
+		mcdi_mbox_write(APMCU_MCUPM_MBOX_ARMPLL_MODE, mode);
+	}
+}
+
+static void mtk_set_mcupm_buck_mode(uint32_t mode)
+{
+	if (mode < NF_MCUPM_BUCK_MODE) {
+		mcdi_mbox_write(APMCU_MCUPM_MBOX_BUCK_MODE, mode);
+	}
+}
+
+static int mtk_mcupm_is_ready(void)
+{
+	unsigned int sta = mcdi_mbox_read(APMCU_MCUPM_MBOX_TASK_STA);
+
+	return (sta == MCUPM_TASK_WAIT) || (sta == MCUPM_TASK_INIT_FINISH);
+}
+
+static int mcdi_init_1(void)
+{
+	unsigned int sta = mcdi_mbox_read(APMCU_MCUPM_MBOX_TASK_STA);
+
+	if (sta != MCUPM_TASK_INIT) {
+		return -1;
+	}
+
+	mtk_set_mcupm_pll_mode(MCUPM_ARMPLL_OFF);
+	mtk_set_mcupm_buck_mode(MCUPM_BUCK_OFF_MODE);
+
+	mtk_mcupm_pwr_ctrl_setting(
+			 MCUPM_MCUSYS_CTRL |
+			 MCUPM_BUCK_CTRL |
+			 MCUPM_ARMPLL_CTRL);
+
+	mcdi_mbox_write(APMCU_MCUPM_MBOX_AP_READY, 1);
+
+	return 0;
+}
+
+static int mcdi_init_2(void)
+{
+	return mtk_mcupm_is_ready() ? 0 : -1;
+}
+
+int mcdi_try_init(void)
+{
+	if (mcdi_init_status == MCDI_INIT_DONE) {
+		return 0;
+	}
+
+	if (mcdi_init_status == MCDI_NOT_INIT) {
+		mcdi_init_status = MCDI_INIT_1;
+	}
+
+	if (mcdi_init_status == MCDI_INIT_1 && mcdi_init_1() == 0) {
+		mcdi_init_status = MCDI_INIT_2;
+	}
+
+	if (mcdi_init_status == MCDI_INIT_2 && mcdi_init_2() == 0) {
+		mcdi_init_status = MCDI_INIT_DONE;
+	}
+
+	INFO("mcdi ready for mcusys-off-idle and system suspend\n");
+
+	return (mcdi_init_status == MCDI_INIT_DONE) ? 0 : mcdi_init_status;
+}
diff --git a/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.h b/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.h
new file mode 100644
index 0000000..f3545aa
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/mcdi/mt_mcdi.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_MCDI_H
+#define MT_MCDI_H
+
+int mcdi_try_init(void);
+
+#endif /* MT_MCDI_H */
diff --git a/plat/mediatek/mt8195/drivers/pmic/pmic.c b/plat/mediatek/mt8195/drivers/pmic/pmic.c
new file mode 100644
index 0000000..cca4413
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/pmic/pmic.c
@@ -0,0 +1,13 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <pmic.h>
+#include <pmic_wrap_init.h>
+
+void pmic_power_off(void)
+{
+	pwrap_write(PMIC_PWRHOLD, 0x0);
+}
diff --git a/plat/mediatek/mt8195/drivers/pmic/pmic.h b/plat/mediatek/mt8195/drivers/pmic/pmic.h
new file mode 100644
index 0000000..aac22af
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/pmic/pmic.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PMIC_H
+#define PMIC_H
+
+#define PMIC_PWRHOLD 0xa08
+
+/* external API */
+void pmic_power_off(void);
+
+#endif /* PMIC_H */
diff --git a/plat/mediatek/mt8195/drivers/pmic/pmic_wrap_init.h b/plat/mediatek/mt8195/drivers/pmic/pmic_wrap_init.h
new file mode 100644
index 0000000..39e78f5
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/pmic/pmic_wrap_init.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PMIC_WRAP_INIT_H
+#define PMIC_WRAP_INIT_H
+
+#include <stdint.h>
+
+#include "platform_def.h"
+
+/* external API */
+int32_t pwrap_read(uint32_t adr, uint32_t *rdata);
+int32_t pwrap_write(uint32_t adr, uint32_t wdata);
+
+static struct mt8195_pmic_wrap_regs *const mtk_pwrap = (void *)PMIC_WRAP_BASE;
+
+/* PMIC_WRAP registers */
+struct mt8195_pmic_wrap_regs {
+	uint32_t init_done;
+	uint32_t reserved[543];
+	uint32_t wacs2_cmd;
+	uint32_t wacs2_wdata;
+	uint32_t reserved1[3];
+	uint32_t wacs2_rdata;
+	uint32_t reserved2[3];
+	uint32_t wacs2_vldclr;
+	uint32_t wacs2_sta;
+};
+
+#define GET_WACS_FSM(x)	((x >> 1) & 0x7)
+
+/* macro for SWINF_FSM */
+#define SWINF_FSM_IDLE		(0x00)
+#define SWINF_FSM_REQ		(0x02)
+#define SWINF_FSM_WFDLE		(0x04)
+#define SWINF_FSM_WFVLDCLR	(0x06)
+#define SWINF_INIT_DONE		(0x01)
+
+/* timeout setting */
+#define PWRAP_READ_US	1000
+#define PWRAP_WAIT_IDLE_US	1000
+
+/* error information flag */
+enum pwrap_errno {
+	E_PWR_INVALID_ARG             = 1,
+	E_PWR_INVALID_RW              = 2,
+	E_PWR_INVALID_ADDR            = 3,
+	E_PWR_INVALID_WDAT            = 4,
+	E_PWR_INVALID_OP_MANUAL       = 5,
+	E_PWR_NOT_IDLE_STATE          = 6,
+	E_PWR_NOT_INIT_DONE           = 7,
+	E_PWR_NOT_INIT_DONE_READ      = 8,
+	E_PWR_WAIT_IDLE_TIMEOUT       = 9,
+	E_PWR_WAIT_IDLE_TIMEOUT_READ  = 10,
+	E_PWR_INIT_SIDLY_FAIL         = 11,
+	E_PWR_RESET_TIMEOUT           = 12,
+	E_PWR_TIMEOUT                 = 13,
+	E_PWR_INIT_RESET_SPI          = 20,
+	E_PWR_INIT_SIDLY              = 21,
+	E_PWR_INIT_REG_CLOCK          = 22,
+	E_PWR_INIT_ENABLE_PMIC        = 23,
+	E_PWR_INIT_DIO                = 24,
+	E_PWR_INIT_CIPHER             = 25,
+	E_PWR_INIT_WRITE_TEST         = 26,
+	E_PWR_INIT_ENABLE_CRC         = 27,
+	E_PWR_INIT_ENABLE_DEWRAP      = 28,
+	E_PWR_INIT_ENABLE_EVENT       = 29,
+	E_PWR_READ_TEST_FAIL          = 30,
+	E_PWR_WRITE_TEST_FAIL         = 31,
+	E_PWR_SWITCH_DIO              = 32
+};
+
+#endif /* PMIC_WRAP_INIT_H */
diff --git a/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_common.h b/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_common.h
new file mode 100644
index 0000000..341cf86
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_common.h
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTK_PTP3_COMMON_H
+#define MTK_PTP3_COMMON_H
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+
+/************************************************
+ * CPU info
+ ************************************************/
+#define NR_PTP3_CFG_CPU			U(8)
+#define PTP3_CFG_CPU_START_ID_L		U(0)
+#define PTP3_CFG_CPU_START_ID_B		U(4)
+#define PTP3_CFG_CPU_END_ID		U(7)
+
+#define NR_PTP3_CFG1_DATA		U(2)
+#define PTP3_CFG1_MASK			0x3000
+
+#define NR_PTP3_CFG2_DATA		U(5)
+
+#define PTP3_CFG3_MASK1			0x1180
+#define PTP3_CFG3_MASK2			0x35C0
+#define PTP3_CFG3_MASK3			0x3DC0
+
+/************************************************
+ * register read/write
+ ************************************************/
+#define ptp3_write(addr, val) mmio_write_32((uintptr_t)addr, val)
+#define ptp3_clrsetbits(addr, clear, set) \
+	mmio_clrsetbits_32((uintptr_t)addr, clear, set)
+
+/************************************************
+ * config enum
+ ************************************************/
+enum PTP3_CFG {
+	PTP3_CFG_ADDR,
+	PTP3_CFG_VALUE,
+	NR_PTP3_CFG,
+};
+
+/************************************
+ * prototype
+ ************************************/
+extern void ptp3_core_init(unsigned int core);
+extern void ptp3_core_unInit(unsigned int core);
+
+#endif /* MTK_PTP3_COMMON_H */
diff --git a/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_main.c b/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_main.c
new file mode 100644
index 0000000..540cb33
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/ptp3/mtk_ptp3_main.c
@@ -0,0 +1,137 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved. \
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <mtk_ptp3_common.h>
+
+#define PTP3_CORE_OFT(core)	(0x800 * (core))
+
+/************************************************
+ * Central control
+ ************************************************/
+static unsigned int ptp3_cfg1[NR_PTP3_CFG1_DATA][NR_PTP3_CFG] = {
+	{0x0C53A2A0, 0x1000},
+	{0x0C53A2A4, 0x1000}
+};
+
+static unsigned int ptp3_cfg2[NR_PTP3_CFG2_DATA][NR_PTP3_CFG] = {
+	{0x0C530404, 0x3A1000},
+	{0x0C530428, 0x13E0408},
+	{0x0C530434, 0xB22800},
+	{0x0C53043C, 0x750},
+	{0x0C530440, 0x0222c4cc}
+};
+
+static unsigned int ptp3_cfg3[NR_PTP3_CFG] = {0x0C530400, 0x2D80};
+static unsigned int ptp3_cfg3_ext[NR_PTP3_CFG] = {0x0C530400, 0xC00};
+
+static void ptp3_init(unsigned int core)
+{
+	unsigned int i, addr, value;
+
+	if (core < PTP3_CFG_CPU_START_ID_B) {
+		ptp3_clrsetbits(ptp3_cfg1[0][PTP3_CFG_ADDR], PTP3_CFG1_MASK,
+				ptp3_cfg1[0][PTP3_CFG_VALUE]);
+	} else {
+		ptp3_clrsetbits(ptp3_cfg1[1][PTP3_CFG_ADDR], PTP3_CFG1_MASK,
+				ptp3_cfg1[1][PTP3_CFG_VALUE]);
+	}
+
+	if (core < PTP3_CFG_CPU_START_ID_B) {
+		for (i = 0; i < NR_PTP3_CFG2_DATA; i++) {
+			addr = ptp3_cfg2[i][PTP3_CFG_ADDR] +
+			       PTP3_CORE_OFT(core);
+			value = ptp3_cfg2[i][PTP3_CFG_VALUE];
+
+			ptp3_write(addr, value);
+		}
+	} else {
+		for (i = 0; i < NR_PTP3_CFG2_DATA; i++) {
+			addr = ptp3_cfg2[i][PTP3_CFG_ADDR] +
+			       PTP3_CORE_OFT(core);
+
+			if (i == 2) {
+				value = ptp3_cfg2[i][PTP3_CFG_VALUE] + 0x5E0;
+			} else {
+				value = ptp3_cfg2[i][PTP3_CFG_VALUE];
+			}
+			ptp3_write(addr, value);
+		}
+	}
+
+	if (core < PTP3_CFG_CPU_START_ID_B) {
+		addr = ptp3_cfg3[PTP3_CFG_ADDR] + PTP3_CORE_OFT(core);
+		value = ptp3_cfg3[PTP3_CFG_VALUE];
+
+		ptp3_write(addr, value & PTP3_CFG3_MASK1);
+		ptp3_write(addr, value & PTP3_CFG3_MASK2);
+		ptp3_write(addr, value & PTP3_CFG3_MASK3);
+	} else {
+		addr = ptp3_cfg3_ext[PTP3_CFG_ADDR] + PTP3_CORE_OFT(core);
+		value = ptp3_cfg3_ext[PTP3_CFG_VALUE];
+
+		ptp3_write(addr, value & PTP3_CFG3_MASK1);
+		ptp3_write(addr, value & PTP3_CFG3_MASK2);
+		ptp3_write(addr, value & PTP3_CFG3_MASK3);
+	}
+}
+
+void pdp_proc_ARM_write(unsigned int pdp_n)
+{
+	unsigned long v = 0;
+
+	dsb();
+	__asm__ volatile ("mrs %0, S3_6_C15_C2_0" : "=r" (v));
+	v |= (UL(0x0) << 52);
+	v |= (UL(0x1) << 53);
+	v |= (UL(0x0) << 54);
+	v |= (UL(0x0) << 48);
+	v |= (UL(0x1) << 49);
+	__asm__ volatile ("msr S3_6_C15_C2_0, %0" : : "r" (v));
+	dsb();
+}
+
+void pdp_init(unsigned int pdp_cpu, unsigned int en)
+{
+	if ((pdp_cpu >= PTP3_CFG_CPU_START_ID_B) &&
+	    (pdp_cpu < NR_PTP3_CFG_CPU)) {
+		pdp_proc_ARM_write(pdp_cpu);
+	}
+}
+
+static void dt_proc_ARM_write(unsigned int dt_n)
+{
+	unsigned long v = 0;
+
+	dsb();
+	__asm__ volatile ("mrs %0, S3_6_C15_C2_0" : "=r" (v));
+	v |= (UL(0x0) << 33);
+	v |= (UL(0x0) << 32);
+	__asm__ volatile ("msr S3_6_C15_C2_0, %0" : : "r" (v));
+	dsb();
+}
+
+void dt_init(unsigned int dt_cpu, unsigned int en)
+{
+	if ((dt_cpu >= PTP3_CFG_CPU_START_ID_B) &&
+	    (dt_cpu < NR_PTP3_CFG_CPU)) {
+		dt_proc_ARM_write(dt_cpu);
+	}
+}
+void ptp3_core_init(unsigned int core)
+{
+	/* init for ptp3 */
+	ptp3_init(core);
+	/* init for pdp */
+	pdp_init(core, 1);
+	/* init for dt */
+	dt_init(core, 1);
+}
+
+void ptp3_core_unInit(unsigned int core)
+{
+	/* TBD */
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/build.mk b/plat/mediatek/mt8195/drivers/spm/build.mk
new file mode 100644
index 0000000..28b2d07
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/build.mk
@@ -0,0 +1,68 @@
+#
+# Copyright (c) 2021, MediaTek Inc. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Enable or disable spm feature
+MT_SPM_FEATURE_SUPPORT = yes
+
+# Enable or disable cirq restore
+MT_SPM_CIRQ_FEATURE_SUPPORT = yes
+
+# sspm notifier support
+MT_SPM_SSPM_NOTIFIER_SUPPORT = yes
+
+CUR_SPM_FOLDER = ${MTK_PLAT_SOC}/drivers/spm
+
+# spm common files
+PLAT_SPM_SOURCE_FILES_COMMON +=			\
+	${CUR_SPM_FOLDER}/mt_spm.c		\
+	${CUR_SPM_FOLDER}/mt_spm_conservation.c	\
+	${CUR_SPM_FOLDER}/mt_spm_internal.c	\
+	${CUR_SPM_FOLDER}/mt_spm_pmic_wrap.c
+
+# spm platform dependcy files
+PLAT_SPM_SOURCE_FILES +=					\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_bus26m.c	\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_cpu_buck_ldo.c	\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_dram.c		\
+	${CUR_SPM_FOLDER}/constraints/mt_spm_rc_syspll.c	\
+	${CUR_SPM_FOLDER}/mt_spm_cond.c				\
+	${CUR_SPM_FOLDER}/mt_spm_suspend.c			\
+	${CUR_SPM_FOLDER}/mt_spm_idle.c				\
+	${CUR_SPM_FOLDER}/mt_spm_vcorefs.c
+
+ifeq (${MT_SPM_FEATURE_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_SPM_UNSUPPORT
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES += ${PLAT_SPM_SOURCE_FILES_COMMON}
+else
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES +=	\
+	${PLAT_SPM_SOURCE_FILES_COMMON} \
+	${PLAT_SPM_SOURCE_FILES}
+endif
+
+ifeq (${MT_SPM_CIRQ_FEATURE_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_CIRQ_UNSUPPORT
+endif
+
+ifeq (${MT_SPM_SSPM_NOTIFIER_SUPPORT}, no)
+PLAT_SPM_DEBUG_CFLAGS += -DATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+else
+BL31_MT_LPM_PLAT_SPM_SOURCE_FILES +=	\
+	${CUR_SPM_FOLDER}/notifier/mt_spm_sspm_notifier.c
+endif
+
+$(info --------------------------------------)
+$(info SPM build flags: ${PLAT_SPM_DEBUG_CFLAGS})
+$(info SPM build files: ${BL31_MT_LPM_PLAT_SPM_SOURCE_FILES})
+$(info --------------------------------------)
+
+# Common makefile for platform.mk
+PLAT_INCLUDES +=				\
+	${PLAT_SPM_DEBUG_CFLAGS}		\
+	-I${CUR_SPM_FOLDER}/			\
+	-I${CUR_SPM_FOLDER}/constraints/	\
+	-I${CUR_SPM_FOLDER}/notifier/
+
+PLAT_BL_COMMON_SOURCES += ${BL31_MT_LPM_PLAT_SPM_SOURCE_FILES}
diff --git a/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_bus26m.c b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_bus26m.c
new file mode 100644
index 0000000..d2ad282
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_bus26m.c
@@ -0,0 +1,241 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#ifndef ATF_PLAT_CIRQ_UNSUPPORT
+#include <mt_gic_v3.h>
+#include <mtk_cirq.h>
+#endif
+
+#define CONSTRAINT_BUS26M_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S0 |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_VCORE_LP |	\
+	 MT_RM_CONSTRAINT_ALLOW_LVTS_STATE |	\
+	 MT_RM_CONSTRAINT_ALLOW_BUS26M_OFF)
+
+#define CONSTRAINT_BUS26M_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_ENABLE_TIA_WORKAROUND |	\
+	 SPM_FLAG_ENABLE_LVTS_WORKAROUND |	\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |	\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP)
+
+#define CONSTRAINT_BUS26M_PCM_FLAG1		0U
+
+#define CONSTRAINT_BUS26M_RESOURCE_REQ		0U
+
+static unsigned int bus26m_ext_opand;
+static struct mt_irqremain *refer2remain_irq;
+static struct mt_spm_cond_tables cond_bus26m = {
+	.name = "bus26m",
+	.table_cg = {
+		0xFFFFD408,	/* MTCMOS1 */
+		0x2284C802,	/* INFRA0  */
+		0x27AF8000,	/* INFRA1  */
+		0x86040650,	/* INFRA2  */
+		0x30038020,	/* INFRA3  */
+		0x80000000,	/* INFRA4  */
+		0x00080ABB,	/* PERI0   */
+		0x00004000,	/* VPPSYS0_0  */
+		0x08803000,	/* VPPSYS0_1  */
+		0x00000000,	/* VPPSYS0_2  */
+		0x80005555,	/* VPPSYS1_0  */
+		0x00009008,	/* VPPSYS1_1  */
+		0x60060000,	/* VDOSYS0_0  */
+		0x00000000,	/* VDOSYS0_1  */
+		0x201E01F8,	/* VDOSYS1_0  */
+		0x00800000,	/* VDOSYS1_1  */
+		0x00000000,	/* VDOSYS1_2  */
+		0x00000080,	/* I2C */
+	},
+	.table_pll = (PLL_BIT_UNIVPLL |
+		      PLL_BIT_MFGPLL |
+		      PLL_BIT_MSDCPLL |
+		      PLL_BIT_TVDPLL |
+		      PLL_BIT_MMPLL),
+};
+
+static struct mt_spm_cond_tables cond_bus26m_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_BUS26M,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_bus26m_res,
+};
+
+/*
+ * Cirq will take the place of gic when gic is off.
+ * However, cirq cannot work if 26m clk is turned off when system idle/suspend.
+ * Therefore, we need to set irq pending for specific wakeup source.
+ */
+#ifdef ATF_PLAT_CIRQ_UNSUPPORT
+#define do_irqs_delivery()
+#else
+static void mt_spm_irq_remain_dump(struct mt_irqremain *irqs,
+				   unsigned int irq_index,
+				   struct wake_status *wakeup)
+{
+	INFO("[SPM] r12 = 0x%08x(0x%08x), flag = 0x%08x 0x%08x 0x%08x\n",
+	     wakeup->tr.comm.r12, wakeup->md32pcm_wakeup_sta,
+	     wakeup->tr.comm.debug_flag, wakeup->tr.comm.b_sw_flag0,
+	     wakeup->tr.comm.b_sw_flag1);
+
+	INFO("irq:%u(0x%08x) set pending\n",
+	     irqs->wakeupsrc[irq_index], irqs->irqs[irq_index]);
+}
+
+static void do_irqs_delivery(void)
+{
+	unsigned int idx;
+	int res = 0;
+	struct wake_status *wakeup = NULL;
+	struct mt_irqremain *irqs = refer2remain_irq;
+
+	res = spm_conservation_get_result(&wakeup);
+
+	if ((res != 0) && (irqs == NULL)) {
+		return;
+	}
+
+	for (idx = 0U; idx < irqs->count; ++idx) {
+		if (((wakeup->tr.comm.r12 & irqs->wakeupsrc[idx]) != 0U) ||
+		    ((wakeup->raw_sta & irqs->wakeupsrc[idx]) != 0U)) {
+			if ((irqs->wakeupsrc_cat[idx] &
+			     MT_IRQ_REMAIN_CAT_LOG) != 0U) {
+				mt_spm_irq_remain_dump(irqs, idx, wakeup);
+			}
+
+			mt_irq_set_pending(irqs->irqs[idx]);
+		}
+	}
+}
+#endif
+
+static void spm_bus26m_conduct(struct spm_lp_scen *spm_lp,
+			       unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_BUS26M_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_BUS26M_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_BUS26M_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_bus26m(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_bus26m(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_bus26m;
+
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_bus26m_res : NULL);
+	} else if (type == PLAT_RC_UPDATE_REMAIN_IRQS) {
+		refer2remain_irq = (struct mt_irqremain *)val;
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_bus26m(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_BUS26M_ALLOW;
+}
+
+int spm_run_rc_bus26m(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, CONSTRAINT_BUS26M_ALLOW |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_HW_S1_DETECT |
+				      MT_SPM_EX_OP_SET_SUSPEND_MODE |
+				      bus26m_ext_opand),
+				     CONSTRAINT_BUS26M_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, MT_SPM_EX_OP_HW_S1_DETECT,
+					  spm_bus26m_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_bus26m(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, 0U);
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		ext_op |= (bus26m_ext_opand | MT_SPM_EX_OP_SET_WDT);
+		mt_spm_suspend_resume(state_id, ext_op, NULL);
+		bus26m_ext_opand = 0U;
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	do_irqs_delivery();
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c
new file mode 100644
index 0000000..cf71350
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_cpu_buck_ldo.c
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+
+#define CONSTRAINT_CPU_BUCK_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH)
+
+#define CONSTRAINT_CPU_BUCK_PCM_FLAG1		0U
+
+#define CONSTRAINT_CPU_BUCK_RESOURCE_REQ	\
+	(MT_SPM_DRAM_S1 |			\
+	 MT_SPM_DRAM_S0 |			\
+	 MT_SPM_SYSPLL |			\
+	 MT_SPM_INFRA |				\
+	 MT_SPM_26M |				\
+	 MT_SPM_XO_FPM)
+
+
+static unsigned int cpubuckldo_status = MT_SPM_RC_VALID_SW;
+static unsigned int cpubuckldo_enter_cnt;
+
+static void spm_cpu_bcuk_ldo_conduct(struct spm_lp_scen *spm_lp,
+				     unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_CPU_BUCK_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_CPU_BUCK_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_CPU_BUCK_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return IS_MT_RM_RC_READY(cpubuckldo_status);
+}
+
+unsigned int spm_allow_rc_cpu_buck_ldo(int state_id)
+{
+	(void)state_id;
+
+	return MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF;
+}
+
+int spm_run_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER,
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     MT_SPM_EX_OP_SET_SUSPEND_MODE |
+				     MT_SPM_EX_OP_SET_WDT,
+				     CONSTRAINT_CPU_BUCK_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, 0U,
+					  spm_cpu_bcuk_ldo_conduct);
+	}
+
+	cpubuckldo_enter_cnt++;
+
+	return 0;
+}
+
+int spm_reset_rc_cpu_buck_ldo(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, 0U);
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id, MT_SPM_EX_OP_SET_WDT, NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, 0U, NULL);
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_dram.c b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_dram.c
new file mode 100644
index 0000000..bd24ddd
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_dram.c
@@ -0,0 +1,201 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#define CONSTRAINT_DRAM_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_DRAM_S0	|	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF)
+
+#define CONSTRAINT_DRAM_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |	\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP)
+
+#define CONSTRAINT_DRAM_PCM_FLAG1		0U
+
+#define CONSTRAINT_DRAM_RESOURCE_REQ		\
+	(MT_SPM_SYSPLL |			\
+	 MT_SPM_INFRA |				\
+	 MT_SPM_26M)
+
+static struct mt_spm_cond_tables cond_dram = {
+	.name = "dram",
+	.table_cg = {
+		0xFFFDD008,	/* MTCMOS1 */
+		0x20040802,	/* INFRA0  */
+		0x27AF8000,	/* INFRA1  */
+		0x86040640,	/* INFRA2  */
+		0x00000000,	/* INFRA3  */
+		0x80000000,	/* INFRA4  */
+		0x00000000,	/* PERI0   */
+		0x00004000,	/* VPPSYS0_0  */
+		0x08803000,	/* VPPSYS0_1  */
+		0x00000000,	/* VPPSYS0_2  */
+		0x80005555,	/* VPPSYS1_0  */
+		0x00009008,	/* VPPSYS1_1  */
+		0x60060000,	/* VDOSYS0_0  */
+		0x00000000,	/* VDOSYS0_1  */
+		0x201E01F8,	/* VDOSYS1_0  */
+		0x00800000,	/* VDOSYS1_1  */
+		0x00000000,	/* VDOSYS1_2  */
+		0x00000080,	/* I2C */
+	},
+	.table_pll = 0U,
+};
+
+static struct mt_spm_cond_tables cond_dram_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_DRAM,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH |
+		  MT_SPM_RC_VALID_XSOC_BBLPM),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_dram_res,
+};
+
+static void spm_dram_conduct(struct spm_lp_scen *spm_lp,
+			     unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_DRAM_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_DRAM_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_DRAM_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_dram(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_dram(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_dram;
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_dram_res : NULL);
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_dram(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_DRAM_ALLOW;
+}
+
+int spm_run_rc_dram(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_DRAM_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, allows |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_SET_SUSPEND_MODE |
+				      MT_SPM_EX_OP_HW_S1_DETECT),
+				     CONSTRAINT_DRAM_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, ext_op, spm_dram_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_dram(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_DRAM_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, allows);
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id,
+				      (MT_SPM_EX_OP_SET_WDT |
+				       MT_SPM_EX_OP_HW_S1_DETECT),
+				      NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_internal.h b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_internal.h
new file mode 100644
index 0000000..9e74ace
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_internal.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_RC_INTERNAL_H
+#define MT_SPM_RC_INTERNAL_H
+
+#include <stdbool.h>
+
+#define SPM_FLAG_SRAM_SLEEP_CTRL			\
+	(SPM_FLAG_DISABLE_SSPM_SRAM_SLEEP |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |	\
+	 SPM_FLAG_DISABLE_SYSRAM_SLEEP)
+
+/* cpu buck/ldo constraint function */
+bool spm_is_valid_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+unsigned int spm_allow_rc_cpu_buck_ldo(int state_id);
+int spm_run_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+int spm_reset_rc_cpu_buck_ldo(unsigned int cpu, int state_id);
+
+/* spm resource dram constraint function */
+bool spm_is_valid_rc_dram(unsigned int cpu, int state_id);
+int spm_update_rc_dram(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_dram(int state_id);
+int spm_run_rc_dram(unsigned int cpu, int state_id);
+int spm_reset_rc_dram(unsigned int cpu, int state_id);
+
+/* spm resource syspll constraint function */
+bool spm_is_valid_rc_syspll(unsigned int cpu, int state_id);
+int spm_update_rc_syspll(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_syspll(int state_id);
+int spm_run_rc_syspll(unsigned int cpu, int state_id);
+int spm_reset_rc_syspll(unsigned int cpu, int state_id);
+
+/* spm resource bus26m constraint function */
+bool spm_is_valid_rc_bus26m(unsigned int cpu, int state_id);
+int spm_update_rc_bus26m(int state_id, int type, const void *val);
+unsigned int spm_allow_rc_bus26m(int state_id);
+int spm_run_rc_bus26m(unsigned int cpu, int state_id);
+int spm_reset_rc_bus26m(unsigned int cpu, int state_id);
+#endif /* MT_SPM_RC_INTERNAL_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_syspll.c b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_syspll.c
new file mode 100644
index 0000000..662f85e
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/constraints/mt_spm_rc_syspll.c
@@ -0,0 +1,200 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_notifier.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <plat_mtk_lpm.h>
+
+#define CONSTRAINT_SYSPLL_ALLOW			\
+	(MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S0 |	\
+	 MT_RM_CONSTRAINT_ALLOW_DRAM_S1 |	\
+	 MT_RM_CONSTRAINT_ALLOW_VCORE_LP)
+
+#define CONSTRAINT_SYSPLL_PCM_FLAG		\
+	(SPM_FLAG_DISABLE_INFRA_PDN |		\
+	 SPM_FLAG_DISABLE_VCORE_DVS |		\
+	 SPM_FLAG_DISABLE_VCORE_DFS |		\
+	 SPM_FLAG_SRAM_SLEEP_CTRL |		\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |	\
+	 SPM_FLAG_ENABLE_6315_CTRL |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |\
+	 SPM_FLAG_USE_SRCCLKENO2)
+
+#define CONSTRAINT_SYSPLL_PCM_FLAG1		0U
+#define CONSTRAINT_SYSPLL_RESOURCE_REQ		(MT_SPM_26M)
+
+static struct mt_spm_cond_tables cond_syspll = {
+	.name = "syspll",
+	.table_cg = {
+		0xFFFFD008,	/* MTCMOS1 */
+		0x20844802,	/* INFRA0  */
+		0x27AF8000,	/* INFRA1  */
+		0x86040640,	/* INFRA2  */
+		0x30038020,	/* INFRA3  */
+		0x80000000,	/* INFRA4  */
+		0x00080A8B,	/* PERI0   */
+		0x00004000,	/* VPPSYS0_0  */
+		0x08803000,	/* VPPSYS0_1  */
+		0x00000000,	/* VPPSYS0_2  */
+		0x80005555,	/* VPPSYS1_0  */
+		0x00009008,	/* VPPSYS1_1  */
+		0x60060000,	/* VDOSYS0_0  */
+		0x00000000,	/* VDOSYS0_1  */
+		0x201E01F8,	/* VDOSYS1_0  */
+		0x00800000,	/* VDOSYS1_1  */
+		0x00000000,	/* VDOSYS1_2  */
+		0x00000080,	/* I2C */
+	},
+	.table_pll = 0U,
+};
+
+static struct mt_spm_cond_tables cond_syspll_res = {
+	.table_cg = { 0U },
+	.table_pll = 0U,
+};
+
+static struct constraint_status status = {
+	.id = MT_RM_CONSTRAINT_ID_SYSPLL,
+	.valid = (MT_SPM_RC_VALID_SW |
+		  MT_SPM_RC_VALID_COND_LATCH |
+		  MT_SPM_RC_VALID_XSOC_BBLPM),
+	.cond_block = 0U,
+	.enter_cnt = 0U,
+	.cond_res = &cond_syspll_res,
+};
+
+static void spm_syspll_conduct(struct spm_lp_scen *spm_lp,
+			       unsigned int *resource_req)
+{
+	spm_lp->pwrctrl->pcm_flags = (uint32_t)CONSTRAINT_SYSPLL_PCM_FLAG;
+	spm_lp->pwrctrl->pcm_flags1 = (uint32_t)CONSTRAINT_SYSPLL_PCM_FLAG1;
+	*resource_req |= CONSTRAINT_SYSPLL_RESOURCE_REQ;
+}
+
+bool spm_is_valid_rc_syspll(unsigned int cpu, int state_id)
+{
+	(void)cpu;
+	(void)state_id;
+
+	return (status.cond_block == 0U) && IS_MT_RM_RC_READY(status.valid);
+}
+
+int spm_update_rc_syspll(int state_id, int type, const void *val)
+{
+	const struct mt_spm_cond_tables *tlb;
+	const struct mt_spm_cond_tables *tlb_check;
+	int res = MT_RM_STATUS_OK;
+
+	if (val == NULL) {
+		return MT_RM_STATUS_BAD;
+	}
+
+	if (type == PLAT_RC_UPDATE_CONDITION) {
+		tlb = (const struct mt_spm_cond_tables *)val;
+		tlb_check = (const struct mt_spm_cond_tables *)&cond_syspll;
+
+		status.cond_block =
+			mt_spm_cond_check(state_id, tlb, tlb_check,
+					  ((status.valid &
+					    MT_SPM_RC_VALID_COND_LATCH) != 0U) ?
+					  &cond_syspll_res : NULL);
+	} else {
+		res = MT_RM_STATUS_BAD;
+	}
+
+	return res;
+}
+
+unsigned int spm_allow_rc_syspll(int state_id)
+{
+	(void)state_id;
+
+	return CONSTRAINT_SYSPLL_ALLOW;
+}
+
+int spm_run_rc_syspll(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_SYSPLL_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_ENTER, allows |
+			       (IS_PLAT_SUSPEND_ID(state_id) ?
+				MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND : 0U));
+#else
+	(void)allows;
+#endif
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_enter(state_id,
+				     (MT_SPM_EX_OP_SET_WDT |
+				      MT_SPM_EX_OP_HW_S1_DETECT |
+				      MT_SPM_EX_OP_SET_SUSPEND_MODE),
+				     CONSTRAINT_SYSPLL_RESOURCE_REQ);
+	} else {
+		mt_spm_idle_generic_enter(state_id, ext_op, spm_syspll_conduct);
+	}
+
+	return 0;
+}
+
+int spm_reset_rc_syspll(unsigned int cpu, int state_id)
+{
+	unsigned int ext_op = MT_SPM_EX_OP_HW_S1_DETECT;
+	unsigned int allows = CONSTRAINT_SYSPLL_ALLOW;
+
+	(void)cpu;
+
+	if (IS_MT_SPM_RC_BBLPM_MODE(status.valid)) {
+#ifdef MT_SPM_USING_SRCLKEN_RC
+		ext_op |= MT_SPM_EX_OP_SRCLKEN_RC_BBLPM;
+#else
+		allows |= MT_RM_CONSTRAINT_ALLOW_BBLPM;
+#endif
+	}
+
+#ifndef ATF_PLAT_SPM_SSPM_NOTIFIER_UNSUPPORT
+	mt_spm_sspm_notify_u32(MT_SPM_NOTIFY_LP_LEAVE, allows);
+#else
+	(void)allows;
+#endif
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		mt_spm_suspend_resume(state_id,
+				      (MT_SPM_EX_OP_SET_SUSPEND_MODE |
+				       MT_SPM_EX_OP_SET_WDT |
+				       MT_SPM_EX_OP_HW_S1_DETECT),
+				      NULL);
+	} else {
+		mt_spm_idle_generic_resume(state_id, ext_op, NULL);
+		status.enter_cnt++;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm.c b/plat/mediatek/mt8195/drivers/spm/mt_spm.c
new file mode 100644
index 0000000..f708bf5
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm.c
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+#include <string.h>
+#include <common/debug.h>
+#include <lib/bakery_lock.h>
+#include <lib/mmio.h>
+#include <mt_lp_rm.h>
+#include <mt_spm.h>
+#include <mt_spm_cond.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_constraint.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <mtk_plat_common.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+#include <sleep_def.h>
+
+#ifdef MT_SPM_USING_BAKERY_LOCK
+DEFINE_BAKERY_LOCK(spm_lock);
+#define plat_spm_lock_init() bakery_lock_init(&spm_lock)
+#else
+spinlock_t spm_lock;
+#define plat_spm_lock_init()
+#endif
+
+/* CLK_SCP_CFG_0 */
+#define CLK_SCP_CFG_0		(TOPCKGEN_BASE + 0x264)
+#define SPM_CK_CONTROL_EN	0x7FF
+
+struct mt_resource_constraint plat_constraint_bus26m = {
+	.is_valid = spm_is_valid_rc_bus26m,
+	.update = spm_update_rc_bus26m,
+	.allow = spm_allow_rc_bus26m,
+	.run = spm_run_rc_bus26m,
+	.reset = spm_reset_rc_bus26m,
+};
+
+struct mt_resource_constraint plat_constraint_syspll = {
+	.is_valid = spm_is_valid_rc_syspll,
+	.update = spm_update_rc_syspll,
+	.allow = spm_allow_rc_syspll,
+	.run = spm_run_rc_syspll,
+	.reset = spm_reset_rc_syspll,
+};
+
+struct mt_resource_constraint plat_constraint_dram = {
+	.is_valid = spm_is_valid_rc_dram,
+	.update = spm_update_rc_dram,
+	.allow = spm_allow_rc_dram,
+	.run = spm_run_rc_dram,
+	.reset = spm_reset_rc_dram,
+};
+
+struct mt_resource_constraint plat_constraint_cpu = {
+	.is_valid = spm_is_valid_rc_cpu_buck_ldo,
+	.update = NULL,
+	.allow = spm_allow_rc_cpu_buck_ldo,
+	.run = spm_run_rc_cpu_buck_ldo,
+	.reset = spm_reset_rc_cpu_buck_ldo,
+};
+
+struct mt_resource_constraint *plat_constraints[] = {
+	&plat_constraint_bus26m,
+	&plat_constraint_syspll,
+	&plat_constraint_dram,
+	&plat_constraint_cpu,
+	NULL,
+};
+
+struct mt_resource_manager plat_mt8195_rm = {
+	.update = mt_spm_cond_update,
+	.consts = plat_constraints,
+};
+
+void spm_boot_init(void)
+{
+	NOTICE("MT8195 %s\n", __func__);
+	/* switch ck_off/axi_26m control to SPM */
+	mmio_setbits_32(CLK_SCP_CFG_0, SPM_CK_CONTROL_EN);
+
+	plat_spm_lock_init();
+	mt_spm_pmic_wrap_set_phase(PMIC_WRAP_PHASE_ALLINONE);
+	mt_lp_rm_register(&plat_mt8195_rm);
+	mt_spm_idle_generic_init();
+	mt_spm_suspend_init();
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm.h b/plat/mediatek/mt8195/drivers/spm/mt_spm.h
new file mode 100644
index 0000000..bc57b61
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_H
+#define MT_SPM_H
+
+#include <lib/bakery_lock.h>
+#include <lib/spinlock.h>
+
+#include <plat_mtk_lpm.h>
+
+/*
+ * ARM v8.2, the cache will turn off automatically when cpu
+ * power down. So, there is no doubt to use the spin_lock here
+ */
+#if !HW_ASSISTED_COHERENCY
+#define MT_SPM_USING_BAKERY_LOCK
+#endif
+
+#ifdef MT_SPM_USING_BAKERY_LOCK
+DECLARE_BAKERY_LOCK(spm_lock);
+#define plat_spm_lock() bakery_lock_get(&spm_lock)
+#define plat_spm_unlock() bakery_lock_release(&spm_lock)
+#else
+extern spinlock_t spm_lock;
+#define plat_spm_lock() spin_lock(&spm_lock)
+#define plat_spm_unlock() spin_unlock(&spm_lock)
+#endif
+
+#define MT_SPM_USING_SRCLKEN_RC
+
+/* spm extern operand definition */
+#define MT_SPM_EX_OP_CLR_26M_RECORD			(1U << 0)
+#define MT_SPM_EX_OP_SET_WDT				(1U << 1)
+#define MT_SPM_EX_OP_NON_GENERIC_RESOURCE_REQ		(1U << 2)
+#define MT_SPM_EX_OP_SET_SUSPEND_MODE			(1U << 3)
+#define MT_SPM_EX_OP_SET_IS_ADSP			(1U << 4)
+#define MT_SPM_EX_OP_SRCLKEN_RC_BBLPM			(1U << 5)
+#define MT_SPM_EX_OP_HW_S1_DETECT			(1U << 6)
+
+typedef enum {
+	WR_NONE = 0,
+	WR_UART_BUSY = 1,
+	WR_ABORT = 2,
+	WR_PCM_TIMER = 3,
+	WR_WAKE_SRC = 4,
+	WR_DVFSRC = 5,
+	WR_TWAM = 6,
+	WR_PMSR = 7,
+	WR_SPM_ACK_CHK = 8,
+	WR_UNKNOWN = 9,
+} wake_reason_t;
+
+static inline void spm_lock_get(void)
+{
+	plat_spm_lock();
+}
+
+static inline void spm_lock_release(void)
+{
+	plat_spm_unlock();
+}
+
+extern void spm_boot_init(void);
+#endif /* MT_SPM_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.c
new file mode 100644
index 0000000..c80faf5
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.c
@@ -0,0 +1,235 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdbool.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm_cond.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_constraint.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+
+#define MT_LP_TZ_INFRA_REG(ofs)		(INFRACFG_AO_BASE + ofs)
+#define MT_LP_TZ_SPM_REG(ofs)		(SPM_BASE + ofs)
+#define MT_LP_TZ_TOPCK_REG(ofs)		(TOPCKGEN_BASE + ofs)
+#define MT_LP_TZ_APMIXEDSYS(ofs)	(APMIXEDSYS + ofs)
+#define MT_LP_TZ_VPPSYS0_REG(ofs)	(VPPSYS0_BASE + ofs)
+#define MT_LP_TZ_VPPSYS1_REG(ofs)	(VPPSYS1_BASE + ofs)
+#define MT_LP_TZ_VDOSYS0_REG(ofs)	(VDOSYS0_BASE + ofs)
+#define MT_LP_TZ_VDOSYS1_REG(ofs)	(VDOSYS1_BASE + ofs)
+#define MT_LP_TZ_PERI_AO_REG(ofs)	(PERICFG_AO_BASE + ofs)
+
+#define SPM_PWR_STATUS			MT_LP_TZ_SPM_REG(0x016C)
+#define SPM_PWR_STATUS_2ND		MT_LP_TZ_SPM_REG(0x0170)
+#define INFRA_SW_CG0			MT_LP_TZ_INFRA_REG(0x0094)
+#define INFRA_SW_CG1			MT_LP_TZ_INFRA_REG(0x0090)
+#define INFRA_SW_CG2			MT_LP_TZ_INFRA_REG(0x00AC)
+#define INFRA_SW_CG3			MT_LP_TZ_INFRA_REG(0x00C8)
+#define INFRA_SW_CG4			MT_LP_TZ_INFRA_REG(0x00E8)
+#define TOP_SW_I2C_CG			MT_LP_TZ_TOPCK_REG(0x00BC)
+#define PERI_SW_CG0			MT_LP_TZ_PERI_AO_REG(0x0018)
+#define VPPSYS0_SW_CG0			MT_LP_TZ_VPPSYS0_REG(0x0020)
+#define VPPSYS0_SW_CG1			MT_LP_TZ_VPPSYS0_REG(0x002C)
+#define VPPSYS0_SW_CG2			MT_LP_TZ_VPPSYS0_REG(0x0038)
+#define VPPSYS1_SW_CG0			MT_LP_TZ_VPPSYS1_REG(0x0100)
+#define VPPSYS1_SW_CG1			MT_LP_TZ_VPPSYS1_REG(0x0110)
+#define VDOSYS0_SW_CG0			MT_LP_TZ_VDOSYS0_REG(0x0100)
+#define VDOSYS0_SW_CG1			MT_LP_TZ_VDOSYS0_REG(0x0110)
+#define VDOSYS1_SW_CG0			MT_LP_TZ_VDOSYS1_REG(0x0100)
+#define VDOSYS1_SW_CG1			MT_LP_TZ_VDOSYS1_REG(0x0120)
+#define VDOSYS1_SW_CG2			MT_LP_TZ_VDOSYS1_REG(0x0130)
+
+/***********************************************************
+ * Check clkmux registers
+ ***********************************************************/
+#define CLK_CFG(id)	MT_LP_TZ_TOPCK_REG(0x98 + id * 0x10)
+#define PDN_CHECK	BIT(7)
+#define CLK_CHECK	BIT(31)
+
+enum {
+	CLKMUX_DISP = 0,
+	NF_CLKMUX,
+};
+
+static bool is_clkmux_pdn(unsigned int clkmux_id)
+{
+	unsigned int reg, val, idx;
+
+	if ((clkmux_id & CLK_CHECK) != 0U) {
+		clkmux_id = (clkmux_id & ~CLK_CHECK);
+		reg = clkmux_id / 4U;
+		val = mmio_read_32(CLK_CFG(reg));
+		idx = clkmux_id % 4U;
+		val = (val >> (idx * 8U)) & PDN_CHECK;
+		return (val != 0U);
+	}
+
+	return false;
+}
+
+static struct mt_spm_cond_tables spm_cond_t;
+
+struct idle_cond_info {
+	unsigned int subsys_mask;
+	uintptr_t addr;
+	bool bBitflip;
+	unsigned int clkmux_id;
+};
+
+#define IDLE_CG(mask, addr, bitflip, clkmux)	\
+	{mask, (uintptr_t)addr, bitflip, clkmux}
+
+static struct idle_cond_info idle_cg_info[PLAT_SPM_COND_MAX] = {
+	IDLE_CG(0xffffffff, SPM_PWR_STATUS, false, 0U),
+	IDLE_CG(0xffffffff, INFRA_SW_CG0, true, 0U),
+	IDLE_CG(0xffffffff, INFRA_SW_CG1, true, 0U),
+	IDLE_CG(0xffffffff, INFRA_SW_CG2, true, 0U),
+	IDLE_CG(0xffffffff, INFRA_SW_CG3, true, 0U),
+	IDLE_CG(0xffffffff, INFRA_SW_CG4, true, 0U),
+	IDLE_CG(0xffffffff, PERI_SW_CG0, true, 0U),
+	IDLE_CG(0x00000800, VPPSYS0_SW_CG0, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00000800, VPPSYS0_SW_CG1, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00000800, VPPSYS0_SW_CG2, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00001000, VPPSYS1_SW_CG0, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00001000, VPPSYS1_SW_CG1, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00002000, VDOSYS0_SW_CG0, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00002000, VDOSYS0_SW_CG1, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00004000, VDOSYS1_SW_CG0, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00004000, VDOSYS1_SW_CG1, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00004000, VDOSYS1_SW_CG2, true, (CLK_CHECK|CLKMUX_DISP)),
+	IDLE_CG(0x00000080, TOP_SW_I2C_CG, true, (CLK_CHECK|CLKMUX_DISP)),
+};
+
+/***********************************************************
+ * Check pll idle condition
+ ***********************************************************/
+#define PLL_MFGPLL	MT_LP_TZ_APMIXEDSYS(0x340)
+#define PLL_MMPLL	MT_LP_TZ_APMIXEDSYS(0x0E0)
+#define PLL_UNIVPLL	MT_LP_TZ_APMIXEDSYS(0x1F0)
+#define PLL_MSDCPLL	MT_LP_TZ_APMIXEDSYS(0x710)
+#define PLL_TVDPLL	MT_LP_TZ_APMIXEDSYS(0x380)
+
+unsigned int mt_spm_cond_check(int state_id,
+			       const struct mt_spm_cond_tables *src,
+			       const struct mt_spm_cond_tables *dest,
+			       struct mt_spm_cond_tables *res)
+{
+	unsigned int blocked = 0U, i;
+	bool is_system_suspend = IS_PLAT_SUSPEND_ID(state_id);
+
+	if ((src == NULL) || (dest == NULL)) {
+		return SPM_COND_CHECK_FAIL;
+	}
+
+	for (i = 0U; i < PLAT_SPM_COND_MAX; i++) {
+		if (res != NULL) {
+			res->table_cg[i] =
+				(src->table_cg[i] & dest->table_cg[i]);
+
+			if (is_system_suspend && (res->table_cg[i] != 0U)) {
+				INFO("suspend: %s block[%u](0x%lx) = 0x%08x\n",
+				     dest->name, i, idle_cg_info[i].addr,
+				     res->table_cg[i]);
+			}
+
+			if (res->table_cg[i] != 0U) {
+				blocked |= (1U << i);
+			}
+		} else if ((src->table_cg[i] & dest->table_cg[i]) != 0U) {
+			blocked |= (1U << i);
+			break;
+		}
+	}
+
+	if (res != NULL) {
+		res->table_pll = (src->table_pll & dest->table_pll);
+
+		if (res->table_pll != 0U) {
+			blocked |=
+				(res->table_pll << SPM_COND_BLOCKED_PLL_IDX) |
+				 SPM_COND_CHECK_BLOCKED_PLL;
+		}
+	} else if ((src->table_pll & dest->table_pll) != 0U) {
+		blocked |= SPM_COND_CHECK_BLOCKED_PLL;
+	}
+
+	if (is_system_suspend && (blocked != 0U)) {
+		INFO("suspend: %s blocked=0x%08x\n", dest->name, blocked);
+	}
+
+	return blocked;
+}
+
+#define IS_MT_SPM_PWR_OFF(mask)					\
+	(((mmio_read_32(SPM_PWR_STATUS) & mask) == 0U) &&	\
+	 ((mmio_read_32(SPM_PWR_STATUS_2ND) & mask) == 0U))
+
+int mt_spm_cond_update(struct mt_resource_constraint **con,
+		       int stateid, void *priv)
+{
+	int res;
+	uint32_t i;
+	struct mt_resource_constraint *const *rc;
+
+	/* read all cg state */
+	for (i = 0U; i < PLAT_SPM_COND_MAX; i++) {
+		spm_cond_t.table_cg[i] = 0U;
+
+		/* check mtcmos, if off set idle_value and clk to 0 disable */
+		if (IS_MT_SPM_PWR_OFF(idle_cg_info[i].subsys_mask)) {
+			continue;
+		}
+
+		/* check clkmux */
+		if (is_clkmux_pdn(idle_cg_info[i].clkmux_id)) {
+			continue;
+		}
+
+		spm_cond_t.table_cg[i] = idle_cg_info[i].bBitflip ?
+					 ~mmio_read_32(idle_cg_info[i].addr) :
+					 mmio_read_32(idle_cg_info[i].addr);
+	}
+
+	spm_cond_t.table_pll = 0U;
+	if ((mmio_read_32(PLL_MFGPLL) & 0x200) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MFGPLL;
+	}
+
+	if ((mmio_read_32(PLL_MMPLL) & 0x200) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MMPLL;
+	}
+
+	if ((mmio_read_32(PLL_UNIVPLL) & 0x200) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_UNIVPLL;
+	}
+
+	if ((mmio_read_32(PLL_MSDCPLL) & 0x200) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_MSDCPLL;
+	}
+
+	if ((mmio_read_32(PLL_TVDPLL) & 0x200) != 0U) {
+		spm_cond_t.table_pll |= PLL_BIT_TVDPLL;
+	}
+
+	spm_cond_t.priv = priv;
+	for (rc = con; *rc != NULL; rc++) {
+		if (((*rc)->update) == NULL) {
+			continue;
+		}
+
+		res = (*rc)->update(stateid, PLAT_RC_UPDATE_CONDITION,
+				    (void const *)&spm_cond_t);
+		if (res != MT_RM_STATUS_OK) {
+			break;
+		}
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.h
new file mode 100644
index 0000000..e471b55
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_cond.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONDIT_H
+#define MT_SPM_CONDIT_H
+
+#include <mt_lp_rm.h>
+
+enum PLAT_SPM_COND {
+	PLAT_SPM_COND_MTCMOS1 = 0,
+	PLAT_SPM_COND_CG_INFRA_0,
+	PLAT_SPM_COND_CG_INFRA_1,
+	PLAT_SPM_COND_CG_INFRA_2,
+	PLAT_SPM_COND_CG_INFRA_3,
+	PLAT_SPM_COND_CG_INFRA_4,
+	PLAT_SPM_COND_CG_PERI_SW_0,
+	PLAT_SPM_COND_CG_VPPSYS0_SW_CG_0,
+	PLAT_SPM_COND_CG_VPPSYS0_SW_CG_1,
+	PLAT_SPM_COND_CG_VPPSYS0_SW_CG_2,
+	PLAT_SPM_COND_CG_VPPSYS1_SW_CG_0,
+	PLAT_SPM_COND_CG_VPPSYS1_SW_CG_1,
+	PLAT_SPM_COND_CG_VDOSYS0_SW_CG_0,
+	PLAT_SPM_COND_CG_VDOSYS0_SW_CG_1,
+	PLAT_SPM_COND_CG_VDOSYS1_SW_CG_0,
+	PLAT_SPM_COND_CG_VDOSYS1_SW_CG_1,
+	PLAT_SPM_COND_CG_VDOSYS1_SW_CG_2,
+	PLAT_SPM_COND_CG_I2C_SW_CG,
+	PLAT_SPM_COND_MAX,
+};
+
+enum PLAT_SPM_COND_PLL {
+	PLAT_SPM_COND_PLL_UNIVPLL = 0,
+	PLAT_SPM_COND_PLL_MFGPLL,
+	PLAT_SPM_COND_PLL_MSDCPLL,
+	PLAT_SPM_COND_PLL_TVDPLL,
+	PLAT_SPM_COND_PLL_MMPLL,
+	PLAT_SPM_COND_PLL_MAX,
+};
+
+#define PLL_BIT_MFGPLL	BIT(PLAT_SPM_COND_PLL_MFGPLL)
+#define PLL_BIT_MMPLL	BIT(PLAT_SPM_COND_PLL_MMPLL)
+#define PLL_BIT_UNIVPLL	BIT(PLAT_SPM_COND_PLL_UNIVPLL)
+#define PLL_BIT_MSDCPLL	BIT(PLAT_SPM_COND_PLL_MSDCPLL)
+#define PLL_BIT_TVDPLL	BIT(PLAT_SPM_COND_PLL_TVDPLL)
+
+/* Definition about SPM_COND_CHECK_BLOCKED
+ * bit [00 ~ 17]: cg blocking index
+ * bit [18 ~ 29]: pll blocking index
+ * bit [30]     : pll blocking information
+ * bit [31]	: idle condition check fail
+ */
+#define SPM_COND_BLOCKED_CG_IDX		U(0)
+#define SPM_COND_BLOCKED_PLL_IDX	U(18)
+#define SPM_COND_CHECK_BLOCKED_PLL	BIT(30)
+#define SPM_COND_CHECK_FAIL		BIT(31)
+
+struct mt_spm_cond_tables {
+	char *name;
+	unsigned int table_cg[PLAT_SPM_COND_MAX];
+	unsigned int table_pll;
+	void *priv;
+};
+
+extern unsigned int mt_spm_cond_check(int state_id,
+				      const struct mt_spm_cond_tables *src,
+				      const struct mt_spm_cond_tables *dest,
+				      struct mt_spm_cond_tables *res);
+extern int mt_spm_cond_update(struct mt_resource_constraint **con,
+			      int stateid, void *priv);
+#endif /* MT_SPM_CONDIT_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.c
new file mode 100644
index 0000000..7f33408
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.c
@@ -0,0 +1,155 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_reg.h>
+#include <plat_mtk_lpm.h>
+#include <plat_pm.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+struct wake_status spm_wakesta; /* record last wakesta */
+
+static int go_to_spm_before_wfi(int state_id, unsigned int ext_opand,
+				struct spm_lp_scen *spm_lp,
+				unsigned int resource_req)
+{
+	int ret = 0;
+	struct pwr_ctrl *pwrctrl;
+	uint32_t cpu = plat_my_core_pos();
+
+	pwrctrl = spm_lp->pwrctrl;
+
+	__spm_set_cpu_status(cpu);
+	__spm_set_power_control(pwrctrl);
+	__spm_set_wakeup_event(pwrctrl);
+	__spm_set_pcm_flags(pwrctrl);
+	__spm_src_req_update(pwrctrl, resource_req);
+
+	if ((ext_opand & MT_SPM_EX_OP_SET_WDT) != 0U) {
+		__spm_set_pcm_wdt(1);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_SRCLKEN_RC_BBLPM) != 0U) {
+		__spm_xo_soc_bblpm(1);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_HW_S1_DETECT) != 0U) {
+		spm_hw_s1_state_monitor_resume();
+	}
+
+	/* Disable auto resume by PCM in system suspend stage */
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		__spm_disable_pcm_timer();
+		__spm_set_pcm_wdt(0);
+	}
+
+	__spm_send_cpu_wakeup_event();
+
+	INFO("cpu%d: wakesrc = 0x%x, settle = 0x%x, sec = %u\n",
+	     cpu, pwrctrl->wake_src, mmio_read_32(SPM_CLK_SETTLE),
+	     mmio_read_32(PCM_TIMER_VAL) / 32768);
+	INFO("sw_flag = 0x%x 0x%x, req = 0x%x, pwr = 0x%x 0x%x\n",
+	     pwrctrl->pcm_flags, pwrctrl->pcm_flags1,
+	     mmio_read_32(SPM_SRC_REQ), mmio_read_32(PWR_STATUS),
+	     mmio_read_32(PWR_STATUS_2ND));
+	INFO("cpu_pwr = 0x%x 0x%x\n", mmio_read_32(CPU_PWR_STATUS),
+	     mmio_read_32(CPU_PWR_STATUS_2ND));
+
+	return ret;
+}
+
+static void go_to_spm_after_wfi(int state_id, unsigned int ext_opand,
+				struct spm_lp_scen *spm_lp,
+				struct wake_status **status)
+{
+	unsigned int ext_status = 0U;
+
+	/* system watchdog will be resumed at kernel stage */
+	if ((ext_opand & MT_SPM_EX_OP_SET_WDT) != 0U) {
+		__spm_set_pcm_wdt(0);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_SRCLKEN_RC_BBLPM) != 0U) {
+		__spm_xo_soc_bblpm(0);
+	}
+
+	if ((ext_opand & MT_SPM_EX_OP_HW_S1_DETECT) != 0U) {
+		spm_hw_s1_state_monitor_pause(&ext_status);
+	}
+
+	__spm_ext_int_wakeup_req_clr();
+	__spm_get_wakeup_status(&spm_wakesta, ext_status);
+
+	if (status != NULL) {
+		*status = &spm_wakesta;
+	}
+
+	__spm_clean_after_wakeup();
+
+	if (IS_PLAT_SUSPEND_ID(state_id)) {
+		__spm_output_wake_reason(state_id, &spm_wakesta);
+	}
+}
+
+int spm_conservation(int state_id, unsigned int ext_opand,
+		     struct spm_lp_scen *spm_lp, unsigned int resource_req)
+{
+	if (spm_lp == NULL) {
+		return -1;
+	}
+
+	spm_lock_get();
+	go_to_spm_before_wfi(state_id, ext_opand, spm_lp, resource_req);
+	spm_lock_release();
+
+	return 0;
+}
+
+void spm_conservation_finish(int state_id, unsigned int ext_opand,
+			     struct spm_lp_scen *spm_lp,
+			     struct wake_status **status)
+{
+	spm_lock_get();
+	go_to_spm_after_wfi(state_id, ext_opand, spm_lp, status);
+	spm_lock_release();
+}
+
+int spm_conservation_get_result(struct wake_status **res)
+{
+	if (res == NULL) {
+		return -1;
+	}
+
+	*res = &spm_wakesta;
+
+	return 0;
+}
+
+#define GPIO_BANK	(GPIO_BASE + 0x6F0)
+#define TRAP_UFS_FIRST	BIT(11) /* bit 11, 0: UFS, 1: eMMC */
+
+void spm_conservation_pwrctrl_init(struct pwr_ctrl *pwrctrl)
+{
+	if (pwrctrl == NULL) {
+		return;
+	}
+
+	/* For ufs, emmc storage type */
+	if ((mmio_read_32(GPIO_BANK) & TRAP_UFS_FIRST) != 0U) {
+		/* If eMMC is used, mask UFS req */
+		pwrctrl->reg_ufs_srcclkena_mask_b = 0;
+		pwrctrl->reg_ufs_infra_req_mask_b = 0;
+		pwrctrl->reg_ufs_apsrc_req_mask_b = 0;
+		pwrctrl->reg_ufs_vrf18_req_mask_b = 0;
+		pwrctrl->reg_ufs_ddr_en_mask_b = 0;
+	}
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.h
new file mode 100644
index 0000000..aa627e7
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_conservation.h
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONSERVATION_H
+#define MT_SPM_CONSERVATION_H
+
+#include <mt_spm_internal.h>
+
+extern int spm_conservation(int state_id, unsigned int ext_opand,
+			    struct spm_lp_scen *spm_lp,
+			    unsigned int resource_req);
+extern void spm_conservation_finish(int state_id, unsigned int ext_opand,
+				    struct spm_lp_scen *spm_lp,
+				    struct wake_status **status);
+extern int spm_conservation_get_result(struct wake_status **res);
+extern void spm_conservation_pwrctrl_init(struct pwr_ctrl *pwrctrl);
+#endif /* MT_SPM_CONSERVATION_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_constraint.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_constraint.h
new file mode 100644
index 0000000..944c227
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_constraint.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_CONSTRAINT_H
+#define MT_SPM_CONSTRAINT_H
+
+#include <mt_lp_rm.h>
+
+#define MT_RM_CONSTRAINT_ALLOW_CPU_BUCK_OFF	(1U << 0)
+#define MT_RM_CONSTRAINT_ALLOW_DRAM_S0		(1U << 1)
+#define MT_RM_CONSTRAINT_ALLOW_DRAM_S1		(1U << 2)
+#define MT_RM_CONSTRAINT_ALLOW_VCORE_LP		(1U << 3)
+#define MT_RM_CONSTRAINT_ALLOW_INFRA_PDN	(1U << 4)
+#define MT_RM_CONSTRAINT_ALLOW_BUS26M_OFF	(1U << 5)
+#define MT_RM_CONSTRAINT_ALLOW_AP_SUSPEND	(1U << 6)
+#define MT_RM_CONSTRAINT_ALLOW_BBLPM		(1U << 7)
+#define MT_RM_CONSTRAINT_ALLOW_XO_UFS		(1U << 8)
+#define MT_RM_CONSTRAINT_ALLOW_GPS_STATE	(1U << 9)
+#define MT_RM_CONSTRAINT_ALLOW_LVTS_STATE	(1U << 10)
+
+#define MT_SPM_RC_INVALID		0x0
+#define MT_SPM_RC_VALID_SW		(1U << 0)
+#define MT_SPM_RC_VALID_FW		(1U << 1)
+#define MT_SPM_RC_VALID_RESIDNECY	(1U << 2)
+#define MT_SPM_RC_VALID_COND_CHECK	(1U << 3)
+#define MT_SPM_RC_VALID_COND_LATCH	(1U << 4)
+#define MT_SPM_RC_VALID_UFS_H8		(1U << 5)
+#define MT_SPM_RC_VALID_FLIGHTMODE	(1U << 6)
+#define MT_SPM_RC_VALID_XSOC_BBLPM	(1U << 7)
+#define MT_SPM_RC_VALID_TRACE_EVENT	(1U << 8)
+
+#define MT_SPM_RC_VALID	(MT_SPM_RC_VALID_SW)
+
+#define IS_MT_RM_RC_READY(status)	\
+	((status & MT_SPM_RC_VALID) == MT_SPM_RC_VALID)
+
+#define MT_SPM_RC_BBLPM_MODE		\
+	(MT_SPM_RC_VALID_UFS_H8 |	\
+	 MT_SPM_RC_VALID_FLIGHTMODE |	\
+	 MT_SPM_RC_VALID_XSOC_BBLPM)
+
+#define IS_MT_SPM_RC_BBLPM_MODE(st)	\
+	((st & (MT_SPM_RC_BBLPM_MODE)) == MT_SPM_RC_BBLPM_MODE)
+
+struct constraint_status {
+	uint16_t id;
+	uint16_t valid;
+	uint32_t cond_block;
+	uint32_t enter_cnt;
+	struct mt_spm_cond_tables *cond_res;
+};
+
+enum MT_SPM_RM_RC_TYPE {
+	MT_RM_CONSTRAINT_ID_BUS26M,
+	MT_RM_CONSTRAINT_ID_SYSPLL,
+	MT_RM_CONSTRAINT_ID_DRAM,
+	MT_RM_CONSTRAINT_ID_CPU_BUCK_LDO,
+	MT_RM_CONSTRAINT_ID_ALL,
+};
+#endif /* MT_SPM_CONSTRAINT_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.c
new file mode 100644
index 0000000..4bafe95
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.c
@@ -0,0 +1,346 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_idle.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <plat_pm.h>
+
+#define __WAKE_SRC_FOR_IDLE_COMMON__	\
+	(R12_PCM_TIMER |		\
+	 R12_KP_IRQ_B |			\
+	 R12_APWDT_EVENT_B |		\
+	 R12_APXGPT1_EVENT_B |		\
+	 R12_CONN2AP_SPM_WAKEUP_B |	\
+	 R12_EINT_EVENT_B |		\
+	 R12_CONN_WDT_IRQ_B |		\
+	 R12_CCIF0_EVENT_B |		\
+	 R12_SSPM2SPM_WAKEUP_B |	\
+	 R12_SCP2SPM_WAKEUP_B |		\
+	 R12_ADSP2SPM_WAKEUP_B |	\
+	 R12_USBX_CDSC_B |		\
+	 R12_USBX_POWERDWN_B |		\
+	 R12_SYS_TIMER_EVENT_B |	\
+	 R12_EINT_EVENT_SECURE_B |	\
+	 R12_AFE_IRQ_MCU_B |		\
+	 R12_SYS_CIRQ_IRQ_B |		\
+	 R12_MD2AP_PEER_EVENT_B |	\
+	 R12_MD1_WDT_B |		\
+	 R12_CLDMA_EVENT_B |		\
+	 R12_REG_CPU_WAKEUP |		\
+	 R12_APUSYS_WAKE_HOST_B)
+
+#if defined(CFG_MICROTRUST_TEE_SUPPORT)
+#define WAKE_SRC_FOR_IDLE (__WAKE_SRC_FOR_IDLE_COMMON__)
+#else
+#define WAKE_SRC_FOR_IDLE		\
+	(__WAKE_SRC_FOR_IDLE_COMMON__ |	\
+	  R12_SEJ_EVENT_B)
+#endif
+
+static struct pwr_ctrl idle_spm_pwr = {
+	.wake_src = WAKE_SRC_FOR_IDLE,
+
+	/* SPM_AP_STANDBY_CON */
+	/* [0] */
+	.reg_wfi_op = 0,
+	/* [1] */
+	.reg_wfi_type = 0,
+	/* [2] */
+	.reg_mp0_cputop_idle_mask = 0,
+	/* [3] */
+	.reg_mp1_cputop_idle_mask = 0,
+	/* [4] */
+	.reg_mcusys_idle_mask = 0,
+	/* [25] */
+	.reg_md_apsrc_1_sel = 0,
+	/* [26] */
+	.reg_md_apsrc_0_sel = 0,
+	/* [29] */
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC_REQ */
+	/* [0] */
+	.reg_spm_apsrc_req = 0,
+	/* [1] */
+	.reg_spm_f26m_req = 1,
+	/* [3] */
+	.reg_spm_infra_req = 1,
+	/* [4] */
+	.reg_spm_vrf18_req = 0,
+	/* [7] FIXME: default disable HW Auto S1 */
+	.reg_spm_ddr_en_req = 1,
+	/* [8] */
+	.reg_spm_dvfs_req = 0,
+	/* [9] */
+	.reg_spm_sw_mailbox_req = 0,
+	/* [10] */
+	.reg_spm_sspm_mailbox_req = 0,
+	/* [11] */
+	.reg_spm_adsp_mailbox_req = 0,
+	/* [12] */
+	.reg_spm_scp_mailbox_req = 0,
+
+
+	/* SPM_SRC_MASK */
+	/* [0] */
+	.reg_sspm_srcclkena_0_mask_b = 1,
+	/* [1] */
+	.reg_sspm_infra_req_0_mask_b = 1,
+	/* [2] */
+	.reg_sspm_apsrc_req_0_mask_b = 1,
+	/* [3] */
+	.reg_sspm_vrf18_req_0_mask_b = 1,
+	/* [4] */
+	.reg_sspm_ddr_en_0_mask_b = 1,
+	/* [5] */
+	.reg_scp_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_scp_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_scp_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_scp_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_scp_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_apu_srcclkena_mask_b = 1,
+	/* [16] */
+	.reg_apu_infra_req_mask_b = 1,
+	/* [17] */
+	.reg_apu_apsrc_req_mask_b = 1,
+	/* [18] */
+	.reg_apu_vrf18_req_mask_b = 1,
+	/* [19] */
+	.reg_apu_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_cpueb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_cpueb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_cpueb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_cpueb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_cpueb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	/* [26] */
+	.reg_bak_psri_infra_req_mask_b = 0,
+	/* [27] */
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	/* [28] */
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	/* [29] */
+	.reg_bak_psri_ddr_en_mask_b = 0,
+
+	/* SPM_SRC2_MASK */
+	/* [0] */
+	.reg_msdc0_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_msdc0_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_msdc0_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_msdc1_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_msdc1_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_msdc1_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_msdc2_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_msdc2_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_msdc2_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_ufs_srcclkena_mask_b = 1,
+	/* [16] */
+	.reg_ufs_infra_req_mask_b = 1,
+	/* [17] */
+	.reg_ufs_apsrc_req_mask_b = 1,
+	/* [18] */
+	.reg_ufs_vrf18_req_mask_b = 1,
+	/* [19] */
+	.reg_ufs_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_usb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_usb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_usb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_usb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_usb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_pextp_p0_srcclkena_mask_b = 1,
+	/* [26] */
+	.reg_pextp_p0_infra_req_mask_b = 1,
+	/* [27] */
+	.reg_pextp_p0_apsrc_req_mask_b = 1,
+	/* [28] */
+	.reg_pextp_p0_vrf18_req_mask_b = 1,
+	/* [29] */
+	.reg_pextp_p0_ddr_en_mask_b = 1,
+
+	/* SPM_SRC3_MASK */
+	/* [0] */
+	.reg_pextp_p1_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_pextp_p1_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_pextp_p1_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_pextp_p1_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_pextp_p1_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_gce0_infra_req_mask_b = 1,
+	/* [6] */
+	.reg_gce0_apsrc_req_mask_b = 1,
+	/* [7] */
+	.reg_gce0_vrf18_req_mask_b = 1,
+	/* [8] */
+	.reg_gce0_ddr_en_mask_b = 1,
+	/* [9] */
+	.reg_gce1_infra_req_mask_b = 1,
+	/* [10] */
+	.reg_gce1_apsrc_req_mask_b = 1,
+	/* [11] */
+	.reg_gce1_vrf18_req_mask_b = 1,
+	/* [12] */
+	.reg_gce1_ddr_en_mask_b = 1,
+	/* [13] */
+	.reg_spm_srcclkena_reserved_mask_b = 1,
+	/* [14] */
+	.reg_spm_infra_req_reserved_mask_b = 1,
+	/* [15] */
+	.reg_spm_apsrc_req_reserved_mask_b = 1,
+	/* [16] */
+	.reg_spm_vrf18_req_reserved_mask_b = 1,
+	/* [17] */
+	.reg_spm_ddr_en_reserved_mask_b = 1,
+	/* [18] */
+	.reg_disp0_apsrc_req_mask_b = 1,
+	/* [19] */
+	.reg_disp0_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_disp1_apsrc_req_mask_b = 1,
+	/* [21] */
+	.reg_disp1_ddr_en_mask_b = 1,
+	/* [22] */
+	.reg_disp2_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_disp2_ddr_en_mask_b = 1,
+	/* [24] */
+	.reg_disp3_apsrc_req_mask_b = 1,
+	/* [25] */
+	.reg_disp3_ddr_en_mask_b = 1,
+	/* [26] */
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	/* [27] */
+	.reg_infrasys_ddr_en_mask_b = 1,
+
+	/* [28] */
+	.reg_cg_check_srcclkena_mask_b = 1,
+	/* [29] */
+	.reg_cg_check_apsrc_req_mask_b = 1,
+	/* [30] */
+	.reg_cg_check_vrf18_req_mask_b = 1,
+	/* [31] */
+	.reg_cg_check_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	/* [8:0] */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x17,
+	/* [17:9] */
+	.reg_mcusys_merge_ddr_en_mask_b = 0x17,
+	/* [19:18] */
+	.reg_dramc_md32_infra_req_mask_b = 0,
+	/* [21:20] */
+	.reg_dramc_md32_vrf18_req_mask_b = 0,
+	/* [23:22] */
+	.reg_dramc_md32_ddr_en_mask_b = 0,
+	/* [24] */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK2 */
+	/* [3:0] */
+	.reg_sc_sw2spm_wakeup_mask_b = 0,
+	/* [4] */
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	/* [8:5] */
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	/* [9] */
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	/* [10] */
+	.reg_csyspwrup_ack_mask = 0,
+	/* [11] */
+	.reg_csyspwrup_req_mask = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	/* [31:0] */
+	.reg_wakeup_event_mask = 0xC1282203,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	/* [31:0] */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+};
+
+struct spm_lp_scen idle_spm_lp = {
+	.pwrctrl = &idle_spm_pwr,
+};
+
+int mt_spm_idle_generic_enter(int state_id, unsigned int ext_opand,
+			      spm_idle_conduct fn)
+{
+	unsigned int src_req = 0;
+
+	if (fn != NULL) {
+		fn(&idle_spm_lp, &src_req);
+	}
+
+	return spm_conservation(state_id, ext_opand, &idle_spm_lp, src_req);
+}
+void mt_spm_idle_generic_resume(int state_id, unsigned int ext_opand,
+				struct wake_status **status)
+{
+	spm_conservation_finish(state_id, ext_opand, &idle_spm_lp, status);
+}
+
+void mt_spm_idle_generic_init(void)
+{
+	spm_conservation_pwrctrl_init(idle_spm_lp.pwrctrl);
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.h
new file mode 100644
index 0000000..7f6fb0c
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_idle.h
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_IDLE_H
+#define MT_SPM_IDLE_H
+
+typedef void (*spm_idle_conduct)(struct spm_lp_scen *spm_lp,
+				 unsigned int *resource_req);
+int mt_spm_idle_generic_enter(int state_id, unsigned int ext_opand,
+			      spm_idle_conduct fn);
+void mt_spm_idle_generic_resume(int state_id, unsigned int ext_opand,
+				struct wake_status **status);
+void mt_spm_idle_generic_init(void);
+#endif /* MT_SPM_IDLE_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.c
new file mode 100644
index 0000000..2f460e6
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.c
@@ -0,0 +1,543 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <assert.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <platform_def.h>
+#include <plat_pm.h>
+
+/**************************************
+ * Define and Declare
+ **************************************/
+#define ROOT_CORE_ADDR_OFFSET			0x20000000
+#define SPM_WAKEUP_EVENT_MASK_CLEAN_MASK	0xefffffff
+#define	SPM_INIT_DONE_US			20
+
+static unsigned int mt_spm_bblpm_cnt;
+
+const char *wakeup_src_str[32] = {
+	[0] = "R12_PCM_TIMER",
+	[1] = "R12_RESERVED_DEBUG_B",
+	[2] = "R12_KP_IRQ_B",
+	[3] = "R12_APWDT_EVENT_B",
+	[4] = "R12_APXGPT1_EVENT_B",
+	[5] = "R12_MSDC_WAKEUP_B",
+	[6] = "R12_EINT_EVENT_B",
+	[7] = "R12_IRRX_WAKEUP_B",
+	[8] = "R12_SBD_INTR_WAKEUP_B",
+	[9] = "R12_RESERVE0",
+	[10] = "R12_SC_SSPM2SPM_WAKEUP_B",
+	[11] = "R12_SC_SCP2SPM_WAKEUP_B",
+	[12] = "R12_SC_ADSP2SPM_WAKEUP_B",
+	[13] = "R12_WDT_WAKEUP_B",
+	[14] = "R12_USB_U2_B",
+	[15] = "R12_USB_TOP_B",
+	[16] = "R12_SYS_TIMER_EVENT_B",
+	[17] = "R12_EINT_EVENT_SECURE_B",
+	[18] = "R12_ECE_INT_HDMI_B",
+	[19] = "R12_RESERVE1",
+	[20] = "R12_AFE_IRQ_MCU_B",
+	[21] = "R12_THERM_CTRL_EVENT_B",
+	[22] = "R12_SCP_CIRQ_IRQ_B",
+	[23] = "R12_NNA2INFRA_WAKEUP_B",
+	[24] = "R12_CSYSPWREQ_B",
+	[25] = "R12_RESERVE2",
+	[26] = "R12_PCIE_WAKEUPEVENT_B",
+	[27] = "R12_SEJ_EVENT_B",
+	[28] = "R12_SPM_CPU_WAKEUPEVENT_B",
+	[29] = "R12_APUSYS",
+	[30] = "R12_RESERVE3",
+	[31] = "R12_RESERVE4",
+};
+
+/**************************************
+ * Function and API
+ **************************************/
+
+wake_reason_t __spm_output_wake_reason(int state_id,
+				       const struct wake_status *wakesta)
+{
+	uint32_t i, bk_vtcxo_dur, spm_26m_off_pct = 0U;
+	wake_reason_t wr = WR_UNKNOWN;
+
+	if (wakesta == NULL) {
+		return WR_UNKNOWN;
+	}
+
+	if (wakesta->abort != 0U) {
+		ERROR("spmfw flow is aborted: 0x%x, timer_out = %u\n",
+		      wakesta->abort, wakesta->timer_out);
+	} else {
+		for (i = 0U; i < 32U; i++) {
+			if ((wakesta->r12 & (1U << i)) != 0U) {
+				INFO("wake up by %s, timer_out = %u\n",
+				     wakeup_src_str[i], wakesta->timer_out);
+				wr = WR_WAKE_SRC;
+				break;
+			}
+		}
+	}
+
+	INFO("r12 = 0x%x, r12_ext = 0x%x, r13 = 0x%x, debug_flag = 0x%x 0x%x\n",
+	     wakesta->r12, wakesta->r12_ext, wakesta->r13, wakesta->debug_flag,
+	     wakesta->debug_flag1);
+	INFO("raw_sta = 0x%x 0x%x 0x%x, idle_sta = 0x%x, cg_check_sta = 0x%x\n",
+	     wakesta->raw_sta, wakesta->md32pcm_wakeup_sta,
+	     wakesta->md32pcm_event_sta, wakesta->idle_sta,
+	     wakesta->cg_check_sta);
+	INFO("req_sta = 0x%x 0x%x 0x%x 0x%x 0x%x, isr = 0x%x\n",
+	     wakesta->req_sta0, wakesta->req_sta1, wakesta->req_sta2,
+	     wakesta->req_sta3, wakesta->req_sta4, wakesta->isr);
+	INFO("rt_req_sta0 = 0x%x, rt_req_sta1 = 0x%x, rt_req_sta2 = 0x%x\n",
+	     wakesta->rt_req_sta0, wakesta->rt_req_sta1, wakesta->rt_req_sta2);
+	INFO("rt_req_sta3 = 0x%x, dram_sw_con_3 = 0x%x, raw_ext_sta = 0x%x\n",
+	     wakesta->rt_req_sta3, wakesta->rt_req_sta4, wakesta->raw_ext_sta);
+	INFO("wake_misc = 0x%x, pcm_flag = 0x%x 0x%x 0x%x 0x%x, req = 0x%x\n",
+	     wakesta->wake_misc, wakesta->sw_flag0, wakesta->sw_flag1,
+	     wakesta->b_sw_flag0, wakesta->b_sw_flag1, wakesta->src_req);
+	INFO("clk_settle = 0x%x, wlk_cntcv_l = 0x%x, wlk_cntcv_h = 0x%x\n",
+	     wakesta->clk_settle, mmio_read_32(SYS_TIMER_VALUE_L),
+	     mmio_read_32(SYS_TIMER_VALUE_H));
+
+	if (wakesta->timer_out != 0U) {
+		bk_vtcxo_dur = mmio_read_32(SPM_BK_VTCXO_DUR);
+		spm_26m_off_pct = (100 * bk_vtcxo_dur) / wakesta->timer_out;
+		INFO("spm_26m_off_pct = %u\n", spm_26m_off_pct);
+	}
+
+	return wr;
+}
+
+void __spm_set_cpu_status(unsigned int cpu)
+{
+	uint32_t root_core_addr;
+
+	if (cpu < 8U) {
+		mmio_write_32(ROOT_CPUTOP_ADDR, (1U << cpu));
+		root_core_addr = SPM_CPU0_PWR_CON + (cpu * 0x4);
+		root_core_addr += ROOT_CORE_ADDR_OFFSET;
+		mmio_write_32(ROOT_CORE_ADDR, root_core_addr);
+		/* Notify MCUPM that preferred cpu wakeup */
+		mmio_write_32(MCUPM_MBOX_WAKEUP_CPU, cpu);
+	} else {
+		ERROR("%s: error cpu number %d\n", __func__, cpu);
+	}
+}
+
+void __spm_src_req_update(const struct pwr_ctrl *pwrctrl,
+			  unsigned int resource_usage)
+{
+	uint8_t apsrc_req = ((resource_usage & MT_SPM_DRAM_S0) != 0U) ?
+			    1 : pwrctrl->reg_spm_apsrc_req;
+	uint8_t ddr_en_req = ((resource_usage & MT_SPM_DRAM_S1) != 0U) ?
+			     1 : pwrctrl->reg_spm_ddr_en_req;
+	uint8_t vrf18_req = ((resource_usage & MT_SPM_SYSPLL) != 0U) ?
+			    1 : pwrctrl->reg_spm_vrf18_req;
+	uint8_t infra_req = ((resource_usage & MT_SPM_INFRA) != 0U) ?
+			    1 : pwrctrl->reg_spm_infra_req;
+	uint8_t f26m_req  = ((resource_usage &
+			      (MT_SPM_26M | MT_SPM_XO_FPM)) != 0U) ?
+			    1 : pwrctrl->reg_spm_f26m_req;
+
+	mmio_write_32(SPM_SRC_REQ,
+		      ((apsrc_req & 0x1) << 0) |
+		      ((f26m_req & 0x1) << 1) |
+		      ((infra_req & 0x1) << 3) |
+		      ((vrf18_req & 0x1) << 4) |
+		      ((ddr_en_req & 0x1) << 7) |
+		      ((pwrctrl->reg_spm_dvfs_req & 0x1) << 8) |
+		      ((pwrctrl->reg_spm_sw_mailbox_req & 0x1) << 9) |
+		      ((pwrctrl->reg_spm_sspm_mailbox_req & 0x1) << 10) |
+		      ((pwrctrl->reg_spm_adsp_mailbox_req & 0x1) << 11) |
+		      ((pwrctrl->reg_spm_scp_mailbox_req & 0x1) << 12));
+}
+
+void __spm_set_power_control(const struct pwr_ctrl *pwrctrl)
+{
+	/* Auto-gen Start */
+
+	/* SPM_AP_STANDBY_CON */
+	mmio_write_32(SPM_AP_STANDBY_CON,
+		((pwrctrl->reg_wfi_op & 0x1) << 0) |
+		((pwrctrl->reg_wfi_type & 0x1) << 1) |
+		((pwrctrl->reg_mp0_cputop_idle_mask & 0x1) << 2) |
+		((pwrctrl->reg_mp1_cputop_idle_mask & 0x1) << 3) |
+		((pwrctrl->reg_mcusys_idle_mask & 0x1) << 4) |
+		((pwrctrl->reg_md_apsrc_1_sel & 0x1) << 25) |
+		((pwrctrl->reg_md_apsrc_0_sel & 0x1) << 26) |
+		((pwrctrl->reg_conn_apsrc_sel & 0x1) << 29));
+
+	/* SPM_SRC_REQ */
+	mmio_write_32(SPM_SRC_REQ,
+		((pwrctrl->reg_spm_apsrc_req & 0x1) << 0) |
+		((pwrctrl->reg_spm_f26m_req & 0x1) << 1) |
+		((pwrctrl->reg_spm_infra_req & 0x1) << 3) |
+		((pwrctrl->reg_spm_vrf18_req & 0x1) << 4) |
+		((pwrctrl->reg_spm_ddr_en_req & 0x1) << 7) |
+		((pwrctrl->reg_spm_dvfs_req & 0x1) << 8) |
+		((pwrctrl->reg_spm_sw_mailbox_req & 0x1) << 9) |
+		((pwrctrl->reg_spm_sspm_mailbox_req & 0x1) << 10) |
+		((pwrctrl->reg_spm_adsp_mailbox_req & 0x1) << 11) |
+		((pwrctrl->reg_spm_scp_mailbox_req & 0x1) << 12));
+
+	/* SPM_SRC_MASK */
+	mmio_write_32(SPM_SRC_MASK,
+		((pwrctrl->reg_sspm_srcclkena_0_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_sspm_infra_req_0_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_sspm_apsrc_req_0_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_sspm_vrf18_req_0_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_sspm_ddr_en_0_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_scp_srcclkena_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_scp_infra_req_mask_b & 0x1) << 6) |
+		((pwrctrl->reg_scp_apsrc_req_mask_b & 0x1) << 7) |
+		((pwrctrl->reg_scp_vrf18_req_mask_b & 0x1) << 8) |
+		((pwrctrl->reg_scp_ddr_en_mask_b & 0x1) << 9) |
+		((pwrctrl->reg_audio_dsp_srcclkena_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_audio_dsp_infra_req_mask_b & 0x1) << 11) |
+		((pwrctrl->reg_audio_dsp_apsrc_req_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_audio_dsp_vrf18_req_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_audio_dsp_ddr_en_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_apu_srcclkena_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_apu_infra_req_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_apu_apsrc_req_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_apu_vrf18_req_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_apu_ddr_en_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_cpueb_srcclkena_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_cpueb_infra_req_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_cpueb_apsrc_req_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_cpueb_vrf18_req_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_cpueb_ddr_en_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_bak_psri_srcclkena_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_bak_psri_infra_req_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_bak_psri_apsrc_req_mask_b & 0x1) << 27) |
+		((pwrctrl->reg_bak_psri_vrf18_req_mask_b & 0x1) << 28) |
+		((pwrctrl->reg_bak_psri_ddr_en_mask_b & 0x1) << 29));
+
+	/* SPM_SRC2_MASK */
+	mmio_write_32(SPM_SRC2_MASK,
+		((pwrctrl->reg_msdc0_srcclkena_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_msdc0_infra_req_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_msdc0_apsrc_req_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_msdc0_vrf18_req_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_msdc0_ddr_en_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_msdc1_srcclkena_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_msdc1_infra_req_mask_b & 0x1) << 6) |
+		((pwrctrl->reg_msdc1_apsrc_req_mask_b & 0x1) << 7) |
+		((pwrctrl->reg_msdc1_vrf18_req_mask_b & 0x1) << 8) |
+		((pwrctrl->reg_msdc1_ddr_en_mask_b & 0x1) << 9) |
+		((pwrctrl->reg_msdc2_srcclkena_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_msdc2_infra_req_mask_b & 0x1) << 11) |
+		((pwrctrl->reg_msdc2_apsrc_req_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_msdc2_vrf18_req_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_msdc2_ddr_en_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_ufs_srcclkena_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_ufs_infra_req_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_ufs_apsrc_req_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_ufs_vrf18_req_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_ufs_ddr_en_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_usb_srcclkena_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_usb_infra_req_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_usb_apsrc_req_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_usb_vrf18_req_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_usb_ddr_en_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_pextp_p0_srcclkena_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_pextp_p0_infra_req_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_pextp_p0_apsrc_req_mask_b & 0x1) << 27) |
+		((pwrctrl->reg_pextp_p0_vrf18_req_mask_b & 0x1) << 28) |
+		((pwrctrl->reg_pextp_p0_ddr_en_mask_b & 0x1) << 29));
+
+	/* SPM_SRC3_MASK */
+	mmio_write_32(SPM_SRC3_MASK,
+		((pwrctrl->reg_pextp_p1_srcclkena_mask_b & 0x1) << 0) |
+		((pwrctrl->reg_pextp_p1_infra_req_mask_b & 0x1) << 1) |
+		((pwrctrl->reg_pextp_p1_apsrc_req_mask_b & 0x1) << 2) |
+		((pwrctrl->reg_pextp_p1_vrf18_req_mask_b & 0x1) << 3) |
+		((pwrctrl->reg_pextp_p1_ddr_en_mask_b & 0x1) << 4) |
+		((pwrctrl->reg_gce0_infra_req_mask_b & 0x1) << 5) |
+		((pwrctrl->reg_gce0_apsrc_req_mask_b & 0x1) << 6) |
+		((pwrctrl->reg_gce0_vrf18_req_mask_b & 0x1) << 7) |
+		((pwrctrl->reg_gce0_ddr_en_mask_b & 0x1) << 8) |
+		((pwrctrl->reg_gce1_infra_req_mask_b & 0x1) << 9) |
+		((pwrctrl->reg_gce1_apsrc_req_mask_b & 0x1) << 10) |
+		((pwrctrl->reg_gce1_vrf18_req_mask_b & 0x1) << 11) |
+		((pwrctrl->reg_gce1_ddr_en_mask_b & 0x1) << 12) |
+		((pwrctrl->reg_spm_srcclkena_reserved_mask_b & 0x1) << 13) |
+		((pwrctrl->reg_spm_infra_req_reserved_mask_b & 0x1) << 14) |
+		((pwrctrl->reg_spm_apsrc_req_reserved_mask_b & 0x1) << 15) |
+		((pwrctrl->reg_spm_vrf18_req_reserved_mask_b & 0x1) << 16) |
+		((pwrctrl->reg_spm_ddr_en_reserved_mask_b & 0x1) << 17) |
+		((pwrctrl->reg_disp0_ddr_en_mask_b & 0x1) << 18) |
+		((pwrctrl->reg_disp0_ddr_en_mask_b & 0x1) << 19) |
+		((pwrctrl->reg_disp1_apsrc_req_mask_b & 0x1) << 20) |
+		((pwrctrl->reg_disp1_ddr_en_mask_b & 0x1) << 21) |
+		((pwrctrl->reg_disp2_apsrc_req_mask_b & 0x1) << 22) |
+		((pwrctrl->reg_disp2_ddr_en_mask_b & 0x1) << 23) |
+		((pwrctrl->reg_disp3_apsrc_req_mask_b & 0x1) << 24) |
+		((pwrctrl->reg_disp3_ddr_en_mask_b & 0x1) << 25) |
+		((pwrctrl->reg_infrasys_apsrc_req_mask_b & 0x1) << 26) |
+		((pwrctrl->reg_infrasys_ddr_en_mask_b & 0x1) << 27));
+
+	/* Mask MCUSYS request since SOC HW would check it */
+	mmio_write_32(SPM_SRC4_MASK, 0x1fc0000);
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK,
+		((pwrctrl->reg_wakeup_event_mask & 0xffffffff) << 0));
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	mmio_write_32(SPM_WAKEUP_EVENT_EXT_MASK,
+		((pwrctrl->reg_ext_wakeup_event_mask & 0xffffffff) << 0));
+
+	/* Auto-gen End */
+}
+
+void __spm_disable_pcm_timer(void)
+{
+	mmio_clrsetbits_32(PCM_CON1, RG_PCM_TIMER_EN_LSB, SPM_REGWR_CFG_KEY);
+}
+
+void __spm_set_wakeup_event(const struct pwr_ctrl *pwrctrl)
+{
+	uint32_t val, mask;
+
+	/* toggle event counter clear */
+	mmio_setbits_32(PCM_CON1,
+			SPM_REGWR_CFG_KEY | SPM_EVENT_COUNTER_CLR_LSB);
+
+	/* toggle for reset SYS TIMER start point */
+	mmio_setbits_32(SYS_TIMER_CON, SYS_TIMER_START_EN_LSB);
+
+	if (pwrctrl->timer_val_cust == 0U) {
+		val = pwrctrl->timer_val;
+	} else {
+		val = pwrctrl->timer_val_cust;
+	}
+
+	mmio_write_32(PCM_TIMER_VAL, val);
+	mmio_setbits_32(PCM_CON1, SPM_REGWR_CFG_KEY | RG_PCM_TIMER_EN_LSB);
+
+	/* unmask AP wakeup source */
+	if (pwrctrl->wake_src_cust == 0U) {
+		mask = pwrctrl->wake_src;
+	} else {
+		mask = pwrctrl->wake_src_cust;
+	}
+
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK, ~mask);
+
+	/* unmask SPM ISR (keep TWAM setting) */
+	mmio_setbits_32(SPM_IRQ_MASK, ISRM_RET_IRQ_AUX);
+
+	/* toggle event counter clear */
+	mmio_clrsetbits_32(PCM_CON1, SPM_EVENT_COUNTER_CLR_LSB,
+			   SPM_REGWR_CFG_KEY);
+	/* toggle for reset SYS TIMER start point */
+	mmio_clrbits_32(SYS_TIMER_CON, SYS_TIMER_START_EN_LSB);
+}
+
+void __spm_set_pcm_flags(struct pwr_ctrl *pwrctrl)
+{
+	/* set PCM flags and data */
+	if (pwrctrl->pcm_flags_cust_clr != 0U) {
+		pwrctrl->pcm_flags &= ~pwrctrl->pcm_flags_cust_clr;
+	}
+
+	if (pwrctrl->pcm_flags_cust_set != 0U) {
+		pwrctrl->pcm_flags |= pwrctrl->pcm_flags_cust_set;
+	}
+
+	if (pwrctrl->pcm_flags1_cust_clr != 0U) {
+		pwrctrl->pcm_flags1 &= ~pwrctrl->pcm_flags1_cust_clr;
+	}
+
+	if (pwrctrl->pcm_flags1_cust_set != 0U) {
+		pwrctrl->pcm_flags1 |= pwrctrl->pcm_flags1_cust_set;
+	}
+
+	mmio_write_32(SPM_SW_FLAG_0, pwrctrl->pcm_flags);
+	mmio_write_32(SPM_SW_FLAG_1, pwrctrl->pcm_flags1);
+	mmio_write_32(SPM_SW_RSV_7, pwrctrl->pcm_flags);
+	mmio_write_32(SPM_SW_RSV_8, pwrctrl->pcm_flags1);
+}
+
+void __spm_get_wakeup_status(struct wake_status *wakesta,
+			     unsigned int ext_status)
+{
+	wakesta->tr.comm.r12 = mmio_read_32(SPM_BK_WAKE_EVENT);
+	wakesta->tr.comm.timer_out = mmio_read_32(SPM_BK_PCM_TIMER);
+	wakesta->tr.comm.r13 = mmio_read_32(PCM_REG13_DATA);
+	wakesta->tr.comm.req_sta0 = mmio_read_32(SRC_REQ_STA_0);
+	wakesta->tr.comm.req_sta1 = mmio_read_32(SRC_REQ_STA_1);
+	wakesta->tr.comm.req_sta2 = mmio_read_32(SRC_REQ_STA_2);
+	wakesta->tr.comm.req_sta3 = mmio_read_32(SRC_REQ_STA_3);
+	wakesta->tr.comm.req_sta4 = mmio_read_32(SRC_REQ_STA_4);
+	wakesta->tr.comm.debug_flag = mmio_read_32(PCM_WDT_LATCH_SPARE_0);
+	wakesta->tr.comm.debug_flag1 = mmio_read_32(PCM_WDT_LATCH_SPARE_1);
+
+	if ((ext_status & SPM_INTERNAL_STATUS_HW_S1) != 0U) {
+		wakesta->tr.comm.debug_flag |= (SPM_DBG_DEBUG_IDX_DDREN_WAKE |
+						SPM_DBG_DEBUG_IDX_DDREN_SLEEP);
+		mmio_write_32(PCM_WDT_LATCH_SPARE_0,
+			      wakesta->tr.comm.debug_flag);
+	}
+
+	wakesta->tr.comm.b_sw_flag0 = mmio_read_32(SPM_SW_RSV_7);
+	wakesta->tr.comm.b_sw_flag1 = mmio_read_32(SPM_SW_RSV_8);
+
+	/* record below spm info for debug */
+	wakesta->r12 = mmio_read_32(SPM_BK_WAKE_EVENT);
+	wakesta->r12_ext = mmio_read_32(SPM_WAKEUP_STA);
+	wakesta->raw_sta = mmio_read_32(SPM_WAKEUP_STA);
+	wakesta->raw_ext_sta = mmio_read_32(SPM_WAKEUP_EXT_STA);
+	wakesta->md32pcm_wakeup_sta = mmio_read_32(MD32PCM_WAKEUP_STA);
+	wakesta->md32pcm_event_sta = mmio_read_32(MD32PCM_EVENT_STA);
+	wakesta->src_req = mmio_read_32(SPM_SRC_REQ);
+
+	/* backup of SPM_WAKEUP_MISC */
+	wakesta->wake_misc = mmio_read_32(SPM_BK_WAKE_MISC);
+
+	/* get sleep time, backup of PCM_TIMER_OUT */
+	wakesta->timer_out = mmio_read_32(SPM_BK_PCM_TIMER);
+
+	/* get other SYS and co-clock status */
+	wakesta->r13 = mmio_read_32(PCM_REG13_DATA);
+	wakesta->idle_sta = mmio_read_32(SUBSYS_IDLE_STA);
+	wakesta->req_sta0 = mmio_read_32(SRC_REQ_STA_0);
+	wakesta->req_sta1 = mmio_read_32(SRC_REQ_STA_1);
+	wakesta->req_sta2 = mmio_read_32(SRC_REQ_STA_2);
+	wakesta->req_sta3 = mmio_read_32(SRC_REQ_STA_3);
+	wakesta->req_sta4 = mmio_read_32(SRC_REQ_STA_4);
+
+	/* get HW CG check status */
+	wakesta->cg_check_sta = mmio_read_32(SPM_CG_CHECK_STA);
+
+	/* get debug flag for PCM execution check */
+	wakesta->debug_flag = mmio_read_32(PCM_WDT_LATCH_SPARE_0);
+	wakesta->debug_flag1 = mmio_read_32(PCM_WDT_LATCH_SPARE_1);
+
+	/* get backup SW flag status */
+	wakesta->b_sw_flag0 = mmio_read_32(SPM_SW_RSV_7);
+	wakesta->b_sw_flag1 = mmio_read_32(SPM_SW_RSV_8);
+
+	wakesta->rt_req_sta0 = mmio_read_32(SPM_SW_RSV_2);
+	wakesta->rt_req_sta1 = mmio_read_32(SPM_SW_RSV_3);
+	wakesta->rt_req_sta2 = mmio_read_32(SPM_SW_RSV_4);
+	wakesta->rt_req_sta3 = mmio_read_32(SPM_SW_RSV_5);
+	wakesta->rt_req_sta4 = mmio_read_32(SPM_SW_RSV_6);
+
+	/* get ISR status */
+	wakesta->isr = mmio_read_32(SPM_IRQ_STA);
+
+	/* get SW flag status */
+	wakesta->sw_flag0 = mmio_read_32(SPM_SW_FLAG_0);
+	wakesta->sw_flag1 = mmio_read_32(SPM_SW_FLAG_1);
+
+	/* get CLK SETTLE */
+	wakesta->clk_settle = mmio_read_32(SPM_CLK_SETTLE);
+
+	/* check abort */
+	wakesta->abort = (wakesta->debug_flag & DEBUG_ABORT_MASK) |
+			 (wakesta->debug_flag1 & DEBUG_ABORT_MASK_1);
+}
+
+void __spm_clean_after_wakeup(void)
+{
+	mmio_write_32(SPM_BK_WAKE_EVENT,
+		      mmio_read_32(SPM_WAKEUP_STA) |
+		      mmio_read_32(SPM_BK_WAKE_EVENT));
+	mmio_write_32(SPM_CPU_WAKEUP_EVENT, 0);
+
+	/*
+	 * clean wakeup event raw status (for edge trigger event)
+	 * bit[28] for cpu wake up event
+	 */
+	mmio_write_32(SPM_WAKEUP_EVENT_MASK, SPM_WAKEUP_EVENT_MASK_CLEAN_MASK);
+
+	/* clean ISR status (except TWAM) */
+	mmio_setbits_32(SPM_IRQ_MASK, ISRM_ALL_EXC_TWAM);
+	mmio_write_32(SPM_IRQ_STA, ISRC_ALL_EXC_TWAM);
+	mmio_write_32(SPM_SWINT_CLR, PCM_SW_INT_ALL);
+}
+
+void __spm_set_pcm_wdt(int en)
+{
+	mmio_clrsetbits_32(PCM_CON1, RG_PCM_WDT_EN_LSB,
+			   SPM_REGWR_CFG_KEY);
+
+	if (en == 1) {
+		mmio_clrsetbits_32(PCM_CON1, RG_PCM_WDT_WAKE_LSB,
+				   SPM_REGWR_CFG_KEY);
+
+		if (mmio_read_32(PCM_TIMER_VAL) > PCM_TIMER_MAX) {
+			mmio_write_32(PCM_TIMER_VAL, PCM_TIMER_MAX);
+		}
+
+		mmio_write_32(PCM_WDT_VAL,
+			      mmio_read_32(PCM_TIMER_VAL) + PCM_WDT_TIMEOUT);
+		mmio_setbits_32(PCM_CON1,
+				SPM_REGWR_CFG_KEY | RG_PCM_WDT_EN_LSB);
+	}
+}
+
+void __spm_send_cpu_wakeup_event(void)
+{
+	/* SPM will clear SPM_CPU_WAKEUP_EVENT */
+	mmio_write_32(SPM_CPU_WAKEUP_EVENT, 1);
+}
+
+void __spm_ext_int_wakeup_req_clr(void)
+{
+	mmio_write_32(EXT_INT_WAKEUP_REQ_CLR, mmio_read_32(ROOT_CPUTOP_ADDR));
+
+	/* Clear spm2mcupm wakeup interrupt status */
+	mmio_write_32(SPM2CPUEB_CON, 0);
+}
+
+void __spm_xo_soc_bblpm(int en)
+{
+	if (en == 1) {
+		mmio_clrsetbits_32(RC_M00_SRCLKEN_CFG,
+				   RC_SW_SRCLKEN_FPM, RC_SW_SRCLKEN_RC);
+		assert(mt_spm_bblpm_cnt == 0);
+		mt_spm_bblpm_cnt += 1;
+	} else {
+		mmio_clrsetbits_32(RC_M00_SRCLKEN_CFG,
+				   RC_SW_SRCLKEN_RC, RC_SW_SRCLKEN_FPM);
+		mt_spm_bblpm_cnt -= 1;
+	}
+}
+
+void __spm_hw_s1_state_monitor(int en, unsigned int *status)
+{
+	unsigned int reg;
+
+	reg = mmio_read_32(SPM_ACK_CHK_CON_3);
+
+	if (en == 1) {
+		reg &= ~SPM_ACK_CHK_3_CON_CLR_ALL;
+		mmio_write_32(SPM_ACK_CHK_CON_3, reg);
+		reg |= SPM_ACK_CHK_3_CON_EN;
+		mmio_write_32(SPM_ACK_CHK_CON_3, reg);
+	} else {
+		if (((reg & SPM_ACK_CHK_3_CON_RESULT) != 0U) &&
+		    (status != NULL)) {
+			*status |= SPM_INTERNAL_STATUS_HW_S1;
+		}
+
+		mmio_clrsetbits_32(SPM_ACK_CHK_CON_3, SPM_ACK_CHK_3_CON_EN,
+				   SPM_ACK_CHK_3_CON_HW_MODE_TRIG |
+				   SPM_ACK_CHK_3_CON_CLR_ALL);
+	}
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.h
new file mode 100644
index 0000000..5ac7c91
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_internal.h
@@ -0,0 +1,583 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_INTERNAL_H
+#define MT_SPM_INTERNAL_H
+
+#include "mt_spm.h"
+
+/**************************************
+ * Config and Parameter
+ **************************************/
+#define POWER_ON_VAL0_DEF	0x0000F100
+#define POWER_ON_VAL1_DEF	0x80015860
+#define PCM_WDT_TIMEOUT		(30 * 32768)	/* 30s */
+#define PCM_TIMER_MAX		(0xffffffff - PCM_WDT_TIMEOUT)
+
+/**************************************
+ * Define and Declare
+ **************************************/
+/* PCM_PWR_IO_EN */
+#define PCM_PWRIO_EN_R0		(1U << 0)
+#define PCM_PWRIO_EN_R7		(1U << 7)
+#define PCM_RF_SYNC_R0		(1U << 16)
+#define PCM_RF_SYNC_R6		(1U << 22)
+#define PCM_RF_SYNC_R7		(1U << 23)
+
+/* SPM_SWINT */
+#define PCM_SW_INT0		(1U << 0)
+#define PCM_SW_INT1		(1U << 1)
+#define PCM_SW_INT2		(1U << 2)
+#define PCM_SW_INT3		(1U << 3)
+#define PCM_SW_INT4		(1U << 4)
+#define PCM_SW_INT5		(1U << 5)
+#define PCM_SW_INT6		(1U << 6)
+#define PCM_SW_INT7		(1U << 7)
+#define PCM_SW_INT8		(1U << 8)
+#define PCM_SW_INT9		(1U << 9)
+#define PCM_SW_INT_ALL		(PCM_SW_INT9 | PCM_SW_INT8 | PCM_SW_INT7 | \
+				 PCM_SW_INT6 | PCM_SW_INT5 | PCM_SW_INT4 | \
+				 PCM_SW_INT3 | PCM_SW_INT2 | PCM_SW_INT1 | \
+				 PCM_SW_INT0)
+
+/* SPM_AP_STANDBY_CON */
+#define WFI_OP_AND		1
+#define WFI_OP_OR		0
+
+/* SPM_IRQ_MASK */
+#define ISRM_TWAM		(1U << 2)
+#define ISRM_PCM_RETURN		(1U << 3)
+#define ISRM_RET_IRQ0		(1U << 8)
+#define ISRM_RET_IRQ1		(1U << 9)
+#define ISRM_RET_IRQ2		(1U << 10)
+#define ISRM_RET_IRQ3		(1U << 11)
+#define ISRM_RET_IRQ4		(1U << 12)
+#define ISRM_RET_IRQ5		(1U << 13)
+#define ISRM_RET_IRQ6		(1U << 14)
+#define ISRM_RET_IRQ7		(1U << 15)
+#define ISRM_RET_IRQ8		(1U << 16)
+#define ISRM_RET_IRQ9		(1U << 17)
+#define ISRM_RET_IRQ_AUX	((ISRM_RET_IRQ9) | (ISRM_RET_IRQ8) | \
+				 (ISRM_RET_IRQ7) | (ISRM_RET_IRQ6) | \
+				 (ISRM_RET_IRQ5) | (ISRM_RET_IRQ4) | \
+				 (ISRM_RET_IRQ3) | (ISRM_RET_IRQ2) | \
+				 (ISRM_RET_IRQ1))
+#define ISRM_ALL_EXC_TWAM	(ISRM_RET_IRQ_AUX)
+#define ISRM_ALL		(ISRM_ALL_EXC_TWAM | ISRM_TWAM)
+
+/* SPM_IRQ_STA */
+#define ISRS_TWAM		(1U << 2)
+#define ISRS_PCM_RETURN		(1U << 3)
+#define ISRC_TWAM		ISRS_TWAM
+#define ISRC_ALL_EXC_TWAM	ISRS_PCM_RETURN
+#define ISRC_ALL		(ISRC_ALL_EXC_TWAM | ISRC_TWAM)
+
+/* SPM_WAKEUP_MISC */
+#define WAKE_MISC_GIC_WAKEUP             0x3FF
+#define WAKE_MISC_DVFSRC_IRQ	         DVFSRC_IRQ_LSB
+#define WAKE_MISC_REG_CPU_WAKEUP         SPM_WAKEUP_MISC_REG_CPU_WAKEUP_LSB
+#define WAKE_MISC_PCM_TIMER_EVENT        PCM_TIMER_EVENT_LSB
+#define WAKE_MISC_PMIC_OUT_B		 ((1U << 19) | (1U << 20))
+#define WAKE_MISC_TWAM_IRQ_B             TWAM_IRQ_B_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET0        PMSR_IRQ_B_SET0_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET1        PMSR_IRQ_B_SET1_LSB
+#define WAKE_MISC_PMSR_IRQ_B_SET2        PMSR_IRQ_B_SET2_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_0   SPM_ACK_CHK_WAKEUP_0_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_1	 SPM_ACK_CHK_WAKEUP_1_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_2	 SPM_ACK_CHK_WAKEUP_2_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_3	 SPM_ACK_CHK_WAKEUP_3_LSB
+#define WAKE_MISC_SPM_ACK_CHK_WAKEUP_ALL SPM_ACK_CHK_WAKEUP_ALL_LSB
+#define WAKE_MISC_PMIC_IRQ_ACK           PMIC_IRQ_ACK_LSB
+#define WAKE_MISC_PMIC_SCP_IRQ           PMIC_SCP_IRQ_LSB
+
+/* ABORT MASK for DEBUG FOORTPRINT */
+#define DEBUG_ABORT_MASK				\
+	(SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_APSRC |	\
+	 SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_DDREN)
+
+#define DEBUG_ABORT_MASK_1					\
+	(SPM_DBG1_DEBUG_IDX_VRCXO_SLEEP_ABORT |			\
+	 SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_LOW_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_HIGH_ABORT |	\
+	 SPM_DBG1_DEBUG_IDX_EMI_SLP_IDLE_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_LOW_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_HIGH_ABORT |		\
+	 SPM_DBG1_DEBUG_IDX_SPM_DVFS_CMD_RDY_ABORT)
+
+#define MCUPM_MBOX_WAKEUP_CPU		0x0C55FD10
+
+struct pwr_ctrl {
+	uint32_t pcm_flags;
+	uint32_t pcm_flags_cust;
+	uint32_t pcm_flags_cust_set;
+	uint32_t pcm_flags_cust_clr;
+	uint32_t pcm_flags1;
+	uint32_t pcm_flags1_cust;
+	uint32_t pcm_flags1_cust_set;
+	uint32_t pcm_flags1_cust_clr;
+	uint32_t timer_val;
+	uint32_t timer_val_cust;
+	uint32_t timer_val_ramp_en;
+	uint32_t timer_val_ramp_en_sec;
+	uint32_t wake_src;
+	uint32_t wake_src_cust;
+	uint8_t wdt_disable;
+
+	/* SPM_AP_STANDBY_CON */
+	uint8_t reg_wfi_op;
+	uint8_t reg_wfi_type;
+	uint8_t reg_mp0_cputop_idle_mask;
+	uint8_t reg_mp1_cputop_idle_mask;
+	uint8_t reg_mcusys_idle_mask;
+	uint8_t reg_md_apsrc_1_sel;
+	uint8_t reg_md_apsrc_0_sel;
+	uint8_t reg_conn_apsrc_sel;
+
+	/* SPM_SRC_REQ */
+	uint8_t reg_spm_apsrc_req;
+	uint8_t reg_spm_f26m_req;
+	uint8_t reg_spm_infra_req;
+	uint8_t reg_spm_vrf18_req;
+	uint8_t reg_spm_ddr_en_req;
+	uint8_t reg_spm_dvfs_req;
+	uint8_t reg_spm_sw_mailbox_req;
+	uint8_t reg_spm_sspm_mailbox_req;
+	uint8_t reg_spm_adsp_mailbox_req;
+	uint8_t reg_spm_scp_mailbox_req;
+
+	/* SPM_SRC_MASK */
+	uint8_t reg_sspm_srcclkena_0_mask_b;
+	uint8_t reg_sspm_infra_req_0_mask_b;
+	uint8_t reg_sspm_apsrc_req_0_mask_b;
+	uint8_t reg_sspm_vrf18_req_0_mask_b;
+	uint8_t reg_sspm_ddr_en_0_mask_b;
+	uint8_t reg_scp_srcclkena_mask_b;
+	uint8_t reg_scp_infra_req_mask_b;
+	uint8_t reg_scp_apsrc_req_mask_b;
+	uint8_t reg_scp_vrf18_req_mask_b;
+	uint8_t reg_scp_ddr_en_mask_b;
+	uint8_t reg_audio_dsp_srcclkena_mask_b;
+	uint8_t reg_audio_dsp_infra_req_mask_b;
+	uint8_t reg_audio_dsp_apsrc_req_mask_b;
+	uint8_t reg_audio_dsp_vrf18_req_mask_b;
+	uint8_t reg_audio_dsp_ddr_en_mask_b;
+	uint8_t reg_apu_srcclkena_mask_b;
+	uint8_t reg_apu_infra_req_mask_b;
+	uint8_t reg_apu_apsrc_req_mask_b;
+	uint8_t reg_apu_vrf18_req_mask_b;
+	uint8_t reg_apu_ddr_en_mask_b;
+	uint8_t reg_cpueb_srcclkena_mask_b;
+	uint8_t reg_cpueb_infra_req_mask_b;
+	uint8_t reg_cpueb_apsrc_req_mask_b;
+	uint8_t reg_cpueb_vrf18_req_mask_b;
+	uint8_t reg_cpueb_ddr_en_mask_b;
+	uint8_t reg_bak_psri_srcclkena_mask_b;
+	uint8_t reg_bak_psri_infra_req_mask_b;
+	uint8_t reg_bak_psri_apsrc_req_mask_b;
+	uint8_t reg_bak_psri_vrf18_req_mask_b;
+	uint8_t reg_bak_psri_ddr_en_mask_b;
+
+	/* SPM_SRC2_MASK */
+	uint8_t reg_msdc0_srcclkena_mask_b;
+	uint8_t reg_msdc0_infra_req_mask_b;
+	uint8_t reg_msdc0_apsrc_req_mask_b;
+	uint8_t reg_msdc0_vrf18_req_mask_b;
+	uint8_t reg_msdc0_ddr_en_mask_b;
+	uint8_t reg_msdc1_srcclkena_mask_b;
+	uint8_t reg_msdc1_infra_req_mask_b;
+	uint8_t reg_msdc1_apsrc_req_mask_b;
+	uint8_t reg_msdc1_vrf18_req_mask_b;
+	uint8_t reg_msdc1_ddr_en_mask_b;
+	uint8_t reg_msdc2_srcclkena_mask_b;
+	uint8_t reg_msdc2_infra_req_mask_b;
+	uint8_t reg_msdc2_apsrc_req_mask_b;
+	uint8_t reg_msdc2_vrf18_req_mask_b;
+	uint8_t reg_msdc2_ddr_en_mask_b;
+	uint8_t reg_ufs_srcclkena_mask_b;
+	uint8_t reg_ufs_infra_req_mask_b;
+	uint8_t reg_ufs_apsrc_req_mask_b;
+	uint8_t reg_ufs_vrf18_req_mask_b;
+	uint8_t reg_ufs_ddr_en_mask_b;
+	uint8_t reg_usb_srcclkena_mask_b;
+	uint8_t reg_usb_infra_req_mask_b;
+	uint8_t reg_usb_apsrc_req_mask_b;
+	uint8_t reg_usb_vrf18_req_mask_b;
+	uint8_t reg_usb_ddr_en_mask_b;
+	uint8_t reg_pextp_p0_srcclkena_mask_b;
+	uint8_t reg_pextp_p0_infra_req_mask_b;
+	uint8_t reg_pextp_p0_apsrc_req_mask_b;
+	uint8_t reg_pextp_p0_vrf18_req_mask_b;
+	uint8_t reg_pextp_p0_ddr_en_mask_b;
+
+	/* SPM_SRC3_MASK */
+	uint8_t reg_pextp_p1_srcclkena_mask_b;
+	uint8_t reg_pextp_p1_infra_req_mask_b;
+	uint8_t reg_pextp_p1_apsrc_req_mask_b;
+	uint8_t reg_pextp_p1_vrf18_req_mask_b;
+	uint8_t reg_pextp_p1_ddr_en_mask_b;
+	uint8_t reg_gce0_infra_req_mask_b;
+	uint8_t reg_gce0_apsrc_req_mask_b;
+	uint8_t reg_gce0_vrf18_req_mask_b;
+	uint8_t reg_gce0_ddr_en_mask_b;
+	uint8_t reg_gce1_infra_req_mask_b;
+	uint8_t reg_gce1_apsrc_req_mask_b;
+	uint8_t reg_gce1_vrf18_req_mask_b;
+	uint8_t reg_gce1_ddr_en_mask_b;
+	uint8_t reg_spm_srcclkena_reserved_mask_b;
+	uint8_t reg_spm_infra_req_reserved_mask_b;
+	uint8_t reg_spm_apsrc_req_reserved_mask_b;
+	uint8_t reg_spm_vrf18_req_reserved_mask_b;
+	uint8_t reg_spm_ddr_en_reserved_mask_b;
+	uint8_t reg_disp0_apsrc_req_mask_b;
+	uint8_t reg_disp0_ddr_en_mask_b;
+	uint8_t reg_disp1_apsrc_req_mask_b;
+	uint8_t reg_disp1_ddr_en_mask_b;
+	uint8_t reg_disp2_apsrc_req_mask_b;
+	uint8_t reg_disp2_ddr_en_mask_b;
+	uint8_t reg_disp3_apsrc_req_mask_b;
+	uint8_t reg_disp3_ddr_en_mask_b;
+	uint8_t reg_infrasys_apsrc_req_mask_b;
+	uint8_t reg_infrasys_ddr_en_mask_b;
+	uint8_t reg_cg_check_srcclkena_mask_b;
+	uint8_t reg_cg_check_apsrc_req_mask_b;
+	uint8_t reg_cg_check_vrf18_req_mask_b;
+	uint8_t reg_cg_check_ddr_en_mask_b;
+
+	/* SPM_SRC4_MASK */
+	uint32_t reg_mcusys_merge_apsrc_req_mask_b;
+	uint32_t reg_mcusys_merge_ddr_en_mask_b;
+	uint8_t reg_dramc_md32_infra_req_mask_b;
+	uint8_t reg_dramc_md32_vrf18_req_mask_b;
+	uint8_t reg_dramc_md32_ddr_en_mask_b;
+	uint8_t reg_dvfsrc_event_trigger_mask_b;
+
+	/* SPM_WAKEUP_EVENT_MASK2 */
+	uint8_t reg_sc_sw2spm_wakeup_mask_b;
+	uint8_t reg_sc_adsp2spm_wakeup_mask_b;
+	uint8_t reg_sc_sspm2spm_wakeup_mask_b;
+	uint8_t reg_sc_scp2spm_wakeup_mask_b;
+	uint8_t reg_csyspwrup_ack_mask;
+	uint8_t reg_csyspwrup_req_mask;
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	uint32_t reg_wakeup_event_mask;
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	uint32_t reg_ext_wakeup_event_mask;
+};
+
+/* code gen by spm_pwr_ctrl_atf.pl, need struct pwr_ctrl */
+enum pwr_ctrl_enum {
+	PW_PCM_FLAGS,
+	PW_PCM_FLAGS_CUST,
+	PW_PCM_FLAGS_CUST_SET,
+	PW_PCM_FLAGS_CUST_CLR,
+	PW_PCM_FLAGS1,
+	PW_PCM_FLAGS1_CUST,
+	PW_PCM_FLAGS1_CUST_SET,
+	PW_PCM_FLAGS1_CUST_CLR,
+	PW_TIMER_VAL,
+	PW_TIMER_VAL_CUST,
+	PW_TIMER_VAL_RAMP_EN,
+	PW_TIMER_VAL_RAMP_EN_SEC,
+	PW_WAKE_SRC,
+	PW_WAKE_SRC_CUST,
+	PW_WAKELOCK_TIMER_VAL,
+	PW_WDT_DISABLE,
+
+	/* SPM_CLK_CON */
+	PW_REG_SRCCLKEN0_CTL,
+	PW_REG_SRCCLKEN1_CTL,
+	PW_REG_SPM_LOCK_INFRA_DCM,
+	PW_REG_SRCCLKEN_MASK,
+	PW_REG_MD1_C32RM_EN,
+	PW_REG_MD2_C32RM_EN,
+	PW_REG_CLKSQ0_SEL_CTRL,
+	PW_REG_CLKSQ1_SEL_CTRL,
+	PW_REG_SRCCLKEN0_EN,
+	PW_REG_SRCCLKEN1_EN,
+	PW_REG_SYSCLK0_SRC_MASK_B,
+	PW_REG_SYSCLK1_SRC_MASK_B,
+
+	/* SPM_AP_STANDBY_CON */
+	PW_REG_WFI_OP,
+	PW_REG_WFI_TYPE,
+	PW_REG_MP0_CPUTOP_IDLE_MASK,
+	PW_REG_MP1_CPUTOP_IDLE_MASK,
+	PW_REG_MCUSYS_IDLE_MASK,
+	PW_REG_MD_APSRC_1_SEL,
+	PW_REG_MD_APSRC_0_SEL,
+	PW_REG_CONN_APSRC_SEL,
+
+	/* SPM_SRC_REQ */
+	PW_REG_SPM_APSRC_REQ,
+	PW_REG_SPM_F26M_REQ,
+	PW_REG_SPM_INFRA_REQ,
+	PW_REG_SPM_VRF18_REQ,
+	PW_REG_SPM_DDR_EN_REQ,
+	PW_REG_SPM_DVFS_REQ,
+	PW_REG_SPM_SW_MAILBOX_REQ,
+	PW_REG_SPM_SSPM_MAILBOX_REQ,
+	PW_REG_SPM_ADSP_MAILBOX_REQ,
+	PW_REG_SPM_SCP_MAILBOX_REQ,
+
+	/* SPM_SRC_MASK */
+	PW_REG_MD_SRCCLKENA_0_MASK_B,
+	PW_REG_MD_SRCCLKENA2INFRA_REQ_0_MASK_B,
+	PW_REG_MD_APSRC2INFRA_REQ_0_MASK_B,
+	PW_REG_MD_APSRC_REQ_0_MASK_B,
+	PW_REG_MD_VRF18_REQ_0_MASK_B,
+	PW_REG_MD_DDR_EN_0_MASK_B,
+	PW_REG_MD_SRCCLKENA_1_MASK_B,
+	PW_REG_MD_SRCCLKENA2INFRA_REQ_1_MASK_B,
+	PW_REG_MD_APSRC2INFRA_REQ_1_MASK_B,
+	PW_REG_MD_APSRC_REQ_1_MASK_B,
+	PW_REG_MD_VRF18_REQ_1_MASK_B,
+	PW_REG_MD_DDR_EN_1_MASK_B,
+	PW_REG_CONN_SRCCLKENA_MASK_B,
+	PW_REG_CONN_SRCCLKENB_MASK_B,
+	PW_REG_CONN_INFRA_REQ_MASK_B,
+	PW_REG_CONN_APSRC_REQ_MASK_B,
+	PW_REG_CONN_VRF18_REQ_MASK_B,
+	PW_REG_CONN_DDR_EN_MASK_B,
+	PW_REG_CONN_VFE28_MASK_B,
+	PW_REG_SRCCLKENI0_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI0_INFRA_REQ_MASK_B,
+	PW_REG_SRCCLKENI1_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI1_INFRA_REQ_MASK_B,
+	PW_REG_SRCCLKENI2_SRCCLKENA_MASK_B,
+	PW_REG_SRCCLKENI2_INFRA_REQ_MASK_B,
+	PW_REG_INFRASYS_APSRC_REQ_MASK_B,
+	PW_REG_INFRASYS_DDR_EN_MASK_B,
+	PW_REG_MD32_SRCCLKENA_MASK_B,
+	PW_REG_MD32_INFRA_REQ_MASK_B,
+	PW_REG_MD32_APSRC_REQ_MASK_B,
+	PW_REG_MD32_VRF18_REQ_MASK_B,
+	PW_REG_MD32_DDR_EN_MASK_B,
+
+	/* SPM_SRC2_MASK */
+	PW_REG_SCP_SRCCLKENA_MASK_B,
+	PW_REG_SCP_INFRA_REQ_MASK_B,
+	PW_REG_SCP_APSRC_REQ_MASK_B,
+	PW_REG_SCP_VRF18_REQ_MASK_B,
+	PW_REG_SCP_DDR_EN_MASK_B,
+	PW_REG_AUDIO_DSP_SRCCLKENA_MASK_B,
+	PW_REG_AUDIO_DSP_INFRA_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_APSRC_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_VRF18_REQ_MASK_B,
+	PW_REG_AUDIO_DSP_DDR_EN_MASK_B,
+	PW_REG_UFS_SRCCLKENA_MASK_B,
+	PW_REG_UFS_INFRA_REQ_MASK_B,
+	PW_REG_UFS_APSRC_REQ_MASK_B,
+	PW_REG_UFS_VRF18_REQ_MASK_B,
+	PW_REG_UFS_DDR_EN_MASK_B,
+	PW_REG_DISP0_APSRC_REQ_MASK_B,
+	PW_REG_DISP0_DDR_EN_MASK_B,
+	PW_REG_DISP1_APSRC_REQ_MASK_B,
+	PW_REG_DISP1_DDR_EN_MASK_B,
+	PW_REG_GCE_INFRA_REQ_MASK_B,
+	PW_REG_GCE_APSRC_REQ_MASK_B,
+	PW_REG_GCE_VRF18_REQ_MASK_B,
+	PW_REG_GCE_DDR_EN_MASK_B,
+	PW_REG_APU_SRCCLKENA_MASK_B,
+	PW_REG_APU_INFRA_REQ_MASK_B,
+	PW_REG_APU_APSRC_REQ_MASK_B,
+	PW_REG_APU_VRF18_REQ_MASK_B,
+	PW_REG_APU_DDR_EN_MASK_B,
+	PW_REG_CG_CHECK_SRCCLKENA_MASK_B,
+	PW_REG_CG_CHECK_APSRC_REQ_MASK_B,
+	PW_REG_CG_CHECK_VRF18_REQ_MASK_B,
+	PW_REG_CG_CHECK_DDR_EN_MASK_B,
+
+	/* SPM_SRC3_MASK */
+	PW_REG_DVFSRC_EVENT_TRIGGER_MASK_B,
+	PW_REG_SW2SPM_INT0_MASK_B,
+	PW_REG_SW2SPM_INT1_MASK_B,
+	PW_REG_SW2SPM_INT2_MASK_B,
+	PW_REG_SW2SPM_INT3_MASK_B,
+	PW_REG_SC_ADSP2SPM_WAKEUP_MASK_B,
+	PW_REG_SC_SSPM2SPM_WAKEUP_MASK_B,
+	PW_REG_SC_SCP2SPM_WAKEUP_MASK_B,
+	PW_REG_CSYSPWRREQ_MASK,
+	PW_REG_SPM_SRCCLKENA_RESERVED_MASK_B,
+	PW_REG_SPM_INFRA_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_APSRC_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_VRF18_REQ_RESERVED_MASK_B,
+	PW_REG_SPM_DDR_EN_RESERVED_MASK_B,
+	PW_REG_MCUPM_SRCCLKENA_MASK_B,
+	PW_REG_MCUPM_INFRA_REQ_MASK_B,
+	PW_REG_MCUPM_APSRC_REQ_MASK_B,
+	PW_REG_MCUPM_VRF18_REQ_MASK_B,
+	PW_REG_MCUPM_DDR_EN_MASK_B,
+	PW_REG_MSDC0_SRCCLKENA_MASK_B,
+	PW_REG_MSDC0_INFRA_REQ_MASK_B,
+	PW_REG_MSDC0_APSRC_REQ_MASK_B,
+	PW_REG_MSDC0_VRF18_REQ_MASK_B,
+	PW_REG_MSDC0_DDR_EN_MASK_B,
+	PW_REG_MSDC1_SRCCLKENA_MASK_B,
+	PW_REG_MSDC1_INFRA_REQ_MASK_B,
+	PW_REG_MSDC1_APSRC_REQ_MASK_B,
+	PW_REG_MSDC1_VRF18_REQ_MASK_B,
+	PW_REG_MSDC1_DDR_EN_MASK_B,
+
+	/* SPM_SRC4_MASK */
+	PW_CCIF_EVENT_MASK_B,
+	PW_REG_BAK_PSRI_SRCCLKENA_MASK_B,
+	PW_REG_BAK_PSRI_INFRA_REQ_MASK_B,
+	PW_REG_BAK_PSRI_APSRC_REQ_MASK_B,
+	PW_REG_BAK_PSRI_VRF18_REQ_MASK_B,
+	PW_REG_BAK_PSRI_DDR_EN_MASK_B,
+	PW_REG_DRAMC0_MD32_INFRA_REQ_MASK_B,
+	PW_REG_DRAMC0_MD32_VRF18_REQ_MASK_B,
+	PW_REG_DRAMC1_MD32_INFRA_REQ_MASK_B,
+	PW_REG_DRAMC1_MD32_VRF18_REQ_MASK_B,
+	PW_REG_CONN_SRCCLKENB2PWRAP_MASK_B,
+	PW_REG_DRAMC0_MD32_WAKEUP_MASK,
+	PW_REG_DRAMC1_MD32_WAKEUP_MASK,
+
+	/* SPM_SRC5_MASK */
+	PW_REG_MCUSYS_MERGE_APSRC_REQ_MASK_B,
+	PW_REG_MCUSYS_MERGE_DDR_EN_MASK_B,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	PW_REG_WAKEUP_EVENT_MASK,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	PW_REG_EXT_WAKEUP_EVENT_MASK,
+
+	PW_MAX_COUNT,
+};
+
+#define SPM_INTERNAL_STATUS_HW_S1	(1U << 0)
+#define SPM_ACK_CHK_3_SEL_HW_S1		0x00350098
+#define SPM_ACK_CHK_3_HW_S1_CNT		1
+#define SPM_ACK_CHK_3_CON_HW_MODE_TRIG	0x800
+#define SPM_ACK_CHK_3_CON_EN		0x110
+#define SPM_ACK_CHK_3_CON_CLR_ALL	0x2
+#define SPM_ACK_CHK_3_CON_RESULT	0x8000
+
+struct wake_status_trace_comm {
+	uint32_t debug_flag;			/* PCM_WDT_LATCH_SPARE_0 */
+	uint32_t debug_flag1;			/* PCM_WDT_LATCH_SPARE_1 */
+	uint32_t timer_out;			/* SPM_BK_PCM_TIMER */
+	uint32_t b_sw_flag0;			/* SPM_SW_RSV_7 */
+	uint32_t b_sw_flag1;			/* SPM_SW_RSV_8 */
+	uint32_t r12;				/* SPM_SW_RSV_0 */
+	uint32_t r13;				/* PCM_REG13_DATA */
+	uint32_t req_sta0;			/* SRC_REQ_STA_0 */
+	uint32_t req_sta1;			/* SRC_REQ_STA_1 */
+	uint32_t req_sta2;			/* SRC_REQ_STA_2 */
+	uint32_t req_sta3;			/* SRC_REQ_STA_3 */
+	uint32_t req_sta4;			/* SRC_REQ_STA_4 */
+	uint32_t raw_sta;			/* SPM_WAKEUP_STA */
+	uint32_t times_h;			/* timestamp high bits */
+	uint32_t times_l;			/* timestamp low bits */
+	uint32_t resumetime;			/* timestamp low bits */
+};
+
+struct wake_status_trace {
+	struct wake_status_trace_comm comm;
+};
+
+struct wake_status {
+	struct wake_status_trace tr;
+	uint32_t r12;				/* SPM_BK_WAKE_EVENT */
+	uint32_t r12_ext;			/* SPM_WAKEUP_STA */
+	uint32_t raw_sta;			/* SPM_WAKEUP_STA */
+	uint32_t raw_ext_sta;			/* SPM_WAKEUP_EXT_STA */
+	uint32_t md32pcm_wakeup_sta;		/* MD32PCM_WAKEUP_STA */
+	uint32_t md32pcm_event_sta;		/* MD32PCM_EVENT_STA */
+	uint32_t src_req;			/* SPM_SRC_REQ */
+	uint32_t wake_misc;			/* SPM_BK_WAKE_MISC */
+	uint32_t timer_out;			/* SPM_BK_PCM_TIMER */
+	uint32_t r13;				/* PCM_REG13_DATA */
+	uint32_t idle_sta;			/* SUBSYS_IDLE_STA */
+	uint32_t req_sta0;			/* SRC_REQ_STA_0 */
+	uint32_t req_sta1;			/* SRC_REQ_STA_1 */
+	uint32_t req_sta2;			/* SRC_REQ_STA_2 */
+	uint32_t req_sta3;			/* SRC_REQ_STA_3 */
+	uint32_t req_sta4;			/* SRC_REQ_STA_4 */
+	uint32_t cg_check_sta;			/* SPM_CG_CHECK_STA */
+	uint32_t debug_flag;			/* PCM_WDT_LATCH_SPARE_0 */
+	uint32_t debug_flag1;			/* PCM_WDT_LATCH_SPARE_1 */
+	uint32_t b_sw_flag0;			/* SPM_SW_RSV_7 */
+	uint32_t b_sw_flag1;			/* SPM_SW_RSV_8 */
+	uint32_t rt_req_sta0;			/* SPM_SW_RSV_2 */
+	uint32_t rt_req_sta1;			/* SPM_SW_RSV_3 */
+	uint32_t rt_req_sta2;			/* SPM_SW_RSV_4 */
+	uint32_t rt_req_sta3;			/* SPM_SW_RSV_5 */
+	uint32_t rt_req_sta4;			/* SPM_SW_RSV_6 */
+	uint32_t isr;				/* SPM_IRQ_STA */
+	uint32_t sw_flag0;			/* SPM_SW_FLAG_0 */
+	uint32_t sw_flag1;			/* SPM_SW_FLAG_1 */
+	uint32_t clk_settle;			/* SPM_CLK_SETTLE */
+	uint32_t abort;
+};
+
+struct spm_lp_scen {
+	struct pcm_desc *pcmdesc;
+	struct pwr_ctrl *pwrctrl;
+};
+
+extern struct spm_lp_scen __spm_vcorefs;
+extern void __spm_set_cpu_status(unsigned int cpu);
+extern void __spm_reset_and_init_pcm(const struct pcm_desc *pcmdesc);
+extern void __spm_kick_im_to_fetch(const struct pcm_desc *pcmdesc);
+extern void __spm_init_pcm_register(void);
+extern void __spm_src_req_update(const struct pwr_ctrl *pwrctrl,
+				 unsigned int resource_usage);
+extern void __spm_set_power_control(const struct pwr_ctrl *pwrctrl);
+extern void __spm_disable_pcm_timer(void);
+extern void __spm_set_wakeup_event(const struct pwr_ctrl *pwrctrl);
+extern void __spm_kick_pcm_to_run(struct pwr_ctrl *pwrctrl);
+extern void __spm_set_pcm_flags(struct pwr_ctrl *pwrctrl);
+extern void __spm_send_cpu_wakeup_event(void);
+extern void __spm_get_wakeup_status(struct wake_status *wakesta,
+				    unsigned int ext_status);
+extern void __spm_clean_after_wakeup(void);
+extern wake_reason_t
+__spm_output_wake_reason(int state_id, const struct wake_status *wakesta);
+extern void
+__spm_sync_vcore_dvfs_power_control(struct pwr_ctrl *dest_pwr_ctrl,
+				    const struct pwr_ctrl *src_pwr_ctrl);
+extern void __spm_set_pcm_wdt(int en);
+extern uint32_t _spm_get_wake_period(int pwake_time, wake_reason_t last_wr);
+extern void __spm_set_fw_resume_option(struct pwr_ctrl *pwrctrl);
+extern void __spm_ext_int_wakeup_req_clr(void);
+extern void __spm_xo_soc_bblpm(int en);
+
+static inline void set_pwrctrl_pcm_flags(struct pwr_ctrl *pwrctrl,
+					 uint32_t flags)
+{
+	if (pwrctrl->pcm_flags_cust == 0U) {
+		pwrctrl->pcm_flags = flags;
+	} else {
+		pwrctrl->pcm_flags = pwrctrl->pcm_flags_cust;
+	}
+}
+
+static inline void set_pwrctrl_pcm_flags1(struct pwr_ctrl *pwrctrl,
+					  uint32_t flags)
+{
+	if (pwrctrl->pcm_flags1_cust == 0U) {
+		pwrctrl->pcm_flags1 = flags;
+	} else {
+		pwrctrl->pcm_flags1 = pwrctrl->pcm_flags1_cust;
+	}
+}
+
+extern void __spm_hw_s1_state_monitor(int en, unsigned int *status);
+
+static inline void spm_hw_s1_state_monitor_resume(void)
+{
+	__spm_hw_s1_state_monitor(1, NULL);
+}
+
+static inline void spm_hw_s1_state_monitor_pause(unsigned int *status)
+{
+	__spm_hw_s1_state_monitor(0, status);
+}
+#endif /* MT_SPM_INTERNAL_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.c
new file mode 100644
index 0000000..9da644c
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.c
@@ -0,0 +1,159 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include <mt_spm.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_reg.h>
+#include <plat_pm.h>
+#include <platform_def.h>
+
+/* PMIC_WRAP MT6359 */
+#define VCORE_BASE_UV		40000
+#define VOLT_TO_PMIC_VAL(volt)	(((volt) - VCORE_BASE_UV + 625 - 1) / 625)
+#define PMIC_VAL_TO_VOLT(pmic)	(((pmic) * 625) + VCORE_BASE_UV)
+
+#define NR_PMIC_WRAP_CMD	(NR_IDX_ALL)
+#define SPM_DATA_SHIFT		16
+
+#define BUCK_VGPU11_ELR0	0x15B4
+#define TOP_SPI_CON0		0x0456
+#define BUCK_TOP_CON1		0x1443
+#define TOP_CON			0x0013
+#define TOP_DIG_WPK		0x03a9
+#define TOP_CON_LOCK		0x03a8
+#define TOP_CLK_CON0		0x0134
+
+struct pmic_wrap_cmd {
+	unsigned long cmd_addr;
+	unsigned long cmd_wdata;
+};
+
+struct pmic_wrap_setting {
+	enum pmic_wrap_phase_id phase;
+	struct pmic_wrap_cmd addr[NR_PMIC_WRAP_CMD];
+	struct {
+		struct {
+			unsigned long cmd_addr;
+			unsigned long cmd_wdata;
+		} _[NR_PMIC_WRAP_CMD];
+		const int nr_idx;
+	} set[NR_PMIC_WRAP_PHASE];
+};
+
+static struct pmic_wrap_setting pw = {
+	.phase = NR_PMIC_WRAP_PHASE,    /* invalid setting for init */
+	.addr = { {0UL, 0UL} },
+	.set[PMIC_WRAP_PHASE_ALLINONE] = {
+		._[CMD_0]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(75000),},
+		._[CMD_1]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(65000),},
+		._[CMD_2]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(60000),},
+		._[CMD_3]	= {BUCK_VGPU11_ELR0, VOLT_TO_PMIC_VAL(55000),},
+		._[CMD_4]	= {TOP_SPI_CON0, 0x1,},
+		._[CMD_5]	= {TOP_SPI_CON0, 0x0,},
+		._[CMD_6]	= {BUCK_TOP_CON1, 0x0,},
+		._[CMD_7]	= {BUCK_TOP_CON1, 0xf,},
+		._[CMD_8]	= {TOP_CON, 0x3,},
+		._[CMD_9]	= {TOP_CON, 0x0,},
+		._[CMD_10]	= {TOP_DIG_WPK, 0x63,},
+		._[CMD_11]	= {TOP_CON_LOCK, 0x15,},
+		._[CMD_12]	= {TOP_DIG_WPK, 0x0,},
+		._[CMD_13]	= {TOP_CON_LOCK, 0x0,},
+		._[CMD_14]	= {TOP_CLK_CON0, 0x40,},
+		._[CMD_15]	= {TOP_CLK_CON0, 0x0,},
+		.nr_idx = NR_IDX_ALL,
+	},
+};
+
+void _mt_spm_pmic_table_init(void)
+{
+	struct pmic_wrap_cmd pwrap_cmd_default[NR_PMIC_WRAP_CMD] = {
+		{(uint32_t)SPM_DVFS_CMD0, (uint32_t)SPM_DVFS_CMD0,},
+		{(uint32_t)SPM_DVFS_CMD1, (uint32_t)SPM_DVFS_CMD1,},
+		{(uint32_t)SPM_DVFS_CMD2, (uint32_t)SPM_DVFS_CMD2,},
+		{(uint32_t)SPM_DVFS_CMD3, (uint32_t)SPM_DVFS_CMD3,},
+		{(uint32_t)SPM_DVFS_CMD4, (uint32_t)SPM_DVFS_CMD4,},
+		{(uint32_t)SPM_DVFS_CMD5, (uint32_t)SPM_DVFS_CMD5,},
+		{(uint32_t)SPM_DVFS_CMD6, (uint32_t)SPM_DVFS_CMD6,},
+		{(uint32_t)SPM_DVFS_CMD7, (uint32_t)SPM_DVFS_CMD7,},
+		{(uint32_t)SPM_DVFS_CMD8, (uint32_t)SPM_DVFS_CMD8,},
+		{(uint32_t)SPM_DVFS_CMD9, (uint32_t)SPM_DVFS_CMD9,},
+		{(uint32_t)SPM_DVFS_CMD10, (uint32_t)SPM_DVFS_CMD10,},
+		{(uint32_t)SPM_DVFS_CMD11, (uint32_t)SPM_DVFS_CMD11,},
+		{(uint32_t)SPM_DVFS_CMD12, (uint32_t)SPM_DVFS_CMD12,},
+		{(uint32_t)SPM_DVFS_CMD13, (uint32_t)SPM_DVFS_CMD13,},
+		{(uint32_t)SPM_DVFS_CMD14, (uint32_t)SPM_DVFS_CMD14,},
+		{(uint32_t)SPM_DVFS_CMD15, (uint32_t)SPM_DVFS_CMD15,},
+	};
+
+	memcpy(pw.addr, pwrap_cmd_default, sizeof(pwrap_cmd_default));
+}
+
+void mt_spm_pmic_wrap_set_phase(enum pmic_wrap_phase_id phase)
+{
+	uint32_t idx, addr, data;
+
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return;
+	}
+
+	if (pw.phase == phase) {
+		return;
+	}
+
+	if (pw.addr[0].cmd_addr == 0UL) {
+		_mt_spm_pmic_table_init();
+	}
+
+	pw.phase = phase;
+	mmio_write_32(POWERON_CONFIG_EN, SPM_REGWR_CFG_KEY | BCLK_CG_EN_LSB);
+
+	for (idx = 0U; idx < pw.set[phase].nr_idx; idx++) {
+		addr = pw.set[phase]._[idx].cmd_addr << SPM_DATA_SHIFT;
+		data = pw.set[phase]._[idx].cmd_wdata;
+		mmio_write_32(pw.addr[idx].cmd_addr, addr | data);
+	}
+}
+
+void mt_spm_pmic_wrap_set_cmd(enum pmic_wrap_phase_id phase, uint32_t idx,
+			      uint32_t cmd_wdata)
+{
+	uint32_t addr;
+
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return;
+	}
+
+	if (idx >= pw.set[phase].nr_idx) {
+		return;
+	}
+
+	pw.set[phase]._[idx].cmd_wdata = cmd_wdata;
+	mmio_write_32(POWERON_CONFIG_EN, SPM_REGWR_CFG_KEY | BCLK_CG_EN_LSB);
+
+	if (pw.phase == phase) {
+		addr = pw.set[phase]._[idx].cmd_addr << SPM_DATA_SHIFT;
+		mmio_write_32(pw.addr[idx].cmd_addr, addr | cmd_wdata);
+	}
+}
+
+uint64_t mt_spm_pmic_wrap_get_cmd(enum pmic_wrap_phase_id phase, uint32_t idx)
+{
+	if (phase >= NR_PMIC_WRAP_PHASE) {
+		return 0UL;
+	}
+
+	if (idx >= pw.set[phase].nr_idx) {
+		return 0UL;
+	}
+
+	return pw.set[phase]._[idx].cmd_wdata;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.h
new file mode 100644
index 0000000..53fdda2
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_pmic_wrap.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/****************************************************************
+ * Auto generated by DE, please DO NOT modify this file directly.
+ *****************************************************************/
+#ifndef MT_SPM_PMIC_WRAP_H
+#define MT_SPM_PMIC_WRAP_H
+
+enum pmic_wrap_phase_id {
+	PMIC_WRAP_PHASE_ALLINONE,
+	NR_PMIC_WRAP_PHASE,
+};
+
+/* IDX mapping, PMIC_WRAP_PHASE_ALLINONE */
+enum {
+	CMD_0,        /* 0x0 */
+	CMD_1,        /* 0x1 */
+	CMD_2,        /* 0x2 */
+	CMD_3,        /* 0x3 */
+	CMD_4,        /* 0x4 */
+	CMD_5,        /* 0x5 */
+	CMD_6,        /* 0x6 */
+	CMD_7,        /* 0x7 */
+	CMD_8,        /* 0x8 */
+	CMD_9,        /* 0x9 */
+	CMD_10,        /* 0xA */
+	CMD_11,        /* 0xB */
+	CMD_12,        /* 0xC */
+	CMD_13,        /* 0xD */
+	CMD_14,        /* 0xE */
+	CMD_15,        /* 0xF */
+	NR_IDX_ALL,
+};
+
+/* APIs */
+extern void mt_spm_pmic_wrap_set_phase(enum pmic_wrap_phase_id phase);
+extern void mt_spm_pmic_wrap_set_cmd(enum pmic_wrap_phase_id phase,
+				     uint32_t idx, uint32_t cmd_wdata);
+extern uint64_t mt_spm_pmic_wrap_get_cmd(enum pmic_wrap_phase_id phase,
+					 uint32_t idx);
+#endif /* MT_SPM_PMIC_WRAP_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_reg.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_reg.h
new file mode 100644
index 0000000..d8b9b29
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_reg.h
@@ -0,0 +1,2859 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/****************************************************************
+ * Auto generated by DE, please DO NOT modify this file directly.
+ *****************************************************************/
+
+#ifndef MT_SPM_REG
+#define MT_SPM_REG
+
+#include "sleep_def.h"
+#include <platform_def.h>
+#include "pcm_def.h"
+
+/**************************************
+ * Define and Declare
+ **************************************/
+
+/*******Register_SPM_CFG*************************************************/
+#define POWERON_CONFIG_EN              (SPM_BASE + 0x000)
+#define SPM_POWER_ON_VAL0              (SPM_BASE + 0x004)
+#define SPM_POWER_ON_VAL1              (SPM_BASE + 0x008)
+#define SPM_CLK_CON                    (SPM_BASE + 0x00C)
+#define SPM_CLK_SETTLE                 (SPM_BASE + 0x010)
+#define SPM_AP_STANDBY_CON             (SPM_BASE + 0x014)
+#define PCM_CON0                       (SPM_BASE + 0x018)
+#define PCM_CON1                       (SPM_BASE + 0x01C)
+#define SPM_POWER_ON_VAL2              (SPM_BASE + 0x020)
+#define SPM_POWER_ON_VAL3              (SPM_BASE + 0x024)
+#define PCM_REG_DATA_INI               (SPM_BASE + 0x028)
+#define PCM_PWR_IO_EN                  (SPM_BASE + 0x02C)
+#define PCM_TIMER_VAL                  (SPM_BASE + 0x030)
+#define PCM_WDT_VAL                    (SPM_BASE + 0x034)
+#define SPM_SW_RST_CON                 (SPM_BASE + 0x040)
+#define SPM_SW_RST_CON_SET             (SPM_BASE + 0x044)
+#define SPM_SW_RST_CON_CLR             (SPM_BASE + 0x048)
+#define VS1_PSR_MASK_B                 (SPM_BASE + 0x04C)
+#define SPM_ARBITER_EN                 (SPM_BASE + 0x050)
+#define SCPSYS_CLK_CON                 (SPM_BASE + 0x054)
+#define SPM_SRAM_RSV_CON               (SPM_BASE + 0x058)
+#define SPM_SWINT                      (SPM_BASE + 0x05C)
+#define SPM_SWINT_SET                  (SPM_BASE + 0x060)
+#define SPM_SWINT_CLR                  (SPM_BASE + 0x064)
+#define SPM_SCP_MAILBOX                (SPM_BASE + 0x068)
+#define SCP_SPM_MAILBOX                (SPM_BASE + 0x06C)
+#define SPM_SCP_IRQ                    (SPM_BASE + 0x070)
+#define SPM_CPU_WAKEUP_EVENT           (SPM_BASE + 0x074)
+#define SPM_IRQ_MASK                   (SPM_BASE + 0x078)
+#define SPM_SRC_REQ                    (SPM_BASE + 0x080)
+#define SPM_SRC_MASK                   (SPM_BASE + 0x084)
+#define SPM_SRC2_MASK                  (SPM_BASE + 0x088)
+#define SPM_SRC3_MASK                  (SPM_BASE + 0x090)
+#define SPM_SRC4_MASK                  (SPM_BASE + 0x094)
+#define SPM_WAKEUP_EVENT_MASK2         (SPM_BASE + 0x098)
+#define SPM_WAKEUP_EVENT_MASK          (SPM_BASE + 0x09C)
+#define SPM_WAKEUP_EVENT_SENS          (SPM_BASE + 0x0A0)
+#define SPM_WAKEUP_EVENT_CLEAR         (SPM_BASE + 0x0A4)
+#define SPM_WAKEUP_EVENT_EXT_MASK      (SPM_BASE + 0x0A8)
+#define SCP_CLK_CON                    (SPM_BASE + 0x0AC)
+#define PCM_DEBUG_CON                  (SPM_BASE + 0x0B0)
+#define DDREN_DBC_CON                  (SPM_BASE + 0x0B4)
+#define SPM_RESOURCE_ACK_CON0          (SPM_BASE + 0x0B8)
+#define SPM_RESOURCE_ACK_CON1          (SPM_BASE + 0x0BC)
+#define SPM_RESOURCE_ACK_CON2          (SPM_BASE + 0x0C0)
+#define SPM_RESOURCE_ACK_CON3          (SPM_BASE + 0x0C4)
+#define SPM_RESOURCE_ACK_CON4          (SPM_BASE + 0x0C8)
+#define SPM_SRAM_CON                   (SPM_BASE + 0x0CC)
+/*******Register_SPM_STA*************************************************/
+#define PCM_REG0_DATA                  (SPM_BASE + 0x100)
+#define PCM_REG2_DATA                  (SPM_BASE + 0x104)
+#define PCM_REG6_DATA                  (SPM_BASE + 0x108)
+#define PCM_REG7_DATA                  (SPM_BASE + 0x10C)
+#define PCM_REG13_DATA                 (SPM_BASE + 0x110)
+#define SRC_REQ_STA_0                  (SPM_BASE + 0x114)
+#define SRC_REQ_STA_1                  (SPM_BASE + 0x118)
+#define SRC_REQ_STA_2                  (SPM_BASE + 0x120)
+#define SRC_REQ_STA_3                  (SPM_BASE + 0x124)
+#define SRC_REQ_STA_4                  (SPM_BASE + 0x128)
+#define PCM_TIMER_OUT                  (SPM_BASE + 0x130)
+#define PCM_WDT_OUT                    (SPM_BASE + 0x134)
+#define SPM_IRQ_STA                    (SPM_BASE + 0x138)
+#define MD32PCM_WAKEUP_STA             (SPM_BASE + 0x13C)
+#define MD32PCM_EVENT_STA              (SPM_BASE + 0x140)
+#define SPM_WAKEUP_STA                 (SPM_BASE + 0x144)
+#define SPM_WAKEUP_EXT_STA             (SPM_BASE + 0x148)
+#define SPM_WAKEUP_MISC                (SPM_BASE + 0x14C)
+#define MM_DVFS_HALT                   (SPM_BASE + 0x150)
+#define SUBSYS_IDLE_STA                (SPM_BASE + 0x164)
+#define PCM_STA                        (SPM_BASE + 0x168)
+#define PWR_STATUS                     (SPM_BASE + 0x16C)
+#define PWR_STATUS_2ND                 (SPM_BASE + 0x170)
+#define CPU_PWR_STATUS                 (SPM_BASE + 0x174)
+#define CPU_PWR_STATUS_2ND             (SPM_BASE + 0x178)
+#define SPM_VTCXO_EVENT_COUNT_STA      (SPM_BASE + 0x17C)
+#define SPM_INFRA_EVENT_COUNT_STA      (SPM_BASE + 0x180)
+#define SPM_VRF18_EVENT_COUNT_STA      (SPM_BASE + 0x184)
+#define SPM_APSRC_EVENT_COUNT_STA      (SPM_BASE + 0x188)
+#define SPM_DDREN_EVENT_COUNT_STA      (SPM_BASE + 0x18C)
+#define MD32PCM_STA                    (SPM_BASE + 0x190)
+#define MD32PCM_PC                     (SPM_BASE + 0x194)
+#define OTHER_PWR_STATUS               (SPM_BASE + 0x198)
+#define DVFSRC_EVENT_STA               (SPM_BASE + 0x19C)
+#define BUS_PROTECT_RDY                (SPM_BASE + 0x1A0)
+#define BUS_PROTECT1_RDY               (SPM_BASE + 0x1A4)
+#define BUS_PROTECT2_RDY               (SPM_BASE + 0x1A8)
+#define BUS_PROTECT3_RDY               (SPM_BASE + 0x1AC)
+#define BUS_PROTECT4_RDY               (SPM_BASE + 0x1B0)
+#define BUS_PROTECT5_RDY               (SPM_BASE + 0x1B4)
+#define BUS_PROTECT6_RDY               (SPM_BASE + 0x1B8)
+#define BUS_PROTECT7_RDY               (SPM_BASE + 0x1BC)
+#define BUS_PROTECT8_RDY               (SPM_BASE + 0x1C0)
+#define BUS_PROTECT9_RDY               (SPM_BASE + 0x1C4)
+#define SPM_TWAM_LAST_STA0             (SPM_BASE + 0x1D0)
+#define SPM_TWAM_LAST_STA1             (SPM_BASE + 0x1D4)
+#define SPM_TWAM_LAST_STA2             (SPM_BASE + 0x1D8)
+#define SPM_TWAM_LAST_STA3             (SPM_BASE + 0x1DC)
+#define SPM_TWAM_CURR_STA0             (SPM_BASE + 0x1E0)
+#define SPM_TWAM_CURR_STA1             (SPM_BASE + 0x1E4)
+#define SPM_TWAM_CURR_STA2             (SPM_BASE + 0x1E8)
+#define SPM_TWAM_CURR_STA3             (SPM_BASE + 0x1EC)
+#define SPM_TWAM_TIMER_OUT             (SPM_BASE + 0x1F0)
+#define SPM_CG_CHECK_STA               (SPM_BASE + 0x1F4)
+#define SPM_DVFS_STA                   (SPM_BASE + 0x1F8)
+#define SPM_DVFS_OPP_STA               (SPM_BASE + 0x1FC)
+/*******Register_CPU_MT*************************************************/
+#define CPUEB_PWR_CON                  (SPM_BASE + 0x200)
+#define SPM_MCUSYS_PWR_CON             (SPM_BASE + 0x204)
+#define SPM_CPUTOP_PWR_CON             (SPM_BASE + 0x208)
+#define SPM_CPU0_PWR_CON               (SPM_BASE + 0x20C)
+#define SPM_CPU1_PWR_CON               (SPM_BASE + 0x210)
+#define SPM_CPU2_PWR_CON               (SPM_BASE + 0x214)
+#define SPM_CPU3_PWR_CON               (SPM_BASE + 0x218)
+#define SPM_CPU4_PWR_CON               (SPM_BASE + 0x21C)
+#define SPM_CPU5_PWR_CON               (SPM_BASE + 0x220)
+#define SPM_CPU6_PWR_CON               (SPM_BASE + 0x224)
+#define SPM_CPU7_PWR_CON               (SPM_BASE + 0x228)
+#define ARMPLL_CLK_CON                 (SPM_BASE + 0x22C)
+#define MCUSYS_IDLE_STA                (SPM_BASE + 0x230)
+#define GIC_WAKEUP_STA                 (SPM_BASE + 0x234)
+#define CPU_SPARE_CON                  (SPM_BASE + 0x238)
+#define CPU_SPARE_CON_SET              (SPM_BASE + 0x23C)
+#define CPU_SPARE_CON_CLR              (SPM_BASE + 0x240)
+#define ARMPLL_CLK_SEL                 (SPM_BASE + 0x244)
+#define EXT_INT_WAKEUP_REQ             (SPM_BASE + 0x248)
+#define EXT_INT_WAKEUP_REQ_SET         (SPM_BASE + 0x24C)
+#define EXT_INT_WAKEUP_REQ_CLR         (SPM_BASE + 0x250)
+#define CPU0_IRQ_MASK                  (SPM_BASE + 0x260)
+#define CPU_IRQ_MASK_SET               (SPM_BASE + 0x264)
+#define CPU_IRQ_MASK_CLR               (SPM_BASE + 0x268)
+#define CPU_WFI_EN                     (SPM_BASE + 0x280)
+#define CPU_WFI_EN_SET                 (SPM_BASE + 0x284)
+#define CPU_WFI_EN_CLR                 (SPM_BASE + 0x288)
+#define SYSRAM_CON                     (SPM_BASE + 0x290)
+#define SYSROM_CON                     (SPM_BASE + 0x294)
+#define ROOT_CPUTOP_ADDR               (SPM_BASE + 0x2A0)
+#define ROOT_CORE_ADDR                 (SPM_BASE + 0x2A4)
+#define SPM2SW_MAILBOX_0               (SPM_BASE + 0x2D0)
+#define SPM2SW_MAILBOX_1               (SPM_BASE + 0x2D4)
+#define SPM2SW_MAILBOX_2               (SPM_BASE + 0x2D8)
+#define SPM2SW_MAILBOX_3               (SPM_BASE + 0x2DC)
+#define SW2SPM_INT                     (SPM_BASE + 0x2E0)
+#define SW2SPM_INT_SET                 (SPM_BASE + 0x2E4)
+#define SW2SPM_INT_CLR                 (SPM_BASE + 0x2E8)
+#define SW2SPM_MAILBOX_0               (SPM_BASE + 0x2EC)
+#define SW2SPM_MAILBOX_1               (SPM_BASE + 0x2F0)
+#define SW2SPM_MAILBOX_2               (SPM_BASE + 0x2F4)
+#define SW2SPM_MAILBOX_3               (SPM_BASE + 0x2F8)
+#define SW2SPM_CFG                     (SPM_BASE + 0x2FC)
+/*******Register_NONCPU_MT*************************************************/
+#define MFG0_PWR_CON                   (SPM_BASE + 0x300)
+#define MFG1_PWR_CON                   (SPM_BASE + 0x304)
+#define MFG2_PWR_CON                   (SPM_BASE + 0x308)
+#define MFG3_PWR_CON                   (SPM_BASE + 0x30C)
+#define MFG4_PWR_CON                   (SPM_BASE + 0x310)
+#define MFG5_PWR_CON                   (SPM_BASE + 0x314)
+#define MFG6_PWR_CON                   (SPM_BASE + 0x318)
+#define IFR_PWR_CON                    (SPM_BASE + 0x31C)
+#define IFR_SUB_PWR_CON                (SPM_BASE + 0x320)
+#define PERI_PWR_CON                   (SPM_BASE + 0x324)
+#define PEXTP_MAC_TOP_P0_PWR_CON       (SPM_BASE + 0x328)
+#define PEXTP_MAC_TOP_P1_PWR_CON       (SPM_BASE + 0x32C)
+#define PCIE_PHY_PWR_CON               (SPM_BASE + 0x330)
+#define SSUSB_PCIE_PHY_PWR_CON         (SPM_BASE + 0x334)
+#define SSUSB_TOP_P1_PWR_CON           (SPM_BASE + 0x338)
+#define SSUSB_TOP_P2_PWR_CON           (SPM_BASE + 0x33C)
+#define SSUSB_TOP_P3_PWR_CON           (SPM_BASE + 0x340)
+#define ETHER_PWR_CON                  (SPM_BASE + 0x344)
+#define DPY0_PWR_CON                   (SPM_BASE + 0x348)
+#define DPY1_PWR_CON                   (SPM_BASE + 0x34C)
+#define DPM0_PWR_CON                   (SPM_BASE + 0x350)
+#define DPM1_PWR_CON                   (SPM_BASE + 0x354)
+#define AUDIO_PWR_CON                  (SPM_BASE + 0x358)
+#define AUDIO_ASRC_PWR_CON             (SPM_BASE + 0x35C)
+#define ADSP_PWR_CON                   (SPM_BASE + 0x360)
+#define VPPSYS0_PWR_CON                (SPM_BASE + 0x364)
+#define VPPSYS1_PWR_CON                (SPM_BASE + 0x368)
+#define VDOSYS0_PWR_CON                (SPM_BASE + 0x36C)
+#define VDOSYS1_PWR_CON                (SPM_BASE + 0x370)
+#define WPESYS_PWR_CON                 (SPM_BASE + 0x374)
+#define DP_TX_PWR_CON                  (SPM_BASE + 0x378)
+#define EDP_TX_PWR_CON                 (SPM_BASE + 0x37C)
+#define HDMI_TX_PWR_CON                (SPM_BASE + 0x380)
+#define HDMI_RX_PWR_CON                (SPM_BASE + 0x384)
+#define VDE0_PWR_CON                   (SPM_BASE + 0x388)
+#define VDE1_PWR_CON                   (SPM_BASE + 0x38C)
+#define VDE2_PWR_CON                   (SPM_BASE + 0x390)
+#define VEN_PWR_CON                    (SPM_BASE + 0x394)
+#define VEN_CORE1_PWR_CON              (SPM_BASE + 0x398)
+#define CAM_PWR_CON                    (SPM_BASE + 0x39C)
+#define CAM_RAWA_PWR_CON               (SPM_BASE + 0x3A0)
+#define CAM_RAWB_PWR_CON               (SPM_BASE + 0x3A4)
+#define CAM_RAWC_PWR_CON               (SPM_BASE + 0x3A8)
+#define IMG_M_PWR_CON                  (SPM_BASE + 0x3AC)
+#define IMG_D_PWR_CON                  (SPM_BASE + 0x3B0)
+#define IPE_PWR_CON                    (SPM_BASE + 0x3B4)
+#define NNA0_PWR_CON                   (SPM_BASE + 0x3B8)
+#define NNA1_PWR_CON                   (SPM_BASE + 0x3BC)
+#define IPNNA_PWR_CON                  (SPM_BASE + 0x3C0)
+#define CSI_RX_TOP_PWR_CON             (SPM_BASE + 0x3C4)
+#define SSPM_SRAM_CON                  (SPM_BASE + 0x3C4)
+#define SCP_SRAM_CON                   (SPM_BASE + 0x3D0)
+#define UFS_SRAM_CON                   (SPM_BASE + 0x3D4)
+#define DEVAPC_IFR_SRAM_CON            (SPM_BASE + 0x3D8)
+#define DEVAPC_SUBIFR_SRAM_CON         (SPM_BASE + 0x3DC)
+#define DEVAPC_ACP_SRAM_CON            (SPM_BASE + 0x3E0)
+#define USB_SRAM_CON                   (SPM_BASE + 0x3E4)
+#define DUMMY_SRAM_CO                  (SPM_BASE + 0x3E8)
+#define EXT_BUCK_ISO                   (SPM_BASE + 0x3EC)
+#define MSDC_SRAM_CON                  (SPM_BASE + 0x3F0)
+#define DEBUGTOP_SRAM                  (SPM_BASE + 0x3F4)
+#define DPMAIF_SRAM_C                  (SPM_BASE + 0x3F8)
+#define GCPU_SRAM_CON                  (SPM_BASE + 0x3FC)
+/*******Register_DIRC_IF*************************************************/
+#define SPM_MEM_CK_SEL                 (SPM_BASE + 0x400)
+#define SPM_BUS_PROTECT_MASK_B         (SPM_BASE + 0x404)
+#define SPM_BUS_PROTECT1_MASK_B        (SPM_BASE + 0x408)
+#define SPM_BUS_PROTECT2_MASK_B        (SPM_BASE + 0x40C)
+#define SPM_BUS_PROTECT3_MASK_B        (SPM_BASE + 0x410)
+#define SPM_BUS_PROTECT4_MASK_B        (SPM_BASE + 0x414)
+#define SPM_BUS_PROTECT5_MASK_B        (SPM_BASE + 0x418)
+#define SPM_BUS_PROTECT6_MASK_B        (SPM_BASE + 0x41C)
+#define SPM_BUS_PROTECT7_MASK_B        (SPM_BASE + 0x420)
+#define SPM_BUS_PROTECT8_MASK_B        (SPM_BASE + 0x424)
+#define SPM_BUS_PROTECT9_MASK_B        (SPM_BASE + 0x428)
+#define SPM_EMI_BW_MODE                (SPM_BASE + 0x42C)
+#define SPM2MM_CON                     (SPM_BASE + 0x434)
+#define SPM2CPUEB_CON                  (SPM_BASE + 0x438)
+#define AP_MDSRC_REQ                   (SPM_BASE + 0x43C)
+#define SPM2EMI_ENTER_ULPM             (SPM_BASE + 0x440)
+#define SPM_PLL_CON                    (SPM_BASE + 0x444)
+#define RC_SPM_CTRL                    (SPM_BASE + 0x448)
+#define SPM_DRAM_MCU_SW_CON_0          (SPM_BASE + 0x44C)
+#define SPM_DRAM_MCU_SW_CON_1          (SPM_BASE + 0x450)
+#define SPM_DRAM_MCU_SW_CON_2          (SPM_BASE + 0x454)
+#define SPM_DRAM_MCU_SW_CON_3          (SPM_BASE + 0x458)
+#define SPM_DRAM_MCU_SW_CON_4          (SPM_BASE + 0x45C)
+#define SPM_DRAM_MCU_STA_0             (SPM_BASE + 0x460)
+#define SPM_DRAM_MCU_STA_1             (SPM_BASE + 0x464)
+#define SPM_DRAM_MCU_STA_2             (SPM_BASE + 0x468)
+#define SPM_DRAM_MCU_SW_SEL_0          (SPM_BASE + 0x46C)
+#define RELAY_DVFS_LEVEL               (SPM_BASE + 0x470)
+#define DRAMC_DPY_CLK_SW_CON_0         (SPM_BASE + 0x474)
+#define DRAMC_DPY_CLK_SW_CON_1         (SPM_BASE + 0x478)
+#define DRAMC_DPY_CLK_SW_CON_2         (SPM_BASE + 0x47C)
+#define DRAMC_DPY_CLK_SW_CON_3         (SPM_BASE + 0x480)
+#define DRAMC_DPY_CLK_SW_SEL_0         (SPM_BASE + 0x484)
+#define DRAMC_DPY_CLK_SW_SEL_1         (SPM_BASE + 0x488)
+#define DRAMC_DPY_CLK_SW_SEL_2         (SPM_BASE + 0x48C)
+#define DRAMC_DPY_CLK_SW_SEL_3         (SPM_BASE + 0x490)
+#define DRAMC_DPY_CLK_SPM_CON          (SPM_BASE + 0x494)
+#define SPM_DVFS_LEVEL                 (SPM_BASE + 0x498)
+#define SPM_CIRQ_CON                   (SPM_BASE + 0x49C)
+#define SPM_DVFS_MISC                  (SPM_BASE + 0x4A0)
+#define RG_MODULE_SW_CG_0_MASK_REQ_0   (SPM_BASE + 0x4A4)
+#define RG_MODULE_SW_CG_0_MASK_REQ_1   (SPM_BASE + 0x4A8)
+#define RG_MODULE_SW_CG_0_MASK_REQ_2   (SPM_BASE + 0x4AC)
+#define RG_MODULE_SW_CG_1_MASK_REQ_0   (SPM_BASE + 0x4B0)
+#define RG_MODULE_SW_CG_1_MASK_REQ_1   (SPM_BASE + 0x4B4)
+#define RG_MODULE_SW_CG_1_MASK_REQ_2   (SPM_BASE + 0x4B8)
+#define RG_MODULE_SW_CG_2_MASK_REQ_0   (SPM_BASE + 0x4BC)
+#define RG_MODULE_SW_CG_2_MASK_REQ_1   (SPM_BASE + 0x4C0)
+#define RG_MODULE_SW_CG_2_MASK_REQ_2   (SPM_BASE + 0x4C4)
+#define RG_MODULE_SW_CG_3_MASK_REQ_0   (SPM_BASE + 0x4C8)
+#define RG_MODULE_SW_CG_3_MASK_REQ_1   (SPM_BASE + 0x4CC)
+#define RG_MODULE_SW_CG_3_MASK_REQ_2   (SPM_BASE + 0x4D0)
+#define PWR_STATUS_MASK_REQ_0          (SPM_BASE + 0x4D4)
+#define PWR_STATUS_MASK_REQ_1          (SPM_BASE + 0x4D8)
+#define PWR_STATUS_MASK_REQ_2          (SPM_BASE + 0x4DC)
+#define SPM_CG_CHECK_CON               (SPM_BASE + 0x4E0)
+#define SPM_SRC_RDY_STA                (SPM_BASE + 0x4E4)
+#define SPM_DVS_DFS_LEVEL              (SPM_BASE + 0x4E8)
+#define SPM_FORCE_DVFS                 (SPM_BASE + 0x4EC)
+#define DRAMC_MCU_SRAM_CON             (SPM_BASE + 0x4F0)
+#define DRAMC_MCU2_SRAM_CON            (SPM_BASE + 0x4F4)
+#define DPY_SHU_SRAM_CON               (SPM_BASE + 0x4F8)
+#define DPY_SHU2_SRAM_CON              (SPM_BASE + 0x4FC)
+/*******The Others*************************************************/
+#define SRCLKEN_RC_CFG                 (SPM_BASE + 0x500)
+#define RC_CENTRAL_CFG1                (SPM_BASE + 0x504)
+#define RC_CENTRAL_CFG2                (SPM_BASE + 0x508)
+#define RC_CMD_ARB_CFG                 (SPM_BASE + 0x50C)
+#define RC_PMIC_RCEN_ADDR              (SPM_BASE + 0x510)
+#define RC_PMIC_RCEN_SET_CLR_ADDR      (SPM_BASE + 0x514)
+#define RC_DCXO_FPM_CFG                (SPM_BASE + 0x518)
+#define RC_CENTRAL_CFG3                (SPM_BASE + 0x51C)
+#define RC_M00_SRCLKEN_CFG             (SPM_BASE + 0x520)
+#define RC_M01_SRCLKEN_CFG             (SPM_BASE + 0x524)
+#define RC_M02_SRCLKEN_CFG             (SPM_BASE + 0x528)
+#define RC_M03_SRCLKEN_CFG             (SPM_BASE + 0x52C)
+#define RC_M04_SRCLKEN_CFG             (SPM_BASE + 0x530)
+#define RC_M05_SRCLKEN_CFG             (SPM_BASE + 0x534)
+#define RC_M06_SRCLKEN_CFG             (SPM_BASE + 0x538)
+#define RC_M07_SRCLKEN_CFG             (SPM_BASE + 0x53C)
+#define RC_M08_SRCLKEN_CFG             (SPM_BASE + 0x540)
+#define RC_M09_SRCLKEN_CFG             (SPM_BASE + 0x544)
+#define RC_M10_SRCLKEN_CFG             (SPM_BASE + 0x548)
+#define RC_M11_SRCLKEN_CFG             (SPM_BASE + 0x54C)
+#define RC_M12_SRCLKEN_CFG             (SPM_BASE + 0x550)
+#define RC_SRCLKEN_SW_CON_CFG          (SPM_BASE + 0x554)
+#define RC_CENTRAL_CFG4                (SPM_BASE + 0x558)
+#define RC_PROTOCOL_CHK_CFG            (SPM_BASE + 0x560)
+#define RC_DEBUG_CFG                   (SPM_BASE + 0x564)
+#define RC_MISC_0                      (SPM_BASE + 0x5B4)
+
+#define SUBSYS_INTF_CFG                (SPM_BASE + 0x5BC)
+#define PCM_WDT_LATCH_25               (SPM_BASE + 0x5C0)
+#define PCM_WDT_LATCH_26               (SPM_BASE + 0x5C4)
+#define PCM_WDT_LATCH_27               (SPM_BASE + 0x5C8)
+#define PCM_WDT_LATCH_28               (SPM_BASE + 0x5CC)
+#define PCM_WDT_LATCH_29               (SPM_BASE + 0x5D0)
+#define PCM_WDT_LATCH_30               (SPM_BASE + 0x5D4)
+#define PCM_WDT_LATCH_31               (SPM_BASE + 0x5D8)
+#define PCM_WDT_LATCH_32               (SPM_BASE + 0x5DC)
+#define PCM_WDT_LATCH_33               (SPM_BASE + 0x5E0)
+#define PCM_WDT_LATCH_34               (SPM_BASE + 0x5E4)
+#define PCM_WDT_LATCH_35               (SPM_BASE + 0x5EC)
+#define PCM_WDT_LATCH_36               (SPM_BASE + 0x5F0)
+#define PCM_WDT_LATCH_37               (SPM_BASE + 0x5F4)
+#define PCM_WDT_LATCH_38               (SPM_BASE + 0x5F8)
+#define PCM_WDT_LATCH_39               (SPM_BASE + 0x5FC)
+/*******Register_RSV*************************************************/
+#define SPM_SW_FLAG_0                  (SPM_BASE + 0x600)
+#define SPM_SW_DEBUG_0                 (SPM_BASE + 0x604)
+#define SPM_SW_FLAG_1                  (SPM_BASE + 0x608)
+#define SPM_SW_DEBUG_1                 (SPM_BASE + 0x60C)
+#define SPM_SW_RSV_0                   (SPM_BASE + 0x610)
+#define SPM_SW_RSV_1                   (SPM_BASE + 0x614)
+#define SPM_SW_RSV_2                   (SPM_BASE + 0x618)
+#define SPM_SW_RSV_3                   (SPM_BASE + 0x61C)
+#define SPM_SW_RSV_4                   (SPM_BASE + 0x620)
+#define SPM_SW_RSV_5                   (SPM_BASE + 0x624)
+#define SPM_SW_RSV_6                   (SPM_BASE + 0x628)
+#define SPM_SW_RSV_7                   (SPM_BASE + 0x62C)
+#define SPM_SW_RSV_8                   (SPM_BASE + 0x630)
+#define SPM_BK_WAKE_EVENT              (SPM_BASE + 0x634)
+#define SPM_BK_VTCXO_DUR               (SPM_BASE + 0x638)
+#define SPM_BK_WAKE_MISC               (SPM_BASE + 0x63C)
+#define SPM_BK_PCM_TIMER               (SPM_BASE + 0x640)
+#define ULPOSC_CON                     (SPM_BASE + 0x644)
+#define SPM_RSV_CON_0                  (SPM_BASE + 0x650)
+#define SPM_RSV_CON_1                  (SPM_BASE + 0x654)
+#define SPM_RSV_STA_0                  (SPM_BASE + 0x658)
+#define SPM_RSV_STA_1                  (SPM_BASE + 0x65C)
+#define SPM_SPARE_CON                  (SPM_BASE + 0x660)
+#define SPM_SPARE_CON_SET              (SPM_BASE + 0x664)
+#define SPM_SPARE_CON_CLR              (SPM_BASE + 0x668)
+#define SPM_CROSS_WAKE_M00_REQ         (SPM_BASE + 0x66C)
+#define SPM_CROSS_WAKE_M01_REQ         (SPM_BASE + 0x670)
+#define SPM_CROSS_WAKE_M02_REQ         (SPM_BASE + 0x674)
+#define SPM_CROSS_WAKE_M03_REQ         (SPM_BASE + 0x678)
+#define SCP_VCORE_LEVEL                (SPM_BASE + 0x67C)
+#define SC_MM_CK_SEL_CON               (SPM_BASE + 0x680)
+#define SPARE_ACK_MASK                 (SPM_BASE + 0x684)
+#define SPM_DV_CON_0                   (SPM_BASE + 0x68C)
+#define SPM_DV_CON_1                   (SPM_BASE + 0x690)
+#define SPM_DV_STA                     (SPM_BASE + 0x694)
+#define CONN_XOWCN_DEBUG_EN            (SPM_BASE + 0x698)
+#define SPM_SEMA_M0                    (SPM_BASE + 0x69C)
+#define SPM_SEMA_M1                    (SPM_BASE + 0x6A0)
+#define SPM_SEMA_M2                    (SPM_BASE + 0x6A4)
+#define SPM_SEMA_M3                    (SPM_BASE + 0x6A8)
+#define SPM_SEMA_M4                    (SPM_BASE + 0x6AC)
+#define SPM_SEMA_M5                    (SPM_BASE + 0x6B0)
+#define SPM_SEMA_M6                    (SPM_BASE + 0x6B4)
+#define SPM_SEMA_M7                    (SPM_BASE + 0x6B8)
+#define SPM2ADSP_MAILBOX               (SPM_BASE + 0x6BC)
+#define ADSP2SPM_MAILBOX               (SPM_BASE + 0x6C0)
+#define SPM_ADSP_IRQ                   (SPM_BASE + 0x6C4)
+#define SPM_MD32_IRQ                   (SPM_BASE + 0x6C8)
+#define SPM2PMCU_MAILBOX_0             (SPM_BASE + 0x6CC)
+#define SPM2PMCU_MAILBOX_1             (SPM_BASE + 0x6D0)
+#define SPM2PMCU_MAILBOX_2             (SPM_BASE + 0x6D4)
+#define SPM2PMCU_MAILBOX_3             (SPM_BASE + 0x6D8)
+#define PMCU2SPM_MAILBOX_0             (SPM_BASE + 0x6DC)
+#define PMCU2SPM_MAILBOX_1             (SPM_BASE + 0x6E0)
+#define PMCU2SPM_MAILBOX_2             (SPM_BASE + 0x6E4)
+#define PMCU2SPM_MAILBOX_3             (SPM_BASE + 0x6E8)
+#define UFS_PSRI_SW                    (SPM_BASE + 0x6EC)
+#define UFS_PSRI_SW_SET                (SPM_BASE + 0x6F0)
+#define UFS_PSRI_SW_CLR                (SPM_BASE + 0x6F4)
+#define SPM_AP_SEMA                    (SPM_BASE + 0x6F8)
+#define SPM_SPM_SEMA                   (SPM_BASE + 0x6FC)
+/*******Register_DVFS_TAB*************************************************/
+#define SPM_DVFS_CON                   (SPM_BASE + 0x700)
+#define SPM_DVFS_CON_STA               (SPM_BASE + 0x704)
+#define SPM_PMIC_SPMI_CON              (SPM_BASE + 0x708)
+#define SPM_DVFS_CMD0                  (SPM_BASE + 0x710)
+#define SPM_DVFS_CMD1                  (SPM_BASE + 0x714)
+#define SPM_DVFS_CMD2                  (SPM_BASE + 0x718)
+#define SPM_DVFS_CMD3                  (SPM_BASE + 0x71C)
+#define SPM_DVFS_CMD4                  (SPM_BASE + 0x720)
+#define SPM_DVFS_CMD5                  (SPM_BASE + 0x724)
+#define SPM_DVFS_CMD6                  (SPM_BASE + 0x728)
+#define SPM_DVFS_CMD7                  (SPM_BASE + 0x72C)
+#define SPM_DVFS_CMD8                  (SPM_BASE + 0x730)
+#define SPM_DVFS_CMD9                  (SPM_BASE + 0x734)
+#define SPM_DVFS_CMD10                 (SPM_BASE + 0x738)
+#define SPM_DVFS_CMD11                 (SPM_BASE + 0x73C)
+#define SPM_DVFS_CMD12                 (SPM_BASE + 0x740)
+#define SPM_DVFS_CMD13                 (SPM_BASE + 0x744)
+#define SPM_DVFS_CMD14                 (SPM_BASE + 0x748)
+#define SPM_DVFS_CMD15                 (SPM_BASE + 0x74C)
+#define SPM_DVFS_CMD16                 (SPM_BASE + 0x750)
+#define SPM_DVFS_CMD17                 (SPM_BASE + 0x754)
+#define SPM_DVFS_CMD18                 (SPM_BASE + 0x758)
+#define SPM_DVFS_CMD19                 (SPM_BASE + 0x75C)
+#define SPM_DVFS_CMD20                 (SPM_BASE + 0x760)
+#define SPM_DVFS_CMD21                 (SPM_BASE + 0x764)
+#define SPM_DVFS_CMD22                 (SPM_BASE + 0x768)
+#define SPM_DVFS_CMD23                 (SPM_BASE + 0x76C)
+#define SYS_TIMER_VALUE_L              (SPM_BASE + 0x770)
+#define SYS_TIMER_VALUE_H              (SPM_BASE + 0x774)
+#define SYS_TIMER_START_L              (SPM_BASE + 0x778)
+#define SYS_TIMER_START_H              (SPM_BASE + 0x77C)
+#define SYS_TIMER_LATCH_L_00           (SPM_BASE + 0x780)
+#define SYS_TIMER_LATCH_H_00           (SPM_BASE + 0x784)
+#define SYS_TIMER_LATCH_L_01           (SPM_BASE + 0x788)
+#define SYS_TIMER_LATCH_H_01           (SPM_BASE + 0x78C)
+#define SYS_TIMER_LATCH_L_02           (SPM_BASE + 0x790)
+#define SYS_TIMER_LATCH_H_02           (SPM_BASE + 0x794)
+#define SYS_TIMER_LATCH_L_03           (SPM_BASE + 0x798)
+#define SYS_TIMER_LATCH_H_03           (SPM_BASE + 0x79C)
+#define SYS_TIMER_LATCH_L_04           (SPM_BASE + 0x7A0)
+#define SYS_TIMER_LATCH_H_04           (SPM_BASE + 0x7A4)
+#define SYS_TIMER_LATCH_L_05           (SPM_BASE + 0x7A8)
+#define SYS_TIMER_LATCH_H_05           (SPM_BASE + 0x7AC)
+#define SYS_TIMER_LATCH_L_06           (SPM_BASE + 0x7B0)
+#define SYS_TIMER_LATCH_H_06           (SPM_BASE + 0x7B4)
+#define SYS_TIMER_LATCH_L_07           (SPM_BASE + 0x7B8)
+#define SYS_TIMER_LATCH_H_07           (SPM_BASE + 0x7BC)
+#define SYS_TIMER_LATCH_L_08           (SPM_BASE + 0x7C0)
+#define SYS_TIMER_LATCH_H_08           (SPM_BASE + 0x7C4)
+#define SYS_TIMER_LATCH_L_09           (SPM_BASE + 0x7C8)
+#define SYS_TIMER_LATCH_H_09           (SPM_BASE + 0x7CC)
+#define SYS_TIMER_LATCH_L_10           (SPM_BASE + 0x7D0)
+#define SYS_TIMER_LATCH_H_10           (SPM_BASE + 0x7D4)
+#define SYS_TIMER_LATCH_L_11           (SPM_BASE + 0x7D8)
+#define SYS_TIMER_LATCH_H_11           (SPM_BASE + 0x7DC)
+#define SYS_TIMER_LATCH_L_12           (SPM_BASE + 0x7E0)
+#define SYS_TIMER_LATCH_H_12           (SPM_BASE + 0x7E4)
+#define SYS_TIMER_LATCH_L_13           (SPM_BASE + 0x7E8)
+#define SYS_TIMER_LATCH_H_13           (SPM_BASE + 0x7EC)
+#define SYS_TIMER_LATCH_L_14           (SPM_BASE + 0x7F0)
+#define SYS_TIMER_LATCH_H_14           (SPM_BASE + 0x7F4)
+#define SYS_TIMER_LATCH_L_15           (SPM_BASE + 0x7F8)
+#define SYS_TIMER_LATCH_H_15           (SPM_BASE + 0x7FC)
+/*******Register_LAT_STA*************************************************/
+#define PCM_WDT_LATCH_0                (SPM_BASE + 0x800)
+#define PCM_WDT_LATCH_1                (SPM_BASE + 0x804)
+#define PCM_WDT_LATCH_2                (SPM_BASE + 0x808)
+#define PCM_WDT_LATCH_3                (SPM_BASE + 0x80C)
+#define PCM_WDT_LATCH_4                (SPM_BASE + 0x810)
+#define PCM_WDT_LATCH_5                (SPM_BASE + 0x814)
+#define PCM_WDT_LATCH_6                (SPM_BASE + 0x818)
+#define PCM_WDT_LATCH_7                (SPM_BASE + 0x81C)
+#define PCM_WDT_LATCH_8                (SPM_BASE + 0x820)
+#define PCM_WDT_LATCH_9                (SPM_BASE + 0x824)
+#define PCM_WDT_LATCH_10               (SPM_BASE + 0x828)
+#define PCM_WDT_LATCH_11               (SPM_BASE + 0x82C)
+#define PCM_WDT_LATCH_12               (SPM_BASE + 0x830)
+#define PCM_WDT_LATCH_13               (SPM_BASE + 0x834)
+#define PCM_WDT_LATCH_14               (SPM_BASE + 0x838)
+#define PCM_WDT_LATCH_15               (SPM_BASE + 0x83C)
+#define PCM_WDT_LATCH_16               (SPM_BASE + 0x840)
+#define PCM_WDT_LATCH_17               (SPM_BASE + 0x844)
+#define PCM_WDT_LATCH_18               (SPM_BASE + 0x848)
+#define PCM_WDT_LATCH_SPARE_0          (SPM_BASE + 0x84C)
+#define PCM_WDT_LATCH_SPARE_1          (SPM_BASE + 0x850)
+#define PCM_WDT_LATCH_SPARE_2          (SPM_BASE + 0x854)
+#define PCM_WDT_LATCH_CONN_0           (SPM_BASE + 0x870)
+#define PCM_WDT_LATCH_CONN_1           (SPM_BASE + 0x874)
+#define PCM_WDT_LATCH_CONN_2           (SPM_BASE + 0x878)
+#define DRAMC_GATING_ERR_LATCH_CH0_0   (SPM_BASE + 0x8A0)
+#define DRAMC_GATING_ERR_LATCH_CH0_1   (SPM_BASE + 0x8A4)
+#define DRAMC_GATING_ERR_LATCH_CH0_2   (SPM_BASE + 0x8A8)
+#define DRAMC_GATING_ERR_LATCH_CH0_3   (SPM_BASE + 0x8AC)
+#define DRAMC_GATING_ERR_LATCH_CH0_4   (SPM_BASE + 0x8B0)
+#define DRAMC_GATING_ERR_LATCH_CH0_5   (SPM_BASE + 0x8B4)
+#define DRAMC_GATING_ERR_LATCH_CH0_6   (SPM_BASE + 0x8B8)
+#define DRAMC_GATING_ERR_LATCH_SPARE_0 (SPM_BASE + 0x8F4)
+/*******Register_SPM_ACK_CHK*************************************************/
+#define SPM_ACK_CHK_CON_0              (SPM_BASE + 0x900)
+#define SPM_ACK_CHK_PC_0               (SPM_BASE + 0x904)
+#define SPM_ACK_CHK_SEL_0              (SPM_BASE + 0x908)
+#define SPM_ACK_CHK_TIMER_0            (SPM_BASE + 0x90C)
+#define SPM_ACK_CHK_STA_0              (SPM_BASE + 0x910)
+#define SPM_ACK_CHK_SWINT_0            (SPM_BASE + 0x914)
+#define SPM_ACK_CHK_CON_1              (SPM_BASE + 0x920)
+#define SPM_ACK_CHK_PC_1               (SPM_BASE + 0x924)
+#define SPM_ACK_CHK_SEL_1              (SPM_BASE + 0x928)
+#define SPM_ACK_CHK_TIMER_1            (SPM_BASE + 0x92C)
+#define SPM_ACK_CHK_STA_1              (SPM_BASE + 0x930)
+#define SPM_ACK_CHK_SWINT_1            (SPM_BASE + 0x934)
+#define SPM_ACK_CHK_CON_2              (SPM_BASE + 0x940)
+#define SPM_ACK_CHK_PC_2               (SPM_BASE + 0x944)
+#define SPM_ACK_CHK_SEL_2              (SPM_BASE + 0x948)
+#define SPM_ACK_CHK_TIMER_2            (SPM_BASE + 0x94C)
+#define SPM_ACK_CHK_STA_2              (SPM_BASE + 0x950)
+#define SPM_ACK_CHK_SWINT_2            (SPM_BASE + 0x954)
+#define SPM_ACK_CHK_CON_3              (SPM_BASE + 0x960)
+#define SPM_ACK_CHK_PC_3               (SPM_BASE + 0x964)
+#define SPM_ACK_CHK_SEL_3              (SPM_BASE + 0x968)
+#define SPM_ACK_CHK_TIMER_3            (SPM_BASE + 0x96C)
+#define SPM_ACK_CHK_STA_3              (SPM_BASE + 0x970)
+#define SPM_ACK_CHK_SWINT_3            (SPM_BASE + 0x974)
+#define SPM_COUNTER_0                  (SPM_BASE + 0x978)
+#define SPM_COUNTER_1                  (SPM_BASE + 0x97C)
+#define SPM_COUNTER_2                  (SPM_BASE + 0x980)
+#define SYS_TIMER_CON                  (SPM_BASE + 0x98C)
+#define SPM_TWAM_CON                   (SPM_BASE + 0x990)
+#define SPM_TWAM_WINDOW_LEN            (SPM_BASE + 0x994)
+#define SPM_TWAM_IDLE_SEL              (SPM_BASE + 0x998)
+#define SPM_TWAM_EVENT_CLEAR           (SPM_BASE + 0x99C)
+/*******The OTHERS*************************************************/
+#define RC_FSM_STA_0                   (SPM_BASE + 0xE00)
+#define RC_CMD_STA_0                   (SPM_BASE + 0xE04)
+#define RC_CMD_STA_1                   (SPM_BASE + 0xE08)
+#define RC_SPI_STA_0                   (SPM_BASE + 0xE0C)
+#define RC_PI_PO_STA_0                 (SPM_BASE + 0xE10)
+#define RC_M00_REQ_STA_0               (SPM_BASE + 0xE14)
+#define RC_M01_REQ_STA_0               (SPM_BASE + 0xE1C)
+#define RC_M02_REQ_STA_0               (SPM_BASE + 0xE20)
+#define RC_M03_REQ_STA_0               (SPM_BASE + 0xE24)
+#define RC_M04_REQ_STA_0               (SPM_BASE + 0xE28)
+#define RC_M05_REQ_STA_0               (SPM_BASE + 0xE2C)
+#define RC_M06_REQ_STA_0               (SPM_BASE + 0xE30)
+#define RC_M07_REQ_STA_0               (SPM_BASE + 0xE34)
+#define RC_M08_REQ_STA_0               (SPM_BASE + 0xE38)
+#define RC_M09_REQ_STA_0               (SPM_BASE + 0xE3C)
+#define RC_M10_REQ_STA_0               (SPM_BASE + 0xE40)
+#define RC_M11_REQ_STA_0               (SPM_BASE + 0xE44)
+#define RC_M12_REQ_STA_0               (SPM_BASE + 0xE48)
+#define RC_DEBUG_STA_0                 (SPM_BASE + 0xE4C)
+#define RC_DEBUG_TRACE_0_LSB           (SPM_BASE + 0xE50)
+#define RC_DEBUG_TRACE_0_MSB           (SPM_BASE + 0xE54)
+#define RC_DEBUG_TRACE_1_LSB           (SPM_BASE + 0xE5C)
+#define RC_DEBUG_TRACE_1_MSB           (SPM_BASE + 0xE60)
+#define RC_DEBUG_TRACE_2_LSB           (SPM_BASE + 0xE64)
+#define RC_DEBUG_TRACE_2_MSB           (SPM_BASE + 0xE6C)
+#define RC_DEBUG_TRACE_3_LSB           (SPM_BASE + 0xE70)
+#define RC_DEBUG_TRACE_3_MSB           (SPM_BASE + 0xE74)
+#define RC_DEBUG_TRACE_4_LSB           (SPM_BASE + 0xE78)
+#define RC_DEBUG_TRACE_4_MSB           (SPM_BASE + 0xE7C)
+#define RC_DEBUG_TRACE_5_LSB           (SPM_BASE + 0xE80)
+#define RC_DEBUG_TRACE_5_MSB           (SPM_BASE + 0xE84)
+#define RC_DEBUG_TRACE_6_LSB           (SPM_BASE + 0xE88)
+#define RC_DEBUG_TRACE_6_MSB           (SPM_BASE + 0xE8C)
+#define RC_DEBUG_TRACE_7_LSB           (SPM_BASE + 0xE90)
+#define RC_DEBUG_TRACE_7_MSB           (SPM_BASE + 0xE94)
+#define RC_SYS_TIMER_LATCH_0_LSB       (SPM_BASE + 0xE98)
+#define RC_SYS_TIMER_LATCH_0_MSB       (SPM_BASE + 0xE9C)
+#define RC_SYS_TIMER_LATCH_1_LSB       (SPM_BASE + 0xEA0)
+#define RC_SYS_TIMER_LATCH_1_MSB       (SPM_BASE + 0xEA4)
+#define RC_SYS_TIMER_LATCH_2_LSB       (SPM_BASE + 0xEA8)
+#define RC_SYS_TIMER_LATCH_2_MSB       (SPM_BASE + 0xEAC)
+#define RC_SYS_TIMER_LATCH_3_LSB       (SPM_BASE + 0xEB0)
+#define RC_SYS_TIMER_LATCH_3_MSB       (SPM_BASE + 0xEB4)
+#define RC_SYS_TIMER_LATCH_4_LSB       (SPM_BASE + 0xEB8)
+#define RC_SYS_TIMER_LATCH_4_MSB       (SPM_BASE + 0xEBC)
+#define RC_SYS_TIMER_LATCH_5_LSB       (SPM_BASE + 0xEC0)
+#define RC_SYS_TIMER_LATCH_5_MSB       (SPM_BASE + 0xEC4)
+#define RC_SYS_TIMER_LATCH_6_LSB       (SPM_BASE + 0xEC8)
+#define RC_SYS_TIMER_LATCH_6_MSB       (SPM_BASE + 0xECC)
+#define RC_SYS_TIMER_LATCH_7_LSB       (SPM_BASE + 0xED0)
+#define RC_SYS_TIMER_LATCH_7_MSB       (SPM_BASE + 0xED4)
+#define PCM_WDT_LATCH_19               (SPM_BASE + 0xED8)
+#define PCM_WDT_LATCH_20               (SPM_BASE + 0xEDC)
+#define PCM_WDT_LATCH_21               (SPM_BASE + 0xEE0)
+#define PCM_WDT_LATCH_22               (SPM_BASE + 0xEE4)
+#define PCM_WDT_LATCH_23               (SPM_BASE + 0xEE8)
+#define PCM_WDT_LATCH_24               (SPM_BASE + 0xEEC)
+/*******Register_PMSR*************************************************/
+#define PMSR_LAST_DAT                  (SPM_BASE + 0xF00)
+#define PMSR_LAST_CNT                  (SPM_BASE + 0xF04)
+#define PMSR_LAST_ACK                  (SPM_BASE + 0xF08)
+#define SPM_PMSR_SEL_CON0              (SPM_BASE + 0xF10)
+#define SPM_PMSR_SEL_CON1              (SPM_BASE + 0xF14)
+#define SPM_PMSR_SEL_CON2              (SPM_BASE + 0xF18)
+#define SPM_PMSR_SEL_CON3              (SPM_BASE + 0xF1C)
+#define SPM_PMSR_SEL_CON4              (SPM_BASE + 0xF20)
+#define SPM_PMSR_SEL_CON5              (SPM_BASE + 0xF24)
+#define SPM_PMSR_SEL_CON6              (SPM_BASE + 0xF28)
+#define SPM_PMSR_SEL_CON7              (SPM_BASE + 0xF2C)
+#define SPM_PMSR_SEL_CON8              (SPM_BASE + 0xF30)
+#define SPM_PMSR_SEL_CON9              (SPM_BASE + 0xF34)
+#define SPM_PMSR_SEL_CON10             (SPM_BASE + 0xF3C)
+#define SPM_PMSR_SEL_CON11             (SPM_BASE + 0xF40)
+#define SPM_PMSR_TIEMR_STA0            (SPM_BASE + 0xFB8)
+#define SPM_PMSR_TIEMR_STA1            (SPM_BASE + 0xFBC)
+#define SPM_PMSR_TIEMR_STA2            (SPM_BASE + 0xFC0)
+#define SPM_PMSR_GENERAL_CON0          (SPM_BASE + 0xFC4)
+#define SPM_PMSR_GENERAL_CON1          (SPM_BASE + 0xFC8)
+#define SPM_PMSR_GENERAL_CON2          (SPM_BASE + 0xFCC)
+#define SPM_PMSR_GENERAL_CON3          (SPM_BASE + 0xFD0)
+#define SPM_PMSR_GENERAL_CON4          (SPM_BASE + 0xFD4)
+#define SPM_PMSR_GENERAL_CON5          (SPM_BASE + 0xFD8)
+#define SPM_PMSR_SW_RESET              (SPM_BASE + 0xFDC)
+#define SPM_PMSR_MON_CON0              (SPM_BASE + 0xFE0)
+#define SPM_PMSR_MON_CON1              (SPM_BASE + 0xFE4)
+#define SPM_PMSR_MON_CON2              (SPM_BASE + 0xFE8)
+#define SPM_PMSR_LEN_CON0              (SPM_BASE + 0xFEC)
+#define SPM_PMSR_LEN_CON1              (SPM_BASE + 0xFF0)
+#define SPM_PMSR_LEN_CON2              (SPM_BASE + 0xFF4)
+/*******Register End*************************************************/
+
+/* POWERON_CONFIG_EN (0x10006000+0x000) */
+#define BCLK_CG_EN_LSB                      (1U << 0)       /* 1b */
+#define PROJECT_CODE_LSB                    (1U << 16)      /* 16b */
+/* SPM_POWER_ON_VAL0 (0x10006000+0x004) */
+#define POWER_ON_VAL0_LSB                   (1U << 0)       /* 32b */
+/* SPM_POWER_ON_VAL1 (0x10006000+0x008) */
+#define POWER_ON_VAL1_LSB                   (1U << 0)       /* 32b */
+/* SPM_CLK_CON (0x10006000+0x00C) */
+#define REG_SRCCLKEN0_CTL_LSB               (1U << 0)       /* 2b */
+#define REG_SRCCLKEN1_CTL_LSB               (1U << 2)       /* 2b */
+#define SYS_SETTLE_SEL_LSB                  (1U << 4)       /* 1b */
+#define REG_SPM_LOCK_INFRA_DCM_LSB          (1U << 5)       /* 1b */
+#define REG_SRCCLKEN_MASK_LSB               (1U << 6)       /* 3b */
+#define REG_MD1_C32RM_EN_LSB                (1U << 9)       /* 1b */
+#define REG_MD2_C32RM_EN_LSB                (1U << 10)      /* 1b */
+#define REG_CLKSQ0_SEL_CTRL_LSB             (1U << 11)      /* 1b */
+#define REG_CLKSQ1_SEL_CTRL_LSB             (1U << 12)      /* 1b */
+#define REG_SRCCLKEN0_EN_LSB                (1U << 13)      /* 1b */
+#define REG_SRCCLKEN1_EN_LSB                (1U << 14)      /* 1b */
+#define SCP_DCM_EN_LSB                      (1U << 15)      /* 1b */
+#define REG_SYSCLK0_SRC_MASK_B_LSB          (1U << 16)      /* 8b */
+#define REG_SYSCLK1_SRC_MASK_B_LSB          (1U << 24)      /* 8b */
+/* SPM_CLK_SETTLE (0x10006000+0x010) */
+#define SYSCLK_SETTLE_LSB                   (1U << 0)       /* 28b */
+/* SPM_AP_STANDBY_CON (0x10006000+0x014) */
+#define REG_WFI_OP_LSB                      (1U << 0)       /* 1b */
+#define REG_WFI_TYPE_LSB                    (1U << 1)       /* 1b */
+#define REG_MP0_CPUTOP_IDLE_MASK_LSB        (1U << 2)       /* 1b */
+#define REG_MP1_CPUTOP_IDLE_MASK_LSB        (1U << 3)       /* 1b */
+#define REG_MCUSYS_IDLE_MASK_LSB            (1U << 4)       /* 1b */
+#define REG_MD_APSRC_1_SEL_LSB              (1U << 25)      /* 1b */
+#define REG_MD_APSRC_0_SEL_LSB              (1U << 26)      /* 1b */
+#define REG_CONN_APSRC_SEL_LSB              (1U << 29)      /* 1b */
+/* PCM_CON0 (0x10006000+0x018) */
+#define PCM_CK_EN_LSB                       (1U << 2)       /* 1b */
+#define RG_EN_IM_SLEEP_DVS_LSB              (1U << 3)       /* 1b */
+#define PCM_CK_FROM_CKSYS_LSB               (1U << 4)       /* 1b */
+#define PCM_SW_RESET_LSB                    (1U << 15)      /* 1b */
+#define PCM_CON0_PROJECT_CODE_LSB           (1U << 16)      /* 16b */
+/* PCM_CON1 (0x10006000+0x01C) */
+#define RG_IM_SLAVE_LSB                     (1U << 0)       /* 1b */
+#define RG_IM_SLEEP_LSB                     (1U << 1)       /* 1b */
+#define REG_SPM_SRAM_CTRL_MUX_LSB           (1U << 2)       /* 1b */
+#define RG_AHBMIF_APBEN_LSB                 (1U << 3)       /* 1b */
+#define RG_IM_PDN_LSB                       (1U << 4)       /* 1b */
+#define RG_PCM_TIMER_EN_LSB                 (1U << 5)       /* 1b */
+#define SPM_EVENT_COUNTER_CLR_LSB           (1U << 6)       /* 1b */
+#define RG_DIS_MIF_PROT_LSB                 (1U << 7)       /* 1b */
+#define RG_PCM_WDT_EN_LSB                   (1U << 8)       /* 1b */
+#define RG_PCM_WDT_WAKE_LSB                 (1U << 9)       /* 1b */
+#define REG_SPM_SRAM_SLEEP_B_LSB            (1U << 10)      /* 1b */
+#define REG_SPM_SRAM_ISOINT_B_LSB           (1U << 11)      /* 1b */
+#define REG_EVENT_LOCK_EN_LSB               (1U << 12)      /* 1b */
+#define REG_SRCCLKEN_FAST_RESP_LSB          (1U << 13)      /* 1b */
+#define REG_MD32_APB_INTERNAL_EN_LSB        (1U << 14)      /* 1b */
+#define RG_PCM_IRQ_MSK_LSB                  (1U << 15)      /* 1b */
+#define PCM_CON1_PROJECT_CODE_LSB           (1U << 16)      /* 16b */
+/* SPM_POWER_ON_VAL2 (0x10006000+0x020) */
+#define POWER_ON_VAL2_LSB                   (1U << 0)       /* 32b */
+/* SPM_POWER_ON_VAL3 (0x10006000+0x024) */
+#define POWER_ON_VAL3_LSB                   (1U << 0)       /* 32b */
+/* PCM_REG_DATA_INI (0x10006000+0x028) */
+#define PCM_REG_DATA_INI_LSB                (1U << 0)       /* 32b */
+/* PCM_PWR_IO_EN (0x10006000+0x02C) */
+#define PCM_PWR_IO_EN_LSB                   (1U << 0)       /* 8b */
+#define RG_RF_SYNC_EN_LSB                   (1U << 16)      /* 8b */
+/* PCM_TIMER_VAL (0x10006000+0x030) */
+#define REG_PCM_TIMER_VAL_LSB               (1U << 0)       /* 32b */
+/* PCM_WDT_VAL (0x10006000+0x034) */
+#define RG_PCM_WDT_VAL_LSB                  (1U << 0)       /* 32b */
+/* SPM_SW_RST_CON (0x10006000+0x040) */
+#define SPM_SW_RST_CON_LSB                  (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_PROJECT_CODE_LSB     (1U << 16)      /* 16b */
+/* SPM_SW_RST_CON_SET (0x10006000+0x044) */
+#define SPM_SW_RST_CON_SET_LSB              (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_SET_PROJECT_CODE_LSB (1U << 16)      /* 16b */
+/* SPM_SW_RST_CON_CLR (0x10006000+0x048) */
+#define SPM_SW_RST_CON_CLR_LSB              (1U << 0)       /* 16b */
+#define SPM_SW_RST_CON_CLR_PROJECT_CODE_LSB (1U << 16)      /* 16b */
+/* VS1_PSR_MASK_B (0x10006000+0x04C) */
+#define VS1_OPP0_PSR_MASK_B_LSB             (1U << 0)       /* 8b */
+#define VS1_OPP1_PSR_MASK_B_LSB             (1U << 8)       /* 8b */
+/* VS2_PSR_MASK_B (0x10006000+0x050) */
+#define VS2_OPP0_PSR_MASK_B_LSB             (1U << 0)       /* 8b */
+#define VS2_OPP1_PSR_MASK_B_LSB             (1U << 8)       /* 8b */
+#define VS2_OPP2_PSR_MASK_B_LSB             (1U << 16)      /* 8b */
+/* MD32_CLK_CON (0x10006000+0x084) */
+#define REG_MD32_26M_CK_SEL_LSB             (1U << 0)       /* 1b */
+#define REG_MD32_DCM_EN_LSB                 (1U << 1)       /* 1b */
+/* SPM_SRAM_RSV_CON (0x10006000+0x088) */
+#define SPM_SRAM_SLEEP_B_ECO_EN_LSB         (1U << 0)       /* 1b */
+/* SPM_SWINT (0x10006000+0x08C) */
+#define SPM_SWINT_LSB                       (1U << 0)       /* 32b */
+/* SPM_SWINT_SET (0x10006000+0x090) */
+#define SPM_SWINT_SET_LSB                   (1U << 0)       /* 32b */
+/* SPM_SWINT_CLR (0x10006000+0x094) */
+#define SPM_SWINT_CLR_LSB                   (1U << 0)       /* 32b */
+/* SPM_SCP_MAILBOX (0x10006000+0x098) */
+#define SPM_SCP_MAILBOX_LSB                 (1U << 0)       /* 32b */
+/* SCP_SPM_MAILBOX (0x10006000+0x09C) */
+#define SCP_SPM_MAILBOX_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_CON (0x10006000+0x0A0) */
+#define REG_TWAM_ENABLE_LSB                 (1U << 0)       /* 1b */
+#define REG_TWAM_SPEED_MODE_EN_LSB          (1U << 1)       /* 1b */
+#define REG_TWAM_SW_RST_LSB                 (1U << 2)       /* 1b */
+#define REG_TWAM_IRQ_MASK_LSB               (1U << 3)       /* 1b */
+#define REG_TWAM_MON_TYPE_0_LSB             (1U << 4)       /* 2b */
+#define REG_TWAM_MON_TYPE_1_LSB             (1U << 6)       /* 2b */
+#define REG_TWAM_MON_TYPE_2_LSB             (1U << 8)       /* 2b */
+#define REG_TWAM_MON_TYPE_3_LSB             (1U << 10)      /* 2b */
+/* SPM_TWAM_WINDOW_LEN (0x10006000+0x0A4) */
+#define REG_TWAM_WINDOW_LEN_LSB             (1U << 0)       /* 32b */
+/* SPM_TWAM_IDLE_SEL (0x10006000+0x0A8) */
+#define REG_TWAM_SIG_SEL_0_LSB              (1U << 0)       /* 7b */
+#define REG_TWAM_SIG_SEL_1_LSB              (1U << 8)       /* 7b */
+#define REG_TWAM_SIG_SEL_2_LSB              (1U << 16)      /* 7b */
+#define REG_TWAM_SIG_SEL_3_LSB              (1U << 24)      /* 7b */
+/* SPM_SCP_IRQ (0x10006000+0x0AC) */
+#define SC_SPM2SCP_WAKEUP_LSB               (1U << 0)       /* 1b */
+#define SC_SCP2SPM_WAKEUP_LSB               (1U << 4)       /* 1b */
+/* SPM_CPU_WAKEUP_EVENT (0x10006000+0x0B0) */
+#define REG_CPU_WAKEUP_LSB                  (1U << 0)       /* 1b */
+/* SPM_IRQ_MASK (0x10006000+0x0B4) */
+#define REG_SPM_IRQ_MASK_LSB                (1U << 0)       /* 32b */
+/* DDR_EN_DBC (0x10006000+0x0B4) */
+#define REG_ALL_DDR_EN_DBC_EN_LSB           (1U << 16)       /* 1b */
+/* SPM_SRC_REQ (0x10006000+0x0B8) */
+#define REG_SPM_APSRC_REQ_LSB               (1U << 0)       /* 1b */
+#define REG_SPM_F26M_REQ_LSB                (1U << 1)       /* 1b */
+#define REG_SPM_INFRA_REQ_LSB               (1U << 3)       /* 1b */
+#define REG_SPM_VRF18_REQ_LSB               (1U << 4)       /* 1b */
+#define REG_SPM_DDR_EN_REQ_LSB              (1U << 7)       /* 1b */
+#define REG_SPM_DVFS_REQ_LSB                (1U << 8)       /* 1b */
+#define REG_SPM_SW_MAILBOX_REQ_LSB          (1U << 9)       /* 1b */
+#define REG_SPM_SSPM_MAILBOX_REQ_LSB        (1U << 10)      /* 1b */
+#define REG_SPM_ADSP_MAILBOX_REQ_LSB        (1U << 11)      /* 1b */
+#define REG_SPM_SCP_MAILBOX_REQ_LSB         (1U << 12)      /* 1b */
+/* SPM_SRC_MASK (0x10006000+0x0BC) */
+#define REG_MD_SRCCLKENA_0_MASK_B_LSB       (1U << 0)       /* 1b */
+#define REG_MD_SRCCLKENA2INFRA_REQ_0_MASK_B_LSB (1U << 1)       /* 1b */
+#define REG_MD_APSRC2INFRA_REQ_0_MASK_B_LSB (1U << 2)       /* 1b */
+#define REG_MD_APSRC_REQ_0_MASK_B_LSB       (1U << 3)       /* 1b */
+#define REG_MD_VRF18_REQ_0_MASK_B_LSB       (1U << 4)       /* 1b */
+#define REG_MD_DDR_EN_0_MASK_B_LSB          (1U << 5)       /* 1b */
+#define REG_MD_SRCCLKENA_1_MASK_B_LSB       (1U << 6)       /* 1b */
+#define REG_MD_SRCCLKENA2INFRA_REQ_1_MASK_B_LSB (1U << 7)       /* 1b */
+#define REG_MD_APSRC2INFRA_REQ_1_MASK_B_LSB (1U << 8)       /* 1b */
+#define REG_MD_APSRC_REQ_1_MASK_B_LSB       (1U << 9)       /* 1b */
+#define REG_MD_VRF18_REQ_1_MASK_B_LSB       (1U << 10)      /* 1b */
+#define REG_MD_DDR_EN_1_MASK_B_LSB          (1U << 11)      /* 1b */
+#define REG_CONN_SRCCLKENA_MASK_B_LSB       (1U << 12)      /* 1b */
+#define REG_CONN_SRCCLKENB_MASK_B_LSB       (1U << 13)      /* 1b */
+#define REG_CONN_INFRA_REQ_MASK_B_LSB       (1U << 14)      /* 1b */
+#define REG_CONN_APSRC_REQ_MASK_B_LSB       (1U << 15)      /* 1b */
+#define REG_CONN_VRF18_REQ_MASK_B_LSB       (1U << 16)      /* 1b */
+#define REG_CONN_DDR_EN_MASK_B_LSB          (1U << 17)      /* 1b */
+#define REG_CONN_VFE28_MASK_B_LSB           (1U << 18)      /* 1b */
+#define REG_SRCCLKENI0_SRCCLKENA_MASK_B_LSB (1U << 19)      /* 1b */
+#define REG_SRCCLKENI0_INFRA_REQ_MASK_B_LSB (1U << 20)      /* 1b */
+#define REG_SRCCLKENI1_SRCCLKENA_MASK_B_LSB (1U << 21)      /* 1b */
+#define REG_SRCCLKENI1_INFRA_REQ_MASK_B_LSB (1U << 22)      /* 1b */
+#define REG_SRCCLKENI2_SRCCLKENA_MASK_B_LSB (1U << 23)      /* 1b */
+#define REG_SRCCLKENI2_INFRA_REQ_MASK_B_LSB (1U << 24)      /* 1b */
+#define REG_INFRASYS_APSRC_REQ_MASK_B_LSB   (1U << 25)      /* 1b */
+#define REG_INFRASYS_DDR_EN_MASK_B_LSB      (1U << 26)      /* 1b */
+#define REG_MD32_SRCCLKENA_MASK_B_LSB       (1U << 27)      /* 1b */
+#define REG_MD32_INFRA_REQ_MASK_B_LSB       (1U << 28)      /* 1b */
+#define REG_MD32_APSRC_REQ_MASK_B_LSB       (1U << 29)      /* 1b */
+#define REG_MD32_VRF18_REQ_MASK_B_LSB       (1U << 30)      /* 1b */
+#define REG_MD32_DDR_EN_MASK_B_LSB          (1U << 31)      /* 1b */
+/* SPM_SRC2_MASK (0x10006000+0x0C0) */
+#define REG_SCP_SRCCLKENA_MASK_B_LSB        (1U << 0)       /* 1b */
+#define REG_SCP_INFRA_REQ_MASK_B_LSB        (1U << 1)       /* 1b */
+#define REG_SCP_APSRC_REQ_MASK_B_LSB        (1U << 2)       /* 1b */
+#define REG_SCP_VRF18_REQ_MASK_B_LSB        (1U << 3)       /* 1b */
+#define REG_SCP_DDR_EN_MASK_B_LSB           (1U << 4)       /* 1b */
+#define REG_AUDIO_DSP_SRCCLKENA_MASK_B_LSB  (1U << 5)       /* 1b */
+#define REG_AUDIO_DSP_INFRA_REQ_MASK_B_LSB  (1U << 6)       /* 1b */
+#define REG_AUDIO_DSP_APSRC_REQ_MASK_B_LSB  (1U << 7)       /* 1b */
+#define REG_AUDIO_DSP_VRF18_REQ_MASK_B_LSB  (1U << 8)       /* 1b */
+#define REG_AUDIO_DSP_DDR_EN_MASK_B_LSB     (1U << 9)       /* 1b */
+#define REG_UFS_SRCCLKENA_MASK_B_LSB        (1U << 10)      /* 1b */
+#define REG_UFS_INFRA_REQ_MASK_B_LSB        (1U << 11)      /* 1b */
+#define REG_UFS_APSRC_REQ_MASK_B_LSB        (1U << 12)      /* 1b */
+#define REG_UFS_VRF18_REQ_MASK_B_LSB        (1U << 13)      /* 1b */
+#define REG_UFS_DDR_EN_MASK_B_LSB           (1U << 14)      /* 1b */
+#define REG_DISP0_APSRC_REQ_MASK_B_LSB      (1U << 15)      /* 1b */
+#define REG_DISP0_DDR_EN_MASK_B_LSB         (1U << 16)      /* 1b */
+#define REG_DISP1_APSRC_REQ_MASK_B_LSB      (1U << 17)      /* 1b */
+#define REG_DISP1_DDR_EN_MASK_B_LSB         (1U << 18)      /* 1b */
+#define REG_GCE_INFRA_REQ_MASK_B_LSB        (1U << 19)      /* 1b */
+#define REG_GCE_APSRC_REQ_MASK_B_LSB        (1U << 20)      /* 1b */
+#define REG_GCE_VRF18_REQ_MASK_B_LSB        (1U << 21)      /* 1b */
+#define REG_GCE_DDR_EN_MASK_B_LSB           (1U << 22)      /* 1b */
+#define REG_APU_SRCCLKENA_MASK_B_LSB        (1U << 23)      /* 1b */
+#define REG_APU_INFRA_REQ_MASK_B_LSB        (1U << 24)      /* 1b */
+#define REG_APU_APSRC_REQ_MASK_B_LSB        (1U << 25)      /* 1b */
+#define REG_APU_VRF18_REQ_MASK_B_LSB        (1U << 26)      /* 1b */
+#define REG_APU_DDR_EN_MASK_B_LSB           (1U << 27)      /* 1b */
+#define REG_CG_CHECK_SRCCLKENA_MASK_B_LSB   (1U << 28)      /* 1b */
+#define REG_CG_CHECK_APSRC_REQ_MASK_B_LSB   (1U << 29)      /* 1b */
+#define REG_CG_CHECK_VRF18_REQ_MASK_B_LSB   (1U << 30)      /* 1b */
+#define REG_CG_CHECK_DDR_EN_MASK_B_LSB      (1U << 31)      /* 1b */
+/* SPM_SRC3_MASK (0x10006000+0x0C4) */
+#define REG_DVFSRC_EVENT_TRIGGER_MASK_B_LSB (1U << 0)       /* 1b */
+#define REG_SW2SPM_INT0_MASK_B_LSB          (1U << 1)       /* 1b */
+#define REG_SW2SPM_INT1_MASK_B_LSB          (1U << 2)       /* 1b */
+#define REG_SW2SPM_INT2_MASK_B_LSB          (1U << 3)       /* 1b */
+#define REG_SW2SPM_INT3_MASK_B_LSB          (1U << 4)       /* 1b */
+#define REG_SC_ADSP2SPM_WAKEUP_MASK_B_LSB   (1U << 5)       /* 1b */
+#define REG_SC_SSPM2SPM_WAKEUP_MASK_B_LSB   (1U << 6)       /* 4b */
+#define REG_SC_SCP2SPM_WAKEUP_MASK_B_LSB    (1U << 10)      /* 1b */
+#define REG_CSYSPWRREQ_MASK_LSB             (1U << 11)      /* 1b */
+#define REG_SPM_SRCCLKENA_RESERVED_MASK_B_LSB (1U << 12)      /* 1b */
+#define REG_SPM_INFRA_REQ_RESERVED_MASK_B_LSB (1U << 13)      /* 1b */
+#define REG_SPM_APSRC_REQ_RESERVED_MASK_B_LSB (1U << 14)      /* 1b */
+#define REG_SPM_VRF18_REQ_RESERVED_MASK_B_LSB (1U << 15)      /* 1b */
+#define REG_SPM_DDR_EN_RESERVED_MASK_B_LSB  (1U << 16)      /* 1b */
+#define REG_MCUPM_SRCCLKENA_MASK_B_LSB      (1U << 17)      /* 1b */
+#define REG_MCUPM_INFRA_REQ_MASK_B_LSB      (1U << 18)      /* 1b */
+#define REG_MCUPM_APSRC_REQ_MASK_B_LSB      (1U << 19)      /* 1b */
+#define REG_MCUPM_VRF18_REQ_MASK_B_LSB      (1U << 20)      /* 1b */
+#define REG_MCUPM_DDR_EN_MASK_B_LSB         (1U << 21)      /* 1b */
+#define REG_MSDC0_SRCCLKENA_MASK_B_LSB      (1U << 22)      /* 1b */
+#define REG_MSDC0_INFRA_REQ_MASK_B_LSB      (1U << 23)      /* 1b */
+#define REG_MSDC0_APSRC_REQ_MASK_B_LSB      (1U << 24)      /* 1b */
+#define REG_MSDC0_VRF18_REQ_MASK_B_LSB      (1U << 25)      /* 1b */
+#define REG_MSDC0_DDR_EN_MASK_B_LSB         (1U << 26)      /* 1b */
+#define REG_MSDC1_SRCCLKENA_MASK_B_LSB      (1U << 27)      /* 1b */
+#define REG_MSDC1_INFRA_REQ_MASK_B_LSB      (1U << 28)      /* 1b */
+#define REG_MSDC1_APSRC_REQ_MASK_B_LSB      (1U << 29)      /* 1b */
+#define REG_MSDC1_VRF18_REQ_MASK_B_LSB      (1U << 30)      /* 1b */
+#define REG_MSDC1_DDR_EN_MASK_B_LSB         (1U << 31)      /* 1b */
+/* SPM_SRC4_MASK (0x10006000+0x0C8) */
+#define CCIF_EVENT_MASK_B_LSB               (1U << 0)       /* 16b */
+#define REG_BAK_PSRI_SRCCLKENA_MASK_B_LSB   (1U << 16)      /* 1b */
+#define REG_BAK_PSRI_INFRA_REQ_MASK_B_LSB   (1U << 17)      /* 1b */
+#define REG_BAK_PSRI_APSRC_REQ_MASK_B_LSB   (1U << 18)      /* 1b */
+#define REG_BAK_PSRI_VRF18_REQ_MASK_B_LSB   (1U << 19)      /* 1b */
+#define REG_BAK_PSRI_DDR_EN_MASK_B_LSB      (1U << 20)      /* 1b */
+#define REG_DRAMC0_MD32_INFRA_REQ_MASK_B_LSB (1U << 21)      /* 1b */
+#define REG_DRAMC0_MD32_VRF18_REQ_MASK_B_LSB (1U << 22)      /* 1b */
+#define REG_DRAMC1_MD32_INFRA_REQ_MASK_B_LSB (1U << 23)      /* 1b */
+#define REG_DRAMC1_MD32_VRF18_REQ_MASK_B_LSB (1U << 24)      /* 1b */
+#define REG_CONN_SRCCLKENB2PWRAP_MASK_B_LSB (1U << 25)      /* 1b */
+#define REG_DRAMC0_MD32_WAKEUP_MASK_LSB     (1U << 26)      /* 1b */
+#define REG_DRAMC1_MD32_WAKEUP_MASK_LSB     (1U << 27)      /* 1b */
+/* SPM_SRC5_MASK (0x10006000+0x0CC) */
+#define REG_MCUSYS_MERGE_APSRC_REQ_MASK_B_LSB (1U << 0)       /* 9b */
+#define REG_MCUSYS_MERGE_DDR_EN_MASK_B_LSB  (1U << 9)       /* 9b */
+/* SPM_WAKEUP_EVENT_MASK (0x10006000+0x0D0) */
+#define REG_WAKEUP_EVENT_MASK_LSB           (1U << 0)       /* 32b */
+/* SPM_WAKEUP_EVENT_EXT_MASK (0x10006000+0x0D4) */
+#define REG_EXT_WAKEUP_EVENT_MASK_LSB       (1U << 0)       /* 32b */
+/* SPM_TWAM_EVENT_CLEAR (0x10006000+0x0D8) */
+#define SPM_TWAM_EVENT_CLEAR_LSB            (1U << 0)       /* 1b */
+/* SCP_CLK_CON (0x10006000+0x0DC) */
+#define REG_SCP_26M_CK_SEL_LSB              (1U << 0)       /* 1b */
+#define REG_SCP_DCM_EN_LSB                  (1U << 1)       /* 1b */
+#define SCP_SECURE_V_REQ_MASK_LSB           (1U << 2)       /* 1b */
+#define SCP_SLP_REQ_LSB                     (1U << 3)       /* 1b */
+#define SCP_SLP_ACK_LSB                     (1U << 4)       /* 1b */
+/* SPM_RESOURCE_ACK_CON0 (0x10006000+0x0F0) */
+#define REG_MD_SRCCLKENA_ACK_0_MASK_LSB     (1U << 0)       /* 1b */
+#define REG_MD_INFRA_ACK_0_MASK_LSB         (1U << 1)       /* 1b */
+#define REG_MD_APSRC_ACK_0_MASK_LSB         (1U << 2)       /* 1b */
+#define REG_MD_VRF18_ACK_0_MASK_LSB         (1U << 3)       /* 1b */
+#define REG_MD_DDR_EN_ACK_0_MASK_LSB        (1U << 4)       /* 1b */
+#define REG_MD_SRCCLKENA_ACK_1_MASK_LSB     (1U << 5)       /* 1b */
+#define REG_MD_INFRA_ACK_1_MASK_LSB         (1U << 6)       /* 1b */
+#define REG_MD_APSRC_ACK_1_MASK_LSB         (1U << 7)       /* 1b */
+#define REG_MD_VRF18_ACK_1_MASK_LSB         (1U << 8)       /* 1b */
+#define REG_MD_DDR_EN_ACK_1_MASK_LSB        (1U << 9)       /* 1b */
+#define REG_CONN_SRCCLKENA_ACK_MASK_LSB     (1U << 10)      /* 1b */
+#define REG_CONN_INFRA_ACK_MASK_LSB         (1U << 11)      /* 1b */
+#define REG_CONN_APSRC_ACK_MASK_LSB         (1U << 12)      /* 1b */
+#define REG_CONN_VRF18_ACK_MASK_LSB         (1U << 13)      /* 1b */
+#define REG_CONN_DDR_EN_ACK_MASK_LSB        (1U << 14)      /* 1b */
+#define REG_MD32_SRCCLKENA_ACK_MASK_LSB     (1U << 15)      /* 1b */
+#define REG_MD32_INFRA_ACK_MASK_LSB         (1U << 16)      /* 1b */
+#define REG_MD32_APSRC_ACK_MASK_LSB         (1U << 17)      /* 1b */
+#define REG_MD32_VRF18_ACK_MASK_LSB         (1U << 18)      /* 1b */
+#define REG_MD32_DDR_EN_ACK_MASK_LSB        (1U << 19)      /* 1b */
+#define REG_SCP_SRCCLKENA_ACK_MASK_LSB      (1U << 20)      /* 1b */
+#define REG_SCP_INFRA_ACK_MASK_LSB          (1U << 21)      /* 1b */
+#define REG_SCP_APSRC_ACK_MASK_LSB          (1U << 22)      /* 1b */
+#define REG_SCP_VRF18_ACK_MASK_LSB          (1U << 23)      /* 1b */
+#define REG_SCP_DDR_EN_ACK_MASK_LSB         (1U << 24)      /* 1b */
+#define REG_AUDIO_DSP_SRCCLKENA_ACK_MASK_LSB (1U << 25)      /* 1b */
+#define REG_AUDIO_DSP_INFRA_ACK_MASK_LSB    (1U << 26)      /* 1b */
+#define REG_AUDIO_DSP_APSRC_ACK_MASK_LSB    (1U << 27)      /* 1b */
+#define REG_AUDIO_DSP_VRF18_ACK_MASK_LSB    (1U << 28)      /* 1b */
+#define REG_AUDIO_DSP_DDR_EN_ACK_MASK_LSB   (1U << 29)      /* 1b */
+#define REG_DISP0_DDR_EN_ACK_MASK_LSB       (1U << 30)      /* 1b */
+#define REG_DISP1_APSRC_ACK_MASK_LSB        (1U << 31)      /* 1b */
+/* SPM_RESOURCE_ACK_CON1 (0x10006000+0x0F4) */
+#define REG_UFS_SRCCLKENA_ACK_MASK_LSB      (1U << 0)       /* 1b */
+#define REG_UFS_INFRA_ACK_MASK_LSB          (1U << 1)       /* 1b */
+#define REG_UFS_APSRC_ACK_MASK_LSB          (1U << 2)       /* 1b */
+#define REG_UFS_VRF18_ACK_MASK_LSB          (1U << 3)       /* 1b */
+#define REG_UFS_DDR_EN_ACK_MASK_LSB         (1U << 4)       /* 1b */
+#define REG_APU_SRCCLKENA_ACK_MASK_LSB      (1U << 5)       /* 1b */
+#define REG_APU_INFRA_ACK_MASK_LSB          (1U << 6)       /* 1b */
+#define REG_APU_APSRC_ACK_MASK_LSB          (1U << 7)       /* 1b */
+#define REG_APU_VRF18_ACK_MASK_LSB          (1U << 8)       /* 1b */
+#define REG_APU_DDR_EN_ACK_MASK_LSB         (1U << 9)       /* 1b */
+#define REG_MCUPM_SRCCLKENA_ACK_MASK_LSB    (1U << 10)      /* 1b */
+#define REG_MCUPM_INFRA_ACK_MASK_LSB        (1U << 11)      /* 1b */
+#define REG_MCUPM_APSRC_ACK_MASK_LSB        (1U << 12)      /* 1b */
+#define REG_MCUPM_VRF18_ACK_MASK_LSB        (1U << 13)      /* 1b */
+#define REG_MCUPM_DDR_EN_ACK_MASK_LSB       (1U << 14)      /* 1b */
+#define REG_MSDC0_SRCCLKENA_ACK_MASK_LSB    (1U << 15)      /* 1b */
+#define REG_MSDC0_INFRA_ACK_MASK_LSB        (1U << 16)      /* 1b */
+#define REG_MSDC0_APSRC_ACK_MASK_LSB        (1U << 17)      /* 1b */
+#define REG_MSDC0_VRF18_ACK_MASK_LSB        (1U << 18)      /* 1b */
+#define REG_MSDC0_DDR_EN_ACK_MASK_LSB       (1U << 19)      /* 1b */
+#define REG_MSDC1_SRCCLKENA_ACK_MASK_LSB    (1U << 20)      /* 1b */
+#define REG_MSDC1_INFRA_ACK_MASK_LSB        (1U << 21)      /* 1b */
+#define REG_MSDC1_APSRC_ACK_MASK_LSB        (1U << 22)      /* 1b */
+#define REG_MSDC1_VRF18_ACK_MASK_LSB        (1U << 23)      /* 1b */
+#define REG_MSDC1_DDR_EN_ACK_MASK_LSB       (1U << 24)      /* 1b */
+#define REG_DISP0_APSRC_ACK_MASK_LSB        (1U << 25)      /* 1b */
+#define REG_DISP1_DDR_EN_ACK_MASK_LSB       (1U << 26)      /* 1b */
+#define REG_GCE_INFRA_ACK_MASK_LSB          (1U << 27)      /* 1b */
+#define REG_GCE_APSRC_ACK_MASK_LSB          (1U << 28)      /* 1b */
+#define REG_GCE_VRF18_ACK_MASK_LSB          (1U << 29)      /* 1b */
+#define REG_GCE_DDR_EN_ACK_MASK_LSB         (1U << 30)      /* 1b */
+/* SPM_RESOURCE_ACK_CON2 (0x10006000+0x0F8) */
+#define SPM_F26M_ACK_WAIT_CYCLE_LSB         (1U << 0)       /* 8b */
+#define SPM_INFRA_ACK_WAIT_CYCLE_LSB        (1U << 8)       /* 8b */
+#define SPM_APSRC_ACK_WAIT_CYCLE_LSB        (1U << 16)      /* 8b */
+#define SPM_VRF18_ACK_WAIT_CYCLE_LSB        (1U << 24)      /* 8b */
+/* SPM_RESOURCE_ACK_CON3 (0x10006000+0x0FC) */
+#define SPM_DDR_EN_ACK_WAIT_CYCLE_LSB       (1U << 0)       /* 8b */
+#define REG_BAK_PSRI_SRCCLKENA_ACK_MASK_LSB (1U << 8)       /* 1b */
+#define REG_BAK_PSRI_INFRA_ACK_MASK_LSB     (1U << 9)       /* 1b */
+#define REG_BAK_PSRI_APSRC_ACK_MASK_LSB     (1U << 10)      /* 1b */
+#define REG_BAK_PSRI_VRF18_ACK_MASK_LSB     (1U << 11)      /* 1b */
+#define REG_BAK_PSRI_DDR_EN_ACK_MASK_LSB    (1U << 12)      /* 1b */
+/* PCM_REG0_DATA (0x10006000+0x100) */
+#define PCM_REG0_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG2_DATA (0x10006000+0x104) */
+#define PCM_REG2_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG6_DATA (0x10006000+0x108) */
+#define PCM_REG6_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG7_DATA (0x10006000+0x10C) */
+#define PCM_REG7_RF_LSB                     (1U << 0)       /* 32b */
+/* PCM_REG13_DATA (0x10006000+0x110) */
+#define PCM_REG13_RF_LSB                    (1U << 0)       /* 32b */
+/* SRC_REQ_STA_0 (0x10006000+0x114) */
+#define MD_SRCCLKENA_0_LSB                  (1U << 0)       /* 1b */
+#define MD_SRCCLKENA2INFRA_REQ_0_LSB        (1U << 1)       /* 1b */
+#define MD_APSRC2INFRA_REQ_0_LSB            (1U << 2)       /* 1b */
+#define MD_APSRC_REQ_0_LSB                  (1U << 3)       /* 1b */
+#define MD_VRF18_REQ_0_LSB                  (1U << 4)       /* 1b */
+#define MD_DDR_EN_0_LSB                     (1U << 5)       /* 1b */
+#define MD_SRCCLKENA_1_LSB                  (1U << 6)       /* 1b */
+#define MD_SRCCLKENA2INFRA_REQ_1_LSB        (1U << 7)       /* 1b */
+#define MD_APSRC2INFRA_REQ_1_LSB            (1U << 8)       /* 1b */
+#define MD_APSRC_REQ_1_LSB                  (1U << 9)       /* 1b */
+#define MD_VRF18_REQ_1_LSB                  (1U << 10)      /* 1b */
+#define MD_DDR_EN_1_LSB                     (1U << 11)      /* 1b */
+#define CONN_SRCCLKENA_LSB                  (1U << 12)      /* 1b */
+#define CONN_SRCCLKENB_LSB                  (1U << 13)      /* 1b */
+#define CONN_INFRA_REQ_LSB                  (1U << 14)      /* 1b */
+#define CONN_APSRC_REQ_LSB                  (1U << 15)      /* 1b */
+#define CONN_VRF18_REQ_LSB                  (1U << 16)      /* 1b */
+#define CONN_DDR_EN_LSB                     (1U << 17)      /* 1b */
+#define SRCCLKENI_LSB                       (1U << 18)      /* 3b */
+#define MD32_SRCCLKENA_LSB                  (1U << 21)      /* 1b */
+#define MD32_INFRA_REQ_LSB                  (1U << 22)      /* 1b */
+#define MD32_APSRC_REQ_LSB                  (1U << 23)      /* 1b */
+#define MD32_VRF18_REQ_LSB                  (1U << 24)      /* 1b */
+#define MD32_DDR_EN_LSB                     (1U << 25)      /* 1b */
+#define DISP0_APSRC_REQ_LSB                 (1U << 26)      /* 1b */
+#define DISP0_DDR_EN_LSB                    (1U << 27)      /* 1b */
+#define DISP1_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define DISP1_DDR_EN_LSB                    (1U << 29)      /* 1b */
+#define DVFSRC_EVENT_TRIGGER_LSB            (1U << 30)      /* 1b */
+/* SRC_REQ_STA_1 (0x10006000+0x118) */
+#define SCP_SRCCLKENA_LSB                   (1U << 0)       /* 1b */
+#define SCP_INFRA_REQ_LSB                   (1U << 1)       /* 1b */
+#define SCP_APSRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define SCP_VRF18_REQ_LSB                   (1U << 3)       /* 1b */
+#define SCP_DDR_EN_LSB                      (1U << 4)       /* 1b */
+#define AUDIO_DSP_SRCCLKENA_LSB             (1U << 5)       /* 1b */
+#define AUDIO_DSP_INFRA_REQ_LSB             (1U << 6)       /* 1b */
+#define AUDIO_DSP_APSRC_REQ_LSB             (1U << 7)       /* 1b */
+#define AUDIO_DSP_VRF18_REQ_LSB             (1U << 8)       /* 1b */
+#define AUDIO_DSP_DDR_EN_LSB                (1U << 9)       /* 1b */
+#define UFS_SRCCLKENA_LSB                   (1U << 10)      /* 1b */
+#define UFS_INFRA_REQ_LSB                   (1U << 11)      /* 1b */
+#define UFS_APSRC_REQ_LSB                   (1U << 12)      /* 1b */
+#define UFS_VRF18_REQ_LSB                   (1U << 13)      /* 1b */
+#define UFS_DDR_EN_LSB                      (1U << 14)      /* 1b */
+#define GCE_INFRA_REQ_LSB                   (1U << 15)      /* 1b */
+#define GCE_APSRC_REQ_LSB                   (1U << 16)      /* 1b */
+#define GCE_VRF18_REQ_LSB                   (1U << 17)      /* 1b */
+#define GCE_DDR_EN_LSB                      (1U << 18)      /* 1b */
+#define INFRASYS_APSRC_REQ_LSB              (1U << 19)      /* 1b */
+#define INFRASYS_DDR_EN_LSB                 (1U << 20)      /* 1b */
+#define MSDC0_SRCCLKENA_LSB                 (1U << 21)      /* 1b */
+#define MSDC0_INFRA_REQ_LSB                 (1U << 22)      /* 1b */
+#define MSDC0_APSRC_REQ_LSB                 (1U << 23)      /* 1b */
+#define MSDC0_VRF18_REQ_LSB                 (1U << 24)      /* 1b */
+#define MSDC0_DDR_EN_LSB                    (1U << 25)      /* 1b */
+#define MSDC1_SRCCLKENA_LSB                 (1U << 26)      /* 1b */
+#define MSDC1_INFRA_REQ_LSB                 (1U << 27)      /* 1b */
+#define MSDC1_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define MSDC1_VRF18_REQ_LSB                 (1U << 29)      /* 1b */
+#define MSDC1_DDR_EN_LSB                    (1U << 30)      /* 1b */
+/* SRC_REQ_STA_2 (0x10006000+0x11C) */
+#define MCUSYS_MERGE_DDR_EN_LSB             (1U << 0)       /* 9b */
+#define EMI_SELF_REFRESH_CH_LSB             (1U << 9)       /* 2b */
+#define SW2SPM_INT_LSB                      (1U << 11)      /* 4b */
+#define SC_ADSP2SPM_WAKEUP_LSB              (1U << 15)      /* 1b */
+#define SC_SSPM2SPM_WAKEUP_LSB              (1U << 16)      /* 4b */
+#define SRC_REQ_STA_2_SC_SCP2SPM_WAKEUP_LSB (1U << 20)      /* 1b */
+#define SPM_SRCCLKENA_RESERVED_LSB          (1U << 21)      /* 1b */
+#define SPM_INFRA_REQ_RESERVED_LSB          (1U << 22)      /* 1b */
+#define SPM_APSRC_REQ_RESERVED_LSB          (1U << 23)      /* 1b */
+#define SPM_VRF18_REQ_RESERVED_LSB          (1U << 24)      /* 1b */
+#define SPM_DDR_EN_RESERVED_LSB             (1U << 25)      /* 1b */
+#define MCUPM_SRCCLKENA_LSB                 (1U << 26)      /* 1b */
+#define MCUPM_INFRA_REQ_LSB                 (1U << 27)      /* 1b */
+#define MCUPM_APSRC_REQ_LSB                 (1U << 28)      /* 1b */
+#define MCUPM_VRF18_REQ_LSB                 (1U << 29)      /* 1b */
+#define MCUPM_DDR_EN_LSB                    (1U << 30)      /* 1b */
+/* PCM_TIMER_OUT (0x10006000+0x120) */
+#define PCM_TIMER_LSB                       (1U << 0)       /* 32b */
+/* PCM_WDT_OUT (0x10006000+0x124) */
+#define PCM_WDT_TIMER_VAL_OUT_LSB           (1U << 0)       /* 32b */
+/* SPM_IRQ_STA (0x10006000+0x128) */
+#define TWAM_IRQ_LSB                        (1U << 2)       /* 1b */
+#define PCM_IRQ_LSB                         (1U << 3)       /* 1b */
+/* SRC_REQ_STA_4 (0x10006000+0x12C) */
+#define APU_SRCCLKENA_LSB                   (1U << 0)       /* 1b */
+#define APU_INFRA_REQ_LSB                   (1U << 1)       /* 1b */
+#define APU_APSRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define APU_VRF18_REQ_LSB                   (1U << 3)       /* 1b */
+#define APU_DDR_EN_LSB                      (1U << 4)       /* 1b */
+#define BAK_PSRI_SRCCLKENA_LSB              (1U << 5)       /* 1b */
+#define BAK_PSRI_INFRA_REQ_LSB              (1U << 6)       /* 1b */
+#define BAK_PSRI_APSRC_REQ_LSB              (1U << 7)       /* 1b */
+#define BAK_PSRI_VRF18_REQ_LSB              (1U << 8)       /* 1b */
+#define BAK_PSRI_DDR_EN_LSB                 (1U << 9)       /* 1b */
+/* MD32PCM_WAKEUP_STA (0x10006000+0x130) */
+#define MD32PCM_WAKEUP_STA_LSB              (1U << 0)       /* 32b */
+/* MD32PCM_EVENT_STA (0x10006000+0x134) */
+#define MD32PCM_EVENT_STA_LSB               (1U << 0)       /* 32b */
+/* SPM_WAKEUP_STA (0x10006000+0x138) */
+#define F32K_WAKEUP_EVENT_L_LSB             (1U << 0)       /* 16b */
+#define ASYN_WAKEUP_EVENT_L_LSB             (1U << 16)      /* 16b */
+/* SPM_WAKEUP_EXT_STA (0x10006000+0x13C) */
+#define EXT_WAKEUP_EVENT_LSB                (1U << 0)       /* 32b */
+/* SPM_WAKEUP_MISC (0x10006000+0x140) */
+#define GIC_WAKEUP_LSB                      (1U << 0)       /* 10b */
+#define DVFSRC_IRQ_LSB                      (1U << 16)      /* 1b */
+#define SPM_WAKEUP_MISC_REG_CPU_WAKEUP_LSB  (1U << 17)      /* 1b */
+#define PCM_TIMER_EVENT_LSB                 (1U << 18)      /* 1b */
+#define PMIC_EINT_OUT_B_LSB                 (1U << 19)      /* 2b */
+#define TWAM_IRQ_B_LSB                      (1U << 21)      /* 1b */
+#define PMSR_IRQ_B_SET0_LSB                 (1U << 22)      /* 1b */
+#define PMSR_IRQ_B_SET1_LSB                 (1U << 23)      /* 1b */
+#define PMSR_IRQ_B_SET2_LSB                 (1U << 24)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_0_LSB            (1U << 25)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_1_LSB            (1U << 26)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_2_LSB            (1U << 27)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_3_LSB            (1U << 28)      /* 1b */
+#define SPM_ACK_CHK_WAKEUP_ALL_LSB          (1U << 29)      /* 1b */
+#define PMIC_IRQ_ACK_LSB                    (1U << 30)      /* 1b */
+#define PMIC_SCP_IRQ_LSB                    (1U << 31)      /* 1b */
+/* MM_DVFS_HALT (0x10006000+0x144) */
+#define MM_DVFS_HALT_LSB                    (1U << 0)       /* 5b */
+/* BUS_PROTECT_RDY (0x10006000+0x150) */
+#define PROTECT_READY_LSB                   (1U << 0)       /* 32b */
+/* BUS_PROTECT1_RDY (0x10006000+0x154) */
+#define PROTECT1_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT2_RDY (0x10006000+0x158) */
+#define PROTECT2_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT3_RDY (0x10006000+0x15C) */
+#define PROTECT3_READY_LSB                  (1U << 0)       /* 32b */
+/* SUBSYS_IDLE_STA (0x10006000+0x160) */
+#define SUBSYS_IDLE_SIGNALS_LSB             (1U << 0)       /* 32b */
+/* PCM_STA (0x10006000+0x164) */
+#define PCM_CK_SEL_O_LSB                    (1U << 0)       /* 4b */
+#define EXT_SRC_STA_LSB                     (1U << 4)       /* 3b */
+/* SRC_REQ_STA_3 (0x10006000+0x168) */
+#define CCIF_EVENT_RAW_STATUS_LSB           (1U << 0)       /* 16b */
+#define F26M_STATE_LSB                      (1U << 16)      /* 1b */
+#define INFRA_STATE_LSB                     (1U << 17)      /* 1b */
+#define APSRC_STATE_LSB                     (1U << 18)      /* 1b */
+#define VRF18_STATE_LSB                     (1U << 19)      /* 1b */
+#define DDR_EN_STATE_LSB                    (1U << 20)      /* 1b */
+#define DVFS_STATE_LSB                      (1U << 21)      /* 1b */
+#define SW_MAILBOX_STATE_LSB                (1U << 22)      /* 1b */
+#define SSPM_MAILBOX_STATE_LSB              (1U << 23)      /* 1b */
+#define ADSP_MAILBOX_STATE_LSB              (1U << 24)      /* 1b */
+#define SCP_MAILBOX_STATE_LSB               (1U << 25)      /* 1b */
+/* PWR_STATUS (0x10006000+0x16C) */
+#define PWR_STATUS_LSB                      (1U << 0)       /* 32b */
+/* PWR_STATUS_2ND (0x10006000+0x170) */
+#define PWR_STATUS_2ND_LSB                  (1U << 0)       /* 32b */
+/* CPU_PWR_STATUS (0x10006000+0x174) */
+#define MP0_SPMC_PWR_ON_ACK_CPU0_LSB        (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU1_LSB        (1U << 1)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU2_LSB        (1U << 2)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU3_LSB        (1U << 3)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU4_LSB        (1U << 4)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU5_LSB        (1U << 5)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU6_LSB        (1U << 6)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPU7_LSB        (1U << 7)       /* 1b */
+#define MP0_SPMC_PWR_ON_ACK_CPUTOP_LSB      (1U << 8)       /* 1b */
+#define MCUSYS_SPMC_PWR_ON_ACK_LSB          (1U << 9)       /* 1b */
+/* OTHER_PWR_STATUS (0x10006000+0x178) */
+#define OTHER_PWR_STATUS_LSB                (1U << 0)       /* 32b */
+/* SPM_VTCXO_EVENT_COUNT_STA (0x10006000+0x17C) */
+#define SPM_VTCXO_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_VTCXO_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_INFRA_EVENT_COUNT_STA (0x10006000+0x180) */
+#define SPM_INFRA_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_INFRA_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_VRF18_EVENT_COUNT_STA (0x10006000+0x184) */
+#define SPM_VRF18_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_VRF18_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_APSRC_EVENT_COUNT_STA (0x10006000+0x188) */
+#define SPM_APSRC_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_APSRC_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* SPM_DDREN_EVENT_COUNT_STA (0x10006000+0x18C) */
+#define SPM_DDREN_SLEEP_COUNT_LSB           (1U << 0)       /* 16b */
+#define SPM_DDREN_WAKE_COUNT_LSB            (1U << 16)      /* 16b */
+/* MD32PCM_STA (0x10006000+0x190) */
+#define MD32PCM_HALT_LSB                    (1U << 0)       /* 1b */
+#define MD32PCM_GATED_LSB                   (1U << 1)       /* 1b */
+/* MD32PCM_PC (0x10006000+0x194) */
+#define MON_PC_LSB                          (1U << 0)       /* 32b */
+/* DVFSRC_EVENT_STA (0x10006000+0x1A4) */
+#define DVFSRC_EVENT_LSB                    (1U << 0)       /* 32b */
+/* BUS_PROTECT4_RDY (0x10006000+0x1A8) */
+#define PROTECT4_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT5_RDY (0x10006000+0x1AC) */
+#define PROTECT5_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT6_RDY (0x10006000+0x1B0) */
+#define PROTECT6_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT7_RDY (0x10006000+0x1B4) */
+#define PROTECT7_READY_LSB                  (1U << 0)       /* 32b */
+/* BUS_PROTECT8_RDY (0x10006000+0x1B8) */
+#define PROTECT8_READY_LSB                  (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA0 (0x10006000+0x1D0) */
+#define LAST_IDLE_CNT_0_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA1 (0x10006000+0x1D4) */
+#define LAST_IDLE_CNT_1_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA2 (0x10006000+0x1D8) */
+#define LAST_IDLE_CNT_2_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_LAST_STA3 (0x10006000+0x1DC) */
+#define LAST_IDLE_CNT_3_LSB                 (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA0 (0x10006000+0x1E0) */
+#define CURRENT_IDLE_CNT_0_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA1 (0x10006000+0x1E4) */
+#define CURRENT_IDLE_CNT_1_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA2 (0x10006000+0x1E8) */
+#define CURRENT_IDLE_CNT_2_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_CURR_STA3 (0x10006000+0x1EC) */
+#define CURRENT_IDLE_CNT_3_LSB              (1U << 0)       /* 32b */
+/* SPM_TWAM_TIMER_OUT (0x10006000+0x1F0) */
+#define TWAM_TIMER_LSB                      (1U << 0)       /* 32b */
+/* SPM_CG_CHECK_STA (0x10006000+0x1F4) */
+#define SPM_CG_CHECK_SLEEP_REQ_0_LSB        (1U << 0)       /* 1b */
+#define SPM_CG_CHECK_SLEEP_REQ_1_LSB        (1U << 1)       /* 1b */
+#define SPM_CG_CHECK_SLEEP_REQ_2_LSB        (1U << 2)       /* 1b */
+/* SPM_DVFS_STA (0x10006000+0x1F8) */
+#define TARGET_DVFS_LEVEL_LSB               (1U << 0)       /* 32b */
+/* SPM_DVFS_OPP_STA (0x10006000+0x1FC) */
+#define TARGET_DVFS_OPP_LSB                 (1U << 0)       /* 5b */
+#define CURRENT_DVFS_OPP_LSB                (1U << 5)       /* 5b */
+#define RELAY_DVFS_OPP_LSB                  (1U << 10)      /* 5b */
+/* SPM_MCUSYS_PWR_CON (0x10006000+0x200) */
+#define MCUSYS_SPMC_PWR_RST_B_LSB           (1U << 0)       /* 1b */
+#define MCUSYS_SPMC_PWR_ON_LSB              (1U << 2)       /* 1b */
+#define MCUSYS_SPMC_PWR_CLK_DIS_LSB         (1U << 4)       /* 1b */
+#define MCUSYS_SPMC_RESETPWRON_CONFIG_LSB   (1U << 5)       /* 1b */
+#define MCUSYS_SPMC_DORMANT_EN_LSB          (1U << 6)       /* 1b */
+#define MCUSYS_VPROC_EXT_OFF_LSB            (1U << 7)       /* 1b */
+#define SPM_MCUSYS_PWR_CON_MCUSYS_SPMC_PWR_ON_ACK_LSB (1U << 31)      /* 1b */
+/* SPM_CPUTOP_PWR_CON (0x10006000+0x204) */
+#define MP0_SPMC_PWR_RST_B_CPUTOP_LSB       (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPUTOP_LSB          (1U << 2)       /* 1b */
+#define MP0_SPMC_PWR_CLK_DIS_CPUTOP_LSB     (1U << 4)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPUTOP_LSB (1U << 5)       /* 1b */
+#define MP0_SPMC_DORMANT_EN_CPUTOP_LSB      (1U << 6)       /* 1b */
+#define MP0_VPROC_EXT_OFF_LSB               (1U << 7)       /* 1b */
+#define MP0_VSRAM_EXT_OFF_LSB               (1U << 8)       /* 1b */
+#define SPM_CPUTOP_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPUTOP_LSB (1U << 31)      /* 1b */
+/* SPM_CPU0_PWR_CON (0x10006000+0x208) */
+#define MP0_SPMC_PWR_RST_B_CPU0_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU0_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU0_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU0_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU0_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU0_LSB (1U << 31)      /* 1b */
+/* SPM_CPU1_PWR_CON (0x10006000+0x20C) */
+#define MP0_SPMC_PWR_RST_B_CPU1_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU1_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU1_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU1_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU1_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU1_LSB (1U << 31)      /* 1b */
+/* SPM_CPU2_PWR_CON (0x10006000+0x210) */
+#define MP0_SPMC_PWR_RST_B_CPU2_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU2_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU2_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU2_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU2_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU2_LSB (1U << 31)      /* 1b */
+/* SPM_CPU3_PWR_CON (0x10006000+0x214) */
+#define MP0_SPMC_PWR_RST_B_CPU3_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU3_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU3_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU3_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU3_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU3_LSB (1U << 31)      /* 1b */
+/* SPM_CPU4_PWR_CON (0x10006000+0x218) */
+#define MP0_SPMC_PWR_RST_B_CPU4_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU4_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU4_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU4_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU4_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU4_LSB (1U << 31)      /* 1b */
+/* SPM_CPU5_PWR_CON (0x10006000+0x21C) */
+#define MP0_SPMC_PWR_RST_B_CPU5_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU5_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU5_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU5_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU5_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU5_LSB (1U << 31)      /* 1b */
+/* SPM_CPU6_PWR_CON (0x10006000+0x220) */
+#define MP0_SPMC_PWR_RST_B_CPU6_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU6_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU6_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU6_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU6_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU6_LSB (1U << 31)      /* 1b */
+/* SPM_CPU7_PWR_CON (0x10006000+0x224) */
+#define MP0_SPMC_PWR_RST_B_CPU7_LSB         (1U << 0)       /* 1b */
+#define MP0_SPMC_PWR_ON_CPU7_LSB            (1U << 2)       /* 1b */
+#define MP0_SPMC_RESETPWRON_CONFIG_CPU7_LSB (1U << 5)       /* 1b */
+#define MP0_VPROC_EXT_OFF_CPU7_LSB          (1U << 7)       /* 1b */
+#define SPM_CPU7_PWR_CON_MP0_SPMC_PWR_ON_ACK_CPU7_LSB (1U << 31)      /* 1b */
+/* ARMPLL_CLK_CON (0x10006000+0x22C) */
+#define SC_ARM_FHC_PAUSE_LSB                (1U << 0)       /* 6b */
+#define SC_ARM_CK_OFF_LSB                   (1U << 6)       /* 6b */
+#define SC_ARMPLL_OFF_LSB                   (1U << 12)      /* 1b */
+#define SC_ARMBPLL_OFF_LSB                  (1U << 13)      /* 1b */
+#define SC_ARMBPLL1_OFF_LSB                 (1U << 14)      /* 1b */
+#define SC_ARMBPLL2_OFF_LSB                 (1U << 15)      /* 1b */
+#define SC_ARMBPLL3_OFF_LSB                 (1U << 16)      /* 1b */
+#define SC_CCIPLL_CKOFF_LSB                 (1U << 17)      /* 1b */
+#define SC_ARMDDS_OFF_LSB                   (1U << 18)      /* 1b */
+#define SC_ARMBPLL_S_OFF_LSB                (1U << 19)      /* 1b */
+#define SC_ARMBPLL1_S_OFF_LSB               (1U << 20)      /* 1b */
+#define SC_ARMBPLL2_S_OFF_LSB               (1U << 21)      /* 1b */
+#define SC_ARMBPLL3_S_OFF_LSB               (1U << 22)      /* 1b */
+#define SC_CCIPLL_PWROFF_LSB                (1U << 23)      /* 1b */
+#define SC_ARMPLLOUT_OFF_LSB                (1U << 24)      /* 1b */
+#define SC_ARMBPLLOUT_OFF_LSB               (1U << 25)      /* 1b */
+#define SC_ARMBPLLOUT1_OFF_LSB              (1U << 26)      /* 1b */
+#define SC_ARMBPLLOUT2_OFF_LSB              (1U << 27)      /* 1b */
+#define SC_ARMBPLLOUT3_OFF_LSB              (1U << 28)      /* 1b */
+#define SC_CCIPLL_OUT_OFF_LSB               (1U << 29)      /* 1b */
+/* MCUSYS_IDLE_STA (0x10006000+0x230) */
+#define ARMBUS_IDLE_TO_26M_LSB              (1U << 0)       /* 1b */
+#define MP0_CLUSTER_IDLE_TO_PWR_OFF_LSB     (1U << 1)       /* 1b */
+#define MCUSYS_DDR_EN_0_LSB                 (1U << 2)       /* 1b */
+#define MCUSYS_DDR_EN_1_LSB                 (1U << 3)       /* 1b */
+#define MCUSYS_DDR_EN_2_LSB                 (1U << 4)       /* 1b */
+#define MCUSYS_DDR_EN_3_LSB                 (1U << 5)       /* 1b */
+#define MCUSYS_DDR_EN_4_LSB                 (1U << 6)       /* 1b */
+#define MCUSYS_DDR_EN_5_LSB                 (1U << 7)       /* 1b */
+#define MCUSYS_DDR_EN_6_LSB                 (1U << 8)       /* 1b */
+#define MCUSYS_DDR_EN_7_LSB                 (1U << 9)       /* 1b */
+#define MP0_CPU_IDLE_TO_PWR_OFF_LSB         (1U << 16)      /* 8b */
+#define WFI_AF_SEL_LSB                      (1U << 24)      /* 8b */
+/* GIC_WAKEUP_STA (0x10006000+0x234) */
+#define GIC_WAKEUP_STA_GIC_WAKEUP_LSB       (1U << 10)      /* 10b */
+/* CPU_SPARE_CON (0x10006000+0x238) */
+#define CPU_SPARE_CON_LSB                   (1U << 0)       /* 32b */
+/* CPU_SPARE_CON_SET (0x10006000+0x23C) */
+#define CPU_SPARE_CON_SET_LSB               (1U << 0)       /* 32b */
+/* CPU_SPARE_CON_CLR (0x10006000+0x240) */
+#define CPU_SPARE_CON_CLR_LSB               (1U << 0)       /* 32b */
+/* ARMPLL_CLK_SEL (0x10006000+0x244) */
+#define ARMPLL_CLK_SEL_LSB                  (1U << 0)       /* 15b */
+/* EXT_INT_WAKEUP_REQ (0x10006000+0x248) */
+#define EXT_INT_WAKEUP_REQ_LSB              (1U << 0)       /* 10b */
+/* EXT_INT_WAKEUP_REQ_SET (0x10006000+0x24C) */
+#define EXT_INT_WAKEUP_REQ_SET_LSB          (1U << 0)       /* 10b */
+/* EXT_INT_WAKEUP_REQ_CLR (0x10006000+0x250) */
+#define EXT_INT_WAKEUP_REQ_CLR_LSB          (1U << 0)       /* 10b */
+/* MP0_CPU0_IRQ_MASK (0x10006000+0x260) */
+#define MP0_CPU0_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU0_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU1_IRQ_MASK (0x10006000+0x264) */
+#define MP0_CPU1_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU1_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU2_IRQ_MASK (0x10006000+0x268) */
+#define MP0_CPU2_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU2_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU3_IRQ_MASK (0x10006000+0x26C) */
+#define MP0_CPU3_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP0_CPU3_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU0_IRQ_MASK (0x10006000+0x270) */
+#define MP1_CPU0_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU0_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU1_IRQ_MASK (0x10006000+0x274) */
+#define MP1_CPU1_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU1_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU2_IRQ_MASK (0x10006000+0x278) */
+#define MP1_CPU2_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU2_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP1_CPU3_IRQ_MASK (0x10006000+0x27C) */
+#define MP1_CPU3_IRQ_MASK_LSB               (1U << 0)       /* 1b */
+#define MP1_CPU3_AUX_LSB                    (1U << 8)       /* 11b */
+/* MP0_CPU0_WFI_EN (0x10006000+0x280) */
+#define MP0_CPU0_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU1_WFI_EN (0x10006000+0x284) */
+#define MP0_CPU1_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU2_WFI_EN (0x10006000+0x288) */
+#define MP0_CPU2_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU3_WFI_EN (0x10006000+0x28C) */
+#define MP0_CPU3_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU4_WFI_EN (0x10006000+0x290) */
+#define MP0_CPU4_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU5_WFI_EN (0x10006000+0x294) */
+#define MP0_CPU5_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU6_WFI_EN (0x10006000+0x298) */
+#define MP0_CPU6_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* MP0_CPU7_WFI_EN (0x10006000+0x29C) */
+#define MP0_CPU7_WFI_EN_LSB                 (1U << 0)       /* 1b */
+/* ROOT_CPUTOP_ADDR (0x10006000+0x2A0) */
+#define ROOT_CPUTOP_ADDR_LSB                (1U << 0)       /* 32b */
+/* ROOT_CORE_ADDR (0x10006000+0x2A4) */
+#define ROOT_CORE_ADDR_LSB                  (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_0 (0x10006000+0x2D0) */
+#define SPM2SW_MAILBOX_0_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_1 (0x10006000+0x2D4) */
+#define SPM2SW_MAILBOX_1_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_2 (0x10006000+0x2D8) */
+#define SPM2SW_MAILBOX_2_LSB                (1U << 0)       /* 32b */
+/* SPM2SW_MAILBOX_3 (0x10006000+0x2DC) */
+#define SPM2SW_MAILBOX_3_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_INT (0x10006000+0x2E0) */
+#define SW2SPM_INT_SW2SPM_INT_LSB           (1U << 0)       /* 4b */
+/* SW2SPM_INT_SET (0x10006000+0x2E4) */
+#define SW2SPM_INT_SET_LSB                  (1U << 0)       /* 4b */
+/* SW2SPM_INT_CLR (0x10006000+0x2E8) */
+#define SW2SPM_INT_CLR_LSB                  (1U << 0)       /* 4b */
+/* SW2SPM_MAILBOX_0 (0x10006000+0x2EC) */
+#define SW2SPM_MAILBOX_0_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_1 (0x10006000+0x2F0) */
+#define SW2SPM_MAILBOX_1_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_2 (0x10006000+0x2F4) */
+#define SW2SPM_MAILBOX_2_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_MAILBOX_3 (0x10006000+0x2F8) */
+#define SW2SPM_MAILBOX_3_LSB                (1U << 0)       /* 32b */
+/* SW2SPM_CFG (0x10006000+0x2FC) */
+#define SWU2SPM_INT_MASK_B_LSB              (1U << 0)       /* 4b */
+/* MD1_PWR_CON (0x10006000+0x300) */
+#define MD1_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define MD1_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define MD1_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define MD1_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define MD1_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define MD1_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_MD1_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* CONN_PWR_CON (0x10006000+0x304) */
+#define CONN_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define CONN_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define CONN_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define CONN_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define CONN_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+/* MFG0_PWR_CON (0x10006000+0x308) */
+#define MFG0_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG0_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG0_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG0_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG0_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG0_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG0_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG1_PWR_CON (0x10006000+0x30C) */
+#define MFG1_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG1_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG1_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG1_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG1_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG1_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG1_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG2_PWR_CON (0x10006000+0x310) */
+#define MFG2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG3_PWR_CON (0x10006000+0x314) */
+#define MFG3_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG3_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG3_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG3_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG3_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG3_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG3_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG4_PWR_CON (0x10006000+0x318) */
+#define MFG4_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG4_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG4_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG4_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG4_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG4_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG4_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG5_PWR_CON (0x10006000+0x31C) */
+#define MFG5_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG5_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG5_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG5_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG5_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG5_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG5_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* MFG6_PWR_CON (0x10006000+0x320) */
+#define MFG6_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define MFG6_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define MFG6_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define MFG6_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define MFG6_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define MFG6_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_MFG6_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* IFR_PWR_CON (0x10006000+0x324) */
+#define IFR_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define IFR_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define IFR_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define IFR_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define IFR_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define IFR_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_IFR_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* IFR_SUB_PWR_CON (0x10006000+0x328) */
+#define IFR_SUB_PWR_RST_B_LSB               (1U << 0)       /* 1b */
+#define IFR_SUB_PWR_ISO_LSB                 (1U << 1)       /* 1b */
+#define IFR_SUB_PWR_ON_LSB                  (1U << 2)       /* 1b */
+#define IFR_SUB_PWR_ON_2ND_LSB              (1U << 3)       /* 1b */
+#define IFR_SUB_PWR_CLK_DIS_LSB             (1U << 4)       /* 1b */
+#define IFR_SUB_SRAM_PDN_LSB                (1U << 8)       /* 1b */
+#define SC_IFR_SUB_SRAM_PDN_ACK_LSB         (1U << 12)      /* 1b */
+/* DPY_PWR_CON (0x10006000+0x32C) */
+#define DPY_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define DPY_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define DPY_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define DPY_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define DPY_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define DPY_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_DPY_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* ISP_PWR_CON (0x10006000+0x330) */
+#define ISP_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define ISP_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define ISP_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define ISP_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define ISP_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define ISP_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_ISP_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* ISP2_PWR_CON (0x10006000+0x334) */
+#define ISP2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define ISP2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define ISP2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define ISP2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define ISP2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define ISP2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_ISP2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* IPE_PWR_CON (0x10006000+0x338) */
+#define IPE_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define IPE_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define IPE_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define IPE_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define IPE_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define IPE_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_IPE_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VDE_PWR_CON (0x10006000+0x33C) */
+#define VDE_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define VDE_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define VDE_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define VDE_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define VDE_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define VDE_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_VDE_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VDE2_PWR_CON (0x10006000+0x340) */
+#define VDE2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define VDE2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define VDE2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define VDE2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define VDE2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define VDE2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_VDE2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* VEN_PWR_CON (0x10006000+0x344) */
+#define VEN_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define VEN_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define VEN_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define VEN_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define VEN_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define VEN_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_VEN_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* VEN_CORE1_PWR_CON (0x10006000+0x348) */
+#define VEN_CORE1_PWR_RST_B_LSB             (1U << 0)       /* 1b */
+#define VEN_CORE1_PWR_ISO_LSB               (1U << 1)       /* 1b */
+#define VEN_CORE1_PWR_ON_LSB                (1U << 2)       /* 1b */
+#define VEN_CORE1_PWR_ON_2ND_LSB            (1U << 3)       /* 1b */
+#define VEN_CORE1_PWR_CLK_DIS_LSB           (1U << 4)       /* 1b */
+#define VEN_CORE1_SRAM_PDN_LSB              (1U << 8)       /* 1b */
+#define SC_VEN_CORE1_SRAM_PDN_ACK_LSB       (1U << 12)      /* 1b */
+/* MDP_PWR_CON (0x10006000+0x34C) */
+#define MDP_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define MDP_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define MDP_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define MDP_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define MDP_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define MDP_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_MDP_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* DIS_PWR_CON (0x10006000+0x350) */
+#define DIS_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define DIS_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define DIS_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define DIS_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define DIS_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define DIS_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_DIS_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* AUDIO_PWR_CON (0x10006000+0x354) */
+#define AUDIO_PWR_RST_B_LSB                 (1U << 0)       /* 1b */
+#define AUDIO_PWR_ISO_LSB                   (1U << 1)       /* 1b */
+#define AUDIO_PWR_ON_LSB                    (1U << 2)       /* 1b */
+#define AUDIO_PWR_ON_2ND_LSB                (1U << 3)       /* 1b */
+#define AUDIO_PWR_CLK_DIS_LSB               (1U << 4)       /* 1b */
+#define AUDIO_SRAM_PDN_LSB                  (1U << 8)       /* 1b */
+#define SC_AUDIO_SRAM_PDN_ACK_LSB           (1U << 12)      /* 1b */
+/* ADSP_PWR_CON (0x10006000+0x358) */
+#define ADSP_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define ADSP_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define ADSP_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define ADSP_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define ADSP_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define ADSP_SRAM_CKISO_LSB                 (1U << 5)       /* 1b */
+#define ADSP_SRAM_ISOINT_B_LSB              (1U << 6)       /* 1b */
+#define ADSP_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define ADSP_SRAM_SLEEP_B_LSB               (1U << 9)       /* 1b */
+#define SC_ADSP_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+#define SC_ADSP_SRAM_SLEEP_B_ACK_LSB        (1U << 13)      /* 1b */
+/* CAM_PWR_CON (0x10006000+0x35C) */
+#define CAM_PWR_RST_B_LSB                   (1U << 0)       /* 1b */
+#define CAM_PWR_ISO_LSB                     (1U << 1)       /* 1b */
+#define CAM_PWR_ON_LSB                      (1U << 2)       /* 1b */
+#define CAM_PWR_ON_2ND_LSB                  (1U << 3)       /* 1b */
+#define CAM_PWR_CLK_DIS_LSB                 (1U << 4)       /* 1b */
+#define CAM_SRAM_PDN_LSB                    (1U << 8)       /* 1b */
+#define SC_CAM_SRAM_PDN_ACK_LSB             (1U << 12)      /* 1b */
+/* CAM_RAWA_PWR_CON (0x10006000+0x360) */
+#define CAM_RAWA_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWA_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWA_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWA_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWA_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWA_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWA_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* CAM_RAWB_PWR_CON (0x10006000+0x364) */
+#define CAM_RAWB_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWB_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWB_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWB_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWB_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWB_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWB_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* CAM_RAWC_PWR_CON (0x10006000+0x368) */
+#define CAM_RAWC_PWR_RST_B_LSB              (1U << 0)       /* 1b */
+#define CAM_RAWC_PWR_ISO_LSB                (1U << 1)       /* 1b */
+#define CAM_RAWC_PWR_ON_LSB                 (1U << 2)       /* 1b */
+#define CAM_RAWC_PWR_ON_2ND_LSB             (1U << 3)       /* 1b */
+#define CAM_RAWC_PWR_CLK_DIS_LSB            (1U << 4)       /* 1b */
+#define CAM_RAWC_SRAM_PDN_LSB               (1U << 8)       /* 1b */
+#define SC_CAM_RAWC_SRAM_PDN_ACK_LSB        (1U << 12)      /* 1b */
+/* SYSRAM_CON (0x10006000+0x36C) */
+#define SYSRAM_SRAM_CKISO_LSB               (1U << 0)       /* 1b */
+#define SYSRAM_SRAM_ISOINT_B_LSB            (1U << 1)       /* 1b */
+#define SYSRAM_SRAM_SLEEP_B_LSB             (1U << 4)       /* 4b */
+#define SYSRAM_SRAM_PDN_LSB                 (1U << 16)      /* 4b */
+/* SYSROM_CON (0x10006000+0x370) */
+#define SYSROM_SRAM_PDN_LSB                 (1U << 0)       /* 6b */
+/* SSPM_SRAM_CON (0x10006000+0x374) */
+#define SSPM_SRAM_CKISO_LSB                 (1U << 0)       /* 1b */
+#define SSPM_SRAM_ISOINT_B_LSB              (1U << 1)       /* 1b */
+#define SSPM_SRAM_SLEEP_B_LSB               (1U << 4)       /* 1b */
+#define SSPM_SRAM_PDN_LSB                   (1U << 16)      /* 1b */
+/* SCP_SRAM_CON (0x10006000+0x378) */
+#define SCP_SRAM_CKISO_LSB                  (1U << 0)       /* 1b */
+#define SCP_SRAM_ISOINT_B_LSB               (1U << 1)       /* 1b */
+#define SCP_SRAM_SLEEP_B_LSB                (1U << 4)       /* 1b */
+#define SCP_SRAM_PDN_LSB                    (1U << 16)      /* 1b */
+/* DPY_SHU_SRAM_CON (0x10006000+0x37C) */
+#define DPY_SHU_SRAM_CKISO_LSB              (1U << 0)       /* 1b */
+#define DPY_SHU_SRAM_ISOINT_B_LSB           (1U << 1)       /* 1b */
+#define DPY_SHU_SRAM_SLEEP_B_LSB            (1U << 4)       /* 2b */
+#define DPY_SHU_SRAM_PDN_LSB                (1U << 16)      /* 2b */
+/* UFS_SRAM_CON (0x10006000+0x380) */
+#define UFS_SRAM_CKISO_LSB                  (1U << 0)       /* 1b */
+#define UFS_SRAM_ISOINT_B_LSB               (1U << 1)       /* 1b */
+#define UFS_SRAM_SLEEP_B_LSB                (1U << 4)       /* 5b */
+#define UFS_SRAM_PDN_LSB                    (1U << 16)      /* 5b */
+/* DEVAPC_IFR_SRAM_CON (0x10006000+0x384) */
+#define DEVAPC_IFR_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DEVAPC_IFR_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DEVAPC_IFR_SRAM_SLEEP_B_LSB         (1U << 4)       /* 6b */
+#define DEVAPC_IFR_SRAM_PDN_LSB             (1U << 16)      /* 6b */
+/* DEVAPC_SUBIFR_SRAM_CON (0x10006000+0x388) */
+#define DEVAPC_SUBIFR_SRAM_CKISO_LSB        (1U << 0)       /* 1b */
+#define DEVAPC_SUBIFR_SRAM_ISOINT_B_LSB     (1U << 1)       /* 1b */
+#define DEVAPC_SUBIFR_SRAM_SLEEP_B_LSB      (1U << 4)       /* 6b */
+#define DEVAPC_SUBIFR_SRAM_PDN_LSB          (1U << 16)      /* 6b */
+/* DEVAPC_ACP_SRAM_CON (0x10006000+0x38C) */
+#define DEVAPC_ACP_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DEVAPC_ACP_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DEVAPC_ACP_SRAM_SLEEP_B_LSB         (1U << 4)       /* 6b */
+#define DEVAPC_ACP_SRAM_PDN_LSB             (1U << 16)      /* 6b */
+/* USB_SRAM_CON (0x10006000+0x390) */
+#define USB_SRAM_PDN_LSB                    (1U << 0)       /* 7b */
+/* DUMMY_SRAM_CON (0x10006000+0x394) */
+#define DUMMY_SRAM_CKISO_LSB                (1U << 0)       /* 1b */
+#define DUMMY_SRAM_ISOINT_B_LSB             (1U << 1)       /* 1b */
+#define DUMMY_SRAM_SLEEP_B_LSB              (1U << 4)       /* 8b */
+#define DUMMY_SRAM_PDN_LSB                  (1U << 16)      /* 8b */
+/* MD_EXT_BUCK_ISO_CON (0x10006000+0x398) */
+#define VMODEM_EXT_BUCK_ISO_LSB             (1U << 0)       /* 1b */
+#define VMD_EXT_BUCK_ISO_LSB                (1U << 1)       /* 1b */
+/* EXT_BUCK_ISO (0x10006000+0x39C) */
+#define VIMVO_EXT_BUCK_ISO_LSB              (1U << 0)       /* 1b */
+#define GPU_EXT_BUCK_ISO_LSB                (1U << 1)       /* 1b */
+#define IPU_EXT_BUCK_ISO_LSB                (1U << 5)       /* 3b */
+/* DXCC_SRAM_CON (0x10006000+0x3A0) */
+#define DXCC_SRAM_CKISO_LSB                 (1U << 0)       /* 1b */
+#define DXCC_SRAM_ISOINT_B_LSB              (1U << 1)       /* 1b */
+#define DXCC_SRAM_SLEEP_B_LSB               (1U << 4)       /* 1b */
+#define DXCC_SRAM_PDN_LSB                   (1U << 16)      /* 1b */
+/* MSDC_SRAM_CON (0x10006000+0x3A4) */
+#define MSDC_SRAM_CKISO_LSB                 (1U << 0)       /* 1b */
+#define MSDC_SRAM_ISOINT_B_LSB              (1U << 1)       /* 1b */
+#define MSDC_SRAM_SLEEP_B_LSB               (1U << 4)       /* 5b */
+#define MSDC_SRAM_PDN_LSB                   (1U << 16)      /* 5b */
+/* DEBUGTOP_SRAM_CON (0x10006000+0x3A8) */
+#define DEBUGTOP_SRAM_PDN_LSB               (1U << 0)       /* 1b */
+/* DP_TX_PWR_CON (0x10006000+0x3AC) */
+#define DP_TX_PWR_RST_B_LSB                 (1U << 0)       /* 1b */
+#define DP_TX_PWR_ISO_LSB                   (1U << 1)       /* 1b */
+#define DP_TX_PWR_ON_LSB                    (1U << 2)       /* 1b */
+#define DP_TX_PWR_ON_2ND_LSB                (1U << 3)       /* 1b */
+#define DP_TX_PWR_CLK_DIS_LSB               (1U << 4)       /* 1b */
+#define DP_TX_SRAM_PDN_LSB                  (1U << 8)       /* 1b */
+#define SC_DP_TX_SRAM_PDN_ACK_LSB           (1U << 12)      /* 1b */
+/* DPMAIF_SRAM_CON (0x10006000+0x3B0) */
+#define DPMAIF_SRAM_CKISO_LSB               (1U << 0)       /* 1b */
+#define DPMAIF_SRAM_ISOINT_B_LSB            (1U << 1)       /* 1b */
+#define DPMAIF_SRAM_SLEEP_B_LSB             (1U << 4)       /* 1b */
+#define DPMAIF_SRAM_PDN_LSB                 (1U << 16)      /* 1b */
+/* DPY_SHU2_SRAM_CON (0x10006000+0x3B4) */
+#define DPY_SHU2_SRAM_CKISO_LSB             (1U << 0)       /* 1b */
+#define DPY_SHU2_SRAM_ISOINT_B_LSB          (1U << 1)       /* 1b */
+#define DPY_SHU2_SRAM_SLEEP_B_LSB           (1U << 4)       /* 2b */
+#define DPY_SHU2_SRAM_PDN_LSB               (1U << 16)      /* 2b */
+/* DRAMC_MCU2_SRAM_CON (0x10006000+0x3B8) */
+#define DRAMC_MCU2_SRAM_CKISO_LSB           (1U << 0)       /* 1b */
+#define DRAMC_MCU2_SRAM_ISOINT_B_LSB        (1U << 1)       /* 1b */
+#define DRAMC_MCU2_SRAM_SLEEP_B_LSB         (1U << 4)       /* 1b */
+#define DRAMC_MCU2_SRAM_PDN_LSB             (1U << 16)      /* 1b */
+/* DRAMC_MCU_SRAM_CON (0x10006000+0x3BC) */
+#define DRAMC_MCU_SRAM_CKISO_LSB            (1U << 0)       /* 1b */
+#define DRAMC_MCU_SRAM_ISOINT_B_LSB         (1U << 1)       /* 1b */
+#define DRAMC_MCU_SRAM_SLEEP_B_LSB          (1U << 4)       /* 1b */
+#define DRAMC_MCU_SRAM_PDN_LSB              (1U << 16)      /* 1b */
+/* MCUPM_SRAM_CON (0x10006000+0x3C0) */
+#define MCUPM_SRAM_CKISO_LSB                (1U << 0)       /* 1b */
+#define MCUPM_SRAM_ISOINT_B_LSB             (1U << 1)       /* 1b */
+#define MCUPM_SRAM_SLEEP_B_LSB              (1U << 4)       /* 8b */
+#define MCUPM_SRAM_PDN_LSB                  (1U << 16)      /* 8b */
+/* DPY2_PWR_CON (0x10006000+0x3C4) */
+#define DPY2_PWR_RST_B_LSB                  (1U << 0)       /* 1b */
+#define DPY2_PWR_ISO_LSB                    (1U << 1)       /* 1b */
+#define DPY2_PWR_ON_LSB                     (1U << 2)       /* 1b */
+#define DPY2_PWR_ON_2ND_LSB                 (1U << 3)       /* 1b */
+#define DPY2_PWR_CLK_DIS_LSB                (1U << 4)       /* 1b */
+#define DPY2_SRAM_PDN_LSB                   (1U << 8)       /* 1b */
+#define SC_DPY2_SRAM_PDN_ACK_LSB            (1U << 12)      /* 1b */
+/* SPM_MEM_CK_SEL (0x10006000+0x400) */
+#define SC_MEM_CK_SEL_LSB                   (1U << 0)       /* 1b */
+#define SPM2CKSYS_MEM_CK_MUX_UPDATE_LSB     (1U << 1)       /* 1b */
+/* SPM_BUS_PROTECT_MASK_B (0x10006000+0X404) */
+#define SPM_BUS_PROTECT_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT1_MASK_B (0x10006000+0x408) */
+#define SPM_BUS_PROTECT1_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT2_MASK_B (0x10006000+0x40C) */
+#define SPM_BUS_PROTECT2_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT3_MASK_B (0x10006000+0x410) */
+#define SPM_BUS_PROTECT3_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT4_MASK_B (0x10006000+0x414) */
+#define SPM_BUS_PROTECT4_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_EMI_BW_MODE (0x10006000+0x418) */
+#define EMI_BW_MODE_LSB                     (1U << 0)       /* 1b */
+#define EMI_BOOST_MODE_LSB                  (1U << 1)       /* 1b */
+#define EMI_BW_MODE_2_LSB                   (1U << 2)       /* 1b */
+#define EMI_BOOST_MODE_2_LSB                (1U << 3)       /* 1b */
+/* AP2MD_PEER_WAKEUP (0x10006000+0x41C) */
+#define AP2MD_PEER_WAKEUP_LSB               (1U << 0)       /* 1b */
+/* ULPOSC_CON (0x10006000+0x420) */
+#define ULPOSC_EN_LSB                       (1U << 0)       /* 1b */
+#define ULPOSC_RST_LSB                      (1U << 1)       /* 1b */
+#define ULPOSC_CG_EN_LSB                    (1U << 2)       /* 1b */
+#define ULPOSC_CLK_SEL_LSB                  (1U << 3)       /* 1b */
+/* SPM2MM_CON (0x10006000+0x424) */
+#define SPM2MM_FORCE_ULTRA_LSB              (1U << 0)       /* 1b */
+#define SPM2MM_DBL_OSTD_ACT_LSB             (1U << 1)       /* 1b */
+#define SPM2MM_ULTRAREQ_LSB                 (1U << 2)       /* 1b */
+#define SPM2MD_ULTRAREQ_LSB                 (1U << 3)       /* 1b */
+#define SPM2ISP_ULTRAREQ_LSB                (1U << 4)       /* 1b */
+#define MM2SPM_FORCE_ULTRA_ACK_D2T_LSB      (1U << 16)      /* 1b */
+#define MM2SPM_DBL_OSTD_ACT_ACK_D2T_LSB     (1U << 17)      /* 1b */
+#define SPM2ISP_ULTRAACK_D2T_LSB            (1U << 18)      /* 1b */
+#define SPM2MM_ULTRAACK_D2T_LSB             (1U << 19)      /* 1b */
+#define SPM2MD_ULTRAACK_D2T_LSB             (1U << 20)      /* 1b */
+/* SPM_BUS_PROTECT5_MASK_B (0x10006000+0x428) */
+#define SPM_BUS_PROTECT5_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM2MCUPM_CON (0x10006000+0x42C) */
+#define SPM2MCUPM_SW_RST_B_LSB              (1U << 0)       /* 1b */
+#define SPM2MCUPM_SW_INT_LSB                (1U << 1)       /* 1b */
+/* AP_MDSRC_REQ (0x10006000+0x430) */
+#define AP_MDSMSRC_REQ_LSB                  (1U << 0)       /* 1b */
+#define AP_L1SMSRC_REQ_LSB                  (1U << 1)       /* 1b */
+#define AP_MD2SRC_REQ_LSB                   (1U << 2)       /* 1b */
+#define AP_MDSMSRC_ACK_LSB                  (1U << 4)       /* 1b */
+#define AP_L1SMSRC_ACK_LSB                  (1U << 5)       /* 1b */
+#define AP_MD2SRC_ACK_LSB                   (1U << 6)       /* 1b */
+/* SPM2EMI_ENTER_ULPM (0x10006000+0x434) */
+#define SPM2EMI_ENTER_ULPM_LSB              (1U << 0)       /* 1b */
+/* SPM2MD_DVFS_CON (0x10006000+0x438) */
+#define SPM2MD_DVFS_CON_LSB                 (1U << 0)       /* 32b */
+/* MD2SPM_DVFS_CON (0x10006000+0x43C) */
+#define MD2SPM_DVFS_CON_LSB                 (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT6_MASK_B (0x10006000+0X440) */
+#define SPM_BUS_PROTECT6_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT7_MASK_B (0x10006000+0x444) */
+#define SPM_BUS_PROTECT7_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_BUS_PROTECT8_MASK_B (0x10006000+0x448) */
+#define SPM_BUS_PROTECT8_MASK_B_LSB         (1U << 0)       /* 32b */
+/* SPM_PLL_CON (0x10006000+0x44C) */
+#define SC_MAINPLLOUT_OFF_LSB               (1U << 0)       /* 1b */
+#define SC_UNIPLLOUT_OFF_LSB                (1U << 1)       /* 1b */
+#define SC_MAINPLL_OFF_LSB                  (1U << 4)       /* 1b */
+#define SC_UNIPLL_OFF_LSB                   (1U << 5)       /* 1b */
+#define SC_MAINPLL_S_OFF_LSB                (1U << 8)       /* 1b */
+#define SC_UNIPLL_S_OFF_LSB                 (1U << 9)       /* 1b */
+#define SC_SMI_CK_OFF_LSB                   (1U << 16)      /* 1b */
+#define SC_MD32K_CK_OFF_LSB                 (1U << 17)      /* 1b */
+#define SC_CKSQ1_OFF_LSB                    (1U << 18)      /* 1b */
+#define SC_AXI_MEM_CK_OFF_LSB               (1U << 19)      /* 1b */
+/* CPU_DVFS_REQ (0x10006000+0x450) */
+#define CPU_DVFS_REQ_LSB                    (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_0 (0x10006000+0x454) */
+#define SW_DDR_PST_REQ_LSB                  (1U << 0)       /* 2b */
+#define SW_DDR_PST_ABORT_REQ_LSB            (1U << 2)       /* 2b */
+/* SPM_DRAM_MCU_SW_CON_1 (0x10006000+0x458) */
+#define SW_DDR_PST_CH0_LSB                  (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_2 (0x10006000+0x45C) */
+#define SW_DDR_PST_CH1_LSB                  (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_3 (0x10006000+0x460) */
+#define SW_DDR_RESERVED_CH0_LSB             (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_CON_4 (0x10006000+0x464) */
+#define SW_DDR_RESERVED_CH1_LSB             (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_STA_0 (0x10006000+0x468) */
+#define SC_DDR_PST_ACK_LSB                  (1U << 0)       /* 2b */
+#define SC_DDR_PST_ABORT_ACK_LSB            (1U << 2)       /* 2b */
+/* SPM_DRAM_MCU_STA_1 (0x10006000+0x46C) */
+#define SC_DDR_CUR_PST_STA_CH0_LSB          (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_STA_2 (0x10006000+0x470) */
+#define SC_DDR_CUR_PST_STA_CH1_LSB          (1U << 0)       /* 32b */
+/* SPM_DRAM_MCU_SW_SEL_0 (0x10006000+0x474) */
+#define SW_DDR_PST_REQ_SEL_LSB              (1U << 0)       /* 2b */
+#define SW_DDR_PST_SEL_LSB                  (1U << 2)       /* 2b */
+#define SW_DDR_PST_ABORT_REQ_SEL_LSB        (1U << 4)       /* 2b */
+#define SW_DDR_RESERVED_SEL_LSB             (1U << 6)       /* 2b */
+#define SW_DDR_PST_ACK_SEL_LSB              (1U << 8)       /* 2b */
+#define SW_DDR_PST_ABORT_ACK_SEL_LSB        (1U << 10)      /* 2b */
+/* RELAY_DVFS_LEVEL (0x10006000+0x478) */
+#define RELAY_DVFS_LEVEL_LSB                (1U << 0)       /* 32b */
+/* DRAMC_DPY_CLK_SW_CON_0 (0x10006000+0x480) */
+#define SW_PHYPLL_EN_LSB                    (1U << 0)       /* 2b */
+#define SW_DPY_VREF_EN_LSB                  (1U << 2)       /* 2b */
+#define SW_DPY_DLL_CK_EN_LSB                (1U << 4)       /* 2b */
+#define SW_DPY_DLL_EN_LSB                   (1U << 6)       /* 2b */
+#define SW_DPY_2ND_DLL_EN_LSB               (1U << 8)       /* 2b */
+#define SW_MEM_CK_OFF_LSB                   (1U << 10)      /* 2b */
+#define SW_DMSUS_OFF_LSB                    (1U << 12)      /* 2b */
+#define SW_DPY_MODE_SW_LSB                  (1U << 14)      /* 2b */
+#define SW_EMI_CLK_OFF_LSB                  (1U << 16)      /* 2b */
+#define SW_DDRPHY_FB_CK_EN_LSB              (1U << 18)      /* 2b */
+#define SW_DR_GATE_RETRY_EN_LSB             (1U << 20)      /* 2b */
+#define SW_DPHY_PRECAL_UP_LSB               (1U << 24)      /* 2b */
+#define SW_DPY_BCLK_ENABLE_LSB              (1U << 26)      /* 2b */
+#define SW_TX_TRACKING_DIS_LSB              (1U << 28)      /* 2b */
+#define SW_DPHY_RXDLY_TRACKING_EN_LSB       (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_CON_1 (0x10006000+0x484) */
+#define SW_SHU_RESTORE_LSB                  (1U << 0)       /* 2b */
+#define SW_DMYRD_MOD_LSB                    (1U << 2)       /* 2b */
+#define SW_DMYRD_INTV_LSB                   (1U << 4)       /* 2b */
+#define SW_DMYRD_EN_LSB                     (1U << 6)       /* 2b */
+#define SW_DRS_DIS_REQ_LSB                  (1U << 8)       /* 2b */
+#define SW_DR_SRAM_LOAD_LSB                 (1U << 10)      /* 2b */
+#define SW_DR_SRAM_RESTORE_LSB              (1U << 12)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_LATCH_LSB      (1U << 14)      /* 2b */
+#define SW_TX_TRACK_RETRY_EN_LSB            (1U << 16)      /* 2b */
+#define SW_DPY_MIDPI_EN_LSB                 (1U << 18)      /* 2b */
+#define SW_DPY_PI_RESETB_EN_LSB             (1U << 20)      /* 2b */
+#define SW_DPY_MCK8X_EN_LSB                 (1U << 22)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_CH0_LSB        (1U << 24)      /* 4b */
+#define SW_DR_SHU_LEVEL_SRAM_CH1_LSB        (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SW_CON_2 (0x10006000+0x488) */
+#define SW_DR_SHU_LEVEL_LSB                 (1U << 0)       /* 2b */
+#define SW_DR_SHU_EN_LSB                    (1U << 2)       /* 1b */
+#define SW_DR_SHORT_QUEUE_LSB               (1U << 3)       /* 1b */
+#define SW_PHYPLL_MODE_SW_LSB               (1U << 4)       /* 1b */
+#define SW_PHYPLL2_MODE_SW_LSB              (1U << 5)       /* 1b */
+#define SW_PHYPLL_SHU_EN_LSB                (1U << 6)       /* 1b */
+#define SW_PHYPLL2_SHU_EN_LSB               (1U << 7)       /* 1b */
+#define SW_DR_RESERVED_0_LSB                (1U << 24)      /* 2b */
+#define SW_DR_RESERVED_1_LSB                (1U << 26)      /* 2b */
+#define SW_DR_RESERVED_2_LSB                (1U << 28)      /* 2b */
+#define SW_DR_RESERVED_3_LSB                (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_CON_3 (0x10006000+0x48C) */
+#define SC_DR_SHU_EN_ACK_LSB                (1U << 0)       /* 4b */
+#define SC_EMI_CLK_OFF_ACK_LSB              (1U << 4)       /* 4b */
+#define SC_DR_SHORT_QUEUE_ACK_LSB           (1U << 8)       /* 4b */
+#define SC_DRAMC_DFS_STA_LSB                (1U << 12)      /* 4b */
+#define SC_DRS_DIS_ACK_LSB                  (1U << 16)      /* 4b */
+#define SC_DR_SRAM_LOAD_ACK_LSB             (1U << 20)      /* 4b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_LSB         (1U << 24)      /* 4b */
+#define SC_DR_SRAM_RESTORE_ACK_LSB          (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SW_SEL_0 (0x10006000+0x490) */
+#define SW_PHYPLL_EN_SEL_LSB                (1U << 0)       /* 2b */
+#define SW_DPY_VREF_EN_SEL_LSB              (1U << 2)       /* 2b */
+#define SW_DPY_DLL_CK_EN_SEL_LSB            (1U << 4)       /* 2b */
+#define SW_DPY_DLL_EN_SEL_LSB               (1U << 6)       /* 2b */
+#define SW_DPY_2ND_DLL_EN_SEL_LSB           (1U << 8)       /* 2b */
+#define SW_MEM_CK_OFF_SEL_LSB               (1U << 10)      /* 2b */
+#define SW_DMSUS_OFF_SEL_LSB                (1U << 12)      /* 2b */
+#define SW_DPY_MODE_SW_SEL_LSB              (1U << 14)      /* 2b */
+#define SW_EMI_CLK_OFF_SEL_LSB              (1U << 16)      /* 2b */
+#define SW_DDRPHY_FB_CK_EN_SEL_LSB          (1U << 18)      /* 2b */
+#define SW_DR_GATE_RETRY_EN_SEL_LSB         (1U << 20)      /* 2b */
+#define SW_DPHY_PRECAL_UP_SEL_LSB           (1U << 24)      /* 2b */
+#define SW_DPY_BCLK_ENABLE_SEL_LSB          (1U << 26)      /* 2b */
+#define SW_TX_TRACKING_DIS_SEL_LSB          (1U << 28)      /* 2b */
+#define SW_DPHY_RXDLY_TRACKING_EN_SEL_LSB   (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_1 (0x10006000+0x494) */
+#define SW_SHU_RESTORE_SEL_LSB              (1U << 0)       /* 2b */
+#define SW_DMYRD_MOD_SEL_LSB                (1U << 2)       /* 2b */
+#define SW_DMYRD_INTV_SEL_LSB               (1U << 4)       /* 2b */
+#define SW_DMYRD_EN_SEL_LSB                 (1U << 6)       /* 2b */
+#define SW_DRS_DIS_REQ_SEL_LSB              (1U << 8)       /* 2b */
+#define SW_DR_SRAM_LOAD_SEL_LSB             (1U << 10)      /* 2b */
+#define SW_DR_SRAM_RESTORE_SEL_LSB          (1U << 12)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_LATCH_SEL_LSB  (1U << 14)      /* 2b */
+#define SW_TX_TRACK_RETRY_EN_SEL_LSB        (1U << 16)      /* 2b */
+#define SW_DPY_MIDPI_EN_SEL_LSB             (1U << 18)      /* 2b */
+#define SW_DPY_PI_RESETB_EN_SEL_LSB         (1U << 20)      /* 2b */
+#define SW_DPY_MCK8X_EN_SEL_LSB             (1U << 22)      /* 2b */
+#define SW_DR_SHU_LEVEL_SRAM_SEL_LSB        (1U << 24)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_2 (0x10006000+0x498) */
+#define SW_DR_SHU_LEVEL_SEL_LSB             (1U << 0)       /* 1b */
+#define SW_DR_SHU_EN_SEL_LSB                (1U << 2)       /* 1b */
+#define SW_DR_SHORT_QUEUE_SEL_LSB           (1U << 3)       /* 1b */
+#define SW_PHYPLL_MODE_SW_SEL_LSB           (1U << 4)       /* 1b */
+#define SW_PHYPLL2_MODE_SW_SEL_LSB          (1U << 5)       /* 1b */
+#define SW_PHYPLL_SHU_EN_SEL_LSB            (1U << 6)       /* 1b */
+#define SW_PHYPLL2_SHU_EN_SEL_LSB           (1U << 7)       /* 1b */
+#define SW_DR_RESERVED_0_SEL_LSB            (1U << 24)      /* 2b */
+#define SW_DR_RESERVED_1_SEL_LSB            (1U << 26)      /* 2b */
+#define SW_DR_RESERVED_2_SEL_LSB            (1U << 28)      /* 2b */
+#define SW_DR_RESERVED_3_SEL_LSB            (1U << 30)      /* 2b */
+/* DRAMC_DPY_CLK_SW_SEL_3 (0x10006000+0x49C) */
+#define SC_DR_SHU_EN_ACK_SEL_LSB            (1U << 0)       /* 4b */
+#define SC_EMI_CLK_OFF_ACK_SEL_LSB          (1U << 4)       /* 4b */
+#define SC_DR_SHORT_QUEUE_ACK_SEL_LSB       (1U << 8)       /* 4b */
+#define SC_DRAMC_DFS_STA_SEL_LSB            (1U << 12)      /* 4b */
+#define SC_DRS_DIS_ACK_SEL_LSB              (1U << 16)      /* 4b */
+#define SC_DR_SRAM_LOAD_ACK_SEL_LSB         (1U << 20)      /* 4b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_SEL_LSB     (1U << 24)      /* 4b */
+#define SC_DR_SRAM_RESTORE_ACK_SEL_LSB      (1U << 28)      /* 4b */
+/* DRAMC_DPY_CLK_SPM_CON (0x10006000+0x4A0) */
+#define SC_DMYRD_EN_MOD_SEL_PCM_LSB         (1U << 0)       /* 1b */
+#define SC_DMYRD_INTV_SEL_PCM_LSB           (1U << 1)       /* 1b */
+#define SC_DMYRD_EN_PCM_LSB                 (1U << 2)       /* 1b */
+#define SC_DRS_DIS_REQ_PCM_LSB              (1U << 3)       /* 1b */
+#define SC_DR_SHU_LEVEL_SRAM_PCM_LSB        (1U << 4)       /* 4b */
+#define SC_DR_GATE_RETRY_EN_PCM_LSB         (1U << 8)       /* 1b */
+#define SC_DR_SHORT_QUEUE_PCM_LSB           (1U << 9)       /* 1b */
+#define SC_DPY_MIDPI_EN_PCM_LSB             (1U << 10)      /* 1b */
+#define SC_DPY_PI_RESETB_EN_PCM_LSB         (1U << 11)      /* 1b */
+#define SC_DPY_MCK8X_EN_PCM_LSB             (1U << 12)      /* 1b */
+#define SC_DR_RESERVED_0_PCM_LSB            (1U << 13)      /* 1b */
+#define SC_DR_RESERVED_1_PCM_LSB            (1U << 14)      /* 1b */
+#define SC_DR_RESERVED_2_PCM_LSB            (1U << 15)      /* 1b */
+#define SC_DR_RESERVED_3_PCM_LSB            (1U << 16)      /* 1b */
+#define SC_DMDRAMCSHU_ACK_ALL_LSB           (1U << 24)      /* 1b */
+#define SC_EMI_CLK_OFF_ACK_ALL_LSB          (1U << 25)      /* 1b */
+#define SC_DR_SHORT_QUEUE_ACK_ALL_LSB       (1U << 26)      /* 1b */
+#define SC_DRAMC_DFS_STA_ALL_LSB            (1U << 27)      /* 1b */
+#define SC_DRS_DIS_ACK_ALL_LSB              (1U << 28)      /* 1b */
+#define SC_DR_SRAM_LOAD_ACK_ALL_LSB         (1U << 29)      /* 1b */
+#define SC_DR_SRAM_PLL_LOAD_ACK_ALL_LSB     (1U << 30)      /* 1b */
+#define SC_DR_SRAM_RESTORE_ACK_ALL_LSB      (1U << 31)      /* 1b */
+/* SPM_DVFS_LEVEL (0x10006000+0x4A4) */
+#define SPM_DVFS_LEVEL_LSB                  (1U << 0)       /* 32b */
+/* SPM_CIRQ_CON (0x10006000+0x4A8) */
+#define CIRQ_CLK_SEL_LSB                    (1U << 0)       /* 1b */
+/* SPM_DVFS_MISC (0x10006000+0x4AC) */
+#define MSDC_DVFS_REQUEST_LSB               (1U << 0)       /* 1b */
+#define SPM2EMI_SLP_PROT_EN_LSB             (1U << 1)       /* 1b */
+#define SPM_DVFS_FORCE_ENABLE_LSB           (1U << 2)       /* 1b */
+#define FORCE_DVFS_WAKE_LSB                 (1U << 3)       /* 1b */
+#define SPM_DVFSRC_ENABLE_LSB               (1U << 4)       /* 1b */
+#define SPM_DVFS_DONE_LSB                   (1U << 5)       /* 1b */
+#define DVFSRC_IRQ_WAKEUP_EVENT_MASK_LSB    (1U << 6)       /* 1b */
+#define SPM2RC_EVENT_ABORT_LSB              (1U << 7)       /* 1b */
+#define EMI_SLP_IDLE_LSB                    (1U << 14)      /* 1b */
+#define SDIO_READY_TO_SPM_LSB               (1U << 15)      /* 1b */
+/* SPM_VS1_VS2_RC_CON (0x10006000+0x4B0) */
+#define VS1_INIT_LEVEL_LSB                  (1U << 0)       /* 2b */
+#define VS1_INIT_LSB                        (1U << 2)       /* 1b */
+#define VS1_CURR_LEVEL_LSB                  (1U << 3)       /* 2b */
+#define VS1_NEXT_LEVEL_LSB                  (1U << 5)       /* 2b */
+#define VS1_VOTE_LEVEL_LSB                  (1U << 7)       /* 2b */
+#define VS1_TRIGGER_LSB                     (1U << 9)       /* 1b */
+#define VS2_INIT_LEVEL_LSB                  (1U << 10)      /* 3b */
+#define VS2_INIT_LSB                        (1U << 13)      /* 1b */
+#define VS2_CURR_LEVEL_LSB                  (1U << 14)      /* 3b */
+#define VS2_NEXT_LEVEL_LSB                  (1U << 17)      /* 3b */
+#define VS2_VOTE_LEVEL_LSB                  (1U << 20)      /* 3b */
+#define VS2_TRIGGER_LSB                     (1U << 23)      /* 1b */
+#define VS1_FORCE_LSB                       (1U << 24)      /* 1b */
+#define VS2_FORCE_LSB                       (1U << 25)      /* 1b */
+#define VS1_VOTE_LEVEL_FORCE_LSB            (1U << 26)      /* 2b */
+#define VS2_VOTE_LEVEL_FORCE_LSB            (1U << 28)      /* 3b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_0 (0x10006000+0x4B4) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_1 (0x10006000+0x4B8) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_0_MASK_REQ_2 (0x10006000+0x4BC) */
+#define RG_MODULE_SW_CG_0_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_0 (0x10006000+0x4C0) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_1 (0x10006000+0x4C4) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_1_MASK_REQ_2 (0x10006000+0x4C8) */
+#define RG_MODULE_SW_CG_1_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_0 (0x10006000+0x4CC) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_1 (0x10006000+0x4D0) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_2_MASK_REQ_2 (0x10006000+0x4D4) */
+#define RG_MODULE_SW_CG_2_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_0 (0x10006000+0x4D8) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_0_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_1 (0x10006000+0x4DC) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_1_LSB    (1U << 0)       /* 32b */
+/* RG_MODULE_SW_CG_3_MASK_REQ_2 (0x10006000+0x4E0) */
+#define RG_MODULE_SW_CG_3_MASK_REQ_2_LSB    (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_0 (0x10006000+0x4E4) */
+#define PWR_STATUS_MASK_REQ_0_LSB           (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_1 (0x10006000+0x4E8) */
+#define PWR_STATUS_MASK_REQ_1_LSB           (1U << 0)       /* 32b */
+/* PWR_STATUS_MASK_REQ_2 (0x10006000+0x4EC) */
+#define PWR_STATUS_MASK_REQ_2_LSB           (1U << 0)       /* 32b */
+/* SPM_CG_CHECK_CON (0x10006000+0x4F0) */
+#define APMIXEDSYS_BUSY_MASK_REQ_0_LSB      (1U << 0)       /* 5b */
+#define APMIXEDSYS_BUSY_MASK_REQ_1_LSB      (1U << 8)       /* 5b */
+#define APMIXEDSYS_BUSY_MASK_REQ_2_LSB      (1U << 16)      /* 5b */
+#define AUDIOSYS_BUSY_MASK_REQ_0_LSB        (1U << 24)      /* 1b */
+#define AUDIOSYS_BUSY_MASK_REQ_1_LSB        (1U << 25)      /* 1b */
+#define AUDIOSYS_BUSY_MASK_REQ_2_LSB        (1U << 26)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_0_LSB           (1U << 27)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_1_LSB           (1U << 28)      /* 1b */
+#define SSUSB_BUSY_MASK_REQ_2_LSB           (1U << 29)      /* 1b */
+/* SPM_SRC_RDY_STA (0x10006000+0x4F4) */
+#define SPM_INFRA_INTERNAL_ACK_LSB          (1U << 0)       /* 1b */
+#define SPM_VRF18_INTERNAL_ACK_LSB          (1U << 1)       /* 1b */
+/* SPM_DVS_DFS_LEVEL (0x10006000+0x4F8) */
+#define SPM_DFS_LEVEL_LSB                   (1U << 0)       /* 16b */
+#define SPM_DVS_LEVEL_LSB                   (1U << 16)      /* 16b */
+/* SPM_FORCE_DVFS (0x10006000+0x4FC) */
+#define FORCE_DVFS_LEVEL_LSB                (1U << 0)       /* 32b */
+/* SRCLKEN_RC_CFG (0x10006000+0x500) */
+#define SRCLKEN_RC_CFG_LSB                  (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG1 (0x10006000+0x504) */
+#define RC_CENTRAL_CFG1_LSB                 (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG2 (0x10006000+0x508) */
+#define RC_CENTRAL_CFG2_LSB                 (1U << 0)       /* 32b */
+/* RC_CMD_ARB_CFG (0x10006000+0x50C) */
+#define RC_CMD_ARB_CFG_LSB                  (1U << 0)       /* 32b */
+/* RC_PMIC_RCEN_ADDR (0x10006000+0x510) */
+#define RC_PMIC_RCEN_ADDR_LSB               (1U << 0)       /* 16b */
+#define RC_PMIC_RCEN_RESERVE_LSB            (1U << 16)      /* 16b */
+/* RC_PMIC_RCEN_SET_CLR_ADDR (0x10006000+0x514) */
+#define RC_PMIC_RCEN_SET_ADDR_LSB           (1U << 0)       /* 16b */
+#define RC_PMIC_RCEN_CLR_ADDR_LSB           (1U << 16)      /* 16b */
+/* RC_DCXO_FPM_CFG (0x10006000+0x518) */
+#define RC_DCXO_FPM_CFG_LSB                 (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG3 (0x10006000+0x51C) */
+#define RC_CENTRAL_CFG3_LSB                 (1U << 0)       /* 32b */
+/* RC_M00_SRCLKEN_CFG (0x10006000+0x520) */
+#define RC_M00_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+#define RC_SW_SRCLKEN_RC                    (1U << 3)       /* 1b */
+#define RC_SW_SRCLKEN_FPM                   (1U << 4)       /* 1b */
+/* RC_M01_SRCLKEN_CFG (0x10006000+0x524) */
+#define RC_M01_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M02_SRCLKEN_CFG (0x10006000+0x528) */
+#define RC_M02_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M03_SRCLKEN_CFG (0x10006000+0x52C) */
+#define RC_M03_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M04_SRCLKEN_CFG (0x10006000+0x530) */
+#define RC_M04_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M05_SRCLKEN_CFG (0x10006000+0x534) */
+#define RC_M05_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M06_SRCLKEN_CFG (0x10006000+0x538) */
+#define RC_M06_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M07_SRCLKEN_CFG (0x10006000+0x53C) */
+#define RC_M07_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M08_SRCLKEN_CFG (0x10006000+0x540) */
+#define RC_M08_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M09_SRCLKEN_CFG (0x10006000+0x544) */
+#define RC_M09_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M10_SRCLKEN_CFG (0x10006000+0x548) */
+#define RC_M10_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M11_SRCLKEN_CFG (0x10006000+0x54C) */
+#define RC_M11_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_M12_SRCLKEN_CFG (0x10006000+0x550) */
+#define RC_M12_SRCLKEN_CFG_LSB              (1U << 0)       /* 32b */
+/* RC_SRCLKEN_SW_CON_CFG (0x10006000+0x554) */
+#define RC_SRCLKEN_SW_CON_CFG_LSB           (1U << 0)       /* 32b */
+/* RC_CENTRAL_CFG4 (0x10006000+0x558) */
+#define RC_CENTRAL_CFG4_LSB                 (1U << 0)       /* 32b */
+/* RC_PROTOCOL_CHK_CFG (0x10006000+0x560) */
+#define RC_PROTOCOL_CHK_CFG_LSB             (1U << 0)       /* 32b */
+/* RC_DEBUG_CFG (0x10006000+0x564) */
+#define RC_DEBUG_CFG_LSB                    (1U << 0)       /* 32b */
+/* RC_MISC_0 (0x10006000+0x5B4) */
+#define SRCCLKENO_LSB                       (1U << 0)       /* 2b */
+#define PCM_SRCCLKENO_LSB                   (1U << 3)       /* 2b */
+#define RC_VREQ_LSB                         (1U << 5)       /* 1b */
+#define RC_SPM_SRCCLKENO_0_ACK_LSB          (1U << 6)       /* 1b */
+/* RC_SPM_CTRL (0x10006000+0x448) */
+#define SPM_AP_26M_RDY_LSB                  (1U << 0)       /* 1b */
+#define KEEP_RC_SPI_ACTIVE_LSB              (1U << 1)       /* 1b */
+#define SPM2RC_DMY_CTRL_LSB                 (1U << 2)       /* 6b */
+/* SUBSYS_INTF_CFG (0x10006000+0x5BC) */
+#define SRCLKEN_FPM_MASK_B_LSB              (1U << 0)       /* 13b */
+#define SRCLKEN_BBLPM_MASK_B_LSB            (1U << 16)      /* 13b */
+/* PCM_WDT_LATCH_25 (0x10006000+0x5C0) */
+#define PCM_WDT_LATCH_25_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_26 (0x10006000+0x5C4) */
+#define PCM_WDT_LATCH_26_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_27 (0x10006000+0x5C8) */
+#define PCM_WDT_LATCH_27_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_28 (0x10006000+0x5CC) */
+#define PCM_WDT_LATCH_28_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_29 (0x10006000+0x5D0) */
+#define PCM_WDT_LATCH_29_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_30 (0x10006000+0x5D4) */
+#define PCM_WDT_LATCH_30_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_31 (0x10006000+0x5D8) */
+#define PCM_WDT_LATCH_31_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_32 (0x10006000+0x5DC) */
+#define PCM_WDT_LATCH_32_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_33 (0x10006000+0x5E0) */
+#define PCM_WDT_LATCH_33_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_34 (0x10006000+0x5E4) */
+#define PCM_WDT_LATCH_34_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_35 (0x10006000+0x5EC) */
+#define PCM_WDT_LATCH_35_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_36 (0x10006000+0x5F0) */
+#define PCM_WDT_LATCH_36_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_37 (0x10006000+0x5F4) */
+#define PCM_WDT_LATCH_37_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_38 (0x10006000+0x5F8) */
+#define PCM_WDT_LATCH_38_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_39 (0x10006000+0x5FC) */
+#define PCM_WDT_LATCH_39_LSB                (1U << 0)       /* 32b */
+/* SPM_SW_FLAG_0 (0x10006000+0x600) */
+#define SPM_SW_FLAG_LSB                     (1U << 0)       /* 32b */
+/* SPM_SW_DEBUG_0 (0x10006000+0x604) */
+#define SPM_SW_DEBUG_0_LSB                  (1U << 0)       /* 32b */
+/* SPM_SW_FLAG_1 (0x10006000+0x608) */
+#define SPM_SW_FLAG_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_SW_DEBUG_1 (0x10006000+0x60C) */
+#define SPM_SW_DEBUG_1_LSB                  (1U << 0)       /* 32b */
+/* SPM_SW_RSV_0 (0x10006000+0x610) */
+#define SPM_SW_RSV_0_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_1 (0x10006000+0x614) */
+#define SPM_SW_RSV_1_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_2 (0x10006000+0x618) */
+#define SPM_SW_RSV_2_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_3 (0x10006000+0x61C) */
+#define SPM_SW_RSV_3_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_4 (0x10006000+0x620) */
+#define SPM_SW_RSV_4_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_5 (0x10006000+0x624) */
+#define SPM_SW_RSV_5_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_6 (0x10006000+0x628) */
+#define SPM_SW_RSV_6_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_7 (0x10006000+0x62C) */
+#define SPM_SW_RSV_7_LSB                    (1U << 0)       /* 32b */
+/* SPM_SW_RSV_8 (0x10006000+0x630) */
+#define SPM_SW_RSV_8_LSB                    (1U << 0)       /* 32b */
+/* SPM_BK_WAKE_EVENT (0x10006000+0x634) */
+#define SPM_BK_WAKE_EVENT_LSB               (1U << 0)       /* 32b */
+/* SPM_BK_VTCXO_DUR (0x10006000+0x638) */
+#define SPM_BK_VTCXO_DUR_LSB                (1U << 0)       /* 32b */
+/* SPM_BK_WAKE_MISC (0x10006000+0x63C) */
+#define SPM_BK_WAKE_MISC_LSB                (1U << 0)       /* 32b */
+/* SPM_BK_PCM_TIMER (0x10006000+0x640) */
+#define SPM_BK_PCM_TIMER_LSB                (1U << 0)       /* 32b */
+/* SPM_RSV_CON_0 (0x10006000+0x650) */
+#define SPM_RSV_CON_0_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_CON_1 (0x10006000+0x654) */
+#define SPM_RSV_CON_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_STA_0 (0x10006000+0x658) */
+#define SPM_RSV_STA_0_LSB                   (1U << 0)       /* 32b */
+/* SPM_RSV_STA_1 (0x10006000+0x65C) */
+#define SPM_RSV_STA_1_LSB                   (1U << 0)       /* 32b */
+/* SPM_SPARE_CON (0x10006000+0x660) */
+#define SPM_SPARE_CON_LSB                   (1U << 0)       /* 32b */
+/* SPM_SPARE_CON_SET (0x10006000+0x664) */
+#define SPM_SPARE_CON_SET_LSB               (1U << 0)       /* 32b */
+/* SPM_SPARE_CON_CLR (0x10006000+0x668) */
+#define SPM_SPARE_CON_CLR_LSB               (1U << 0)       /* 32b */
+/* SPM_CROSS_WAKE_M00_REQ (0x10006000+0x66C) */
+#define SPM_CROSS_WAKE_M00_REQ_LSB          (1U << 0)       /* 4b */
+#define SPM_CROSS_WAKE_M00_CHK_LSB          (1U << 4)       /* 4b */
+/* SPM_CROSS_WAKE_M01_REQ (0x10006000+0x670) */
+#define SPM_CROSS_WAKE_M01_REQ_LSB          (1U << 0)       /* 4b */
+#define SPM_CROSS_WAKE_M01_CHK_LSB          (1U << 4)       /* 4b */
+/* SPM_CROSS_WAKE_M02_REQ (0x10006000+0x674) */
+#define SPM_CROSS_WAKE_M02_REQ_LSB          (1U << 0)       /* 4b */
+#define SPM_CROSS_WAKE_M02_CHK_LSB          (1U << 4)       /* 4b */
+/* SPM_CROSS_WAKE_M03_REQ (0x10006000+0x678) */
+#define SPM_CROSS_WAKE_M03_REQ_LSB          (1U << 0)       /* 4b */
+#define SPM_CROSS_WAKE_M03_CHK_LSB          (1U << 4)       /* 4b */
+/* SCP_VCORE_LEVEL (0x10006000+0x67C) */
+#define SCP_VCORE_LEVEL_LSB                 (1U << 0)       /* 16b */
+/* SC_MM_CK_SEL_CON (0x10006000+0x680) */
+#define SC_MM_CK_SEL_LSB                    (1U << 0)       /* 4b */
+#define SC_MM_CK_SEL_EN_LSB                 (1U << 4)       /* 1b */
+/* SPARE_ACK_MASK (0x10006000+0x684) */
+#define SPARE_ACK_MASK_B_LSB                (1U << 0)       /* 32b */
+/* SPM_DV_CON_0 (0x10006000+0x68C) */
+#define SPM_DV_CON_0_LSB                    (1U << 0)       /* 32b */
+/* SPM_DV_CON_1 (0x10006000+0x690) */
+#define SPM_DV_CON_1_LSB                    (1U << 0)       /* 32b */
+/* SPM_DV_STA (0x10006000+0x694) */
+#define SPM_DV_STA_LSB                      (1U << 0)       /* 32b */
+/* CONN_XOWCN_DEBUG_EN (0x10006000+0x698) */
+#define CONN_XOWCN_DEBUG_EN_LSB             (1U << 0)       /* 1b */
+/* SPM_SEMA_M0 (0x10006000+0x69C) */
+#define SPM_SEMA_M0_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M1 (0x10006000+0x6A0) */
+#define SPM_SEMA_M1_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M2 (0x10006000+0x6A4) */
+#define SPM_SEMA_M2_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M3 (0x10006000+0x6A8) */
+#define SPM_SEMA_M3_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M4 (0x10006000+0x6AC) */
+#define SPM_SEMA_M4_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M5 (0x10006000+0x6B0) */
+#define SPM_SEMA_M5_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M6 (0x10006000+0x6B4) */
+#define SPM_SEMA_M6_LSB                     (1U << 0)       /* 8b */
+/* SPM_SEMA_M7 (0x10006000+0x6B8) */
+#define SPM_SEMA_M7_LSB                     (1U << 0)       /* 8b */
+/* SPM2ADSP_MAILBOX (0x10006000+0x6BC) */
+#define SPM2ADSP_MAILBOX_LSB                (1U << 0)       /* 32b */
+/* ADSP2SPM_MAILBOX (0x10006000+0x6C0) */
+#define ADSP2SPM_MAILBOX_LSB                (1U << 0)       /* 32b */
+/* SPM_ADSP_IRQ (0x10006000+0x6C4) */
+#define SC_SPM2ADSP_WAKEUP_LSB              (1U << 0)       /* 1b */
+#define SPM_ADSP_IRQ_SC_ADSP2SPM_WAKEUP_LSB (1U << 4)       /* 1b */
+/* SPM_MD32_IRQ (0x10006000+0x6C8) */
+#define SC_SPM2SSPM_WAKEUP_LSB              (1U << 0)       /* 4b */
+#define SPM_MD32_IRQ_SC_SSPM2SPM_WAKEUP_LSB (1U << 4)       /* 4b */
+/* SPM2PMCU_MAILBOX_0 (0x10006000+0x6CC) */
+#define SPM2PMCU_MAILBOX_0_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_1 (0x10006000+0x6D0) */
+#define SPM2PMCU_MAILBOX_1_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_2 (0x10006000+0x6D4) */
+#define SPM2PMCU_MAILBOX_2_LSB              (1U << 0)       /* 32b */
+/* SPM2PMCU_MAILBOX_3 (0x10006000+0x6D8) */
+#define SPM2PMCU_MAILBOX_3_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_0 (0x10006000+0x6DC) */
+#define PMCU2SPM_MAILBOX_0_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_1 (0x10006000+0x6E0) */
+#define PMCU2SPM_MAILBOX_1_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_2 (0x10006000+0x6E4) */
+#define PMCU2SPM_MAILBOX_2_LSB              (1U << 0)       /* 32b */
+/* PMCU2SPM_MAILBOX_3 (0x10006000+0x6E8) */
+#define PMCU2SPM_MAILBOX_3_LSB              (1U << 0)       /* 32b */
+/* UFS_PSRI_SW (0x10006000+0x6EC) */
+#define UFS_PSRI_SW_LSB                     (1U << 0)       /* 1b */
+/* UFS_PSRI_SW_SET (0x10006000+0x6F0) */
+#define UFS_PSRI_SW_SET_LSB                 (1U << 0)       /* 1b */
+/* UFS_PSRI_SW_CLR (0x10006000+0x6F4) */
+#define UFS_PSRI_SW_CLR_LSB                 (1U << 0)       /* 1b */
+/* SPM_AP_SEMA (0x10006000+0x6F8) */
+#define SPM_AP_SEMA_LSB                     (1U << 0)       /* 1b */
+/* SPM_SPM_SEMA (0x10006000+0x6FC) */
+#define SPM_SPM_SEMA_LSB                    (1U << 0)       /* 1b */
+/* SPM_DVFS_CON (0x10006000+0x700) */
+#define SPM_DVFS_CON_LSB                    (1U << 0)       /* 32b */
+/* SPM_DVFS_CON_STA (0x10006000+0x704) */
+#define SPM_DVFS_CON_STA_LSB                (1U << 0)       /* 32b */
+/* SPM_PMIC_SPMI_CON (0x10006000+0x708) */
+#define SPM_PMIC_SPMI_CMD_LSB               (1U << 0)       /* 2b */
+#define SPM_PMIC_SPMI_SLAVEID_LSB           (1U << 2)       /* 4b */
+#define SPM_PMIC_SPMI_PMIFID_LSB            (1U << 6)       /* 1b */
+#define SPM_PMIC_SPMI_DBCNT_LSB             (1U << 7)       /* 1b */
+/* SPM_DVFS_CMD0 (0x10006000+0x710) */
+#define SPM_DVFS_CMD0_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD1 (0x10006000+0x714) */
+#define SPM_DVFS_CMD1_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD2 (0x10006000+0x718) */
+#define SPM_DVFS_CMD2_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD3 (0x10006000+0x71C) */
+#define SPM_DVFS_CMD3_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD4 (0x10006000+0x720) */
+#define SPM_DVFS_CMD4_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD5 (0x10006000+0x724) */
+#define SPM_DVFS_CMD5_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD6 (0x10006000+0x728) */
+#define SPM_DVFS_CMD6_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD7 (0x10006000+0x72C) */
+#define SPM_DVFS_CMD7_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD8 (0x10006000+0x730) */
+#define SPM_DVFS_CMD8_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD9 (0x10006000+0x734) */
+#define SPM_DVFS_CMD9_LSB                   (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD10 (0x10006000+0x738) */
+#define SPM_DVFS_CMD10_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD11 (0x10006000+0x73C) */
+#define SPM_DVFS_CMD11_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD12 (0x10006000+0x740) */
+#define SPM_DVFS_CMD12_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD13 (0x10006000+0x744) */
+#define SPM_DVFS_CMD13_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD14 (0x10006000+0x748) */
+#define SPM_DVFS_CMD14_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD15 (0x10006000+0x74C) */
+#define SPM_DVFS_CMD15_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD16 (0x10006000+0x750) */
+#define SPM_DVFS_CMD16_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD17 (0x10006000+0x754) */
+#define SPM_DVFS_CMD17_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD18 (0x10006000+0x758) */
+#define SPM_DVFS_CMD18_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD19 (0x10006000+0x75C) */
+#define SPM_DVFS_CMD19_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD20 (0x10006000+0x760) */
+#define SPM_DVFS_CMD20_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD21 (0x10006000+0x764) */
+#define SPM_DVFS_CMD21_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD22 (0x10006000+0x768) */
+#define SPM_DVFS_CMD22_LSB                  (1U << 0)       /* 32b */
+/* SPM_DVFS_CMD23 (0x10006000+0x76C) */
+#define SPM_DVFS_CMD23_LSB                  (1U << 0)       /* 32b */
+/* SYS_TIMER_VALUE_L (0x10006000+0x770) */
+#define SYS_TIMER_VALUE_L_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_VALUE_H (0x10006000+0x774) */
+#define SYS_TIMER_VALUE_H_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_START_L (0x10006000+0x778) */
+#define SYS_TIMER_START_L_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_START_H (0x10006000+0x77C) */
+#define SYS_TIMER_START_H_LSB               (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_00 (0x10006000+0x780) */
+#define SYS_TIMER_LATCH_L_00_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_00 (0x10006000+0x784) */
+#define SYS_TIMER_LATCH_H_00_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_01 (0x10006000+0x788) */
+#define SYS_TIMER_LATCH_L_01_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_01 (0x10006000+0x78C) */
+#define SYS_TIMER_LATCH_H_01_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_02 (0x10006000+0x790) */
+#define SYS_TIMER_LATCH_L_02_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_02 (0x10006000+0x794) */
+#define SYS_TIMER_LATCH_H_02_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_03 (0x10006000+0x798) */
+#define SYS_TIMER_LATCH_L_03_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_03 (0x10006000+0x79C) */
+#define SYS_TIMER_LATCH_H_03_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_04 (0x10006000+0x7A0) */
+#define SYS_TIMER_LATCH_L_04_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_04 (0x10006000+0x7A4) */
+#define SYS_TIMER_LATCH_H_04_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_05 (0x10006000+0x7A8) */
+#define SYS_TIMER_LATCH_L_05_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_05 (0x10006000+0x7AC) */
+#define SYS_TIMER_LATCH_H_05_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_06 (0x10006000+0x7B0) */
+#define SYS_TIMER_LATCH_L_06_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_06 (0x10006000+0x7B4) */
+#define SYS_TIMER_LATCH_H_06_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_07 (0x10006000+0x7B8) */
+#define SYS_TIMER_LATCH_L_07_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_07 (0x10006000+0x7BC) */
+#define SYS_TIMER_LATCH_H_07_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_08 (0x10006000+0x7C0) */
+#define SYS_TIMER_LATCH_L_08_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_08 (0x10006000+0x7C4) */
+#define SYS_TIMER_LATCH_H_08_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_09 (0x10006000+0x7C8) */
+#define SYS_TIMER_LATCH_L_09_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_09 (0x10006000+0x7CC) */
+#define SYS_TIMER_LATCH_H_09_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_10 (0x10006000+0x7D0) */
+#define SYS_TIMER_LATCH_L_10_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_10 (0x10006000+0x7D4) */
+#define SYS_TIMER_LATCH_H_10_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_11 (0x10006000+0x7D8) */
+#define SYS_TIMER_LATCH_L_11_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_11 (0x10006000+0x7DC) */
+#define SYS_TIMER_LATCH_H_11_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_12 (0x10006000+0x7E0) */
+#define SYS_TIMER_LATCH_L_12_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_12 (0x10006000+0x7E4) */
+#define SYS_TIMER_LATCH_H_12_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_13 (0x10006000+0x7E8) */
+#define SYS_TIMER_LATCH_L_13_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_13 (0x10006000+0x7EC) */
+#define SYS_TIMER_LATCH_H_13_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_14 (0x10006000+0x7F0) */
+#define SYS_TIMER_LATCH_L_14_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_14 (0x10006000+0x7F4) */
+#define SYS_TIMER_LATCH_H_14_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_L_15 (0x10006000+0x7F8) */
+#define SYS_TIMER_LATCH_L_15_LSB            (1U << 0)       /* 32b */
+/* SYS_TIMER_LATCH_H_15 (0x10006000+0x7FC) */
+#define SYS_TIMER_LATCH_H_15_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_0 (0x10006000+0x800) */
+#define PCM_WDT_LATCH_0_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_1 (0x10006000+0x804) */
+#define PCM_WDT_LATCH_1_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_2 (0x10006000+0x808) */
+#define PCM_WDT_LATCH_2_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_3 (0x10006000+0x80C) */
+#define PCM_WDT_LATCH_3_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_4 (0x10006000+0x810) */
+#define PCM_WDT_LATCH_4_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_5 (0x10006000+0x814) */
+#define PCM_WDT_LATCH_5_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_6 (0x10006000+0x818) */
+#define PCM_WDT_LATCH_6_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_7 (0x10006000+0x81C) */
+#define PCM_WDT_LATCH_7_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_8 (0x10006000+0x820) */
+#define PCM_WDT_LATCH_8_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_9 (0x10006000+0x824) */
+#define PCM_WDT_LATCH_9_LSB                 (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_10 (0x10006000+0x828) */
+#define PCM_WDT_LATCH_10_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_11 (0x10006000+0x82C) */
+#define PCM_WDT_LATCH_11_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_12 (0x10006000+0x830) */
+#define PCM_WDT_LATCH_12_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_13 (0x10006000+0x834) */
+#define PCM_WDT_LATCH_13_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_14 (0x10006000+0x838) */
+#define PCM_WDT_LATCH_14_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_15 (0x10006000+0x83C) */
+#define PCM_WDT_LATCH_15_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_16 (0x10006000+0x840) */
+#define PCM_WDT_LATCH_16_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_17 (0x10006000+0x844) */
+#define PCM_WDT_LATCH_17_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_18 (0x10006000+0x848) */
+#define PCM_WDT_LATCH_18_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_0 (0x10006000+0x84C) */
+#define PCM_WDT_LATCH_SPARE_0_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_1 (0x10006000+0x850) */
+#define PCM_WDT_LATCH_SPARE_1_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_SPARE_2 (0x10006000+0x854) */
+#define PCM_WDT_LATCH_SPARE_2_LSB           (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_0 (0x10006000+0x870) */
+#define PCM_WDT_LATCH_CONN_0_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_1 (0x10006000+0x874) */
+#define PCM_WDT_LATCH_CONN_1_LSB            (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_CONN_2 (0x10006000+0x878) */
+#define PCM_WDT_LATCH_CONN_2_LSB            (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_0 (0x10006000+0x8A0) */
+#define DRAMC_GATING_ERR_LATCH_CH0_0_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_1 (0x10006000+0x8A4) */
+#define DRAMC_GATING_ERR_LATCH_CH0_1_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_2 (0x10006000+0x8A8) */
+#define DRAMC_GATING_ERR_LATCH_CH0_2_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_3 (0x10006000+0x8AC) */
+#define DRAMC_GATING_ERR_LATCH_CH0_3_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_4 (0x10006000+0x8B0) */
+#define DRAMC_GATING_ERR_LATCH_CH0_4_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_5 (0x10006000+0x8B4) */
+#define DRAMC_GATING_ERR_LATCH_CH0_5_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_CH0_6 (0x10006000+0x8B8) */
+#define DRAMC_GATING_ERR_LATCH_CH0_6_LSB    (1U << 0)       /* 32b */
+/* DRAMC_GATING_ERR_LATCH_SPARE_0 (0x10006000+0x8F4) */
+#define DRAMC_GATING_ERR_LATCH_SPARE_0_LSB  (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_0 (0x10006000+0x900) */
+#define SPM_ACK_CHK_SW_EN_0_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_0_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_0_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_0_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_0_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_0_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_0_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_0_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_0_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_0_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_0_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_0 (0x10006000+0x904) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_0_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_0_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_0 (0x10006000+0x908) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_0_LSB (1U << 0)       /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_0_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_0_LSB (1U << 16)      /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_0_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_0 (0x10006000+0x90C) */
+#define SPM_ACK_CHK_TIMER_VAL_0_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_0_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_0 (0x10006000+0x910) */
+#define SPM_ACK_CHK_STA_0_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_0 (0x10006000+0x914) */
+#define SPM_ACK_CHK_SWINT_EN_0_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_1 (0x10006000+0x920) */
+#define SPM_ACK_CHK_SW_EN_1_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_1_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_1_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_1_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_1_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_1_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_1_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_1_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_1_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_1_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_1_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_1 (0x10006000+0x924) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_1_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_1_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_1 (0x10006000+0x928) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_1_LSB (1U << 0)       /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_1_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_1_LSB (1U << 16)      /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_1_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_1 (0x10006000+0x92C) */
+#define SPM_ACK_CHK_TIMER_VAL_1_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_1_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_1 (0x10006000+0x930) */
+#define SPM_ACK_CHK_STA_1_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_1 (0x10006000+0x934) */
+#define SPM_ACK_CHK_SWINT_EN_1_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_2 (0x10006000+0x940) */
+#define SPM_ACK_CHK_SW_EN_2_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_2_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_2_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_2_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_2_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_2_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_2_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_2_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_2_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_2_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_2_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_2 (0x10006000+0x944) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_2_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_2_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_2 (0x10006000+0x948) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_2_LSB (1U << 0)       /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_2_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_2_LSB (1U << 16)      /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_2_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_2 (0x10006000+0x94C) */
+#define SPM_ACK_CHK_TIMER_VAL_2_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_2_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_2 (0x10006000+0x950) */
+#define SPM_ACK_CHK_STA_2_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_2 (0x10006000+0x954) */
+#define SPM_ACK_CHK_SWINT_EN_2_LSB          (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_CON_3 (0x10006000+0x960) */
+#define SPM_ACK_CHK_SW_EN_3_LSB             (1U << 0)       /* 1b */
+#define SPM_ACK_CHK_CLR_ALL_3_LSB           (1U << 1)       /* 1b */
+#define SPM_ACK_CHK_CLR_TIMER_3_LSB         (1U << 2)       /* 1b */
+#define SPM_ACK_CHK_CLR_IRQ_3_LSB           (1U << 3)       /* 1b */
+#define SPM_ACK_CHK_STA_EN_3_LSB            (1U << 4)       /* 1b */
+#define SPM_ACK_CHK_WAKEUP_EN_3_LSB         (1U << 5)       /* 1b */
+#define SPM_ACK_CHK_WDT_EN_3_LSB            (1U << 6)       /* 1b */
+#define SPM_ACK_CHK_LOCK_PC_TRACE_EN_3_LSB  (1U << 7)       /* 1b */
+#define SPM_ACK_CHK_HW_EN_3_LSB             (1U << 8)       /* 1b */
+#define SPM_ACK_CHK_HW_MODE_3_LSB           (1U << 9)       /* 3b */
+#define SPM_ACK_CHK_FAIL_3_LSB              (1U << 15)      /* 1b */
+/* SPM_ACK_CHK_PC_3 (0x10006000+0x964) */
+#define SPM_ACK_CHK_HW_TRIG_PC_VAL_3_LSB    (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_HW_TARG_PC_VAL_3_LSB    (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_SEL_3 (0x10006000+0x968) */
+#define SPM_ACK_CHK_HW_TRIG_SIGNAL_SEL_3_LSB (1U << 0)       /* 5b */
+#define SPM_ACK_CHK_HW_TRIG_GROUP_SEL_3_LSB (1U << 5)       /* 3b */
+#define SPM_ACK_CHK_HW_TARG_SIGNAL_SEL_3_LSB (1U << 16)      /* 5b */
+#define SPM_ACK_CHK_HW_TARG_GROUP_SEL_3_LSB (1U << 21)      /* 3b */
+/* SPM_ACK_CHK_TIMER_3 (0x10006000+0x96C) */
+#define SPM_ACK_CHK_TIMER_VAL_3_LSB         (1U << 0)       /* 16b */
+#define SPM_ACK_CHK_TIMER_3_LSB             (1U << 16)      /* 16b */
+/* SPM_ACK_CHK_STA_3 (0x10006000+0x970) */
+#define SPM_ACK_CHK_STA_3_LSB               (1U << 0)       /* 32b */
+/* SPM_ACK_CHK_SWINT_3 (0x10006000+0x974) */
+#define SPM_ACK_CHK_SWINT_EN_3_LSB          (1U << 0)       /* 32b */
+/* SPM_COUNTER_0 (0x10006000+0x978) */
+#define SPM_COUNTER_VAL_0_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_0_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_0_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_0_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_0_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_0_LSB         (1U << 31)      /* 1b */
+/* SPM_COUNTER_1 (0x10006000+0x97C) */
+#define SPM_COUNTER_VAL_1_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_1_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_1_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_1_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_1_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_1_LSB         (1U << 31)      /* 1b */
+/* SPM_COUNTER_2 (0x10006000+0x980) */
+#define SPM_COUNTER_VAL_2_LSB               (1U << 0)       /* 14b */
+#define SPM_COUNTER_OUT_2_LSB               (1U << 14)      /* 14b */
+#define SPM_COUNTER_EN_2_LSB                (1U << 28)      /* 1b */
+#define SPM_COUNTER_CLR_2_LSB               (1U << 29)      /* 1b */
+#define SPM_COUNTER_TIMEOUT_2_LSB           (1U << 30)      /* 1b */
+#define SPM_COUNTER_WAKEUP_EN_2_LSB         (1U << 31)      /* 1b */
+/* SYS_TIMER_CON (0x10006000+0x98C) */
+#define SYS_TIMER_START_EN_LSB              (1U << 0)       /* 1b */
+#define SYS_TIMER_LATCH_EN_LSB              (1U << 1)       /* 1b */
+#define SYS_TIMER_ID_LSB                    (1U << 8)       /* 8b */
+#define SYS_TIMER_VALID_LSB                 (1U << 31)      /* 1b */
+/* RC_FSM_STA_0 (0x10006000+0xE00) */
+#define RC_FSM_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_CMD_STA_0 (0x10006000+0xE04) */
+#define RC_CMD_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_CMD_STA_1 (0x10006000+0xE08) */
+#define RC_CMD_STA_1_LSB                    (1U << 0)       /* 32b */
+/* RC_SPI_STA_0 (0x10006000+0xE0C) */
+#define RC_SPI_STA_0_LSB                    (1U << 0)       /* 32b */
+/* RC_PI_PO_STA_0 (0x10006000+0xE10) */
+#define RC_PI_PO_STA_0_LSB                  (1U << 0)       /* 32b */
+/* RC_M00_REQ_STA_0 (0x10006000+0xE14) */
+#define RC_M00_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M01_REQ_STA_0 (0x10006000+0xE1C) */
+#define RC_M01_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M02_REQ_STA_0 (0x10006000+0xE20) */
+#define RC_M02_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M03_REQ_STA_0 (0x10006000+0xE24) */
+#define RC_M03_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M04_REQ_STA_0 (0x10006000+0xE28) */
+#define RC_M04_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M05_REQ_STA_0 (0x10006000+0xE2C) */
+#define RC_M05_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M06_REQ_STA_0 (0x10006000+0xE30) */
+#define RC_M06_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M07_REQ_STA_0 (0x10006000+0xE34) */
+#define RC_M07_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M08_REQ_STA_0 (0x10006000+0xE38) */
+#define RC_M08_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M09_REQ_STA_0 (0x10006000+0xE3C) */
+#define RC_M09_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M10_REQ_STA_0 (0x10006000+0xE40) */
+#define RC_M10_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M11_REQ_STA_0 (0x10006000+0xE44) */
+#define RC_M11_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_M12_REQ_STA_0 (0x10006000+0xE48) */
+#define RC_M12_REQ_STA_0_LSB                (1U << 0)       /* 32b */
+/* RC_DEBUG_STA_0 (0x10006000+0xE4C) */
+#define RC_DEBUG_STA_0_LSB                  (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_0_LSB (0x10006000+0xE50) */
+#define RO_PMRC_TRACE_00_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_0_MSB (0x10006000+0xE54) */
+#define RO_PMRC_TRACE_00_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_1_LSB (0x10006000+0xE5C) */
+#define RO_PMRC_TRACE_01_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_1_MSB (0x10006000+0xE60) */
+#define RO_PMRC_TRACE_01_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_2_LSB (0x10006000+0xE64) */
+#define RO_PMRC_TRACE_02_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_2_MSB (0x10006000+0xE6C) */
+#define RO_PMRC_TRACE_02_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_3_LSB (0x10006000+0xE70) */
+#define RO_PMRC_TRACE_03_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_3_MSB (0x10006000+0xE74) */
+#define RO_PMRC_TRACE_03_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_4_LSB (0x10006000+0xE78) */
+#define RO_PMRC_TRACE_04_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_4_MSB (0x10006000+0xE7C) */
+#define RO_PMRC_TRACE_04_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_5_LSB (0x10006000+0xE80) */
+#define RO_PMRC_TRACE_05_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_5_MSB (0x10006000+0xE84) */
+#define RO_PMRC_TRACE_05_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_6_LSB (0x10006000+0xE88) */
+#define RO_PMRC_TRACE_06_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_6_MSB (0x10006000+0xE8C) */
+#define RO_PMRC_TRACE_06_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_7_LSB (0x10006000+0xE90) */
+#define RO_PMRC_TRACE_07_LSB_LSB            (1U << 0)       /* 32b */
+/* RC_DEBUG_TRACE_7_MSB (0x10006000+0xE94) */
+#define RO_PMRC_TRACE_07_MSB_LSB            (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_0_LSB (0x10006000+0xE98) */
+#define RC_SYS_TIMER_LATCH_L_00_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_0_MSB (0x10006000+0xE9C) */
+#define RC_SYS_TIMER_LATCH_H_00_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_1_LSB (0x10006000+0xEA0) */
+#define RC_SYS_TIMER_LATCH_L_01_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_1_MSB (0x10006000+0xEA4) */
+#define RC_SYS_TIMER_LATCH_H_01_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_2_LSB (0x10006000+0xEA8) */
+#define RC_SYS_TIMER_LATCH_L_02_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_2_MSB (0x10006000+0xEAC) */
+#define RC_SYS_TIMER_LATCH_H_02_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_3_LSB (0x10006000+0xEB0) */
+#define RC_SYS_TIMER_LATCH_L_03_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_3_MSB (0x10006000+0xEB4) */
+#define RC_SYS_TIMER_LATCH_H_03_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_4_LSB (0x10006000+0xEB8) */
+#define RC_SYS_TIMER_LATCH_L_04_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_4_MSB (0x10006000+0xEBC) */
+#define RC_SYS_TIMER_LATCH_H_04_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_5_LSB (0x10006000+0xEC0) */
+#define RC_SYS_TIMER_LATCH_L_05_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_5_MSB (0x10006000+0xEC4) */
+#define RC_SYS_TIMER_LATCH_H_05_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_6_LSB (0x10006000+0xEC8) */
+#define RC_SYS_TIMER_LATCH_L_06_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_6_MSB (0x10006000+0xECC) */
+#define RC_SYS_TIMER_LATCH_H_06_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_7_LSB (0x10006000+0xED0) */
+#define RC_SYS_TIMER_LATCH_L_07_LSB         (1U << 0)       /* 32b */
+/* RC_SYS_TIMER_LATCH_7_MSB (0x10006000+0xED4) */
+#define RC_SYS_TIMER_LATCH_H_07_LSB         (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_19 (0x10006000+0xED8) */
+#define PCM_WDT_LATCH_19_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_20 (0x10006000+0xEDC) */
+#define PCM_WDT_LATCH_20_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_21 (0x10006000+0xEE0) */
+#define PCM_WDT_LATCH_21_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_22 (0x10006000+0xEE4) */
+#define PCM_WDT_LATCH_22_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_23 (0x10006000+0xEE8) */
+#define PCM_WDT_LATCH_23_LSB                (1U << 0)       /* 32b */
+/* PCM_WDT_LATCH_24 (0x10006000+0xEEC) */
+#define PCM_WDT_LATCH_24_LSB                (1U << 0)       /* 32b */
+/* PMSR_LAST_DAT (0x10006000+0xF00) */
+#define PMSR_LAST_DAT_LSB                   (1U << 0)       /* 32b */
+/* PMSR_LAST_CNT (0x10006000+0xF04) */
+#define PMSR_LAST_CMD_LSB                   (1U << 0)       /* 30b */
+#define PMSR_LAST_REQ_LSB                   (1U << 30)      /* 1b */
+/* PMSR_LAST_ACK (0x10006000+0xF08) */
+#define PMSR_LAST_ACK_LSB                   (1U << 0)       /* 1b */
+/* SPM_PMSR_SEL_CON0 (0x10006000+0xF10) */
+#define REG_PMSR_SIG_SEL_0_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_1_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_2_LSB              (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_3_LSB              (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON1 (0x10006000+0xF14) */
+#define REG_PMSR_SIG_SEL_4_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_5_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_6_LSB              (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_7_LSB              (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON2 (0x10006000+0xF18) */
+#define REG_PMSR_SIG_SEL_8_LSB              (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_9_LSB              (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_10_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_11_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON3 (0x10006000+0xF1C) */
+#define REG_PMSR_SIG_SEL_12_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_13_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_14_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_15_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON4 (0x10006000+0xF20) */
+#define REG_PMSR_SIG_SEL_16_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_17_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_18_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_19_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON5 (0x10006000+0xF24) */
+#define REG_PMSR_SIG_SEL_20_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_21_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_22_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_23_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON6 (0x10006000+0xF28) */
+#define REG_PMSR_SIG_SEL_24_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_25_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_26_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_27_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON7 (0x10006000+0xF2C) */
+#define REG_PMSR_SIG_SEL_28_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_29_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_30_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_31_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON8 (0x10006000+0xF30) */
+#define REG_PMSR_SIG_SEL_32_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_33_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_34_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_35_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON9 (0x10006000+0xF34) */
+#define REG_PMSR_SIG_SEL_36_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_37_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_38_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_39_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON10 (0x10006000+0xF3C) */
+#define REG_PMSR_SIG_SEL_40_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_41_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_42_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_43_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_SEL_CON11 (0x10006000+0xF40) */
+#define REG_PMSR_SIG_SEL_44_LSB             (1U << 0)       /* 8b */
+#define REG_PMSR_SIG_SEL_45_LSB             (1U << 8)       /* 8b */
+#define REG_PMSR_SIG_SEL_46_LSB             (1U << 16)      /* 8b */
+#define REG_PMSR_SIG_SEL_47_LSB             (1U << 24)      /* 8b */
+/* SPM_PMSR_TIEMR_STA0 (0x10006000+0xFB8) */
+#define PMSR_TIMER_SET0_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_TIEMR_STA1 (0x10006000+0xFBC) */
+#define PMSR_TIMER_SET1_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_TIEMR_STA2 (0x10006000+0xFC0) */
+#define PMSR_TIMER_SET2_LSB                 (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON0 (0x10006000+0xFC4) */
+#define PMSR_ENABLE_SET0_LSB                (1U << 0)       /* 1b */
+#define PMSR_ENABLE_SET1_LSB                (1U << 1)       /* 1b */
+#define PMSR_ENABLE_SET2_LSB                (1U << 2)       /* 1b */
+#define PMSR_IRQ_CLR_SET0_LSB               (1U << 3)       /* 1b */
+#define PMSR_IRQ_CLR_SET1_LSB               (1U << 4)       /* 1b */
+#define PMSR_IRQ_CLR_SET2_LSB               (1U << 5)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET0_LSB         (1U << 6)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET1_LSB         (1U << 7)       /* 1b */
+#define PMSR_SPEED_MODE_EN_SET2_LSB         (1U << 8)       /* 1b */
+#define PMSR_EVENT_CLR_SET0_LSB             (1U << 9)       /* 1b */
+#define PMSR_EVENT_CLR_SET1_LSB             (1U << 10)      /* 1b */
+#define PMSR_EVENT_CLR_SET2_LSB             (1U << 11)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET0_LSB          (1U << 12)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET1_LSB          (1U << 13)      /* 1b */
+#define REG_PMSR_IRQ_MASK_SET2_LSB          (1U << 14)      /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET0_LSB (1U << 15)      /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET1_LSB (1U << 16)      /* 1b */
+#define REG_PMSR_IRQ_WAKEUP_EVENT_MASK_SET2_LSB (1U << 17)      /* 1b */
+#define PMSR_GEN_SW_RST_EN_LSB              (1U << 18)      /* 1b */
+#define PMSR_MODULE_ENABLE_LSB              (1U << 19)      /* 1b */
+#define PMSR_MODE_LSB                       (1U << 20)      /* 2b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET0_LSB (1U << 29)      /* 1b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET1_LSB (1U << 30)      /* 1b */
+#define SPM_PMSR_GENERAL_CON0_PMSR_IRQ_B_SET2_LSB (1U << 31)      /* 1b */
+/* SPM_PMSR_GENERAL_CON1 (0x10006000+0xFC8) */
+#define PMSR_COUNTER_THRES_LSB              (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON2 (0x10006000+0xFCC) */
+#define PMSR_DEBUG_IN_0_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON3 (0x10006000+0xFD0) */
+#define PMSR_DEBUG_IN_1_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON4 (0x10006000+0xFD4) */
+#define PMSR_DEBUG_IN_2_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_GENERAL_CON5 (0x10006000+0xFD8) */
+#define PMSR_DEBUG_IN_3_MASK_B_LSB          (1U << 0)       /* 32b */
+/* SPM_PMSR_SW_RESET (0x10006000+0xFDC) */
+#define PMSR_SW_RST_EN_SET0_LSB             (1U << 0)       /* 1b */
+#define PMSR_SW_RST_EN_SET1_LSB             (1U << 1)       /* 1b */
+#define PMSR_SW_RST_EN_SET2_LSB             (1U << 2)       /* 1b */
+/* SPM_PMSR_MON_CON0 (0x10006000+0xFE0) */
+#define REG_PMSR_MON_TYPE_0_LSB             (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_1_LSB             (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_2_LSB             (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_3_LSB             (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_4_LSB             (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_5_LSB             (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_6_LSB             (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_7_LSB             (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_8_LSB             (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_9_LSB             (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_10_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_11_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_12_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_13_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_14_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_15_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_MON_CON1 (0x10006000+0xFE4) */
+#define REG_PMSR_MON_TYPE_16_LSB            (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_17_LSB            (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_18_LSB            (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_19_LSB            (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_20_LSB            (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_21_LSB            (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_22_LSB            (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_23_LSB            (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_24_LSB            (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_25_LSB            (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_26_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_27_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_28_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_29_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_30_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_31_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_MON_CON2 (0x10006000+0xFE8) */
+#define REG_PMSR_MON_TYPE_32_LSB            (1U << 0)       /* 2b */
+#define REG_PMSR_MON_TYPE_33_LSB            (1U << 2)       /* 2b */
+#define REG_PMSR_MON_TYPE_34_LSB            (1U << 4)       /* 2b */
+#define REG_PMSR_MON_TYPE_35_LSB            (1U << 6)       /* 2b */
+#define REG_PMSR_MON_TYPE_36_LSB            (1U << 8)       /* 2b */
+#define REG_PMSR_MON_TYPE_37_LSB            (1U << 10)      /* 2b */
+#define REG_PMSR_MON_TYPE_38_LSB            (1U << 12)      /* 2b */
+#define REG_PMSR_MON_TYPE_39_LSB            (1U << 14)      /* 2b */
+#define REG_PMSR_MON_TYPE_40_LSB            (1U << 16)      /* 2b */
+#define REG_PMSR_MON_TYPE_41_LSB            (1U << 18)      /* 2b */
+#define REG_PMSR_MON_TYPE_42_LSB            (1U << 20)      /* 2b */
+#define REG_PMSR_MON_TYPE_43_LSB            (1U << 22)      /* 2b */
+#define REG_PMSR_MON_TYPE_44_LSB            (1U << 24)      /* 2b */
+#define REG_PMSR_MON_TYPE_45_LSB            (1U << 26)      /* 2b */
+#define REG_PMSR_MON_TYPE_46_LSB            (1U << 28)      /* 2b */
+#define REG_PMSR_MON_TYPE_47_LSB            (1U << 30)      /* 2b */
+/* SPM_PMSR_LEN_CON0 (0x10006000+0xFEC) */
+#define REG_PMSR_WINDOW_LEN_SET0_LSB        (1U << 0)       /* 32b */
+/* SPM_PMSR_LEN_CON1 (0x10006000+0xFF0) */
+#define REG_PMSR_WINDOW_LEN_SET1_LSB        (1U << 0)       /* 32b */
+/* SPM_PMSR_LEN_CON2 (0x10006000+0xFF4) */
+#define REG_PMSR_WINDOW_LEN_SET2_LSB        (1U << 0)       /* 32b */
+
+#define SPM_PROJECT_CODE	0xb16
+#define SPM_REGWR_CFG_KEY	(SPM_PROJECT_CODE << 16)
+#endif
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_resource_req.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_resource_req.h
new file mode 100644
index 0000000..26250ba
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_resource_req.h
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_RESOURCE_REQ_H
+#define MT_SPM_RESOURCE_REQ_H
+
+/* SPM resource request internal bit */
+#define MT_SPM_BIT_XO_FPM	0
+#define MT_SPM_BIT_26M		1
+#define MT_SPM_BIT_INFRA	2
+#define MT_SPM_BIT_SYSPLL	3
+#define MT_SPM_BIT_DRAM_S0	4
+#define MT_SPM_BIT_DRAM_S1	5
+
+/* SPM resource request internal bit_mask */
+#define MT_SPM_XO_FPM	BIT(MT_SPM_BIT_XO_FPM)
+#define MT_SPM_26M	BIT(MT_SPM_BIT_26M)
+#define MT_SPM_INFRA	BIT(MT_SPM_BIT_INFRA)
+#define MT_SPM_SYSPLL	BIT(MT_SPM_BIT_SYSPLL)
+#define MT_SPM_DRAM_S0	BIT(MT_SPM_BIT_DRAM_S0)
+#define MT_SPM_DRAM_S1	BIT(MT_SPM_BIT_DRAM_S1)
+#endif /* MT_SPM_RESOURCE_REQ_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.c
new file mode 100644
index 0000000..d018953
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.c
@@ -0,0 +1,394 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <mt_spm.h>
+#include <mt_spm_conservation.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_rc_internal.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_resource_req.h>
+#include <mt_spm_suspend.h>
+#include <plat_pm.h>
+#include <uart.h>
+
+#define SPM_SUSPEND_SLEEP_PCM_FLAG			\
+	(SPM_FLAG_DISABLE_INFRA_PDN |			\
+	 SPM_FLAG_DISABLE_VCORE_DVS |			\
+	 SPM_FLAG_DISABLE_VCORE_DFS |			\
+	 SPM_FLAG_KEEP_CSYSPWRACK_HIGH |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |	\
+	 SPM_FLAG_SRAM_SLEEP_CTRL)
+
+#define SPM_SUSPEND_SLEEP_PCM_FLAG1	0
+
+#define SPM_SUSPEND_PCM_FLAG				\
+	(SPM_FLAG_DISABLE_VCORE_DVS |			\
+	 SPM_FLAG_DISABLE_VCORE_DFS |			\
+	 SPM_FLAG_ENABLE_TIA_WORKAROUND |		\
+	 SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP |	\
+	 SPM_FLAG_SRAM_SLEEP_CTRL)
+
+#define SPM_SUSPEND_PCM_FLAG1		0
+
+/* Suspend spm power control */
+#define __WAKE_SRC_FOR_SUSPEND_COMMON__			\
+	(R12_PCM_TIMER |				\
+	 R12_KP_IRQ_B |					\
+	 R12_APWDT_EVENT_B |				\
+	 R12_CONN2AP_SPM_WAKEUP_B |			\
+	 R12_EINT_EVENT_B |				\
+	 R12_CONN_WDT_IRQ_B |				\
+	 R12_CCIF0_EVENT_B |				\
+	 R12_SSPM2SPM_WAKEUP_B |			\
+	 R12_SCP2SPM_WAKEUP_B |				\
+	 R12_USBX_CDSC_B |				\
+	 R12_USBX_POWERDWN_B |				\
+	 R12_SYS_TIMER_EVENT_B |			\
+	 R12_EINT_EVENT_SECURE_B |			\
+	 R12_SYS_CIRQ_IRQ_B |				\
+	 R12_MD2AP_PEER_EVENT_B |			\
+	 R12_MD1_WDT_B |				\
+	 R12_CLDMA_EVENT_B |				\
+	 R12_REG_CPU_WAKEUP |				\
+	 R12_APUSYS_WAKE_HOST_B)
+
+#if defined(CFG_MICROTRUST_TEE_SUPPORT)
+#define WAKE_SRC_FOR_SUSPEND (__WAKE_SRC_FOR_SUSPEND_COMMON__)
+#else
+#define WAKE_SRC_FOR_SUSPEND			\
+	(__WAKE_SRC_FOR_SUSPEND_COMMON__ |	\
+	 R12_SEJ_EVENT_B)
+#endif
+
+static struct pwr_ctrl suspend_ctrl = {
+	.wake_src = WAKE_SRC_FOR_SUSPEND,
+
+	/* SPM_AP_STANDBY_CON */
+	/* [0] */
+	.reg_wfi_op = 0,
+	/* [1] */
+	.reg_wfi_type = 0,
+	/* [2] */
+	.reg_mp0_cputop_idle_mask = 0,
+	/* [3] */
+	.reg_mp1_cputop_idle_mask = 0,
+	/* [4] */
+	.reg_mcusys_idle_mask = 0,
+	/* [25] */
+	.reg_md_apsrc_1_sel = 0,
+	/* [26] */
+	.reg_md_apsrc_0_sel = 0,
+	/* [29] */
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC_REQ */
+	/* [0] */
+	.reg_spm_apsrc_req = 0,
+	/* [1] */
+	.reg_spm_f26m_req = 0,
+	/* [3] */
+	.reg_spm_infra_req = 0,
+	/* [4] */
+	.reg_spm_vrf18_req = 0,
+	/* [7] FIXME: default disable HW Auto S1*/
+	.reg_spm_ddr_en_req = 1,
+	/* [8] */
+	.reg_spm_dvfs_req = 0,
+	/* [9] */
+	.reg_spm_sw_mailbox_req = 0,
+	/* [10] */
+	.reg_spm_sspm_mailbox_req = 0,
+	/* [11] */
+	.reg_spm_adsp_mailbox_req = 0,
+	/* [12] */
+	.reg_spm_scp_mailbox_req = 0,
+
+	/* SPM_SRC_MASK */
+	/* [0] */
+	.reg_sspm_srcclkena_0_mask_b = 1,
+	/* [1] */
+	.reg_sspm_infra_req_0_mask_b = 1,
+	/* [2] */
+	.reg_sspm_apsrc_req_0_mask_b = 1,
+	/* [3] */
+	.reg_sspm_vrf18_req_0_mask_b = 1,
+	/* [4] */
+	.reg_sspm_ddr_en_0_mask_b = 1,
+	/* [5] */
+	.reg_scp_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_scp_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_scp_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_scp_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_scp_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_apu_srcclkena_mask_b = 1,
+	/* [16] */
+	.reg_apu_infra_req_mask_b = 1,
+	/* [17] */
+	.reg_apu_apsrc_req_mask_b = 1,
+	/* [18] */
+	.reg_apu_vrf18_req_mask_b = 1,
+	/* [19] */
+	.reg_apu_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_cpueb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_cpueb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_cpueb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_cpueb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_cpueb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	/* [26] */
+	.reg_bak_psri_infra_req_mask_b = 0,
+	/* [27] */
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	/* [28] */
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	/* [29] */
+	.reg_bak_psri_ddr_en_mask_b = 0,
+
+	/* SPM_SRC2_MASK */
+	/* [0] */
+	.reg_msdc0_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_msdc0_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_msdc0_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_msdc1_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_msdc1_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_msdc1_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_msdc2_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_msdc2_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_msdc2_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_ufs_srcclkena_mask_b = 0,
+	/* [16] */
+	.reg_ufs_infra_req_mask_b = 0,
+	/* [17] */
+	.reg_ufs_apsrc_req_mask_b = 0,
+	/* [18] */
+	.reg_ufs_vrf18_req_mask_b = 0,
+	/* [19] */
+	.reg_ufs_ddr_en_mask_b = 0,
+	/* [20] */
+	.reg_usb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_usb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_usb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_usb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_usb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_pextp_p0_srcclkena_mask_b = 1,
+	/* [26] */
+	.reg_pextp_p0_infra_req_mask_b = 1,
+	/* [27] */
+	.reg_pextp_p0_apsrc_req_mask_b = 1,
+	/* [28] */
+	.reg_pextp_p0_vrf18_req_mask_b = 1,
+	/* [29] */
+	.reg_pextp_p0_ddr_en_mask_b = 1,
+
+	/* SPM_SRC3_MASK */
+	/* [0] */
+	.reg_pextp_p1_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_pextp_p1_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_pextp_p1_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_pextp_p1_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_pextp_p1_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_gce0_infra_req_mask_b = 1,
+	/* [6] */
+	.reg_gce0_apsrc_req_mask_b = 1,
+	/* [7] */
+	.reg_gce0_vrf18_req_mask_b = 1,
+	/* [8] */
+	.reg_gce0_ddr_en_mask_b = 1,
+	/* [9] */
+	.reg_gce1_infra_req_mask_b = 1,
+	/* [10] */
+	.reg_gce1_apsrc_req_mask_b = 1,
+	/* [11] */
+	.reg_gce1_vrf18_req_mask_b = 1,
+	/* [12] */
+	.reg_gce1_ddr_en_mask_b = 1,
+	/* [13] */
+	.reg_spm_srcclkena_reserved_mask_b = 1,
+	/* [14] */
+	.reg_spm_infra_req_reserved_mask_b = 1,
+	/* [15] */
+	.reg_spm_apsrc_req_reserved_mask_b = 1,
+	/* [16] */
+	.reg_spm_vrf18_req_reserved_mask_b = 1,
+	/* [17] */
+	.reg_spm_ddr_en_reserved_mask_b = 1,
+	/* [18] */
+	.reg_disp0_apsrc_req_mask_b = 1,
+	/* [19] */
+	.reg_disp0_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_disp1_apsrc_req_mask_b = 1,
+	/* [21] */
+	.reg_disp1_ddr_en_mask_b = 1,
+	/* [22] */
+	.reg_disp2_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_disp2_ddr_en_mask_b = 1,
+	/* [24] */
+	.reg_disp3_apsrc_req_mask_b = 1,
+	/* [25] */
+	.reg_disp3_ddr_en_mask_b = 1,
+	/* [26] */
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	/* [27] */
+	.reg_infrasys_ddr_en_mask_b = 1,
+
+	/* [28] */
+	.reg_cg_check_srcclkena_mask_b = 1,
+	/* [29] */
+	.reg_cg_check_apsrc_req_mask_b = 1,
+	/* [30] */
+	.reg_cg_check_vrf18_req_mask_b = 1,
+	/* [31] */
+	.reg_cg_check_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	/* [8:0] */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x17,
+	/* [17:9] */
+	.reg_mcusys_merge_ddr_en_mask_b = 0x17,
+	/* [19:18] */
+	.reg_dramc_md32_infra_req_mask_b = 0,
+	/* [21:20] */
+	.reg_dramc_md32_vrf18_req_mask_b = 0,
+	/* [23:22] */
+	.reg_dramc_md32_ddr_en_mask_b = 0,
+	/* [24] */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK2 */
+	/* [3:0] */
+	.reg_sc_sw2spm_wakeup_mask_b = 0,
+	/* [4] */
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	/* [8:5] */
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	/* [9] */
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	/* [10] */
+	.reg_csyspwrup_ack_mask = 0,
+	/* [11] */
+	.reg_csyspwrup_req_mask = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	/* [31:0] */
+	.reg_wakeup_event_mask = 0xC1382213,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	/* [31:0] */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+};
+
+struct spm_lp_scen __spm_suspend = {
+	.pwrctrl = &suspend_ctrl,
+};
+
+int mt_spm_suspend_mode_set(int mode)
+{
+	if (mode == MT_SPM_SUSPEND_SLEEP) {
+		suspend_ctrl.pcm_flags = SPM_SUSPEND_SLEEP_PCM_FLAG;
+		suspend_ctrl.pcm_flags1 = SPM_SUSPEND_SLEEP_PCM_FLAG1;
+	} else {
+		suspend_ctrl.pcm_flags = SPM_SUSPEND_PCM_FLAG;
+		suspend_ctrl.pcm_flags1 = SPM_SUSPEND_PCM_FLAG1;
+	}
+
+	return 0;
+}
+
+int mt_spm_suspend_enter(int state_id, unsigned int ext_opand,
+			 unsigned int resource_req)
+{
+	/* If FMAudio / ADSP is active, change to sleep suspend mode */
+	if ((ext_opand & MT_SPM_EX_OP_SET_SUSPEND_MODE) != 0U) {
+		mt_spm_suspend_mode_set(MT_SPM_SUSPEND_SLEEP);
+	}
+
+	/* Notify MCUPM that device is going suspend flow */
+	mmio_write_32(MCUPM_MBOX_OFFSET_PDN, MCUPM_POWER_DOWN);
+
+	/* Notify UART to sleep */
+	mt_uart_save();
+
+	return spm_conservation(state_id, ext_opand,
+				&__spm_suspend, resource_req);
+}
+
+void mt_spm_suspend_resume(int state_id, unsigned int ext_opand,
+			   struct wake_status **status)
+{
+	spm_conservation_finish(state_id, ext_opand, &__spm_suspend, status);
+
+	/* Notify UART to wakeup */
+	mt_uart_restore();
+
+	/* Notify MCUPM that device leave suspend */
+	mmio_write_32(MCUPM_MBOX_OFFSET_PDN, 0);
+
+	/* If FMAudio / ADSP is active, change back to suspend mode */
+	if ((ext_opand & MT_SPM_EX_OP_SET_SUSPEND_MODE) != 0U) {
+		mt_spm_suspend_mode_set(MT_SPM_SUSPEND_SYSTEM_PDN);
+	}
+}
+
+void mt_spm_suspend_init(void)
+{
+	spm_conservation_pwrctrl_init(__spm_suspend.pwrctrl);
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.h
new file mode 100644
index 0000000..69c5230
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_suspend.h
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SUSPEND_H
+#define MT_SPM_SUSPEND_H
+
+#include <mt_spm_internal.h>
+
+#define MCUPM_MBOX_OFFSET_PDN	0x1031FF88
+#define MCUPM_POWER_DOWN	0x4D50444E
+
+enum MT_SPM_SUSPEND_MODE {
+	MT_SPM_SUSPEND_SYSTEM_PDN,
+	MT_SPM_SUSPEND_SLEEP,
+};
+
+extern int mt_spm_suspend_mode_set(int mode);
+extern int mt_spm_suspend_enter(int state_id, unsigned int ext_opand,
+				unsigned int reosuce_req);
+extern void mt_spm_suspend_resume(int state_id, unsigned int ext_opand,
+				  struct wake_status **status);
+extern void mt_spm_suspend_init(void);
+#endif /* MT_SPM_SUSPEND_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.c b/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.c
new file mode 100644
index 0000000..6a85b5c
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.c
@@ -0,0 +1,526 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <stddef.h>
+#include <string.h>
+#include <common/debug.h>
+#include <lib/bakery_lock.h>
+#include <lib/mmio.h>
+#include <mt_spm.h>
+#include <mt_spm_internal.h>
+#include <mt_spm_pmic_wrap.h>
+#include <mt_spm_reg.h>
+#include <mt_spm_vcorefs.h>
+#include <mtk_plat_common.h>
+#include <mtk_sip_svc.h>
+#include <platform_def.h>
+
+#define VCORE_MAX_OPP 4
+#define DRAM_MAX_OPP 7
+
+static bool spm_dvfs_init_done;
+static bool dvfs_enable_done;
+static int vcore_opp_0_uv = 750000;
+static int vcore_opp_1_uv = 650000;
+static int vcore_opp_2_uv = 600000;
+static int vcore_opp_3_uv = 550000;
+
+static struct reg_config dvfsrc_init_configs[] = {
+	{ DVFSRC_HRT_REQ_UNIT,       0x0000001E },
+	{ DVFSRC_DEBOUNCE_TIME,      0x19651965 },
+	{ DVFSRC_TIMEOUT_NEXTREQ,    0x00000015 },
+	{ DVFSRC_LEVEL_MASK,         0x000EE000 },
+	{ DVFSRC_DDR_QOS0,           0x00000019 },
+	{ DVFSRC_DDR_QOS1,           0x00000026 },
+	{ DVFSRC_DDR_QOS2,           0x00000033 },
+	{ DVFSRC_DDR_QOS3,           0x0000003B },
+	{ DVFSRC_DDR_QOS4,           0x0000004C },
+	{ DVFSRC_DDR_QOS5,           0x00000066 },
+	{ DVFSRC_DDR_QOS6,           0x00660066 },
+	{ DVFSRC_LEVEL_LABEL_0_1,    0x50436053 },
+	{ DVFSRC_LEVEL_LABEL_2_3,    0x40335042 },
+	{ DVFSRC_LEVEL_LABEL_4_5,    0x40314032 },
+	{ DVFSRC_LEVEL_LABEL_6_7,    0x30223023 },
+	{ DVFSRC_LEVEL_LABEL_8_9,    0x20133021 },
+	{ DVFSRC_LEVEL_LABEL_10_11,  0x20112012 },
+	{ DVFSRC_LEVEL_LABEL_12_13,  0x10032010 },
+	{ DVFSRC_LEVEL_LABEL_14_15,  0x10011002 },
+	{ DVFSRC_LEVEL_LABEL_16_17,  0x00131000 },
+	{ DVFSRC_LEVEL_LABEL_18_19,  0x00110012 },
+	{ DVFSRC_LEVEL_LABEL_20_21,  0x00000010 },
+	{ DVFSRC_MD_LATENCY_IMPROVE, 0x00000040 },
+	{ DVFSRC_DDR_REQUEST,        0x00004321 },
+	{ DVFSRC_DDR_REQUEST3,       0x00000065 },
+	{ DVFSRC_DDR_ADD_REQUEST,    0x66543210 },
+	{ DVFSRC_HRT_REQUEST,        0x66654321 },
+	{ DVFSRC_DDR_REQUEST5,       0x54321000 },
+	{ DVFSRC_DDR_REQUEST7,       0x66000000 },
+	{ DVFSRC_VCORE_USER_REQ,     0x00010A29 },
+	{ DVFSRC_HRT_HIGH_3,         0x18A618A6 },
+	{ DVFSRC_HRT_HIGH_2,         0x18A61183 },
+	{ DVFSRC_HRT_HIGH_1,         0x0D690B80 },
+	{ DVFSRC_HRT_HIGH,           0x070804B0 },
+	{ DVFSRC_HRT_LOW_3,          0x18A518A5 },
+	{ DVFSRC_HRT_LOW_2,          0x18A51182 },
+	{ DVFSRC_HRT_LOW_1,          0x0D680B7F },
+	{ DVFSRC_HRT_LOW,            0x070704AF },
+	{ DVFSRC_BASIC_CONTROL_3,    0x00000006 },
+	{ DVFSRC_INT_EN,             0x00000002 },
+	{ DVFSRC_QOS_EN,             0x0000407C },
+	{ DVFSRC_HRT_BW_BASE,        0x00000004 },
+	{ DVFSRC_PCIE_VCORE_REQ,     0x65908101 },
+	{ DVFSRC_CURRENT_FORCE,      0x00000001 },
+	{ DVFSRC_BASIC_CONTROL,      0x6698444B },
+	{ DVFSRC_BASIC_CONTROL,      0x6698054B },
+	{ DVFSRC_CURRENT_FORCE,      0x00000000 },
+};
+
+static struct pwr_ctrl vcorefs_ctrl = {
+	.wake_src		= R12_REG_CPU_WAKEUP,
+
+	/* default VCORE DVFS is disabled */
+	.pcm_flags = (SPM_FLAG_RUN_COMMON_SCENARIO |
+			SPM_FLAG_DISABLE_VCORE_DVS | SPM_FLAG_DISABLE_VCORE_DFS),
+
+	/* SPM_AP_STANDBY_CON */
+	/* [0] */
+	.reg_wfi_op = 0,
+	/* [1] */
+	.reg_wfi_type = 0,
+	/* [2] */
+	.reg_mp0_cputop_idle_mask = 0,
+	/* [3] */
+	.reg_mp1_cputop_idle_mask = 0,
+	/* [4] */
+	.reg_mcusys_idle_mask = 0,
+	/* [25] */
+	.reg_md_apsrc_1_sel = 0,
+	/* [26] */
+	.reg_md_apsrc_0_sel = 0,
+	/* [29] */
+	.reg_conn_apsrc_sel = 0,
+
+	/* SPM_SRC_REQ */
+	/* [0] */
+	.reg_spm_apsrc_req = 0,
+	/* [1] */
+	.reg_spm_f26m_req = 0,
+	/* [3] */
+	.reg_spm_infra_req = 0,
+	/* [4] */
+	.reg_spm_vrf18_req = 0,
+	/* [7] FIXME: default disable HW Auto S1*/
+	.reg_spm_ddr_en_req = 1,
+	/* [8] */
+	.reg_spm_dvfs_req = 0,
+	/* [9] */
+	.reg_spm_sw_mailbox_req = 0,
+	/* [10] */
+	.reg_spm_sspm_mailbox_req = 0,
+	/* [11] */
+	.reg_spm_adsp_mailbox_req = 0,
+	/* [12] */
+	.reg_spm_scp_mailbox_req = 0,
+
+	/* SPM_SRC_MASK */
+	/* [0] */
+	.reg_sspm_srcclkena_0_mask_b = 1,
+	/* [1] */
+	.reg_sspm_infra_req_0_mask_b = 1,
+	/* [2] */
+	.reg_sspm_apsrc_req_0_mask_b = 1,
+	/* [3] */
+	.reg_sspm_vrf18_req_0_mask_b = 1,
+	/* [4] */
+	.reg_sspm_ddr_en_0_mask_b = 1,
+	/* [5] */
+	.reg_scp_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_scp_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_scp_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_scp_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_scp_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_audio_dsp_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_audio_dsp_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_audio_dsp_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_audio_dsp_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_audio_dsp_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_apu_srcclkena_mask_b = 1,
+	/* [16] */
+	.reg_apu_infra_req_mask_b = 1,
+	/* [17] */
+	.reg_apu_apsrc_req_mask_b = 1,
+	/* [18] */
+	.reg_apu_vrf18_req_mask_b = 1,
+	/* [19] */
+	.reg_apu_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_cpueb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_cpueb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_cpueb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_cpueb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_cpueb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_bak_psri_srcclkena_mask_b = 0,
+	/* [26] */
+	.reg_bak_psri_infra_req_mask_b = 0,
+	/* [27] */
+	.reg_bak_psri_apsrc_req_mask_b = 0,
+	/* [28] */
+	.reg_bak_psri_vrf18_req_mask_b = 0,
+	/* [29] */
+	.reg_bak_psri_ddr_en_mask_b = 0,
+
+	/* SPM_SRC2_MASK */
+	/* [0] */
+	.reg_msdc0_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_msdc0_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_msdc0_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_msdc0_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_msdc0_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_msdc1_srcclkena_mask_b = 1,
+	/* [6] */
+	.reg_msdc1_infra_req_mask_b = 1,
+	/* [7] */
+	.reg_msdc1_apsrc_req_mask_b = 1,
+	/* [8] */
+	.reg_msdc1_vrf18_req_mask_b = 1,
+	/* [9] */
+	.reg_msdc1_ddr_en_mask_b = 1,
+	/* [10] */
+	.reg_msdc2_srcclkena_mask_b = 1,
+	/* [11] */
+	.reg_msdc2_infra_req_mask_b = 1,
+	/* [12] */
+	.reg_msdc2_apsrc_req_mask_b = 1,
+	/* [13] */
+	.reg_msdc2_vrf18_req_mask_b = 1,
+	/* [14] */
+	.reg_msdc2_ddr_en_mask_b = 1,
+	/* [15] */
+	.reg_ufs_srcclkena_mask_b = 1,
+	/* [16] */
+	.reg_ufs_infra_req_mask_b = 1,
+	/* [17] */
+	.reg_ufs_apsrc_req_mask_b = 1,
+	/* [18] */
+	.reg_ufs_vrf18_req_mask_b = 1,
+	/* [19] */
+	.reg_ufs_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_usb_srcclkena_mask_b = 1,
+	/* [21] */
+	.reg_usb_infra_req_mask_b = 1,
+	/* [22] */
+	.reg_usb_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_usb_vrf18_req_mask_b = 1,
+	/* [24] */
+	.reg_usb_ddr_en_mask_b = 1,
+	/* [25] */
+	.reg_pextp_p0_srcclkena_mask_b = 1,
+	/* [26] */
+	.reg_pextp_p0_infra_req_mask_b = 1,
+	/* [27] */
+	.reg_pextp_p0_apsrc_req_mask_b = 1,
+	/* [28] */
+	.reg_pextp_p0_vrf18_req_mask_b = 1,
+	/* [29] */
+	.reg_pextp_p0_ddr_en_mask_b = 1,
+
+	/* SPM_SRC3_MASK */
+	/* [0] */
+	.reg_pextp_p1_srcclkena_mask_b = 1,
+	/* [1] */
+	.reg_pextp_p1_infra_req_mask_b = 1,
+	/* [2] */
+	.reg_pextp_p1_apsrc_req_mask_b = 1,
+	/* [3] */
+	.reg_pextp_p1_vrf18_req_mask_b = 1,
+	/* [4] */
+	.reg_pextp_p1_ddr_en_mask_b = 1,
+	/* [5] */
+	.reg_gce0_infra_req_mask_b = 1,
+	/* [6] */
+	.reg_gce0_apsrc_req_mask_b = 1,
+	/* [7] */
+	.reg_gce0_vrf18_req_mask_b = 1,
+	/* [8] */
+	.reg_gce0_ddr_en_mask_b = 1,
+	/* [9] */
+	.reg_gce1_infra_req_mask_b = 1,
+	/* [10] */
+	.reg_gce1_apsrc_req_mask_b = 1,
+	/* [11] */
+	.reg_gce1_vrf18_req_mask_b = 1,
+	/* [12] */
+	.reg_gce1_ddr_en_mask_b = 1,
+	/* [13] */
+	.reg_spm_srcclkena_reserved_mask_b = 1,
+	/* [14] */
+	.reg_spm_infra_req_reserved_mask_b = 1,
+	/* [15] */
+	.reg_spm_apsrc_req_reserved_mask_b = 1,
+	/* [16] */
+	.reg_spm_vrf18_req_reserved_mask_b = 1,
+	/* [17] */
+	.reg_spm_ddr_en_reserved_mask_b = 1,
+	/* [18] */
+	.reg_disp0_apsrc_req_mask_b = 1,
+	/* [19] */
+	.reg_disp0_ddr_en_mask_b = 1,
+	/* [20] */
+	.reg_disp1_apsrc_req_mask_b = 1,
+	/* [21] */
+	.reg_disp1_ddr_en_mask_b = 1,
+	/* [22] */
+	.reg_disp2_apsrc_req_mask_b = 1,
+	/* [23] */
+	.reg_disp2_ddr_en_mask_b = 1,
+	/* [24] */
+	.reg_disp3_apsrc_req_mask_b = 1,
+	/* [25] */
+	.reg_disp3_ddr_en_mask_b = 1,
+	/* [26] */
+	.reg_infrasys_apsrc_req_mask_b = 0,
+	/* [27] */
+	.reg_infrasys_ddr_en_mask_b = 1,
+
+	/* [28] */
+	.reg_cg_check_srcclkena_mask_b = 1,
+	/* [29] */
+	.reg_cg_check_apsrc_req_mask_b = 1,
+	/* [30] */
+	.reg_cg_check_vrf18_req_mask_b = 1,
+	/* [31] */
+	.reg_cg_check_ddr_en_mask_b = 1,
+
+	/* SPM_SRC4_MASK */
+	/* [8:0] */
+	.reg_mcusys_merge_apsrc_req_mask_b = 0x11,
+	/* [17:9] */
+	.reg_mcusys_merge_ddr_en_mask_b = 0x11,
+	/* [19:18] */
+	.reg_dramc_md32_infra_req_mask_b = 0,
+	/* [21:20] */
+	.reg_dramc_md32_vrf18_req_mask_b = 0,
+	/* [23:22] */
+	.reg_dramc_md32_ddr_en_mask_b = 0,
+	/* [24] */
+	.reg_dvfsrc_event_trigger_mask_b = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK2 */
+	/* [3:0] */
+	.reg_sc_sw2spm_wakeup_mask_b = 0,
+	/* [4] */
+	.reg_sc_adsp2spm_wakeup_mask_b = 0,
+	/* [8:5] */
+	.reg_sc_sspm2spm_wakeup_mask_b = 0,
+	/* [9] */
+	.reg_sc_scp2spm_wakeup_mask_b = 0,
+	/* [10] */
+	.reg_csyspwrup_ack_mask = 0,
+	/* [11] */
+	.reg_csyspwrup_req_mask = 1,
+
+	/* SPM_WAKEUP_EVENT_MASK */
+	/* [31:0] */
+	.reg_wakeup_event_mask = 0xEFFFFFFF,
+
+	/* SPM_WAKEUP_EVENT_EXT_MASK */
+	/* [31:0] */
+	.reg_ext_wakeup_event_mask = 0xFFFFFFFF,
+};
+
+struct spm_lp_scen __spm_vcorefs = {
+	.pwrctrl	= &vcorefs_ctrl,
+};
+
+static void spm_vcorefs_pwarp_cmd(uint64_t cmd, uint64_t val)
+{
+	if (cmd < NR_IDX_ALL) {
+		mt_spm_pmic_wrap_set_cmd(PMIC_WRAP_PHASE_ALLINONE, cmd, val);
+	} else {
+		INFO("cmd out of range!\n");
+	}
+}
+
+void spm_dvfsfw_init(uint64_t boot_up_opp, uint64_t dram_issue)
+{
+	if (spm_dvfs_init_done == false) {
+		mmio_write_32(SPM_DVFS_MISC, (mmio_read_32(SPM_DVFS_MISC) &
+				~(SPM_DVFS_FORCE_ENABLE_LSB)) | (SPM_DVFSRC_ENABLE_LSB));
+
+		mmio_write_32(SPM_DVFS_LEVEL, 0x00000001);
+		mmio_write_32(SPM_DVS_DFS_LEVEL, 0x00010001);
+
+		spm_dvfs_init_done = true;
+	}
+}
+
+void __spm_sync_vcore_dvfs_power_control(struct pwr_ctrl *dest_pwr_ctrl,
+						const struct pwr_ctrl *src_pwr_ctrl)
+{
+	uint32_t dvfs_mask = SPM_FLAG_DISABLE_VCORE_DVS |
+			     SPM_FLAG_DISABLE_VCORE_DFS |
+			     SPM_FLAG_ENABLE_VOLTAGE_BIN;
+
+	dest_pwr_ctrl->pcm_flags = (dest_pwr_ctrl->pcm_flags & (~dvfs_mask)) |
+					(src_pwr_ctrl->pcm_flags & dvfs_mask);
+
+	if (dest_pwr_ctrl->pcm_flags_cust) {
+		dest_pwr_ctrl->pcm_flags_cust = (dest_pwr_ctrl->pcm_flags_cust & (~dvfs_mask)) |
+						(src_pwr_ctrl->pcm_flags & dvfs_mask);
+	}
+}
+
+void spm_go_to_vcorefs(uint64_t spm_flags)
+{
+	__spm_set_power_control(__spm_vcorefs.pwrctrl);
+	__spm_set_wakeup_event(__spm_vcorefs.pwrctrl);
+	__spm_set_pcm_flags(__spm_vcorefs.pwrctrl);
+	__spm_send_cpu_wakeup_event();
+}
+
+uint64_t spm_vcorefs_args(uint64_t x1, uint64_t x2, uint64_t x3)
+{
+	uint64_t ret = 0U;
+	uint64_t cmd = x1;
+	uint64_t spm_flags;
+
+	switch (cmd) {
+	case VCOREFS_SMC_CMD_0:
+		spm_dvfsfw_init(x2, x3);
+		break;
+	case VCOREFS_SMC_CMD_1:
+		spm_flags = SPM_FLAG_RUN_COMMON_SCENARIO;
+		if (x2 & SPM_FLAG_DISABLE_VCORE_DVS)
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DVS;
+		if (x2 & SPM_FLAG_DISABLE_VCORE_DFS)
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DFS;
+		spm_go_to_vcorefs(spm_flags);
+		break;
+	case VCOREFS_SMC_CMD_3:
+		spm_vcorefs_pwarp_cmd(x2, x3);
+		break;
+	case VCOREFS_SMC_CMD_2:
+	case VCOREFS_SMC_CMD_4:
+	case VCOREFS_SMC_CMD_5:
+	case VCOREFS_SMC_CMD_7:
+	default:
+		break;
+	}
+	return ret;
+}
+
+static void dvfsrc_init(void)
+{
+	int i;
+	int count = ARRAY_SIZE(dvfsrc_init_configs);
+
+	if (dvfs_enable_done == false) {
+		for (i = 0; i < count; i++) {
+			mmio_write_32(dvfsrc_init_configs[i].offset,
+				dvfsrc_init_configs[i].val);
+		}
+
+		mmio_write_32(DVFSRC_QOS_EN, 0x0011007C);
+
+		dvfs_enable_done = true;
+	}
+}
+
+static void spm_vcorefs_vcore_setting(uint64_t flag)
+{
+	spm_vcorefs_pwarp_cmd(3, __vcore_uv_to_pmic(vcore_opp_3_uv));
+	spm_vcorefs_pwarp_cmd(2, __vcore_uv_to_pmic(vcore_opp_2_uv));
+	spm_vcorefs_pwarp_cmd(1, __vcore_uv_to_pmic(vcore_opp_1_uv));
+	spm_vcorefs_pwarp_cmd(0, __vcore_uv_to_pmic(vcore_opp_0_uv));
+}
+
+int spm_vcorefs_get_vcore(unsigned int gear)
+{
+	int ret_val;
+
+	switch (gear) {
+	case 3:
+		ret_val = vcore_opp_0_uv;
+		break;
+	case 2:
+		ret_val = vcore_opp_1_uv;
+		break;
+	case 1:
+		ret_val = vcore_opp_2_uv;
+		break;
+	case 0:
+	default:
+		ret_val = vcore_opp_3_uv;
+		break;
+	}
+	return ret_val;
+}
+
+uint64_t spm_vcorefs_v2_args(u_register_t x1, u_register_t x2, u_register_t x3, u_register_t *x4)
+{
+	uint64_t ret = 0U;
+	uint64_t cmd = x1;
+	uint64_t spm_flags;
+
+	switch (cmd) {
+	case VCOREFS_SMC_CMD_INIT:
+		/* vcore_dvfs init + kick */
+		spm_dvfsfw_init(0, 0);
+		spm_vcorefs_vcore_setting(x3 & 0xF);
+		spm_flags = SPM_FLAG_RUN_COMMON_SCENARIO;
+		if (x2 & 0x1) {
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DVS;
+		}
+		if (x2 & 0x2) {
+			spm_flags |= SPM_FLAG_DISABLE_VCORE_DFS;
+		}
+		spm_go_to_vcorefs(spm_flags);
+		dvfsrc_init();
+		*x4 = 0U;
+		break;
+	case VCOREFS_SMC_CMD_OPP_TYPE:
+		/* get dram type */
+		*x4 = 0U;
+		break;
+	case VCOREFS_SMC_CMD_FW_TYPE:
+		*x4 = 0U;
+		break;
+	case VCOREFS_SMC_CMD_GET_UV:
+		*x4 = spm_vcorefs_get_vcore(x2);
+		break;
+	case VCOREFS_SMC_CMD_GET_NUM_V:
+		*x4 = VCORE_MAX_OPP;
+		break;
+	case VCOREFS_SMC_CMD_GET_NUM_F:
+		*x4 = DRAM_MAX_OPP;
+		break;
+	default:
+		break;
+	}
+
+	return ret;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.h b/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.h
new file mode 100644
index 0000000..b08fcce
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/mt_spm_vcorefs.h
@@ -0,0 +1,328 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef __MT_SPM_VCOREFS__H__
+#define __MT_SPM_VCOREFS__H__
+
+int spm_vcorefs_get_vcore(unsigned int gear);
+uint64_t spm_vcorefs_v2_args(u_register_t x1, u_register_t x2, u_register_t x3,
+			     u_register_t *x4);
+
+enum vcorefs_smc_cmd {
+	VCOREFS_SMC_CMD_0 = 0,
+	VCOREFS_SMC_CMD_1,
+	VCOREFS_SMC_CMD_2,
+	VCOREFS_SMC_CMD_3,
+	VCOREFS_SMC_CMD_4,
+	/* check spmfw status */
+	VCOREFS_SMC_CMD_5,
+
+	/* get spmfw type */
+	VCOREFS_SMC_CMD_6,
+
+	/* get spm reg status */
+	VCOREFS_SMC_CMD_7,
+
+	NUM_VCOREFS_SMC_CMD,
+};
+
+enum vcorefs_smc_cmd_new {
+	VCOREFS_SMC_CMD_INIT = 0,
+	VCOREFS_SMC_CMD_KICK = 1,
+	VCOREFS_SMC_CMD_OPP_TYPE = 2,
+	VCOREFS_SMC_CMD_FW_TYPE = 3,
+	VCOREFS_SMC_CMD_GET_UV = 4,
+	VCOREFS_SMC_CMD_GET_FREQ = 5,
+	VCOREFS_SMC_CMD_GET_NUM_V = 6,
+	VCOREFS_SMC_CMD_GET_NUM_F = 7,
+	VCOREFS_SMC_CMD_FB_ACTION = 8,
+	/*chip specific setting */
+	VCOREFS_SMC_CMD_SET_FREQ = 16,
+	VCOREFS_SMC_CMD_SET_EFUSE = 17,
+	VCOREFS_SMC_CMD_GET_EFUSE = 18,
+	VCOREFS_SMC_CMD_DVFS_HOPPING = 19,
+	VCOREFS_SMC_CMD_DVFS_HOPPING_STATE = 20,
+};
+
+enum dvfsrc_channel {
+	DVFSRC_CHANNEL_1 = 1,
+	DVFSRC_CHANNEL_2,
+	DVFSRC_CHANNEL_3,
+	DVFSRC_CHANNEL_4,
+	NUM_DVFSRC_CHANNEL,
+};
+
+#define _VCORE_BASE_UV		400000
+#define _VCORE_STEP_UV		6250
+
+/* PMIC */
+#define __vcore_pmic_to_uv(pmic)	\
+	(((pmic) * _VCORE_STEP_UV) + _VCORE_BASE_UV)
+
+#define __vcore_uv_to_pmic(uv)	/* pmic >= uv */	\
+	((((uv) - _VCORE_BASE_UV) + (_VCORE_STEP_UV - 1)) / _VCORE_STEP_UV)
+
+struct reg_config {
+	uint32_t offset;
+	uint32_t val;
+};
+
+#define DVFSRC_BASIC_CONTROL             (DVFSRC_BASE + 0x0)
+#define DVFSRC_SW_REQ1                   (DVFSRC_BASE + 0x4)
+#define DVFSRC_SW_REQ2                   (DVFSRC_BASE + 0x8)
+#define DVFSRC_SW_REQ3                   (DVFSRC_BASE + 0xC)
+#define DVFSRC_SW_REQ4                   (DVFSRC_BASE + 0x10)
+#define DVFSRC_SW_REQ5                   (DVFSRC_BASE + 0x14)
+#define DVFSRC_SW_REQ6                   (DVFSRC_BASE + 0x18)
+#define DVFSRC_SW_REQ7                   (DVFSRC_BASE + 0x1C)
+#define DVFSRC_SW_REQ8                   (DVFSRC_BASE + 0x20)
+#define DVFSRC_EMI_REQUEST               (DVFSRC_BASE + 0x24)
+#define DVFSRC_EMI_REQUEST2              (DVFSRC_BASE + 0x28)
+#define DVFSRC_EMI_REQUEST3              (DVFSRC_BASE + 0x2C)
+#define DVFSRC_EMI_REQUEST4              (DVFSRC_BASE + 0x30)
+#define DVFSRC_EMI_REQUEST5              (DVFSRC_BASE + 0x34)
+#define DVFSRC_EMI_REQUEST6              (DVFSRC_BASE + 0x38)
+#define DVFSRC_EMI_HRT                   (DVFSRC_BASE + 0x3C)
+#define DVFSRC_EMI_HRT2                  (DVFSRC_BASE + 0x40)
+#define DVFSRC_EMI_HRT3                  (DVFSRC_BASE + 0x44)
+#define DVFSRC_EMI_QOS0                  (DVFSRC_BASE + 0x48)
+#define DVFSRC_EMI_QOS1                  (DVFSRC_BASE + 0x4C)
+#define DVFSRC_EMI_QOS2                  (DVFSRC_BASE + 0x50)
+#define DVFSRC_EMI_MD2SPM0               (DVFSRC_BASE + 0x54)
+#define DVFSRC_EMI_MD2SPM1               (DVFSRC_BASE + 0x58)
+#define DVFSRC_EMI_MD2SPM2               (DVFSRC_BASE + 0x5C)
+#define DVFSRC_EMI_MD2SPM0_T             (DVFSRC_BASE + 0x60)
+#define DVFSRC_EMI_MD2SPM1_T             (DVFSRC_BASE + 0x64)
+#define DVFSRC_EMI_MD2SPM2_T             (DVFSRC_BASE + 0x68)
+#define DVFSRC_VCORE_REQUEST             (DVFSRC_BASE + 0x6C)
+#define DVFSRC_VCORE_REQUEST2            (DVFSRC_BASE + 0x70)
+#define DVFSRC_VCORE_REQUEST3            (DVFSRC_BASE + 0x74)
+#define DVFSRC_VCORE_REQUEST4            (DVFSRC_BASE + 0x78)
+#define DVFSRC_VCORE_HRT                 (DVFSRC_BASE + 0x7C)
+#define DVFSRC_VCORE_HRT2                (DVFSRC_BASE + 0x80)
+#define DVFSRC_VCORE_HRT3                (DVFSRC_BASE + 0x84)
+#define DVFSRC_VCORE_QOS0                (DVFSRC_BASE + 0x88)
+#define DVFSRC_VCORE_QOS1                (DVFSRC_BASE + 0x8C)
+#define DVFSRC_VCORE_QOS2                (DVFSRC_BASE + 0x90)
+#define DVFSRC_VCORE_MD2SPM0             (DVFSRC_BASE + 0x94)
+#define DVFSRC_VCORE_MD2SPM1             (DVFSRC_BASE + 0x98)
+#define DVFSRC_VCORE_MD2SPM2             (DVFSRC_BASE + 0x9C)
+#define DVFSRC_VCORE_MD2SPM0_T           (DVFSRC_BASE + 0xA0)
+#define DVFSRC_VCORE_MD2SPM1_T           (DVFSRC_BASE + 0xA4)
+#define DVFSRC_VCORE_MD2SPM2_T           (DVFSRC_BASE + 0xA8)
+#define DVFSRC_MD_VSRAM_REMAP            (DVFSRC_BASE + 0xBC)
+#define DVFSRC_HALT_SW_CONTROL           (DVFSRC_BASE + 0xC0)
+#define DVFSRC_INT                       (DVFSRC_BASE + 0xC4)
+#define DVFSRC_INT_EN                    (DVFSRC_BASE + 0xC8)
+#define DVFSRC_INT_CLR                   (DVFSRC_BASE + 0xCC)
+#define DVFSRC_BW_MON_WINDOW             (DVFSRC_BASE + 0xD0)
+#define DVFSRC_BW_MON_THRES_1            (DVFSRC_BASE + 0xD4)
+#define DVFSRC_BW_MON_THRES_2            (DVFSRC_BASE + 0xD8)
+#define DVFSRC_MD_TURBO                  (DVFSRC_BASE + 0xDC)
+#define DVFSRC_PCIE_VCORE_REQ            (DVFSRC_BASE + 0xE0)
+#define DVFSRC_VCORE_USER_REQ            (DVFSRC_BASE + 0xE4)
+#define DVFSRC_DEBOUNCE_FOUR             (DVFSRC_BASE + 0xF0)
+#define DVFSRC_DEBOUNCE_RISE_FALL        (DVFSRC_BASE + 0xF4)
+#define DVFSRC_TIMEOUT_NEXTREQ           (DVFSRC_BASE + 0xF8)
+#define DVFSRC_LEVEL_LABEL_0_1           (DVFSRC_BASE + 0x100)
+#define DVFSRC_LEVEL_LABEL_2_3           (DVFSRC_BASE + 0x104)
+#define DVFSRC_LEVEL_LABEL_4_5           (DVFSRC_BASE + 0x108)
+#define DVFSRC_LEVEL_LABEL_6_7           (DVFSRC_BASE + 0x10C)
+#define DVFSRC_LEVEL_LABEL_8_9           (DVFSRC_BASE + 0x110)
+#define DVFSRC_LEVEL_LABEL_10_11         (DVFSRC_BASE + 0x114)
+#define DVFSRC_LEVEL_LABEL_12_13         (DVFSRC_BASE + 0x118)
+#define DVFSRC_LEVEL_LABEL_14_15         (DVFSRC_BASE + 0x11C)
+#define DVFSRC_MM_BW_0                   (DVFSRC_BASE + 0x200)
+#define DVFSRC_MM_BW_1                   (DVFSRC_BASE + 0x204)
+#define DVFSRC_MM_BW_2                   (DVFSRC_BASE + 0x208)
+#define DVFSRC_MM_BW_3                   (DVFSRC_BASE + 0x20C)
+#define DVFSRC_MM_BW_4                   (DVFSRC_BASE + 0x210)
+#define DVFSRC_MM_BW_5                   (DVFSRC_BASE + 0x214)
+#define DVFSRC_MM_BW_6                   (DVFSRC_BASE + 0x218)
+#define DVFSRC_MM_BW_7                   (DVFSRC_BASE + 0x21C)
+#define DVFSRC_MM_BW_8                   (DVFSRC_BASE + 0x220)
+#define DVFSRC_MM_BW_9                   (DVFSRC_BASE + 0x224)
+#define DVFSRC_MM_BW_10                  (DVFSRC_BASE + 0x228)
+#define DVFSRC_MM_BW_11                  (DVFSRC_BASE + 0x22C)
+#define DVFSRC_MM_BW_12                  (DVFSRC_BASE + 0x230)
+#define DVFSRC_MM_BW_13                  (DVFSRC_BASE + 0x234)
+#define DVFSRC_MM_BW_14                  (DVFSRC_BASE + 0x238)
+#define DVFSRC_MM_BW_15                  (DVFSRC_BASE + 0x23C)
+#define DVFSRC_MD_BW_0                   (DVFSRC_BASE + 0x240)
+#define DVFSRC_MD_BW_1                   (DVFSRC_BASE + 0x244)
+#define DVFSRC_MD_BW_2                   (DVFSRC_BASE + 0x248)
+#define DVFSRC_MD_BW_3                   (DVFSRC_BASE + 0x24C)
+#define DVFSRC_MD_BW_4                   (DVFSRC_BASE + 0x250)
+#define DVFSRC_MD_BW_5                   (DVFSRC_BASE + 0x254)
+#define DVFSRC_MD_BW_6                   (DVFSRC_BASE + 0x258)
+#define DVFSRC_MD_BW_7                   (DVFSRC_BASE + 0x25C)
+#define DVFSRC_SW_BW_0                   (DVFSRC_BASE + 0x260)
+#define DVFSRC_SW_BW_1                   (DVFSRC_BASE + 0x264)
+#define DVFSRC_SW_BW_2                   (DVFSRC_BASE + 0x268)
+#define DVFSRC_SW_BW_3                   (DVFSRC_BASE + 0x26C)
+#define DVFSRC_SW_BW_4                   (DVFSRC_BASE + 0x270)
+#define DVFSRC_SW_BW_5                   (DVFSRC_BASE + 0x274)
+#define DVFSRC_SW_BW_6                   (DVFSRC_BASE + 0x278)
+#define DVFSRC_QOS_EN                    (DVFSRC_BASE + 0x280)
+#define DVFSRC_MD_BW_URG                 (DVFSRC_BASE + 0x284)
+#define DVFSRC_ISP_HRT                   (DVFSRC_BASE + 0x290)
+#define DVFSRC_HRT_BW_BASE               (DVFSRC_BASE + 0x294)
+#define DVFSRC_SEC_SW_REQ                (DVFSRC_BASE + 0x304)
+#define DVFSRC_EMI_MON_DEBOUNCE_TIME     (DVFSRC_BASE + 0x308)
+#define DVFSRC_MD_LATENCY_IMPROVE        (DVFSRC_BASE + 0x30C)
+#define DVFSRC_BASIC_CONTROL_3           (DVFSRC_BASE + 0x310)
+#define DVFSRC_DEBOUNCE_TIME             (DVFSRC_BASE + 0x314)
+#define DVFSRC_LEVEL_MASK                (DVFSRC_BASE + 0x318)
+#define DVFSRC_DEFAULT_OPP               (DVFSRC_BASE + 0x31C)
+#define DVFSRC_95MD_SCEN_EMI0            (DVFSRC_BASE + 0x500)
+#define DVFSRC_95MD_SCEN_EMI1            (DVFSRC_BASE + 0x504)
+#define DVFSRC_95MD_SCEN_EMI2            (DVFSRC_BASE + 0x508)
+#define DVFSRC_95MD_SCEN_EMI3            (DVFSRC_BASE + 0x50C)
+#define DVFSRC_95MD_SCEN_EMI0_T          (DVFSRC_BASE + 0x510)
+#define DVFSRC_95MD_SCEN_EMI1_T          (DVFSRC_BASE + 0x514)
+#define DVFSRC_95MD_SCEN_EMI2_T          (DVFSRC_BASE + 0x518)
+#define DVFSRC_95MD_SCEN_EMI3_T          (DVFSRC_BASE + 0x51C)
+#define DVFSRC_95MD_SCEN_EMI4            (DVFSRC_BASE + 0x520)
+#define DVFSRC_95MD_SCEN_BW0             (DVFSRC_BASE + 0x524)
+#define DVFSRC_95MD_SCEN_BW1             (DVFSRC_BASE + 0x528)
+#define DVFSRC_95MD_SCEN_BW2             (DVFSRC_BASE + 0x52C)
+#define DVFSRC_95MD_SCEN_BW3             (DVFSRC_BASE + 0x530)
+#define DVFSRC_95MD_SCEN_BW0_T           (DVFSRC_BASE + 0x534)
+#define DVFSRC_95MD_SCEN_BW1_T           (DVFSRC_BASE + 0x538)
+#define DVFSRC_95MD_SCEN_BW2_T           (DVFSRC_BASE + 0x53C)
+#define DVFSRC_95MD_SCEN_BW3_T           (DVFSRC_BASE + 0x540)
+#define DVFSRC_95MD_SCEN_BW4             (DVFSRC_BASE + 0x544)
+#define DVFSRC_MD_LEVEL_SW_REG           (DVFSRC_BASE + 0x548)
+#define DVFSRC_RSRV_0                    (DVFSRC_BASE + 0x600)
+#define DVFSRC_RSRV_1                    (DVFSRC_BASE + 0x604)
+#define DVFSRC_RSRV_2                    (DVFSRC_BASE + 0x608)
+#define DVFSRC_RSRV_3                    (DVFSRC_BASE + 0x60C)
+#define DVFSRC_RSRV_4                    (DVFSRC_BASE + 0x610)
+#define DVFSRC_RSRV_5                    (DVFSRC_BASE + 0x614)
+#define DVFSRC_SPM_RESEND                (DVFSRC_BASE + 0x630)
+#define DVFSRC_DEBUG_STA_0               (DVFSRC_BASE + 0x700)
+#define DVFSRC_DEBUG_STA_1               (DVFSRC_BASE + 0x704)
+#define DVFSRC_DEBUG_STA_2               (DVFSRC_BASE + 0x708)
+#define DVFSRC_DEBUG_STA_3               (DVFSRC_BASE + 0x70C)
+#define DVFSRC_DEBUG_STA_4               (DVFSRC_BASE + 0x710)
+#define DVFSRC_DEBUG_STA_5               (DVFSRC_BASE + 0x714)
+#define DVFSRC_EMI_REQUEST7              (DVFSRC_BASE + 0x800)
+#define DVFSRC_EMI_HRT_1                 (DVFSRC_BASE + 0x804)
+#define DVFSRC_EMI_HRT2_1                (DVFSRC_BASE + 0x808)
+#define DVFSRC_EMI_HRT3_1                (DVFSRC_BASE + 0x80C)
+#define DVFSRC_EMI_QOS3                  (DVFSRC_BASE + 0x810)
+#define DVFSRC_EMI_QOS4                  (DVFSRC_BASE + 0x814)
+#define DVFSRC_DDR_REQUEST               (DVFSRC_BASE + 0xA00)
+#define DVFSRC_DDR_REQUEST2              (DVFSRC_BASE + 0xA04)
+#define DVFSRC_DDR_REQUEST3              (DVFSRC_BASE + 0xA08)
+#define DVFSRC_DDR_REQUEST4              (DVFSRC_BASE + 0xA0C)
+#define DVFSRC_DDR_REQUEST5              (DVFSRC_BASE + 0xA10)
+#define DVFSRC_DDR_REQUEST6              (DVFSRC_BASE + 0xA14)
+#define DVFSRC_DDR_REQUEST7              (DVFSRC_BASE + 0xA18)
+#define DVFSRC_DDR_HRT                   (DVFSRC_BASE + 0xA1C)
+#define DVFSRC_DDR_HRT2                  (DVFSRC_BASE + 0xA20)
+#define DVFSRC_DDR_HRT3                  (DVFSRC_BASE + 0xA24)
+#define DVFSRC_DDR_HRT_1                 (DVFSRC_BASE + 0xA28)
+#define DVFSRC_DDR_HRT2_1                (DVFSRC_BASE + 0xA2C)
+#define DVFSRC_DDR_HRT3_1                (DVFSRC_BASE + 0xA30)
+#define DVFSRC_DDR_QOS0                  (DVFSRC_BASE + 0xA34)
+#define DVFSRC_DDR_QOS1                  (DVFSRC_BASE + 0xA38)
+#define DVFSRC_DDR_QOS2                  (DVFSRC_BASE + 0xA3C)
+#define DVFSRC_DDR_QOS3                  (DVFSRC_BASE + 0xA40)
+#define DVFSRC_DDR_QOS4                  (DVFSRC_BASE + 0xA44)
+#define DVFSRC_DDR_MD2SPM0               (DVFSRC_BASE + 0xA48)
+#define DVFSRC_DDR_MD2SPM1               (DVFSRC_BASE + 0xA4C)
+#define DVFSRC_DDR_MD2SPM2               (DVFSRC_BASE + 0xA50)
+#define DVFSRC_DDR_MD2SPM0_T             (DVFSRC_BASE + 0xA54)
+#define DVFSRC_DDR_MD2SPM1_T             (DVFSRC_BASE + 0xA58)
+#define DVFSRC_DDR_MD2SPM2_T             (DVFSRC_BASE + 0xA5C)
+#define DVFSRC_HRT_REQ_UNIT              (DVFSRC_BASE + 0xA60)
+#define DVSFRC_HRT_REQ_MD_URG            (DVFSRC_BASE + 0xA64)
+#define DVFSRC_HRT_REQ_MD_BW_0           (DVFSRC_BASE + 0xA68)
+#define DVFSRC_HRT_REQ_MD_BW_1           (DVFSRC_BASE + 0xA6C)
+#define DVFSRC_HRT_REQ_MD_BW_2           (DVFSRC_BASE + 0xA70)
+#define DVFSRC_HRT_REQ_MD_BW_3           (DVFSRC_BASE + 0xA74)
+#define DVFSRC_HRT_REQ_MD_BW_4           (DVFSRC_BASE + 0xA78)
+#define DVFSRC_HRT_REQ_MD_BW_5           (DVFSRC_BASE + 0xA7C)
+#define DVFSRC_HRT_REQ_MD_BW_6           (DVFSRC_BASE + 0xA80)
+#define DVFSRC_HRT_REQ_MD_BW_7           (DVFSRC_BASE + 0xA84)
+#define DVFSRC_HRT1_REQ_MD_BW_0          (DVFSRC_BASE + 0xA88)
+#define DVFSRC_HRT1_REQ_MD_BW_1          (DVFSRC_BASE + 0xA8C)
+#define DVFSRC_HRT1_REQ_MD_BW_2          (DVFSRC_BASE + 0xA90)
+#define DVFSRC_HRT1_REQ_MD_BW_3          (DVFSRC_BASE + 0xA94)
+#define DVFSRC_HRT1_REQ_MD_BW_4          (DVFSRC_BASE + 0xA98)
+#define DVFSRC_HRT1_REQ_MD_BW_5          (DVFSRC_BASE + 0xA9C)
+#define DVFSRC_HRT1_REQ_MD_BW_6          (DVFSRC_BASE + 0xAA0)
+#define DVFSRC_HRT1_REQ_MD_BW_7          (DVFSRC_BASE + 0xAA4)
+#define DVFSRC_HRT_REQ_MD_BW_8           (DVFSRC_BASE + 0xAA8)
+#define DVFSRC_HRT_REQ_MD_BW_9           (DVFSRC_BASE + 0xAAC)
+#define DVFSRC_HRT_REQ_MD_BW_10          (DVFSRC_BASE + 0xAB0)
+#define DVFSRC_HRT1_REQ_MD_BW_8          (DVFSRC_BASE + 0xAB4)
+#define DVFSRC_HRT1_REQ_MD_BW_9          (DVFSRC_BASE + 0xAB8)
+#define DVFSRC_HRT1_REQ_MD_BW_10         (DVFSRC_BASE + 0xABC)
+#define DVFSRC_HRT_REQ_BW_SW_REG         (DVFSRC_BASE + 0xAC0)
+#define DVFSRC_HRT_REQUEST               (DVFSRC_BASE + 0xAC4)
+#define DVFSRC_HRT_HIGH_2                (DVFSRC_BASE + 0xAC8)
+#define DVFSRC_HRT_HIGH_1                (DVFSRC_BASE + 0xACC)
+#define DVFSRC_HRT_HIGH                  (DVFSRC_BASE + 0xAD0)
+#define DVFSRC_HRT_LOW_2                 (DVFSRC_BASE + 0xAD4)
+#define DVFSRC_HRT_LOW_1                 (DVFSRC_BASE + 0xAD8)
+#define DVFSRC_HRT_LOW                   (DVFSRC_BASE + 0xADC)
+#define DVFSRC_DDR_ADD_REQUEST           (DVFSRC_BASE + 0xAE0)
+#define DVFSRC_LAST                      (DVFSRC_BASE + 0xAE4)
+#define DVFSRC_LAST_L                    (DVFSRC_BASE + 0xAE8)
+#define DVFSRC_MD_SCENARIO               (DVFSRC_BASE + 0xAEC)
+#define DVFSRC_RECORD_0_0                (DVFSRC_BASE + 0xAF0)
+#define DVFSRC_RECORD_0_1                (DVFSRC_BASE + 0xAF4)
+#define DVFSRC_RECORD_0_2                (DVFSRC_BASE + 0xAF8)
+#define DVFSRC_RECORD_0_3                (DVFSRC_BASE + 0xAFC)
+#define DVFSRC_RECORD_0_4                (DVFSRC_BASE + 0xB00)
+#define DVFSRC_RECORD_0_5                (DVFSRC_BASE + 0xB04)
+#define DVFSRC_RECORD_0_6                (DVFSRC_BASE + 0xB08)
+#define DVFSRC_RECORD_0_7                (DVFSRC_BASE + 0xB0C)
+#define DVFSRC_RECORD_0_L_0              (DVFSRC_BASE + 0xBF0)
+#define DVFSRC_RECORD_0_L_1              (DVFSRC_BASE + 0xBF4)
+#define DVFSRC_RECORD_0_L_2              (DVFSRC_BASE + 0xBF8)
+#define DVFSRC_RECORD_0_L_3              (DVFSRC_BASE + 0xBFC)
+#define DVFSRC_RECORD_0_L_4              (DVFSRC_BASE + 0xC00)
+#define DVFSRC_RECORD_0_L_5              (DVFSRC_BASE + 0xC04)
+#define DVFSRC_RECORD_0_L_6              (DVFSRC_BASE + 0xC08)
+#define DVFSRC_RECORD_0_L_7              (DVFSRC_BASE + 0xC0C)
+#define DVFSRC_EMI_REQUEST8              (DVFSRC_BASE + 0xCF0)
+#define DVFSRC_DDR_REQUEST8              (DVFSRC_BASE + 0xCF4)
+#define DVFSRC_EMI_HRT_2                 (DVFSRC_BASE + 0xCF8)
+#define DVFSRC_EMI_HRT2_2                (DVFSRC_BASE + 0xCFC)
+#define DVFSRC_EMI_HRT3_2                (DVFSRC_BASE + 0xD00)
+#define DVFSRC_EMI_QOS5                  (DVFSRC_BASE + 0xD04)
+#define DVFSRC_EMI_QOS6                  (DVFSRC_BASE + 0xD08)
+#define DVFSRC_DDR_HRT_2                 (DVFSRC_BASE + 0xD0C)
+#define DVFSRC_DDR_HRT2_2                (DVFSRC_BASE + 0xD10)
+#define DVFSRC_DDR_HRT3_2                (DVFSRC_BASE + 0xD14)
+#define DVFSRC_DDR_QOS5                  (DVFSRC_BASE + 0xD18)
+#define DVFSRC_DDR_QOS6                  (DVFSRC_BASE + 0xD1C)
+#define DVFSRC_VCORE_REQUEST5            (DVFSRC_BASE + 0xD20)
+#define DVFSRC_VCORE_HRT_1               (DVFSRC_BASE + 0xD24)
+#define DVFSRC_VCORE_HRT2_1              (DVFSRC_BASE + 0xD28)
+#define DVFSRC_VCORE_HRT3_1              (DVFSRC_BASE + 0xD2C)
+#define DVFSRC_VCORE_QOS3                (DVFSRC_BASE + 0xD30)
+#define DVFSRC_VCORE_QOS4                (DVFSRC_BASE + 0xD34)
+#define DVFSRC_HRT_HIGH_3                (DVFSRC_BASE + 0xD38)
+#define DVFSRC_HRT_LOW_3                 (DVFSRC_BASE + 0xD3C)
+#define DVFSRC_BASIC_CONTROL_2           (DVFSRC_BASE + 0xD40)
+#define DVFSRC_CURRENT_LEVEL             (DVFSRC_BASE + 0xD44)
+#define DVFSRC_TARGET_LEVEL              (DVFSRC_BASE + 0xD48)
+#define DVFSRC_LEVEL_LABEL_16_17         (DVFSRC_BASE + 0xD4C)
+#define DVFSRC_LEVEL_LABEL_18_19         (DVFSRC_BASE + 0xD50)
+#define DVFSRC_LEVEL_LABEL_20_21         (DVFSRC_BASE + 0xD54)
+#define DVFSRC_LEVEL_LABEL_22_23         (DVFSRC_BASE + 0xD58)
+#define DVFSRC_LEVEL_LABEL_24_25         (DVFSRC_BASE + 0xD5C)
+#define DVFSRC_LEVEL_LABEL_26_27         (DVFSRC_BASE + 0xD60)
+#define DVFSRC_LEVEL_LABEL_28_29         (DVFSRC_BASE + 0xD64)
+#define DVFSRC_LEVEL_LABEL_30_31         (DVFSRC_BASE + 0xD68)
+#define DVFSRC_CURRENT_FORCE             (DVFSRC_BASE + 0xD6C)
+#define DVFSRC_TARGET_FORCE              (DVFSRC_BASE + 0xD70)
+#define DVFSRC_EMI_ADD_REQUEST           (DVFSRC_BASE + 0xD74)
+
+#endif /* __MT_SPM_VCOREFS__H__ */
diff --git a/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_notifier.h b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_notifier.h
new file mode 100644
index 0000000..ee3738d
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_notifier.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SSPM_NOTIFIER_H
+#define MT_SPM_SSPM_NOTIFIER_H
+
+enum MT_SPM_SSPM_NOTIFY_ID {
+	MT_SPM_NOTIFY_LP_ENTER,
+	MT_SPM_NOTIFY_LP_LEAVE,
+};
+
+int mt_spm_sspm_notify(int type, unsigned int lp_mode);
+
+static inline int mt_spm_sspm_notify_u32(int type, unsigned int lp_mode)
+{
+	return mt_spm_sspm_notify(type, lp_mode);
+}
+#endif /* MT_SPM_SSPM_NOTIFIER_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_intc.h b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_intc.h
new file mode 100644
index 0000000..6847e77
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_intc.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MT_SPM_SSPM_INTC_H
+#define MT_SPM_SSPM_INTC_H
+
+#include <mt_spm_reg.h>
+
+#define MT_SPM_SSPM_INTC_SEL_0		0x10
+#define MT_SPM_SSPM_INTC_SEL_1		0x20
+#define MT_SPM_SSPM_INTC_SEL_2		0x40
+#define MT_SPM_SSPM_INTC_SEL_3		0x80
+
+#define MT_SPM_SSPM_INTC_TRIGGER(id, sg) \
+	(((0x10 << id) | (sg << id)) & 0xff)
+
+#define MT_SPM_SSPM_INTC0_HIGH	MT_SPM_SSPM_INTC_TRIGGER(0, 1)
+#define MT_SPM_SSPM_INTC0_LOW	MT_SPM_SSPM_INTC_TRIGGER(0, 0)
+#define MT_SPM_SSPM_INTC1_HIGH	MT_SPM_SSPM_INTC_TRIGGER(1, 1)
+#define MT_SPM_SSPM_INTC1_LOW	MT_SPM_SSPM_INTC_TRIGGER(1, 0)
+#define MT_SPM_SSPM_INTC2_HIGH	MT_SPM_SSPM_INTC_TRIGGER(2, 1)
+#define MT_SPM_SSPM_INTC2_LOW	MT_SPM_SSPM_INTC_TRIGGER(2, 0)
+#define MT_SPM_SSPM_INTC3_HIGH	MT_SPM_SSPM_INTC_TRIGGER(3, 1)
+#define MT_SPM_SSPM_INTC3_LOW	MT_SPM_SSPM_INTC_TRIGGER(3, 0)
+
+#define DO_SPM_SSPM_LP_SUSPEND()	\
+	mmio_write_32(SPM_MD32_IRQ, MT_SPM_SSPM_INTC0_HIGH)
+#define DO_SPM_SSPM_LP_RESUME()		\
+	mmio_write_32(SPM_MD32_IRQ, MT_SPM_SSPM_INTC0_LOW)
+#endif /* MT_SPM_SSPM_INTC_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_notifier.c b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_notifier.c
new file mode 100644
index 0000000..a755a38
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/notifier/mt_spm_sspm_notifier.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <lib/mmio.h>
+
+#include <mt_spm_notifier.h>
+#include <mt_spm_sspm_intc.h>
+
+#define MT_SPM_SSPM_MBOX_OFF(x)		(SSPM_MBOX_BASE + x)
+#define MT_SPM_MBOX(slot)		MT_SPM_SSPM_MBOX_OFF((slot << 2UL))
+
+#define SSPM_MBOX_SPM_LP_LOOKUP1	MT_SPM_MBOX(0)
+#define SSPM_MBOX_SPM_LP_LOOKUP2	MT_SPM_MBOX(1)
+#define SSPM_MBOX_SPM_LP1		MT_SPM_MBOX(2)
+#define SSPM_MBOX_SPM_LP2		MT_SPM_MBOX(3)
+
+int mt_spm_sspm_notify(int type, unsigned int lp_mode)
+{
+	switch (type) {
+	case MT_SPM_NOTIFY_LP_ENTER:
+		mmio_write_32(SSPM_MBOX_SPM_LP1, lp_mode);
+		DO_SPM_SSPM_LP_SUSPEND();
+		break;
+	case MT_SPM_NOTIFY_LP_LEAVE:
+		mmio_write_32(SSPM_MBOX_SPM_LP1, lp_mode);
+		DO_SPM_SSPM_LP_RESUME();
+		break;
+	default:
+		break;
+	}
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/drivers/spm/pcm_def.h b/plat/mediatek/mt8195/drivers/spm/pcm_def.h
new file mode 100644
index 0000000..fa77b95
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/pcm_def.h
@@ -0,0 +1,179 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PCM_DEF_H
+#define PCM_DEF_H
+
+/*
+ * Auto generated by DE, please DO NOT modify this file directly.
+ */
+
+/* --- R0 Define --- */
+#define R0_SC_26M_CK_OFF                      (1U << 0)
+#define R0_SC_TX_TRACK_RETRY_EN               (1U << 1)
+#define R0_SC_MEM_CK_OFF                      (1U << 2)
+#define R0_SC_AXI_CK_OFF                      (1U << 3)
+#define R0_SC_DR_SRAM_LOAD                    (1U << 4)
+#define R0_SC_MD26M_CK_OFF                    (1U << 5)
+#define R0_SC_DPY_MODE_SW                     (1U << 6)
+#define R0_SC_DMSUS_OFF                       (1U << 7)
+#define R0_SC_DPY_2ND_DLL_EN                  (1U << 8)
+#define R0_SC_DR_SRAM_RESTORE                 (1U << 9)
+#define R0_SC_MPLLOUT_OFF                     (1U << 10)
+#define R0_SC_TX_TRACKING_DIS                 (1U << 11)
+#define R0_SC_DPY_DLL_EN                      (1U << 12)
+#define R0_SC_DPY_DLL_CK_EN                   (1U << 13)
+#define R0_SC_DPY_VREF_EN                     (1U << 14)
+#define R0_SC_PHYPLL_EN                       (1U << 15)
+#define R0_SC_DDRPHY_FB_CK_EN                 (1U << 16)
+#define R0_SC_DPY_BCLK_ENABLE                 (1U << 17)
+#define R0_SC_MPLL_OFF                        (1U << 18)
+#define R0_SC_SHU_RESTORE                     (1U << 19)
+#define R0_SC_CKSQ0_OFF                       (1U << 20)
+#define R0_SC_DR_SHU_LEVEL_SRAM_LATCH         (1U << 21)
+#define R0_SC_DR_SHU_EN                       (1U << 22)
+#define R0_SC_DPHY_PRECAL_UP                  (1U << 23)
+#define R0_SC_MPLL_S_OFF                      (1U << 24)
+#define R0_SC_DPHY_RXDLY_TRACKING_EN          (1U << 25)
+#define R0_SC_PHYPLL_SHU_EN                   (1U << 26)
+#define R0_SC_PHYPLL2_SHU_EN                  (1U << 27)
+#define R0_SC_PHYPLL_MODE_SW                  (1U << 28)
+#define R0_SC_PHYPLL2_MODE_SW                 (1U << 29)
+#define R0_SC_DR_SHU_LEVEL0                   (1U << 30)
+#define R0_SC_DR_SHU_LEVEL1                   (1U << 31)
+/* --- R7 Define --- */
+#define R7_PWRAP_SLEEP_REQ                    (1U << 0)
+#define R7_EMI_CLK_OFF_REQ                    (1U << 1)
+#define R7_PCM_BUS_PROTECT_REQ                (1U << 2)
+#define R7_SPM_CK_UPDATE                      (1U << 3)
+#define R7_SPM_CK_SEL0                        (1U << 4)
+#define R7_SPM_CK_SEL1                        (1U << 5)
+#define R7_SPM_LEAVE_DEEPIDLE_REQ             (1U << 6)
+#define R7_SC_FHC_PAUSE_MPLL                  (1U << 7)
+#define R7_SC_26M_CK_SEL                      (1U << 8)
+#define R7_PCM_TIMER_SET                      (1U << 9)
+#define R7_PCM_TIMER_CLR                      (1U << 10)
+#define R7_SPM_LEAVE_SUSPEND_REQ              (1U << 11)
+#define R7_CSYSPWRUPACK                       (1U << 12)
+#define R7_PCM_IM_SLP_EN                      (1U << 13)
+#define R7_SRCCLKENO0                         (1U << 14)
+#define R7_FORCE_DDR_EN_WAKE                  (1U << 15)
+#define R7_SPM_APSRC_INTERNAL_ACK             (1U << 16)
+#define R7_CPU_SYS_TIMER_CLK_SEL              (1U << 17)
+#define R7_SC_AXI_DCM_DIS                     (1U << 18)
+#define R7_SC_FHC_PAUSE_MEM                   (1U << 19)
+#define R7_SC_FHC_PAUSE_MAIN                  (1U << 20)
+#define R7_SRCCLKENO1                         (1U << 21)
+#define R7_PCM_WDT_KICK_P                     (1U << 22)
+#define R7_SPM2EMI_S1_MODE_ASYNC              (1U << 23)
+#define R7_SC_DDR_PST_REQ_PCM                 (1U << 24)
+#define R7_SC_DDR_PST_ABORT_REQ_PCM           (1U << 25)
+#define R7_PMIC_IRQ_REQ_EN                    (1U << 26)
+#define R7_FORCE_F26M_WAKE                    (1U << 27)
+#define R7_FORCE_APSRC_WAKE                   (1U << 28)
+#define R7_FORCE_INFRA_WAKE                   (1U << 29)
+#define R7_FORCE_VRF18_WAKE                   (1U << 30)
+#define R7_SPM_DDR_EN_INTERNAL_ACK            (1U << 31)
+/* --- R12 Define --- */
+#define R12_PCM_TIMER                         (1U << 0)
+#define R12_TWAM_IRQ_B                        (1U << 1)
+#define R12_KP_IRQ_B                          (1U << 2)
+#define R12_APWDT_EVENT_B                     (1U << 3)
+#define R12_APXGPT1_EVENT_B                   (1U << 4)
+#define R12_CONN2AP_SPM_WAKEUP_B              (1U << 5)
+#define R12_EINT_EVENT_B                      (1U << 6)
+#define R12_CONN_WDT_IRQ_B                    (1U << 7)
+#define R12_CCIF0_EVENT_B                     (1U << 8)
+#define R12_LOWBATTERY_IRQ_B                  (1U << 9)
+#define R12_SSPM2SPM_WAKEUP_B                 (1U << 10)
+#define R12_SCP2SPM_WAKEUP_B                  (1U << 11)
+#define R12_ADSP2SPM_WAKEUP_B                 (1U << 12)
+#define R12_PCM_WDT_WAKEUP_B                  (1U << 13)
+#define R12_USBX_CDSC_B                       (1U << 14)
+#define R12_USBX_POWERDWN_B                   (1U << 15)
+#define R12_SYS_TIMER_EVENT_B                 (1U << 16)
+#define R12_EINT_EVENT_SECURE_B               (1U << 17)
+#define R12_CCIF1_EVENT_B                     (1U << 18)
+#define R12_UART0_IRQ_B                       (1U << 19)
+#define R12_AFE_IRQ_MCU_B                     (1U << 20)
+#define R12_THERM_CTRL_EVENT_B                (1U << 21)
+#define R12_SYS_CIRQ_IRQ_B                    (1U << 22)
+#define R12_MD2AP_PEER_EVENT_B                (1U << 23)
+#define R12_CSYSPWREQ_B                       (1U << 24)
+#define R12_MD1_WDT_B                         (1U << 25)
+#define R12_CLDMA_EVENT_B                     (1U << 26)
+#define R12_SEJ_EVENT_B                       (1U << 27)
+#define R12_REG_CPU_WAKEUP                    (1U << 28)
+#define R12_APUSYS_WAKE_HOST_B                (1U << 29)
+#define R12_NOT_USED1                         (1U << 30)
+#define R12_NOT_USED2                         (1U << 31)
+/* --- R12ext Define --- */
+#define R12EXT_26M_WAKE                       (1U << 0)
+#define R12EXT_26M_SLEEP                      (1U << 1)
+#define R12EXT_INFRA_WAKE                     (1U << 2)
+#define R12EXT_INFRA_SLEEP                    (1U << 3)
+#define R12EXT_APSRC_WAKE                     (1U << 4)
+#define R12EXT_APSRC_SLEEP                    (1U << 5)
+#define R12EXT_VRF18_WAKE                     (1U << 6)
+#define R12EXT_VRF18_SLEEP                    (1U << 7)
+#define R12EXT_DVFS_WAKE                      (1U << 8)
+#define R12EXT_DDREN_WAKE                     (1U << 9)
+#define R12EXT_DDREN_SLEEP                    (1U << 10)
+#define R12EXT_MCU_PM_WFI                     (1U << 11)
+#define R12EXT_SSPM_IDLE                      (1U << 12)
+#define R12EXT_CONN_SRCCLKENB                 (1U << 13)
+#define R12EXT_DRAMC_SSPM_WFI_MERGE           (1U << 14)
+#define R12EXT_SW_MAILBOX_WAKE                (1U << 15)
+#define R12EXT_SSPM_MAILBOX_WAKE              (1U << 16)
+#define R12EXT_ADSP_MAILBOX_WAKE              (1U << 17)
+#define R12EXT_SCP_MAILBOX_WAKE               (1U << 18)
+#define R12EXT_SPM_LEAVE_SUSPEND_ACK          (1U << 19)
+#define R12EXT_SPM_LEAVE_DEEPIDLE_ACK         (1U << 20)
+#define R12EXT_VS1_TRIGGER                    (1U << 21)
+#define R12EXT_VS2_TRIGGER                    (1U << 22)
+#define R12EXT_COROSS_REQ_APU                 (1U << 23)
+#define R12EXT_CROSS_REQ_L3                   (1U << 24)
+#define R12EXT_DDR_PST_ACK                    (1U << 25)
+#define R12EXT_BIT26                          (1U << 26)
+#define R12EXT_BIT27                          (1U << 27)
+#define R12EXT_BIT28                          (1U << 28)
+#define R12EXT_BIT29                          (1U << 29)
+#define R12EXT_BIT30                          (1U << 30)
+#define R12EXT_BIT31                          (1U << 31)
+/* --- R13 Define --- */
+#define R13_SRCCLKENI0                        (1U << 0)
+#define R13_SRCCLKENI1                        (1U << 1)
+#define R13_MD_SRCCLKENA_0                    (1U << 2)
+#define R13_MD_APSRC_REQ_0                    (1U << 3)
+#define R13_CONN_DDR_EN                       (1U << 4)
+#define R13_MD_SRCCLKENA_1                    (1U << 5)
+#define R13_SSPM_SRCCLKENA                    (1U << 6)
+#define R13_SSPM_APSRC_REQ                    (1U << 7)
+#define R13_MD1_STATE                         (1U << 8)
+#define R13_BIT9                              (1U << 9)
+#define R13_MM_STATE                          (1U << 10)
+#define R13_SSPM_STATE                        (1U << 11)
+#define R13_MD_DDR_EN_0                       (1U << 12)
+#define R13_CONN_STATE                        (1U << 13)
+#define R13_CONN_SRCCLKENA                    (1U << 14)
+#define R13_CONN_APSRC_REQ                    (1U << 15)
+#define R13_SC_DDR_PST_ACK_ALL                (1U << 16)
+#define R13_SC_DDR_PST_ABORT_ACK_ALL          (1U << 17)
+#define R13_SCP_STATE                         (1U << 18)
+#define R13_CSYSPWRUPREQ                      (1U << 19)
+#define R13_PWRAP_SLEEP_ACK                   (1U << 20)
+#define R13_SC_EMI_CLK_OFF_ACK_ALL            (1U << 21)
+#define R13_AUDIO_DSP_STATE                   (1U << 22)
+#define R13_SC_DMDRAMCSHU_ACK_ALL             (1U << 23)
+#define R13_CONN_SRCCLKENB                    (1U << 24)
+#define R13_SC_DR_SRAM_LOAD_ACK_ALL           (1U << 25)
+#define R13_SUBSYS_IDLE_SIGNALS0              (1U << 26)
+#define R13_DVFS_STATE                        (1U << 27)
+#define R13_SC_DR_SRAM_PLL_LOAD_ACK_ALL       (1U << 28)
+#define R13_SC_DR_SRAM_RESTORE_ACK_ALL        (1U << 29)
+#define R13_MD_VRF18_REQ_0                    (1U << 30)
+#define R13_DDR_EN_STATE                      (1U << 31)
+#endif /* PCM_DEF_H */
diff --git a/plat/mediatek/mt8195/drivers/spm/sleep_def.h b/plat/mediatek/mt8195/drivers/spm/sleep_def.h
new file mode 100644
index 0000000..2639b7e
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spm/sleep_def.h
@@ -0,0 +1,151 @@
+/*
+ * Copyright	(c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SLEEP_DEF_H
+#define SLEEP_DEF_H
+
+/*
+ * Auto generated by DE, please DO NOT modify this file directly.
+ */
+
+/* --- SPM Flag Define --- */
+#define SPM_FLAG_DISABLE_CPU_PDN			(1U << 0)
+#define SPM_FLAG_DISABLE_INFRA_PDN			(1U << 1)
+#define SPM_FLAG_DISABLE_DDRPHY_PDN			(1U << 2)
+#define SPM_FLAG_DISABLE_VCORE_DVS			(1U << 3)
+#define SPM_FLAG_DISABLE_VCORE_DFS			(1U << 4)
+#define SPM_FLAG_DISABLE_COMMON_SCENARIO		(1U << 5)
+#define SPM_FLAG_DISABLE_BUS_CLK_OFF			(1U << 6)
+#define SPM_FLAG_DISABLE_ARMPLL_OFF			(1U << 7)
+#define SPM_FLAG_KEEP_CSYSPWRACK_HIGH			(1U << 8)
+#define SPM_FLAG_ENABLE_LVTS_WORKAROUND			(1U << 9)
+#define SPM_FLAG_RUN_COMMON_SCENARIO			(1U << 10)
+#define SPM_FLAG_RESERVED_BIT11				(1U << 11)
+#define SPM_FLAG_ENABLE_SPM_DBG_WDT_DUMP		(1U << 12)
+#define SPM_FLAG_USE_SRCCLKENO2				(1U << 13)
+#define SPM_FLAG_ENABLE_6315_CTRL			(1U << 14)
+#define SPM_FLAG_ENABLE_TIA_WORKAROUND			(1U << 15)
+#define SPM_FLAG_DISABLE_SYSRAM_SLEEP			(1U << 16)
+#define SPM_FLAG_DISABLE_SSPM_SRAM_SLEEP		(1U << 17)
+#define SPM_FLAG_DISABLE_MCUPM_SRAM_SLEEP		(1U << 18)
+#define SPM_FLAG_DISABLE_DRAMC_ISSUE_CMD		(1U << 19)
+#define SPM_FLAG_ENABLE_VOLTAGE_BIN			(1U << 20)
+#define SPM_FLAG_RESERVED_BIT21				(1U << 21)
+#define SPM_FLAG_DISABLE_DRAMC_MCU_SRAM_SLEEP		(1U << 22)
+#define SPM_FLAG_DISABLE_DRAMC_MD32_BACKUP		(1U << 23)
+#define SPM_FLAG_RESERVED_BIT24				(1U << 24)
+#define SPM_FLAG_RESERVED_BIT25				(1U << 25)
+#define SPM_FLAG_RESERVED_BIT26				(1U << 26)
+#define SPM_FLAG_VTCXO_STATE				(1U << 27)
+#define SPM_FLAG_INFRA_STATE				(1U << 28)
+#define SPM_FLAG_APSRC_STATE				(1U << 29)
+#define SPM_FLAG_VRF18_STATE				(1U << 30)
+#define SPM_FLAG_DDREN_STATE				(1U << 31)
+/* --- SPM Flag1 Define --- */
+#define SPM_FLAG1_DISABLE_AXI_BUS_TO_26M		(1U << 0)
+#define SPM_FLAG1_DISABLE_SYSPLL_OFF			(1U << 1)
+#define SPM_FLAG1_DISABLE_PWRAP_CLK_SWITCH		(1U << 2)
+#define SPM_FLAG1_DISABLE_ULPOSC_OFF			(1U << 3)
+#define SPM_FLAG1_FW_SET_ULPOSC_ON			(1U << 4)
+#define SPM_FLAG1_RESERVED_BIT5				(1U << 5)
+#define SPM_FLAG1_ENABLE_REKICK				(1U << 6)
+#define SPM_FLAG1_RESERVED_BIT7				(1U << 7)
+#define SPM_FLAG1_RESERVED_BIT8				(1U << 8)
+#define SPM_FLAG1_RESERVED_BIT9				(1U << 9)
+#define SPM_FLAG1_DISABLE_SRCLKEN_LOW			(1U << 10)
+#define SPM_FLAG1_DISABLE_SCP_CLK_SWITCH		(1U << 11)
+#define SPM_FLAG1_RESERVED_BIT12			(1U << 12)
+#define SPM_FLAG1_RESERVED_BIT13			(1U << 13)
+#define SPM_FLAG1_RESERVED_BIT14			(1U << 14)
+#define SPM_FLAG1_RESERVED_BIT15			(1U << 15)
+#define SPM_FLAG1_RESERVED_BIT16			(1U << 16)
+#define SPM_FLAG1_RESERVED_BIT17			(1U << 17)
+#define SPM_FLAG1_RESERVED_BIT18			(1U << 18)
+#define SPM_FLAG1_RESERVED_BIT19			(1U << 19)
+#define SPM_FLAG1_DISABLE_DEVAPC_SRAM_SLEEP		(1U << 20)
+#define SPM_FLAG1_RESERVED_BIT21			(1U << 21)
+#define SPM_FLAG1_ENABLE_VS1_VOTER			(1U << 22)
+#define SPM_FLAG1_ENABLE_VS2_VOTER			(1U << 23)
+#define SPM_FLAG1_DISABLE_SCP_VREQ_MASK_CONTROL		(1U << 24)
+#define SPM_FLAG1_RESERVED_BIT25			(1U << 25)
+#define SPM_FLAG1_RESERVED_BIT26			(1U << 26)
+#define SPM_FLAG1_RESERVED_BIT27			(1U << 27)
+#define SPM_FLAG1_RESERVED_BIT28			(1U << 28)
+#define SPM_FLAG1_RESERVED_BIT29			(1U << 29)
+#define SPM_FLAG1_RESERVED_BIT30			(1U << 30)
+#define SPM_FLAG1_RESERVED_BIT31			(1U << 31)
+/* --- SPM DEBUG Define --- */
+#define SPM_DBG_DEBUG_IDX_26M_WAKE			(1U << 0)
+#define SPM_DBG_DEBUG_IDX_26M_SLEEP			(1U << 1)
+#define SPM_DBG_DEBUG_IDX_INFRA_WAKE			(1U << 2)
+#define SPM_DBG_DEBUG_IDX_INFRA_SLEEP			(1U << 3)
+#define SPM_DBG_DEBUG_IDX_APSRC_WAKE			(1U << 4)
+#define SPM_DBG_DEBUG_IDX_APSRC_SLEEP			(1U << 5)
+#define SPM_DBG_DEBUG_IDX_VRF18_WAKE			(1U << 6)
+#define SPM_DBG_DEBUG_IDX_VRF18_SLEEP			(1U << 7)
+#define SPM_DBG_DEBUG_IDX_DDREN_WAKE			(1U << 8)
+#define SPM_DBG_DEBUG_IDX_DDREN_SLEEP			(1U << 9)
+#define SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_APSRC	(1U << 10)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_STATE		(1U << 11)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_STATE		(1U << 12)
+#define SPM_DBG_DEBUG_IDX_DRAM_SREF_ABORT_IN_DDREN	(1U << 13)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_STATE		(1U << 14)
+#define SPM_DBG_DEBUG_IDX_SYSRAM_SLP			(1U << 15)
+#define SPM_DBG_DEBUG_IDX_SYSRAM_ON			(1U << 16)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_SLP		(1U << 17)
+#define SPM_DBG_DEBUG_IDX_MCUPM_SRAM_ON			(1U << 18)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_SLP			(1U << 19)
+#define SPM_DBG_DEBUG_IDX_SSPM_SRAM_ON			(1U << 20)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_SLP		(1U << 21)
+#define SPM_DBG_DEBUG_IDX_DRAMC_MCU_SRAM_ON		(1U << 22)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P575V		(1U << 23)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P600V		(1U << 24)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P650V		(1U << 25)
+#define SPM_DBG_DEBUG_IDX_SCP_VCORE_0P725V		(1U << 26)
+#define SPM_DBG_DEBUG_IDX_SPM_GO_WAKEUP_NOW		(1U << 27)
+#define SPM_DBG_DEBUG_IDX_VTCXO_STATE			(1U << 28)
+#define SPM_DBG_DEBUG_IDX_INFRA_STATE			(1U << 29)
+#define SPM_DBG_DEBUG_IDX_VRR18_STATE			(1U << 30)
+#define SPM_DBG_DEBUG_IDX_APSRC_STATE			(1U << 31)
+/* --- SPM DEBUG1 Define --- */
+#define SPM_DBG1_DEBUG_IDX_CURRENT_IS_LP		(1U << 0)
+#define SPM_DBG1_DEBUG_IDX_VCORE_DVFS_START		(1U << 1)
+#define SPM_DBG1_DEBUG_IDX_SYSPLL_OFF			(1U << 2)
+#define SPM_DBG1_DEBUG_IDX_SYSPLL_ON			(1U << 3)
+#define SPM_DBG1_DEBUG_IDX_CURRENT_IS_VCORE_DVFS	(1U << 4)
+#define SPM_DBG1_DEBUG_IDX_INFRA_MTCMOS_OFF		(1U << 5)
+#define SPM_DBG1_DEBUG_IDX_INFRA_MTCMOS_ON		(1U << 6)
+#define SPM_DBG1_DEBUG_IDX_VRCXO_SLEEP_ABORT		(1U << 7)
+#define SPM_DBG1_RESERVED_BIT8				(1U << 8)
+#define SPM_DBG1_DEBUG_IDX_INFRA_SUB_MTCMOS_OFF		(1U << 9)
+#define SPM_DBG1_DEBUG_IDX_INFRA_SUB_MTCMOS_ON		(1U << 10)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_CLK_TO_ULPOSC		(1U << 11)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_CLK_TO_26M		(1U << 12)
+#define SPM_DBG1_DEBUG_IDX_SCP_CLK_TO_32K		(1U << 13)
+#define SPM_DBG1_DEBUG_IDX_SCP_CLK_TO_26M		(1U << 14)
+#define SPM_DBG1_DEBUG_IDX_BUS_CLK_OFF			(1U << 15)
+#define SPM_DBG1_DEBUG_IDX_BUS_CLK_ON			(1U << 16)
+#define SPM_DBG1_DEBUG_IDX_SRCLKEN2_LOW			(1U << 17)
+#define SPM_DBG1_DEBUG_IDX_SRCLKEN2_HIGH		(1U << 18)
+#define SPM_DBG1_RESERVED_BIT19				(1U << 19)
+#define SPM_DBG1_DEBUG_IDX_ULPOSC_IS_OFF_BUT_SHOULD_ON	(1U << 20)
+#define SPM_DBG1_DEBUG_IDX_6315_LOW			(1U << 21)
+#define SPM_DBG1_DEBUG_IDX_6315_HIGH			(1U << 22)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_LOW_ABORT	(1U << 23)
+#define SPM_DBG1_DEBUG_IDX_PWRAP_SLEEP_ACK_HIGH_ABORT	(1U << 24)
+#define SPM_DBG1_DEBUG_IDX_EMI_SLP_IDLE_ABORT		(1U << 25)
+#define SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_LOW_ABORT	(1U << 26)
+#define SPM_DBG1_DEBUG_IDX_SCP_SLP_ACK_HIGH_ABORT	(1U << 27)
+#define SPM_DBG1_DEBUG_IDX_SPM_DVFS_CMD_RDY_ABORT	(1U << 28)
+#define SPM_DBG1_RESERVED_BIT29				(1U << 29)
+#define SPM_DBG1_RESERVED_BIT30				(1U << 30)
+#define SPM_DBG1_RESERVED_BIT31				(1U << 31)
+
+ /* Macro and Inline */
+#define is_cpu_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_CPU_PDN) == 0U)
+#define is_infra_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_INFRA_PDN) == 0U)
+#define is_ddrphy_pdn(flags)	(((flags) & SPM_FLAG_DISABLE_DDRPHY_PDN) == 0U)
+#endif /* SLEEP_DEF_H */
diff --git a/plat/mediatek/mt8195/drivers/spmc/mtspmc.c b/plat/mediatek/mt8195/drivers/spmc/mtspmc.c
new file mode 100644
index 0000000..9b332a0
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spmc/mtspmc.c
@@ -0,0 +1,166 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <drivers/delay_timer.h>
+#include <lib/mmio.h>
+
+#include <mcucfg.h>
+#include <mtspmc.h>
+#include <mtspmc_private.h>
+
+
+void mcucfg_disable_gic_wakeup(unsigned int cluster, unsigned int cpu)
+{
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(cpu));
+}
+
+void mcucfg_enable_gic_wakeup(unsigned int cluster, unsigned int cpu)
+{
+	mmio_clrbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, GIC_WAKEUP_IGNORE(cpu));
+}
+
+void mcucfg_set_bootaddr(unsigned int cluster, unsigned int cpu, uintptr_t bootaddr)
+{
+	assert(cluster == 0U);
+
+	mmio_write_32(per_cpu(cluster, cpu, MCUCFG_BOOTADDR), bootaddr);
+}
+
+uintptr_t mcucfg_get_bootaddr(unsigned int cluster, unsigned int cpu)
+{
+	assert(cluster == 0U);
+
+	return (uintptr_t)mmio_read_32(per_cpu(cluster, cpu, MCUCFG_BOOTADDR));
+}
+
+void mcucfg_init_archstate(unsigned int cluster, unsigned int cpu, bool arm64)
+{
+	uint32_t reg;
+
+	assert(cluster == 0U);
+
+	reg = per_cluster(cluster, MCUCFG_INITARCH);
+
+	if (arm64) {
+		mmio_setbits_32(reg, MCUCFG_INITARCH_CPU_BIT(cpu));
+	} else {
+		mmio_clrbits_32(reg, MCUCFG_INITARCH_CPU_BIT(cpu));
+	}
+}
+
+/**
+ * Return subsystem's power state.
+ *
+ * @mask: mask to MCUCFG_CPC_SPMC_PWR_STATUS to query the power state
+ *        of one subsystem.
+ * RETURNS:
+ * 0 (the subsys was powered off)
+ * 1 (the subsys was powered on)
+ */
+bool spm_get_powerstate(uint32_t mask)
+{
+	return (mmio_read_32(MCUCFG_CPC_SPMC_PWR_STATUS) & mask) != 0U;
+}
+
+bool spm_get_cluster_powerstate(unsigned int cluster)
+{
+	assert(cluster == 0U);
+
+	return spm_get_powerstate(BIT(14));
+}
+
+bool spm_get_cpu_powerstate(unsigned int cluster, unsigned int cpu)
+{
+	uint32_t mask = BIT(cpu);
+
+	assert(cluster == 0U);
+
+	return spm_get_powerstate(mask);
+}
+
+int spmc_init(void)
+{
+	INFO("SPM: enable CPC mode\n");
+
+	mmio_write_32(SPM_POWERON_CONFIG_EN, PROJECT_CODE | BCLK_CG_EN);
+
+	mmio_setbits_32(per_cpu(0, 1, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 2, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 3, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 4, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 5, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 6, SPM_CPU_PWR), PWR_RST_B);
+	mmio_setbits_32(per_cpu(0, 7, SPM_CPU_PWR), PWR_RST_B);
+
+	mmio_clrbits_32(SPM_MCUSYS_PWR_CON, RESETPWRON_CONFIG);
+	mmio_clrbits_32(SPM_MP0_CPUTOP_PWR_CON, RESETPWRON_CONFIG);
+	mmio_clrbits_32(per_cpu(0, 0, SPM_CPU_PWR), RESETPWRON_CONFIG);
+
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, CPC_CTRL_ENABLE);
+	mmio_setbits_32(MCUCFG_CPC_FLOW_CTRL_CFG, SSPM_CORE_PWR_ON_EN);
+
+	return 0;
+}
+
+/**
+ * Power on a core with specified cluster and core index
+ *
+ * @cluster: the cluster ID of the CPU which to be powered on
+ * @cpu: the CPU ID of the CPU which to be powered on
+ */
+void spm_poweron_cpu(unsigned int cluster, unsigned int cpu)
+{
+	uintptr_t cpu_pwr_con = per_cpu(cluster, cpu, SPM_CPU_PWR);
+
+	/* set to 0 after BIG VPROC bulk on & before B-core power on seq. */
+	if (cpu >= 4U) {
+		mmio_write_32(DREQ20_BIG_VPROC_ISO, 0U);
+	}
+
+	mmio_setbits_32(cpu_pwr_con, PWR_ON);
+
+	while (!spm_get_cpu_powerstate(cluster, cpu)) {
+		mmio_clrbits_32(cpu_pwr_con, PWR_ON);
+		mmio_setbits_32(cpu_pwr_con, PWR_ON);
+	}
+}
+
+/**
+ * Power off a core with specified cluster and core index
+ *
+ * @cluster: the cluster ID of the CPU which to be powered off
+ * @cpu: the CPU ID of the CPU which to be powered off
+ */
+void spm_poweroff_cpu(unsigned int cluster, unsigned int cpu)
+{
+	/* Set mp0_spmc_pwr_on_cpuX = 0 */
+	mmio_clrbits_32(per_cpu(cluster, cpu, SPM_CPU_PWR), PWR_ON);
+}
+
+/**
+ * Power off a cluster with specified index
+ *
+ * @cluster: the cluster index which to be powered off
+ */
+void spm_poweroff_cluster(unsigned int cluster)
+{
+	/* No need to power on/off cluster on single cluster platform */
+	assert(false);
+}
+
+/**
+ * Power on a cluster with specified index
+ *
+ * @cluster: the cluster index which to be powered on
+ */
+void spm_poweron_cluster(unsigned int cluster)
+{
+	/* No need to power on/off cluster on single cluster platform */
+	assert(false);
+}
diff --git a/plat/mediatek/mt8195/drivers/spmc/mtspmc.h b/plat/mediatek/mt8195/drivers/spmc/mtspmc.h
new file mode 100644
index 0000000..34e93d0
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spmc/mtspmc.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTSPMC_H
+#define MTSPMC_H
+
+#include <stdint.h>
+
+int spmc_init(void);
+
+void spm_poweron_cpu(unsigned int cluster, unsigned int cpu);
+void spm_poweroff_cpu(unsigned int cluster, unsigned int cpu);
+
+void spm_poweroff_cluster(unsigned int cluster);
+void spm_poweron_cluster(unsigned int cluster);
+
+bool spm_get_cpu_powerstate(unsigned int cluster, unsigned int cpu);
+bool spm_get_cluster_powerstate(unsigned int cluster);
+bool spm_get_powerstate(uint32_t mask);
+
+void mcucfg_init_archstate(unsigned int cluster, unsigned int cpu, bool arm64);
+void mcucfg_set_bootaddr(unsigned int cluster, unsigned int cpu, uintptr_t bootaddr);
+uintptr_t mcucfg_get_bootaddr(unsigned int cluster, unsigned int cpu);
+
+void mcucfg_disable_gic_wakeup(unsigned int cluster, unsigned int cpu);
+void mcucfg_enable_gic_wakeup(unsigned int cluster, unsigned int cpu);
+
+#endif /* MTSPMC_H */
diff --git a/plat/mediatek/mt8195/drivers/spmc/mtspmc_private.h b/plat/mediatek/mt8195/drivers/spmc/mtspmc_private.h
new file mode 100644
index 0000000..bf4092e
--- /dev/null
+++ b/plat/mediatek/mt8195/drivers/spmc/mtspmc_private.h
@@ -0,0 +1,183 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MTSPMC_PRIVATE_H
+#define MTSPMC_PRIVATE_H
+
+#include <lib/utils_def.h>
+#include <platform_def.h>
+
+unsigned long read_cpuectlr(void);
+void write_cpuectlr(unsigned long cpuectlr);
+
+unsigned long read_cpupwrctlr_el1(void);
+void write_cpupwrctlr_el1(unsigned long cpuectlr);
+
+/*
+ * per_cpu/cluster helper
+ */
+struct per_cpu_reg {
+	unsigned int cluster_addr;
+	unsigned int cpu_stride;
+};
+
+#define per_cpu(cluster, cpu, reg)	\
+	(reg[cluster].cluster_addr + (cpu << reg[cluster].cpu_stride))
+
+#define per_cluster(cluster, reg)	(reg[cluster].cluster_addr)
+
+#define SPM_REG(ofs)			(uint32_t)(SPM_BASE + (ofs))
+#define MCUCFG_REG(ofs)			(uint32_t)(MCUCFG_BASE + (ofs))
+#define INFRACFG_AO_REG(ofs)		(uint32_t)(INFRACFG_AO_BASE + (ofs))
+
+/* === SPMC related registers */
+#define SPM_POWERON_CONFIG_EN		SPM_REG(0x000)
+/* bit-fields of SPM_POWERON_CONFIG_EN */
+#define PROJECT_CODE			(U(0xb16) << 16)
+#define BCLK_CG_EN			BIT(0)
+
+#define SPM_PWR_STATUS			SPM_REG(0x16c)
+#define SPM_PWR_STATUS_2ND		SPM_REG(0x170)
+#define SPM_CPU_PWR_STATUS		SPM_REG(0x174)
+
+/* bit-fields of SPM_PWR_STATUS */
+#define MD				BIT(0)
+#define CONN				BIT(1)
+#define DDRPHY				BIT(2)
+#define DISP				BIT(3)
+#define MFG				BIT(4)
+#define ISP				BIT(5)
+#define INFRA				BIT(6)
+#define VDEC				BIT(7)
+#define MP0_CPUTOP			BIT(8)
+#define MP0_CPU0			BIT(9)
+#define MP0_CPU1			BIT(10)
+#define MP0_CPU2			BIT(11)
+#define MP0_CPU3			BIT(12)
+#define MCUSYS				BIT(14)
+#define MP0_CPU4			BIT(15)
+#define MP0_CPU5			BIT(16)
+#define MP0_CPU6			BIT(17)
+#define MP0_CPU7			BIT(18)
+#define VEN				BIT(21)
+
+/* === SPMC related registers */
+#define SPM_MCUSYS_PWR_CON		MCUCFG_REG(0xd200)
+#define SPM_MP0_CPUTOP_PWR_CON		MCUCFG_REG(0xd204)
+#define SPM_MP0_CPU0_PWR_CON		MCUCFG_REG(0xd208)
+#define SPM_MP0_CPU1_PWR_CON		MCUCFG_REG(0xd20c)
+#define SPM_MP0_CPU2_PWR_CON		MCUCFG_REG(0xd210)
+#define SPM_MP0_CPU3_PWR_CON		MCUCFG_REG(0xd214)
+#define SPM_MP0_CPU4_PWR_CON		MCUCFG_REG(0xd218)
+#define SPM_MP0_CPU5_PWR_CON		MCUCFG_REG(0xd21c)
+#define SPM_MP0_CPU6_PWR_CON		MCUCFG_REG(0xd220)
+#define SPM_MP0_CPU7_PWR_CON		MCUCFG_REG(0xd224)
+
+/* bit fields of SPM_*_PWR_CON */
+#define PWR_ON_ACK			BIT(31)
+#define VPROC_EXT_OFF			BIT(7)
+#define DORMANT_EN			BIT(6)
+#define RESETPWRON_CONFIG		BIT(5)
+#define PWR_CLK_DIS			BIT(4)
+#define PWR_ON				BIT(2)
+#define PWR_RST_B			BIT(0)
+
+/**** per_cpu registers for SPM_MP0_CPU?_PWR_CON */
+static const struct per_cpu_reg SPM_CPU_PWR[] = {
+	{ .cluster_addr = SPM_MP0_CPU0_PWR_CON, .cpu_stride = 2U }
+};
+
+/**** per_cluster registers for SPM_MP0_CPUTOP_PWR_CON */
+static const struct per_cpu_reg SPM_CLUSTER_PWR[] = {
+	{ .cluster_addr = SPM_MP0_CPUTOP_PWR_CON, .cpu_stride = 0U }
+};
+
+/* === MCUCFG related registers */
+/* aa64naa32 */
+#define MCUCFG_MP0_CLUSTER_CFG5		MCUCFG_REG(0xc8e4)
+/* reset vectors */
+#define MCUCFG_MP0_CLUSTER_CFG8		MCUCFG_REG(0xc900)
+#define MCUCFG_MP0_CLUSTER_CFG10	MCUCFG_REG(0xc908)
+#define MCUCFG_MP0_CLUSTER_CFG12	MCUCFG_REG(0xc910)
+#define MCUCFG_MP0_CLUSTER_CFG14	MCUCFG_REG(0xc918)
+#define MCUCFG_MP0_CLUSTER_CFG16	MCUCFG_REG(0xc920)
+#define MCUCFG_MP0_CLUSTER_CFG18	MCUCFG_REG(0xc928)
+#define MCUCFG_MP0_CLUSTER_CFG20	MCUCFG_REG(0xc930)
+#define MCUCFG_MP0_CLUSTER_CFG22	MCUCFG_REG(0xc938)
+
+/* MCUSYS DREQ BIG VPROC ISO control */
+#define DREQ20_BIG_VPROC_ISO		MCUCFG_REG(0xad8c)
+
+/**** per_cpu registers for MCUCFG_MP0_CLUSTER_CFG? */
+static const struct per_cpu_reg MCUCFG_BOOTADDR[] = {
+	{ .cluster_addr = MCUCFG_MP0_CLUSTER_CFG8, .cpu_stride = 3U }
+};
+
+/**** per_cpu registers for MCUCFG_MP0_CLUSTER_CFG5 */
+static const struct per_cpu_reg MCUCFG_INITARCH[] = {
+	{ .cluster_addr = MCUCFG_MP0_CLUSTER_CFG5, .cpu_stride = 0U }
+};
+
+#define MCUCFG_INITARCH_CPU_BIT(cpu)	BIT(16U + cpu)
+/* === CPC control */
+#define MCUCFG_CPC_FLOW_CTRL_CFG	MCUCFG_REG(0xa814)
+#define MCUCFG_CPC_SPMC_PWR_STATUS	MCUCFG_REG(0xa840)
+
+/* bit fields of CPC_FLOW_CTRL_CFG */
+#define CPC_CTRL_ENABLE			BIT(16)
+#define SSPM_CORE_PWR_ON_EN		BIT(7) /* for cpu-hotplug */
+#define SSPM_ALL_PWR_CTRL_EN		BIT(13) /* for cpu-hotplug */
+#define GIC_WAKEUP_IGNORE(cpu)		BIT(21 + cpu)
+
+/* bit fields of CPC_SPMC_PWR_STATUS */
+#define CORE_SPMC_PWR_ON_ACK		GENMASK(11, 0)
+
+/* === APB Module infracfg_ao */
+#define INFRA_TOPAXI_PROTECTEN		INFRACFG_AO_REG(0x0220)
+#define INFRA_TOPAXI_PROTECTEN_STA0	INFRACFG_AO_REG(0x0224)
+#define INFRA_TOPAXI_PROTECTEN_STA1	INFRACFG_AO_REG(0x0228)
+#define INFRA_TOPAXI_PROTECTEN_SET	INFRACFG_AO_REG(0x02a0)
+#define INFRA_TOPAXI_PROTECTEN_CLR	INFRACFG_AO_REG(0x02a4)
+#define INFRA_TOPAXI_PROTECTEN_1	INFRACFG_AO_REG(0x0250)
+#define INFRA_TOPAXI_PROTECTEN_STA0_1	INFRACFG_AO_REG(0x0254)
+#define INFRA_TOPAXI_PROTECTEN_STA1_1	INFRACFG_AO_REG(0x0258)
+#define INFRA_TOPAXI_PROTECTEN_1_SET	INFRACFG_AO_REG(0x02a8)
+#define INFRA_TOPAXI_PROTECTEN_1_CLR	INFRACFG_AO_REG(0x02ac)
+
+/* bit fields of INFRA_TOPAXI_PROTECTEN */
+#define MP0_SPMC_PROT_STEP1_0_MASK	BIT(12)
+#define MP0_SPMC_PROT_STEP1_1_MASK	(BIT(26) | BIT(12))
+
+/* === SPARK */
+#define VOLTAGE_04			U(0x40)
+#define VOLTAGE_05			U(0x60)
+
+#define PTP3_CPU0_SPMC_SW_CFG		MCUCFG_REG(0x200)
+#define CPU0_ILDO_CONTROL5		MCUCFG_REG(0x334)
+#define CPU0_ILDO_CONTROL8		MCUCFG_REG(0x340)
+
+/* bit fields of CPU0_ILDO_CONTROL5 */
+#define ILDO_RET_VOSEL			GENMASK(7, 0)
+
+/* bit fields of PTP3_CPU_SPMC_SW_CFG */
+#define SW_SPARK_EN			BIT(0)
+
+/* bit fields of CPU0_ILDO_CONTROL8 */
+#define ILDO_BYPASS_B			BIT(0)
+
+static const struct per_cpu_reg MCUCFG_SPARK[] = {
+	{ .cluster_addr = PTP3_CPU0_SPMC_SW_CFG, .cpu_stride = 11U }
+};
+
+static const struct per_cpu_reg ILDO_CONTROL5[] = {
+	{ .cluster_addr = CPU0_ILDO_CONTROL5, .cpu_stride = 11U }
+};
+
+static const struct per_cpu_reg ILDO_CONTROL8[] = {
+	{ .cluster_addr = CPU0_ILDO_CONTROL8, .cpu_stride = 11U }
+};
+
+#endif /* MTSPMC_PRIVATE_H */
diff --git a/plat/mediatek/mt8195/include/mcucfg.h b/plat/mediatek/mt8195/include/mcucfg.h
new file mode 100644
index 0000000..046cf73
--- /dev/null
+++ b/plat/mediatek/mt8195/include/mcucfg.h
@@ -0,0 +1,257 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef MCUCFG_H
+#define MCUCFG_H
+
+#ifndef __ASSEMBLER__
+#include <stdint.h>
+#endif /* __ASSEMBLER__ */
+
+#include <platform_def.h>
+
+#define MCUCFG_REG(ofs)			(uint32_t)(MCUCFG_BASE + (ofs))
+
+#define MP2_MISC_CONFIG_BOOT_ADDR_L(cpu) (MCUCFG_REG(0x2290) + ((cpu) * 8))
+#define MP2_MISC_CONFIG_BOOT_ADDR_H(cpu) (MCUCFG_REG(0x2294) + ((cpu) * 8))
+
+#define MP2_CPUCFG			MCUCFG_REG(0x2208)
+
+#define MP2_CPU0_STANDBYWFE		BIT(4)
+#define MP2_CPU1_STANDBYWFE		BIT(5)
+
+#define MP0_CPUTOP_SPMC_CTL		MCUCFG_REG(0x788)
+#define MP1_CPUTOP_SPMC_CTL		MCUCFG_REG(0x78C)
+#define MP1_CPUTOP_SPMC_SRAM_CTL	MCUCFG_REG(0x790)
+
+#define sw_spark_en			BIT(0)
+#define sw_no_wait_for_q_channel	BIT(1)
+#define sw_fsm_override			BIT(2)
+#define sw_logic_pre1_pdb		BIT(3)
+#define sw_logic_pre2_pdb		BIT(4)
+#define sw_logic_pdb			BIT(5)
+#define sw_iso				BIT(6)
+#define sw_sram_sleepb			(U(0x3F) << 7)
+#define sw_sram_isointb			BIT(13)
+#define sw_clk_dis			BIT(14)
+#define sw_ckiso			BIT(15)
+#define sw_pd				(U(0x3F) << 16)
+#define sw_hot_plug_reset		BIT(22)
+#define sw_pwr_on_override_en		BIT(23)
+#define sw_pwr_on			BIT(24)
+#define sw_coq_dis			BIT(25)
+#define logic_pdbo_all_off_ack		BIT(26)
+#define logic_pdbo_all_on_ack		BIT(27)
+#define logic_pre2_pdbo_all_on_ack	BIT(28)
+#define logic_pre1_pdbo_all_on_ack	BIT(29)
+
+
+#define CPUSYSx_CPUx_SPMC_CTL(cluster, cpu) \
+	(MCUCFG_REG(0x1c30) + cluster * 0x2000 + cpu * 4)
+
+#define CPUSYS0_CPU0_SPMC_CTL		MCUCFG_REG(0x1c30)
+#define CPUSYS0_CPU1_SPMC_CTL		MCUCFG_REG(0x1c34)
+#define CPUSYS0_CPU2_SPMC_CTL		MCUCFG_REG(0x1c38)
+#define CPUSYS0_CPU3_SPMC_CTL		MCUCFG_REG(0x1c3C)
+
+#define CPUSYS1_CPU0_SPMC_CTL		MCUCFG_REG(0x3c30)
+#define CPUSYS1_CPU1_SPMC_CTL		MCUCFG_REG(0x3c34)
+#define CPUSYS1_CPU2_SPMC_CTL		MCUCFG_REG(0x3c38)
+#define CPUSYS1_CPU3_SPMC_CTL		MCUCFG_REG(0x3c3C)
+
+#define cpu_sw_spark_en			BIT(0)
+#define cpu_sw_no_wait_for_q_channel	BIT(1)
+#define cpu_sw_fsm_override		BIT(2)
+#define cpu_sw_logic_pre1_pdb		BIT(3)
+#define cpu_sw_logic_pre2_pdb		BIT(4)
+#define cpu_sw_logic_pdb		BIT(5)
+#define cpu_sw_iso			BIT(6)
+#define cpu_sw_sram_sleepb		BIT(7)
+#define cpu_sw_sram_isointb		BIT(8)
+#define cpu_sw_clk_dis			BIT(9)
+#define cpu_sw_ckiso			BIT(10)
+#define cpu_sw_pd			(U(0x1F) << 11)
+#define cpu_sw_hot_plug_reset		BIT(16)
+#define cpu_sw_powr_on_override_en	BIT(17)
+#define cpu_sw_pwr_on			BIT(18)
+#define cpu_spark2ldo_allswoff		BIT(19)
+#define cpu_pdbo_all_on_ack		BIT(20)
+#define cpu_pre2_pdbo_allon_ack		BIT(21)
+#define cpu_pre1_pdbo_allon_ack		BIT(22)
+
+/* CPC related registers */
+#define CPC_MCUSYS_CPC_OFF_THRES	MCUCFG_REG(0xa714)
+#define CPC_MCUSYS_PWR_CTRL		MCUCFG_REG(0xa804)
+#define CPC_MCUSYS_CPC_FLOW_CTRL_CFG	MCUCFG_REG(0xa814)
+#define CPC_MCUSYS_LAST_CORE_REQ	MCUCFG_REG(0xa818)
+#define CPC_MCUSYS_MP_LAST_CORE_RESP	MCUCFG_REG(0xa81c)
+#define CPC_MCUSYS_LAST_CORE_RESP	MCUCFG_REG(0xa824)
+#define CPC_MCUSYS_PWR_ON_MASK		MCUCFG_REG(0xa828)
+#define CPC_MCUSYS_CPU_ON_SW_HINT_SET	MCUCFG_REG(0xa8a8)
+#define CPC_MCUSYS_CPU_ON_SW_HINT_CLR	MCUCFG_REG(0xa8ac)
+#define CPC_MCUSYS_CPC_DBG_SETTING	MCUCFG_REG(0xab00)
+#define CPC_MCUSYS_CPC_KERNEL_TIME_L_BASE	MCUCFG_REG(0xab04)
+#define CPC_MCUSYS_CPC_KERNEL_TIME_H_BASE	MCUCFG_REG(0xab08)
+#define CPC_MCUSYS_CPC_SYSTEM_TIME_L_BASE	MCUCFG_REG(0xab0c)
+#define CPC_MCUSYS_CPC_SYSTEM_TIME_H_BASE	MCUCFG_REG(0xab10)
+#define CPC_MCUSYS_TRACE_SEL		MCUCFG_REG(0xab14)
+#define CPC_MCUSYS_TRACE_DATA		MCUCFG_REG(0xab20)
+#define CPC_MCUSYS_CLUSTER_COUNTER	MCUCFG_REG(0xab70)
+#define CPC_MCUSYS_CLUSTER_COUNTER_CLR	MCUCFG_REG(0xab74)
+
+#define SPARK2LDO			MCUCFG_REG(0x2700)
+/* APB Module mcucfg */
+#define MP0_CA7_CACHE_CONFIG		MCUCFG_REG(0x000)
+#define MP0_AXI_CONFIG			MCUCFG_REG(0x02C)
+#define MP0_MISC_CONFIG0		MCUCFG_REG(0x030)
+#define MP0_MISC_CONFIG1		MCUCFG_REG(0x034)
+#define MP0_MISC_CONFIG2		MCUCFG_REG(0x038)
+#define MP0_MISC_CONFIG_BOOT_ADDR(cpu)	(MP0_MISC_CONFIG2 + ((cpu) * 8))
+#define MP0_MISC_CONFIG3		MCUCFG_REG(0x03C)
+#define MP0_MISC_CONFIG9		MCUCFG_REG(0x054)
+#define MP0_CA7_MISC_CONFIG		MCUCFG_REG(0x064)
+
+#define MP0_RW_RSVD0			MCUCFG_REG(0x06C)
+
+
+#define MP1_CA7_CACHE_CONFIG		MCUCFG_REG(0x200)
+#define MP1_AXI_CONFIG			MCUCFG_REG(0x22C)
+#define MP1_MISC_CONFIG0		MCUCFG_REG(0x230)
+#define MP1_MISC_CONFIG1		MCUCFG_REG(0x234)
+#define MP1_MISC_CONFIG2		MCUCFG_REG(0x238)
+#define MP1_MISC_CONFIG_BOOT_ADDR(cpu)	(MP1_MISC_CONFIG2 + ((cpu) * 8))
+#define MP1_MISC_CONFIG3		MCUCFG_REG(0x23C)
+#define MP1_MISC_CONFIG9		MCUCFG_REG(0x254)
+#define MP1_CA7_MISC_CONFIG		MCUCFG_REG(0x264)
+
+#define CCI_ADB400_DCM_CONFIG		MCUCFG_REG(0x740)
+#define SYNC_DCM_CONFIG			MCUCFG_REG(0x744)
+
+#define MP0_CLUSTER_CFG0		MCUCFG_REG(0xC8D0)
+
+#define MP0_SPMC			MCUCFG_REG(0x788)
+#define MP1_SPMC			MCUCFG_REG(0x78C)
+#define MP2_AXI_CONFIG			MCUCFG_REG(0x220C)
+#define MP2_AXI_CONFIG_ACINACTM		BIT(0)
+#define MP2_AXI_CONFIG_AINACTS		BIT(4)
+
+#define MPx_AXI_CONFIG_ACINACTM		BIT(4)
+#define MPx_AXI_CONFIG_AINACTS		BIT(5)
+
+#define MPx_CA7_MISC_CONFIG_standbywfil2	BIT(28)
+
+#define MP0_CPU0_STANDBYWFE		BIT(20)
+#define MP0_CPU1_STANDBYWFE		BIT(21)
+#define MP0_CPU2_STANDBYWFE		BIT(22)
+#define MP0_CPU3_STANDBYWFE		BIT(23)
+
+#define MP1_CPU0_STANDBYWFE		BIT(20)
+#define MP1_CPU1_STANDBYWFE		BIT(21)
+#define MP1_CPU2_STANDBYWFE		BIT(22)
+#define MP1_CPU3_STANDBYWFE		BIT(23)
+
+#define CPUSYS0_SPARKVRETCNTRL		MCUCFG_REG(0x1c00)
+#define CPUSYS0_SPARKEN			MCUCFG_REG(0x1c04)
+#define CPUSYS0_AMUXSEL			MCUCFG_REG(0x1c08)
+#define CPUSYS1_SPARKVRETCNTRL		MCUCFG_REG(0x3c00)
+#define CPUSYS1_SPARKEN			MCUCFG_REG(0x3c04)
+#define CPUSYS1_AMUXSEL			MCUCFG_REG(0x3c08)
+
+#define MP2_PWR_RST_CTL			MCUCFG_REG(0x2008)
+#define MP2_PTP3_CPUTOP_SPMC0		MCUCFG_REG(0x22A0)
+#define MP2_PTP3_CPUTOP_SPMC1		MCUCFG_REG(0x22A4)
+
+#define MP2_COQ				MCUCFG_REG(0x22BC)
+#define MP2_COQ_SW_DIS			BIT(0)
+
+#define MP2_CA15M_MON_SEL		MCUCFG_REG(0x2400)
+#define MP2_CA15M_MON_L			MCUCFG_REG(0x2404)
+
+#define CPUSYS2_CPU0_SPMC_CTL		MCUCFG_REG(0x2430)
+#define CPUSYS2_CPU1_SPMC_CTL		MCUCFG_REG(0x2438)
+#define CPUSYS2_CPU0_SPMC_STA		MCUCFG_REG(0x2434)
+#define CPUSYS2_CPU1_SPMC_STA		MCUCFG_REG(0x243C)
+
+#define MP0_CA7L_DBG_PWR_CTRL		MCUCFG_REG(0x068)
+#define MP1_CA7L_DBG_PWR_CTRL		MCUCFG_REG(0x268)
+#define BIG_DBG_PWR_CTRL		MCUCFG_REG(0x75C)
+
+#define MP2_SW_RST_B			BIT(0)
+#define MP2_TOPAON_APB_MASK		BIT(1)
+
+#define B_SW_HOT_PLUG_RESET		BIT(30)
+
+#define B_SW_PD_OFFSET			18U
+#define B_SW_PD				(U(0x3f) << B_SW_PD_OFFSET)
+
+#define B_SW_SRAM_SLEEPB_OFFSET		12U
+#define B_SW_SRAM_SLEEPB		(U(0x3f) << B_SW_SRAM_SLEEPB_OFFSET)
+
+#define B_SW_SRAM_ISOINTB		BIT(9)
+#define B_SW_ISO			BIT(8)
+#define B_SW_LOGIC_PDB			BIT(7)
+#define B_SW_LOGIC_PRE2_PDB		BIT(6)
+#define B_SW_LOGIC_PRE1_PDB		BIT(5)
+#define B_SW_FSM_OVERRIDE		BIT(4)
+#define B_SW_PWR_ON			BIT(3)
+#define B_SW_PWR_ON_OVERRIDE_EN		BIT(2)
+
+#define B_FSM_STATE_OUT_OFFSET		(6U)
+#define B_FSM_STATE_OUT_MASK		(U(0x1f) << B_FSM_STATE_OUT_OFFSET)
+#define B_SW_LOGIC_PDBO_ALL_OFF_ACK	BIT(5)
+#define B_SW_LOGIC_PDBO_ALL_ON_ACK	BIT(4)
+#define B_SW_LOGIC_PRE2_PDBO_ALL_ON_ACK	BIT(3)
+#define B_SW_LOGIC_PRE1_PDBO_ALL_ON_ACK	BIT(2)
+
+#define B_FSM_OFF			(0U << B_FSM_STATE_OUT_OFFSET)
+#define B_FSM_ON			(1U << B_FSM_STATE_OUT_OFFSET)
+#define B_FSM_RET			(2U << B_FSM_STATE_OUT_OFFSET)
+
+#ifndef __ASSEMBLER__
+/* cpu boot mode */
+enum {
+	MP0_CPUCFG_64BIT_SHIFT = 12U,
+	MP1_CPUCFG_64BIT_SHIFT = 28U,
+	MP0_CPUCFG_64BIT = U(0xf) << MP0_CPUCFG_64BIT_SHIFT,
+	MP1_CPUCFG_64BIT = U(0xf) << MP1_CPUCFG_64BIT_SHIFT
+};
+
+enum {
+	MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK_SHIFT = 0U,
+	MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK_SHIFT = 4U,
+	MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK_SHIFT = 8U,
+	MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK_SHIFT = 12U,
+	MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK_SHIFT = 16U,
+
+	MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU0_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU1_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU2_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU3_WAIT_PD_CPUS_L1_ACK_SHIFT,
+	MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK =
+		U(0xf) << MP1_DIS_RGU_NOCPU_WAIT_PD_CPUS_L1_ACK_SHIFT
+};
+
+enum {
+	MP1_AINACTS_SHIFT = 4U,
+	MP1_AINACTS = 1U << MP1_AINACTS_SHIFT
+};
+
+enum {
+	MP1_SW_CG_GEN_SHIFT = 12U,
+	MP1_SW_CG_GEN = 1U << MP1_SW_CG_GEN_SHIFT
+};
+
+enum {
+	MP1_L2RSTDISABLE_SHIFT = 14U,
+	MP1_L2RSTDISABLE = 1U << MP1_L2RSTDISABLE_SHIFT
+};
+#endif /* __ASSEMBLER__ */
+
+#endif  /* MCUCFG_H */
diff --git a/plat/mediatek/mt8195/include/plat_helpers.h b/plat/mediatek/mt8195/include/plat_helpers.h
new file mode 100644
index 0000000..ebc9fa0
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_helpers.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef __PLAT_HELPERS_H__
+#define __PLAT_HELPERS_H__
+
+unsigned int plat_mediatek_calc_core_pos(u_register_t mpidr);
+
+#endif /* __PLAT_HELPERS_H__ */
diff --git a/plat/mediatek/mt8195/include/plat_macros.S b/plat/mediatek/mt8195/include/plat_macros.S
new file mode 100644
index 0000000..39727ea
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_macros.S
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef PLAT_MACROS_S
+#define PLAT_MACROS_S
+
+#include <platform_def.h>
+
+.section .rodata.gic_reg_name, "aS"
+gicc_regs:
+	.asciz "gicc_hppir", "gicc_ahppir", "gicc_ctlr", ""
+gicd_pend_reg:
+	.asciz "gicd_ispendr regs (Offsets 0x200 - 0x278)\n"	\
+		" Offset:\t\t\tvalue\n"
+newline:
+	.asciz "\n"
+spacer:
+	.asciz ":\t\t0x"
+
+.section .rodata.cci_reg_name, "aS"
+cci_iface_regs:
+	.asciz "cci_snoop_ctrl_cluster0", "cci_snoop_ctrl_cluster1" , ""
+
+	/* ---------------------------------------------
+	 * The below macro prints out relevant GIC
+	 * registers whenever an unhandled exception
+	 * is taken in BL31.
+	 * Clobbers: x0 - x10, x26, x27, sp
+	 * ---------------------------------------------
+	 */
+	.macro plat_crash_print_regs
+	/* TODO: leave implementation to GIC owner */
+	.endm
+
+#endif /* PLAT_MACROS_S */
diff --git a/plat/mediatek/mt8195/include/plat_mtk_lpm.h b/plat/mediatek/mt8195/include/plat_mtk_lpm.h
new file mode 100644
index 0000000..347f358
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_mtk_lpm.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_MTK_LPM_H
+#define PLAT_MTK_LPM_H
+
+#include <lib/psci/psci.h>
+#include <lib/utils_def.h>
+
+#define MT_IRQ_REMAIN_MAX	U(32)
+#define MT_IRQ_REMAIN_CAT_LOG	BIT(31)
+
+struct mt_irqremain {
+	unsigned int count;
+	unsigned int irqs[MT_IRQ_REMAIN_MAX];
+	unsigned int wakeupsrc_cat[MT_IRQ_REMAIN_MAX];
+	unsigned int wakeupsrc[MT_IRQ_REMAIN_MAX];
+};
+
+#define PLAT_RC_STATUS_READY		BIT(0)
+#define PLAT_RC_STATUS_FEATURE_EN	BIT(1)
+#define PLAT_RC_STATUS_UART_NONSLEEP	BIT(31)
+
+struct mt_lpm_tz {
+	int (*pwr_prompt)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_reflect)(unsigned int cpu, const psci_power_state_t *state);
+
+	int (*pwr_cpu_on)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_cpu_dwn)(unsigned int cpu, const psci_power_state_t *state);
+
+	int (*pwr_cluster_on)(unsigned int cpu,
+					const psci_power_state_t *state);
+	int (*pwr_cluster_dwn)(unsigned int cpu,
+					const psci_power_state_t *state);
+
+	int (*pwr_mcusys_on)(unsigned int cpu, const psci_power_state_t *state);
+	int (*pwr_mcusys_on_finished)(unsigned int cpu,
+					const psci_power_state_t *state);
+	int (*pwr_mcusys_dwn)(unsigned int cpu,
+					const psci_power_state_t *state);
+};
+
+const struct mt_lpm_tz *mt_plat_cpu_pm_init(void);
+
+#endif /* PLAT_MTK_LPM_H */
diff --git a/plat/mediatek/mt8195/include/plat_pm.h b/plat/mediatek/mt8195/include/plat_pm.h
new file mode 100644
index 0000000..a2881ce
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_pm.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_PM_H
+#define PLAT_PM_H
+
+#include <lib/utils_def.h>
+
+#define MT_PLAT_PWR_STATE_CPU			U(1)
+#define MT_PLAT_PWR_STATE_CLUSTER		U(2)
+#define MT_PLAT_PWR_STATE_MCUSYS		U(3)
+#define MT_PLAT_PWR_STATE_SUSPEND2IDLE		U(8)
+#define MT_PLAT_PWR_STATE_SYSTEM_SUSPEND	U(9)
+
+#define MTK_LOCAL_STATE_RUN			U(0)
+#define MTK_LOCAL_STATE_RET			U(1)
+#define MTK_LOCAL_STATE_OFF			U(2)
+
+#define MTK_AFFLVL_CPU				U(0)
+#define MTK_AFFLVL_CLUSTER			U(1)
+#define MTK_AFFLVL_MCUSYS			U(2)
+#define MTK_AFFLVL_SYSTEM			U(3)
+
+#define IS_CLUSTER_OFF_STATE(s)		\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_CLUSTER])
+#define IS_MCUSYS_OFF_STATE(s)		\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_MCUSYS])
+#define IS_SYSTEM_SUSPEND_STATE(s)	\
+		is_local_state_off(s->pwr_domain_state[MTK_AFFLVL_SYSTEM])
+
+#define IS_PLAT_SUSPEND_ID(stateid)\
+		((stateid == MT_PLAT_PWR_STATE_SUSPEND2IDLE)	\
+		|| (stateid == MT_PLAT_PWR_STATE_SYSTEM_SUSPEND))
+
+#endif /* PLAT_PM_H */
diff --git a/plat/mediatek/mt8195/include/plat_private.h b/plat/mediatek/mt8195/include/plat_private.h
new file mode 100644
index 0000000..7ef2b85
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_private.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_PRIVATE_H
+#define PLAT_PRIVATE_H
+
+/*******************************************************************************
+ * Function and variable prototypes
+ ******************************************************************************/
+void plat_configure_mmu_el3(uintptr_t total_base,
+			    uintptr_t total_size,
+			    uintptr_t ro_start,
+			    uintptr_t ro_limit);
+
+#endif /* PLAT_PRIVATE_H */
diff --git a/plat/mediatek/mt8195/include/plat_sip_calls.h b/plat/mediatek/mt8195/include/plat_sip_calls.h
new file mode 100644
index 0000000..ce25c6f
--- /dev/null
+++ b/plat/mediatek/mt8195/include/plat_sip_calls.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_SIP_CALLS_H
+#define PLAT_SIP_CALLS_H
+
+/*******************************************************************************
+ * Plat SiP function constants
+ ******************************************************************************/
+#define MTK_PLAT_SIP_NUM_CALLS    4
+
+/* DFD */
+#define MTK_SIP_KERNEL_DFD_AARCH32	0x82000205
+#define MTK_SIP_KERNEL_DFD_AARCH64	0xC2000205
+
+/* DP/eDP */
+#define MTK_SIP_DP_CONTROL_AARCH32	0x82000523
+#define MTK_SIP_DP_CONTROL_AARCH64	0xC2000523
+
+#endif /* PLAT_SIP_CALLS_H */
diff --git a/plat/mediatek/mt8195/include/platform_def.h b/plat/mediatek/mt8195/include/platform_def.h
new file mode 100644
index 0000000..68301d6
--- /dev/null
+++ b/plat/mediatek/mt8195/include/platform_def.h
@@ -0,0 +1,158 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#define PLAT_PRIMARY_CPU	0x0
+
+#define MT_GIC_BASE		(0x0C000000)
+#define MCUCFG_BASE		(0x0C530000)
+#define IO_PHYS			(0x10000000)
+
+/* Aggregate of all devices for MMU mapping */
+#define MTK_DEV_RNG0_BASE	IO_PHYS
+#define MTK_DEV_RNG0_SIZE	0x10000000
+#define MTK_DEV_RNG2_BASE	MT_GIC_BASE
+#define MTK_DEV_RNG2_SIZE	0x600000
+#define MTK_MCDI_SRAM_BASE	0x11B000
+#define MTK_MCDI_SRAM_MAP_SIZE	0x1000
+
+#define TOPCKGEN_BASE           (IO_PHYS + 0x00000000)
+#define INFRACFG_AO_BASE        (IO_PHYS + 0x00001000)
+#define SPM_BASE		(IO_PHYS + 0x00006000)
+#define RGU_BASE		(IO_PHYS + 0x00007000)
+#define APMIXEDSYS              (IO_PHYS + 0x0000C000)
+#define DRM_BASE		(IO_PHYS + 0x0000D000)
+#define SSPM_MBOX_BASE          (IO_PHYS + 0x00480000)
+#define PERICFG_AO_BASE         (IO_PHYS + 0x01003000)
+#define VPPSYS0_BASE            (IO_PHYS + 0x04000000)
+#define VPPSYS1_BASE            (IO_PHYS + 0x04f00000)
+#define VDOSYS0_BASE            (IO_PHYS + 0x0C01A000)
+#define VDOSYS1_BASE            (IO_PHYS + 0x0C100000)
+#define DVFSRC_BASE             (IO_PHYS + 0x00012000)
+
+/*******************************************************************************
+ * DP/eDP related constants
+ ******************************************************************************/
+#define eDP_SEC_BASE		(IO_PHYS + 0x0C504000)
+#define DP_SEC_BASE		(IO_PHYS + 0x0C604000)
+#define eDP_SEC_SIZE		0x1000
+#define DP_SEC_SIZE		0x1000
+
+/*******************************************************************************
+ * GPIO related constants
+ ******************************************************************************/
+#define GPIO_BASE		(IO_PHYS + 0x00005000)
+#define IOCFG_BM_BASE		(IO_PHYS + 0x01D10000)
+#define IOCFG_BL_BASE		(IO_PHYS + 0x01D30000)
+#define IOCFG_BR_BASE		(IO_PHYS + 0x01D40000)
+#define IOCFG_LM_BASE		(IO_PHYS + 0x01E20000)
+#define IOCFG_RB_BASE		(IO_PHYS + 0x01EB0000)
+#define IOCFG_TL_BASE		(IO_PHYS + 0x01F40000)
+
+/*******************************************************************************
+ * UART related constants
+ ******************************************************************************/
+#define UART0_BASE			(IO_PHYS + 0x01001100)
+#define UART1_BASE			(IO_PHYS + 0x01001200)
+
+#define UART_BAUDRATE			115200
+
+/*******************************************************************************
+ * PMIC related constants
+ ******************************************************************************/
+#define PMIC_WRAP_BASE			(IO_PHYS + 0x00024000)
+
+/*******************************************************************************
+ * EMI MPU related constants
+ ******************************************************************************/
+#define EMI_MPU_BASE		(IO_PHYS + 0x00226000)
+#define SUB_EMI_MPU_BASE	(IO_PHYS + 0x00225000)
+
+/*******************************************************************************
+ * System counter frequency related constants
+ ******************************************************************************/
+#define SYS_COUNTER_FREQ_IN_TICKS	13000000
+#define SYS_COUNTER_FREQ_IN_MHZ		13
+
+/*******************************************************************************
+ * GIC-600 & interrupt handling related constants
+ ******************************************************************************/
+/* Base MTK_platform compatible GIC memory map */
+#define BASE_GICD_BASE			MT_GIC_BASE
+#define MT_GIC_RDIST_BASE		(MT_GIC_BASE + 0x40000)
+
+#define SYS_CIRQ_BASE			(IO_PHYS + 0x204000)
+#define CIRQ_REG_NUM			23
+#define CIRQ_IRQ_NUM			730
+#define CIRQ_SPI_START			96
+#define MD_WDT_IRQ_BIT_ID		141
+/*******************************************************************************
+ * Platform binary types for linking
+ ******************************************************************************/
+#define PLATFORM_LINKER_FORMAT		"elf64-littleaarch64"
+#define PLATFORM_LINKER_ARCH		aarch64
+
+/*******************************************************************************
+ * Generic platform constants
+ ******************************************************************************/
+#define PLATFORM_STACK_SIZE		0x800
+
+#define FIRMWARE_WELCOME_STR		"Booting Trusted Firmware\n"
+
+#define PLAT_MAX_PWR_LVL		U(3)
+#define PLAT_MAX_RET_STATE		U(1)
+#define PLAT_MAX_OFF_STATE		U(9)
+
+#define PLATFORM_SYSTEM_COUNT		U(1)
+#define PLATFORM_MCUSYS_COUNT		U(1)
+#define PLATFORM_CLUSTER_COUNT		U(1)
+#define PLATFORM_CLUSTER0_CORE_COUNT	U(8)
+#define PLATFORM_CLUSTER1_CORE_COUNT	U(0)
+
+#define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER0_CORE_COUNT)
+#define PLATFORM_MAX_CPUS_PER_CLUSTER	U(8)
+
+#define SOC_CHIP_ID			U(0x8195)
+
+/*******************************************************************************
+ * Platform memory map related constants
+ ******************************************************************************/
+#define TZRAM_BASE			0x54600000
+#define TZRAM_SIZE			0x00030000
+
+/*******************************************************************************
+ * BL31 specific defines.
+ ******************************************************************************/
+/*
+ * Put BL3-1 at the top of the Trusted SRAM (just below the shared memory, if
+ * present). BL31_BASE is calculated using the current BL3-1 debug size plus a
+ * little space for growth.
+ */
+#define BL31_BASE			(TZRAM_BASE + 0x1000)
+#define BL31_LIMIT			(TZRAM_BASE + TZRAM_SIZE)
+
+/*******************************************************************************
+ * Platform specific page table and MMU setup constants
+ ******************************************************************************/
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
+#define MAX_XLAT_TABLES			16
+#define MAX_MMAP_REGIONS		16
+
+/*******************************************************************************
+ * Declarations and constants to access the mailboxes safely. Each mailbox is
+ * aligned on the biggest cache line size in the platform. This is known only
+ * to the platform as it might have a combination of integrated and external
+ * caches. Such alignment ensures that two maiboxes do not sit on the same cache
+ * line at any cache level. They could belong to different cpus/clusters &
+ * get written while being protected by different locks causing corruption of
+ * a valid mailbox address.
+ ******************************************************************************/
+#define CACHE_WRITEBACK_SHIFT		6
+#define CACHE_WRITEBACK_GRANULE		(1 << CACHE_WRITEBACK_SHIFT)
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/mediatek/mt8195/include/rtc.h b/plat/mediatek/mt8195/include/rtc.h
new file mode 100644
index 0000000..a9c7bc8
--- /dev/null
+++ b/plat/mediatek/mt8195/include/rtc.h
@@ -0,0 +1,12 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RTC_H
+#define RTC_H
+
+#include <rtc_mt6359p.h>
+
+#endif  /* RTC_H */
diff --git a/plat/mediatek/mt8195/plat_pm.c b/plat/mediatek/mt8195/plat_pm.c
new file mode 100644
index 0000000..b77ab27
--- /dev/null
+++ b/plat/mediatek/mt8195/plat_pm.c
@@ -0,0 +1,403 @@
+/*
+ * Copyright (c) 2021, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/* common headers */
+#include <assert.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/gpio.h>
+#include <lib/psci/psci.h>
+
+/* platform specific headers */
+#include <mt_gic_v3.h>
+#include <mtk_ptp3_common.h>
+#include <mtspmc.h>
+#include <plat/common/platform.h>
+#include <plat_dfd.h>
+#include <plat_mtk_lpm.h>
+#include <plat_params.h>
+#include <plat_pm.h>
+#include <pmic.h>
+#include <rtc.h>
+
+/*
+ * Cluster state request:
+ * [0] : The CPU requires cluster power down
+ * [1] : The CPU requires cluster power on
+ */
+#define coordinate_cluster(onoff)	write_clusterpwrdn_el1(onoff)
+#define coordinate_cluster_pwron()	coordinate_cluster(1)
+#define coordinate_cluster_pwroff()	coordinate_cluster(0)
+
+/* platform secure entry point */
+static uintptr_t secure_entrypoint;
+/* per-CPU power state */
+static unsigned int plat_power_state[PLATFORM_CORE_COUNT];
+
+/* platform CPU power domain - ops */
+static const struct mt_lpm_tz *plat_mt_pm;
+
+#define plat_mt_pm_invoke(_name, _cpu, _state) ({ \
+	int ret = -1; \
+	if (plat_mt_pm != NULL && plat_mt_pm->_name != NULL) { \
+		ret = plat_mt_pm->_name(_cpu, _state); \
+	} \
+	ret; })
+
+#define plat_mt_pm_invoke_no_check(_name, _cpu, _state) ({ \
+	if (plat_mt_pm != NULL && plat_mt_pm->_name != NULL) { \
+		(void) plat_mt_pm->_name(_cpu, _state); \
+	} \
+	})
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * CPU in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_cpu_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	plat_mt_pm_invoke_no_check(pwr_cpu_dwn, cpu, state);
+
+	if ((psci_get_pstate_pwrlvl(req_pstate) >= MTK_AFFLVL_CLUSTER) ||
+			(req_pstate == 0U)) { /* hotplug off */
+		coordinate_cluster_pwroff();
+	}
+
+	/* Prevent interrupts from spuriously waking up this CPU */
+	mt_gic_rdistif_save();
+	gicv3_cpuif_disable(cpu);
+	gicv3_rdistif_off(cpu);
+}
+
+static void plat_cpu_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	plat_mt_pm_invoke_no_check(pwr_cpu_on, cpu, state);
+
+	coordinate_cluster_pwron();
+
+	/* PTP3 config */
+	ptp3_core_init(cpu);
+
+	/*
+	 * If mcusys does power down before then restore
+	 * all CPUs' GIC Redistributors
+	 */
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		mt_gic_rdistif_restore_all();
+	} else {
+		gicv3_rdistif_on(cpu);
+		gicv3_cpuif_enable(cpu);
+		mt_gic_rdistif_init();
+		mt_gic_rdistif_restore();
+	}
+}
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * cluster in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_cluster_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_cluster_dwn, cpu, state) != 0) {
+		coordinate_cluster_pwron();
+
+		/* TODO: return on fail.
+		 *       Add a 'return' here before adding any code following
+		 *       the if-block.
+		 */
+	}
+}
+
+static void plat_cluster_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_cluster_on, cpu, state) != 0) {
+		/* TODO: return on fail.
+		 *       Add a 'return' here before adding any code following
+		 *       the if-block.
+		 */
+	}
+}
+
+/*
+ * Common MTK_platform operations to power on/off a
+ * mcusys in response to a CPU_ON, CPU_OFF or CPU_SUSPEND request.
+ */
+
+static void plat_mcusys_pwrdwn_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_mcusys_dwn, cpu, state) != 0) {
+		return;		/* return on fail */
+	}
+
+	mt_gic_distif_save();
+	gic_sgi_save_all();
+}
+
+static void plat_mcusys_pwron_common(unsigned int cpu,
+		const psci_power_state_t *state, unsigned int req_pstate)
+{
+	assert(cpu == plat_my_core_pos());
+
+	if (plat_mt_pm_invoke(pwr_mcusys_on, cpu, state) != 0) {
+		return;		/* return on fail */
+	}
+
+	mt_gic_init();
+	mt_gic_distif_restore();
+	gic_sgi_restore_all();
+
+	dfd_resume();
+
+	plat_mt_pm_invoke_no_check(pwr_mcusys_on_finished, cpu, state);
+}
+
+/*
+ * plat_psci_ops implementation
+ */
+
+static void plat_cpu_standby(plat_local_state_t cpu_state)
+{
+	uint64_t scr;
+
+	scr = read_scr_el3();
+	write_scr_el3(scr | SCR_IRQ_BIT | SCR_FIQ_BIT);
+
+	isb();
+	dsb();
+	wfi();
+
+	write_scr_el3(scr);
+}
+
+static int plat_power_domain_on(u_register_t mpidr)
+{
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+	unsigned int cluster = 0U;
+
+	if (cpu >= PLATFORM_CORE_COUNT) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	if (!spm_get_cluster_powerstate(cluster)) {
+		spm_poweron_cluster(cluster);
+	}
+
+	/* init CPU reset arch as AARCH64 */
+	mcucfg_init_archstate(cluster, cpu, true);
+	mcucfg_set_bootaddr(cluster, cpu, secure_entrypoint);
+	spm_poweron_cpu(cluster, cpu);
+
+	return PSCI_E_SUCCESS;
+}
+
+static void plat_power_domain_on_finish(const psci_power_state_t *state)
+{
+	unsigned long mpidr = read_mpidr_el1();
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	/* Allow IRQs to wakeup this core in IDLE flow */
+	mcucfg_enable_gic_wakeup(0U, cpu);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		plat_cluster_pwron_common(cpu, state, 0U);
+	}
+
+	plat_cpu_pwron_common(cpu, state, 0U);
+}
+
+static void plat_power_domain_off(const psci_power_state_t *state)
+{
+	unsigned long mpidr = read_mpidr_el1();
+	unsigned int cpu = (unsigned int)plat_core_pos_by_mpidr(mpidr);
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	plat_cpu_pwrdwn_common(cpu, state, 0U);
+	spm_poweroff_cpu(0U, cpu);
+
+	/* prevent unintended IRQs from waking up the hot-unplugged core */
+	mcucfg_disable_gic_wakeup(0U, cpu);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		plat_cluster_pwrdwn_common(cpu, state, 0U);
+	}
+}
+
+static void plat_power_domain_suspend(const psci_power_state_t *state)
+{
+	unsigned int cpu = plat_my_core_pos();
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	plat_mt_pm_invoke_no_check(pwr_prompt, cpu, state);
+
+	/* Perform the common CPU specific operations */
+	plat_cpu_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		/* Perform the common cluster specific operations */
+		plat_cluster_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		/* Perform the common mcusys specific operations */
+		plat_mcusys_pwrdwn_common(cpu, state, plat_power_state[cpu]);
+	}
+}
+
+static void plat_power_domain_suspend_finish(const psci_power_state_t *state)
+{
+	unsigned int cpu = plat_my_core_pos();
+
+	assert(cpu < PLATFORM_CORE_COUNT);
+
+	if (IS_MCUSYS_OFF_STATE(state)) {
+		/* Perform the common mcusys specific operations */
+		plat_mcusys_pwron_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	if (IS_CLUSTER_OFF_STATE(state)) {
+		/* Perform the common cluster specific operations */
+		plat_cluster_pwron_common(cpu, state, plat_power_state[cpu]);
+	}
+
+	/* Perform the common CPU specific operations */
+	plat_cpu_pwron_common(cpu, state, plat_power_state[cpu]);
+
+	plat_mt_pm_invoke_no_check(pwr_reflect, cpu, state);
+}
+
+static int plat_validate_power_state(unsigned int power_state,
+					psci_power_state_t *req_state)
+{
+	unsigned int pstate = psci_get_pstate_type(power_state);
+	unsigned int aff_lvl = psci_get_pstate_pwrlvl(power_state);
+	unsigned int cpu = plat_my_core_pos();
+
+	if (aff_lvl > PLAT_MAX_PWR_LVL) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	if (pstate == PSTATE_TYPE_STANDBY) {
+		req_state->pwr_domain_state[0] = PLAT_MAX_RET_STATE;
+	} else {
+		unsigned int i;
+		unsigned int pstate_id = psci_get_pstate_id(power_state);
+		plat_local_state_t s = MTK_LOCAL_STATE_OFF;
+
+		/* Use pstate_id to be power domain state */
+		if (pstate_id > s) {
+			s = (plat_local_state_t)pstate_id;
+		}
+
+		for (i = 0U; i <= aff_lvl; i++) {
+			req_state->pwr_domain_state[i] = s;
+		}
+	}
+
+	plat_power_state[cpu] = power_state;
+	return PSCI_E_SUCCESS;
+}
+
+static void plat_get_sys_suspend_power_state(psci_power_state_t *req_state)
+{
+	unsigned int lv;
+	unsigned int cpu = plat_my_core_pos();
+
+	for (lv = PSCI_CPU_PWR_LVL; lv <= PLAT_MAX_PWR_LVL; lv++) {
+		req_state->pwr_domain_state[lv] = PLAT_MAX_OFF_STATE;
+	}
+
+	plat_power_state[cpu] =
+			psci_make_powerstate(
+				MT_PLAT_PWR_STATE_SYSTEM_SUSPEND,
+				PSTATE_TYPE_POWERDOWN, PLAT_MAX_PWR_LVL);
+
+	flush_dcache_range((uintptr_t)
+			&plat_power_state[cpu],
+			sizeof(plat_power_state[cpu]));
+}
+
+/*******************************************************************************
+ * MTK handlers to shutdown/reboot the system
+ ******************************************************************************/
+static void __dead2 plat_mtk_system_reset(void)
+{
+	struct bl_aux_gpio_info *gpio_reset = plat_get_mtk_gpio_reset();
+
+	INFO("MTK System Reset\n");
+
+	gpio_set_value(gpio_reset->index, gpio_reset->polarity);
+
+	wfi();
+	ERROR("MTK System Reset: operation not handled.\n");
+	panic();
+}
+
+static void __dead2 plat_mtk_system_off(void)
+{
+	INFO("MTK System Off\n");
+
+	rtc_power_off_sequence();
+	pmic_power_off();
+
+	wfi();
+	ERROR("MTK System Off: operation not handled.\n");
+	panic();
+}
+
+static const plat_psci_ops_t plat_psci_ops = {
+	.system_reset			= plat_mtk_system_reset,
+	.system_off			= plat_mtk_system_off,
+	.cpu_standby			= plat_cpu_standby,
+	.pwr_domain_on			= plat_power_domain_on,
+	.pwr_domain_on_finish		= plat_power_domain_on_finish,
+	.pwr_domain_off			= plat_power_domain_off,
+	.pwr_domain_suspend		= plat_power_domain_suspend,
+	.pwr_domain_suspend_finish	= plat_power_domain_suspend_finish,
+	.validate_power_state		= plat_validate_power_state,
+	.get_sys_suspend_power_state	= plat_get_sys_suspend_power_state
+};
+
+int plat_setup_psci_ops(uintptr_t sec_entrypoint,
+			const plat_psci_ops_t **psci_ops)
+{
+	*psci_ops = &plat_psci_ops;
+	secure_entrypoint = sec_entrypoint;
+
+	/*
+	 * init the warm reset config for boot CPU
+	 * reset arch as AARCH64
+	 * reset addr as function bl31_warm_entrypoint()
+	 */
+	mcucfg_init_archstate(0U, 0U, true);
+	mcucfg_set_bootaddr(0U, 0U, secure_entrypoint);
+
+	spmc_init();
+	plat_mt_pm = mt_plat_cpu_pm_init();
+
+	return 0;
+}
diff --git a/plat/mediatek/mt8195/plat_sip_calls.c b/plat/mediatek/mt8195/plat_sip_calls.c
new file mode 100644
index 0000000..ddc7502
--- /dev/null
+++ b/plat/mediatek/mt8195/plat_sip_calls.c
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2020, MediaTek Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <mt_dp.h>
+#include <mt_spm.h>
+#include <mt_spm_vcorefs.h>
+#include <mtk_sip_svc.h>
+#include <plat_dfd.h>
+#include "plat_sip_calls.h"
+
+uintptr_t mediatek_plat_sip_handler(uint32_t smc_fid,
+				u_register_t x1,
+				u_register_t x2,
+				u_register_t x3,
+				u_register_t x4,
+				void *cookie,
+				void *handle,
+				u_register_t flags)
+{
+	int32_t ret;
+	uint32_t ret_val;
+
+	switch (smc_fid) {
+	case MTK_SIP_DP_CONTROL_AARCH32:
+	case MTK_SIP_DP_CONTROL_AARCH64:
+		ret = dp_secure_handler(x1, x2, &ret_val);
+		SMC_RET2(handle, ret, ret_val);
+		break;
+	case MTK_SIP_VCORE_CONTROL_ARCH32:
+	case MTK_SIP_VCORE_CONTROL_ARCH64:
+		ret = spm_vcorefs_v2_args(x1, x2, x3, &x4);
+		SMC_RET2(handle, ret, x4);
+		break;
+	case MTK_SIP_KERNEL_DFD_AARCH32:
+	case MTK_SIP_KERNEL_DFD_AARCH64:
+		ret = dfd_smc_dispatcher(x1, x2, x3, x4);
+		SMC_RET1(handle, ret);
+		break;
+	default:
+		ERROR("%s: unhandled SMC (0x%x)\n", __func__, smc_fid);
+		break;
+	}
+
+	SMC_RET1(handle, SMC_UNK);
+}
diff --git a/plat/mediatek/mt8195/plat_topology.c b/plat/mediatek/mt8195/plat_topology.c
new file mode 100644
index 0000000..bc95c64
--- /dev/null
+++ b/plat/mediatek/mt8195/plat_topology.c
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <lib/psci/psci.h>
+
+#include <plat_helpers.h>
+#include <platform_def.h>
+
+const unsigned char mtk_power_domain_tree_desc[] = {
+	/* Number of root nodes */
+	PLATFORM_SYSTEM_COUNT,
+	/* Number of children for the root node */
+	PLATFORM_MCUSYS_COUNT,
+	/* Number of children for the mcusys node */
+	PLATFORM_CLUSTER_COUNT,
+	/* Number of children for the first cluster node */
+	PLATFORM_CLUSTER0_CORE_COUNT,
+};
+
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	return mtk_power_domain_tree_desc;
+}
+
+/*******************************************************************************
+ * This function implements a part of the critical interface between the psci
+ * generic layer and the platform that allows the former to query the platform
+ * to convert an MPIDR to a unique linear index. An error code (-1) is returned
+ * in case the MPIDR is invalid.
+ ******************************************************************************/
+int plat_core_pos_by_mpidr(u_register_t mpidr)
+{
+	unsigned int cluster_id, cpu_id;
+
+	if ((read_mpidr() & MPIDR_MT_MASK) != 0) {
+		/* ARMv8.2 arch */
+		if ((mpidr & (MPIDR_AFFLVL_MASK << MPIDR_AFF0_SHIFT)) != 0) {
+			return -1;
+		}
+		return plat_mediatek_calc_core_pos(mpidr);
+	}
+
+	mpidr &= MPIDR_AFFINITY_MASK;
+
+	if ((mpidr & ~(MPIDR_CLUSTER_MASK | MPIDR_CPU_MASK)) != 0) {
+		return -1;
+	}
+
+	cluster_id = (mpidr >> MPIDR_AFF1_SHIFT) & MPIDR_AFFLVL_MASK;
+	cpu_id = (mpidr >> MPIDR_AFF0_SHIFT) & MPIDR_AFFLVL_MASK;
+
+	if (cluster_id >= PLATFORM_CLUSTER_COUNT) {
+		return -1;
+	}
+
+	/*
+	 * Validate cpu_id by checking whether it represents a CPU in
+	 * one of the two clusters present on the platform.
+	 */
+	if (cpu_id >= PLATFORM_MAX_CPUS_PER_CLUSTER) {
+		return -1;
+	}
+
+	return (cpu_id + (cluster_id * 8));
+}
diff --git a/plat/mediatek/mt8195/platform.mk b/plat/mediatek/mt8195/platform.mk
new file mode 100644
index 0000000..ef7ff81
--- /dev/null
+++ b/plat/mediatek/mt8195/platform.mk
@@ -0,0 +1,97 @@
+#
+# Copyright (c) 2021, MediaTek Inc. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+MTK_PLAT     := plat/mediatek
+MTK_PLAT_SOC := ${MTK_PLAT}/${PLAT}
+
+PLAT_INCLUDES := -I${MTK_PLAT}/common/                            \
+                 -I${MTK_PLAT}/common/drivers/gic600/             \
+                 -I${MTK_PLAT}/common/drivers/gpio/               \
+                 -I${MTK_PLAT}/common/drivers/rtc/                \
+                 -I${MTK_PLAT}/common/drivers/timer/              \
+                 -I${MTK_PLAT}/common/drivers/uart/               \
+                 -I${MTK_PLAT}/common/lpm/                        \
+                 -I${MTK_PLAT_SOC}/drivers/dcm                    \
+                 -I${MTK_PLAT_SOC}/drivers/dfd                    \
+                 -I${MTK_PLAT_SOC}/drivers/dp/                    \
+                 -I${MTK_PLAT_SOC}/drivers/emi_mpu/               \
+                 -I${MTK_PLAT_SOC}/drivers/gpio/                  \
+                 -I${MTK_PLAT_SOC}/drivers/mcdi/                  \
+                 -I${MTK_PLAT_SOC}/drivers/pmic/                  \
+                 -I${MTK_PLAT_SOC}/drivers/spmc/                  \
+                 -I${MTK_PLAT_SOC}/drivers/ptp3/                   \
+                 -I${MTK_PLAT_SOC}/include/
+
+GICV3_SUPPORT_GIC600        :=      1
+include drivers/arm/gic/v3/gicv3.mk
+include lib/xlat_tables_v2/xlat_tables.mk
+
+PLAT_BL_COMMON_SOURCES := ${GICV3_SOURCES}                              \
+                          ${XLAT_TABLES_LIB_SRCS}                       \
+                          plat/common/aarch64/crash_console_helpers.S   \
+                          plat/common/plat_psci_common.c
+
+
+BL31_SOURCES += common/desc_image_load.c                              \
+                drivers/delay_timer/delay_timer.c                     \
+                drivers/gpio/gpio.c                                   \
+                drivers/delay_timer/generic_delay_timer.c             \
+                drivers/ti/uart/aarch64/16550_console.S               \
+                lib/bl_aux_params/bl_aux_params.c                     \
+                lib/cpus/aarch64/cortex_a55.S                         \
+                lib/cpus/aarch64/cortex_a78.S                         \
+                plat/common/plat_gicv3.c                              \
+                ${MTK_PLAT}/common/drivers/gic600/mt_gic_v3.c         \
+                ${MTK_PLAT}/common/drivers/gpio/mtgpio_common.c       \
+                ${MTK_PLAT}/common/drivers/pmic_wrap/pmic_wrap_init_v2.c \
+                ${MTK_PLAT}/common/drivers/rtc/rtc_common.c           \
+                ${MTK_PLAT}/common/drivers/rtc/rtc_mt6359p.c          \
+                ${MTK_PLAT}/common/drivers/timer/mt_timer.c           \
+		${MTK_PLAT}/common/drivers/uart/uart.c                \
+		${MTK_PLAT}/common/lpm/mt_lp_rm.c                     \
+                ${MTK_PLAT}/common/mtk_cirq.c                         \
+                ${MTK_PLAT}/common/mtk_plat_common.c                  \
+                ${MTK_PLAT}/common/mtk_sip_svc.c                      \
+                ${MTK_PLAT}/common/params_setup.c                     \
+                ${MTK_PLAT_SOC}/aarch64/platform_common.c             \
+                ${MTK_PLAT_SOC}/aarch64/plat_helpers.S                \
+                ${MTK_PLAT_SOC}/bl31_plat_setup.c                     \
+                ${MTK_PLAT_SOC}/drivers/dcm/mtk_dcm.c                 \
+                ${MTK_PLAT_SOC}/drivers/dcm/mtk_dcm_utils.c           \
+                ${MTK_PLAT_SOC}/drivers/dfd/plat_dfd.c                \
+                ${MTK_PLAT_SOC}/drivers/dp/mt_dp.c                    \
+                ${MTK_PLAT_SOC}/drivers/emi_mpu/emi_mpu.c             \
+                ${MTK_PLAT_SOC}/drivers/gpio/mtgpio.c                 \
+                ${MTK_PLAT_SOC}/drivers/mcdi/mt_cpu_pm.c              \
+                ${MTK_PLAT_SOC}/drivers/mcdi/mt_cpu_pm_cpc.c          \
+                ${MTK_PLAT_SOC}/drivers/mcdi/mt_mcdi.c                \
+		${MTK_PLAT_SOC}/drivers/mcdi/mt_lp_irqremain.c        \
+                ${MTK_PLAT_SOC}/drivers/gpio/mtgpio.c                 \
+                ${MTK_PLAT_SOC}/drivers/pmic/pmic.c                   \
+                ${MTK_PLAT_SOC}/drivers/ptp3/mtk_ptp3_main.c          \
+                ${MTK_PLAT_SOC}/drivers/spmc/mtspmc.c                 \
+                ${MTK_PLAT_SOC}/plat_pm.c                             \
+                ${MTK_PLAT_SOC}/plat_sip_calls.c                      \
+                ${MTK_PLAT_SOC}/plat_topology.c
+
+# Build SPM drivers
+include ${MTK_PLAT_SOC}/drivers/spm/build.mk
+
+# Configs for A78 and A55
+HW_ASSISTED_COHERENCY := 1
+USE_COHERENT_MEM := 0
+CTX_INCLUDE_AARCH32_REGS := 0
+ERRATA_A55_1530923 := 1
+
+# indicate the reset vector address can be programmed
+PROGRAMMABLE_RESET_ADDRESS := 1
+
+COLD_BOOT_SINGLE_CPU := 1
+
+MACH_MT8195 := 1
+$(eval $(call add_define,MACH_MT8195))
+
+include lib/coreboot/coreboot.mk
diff --git a/plat/nvidia/tegra/common/tegra_bl31_setup.c b/plat/nvidia/tegra/common/tegra_bl31_setup.c
index cb4886f..6a3eae0 100644
--- a/plat/nvidia/tegra/common/tegra_bl31_setup.c
+++ b/plat/nvidia/tegra/common/tegra_bl31_setup.c
@@ -7,6 +7,7 @@
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
 #include <stddef.h>
 #include <string.h>
 
@@ -336,7 +337,7 @@
 	 * Sanity check the input values
 	 */
 	if ((base == 0U) || (size_in_bytes == 0U)) {
-		ERROR("NS address 0x%llx (%lld bytes) is invalid\n",
+		ERROR("NS address 0x%" PRIx64 " (%" PRId64 " bytes) is invalid\n",
 			base, size_in_bytes);
 		return -EINVAL;
 	}
@@ -347,7 +348,7 @@
 	if ((base < TEGRA_DRAM_BASE) || (base >= TEGRA_DRAM_END) ||
 	    (end > TEGRA_DRAM_END)) {
 
-		ERROR("NS address 0x%llx is out-of-bounds!\n", base);
+		ERROR("NS address 0x%" PRIx64 " is out-of-bounds!\n", base);
 		return -EFAULT;
 	}
 
@@ -356,7 +357,7 @@
 	 * to check if the NS DRAM range overlaps the TZDRAM aperture.
 	 */
 	if ((base < (uint64_t)TZDRAM_END) && (end > tegra_bl31_phys_base)) {
-		ERROR("NS address 0x%llx overlaps TZDRAM!\n", base);
+		ERROR("NS address 0x%" PRIx64 " overlaps TZDRAM!\n", base);
 		return -ENOTSUP;
 	}
 
diff --git a/plat/nvidia/tegra/common/tegra_platform.c b/plat/nvidia/tegra/common/tegra_platform.c
index 7c73e8f..f3aa3ea 100644
--- a/plat/nvidia/tegra/common/tegra_platform.c
+++ b/plat/nvidia/tegra/common/tegra_platform.c
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -82,13 +82,6 @@
 	return (tegra_get_chipid() >> PRE_SI_PLATFORM_SHIFT) & PRE_SI_PLATFORM_MASK;
 }
 
-bool tegra_chipid_is_t132(void)
-{
-	uint32_t chip_id = ((tegra_get_chipid() >> CHIP_ID_SHIFT) & CHIP_ID_MASK);
-
-	return (chip_id == TEGRA_CHIPID_TEGRA13);
-}
-
 bool tegra_chipid_is_t186(void)
 {
 	uint32_t chip_id = (tegra_get_chipid() >> CHIP_ID_SHIFT) & CHIP_ID_MASK;
@@ -280,9 +273,9 @@
 int32_t plat_get_soc_version(void)
 {
 	uint32_t chip_id = ((tegra_get_chipid() >> CHIP_ID_SHIFT) & CHIP_ID_MASK);
-	uint32_t manfid = (JEDEC_NVIDIA_BKID << 24) | (JEDEC_NVIDIA_MFID << 16);
+	uint32_t manfid = SOC_ID_SET_JEP_106(JEDEC_NVIDIA_BKID, JEDEC_NVIDIA_MFID);
 
-	return (int32_t)(manfid | (chip_id & 0xFFFF));
+	return (int32_t)(manfid | (chip_id & SOC_ID_IMPL_DEF_MASK));
 }
 
 /*
@@ -293,18 +286,19 @@
  */
 int32_t plat_get_soc_revision(void)
 {
-	return (int32_t)((tegra_get_chipid_major() << 8) | tegra_get_chipid_minor());
+	return (int32_t)(((tegra_get_chipid_major() << 8) | tegra_get_chipid_minor()) &
+			 SOC_ID_REV_MASK);
 }
 
 /*****************************************************************************
- * plat_smccc_feature_available() - This function checks whether SMCCC feature
+ * plat_is_smccc_feature_available() - This function checks whether SMCCC feature
  *                                  is availabile for the platform or not.
  * @fid: SMCCC function id
  *
  * Return SMC_ARCH_CALL_SUCCESS if SMCCC feature is available and
  * SMC_ARCH_CALL_NOT_SUPPORTED otherwise.
  *****************************************************************************/
-int32_t plat_smccc_feature_available(u_register_t fid)
+int32_t plat_is_smccc_feature_available(u_register_t fid)
 {
 	switch (fid) {
 	case SMCCC_ARCH_SOC_ID:
diff --git a/plat/nvidia/tegra/include/t132/tegra_def.h b/plat/nvidia/tegra/include/t132/tegra_def.h
deleted file mode 100644
index 6b87655..0000000
--- a/plat/nvidia/tegra/include/t132/tegra_def.h
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef TEGRA_DEF_H
-#define TEGRA_DEF_H
-
-#include <lib/utils_def.h>
-
-/*******************************************************************************
- * Platform BL31 specific defines.
- ******************************************************************************/
-#define BL31_SIZE			U(0x40000)
-
-/*******************************************************************************
- * This value is used by the PSCI implementation during the `SYSTEM_SUSPEND`
- * call as the `state-id` field in the 'power state' parameter.
- ******************************************************************************/
-#define PSTATE_ID_SOC_POWERDN	U(0xD)
-
-/*******************************************************************************
- * Platform power states (used by PSCI framework)
- *
- * - PLAT_MAX_RET_STATE should be less than lowest PSTATE_ID
- * - PLAT_MAX_OFF_STATE should be greater than the highest PSTATE_ID
- ******************************************************************************/
-#define PLAT_MAX_RET_STATE		U(1)
-#define PLAT_MAX_OFF_STATE		(PSTATE_ID_SOC_POWERDN + U(1))
-
-/*******************************************************************************
- * Chip specific page table and MMU setup constants
- ******************************************************************************/
-#define PLAT_PHY_ADDR_SPACE_SIZE	(ULL(1) << 35)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(ULL(1) << 35)
-
-/*******************************************************************************
- * GIC memory map
- ******************************************************************************/
-#define TEGRA_GICD_BASE			U(0x50041000)
-#define TEGRA_GICC_BASE			U(0x50042000)
-
-/*******************************************************************************
- * Tegra micro-seconds timer constants
- ******************************************************************************/
-#define TEGRA_TMRUS_BASE		U(0x60005010)
-#define TEGRA_TMRUS_SIZE		U(0x1000)
-
-/*******************************************************************************
- * Tegra Clock and Reset Controller constants
- ******************************************************************************/
-#define TEGRA_CAR_RESET_BASE		U(0x60006000)
-#define TEGRA_GPU_RESET_REG_OFFSET	U(0x28C)
-#define TEGRA_GPU_RESET_GPU_SET_OFFSET	U(0x290)
-#define  GPU_RESET_BIT			(U(1) << 24)
-#define  GPU_SET_BIT			(U(1) << 24)
-
-/*******************************************************************************
- * Tegra Flow Controller constants
- ******************************************************************************/
-#define TEGRA_FLOWCTRL_BASE		U(0x60007000)
-
-/*******************************************************************************
- * Tegra Secure Boot Controller constants
- ******************************************************************************/
-#define TEGRA_SB_BASE			U(0x6000C200)
-
-/*******************************************************************************
- * Tegra Exception Vectors constants
- ******************************************************************************/
-#define TEGRA_EVP_BASE			U(0x6000F000)
-
-/*******************************************************************************
- * Tegra Miscellaneous register constants
- ******************************************************************************/
-#define TEGRA_MISC_BASE			U(0x70000000)
-#define  HARDWARE_REVISION_OFFSET	U(0x804)
-
-/*******************************************************************************
- * Tegra UART controller base addresses
- ******************************************************************************/
-#define TEGRA_UARTA_BASE		U(0x70006000)
-#define TEGRA_UARTB_BASE		U(0x70006040)
-#define TEGRA_UARTC_BASE		U(0x70006200)
-#define TEGRA_UARTD_BASE		U(0x70006300)
-#define TEGRA_UARTE_BASE		U(0x70006400)
-
-/*******************************************************************************
- * Tegra Power Mgmt Controller constants
- ******************************************************************************/
-#define TEGRA_PMC_BASE			U(0x7000E400)
-
-/*******************************************************************************
- * Tegra Memory Controller constants
- ******************************************************************************/
-#define TEGRA_MC_BASE			U(0x70019000)
-
-/* Memory Controller Interrupt Status */
-#define MC_INTSTATUS			0x00U
-
-/* TZDRAM carveout configuration registers */
-#define MC_SECURITY_CFG0_0		U(0x70)
-#define MC_SECURITY_CFG1_0		U(0x74)
-#define MC_SECURITY_CFG3_0		U(0x9BC)
-
-/* Video Memory carveout configuration registers */
-#define MC_VIDEO_PROTECT_BASE_HI	U(0x978)
-#define MC_VIDEO_PROTECT_BASE_LO	U(0x648)
-#define MC_VIDEO_PROTECT_SIZE_MB	U(0x64c)
-#define MC_VIDEO_PROTECT_REG_CTRL	U(0x650)
-#define MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED	U(3)
-
-/*******************************************************************************
- * Tegra TZRAM constants
- ******************************************************************************/
-#define TEGRA_TZRAM_BASE		U(0x7C010000)
-#define TEGRA_TZRAM_SIZE		U(0x10000)
-
-/*******************************************************************************
- * Tegra DRAM memory base address
- ******************************************************************************/
-#define TEGRA_DRAM_BASE			ULL(0x80000000)
-#define TEGRA_DRAM_END			ULL(0x27FFFFFFF)
-
-#endif /* TEGRA_DEF_H */
diff --git a/plat/nvidia/tegra/include/tegra_platform.h b/plat/nvidia/tegra/include/tegra_platform.h
index b8297fd..ab51dfe 100644
--- a/plat/nvidia/tegra/include/tegra_platform.h
+++ b/plat/nvidia/tegra/include/tegra_platform.h
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
+ * Copyright (c) 2020-2021, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -49,7 +49,6 @@
 /*
  * Tegra chip ID identifiers
  */
-bool tegra_chipid_is_t132(void);
 bool tegra_chipid_is_t186(void);
 bool tegra_chipid_is_t210(void);
 bool tegra_chipid_is_t210_b01(void);
diff --git a/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c
deleted file mode 100644
index 0e2edf0..0000000
--- a/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c
+++ /dev/null
@@ -1,208 +0,0 @@
-/*
- * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <platform_def.h>
-
-#include <arch.h>
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <drivers/delay_timer.h>
-#include <denver.h>
-#include <lib/mmio.h>
-#include <lib/psci/psci.h>
-
-#include <flowctrl.h>
-#include <pmc.h>
-#include <tegra_def.h>
-#include <tegra_private.h>
-
-/*
- * Register used to clear CPU reset signals. Each CPU has two reset
- * signals: CPU reset (3:0) and Core reset (19:16)
- */
-#define CPU_CMPLX_RESET_CLR		0x344
-#define CPU_CORE_RESET_MASK		0x10001
-
-/* Clock and Reset controller registers for system clock's settings */
-#define SCLK_RATE			0x30
-#define SCLK_BURST_POLICY		0x28
-#define SCLK_BURST_POLICY_DEFAULT	0x10000000
-
-static int cpu_powergate_mask[PLATFORM_MAX_CPUS_PER_CLUSTER];
-
-plat_local_state_t tegra_soc_get_target_pwr_state(uint32_t lvl,
-					     const plat_local_state_t *states,
-					     uint32_t ncpu)
-{
-	plat_local_state_t target = PLAT_MAX_OFF_STATE, temp;
-	uint32_t num_cpu = ncpu;
-	const plat_local_state_t *local_state = states;
-
-	(void)lvl;
-
-	assert(ncpu != 0U);
-
-	do {
-		temp = *local_state;
-		if ((temp < target)) {
-			target = temp;
-		}
-		--num_cpu;
-		local_state++;
-	} while (num_cpu != 0U);
-
-	return target;
-}
-
-int32_t tegra_soc_validate_power_state(unsigned int power_state,
-					psci_power_state_t *req_state)
-{
-	int state_id = psci_get_pstate_id(power_state);
-	int cpu = read_mpidr() & MPIDR_CPU_MASK;
-
-	/*
-	 * Sanity check the requested state id, power level and CPU number.
-	 * Currently T132 only supports SYSTEM_SUSPEND on last standing CPU
-	 * i.e. CPU 0
-	 */
-	if ((state_id != PSTATE_ID_SOC_POWERDN) || (cpu != 0)) {
-		ERROR("unsupported state id @ power level\n");
-		return PSCI_E_INVALID_PARAMS;
-	}
-
-	/* Set lower power states to PLAT_MAX_OFF_STATE */
-	for (uint32_t i = MPIDR_AFFLVL0; i < PLAT_MAX_PWR_LVL; i++)
-		req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
-
-	/* Set the SYSTEM_SUSPEND state-id */
-	req_state->pwr_domain_state[PLAT_MAX_PWR_LVL] =
-		PSTATE_ID_SOC_POWERDN;
-
-	return PSCI_E_SUCCESS;
-}
-
-int tegra_soc_pwr_domain_on(u_register_t mpidr)
-{
-	int cpu = mpidr & MPIDR_CPU_MASK;
-	uint32_t mask = CPU_CORE_RESET_MASK << cpu;
-
-	if (cpu_powergate_mask[cpu] == 0) {
-
-		/* Deassert CPU reset signals */
-		mmio_write_32(TEGRA_CAR_RESET_BASE + CPU_CMPLX_RESET_CLR, mask);
-
-		/* Power on CPU using PMC */
-		tegra_pmc_cpu_on(cpu);
-
-		/* Fill in the CPU powergate mask */
-		cpu_powergate_mask[cpu] = 1;
-
-	} else {
-		/* Power on CPU using Flow Controller */
-		tegra_fc_cpu_on(cpu);
-	}
-
-	return PSCI_E_SUCCESS;
-}
-
-int tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state)
-{
-	/*
-	 * Lock scratch registers which hold the CPU vectors
-	 */
-	tegra_pmc_lock_cpu_vectors();
-
-	return PSCI_E_SUCCESS;
-}
-
-int tegra_soc_pwr_domain_off(const psci_power_state_t *target_state)
-{
-	uint64_t val;
-
-	tegra_fc_cpu_off(read_mpidr() & MPIDR_CPU_MASK);
-
-	/* Disable DCO operations */
-	denver_disable_dco();
-
-	/* Power down the CPU */
-	val = read_actlr_el1() & ~ACTLR_EL1_PMSTATE_MASK;
-	write_actlr_el1(val | DENVER_CPU_STATE_POWER_DOWN);
-
-	return PSCI_E_SUCCESS;
-}
-
-int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state)
-{
-	(void)cpu_state;
-	return PSCI_E_SUCCESS;
-}
-
-int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state)
-{
-	uint64_t val;
-
-#if ENABLE_ASSERTIONS
-	int cpu = read_mpidr() & MPIDR_CPU_MASK;
-
-	/* SYSTEM_SUSPEND only on CPU0 */
-	assert(cpu == 0);
-#endif
-
-	/* Allow restarting CPU #1 using PMC on suspend exit */
-	cpu_powergate_mask[1] = 0;
-
-	/* Program FC to enter suspend state */
-	tegra_fc_cpu_powerdn(read_mpidr());
-
-	/* Disable DCO operations */
-	denver_disable_dco();
-
-	/* Program the suspend state ID */
-	val = read_actlr_el1() & ~ACTLR_EL1_PMSTATE_MASK;
-	write_actlr_el1(val | target_state->pwr_domain_state[PLAT_MAX_PWR_LVL]);
-
-	return PSCI_E_SUCCESS;
-}
-
-int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state)
-{
-	return PSCI_E_NOT_SUPPORTED;
-}
-
-int tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state)
-{
-	return PSCI_E_SUCCESS;
-}
-
-int tegra_soc_prepare_system_reset(void)
-{
-	/*
-	 * Set System Clock (SCLK) to POR default so that the clock source
-	 * for the PMC APB clock would not be changed due to system reset.
-	 */
-	mmio_write_32((uintptr_t)TEGRA_CAR_RESET_BASE + SCLK_BURST_POLICY,
-		       SCLK_BURST_POLICY_DEFAULT);
-	mmio_write_32((uintptr_t)TEGRA_CAR_RESET_BASE + SCLK_RATE, 0);
-
-	/* Wait 1 ms to make sure clock source/device logic is stabilized. */
-	mdelay(1);
-
-	/*
-	 * Program the PMC in order to restart the system.
-	 */
-	tegra_pmc_system_reset();
-
-	return PSCI_E_SUCCESS;
-}
-
-__dead2 void tegra_soc_prepare_system_off(void)
-{
-	ERROR("Tegra System Off: operation not handled.\n");
-	panic();
-}
diff --git a/plat/nvidia/tegra/soc/t132/plat_secondary.c b/plat/nvidia/tegra/soc/t132/plat_secondary.c
deleted file mode 100644
index f46ad3b..0000000
--- a/plat/nvidia/tegra/soc/t132/plat_secondary.c
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2015, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <arch_helpers.h>
-#include <common/debug.h>
-#include <denver.h>
-#include <lib/mmio.h>
-#include <lib/psci/psci.h>
-#include <plat/common/platform.h>
-
-#include <pmc.h>
-#include <tegra_def.h>
-
-#define SB_CSR				0x0
-#define  SB_CSR_NS_RST_VEC_WR_DIS	(1 << 1)
-
-/* AARCH64 CPU reset vector */
-#define SB_AA64_RESET_LOW		0x30	/* width = 31:0 */
-#define SB_AA64_RESET_HI		0x34	/* width = 11:0 */
-
-/* AARCH32 CPU reset vector */
-#define EVP_CPU_RESET_VECTOR		0x100
-
-extern void tegra_secure_entrypoint(void);
-
-/*
- * For T132, CPUs reset to AARCH32, so the reset vector is first
- * armv8_trampoline which does a warm reset to AARCH64 and starts
- * execution at the address in SB_AA64_RESET_LOW/SB_AA64_RESET_HI.
- */
-__aligned(8) const uint32_t armv8_trampoline[] = {
-	0xE3A00003,		/* mov	r0, #3 */
-	0xEE0C0F50,		/* mcr	p15, 0, r0, c12, c0, 2 */
-	0xEAFFFFFE,		/* b	. */
-};
-
-/*******************************************************************************
- * Setup secondary CPU vectors
- ******************************************************************************/
-void plat_secondary_setup(void)
-{
-	uint32_t val;
-	uint64_t reset_addr = (uint64_t)tegra_secure_entrypoint;
-
-	/*
-	 * For T132, CPUs reset to AARCH32, so the reset vector is first
-	 * armv8_trampoline, which does a warm reset to AARCH64 and starts
-	 * execution at the address in SCRATCH34/SCRATCH35.
-	 */
-	INFO("Setting up T132 CPU boot\n");
-
-	/* initial AARCH32 reset address */
-	tegra_pmc_write_32(PMC_SECURE_SCRATCH22,
-		(unsigned long)&armv8_trampoline);
-
-	/* set AARCH32 exception vector (read to flush) */
-	mmio_write_32(TEGRA_EVP_BASE + EVP_CPU_RESET_VECTOR,
-		(unsigned long)&armv8_trampoline);
-	val = mmio_read_32(TEGRA_EVP_BASE + EVP_CPU_RESET_VECTOR);
-
-	/* setup secondary CPU vector */
-	mmio_write_32(TEGRA_SB_BASE + SB_AA64_RESET_LOW,
-			(reset_addr & 0xFFFFFFFF) | 1);
-	val = reset_addr >> 32;
-	mmio_write_32(TEGRA_SB_BASE + SB_AA64_RESET_HI, val & 0x7FF);
-
-	/* configure PMC */
-	tegra_pmc_cpu_setup(reset_addr);
-	tegra_pmc_lock_cpu_vectors();
-}
diff --git a/plat/nvidia/tegra/soc/t132/plat_setup.c b/plat/nvidia/tegra/soc/t132/plat_setup.c
deleted file mode 100644
index 49e8b5d..0000000
--- a/plat/nvidia/tegra/soc/t132/plat_setup.c
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch_helpers.h>
-#include <assert.h>
-#include <common/bl_common.h>
-#include <drivers/console.h>
-#include <lib/xlat_tables/xlat_tables_v2.h>
-#include <memctrl.h>
-#include <plat/common/platform.h>
-#include <tegra_def.h>
-#include <tegra_platform.h>
-#include <tegra_private.h>
-
-/* sets of MMIO ranges setup */
-#define MMIO_RANGE_0_ADDR	0x50000000
-#define MMIO_RANGE_1_ADDR	0x60000000
-#define MMIO_RANGE_2_ADDR	0x70000000
-#define MMIO_RANGE_SIZE		0x200000
-
-/*
- * Table of regions to map using the MMU.
- */
-static const mmap_region_t tegra_mmap[] = {
-	MAP_REGION_FLAT(MMIO_RANGE_0_ADDR, MMIO_RANGE_SIZE,
-			MT_DEVICE | MT_RW | MT_SECURE),
-	MAP_REGION_FLAT(MMIO_RANGE_1_ADDR, MMIO_RANGE_SIZE,
-			MT_DEVICE | MT_RW | MT_SECURE),
-	MAP_REGION_FLAT(MMIO_RANGE_2_ADDR, MMIO_RANGE_SIZE,
-			MT_DEVICE | MT_RW | MT_SECURE),
-	{0}
-};
-
-/*******************************************************************************
- * Set up the pagetables as per the platform memory map & initialize the MMU
- ******************************************************************************/
-const mmap_region_t *plat_get_mmio_map(void)
-{
-	/* MMIO space */
-	return tegra_mmap;
-}
-
-/*******************************************************************************
- * The Tegra power domain tree has a single system level power domain i.e. a
- * single root node. The first entry in the power domain descriptor specifies
- * the number of power domains at the highest power level.
- *******************************************************************************
- */
-const unsigned char tegra_power_domain_tree_desc[] = {
-	/* No of root nodes */
-	1,
-	/* No of clusters */
-	PLATFORM_CLUSTER_COUNT,
-	/* No of CPU cores */
-	PLATFORM_CORE_COUNT,
-};
-
-/*******************************************************************************
- * This function returns the Tegra default topology tree information.
- ******************************************************************************/
-const unsigned char *plat_get_power_domain_tree_desc(void)
-{
-	return tegra_power_domain_tree_desc;
-}
-
-unsigned int plat_get_syscnt_freq2(void)
-{
-	return 12000000;
-}
-
-/*******************************************************************************
- * Maximum supported UART controllers
- ******************************************************************************/
-#define TEGRA132_MAX_UART_PORTS		5
-
-/*******************************************************************************
- * This variable holds the UART port base addresses
- ******************************************************************************/
-static uint32_t tegra132_uart_addresses[TEGRA132_MAX_UART_PORTS + 1] = {
-	0,	/* undefined - treated as an error case */
-	TEGRA_UARTA_BASE,
-	TEGRA_UARTB_BASE,
-	TEGRA_UARTC_BASE,
-	TEGRA_UARTD_BASE,
-	TEGRA_UARTE_BASE,
-};
-
-/*******************************************************************************
- * Enable console corresponding to the console ID
- ******************************************************************************/
-void plat_enable_console(int32_t id)
-{
-	static console_t uart_console;
-	uint32_t console_clock;
-
-	if ((id > 0) && (id < TEGRA132_MAX_UART_PORTS)) {
-		/*
-		 * Reference clock used by the FPGAs is a lot slower.
-		 */
-		if (tegra_platform_is_fpga()) {
-			console_clock = TEGRA_BOOT_UART_CLK_13_MHZ;
-		} else {
-			console_clock = TEGRA_BOOT_UART_CLK_408_MHZ;
-		}
-
-		(void)console_16550_register(tegra132_uart_addresses[id],
-					     console_clock,
-					     TEGRA_CONSOLE_BAUDRATE,
-					     &uart_console);
-		console_set_scope(&uart_console, CONSOLE_FLAG_BOOT |
-			CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH);
-	}
-}
-
-/*******************************************************************************
- * Initialize the GIC and SGIs
- ******************************************************************************/
-void plat_gic_setup(void)
-{
-	tegra_gic_setup(NULL, 0);
-	tegra_gic_init();
-}
-
-/*******************************************************************************
- * Return pointer to the BL31 params from previous bootloader
- ******************************************************************************/
-struct tegra_bl31_params *plat_get_bl31_params(void)
-{
-	return NULL;
-}
-
-/*******************************************************************************
- * Return pointer to the BL31 platform params from previous bootloader
- ******************************************************************************/
-plat_params_from_bl2_t *plat_get_bl31_plat_params(void)
-{
-	return NULL;
-}
-
-/*******************************************************************************
- * Handler for early platform setup
- ******************************************************************************/
-void plat_early_platform_setup(void)
-{
-	plat_params_from_bl2_t *plat_params = bl31_get_plat_params();
-
-	/* Verify chip id is t132 */
-	assert(tegra_chipid_is_t132());
-
-	/*
-	 * Do initial security configuration to allow DRAM/device access.
-	 */
-	tegra_memctrl_tzdram_setup(plat_params->tzdram_base,
-			(uint32_t)plat_params->tzdram_size);
-}
-
-/*******************************************************************************
- * Handler for late platform setup
- ******************************************************************************/
-void plat_late_platform_setup(void)
-{
-	; /* do nothing */
-}
-
-/*******************************************************************************
- * Handler to indicate support for System Suspend
- ******************************************************************************/
-bool plat_supports_system_suspend(void)
-{
-	return true;
-}
-
-/*******************************************************************************
- * Platform specific runtime setup.
- ******************************************************************************/
-void plat_runtime_setup(void)
-{
-	/*
-	 * During cold boot, it is observed that the arbitration
-	 * bit is set in the Memory controller leading to false
-	 * error interrupts in the non-secure world. To avoid
-	 * this, clean the interrupt status register before
-	 * booting into the non-secure world
-	 */
-	tegra_memctrl_clear_pending_interrupts();
-
-	/*
-	 * During boot, USB3 and flash media (SDMMC/SATA) devices need
-	 * access to IRAM. Because these clients connect to the MC and
-	 * do not have a direct path to the IRAM, the MC implements AHB
-	 * redirection during boot to allow path to IRAM. In this mode
-	 * accesses to a programmed memory address aperture are directed
-	 * to the AHB bus, allowing access to the IRAM. This mode must be
-	 * disabled before we jump to the non-secure world.
-	 */
-	tegra_memctrl_disable_ahb_redirection();
-}
diff --git a/plat/nvidia/tegra/soc/t132/plat_sip_calls.c b/plat/nvidia/tegra/soc/t132/plat_sip_calls.c
deleted file mode 100644
index 90c6bb2..0000000
--- a/plat/nvidia/tegra/soc/t132/plat_sip_calls.c
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2015, ARM Limited and Contributors. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-#include <errno.h>
-
-#include <arch.h>
-#include <arch_helpers.h>
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <lib/el3_runtime/context_mgmt.h>
-
-#include <tegra_private.h>
-
-#define NS_SWITCH_AARCH32	1
-#define SCR_RW_BITPOS		__builtin_ctz(SCR_RW_BIT)
-
-/*******************************************************************************
- * Tegra132 SiP SMCs
- ******************************************************************************/
-#define TEGRA_SIP_AARCH_SWITCH			0x82000004
-
-/*******************************************************************************
- * SPSR settings for AARCH32/AARCH64 modes
- ******************************************************************************/
-#define SPSR32		SPSR_MODE32(MODE32_svc, SPSR_T_ARM, SPSR_E_LITTLE, \
-			DAIF_FIQ_BIT | DAIF_IRQ_BIT | DAIF_ABT_BIT)
-#define SPSR64		SPSR_64(MODE_EL2, MODE_SP_ELX, DISABLE_ALL_EXCEPTIONS)
-
-/*******************************************************************************
- * This function is responsible for handling all T132 SiP calls
- ******************************************************************************/
-int plat_sip_handler(uint32_t smc_fid,
-		     uint64_t x1,
-		     uint64_t x2,
-		     uint64_t x3,
-		     uint64_t x4,
-		     const void *cookie,
-		     void *handle,
-		     uint64_t flags)
-{
-	switch (smc_fid) {
-
-	case TEGRA_SIP_AARCH_SWITCH:
-
-		/* clean up the high bits */
-		x1 = (uint32_t)x1;
-		x2 = (uint32_t)x2;
-
-		if (!x1 || x2 > NS_SWITCH_AARCH32) {
-			ERROR("%s: invalid parameters\n", __func__);
-			return -EINVAL;
-		}
-
-		/* x1 = ns entry point */
-		cm_set_elr_spsr_el3(NON_SECURE, x1,
-			(x2 == NS_SWITCH_AARCH32) ? SPSR32 : SPSR64);
-
-		/* switch NS world mode */
-		cm_write_scr_el3_bit(NON_SECURE, SCR_RW_BITPOS, !x2);
-
-		INFO("CPU switched to AARCH%s mode\n",
-			(x2 == NS_SWITCH_AARCH32) ? "32" : "64");
-		return 0;
-
-	default:
-		ERROR("%s: unhandled SMC (0x%x)\n", __func__, smc_fid);
-		break;
-	}
-
-	return -ENOTSUP;
-}
diff --git a/plat/nvidia/tegra/soc/t132/platform_t132.mk b/plat/nvidia/tegra/soc/t132/platform_t132.mk
deleted file mode 100644
index 9534c07..0000000
--- a/plat/nvidia/tegra/soc/t132/platform_t132.mk
+++ /dev/null
@@ -1,35 +0,0 @@
-#
-# Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
-# Copyright (c) 2020, NVIDIA Corporation. All rights reserved.
-#
-# SPDX-License-Identifier: BSD-3-Clause
-#
-
-TZDRAM_BASE			:= 0xF5C00000
-$(eval $(call add_define,TZDRAM_BASE))
-
-PLATFORM_CLUSTER_COUNT		:= 1
-$(eval $(call add_define,PLATFORM_CLUSTER_COUNT))
-
-PLATFORM_MAX_CPUS_PER_CLUSTER	:= 2
-$(eval $(call add_define,PLATFORM_MAX_CPUS_PER_CLUSTER))
-
-MAX_XLAT_TABLES			:= 3
-$(eval $(call add_define,MAX_XLAT_TABLES))
-
-MAX_MMAP_REGIONS		:= 8
-$(eval $(call add_define,MAX_MMAP_REGIONS))
-
-# platform files
-PLAT_INCLUDES		+=	-Iplat/nvidia/tegra/include/t132
-
-BL31_SOURCES		+=	${TEGRA_GICv2_SOURCES}			\
-				drivers/ti/uart/aarch64/16550_console.S	\
-				lib/cpus/aarch64/denver.S		\
-				${TEGRA_DRIVERS}/flowctrl/flowctrl.c	\
-				${TEGRA_DRIVERS}/memctrl/memctrl_v1.c	\
-				${TEGRA_DRIVERS}/pmc/pmc.c		\
-				${SOC_DIR}/plat_psci_handlers.c		\
-				${SOC_DIR}/plat_sip_calls.c		\
-				${SOC_DIR}/plat_setup.c			\
-				${SOC_DIR}/plat_secondary.c
diff --git a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c
index 54d3b2c..aebaceb 100644
--- a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c
+++ b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c
@@ -7,6 +7,8 @@
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <arch.h>
@@ -341,7 +343,7 @@
 		break;
 
 	default:
-		ERROR("unknown MCE command (%llu)\n", cmd);
+		ERROR("unknown MCE command (%" PRIu64 ")\n", cmd);
 		ret = EINVAL;
 		break;
 	}
diff --git a/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c b/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c
index e3d5bd5..af1c0aa 100644
--- a/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c
+++ b/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c
@@ -16,8 +16,10 @@
 #include <mce_private.h>
 #include <platform_def.h>
 #include <stdbool.h>
+#include <stdint.h>
 #include <string.h>
 #include <errno.h>
+#include <inttypes.h>
 #include <t194_nvg.h>
 #include <tegra_def.h>
 #include <tegra_platform.h>
@@ -69,7 +71,7 @@
 		break;
 
 	default:
-		ERROR("unknown MCE command (%llu)\n", cmd);
+		ERROR("unknown MCE command (%" PRIu64 ")\n", cmd);
 		ret = -EINVAL;
 		break;
 	}
diff --git a/plat/nvidia/tegra/soc/t194/plat_ras.c b/plat/nvidia/tegra/soc/t194/plat_ras.c
index 0c4c6fa..dbd6272 100644
--- a/plat/nvidia/tegra/soc/t194/plat_ras.c
+++ b/plat/nvidia/tegra/soc/t194/plat_ras.c
@@ -4,6 +4,7 @@
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <inttypes.h>
 #include <stdbool.h>
 #include <stdint.h>
 
@@ -54,7 +55,7 @@
 
 	ras_lock();
 
-	ERROR("MPIDR 0x%lx: exception reason=%u syndrome=0x%llx\n",
+	ERROR("MPIDR 0x%lx: exception reason=%u syndrome=0x%" PRIx64 "\n",
 		read_mpidr(), ea_reason, syndrome);
 
 	/* Call RAS EA handler */
@@ -146,7 +147,7 @@
 			/* enable the supported errors */
 			err_ctrl |= err_fr;
 
-			VERBOSE("errselr_el1:0x%x, erxfr:0x%llx, err_ctrl:0x%llx\n",
+			VERBOSE("errselr_el1:0x%x, erxfr:0x%" PRIx64 ", err_ctrl:0x%" PRIx64 "\n",
 				idx_start + j, err_fr, err_ctrl);
 
 			/* enable specified errors, or set to 0 if no supported error */
@@ -288,7 +289,7 @@
 	/* keep the log print same as linux arm64_ras driver. */
 	ERROR("**************************************\n");
 	ERROR("RAS Error in %s, ERRSELR_EL1=0x%x:\n", name, errselr);
-	ERROR("\tStatus = 0x%llx\n", status);
+	ERROR("\tStatus = 0x%" PRIx64 "\n", status);
 
 	/* Print uncorrectable errror information. */
 	if (ERR_STATUS_GET_FIELD(status, UE) != 0U) {
@@ -493,9 +494,6 @@
 #if RAS_EXTENSION
 	tegra194_ea_handler(ea_reason, syndrome, cookie, handle, flags);
 #else
-	ERROR("Unhandled External Abort received on 0x%llx at EL3!\n",
-			read_mpidr_el1());
-	ERROR(" exception reason=%u syndrome=0x%lx\n", ea_reason, syndrome);
-	panic();
+	plat_default_ea_handler(ea_reason, syndrome, cookie, handle, flags);
 #endif
 }
diff --git a/plat/nvidia/tegra/soc/t194/platform_t194.mk b/plat/nvidia/tegra/soc/t194/platform_t194.mk
index 339375f..7583833 100644
--- a/plat/nvidia/tegra/soc/t194/platform_t194.mk
+++ b/plat/nvidia/tegra/soc/t194/platform_t194.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved.
+# Copyright (c) 2019-2021, NVIDIA CORPORATION. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 # platform configs
 ENABLE_CONSOLE_SPE			:= 1
 $(eval $(call add_define,ENABLE_CONSOLE_SPE))
@@ -74,10 +76,10 @@
 
 # SPM dispatcher
 ifeq (${SPD},spmd)
-# include device tree helper library
 include lib/libfdt/libfdt.mk
 # sources to support spmd
 BL31_SOURCES		+=	plat/common/plat_spmd_manifest.c	\
-				common/fdt_wrappers.c			\
 				${LIBFDT_SRCS}
+
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
 endif
diff --git a/plat/nvidia/tegra/soc/t210/plat_sip_calls.c b/plat/nvidia/tegra/soc/t210/plat_sip_calls.c
index 904f8d6..e3484be 100644
--- a/plat/nvidia/tegra/soc/t210/plat_sip_calls.c
+++ b/plat/nvidia/tegra/soc/t210/plat_sip_calls.c
@@ -5,6 +5,9 @@
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <arch.h>
 #include <arch_helpers.h>
 #include <assert.h>
@@ -71,7 +74,7 @@
 		case PMC_CRYPTO_OP_0:
 		case PMC_TSC_MULT_0:
 		case PMC_STICKY_BIT:
-			ERROR("%s: error offset=0x%llx\n", __func__, x2);
+			ERROR("%s: error offset=0x%" PRIx64 "\n", __func__, x2);
 			return -EFAULT;
 		default:
 			/* Valid register */
diff --git a/plat/nxp/common/aarch64/bl31_data.S b/plat/nxp/common/aarch64/bl31_data.S
new file mode 100644
index 0000000..cc91540
--- /dev/null
+++ b/plat/nxp/common/aarch64/bl31_data.S
@@ -0,0 +1,558 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <asm_macros.S>
+
+#include "bl31_data.h"
+#include "plat_psci.h"
+#include "platform_def.h"
+
+.global _getCoreData
+.global _setCoreData
+.global _getCoreState
+.global _setCoreState
+.global _init_global_data
+.global _get_global_data
+.global _set_global_data
+.global _initialize_psci
+.global _init_task_flags
+.global _set_task1_start
+.global _set_task1_done
+
+
+/* Function returns the specified data field value from the specified cpu
+ * core data area
+ * in:  x0 = core mask lsb
+ *	x1 = data field name/offset
+ * out: x0 = data value
+ * uses x0, x1, x2, [x13, x14, x15]
+ */
+func _getCoreData
+
+	/* generate a 0-based core number from the input mask */
+	clz   x2, x0
+	mov   x0, #63
+	sub   x0, x0, x2
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+
+	/* determine if this is bootcore or secondary core */
+	cbnz  x0, 1f
+
+	/* get base address for bootcore data */
+	ldr  x2, =BC_PSCI_BASE
+	add  x2, x2, x1
+	b	2f
+
+1:	/* get base address for secondary core data */
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+
+	/* generate number of regions to offset */
+	mov   x2, #SEC_REGION_SIZE
+	mul   x2, x2, x0
+
+	/* x1 = field offset */
+	/* x2 = region offset */
+
+	/* generate the total offset to data element */
+	sub   x1, x2, x1
+
+	/* x1 = total offset to data element */
+
+	/* get the base address */
+	ldr   x2, =SECONDARY_TOP
+
+	/* apply offset to base addr */
+	sub   x2, x2, x1
+2:
+	/* x2 = data element address */
+
+	dc   ivac, x2
+	dsb  sy
+	isb
+	/* read data */
+	ldr  x0, [x2]
+
+	ret
+endfunc _getCoreData
+
+
+/* Function returns the SoC-specific state of the specified cpu
+ * in:  x0 = core mask lsb
+ * out: x0 = data value
+ * uses x0, x1, x2, [x13, x14, x15]
+ */
+func _getCoreState
+
+	mov   x1, #CORE_STATE_DATA
+
+	/* generate a 0-based core number from the input mask */
+	clz   x2, x0
+	mov   x0, #63
+	sub   x0, x0, x2
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+
+	/* determine if this is bootcore or secondary core */
+	cbnz  x0, 1f
+
+	/* get base address for bootcore data */
+	ldr  x2, =BC_PSCI_BASE
+	add  x2, x2, x1
+	b	2f
+
+1:	/* get base address for secondary core data */
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+
+	/* generate number of regions to offset */
+	mov   x2, #SEC_REGION_SIZE
+	mul   x2, x2, x0
+
+	/* x1 = field offset */
+	/* x2 = region offset */
+
+	/* generate the total offset to data element */
+	sub   x1, x2, x1
+
+	/* x1 = total offset to data element */
+
+	/* get the base address */
+	ldr   x2, =SECONDARY_TOP
+
+	/* apply offset to base addr */
+	sub   x2, x2, x1
+2:
+	/* x2 = data element address */
+
+	dc   ivac, x2
+	dsb  sy
+	isb
+
+	/* read data */
+	ldr  x0, [x2]
+
+	ret
+endfunc _getCoreState
+
+
+/* Function writes the specified data value into the specified cpu
+ * core data area
+ * in:  x0 = core mask lsb
+ *	  x1 = data field offset
+ *	  x2 = data value to write/store
+ * out: none
+ * uses x0, x1, x2, x3, [x13, x14, x15]
+ */
+func _setCoreData
+	/* x0 = core mask */
+	/* x1 = field offset */
+	/* x2 = data value */
+
+	clz   x3, x0
+	mov   x0, #63
+	sub   x0, x0, x3
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+	/* x2 = data value */
+
+	/* determine if this is bootcore or secondary core */
+	cbnz  x0, 1f
+
+	/* get base address for bootcore data */
+	ldr  x3, =BC_PSCI_BASE
+	add  x3, x3, x1
+	b	2f
+
+1:	/* get base address for secondary core data */
+
+	/* x0 = core number (0-based) */
+	/* x1 = field offset */
+	/* x2 = data value */
+
+	/* generate number of regions to offset */
+	mov   x3, #SEC_REGION_SIZE
+	mul   x3, x3, x0
+
+	/* x1 = field offset */
+	/* x2 = data value */
+	/* x3 = region offset */
+
+	/* generate the total offset to data element */
+	sub   x1, x3, x1
+
+	/* x1 = total offset to data element */
+	/* x2 = data value */
+
+	ldr   x3, =SECONDARY_TOP
+
+	/* apply offset to base addr */
+	sub   x3, x3, x1
+
+2:
+	/* x2 = data value */
+	/* x3 = data element address */
+
+	str   x2, [x3]
+
+	dc	cvac, x3
+	dsb   sy
+	isb
+	ret
+endfunc _setCoreData
+
+
+/* Function stores the specified core state
+ * in:  x0 = core mask lsb
+ *	x1 = data value to write/store
+ * out: none
+ * uses x0, x1, x2, x3, [x13, x14, x15]
+ */
+func _setCoreState
+	mov  x2, #CORE_STATE_DATA
+
+	clz   x3, x0
+	mov   x0, #63
+	sub   x0, x0, x3
+
+	/* x0 = core number (0-based) */
+	/* x1 = data value */
+	/* x2 = field offset */
+
+	/* determine if this is bootcore or secondary core */
+	cbnz  x0, 1f
+
+	/* get base address for bootcore data */
+	ldr  x3, =BC_PSCI_BASE
+	add  x3, x3, x2
+	b	2f
+
+1:	/* get base address for secondary core data */
+
+	/* x0 = core number (0-based) */
+	/* x1 = data value */
+	/* x2 = field offset */
+
+	/* generate number of regions to offset */
+	mov   x3, #SEC_REGION_SIZE
+	mul   x3, x3, x0
+
+	/* x1 = data value */
+	/* x2 = field offset */
+	/* x3 = region offset */
+
+	/* generate the total offset to data element */
+	sub   x2, x3, x2
+
+	/* x1 = data value */
+	/* x2 = total offset to data element */
+
+	ldr   x3, =SECONDARY_TOP
+
+	/* apply offset to base addr */
+	sub   x3, x3, x2
+
+2:
+	/* x1 = data value */
+	/* x3 = data element address */
+
+	str   x1, [x3]
+
+	dc	civac, x3
+	dsb   sy
+	isb
+	ret
+endfunc _setCoreState
+
+
+/* Function sets the task1 start
+ * in:  w0 = value to set flag to
+ * out: none
+ * uses x0, x1
+ */
+func _set_task1_start
+
+	ldr  x1, =SMC_TASK1_BASE
+
+	add  x1, x1, #TSK_START_OFFSET
+	str  w0, [x1]
+	dc   cvac, x1
+	dsb  sy
+	isb
+	ret
+endfunc _set_task1_start
+
+
+/* Function sets the state of the task 1 done flag
+ * in:  w0 = value to set flag to
+ * out: none
+ * uses x0, x1
+ */
+func _set_task1_done
+
+	ldr  x1, =SMC_TASK1_BASE
+
+	add  x1, x1, #TSK_DONE_OFFSET
+	str  w0, [x1]
+	dc   cvac, x1
+	dsb  sy
+	isb
+	ret
+endfunc _set_task1_done
+
+
+/* Function initializes the smc global data entries
+ * Note: the constant LAST_SMC_GLBL_OFFSET must reference the last entry in the
+ *	   smc global region
+ * in:  none
+ * out: none
+ * uses x0, x1, x2
+ */
+func _init_global_data
+
+	ldr  x1, =SMC_GLBL_BASE
+
+	/* x1 = SMC_GLBL_BASE */
+
+	mov x2, #LAST_SMC_GLBL_OFFSET
+	add x2, x2, x1
+1:
+	str  xzr, [x1]
+	dc   cvac, x1
+	cmp  x2, x1
+	add  x1, x1, #8
+	b.hi 1b
+
+	dsb  sy
+	isb
+	ret
+endfunc _init_global_data
+
+
+/* Function gets the value of the specified global data element
+ * in:  x0 = offset of data element
+ * out: x0 = requested data element
+ * uses x0, x1
+ */
+func _get_global_data
+
+	ldr  x1, =SMC_GLBL_BASE
+	add  x1, x1, x0
+	dc   ivac, x1
+	isb
+
+	ldr  x0, [x1]
+	ret
+endfunc _get_global_data
+
+
+/* Function sets the value of the specified global data element
+ * in:  x0 = offset of data element
+ *	  x1 = value to write
+ * out: none
+ * uses x0, x1, x2
+ */
+func _set_global_data
+
+	ldr  x2, =SMC_GLBL_BASE
+	add  x0, x0, x2
+	str  x1, [x0]
+	dc   cvac, x0
+
+	dsb  sy
+	isb
+	ret
+endfunc _set_global_data
+
+
+/* Function initializes the core data areas
+ * only executed by the boot core
+ * in:   none
+ * out:  none
+ * uses: x0, x1, x2, x3, x4, x5, x6, x7, [x13, x14, x15]
+ */
+func _initialize_psci
+	mov   x7, x30
+
+	/* initialize the bootcore psci data */
+	ldr   x5, =BC_PSCI_BASE
+	mov   x6, #CORE_RELEASED
+
+	str   x6,  [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5], #8
+	dc cvac, x5
+	str   xzr, [x5]
+	dc cvac, x5
+	dsb sy
+	isb
+
+	/* see if we have any secondary cores */
+	mov   x4, #PLATFORM_CORE_COUNT
+	sub   x4, x4, #1
+	cbz   x4, 3f
+
+	/* initialize the secondary core's psci data */
+	ldr  x5, =SECONDARY_TOP
+	/* core mask lsb for core 1 */
+	mov  x3, #2
+	sub  x5, x5, #SEC_REGION_SIZE
+
+	/* x3 = core1 mask lsb */
+	/* x4 = number of secondary cores */
+	/* x5 = core1 psci data base address */
+2:
+	/* set core state in x6 */
+	mov  x0, x3
+	mov  x6, #CORE_IN_RESET
+	bl   _soc_ck_disabled
+	cbz  x0, 1f
+	mov  x6, #CORE_DISABLED
+1:
+	add   x2, x5, #CORE_STATE_DATA
+	str   x6,  [x2]
+	dc cvac, x2
+	add   x2, x5, #SPSR_EL3_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #CNTXT_ID_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #START_ADDR_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #LINK_REG_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #GICC_CTLR_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #ABORT_FLAG_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #SCTLR_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #CPUECTLR_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #AUX_01_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #AUX_02_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #AUX_03_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #AUX_04_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #AUX_05_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #SCR_EL3_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	add   x2, x5, #HCR_EL2_DATA
+	str   xzr, [x2]
+	dc cvac, x2
+	dsb sy
+	isb
+
+	sub   x4, x4, #1
+	cbz   x4, 3f
+
+	/* generate next core mask */
+	lsl  x3, x3, #1
+
+	/* decrement base address to next data area */
+	sub  x5, x5, #SEC_REGION_SIZE
+	b	2b
+3:
+	mov   x30, x7
+	ret
+endfunc _initialize_psci
+
+
+/* Function initializes the soc init task flags
+ * in:  none
+ * out: none
+ * uses x0, x1, [x13, x14, x15]
+ */
+func _init_task_flags
+
+	/* get the base address of the first task structure */
+	ldr  x0, =SMC_TASK1_BASE
+
+	/* x0 = task1 base address */
+
+	str  wzr, [x0, #TSK_START_OFFSET]
+	str  wzr, [x0, #TSK_DONE_OFFSET]
+	str  wzr, [x0, #TSK_CORE_OFFSET]
+	dc   cvac, x0
+
+	/* move to task2 structure */
+	add  x0, x0, #SMC_TASK_OFFSET
+
+	str  wzr, [x0, #TSK_START_OFFSET]
+	str  wzr, [x0, #TSK_DONE_OFFSET]
+	str  wzr, [x0, #TSK_CORE_OFFSET]
+	dc   cvac, x0
+
+	/* move to task3 structure */
+	add  x0, x0, #SMC_TASK_OFFSET
+
+	str  wzr, [x0, #TSK_START_OFFSET]
+	str  wzr, [x0, #TSK_DONE_OFFSET]
+	str  wzr, [x0, #TSK_CORE_OFFSET]
+	dc   cvac, x0
+
+	/* move to task4 structure */
+	add  x0, x0, #SMC_TASK_OFFSET
+
+	str  wzr, [x0, #TSK_START_OFFSET]
+	str  wzr, [x0, #TSK_DONE_OFFSET]
+	str  wzr, [x0, #TSK_CORE_OFFSET]
+	dc   cvac, x0
+
+	dsb  sy
+	isb
+	ret
+endfunc _init_task_flags
diff --git a/plat/nxp/common/aarch64/ls_helpers.S b/plat/nxp/common/aarch64/ls_helpers.S
new file mode 100644
index 0000000..19ea9e5
--- /dev/null
+++ b/plat/nxp/common/aarch64/ls_helpers.S
@@ -0,0 +1,194 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <asm_macros.S>
+#include <drivers/console.h>
+#include <lib/cpus/aarch64/cortex_a72.h>
+
+#include <platform_def.h>
+
+
+	.globl	plat_crash_console_init
+	.globl	plat_crash_console_putc
+	.globl	plat_crash_console_flush
+	.globl  plat_core_pos
+	.globl  plat_my_core_pos
+	.globl  plat_core_mask
+	.globl  plat_my_core_mask
+	.globl  plat_core_pos_by_mpidr
+	.globl _disable_ldstr_pfetch_A53
+	.globl _disable_ldstr_pfetch_A72
+	.global	_set_smmu_pagesz_64
+
+	/* int plat_crash_console_init(void)
+	 * Function to initialize the crash console
+	 * without a C Runtime to print crash report.
+	 * Clobber list : x0 - x4
+	 */
+
+	/* int plat_crash_console_init(void)
+	 * Use normal console by default. Switch it to crash
+	 * mode so serial consoles become active again.
+	 * NOTE: This default implementation will only work for
+	 * crashes that occur after a normal console (marked
+	 * valid for the crash state) has been registered with
+	 * the console framework. To debug crashes that occur
+	 * earlier, the platform has to override these functions
+	 * with an implementation that initializes a console
+	 * driver with hardcoded parameters. See
+	 * docs/porting-guide.rst for more information.
+	 */
+func plat_crash_console_init
+	mov	x3, x30
+	mov	x0, #CONSOLE_FLAG_CRASH
+	bl	console_switch_state
+	mov	x0, #1
+	ret	x3
+endfunc plat_crash_console_init
+
+	/* void plat_crash_console_putc(int character)
+	 * Output through the normal console by default.
+	 */
+func plat_crash_console_putc
+	b	console_putc
+endfunc plat_crash_console_putc
+
+	/* void plat_crash_console_flush(void)
+	 * Flush normal console by default.
+	 */
+func plat_crash_console_flush
+	b	console_flush
+endfunc plat_crash_console_flush
+
+/* This function implements a part of the critical interface between the psci
+ * generic layer and the platform that allows the former to query the platform
+ * to convert an MPIDR to a unique linear index. An error code (-1) is returned
+ * in case the MPIDR is invalid.
+ */
+func plat_core_pos_by_mpidr
+
+	b	plat_core_pos
+
+endfunc plat_core_pos_by_mpidr
+
+#if (SYMMETRICAL_CLUSTERS)
+/* unsigned int plat_my_core_mask(void)
+ *  generate a mask bit for this core
+ */
+func plat_my_core_mask
+	mrs	x0, MPIDR_EL1
+	b	plat_core_mask
+endfunc plat_my_core_mask
+
+/* unsigned int plat_core_mask(u_register_t mpidr)
+ * generate a lsb-based mask bit for the core specified by mpidr in x0.
+ *
+ * SoC core = ((cluster * cpu_per_cluster) + core)
+ * mask = (1 << SoC core)
+ */
+func plat_core_mask
+	mov	w1, wzr
+	mov	w2, wzr
+
+	/* extract cluster */
+	bfxil	w1, w0, #8, #8
+	/* extract cpu # */
+	bfxil	w2, w0, #0, #8
+
+	mov	w0, wzr
+
+	/* error checking */
+	cmp	w1, #NUMBER_OF_CLUSTERS
+	b.ge	1f
+	cmp	w2, #CORES_PER_CLUSTER
+	b.ge	1f
+
+	mov	w0, #CORES_PER_CLUSTER
+	mul	w1, w1, w0
+	add	w1, w1, w2
+	mov	w2, #0x1
+	lsl	w0, w2, w1
+1:
+	ret
+endfunc plat_core_mask
+
+/*
+ * unsigned int plat_my_core_pos(void)
+ *  generate a linear core number for this core
+ */
+func plat_my_core_pos
+	mrs	x0, MPIDR_EL1
+	b	plat_core_pos
+endfunc plat_my_core_pos
+
+/*
+ * unsigned int plat_core_pos(u_register_t mpidr)
+ * Generate a linear core number for the core specified by mpidr.
+ *
+ * SoC core = ((cluster * cpu_per_cluster) + core)
+ * Returns -1 if mpidr invalid
+ */
+func plat_core_pos
+	mov	w1, wzr
+	mov	w2, wzr
+	bfxil	w1, w0, #8, #8	/* extract cluster */
+	bfxil	w2, w0, #0, #8	/* extract cpu #   */
+
+	mov	w0, #-1
+
+	/* error checking */
+	cmp	w1, #NUMBER_OF_CLUSTERS
+	b.ge	1f
+	cmp	w2, #CORES_PER_CLUSTER
+	b.ge	1f
+
+	mov	w0, #CORES_PER_CLUSTER
+	mul	w1, w1, w0
+	add	w0, w1, w2
+1:
+	ret
+endfunc plat_core_pos
+
+#endif
+
+/* this function disables the load-store prefetch of the calling core
+ * Note: this function is for A72 cores ONLY
+ * in:  none
+ * out: none
+ * uses x0
+ */
+func _disable_ldstr_pfetch_A72
+
+	mrs	x0, CORTEX_A72_CPUACTLR_EL1
+	tst	x0, #CORTEX_A72_CPUACTLR_EL1_DISABLE_L1_DCACHE_HW_PFTCH
+	b.eq	1f
+	b	2f
+
+.align 6
+1:
+	dsb	sy
+	isb
+	orr	x0, x0, #CORTEX_A72_CPUACTLR_EL1_DISABLE_L1_DCACHE_HW_PFTCH
+	msr	CORTEX_A72_CPUACTLR_EL1, x0
+	isb
+
+2:
+	ret
+endfunc _disable_ldstr_pfetch_A72
+
+/*
+ * Function sets the SACR pagesize to 64k
+ */
+func _set_smmu_pagesz_64
+
+	ldr	x1, =NXP_SMMU_ADDR
+	ldr	w0, [x1, #0x10]
+	orr	w0, w0, #1 << 16	/* setting to 64K page */
+	str	w0, [x1, #0x10]
+
+	ret
+endfunc _set_smmu_pagesz_64
diff --git a/plat/nxp/common/fip_handler/common/plat_def_fip_uuid.h b/plat/nxp/common/fip_handler/common/plat_def_fip_uuid.h
new file mode 100644
index 0000000..65aef14
--- /dev/null
+++ b/plat/nxp/common/fip_handler/common/plat_def_fip_uuid.h
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_DEF_FIP_UUID_H
+#define PLAT_DEF_FIP_UUID_H
+
+/* PHy images configs */
+#define UUID_DDR_IMEM_UDIMM_1D \
+	{{0x5b, 0xdb, 0xe3, 0x83}, {0xd1, 0x9f}, {0xc7, 0x06}, 0xd4, 0x91, {0x76, 0x4f, 0x9d, 0x23, 0x2d, 0x2d} }
+
+#define UUID_DDR_IMEM_UDIMM_2D \
+	{{0xfa, 0x0e, 0xeb, 0x21}, {0xe0, 0x7f}, {0x8e, 0x65}, 0x95, 0xd8, {0x2b, 0x94, 0xf6, 0xb8, 0x28, 0x0a} }
+
+#define UUID_DDR_DMEM_UDIMM_1D \
+	{{0xba, 0xbb, 0xfd, 0x7e}, {0x5b, 0xf0}, {0xeb, 0xb8}, 0xeb, 0x71, {0xb1, 0x85, 0x07, 0xdd, 0xe1, 0x32} }
+
+#define UUID_DDR_DMEM_UDIMM_2D \
+	{{0xb6, 0x99, 0x61, 0xda}, {0xf9, 0x92}, {0x4b, 0x9e}, 0x0c, 0x49, {0x74, 0xa5, 0xe0, 0x5c, 0xbe, 0xc3} }
+
+#define UUID_DDR_IMEM_RDIMM_1D \
+	{{0x42, 0x33, 0x66, 0x52}, {0xd8, 0x94}, {0x4d, 0xc1}, 0x91, 0xcc, {0x26, 0x8f, 0x7a, 0x67, 0xf1, 0xa2} }
+
+#define UUID_DDR_IMEM_RDIMM_2D \
+	{{0x2e, 0x95, 0x73, 0xba}, {0xb5, 0xca}, {0x7c, 0xc7}, 0xef, 0xc9, {0x5e, 0xb0, 0x42, 0xec, 0x08, 0x7a} }
+
+#define UUID_DDR_DMEM_RDIMM_1D \
+	{{0x1c, 0x51, 0x17, 0xed}, {0x30, 0x0d}, {0xae, 0xba}, 0x87, 0x03, {0x1f, 0x37, 0x85, 0xec, 0xe1, 0x44} }
+
+#define UUID_DDR_DMEM_RDIMM_2D \
+	{{0xe9, 0x0a, 0x90, 0x78}, {0x11, 0xd6}, {0x8b, 0xba}, 0x24, 0x35, {0xec, 0x10, 0x75, 0x4f, 0x56, 0xa5} }
+
+#define UUID_DDR_FW_KEY_CERT \
+	{{0xac, 0x4b, 0xb8, 0x9c}, {0x8f, 0xb9}, {0x11, 0xea}, 0xbc, 0x55, {0x02, 0x42, 0xac, 0x12, 0x00, 0x03} }
+
+#define UUID_DDR_UDIMM_FW_CONTENT_CERT \
+	{{0x2c, 0x7f, 0x52, 0x54}, {0x70, 0x92}, {0x48, 0x40}, 0x8c, 0x34, {0x87, 0x4b, 0xbf, 0xbd, 0x9d, 0x89} }
+
+#define UUID_DDR_RDIMM_FW_CONTENT_CERT \
+	{{0x94, 0xc3, 0x63, 0x30}, {0x7c, 0xf7}, {0x4f, 0x1d}, 0xaa, 0xcd, {0xb5, 0x80, 0xb2, 0xc2, 0x40, 0xa5} }
+
+#define UUID_FUSE_PROV \
+	{{0xec, 0x45, 0x90, 0x42}, {0x30, 0x0d}, {0xae, 0xba}, 0x87, 0x03, {0x1f, 0x37, 0x85, 0xec, 0xe1, 0x44} }
+
+#define UUID_FUSE_UP \
+	{{0x89, 0x46, 0xef, 0x78}, {0x11, 0xd6}, {0x8b, 0xba}, 0x24, 0x35, {0xec, 0x10, 0x75, 0x4f, 0x56, 0xa5} }
+
+#endif	/*	PLAT_DEF_FIP_UUID_H	*/
diff --git a/plat/nxp/common/fip_handler/common/plat_tbbr_img_def.h b/plat/nxp/common/fip_handler/common/plat_tbbr_img_def.h
new file mode 100644
index 0000000..9856f70
--- /dev/null
+++ b/plat/nxp/common/fip_handler/common/plat_tbbr_img_def.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef NXP_IMG_DEF_H
+#define NXP_IMG_DEF_H
+
+#include <export/common/tbbr/tbbr_img_def_exp.h>
+
+#ifdef CONFIG_DDR_FIP_IMAGE
+/* DDR FIP IMAGE ID */
+#define DDR_FIP_IMAGE_ID		MAX_IMG_IDS_WITH_SPMDS
+
+#define DDR_IMEM_UDIMM_1D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 1
+#define DDR_IMEM_UDIMM_2D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 2
+
+#define DDR_DMEM_UDIMM_1D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 3
+#define DDR_DMEM_UDIMM_2D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 4
+
+#define DDR_IMEM_RDIMM_1D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 5
+#define DDR_IMEM_RDIMM_2D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 6
+
+#define DDR_DMEM_RDIMM_1D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 7
+#define DDR_DMEM_RDIMM_2D_IMAGE_ID	MAX_IMG_IDS_WITH_SPMDS + 8
+
+#define DDR_FW_KEY_CERT_ID		MAX_IMG_IDS_WITH_SPMDS + 9
+#define DDR_UDIMM_FW_CONTENT_CERT_ID	MAX_IMG_IDS_WITH_SPMDS + 10
+#define DDR_RDIMM_FW_CONTENT_CERT_ID	MAX_IMG_IDS_WITH_SPMDS + 11
+/* Max Images */
+#define MAX_IMG_WITH_DDR_IDS		MAX_IMG_IDS_WITH_SPMDS + 12
+#else
+#define MAX_IMG_WITH_DDR_IDS		MAX_IMG_IDS_WITH_SPMDS
+#endif
+
+#ifdef POLICY_FUSE_PROVISION
+/* FUSE FIP IMAGE ID */
+#define FUSE_FIP_IMAGE_ID		MAX_IMG_WITH_DDR_IDS
+
+#define FUSE_PROV_IMAGE_ID		MAX_IMG_WITH_DDR_IDS + 1
+
+#define FUSE_UP_IMAGE_ID		MAX_IMG_WITH_DDR_IDS + 2
+
+#define MAX_IMG_WITH_FIMG_IDS		MAX_IMG_WITH_DDR_IDS + 3
+#else
+#define MAX_IMG_WITH_FIMG_IDS		MAX_IMG_WITH_DDR_IDS
+#endif
+
+#define MAX_NUMBER_IDS			MAX_IMG_WITH_FIMG_IDS
+
+#endif	/* NXP_IMG_DEF_H */
diff --git a/plat/nxp/common/fip_handler/common/platform_oid.h b/plat/nxp/common/fip_handler/common/platform_oid.h
new file mode 100644
index 0000000..bbd6041
--- /dev/null
+++ b/plat/nxp/common/fip_handler/common/platform_oid.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#define DDR_FW_CONTENT_CERT_PK_OID		"1.3.6.1.4.1.4128.2200.1"
+#define DDR_IMEM_UDIMM_1D_HASH_OID		"1.3.6.1.4.1.4128.2200.2"
+#define DDR_IMEM_UDIMM_2D_HASH_OID		"1.3.6.1.4.1.4128.2200.3"
+#define DDR_DMEM_UDIMM_1D_HASH_OID		"1.3.6.1.4.1.4128.2200.4"
+#define DDR_DMEM_UDIMM_2D_HASH_OID		"1.3.6.1.4.1.4128.2200.5"
+#define DDR_IMEM_RDIMM_1D_HASH_OID		"1.3.6.1.4.1.4128.2200.6"
+#define DDR_IMEM_RDIMM_2D_HASH_OID		"1.3.6.1.4.1.4128.2200.7"
+#define DDR_DMEM_RDIMM_1D_HASH_OID		"1.3.6.1.4.1.4128.2200.8"
+#define DDR_DMEM_RDIMM_2D_HASH_OID		"1.3.6.1.4.1.4128.2200.9"
diff --git a/plat/nxp/common/fip_handler/ddr_fip/ddr_fip_io.mk b/plat/nxp/common/fip_handler/ddr_fip/ddr_fip_io.mk
new file mode 100644
index 0000000..7d673ba
--- /dev/null
+++ b/plat/nxp/common/fip_handler/ddr_fip/ddr_fip_io.mk
@@ -0,0 +1,38 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+ifeq (${DDR_FIP_IO_STORAGE_ADDED},)
+
+$(eval $(call add_define, PLAT_DEF_FIP_UUID))
+$(eval $(call add_define, PLAT_TBBR_IMG_DEF))
+$(eval $(call SET_NXP_MAKE_FLAG,IMG_LOADR_NEEDED,BL2))
+
+DDR_FIP_IO_STORAGE_ADDED	:= 1
+$(eval $(call add_define,CONFIG_DDR_FIP_IMAGE))
+
+FIP_HANDLER_PATH	:=  ${PLAT_COMMON_PATH}/fip_handler
+FIP_HANDLER_COMMON_PATH	:=  ${FIP_HANDLER_PATH}/common
+DDR_FIP_IO_STORAGE_PATH	:=  ${FIP_HANDLER_PATH}/ddr_fip
+
+PLAT_INCLUDES		+= -I${FIP_HANDLER_COMMON_PATH}\
+			   -I$(DDR_FIP_IO_STORAGE_PATH)
+
+DDR_FIP_IO_SOURCES	+= $(DDR_FIP_IO_STORAGE_PATH)/ddr_io_storage.c
+
+$(shell cp tools/nxp/plat_fiptool/plat_fiptool.mk ${PLAT_DIR})
+
+ifeq (${BL_COMM_DDR_FIP_IO_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${DDR_FIP_IO_SOURCES}
+else
+ifeq (${BL2_DDR_FIP_IO_NEEDED},yes)
+BL2_SOURCES		+= ${DDR_FIP_IO_SOURCES}
+endif
+ifeq (${BL31_DDR_FIP_IO_NEEDED},yes)
+BL31_SOURCES		+= ${DDR_FIP_IO_SOURCES}
+endif
+endif
+endif
+#------------------------------------------------
diff --git a/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.c b/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.c
new file mode 100644
index 0000000..fc3c4a4
--- /dev/null
+++ b/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.c
@@ -0,0 +1,232 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <io_block.h>
+#include <io_driver.h>
+#include <io_fip.h>
+#include <io_memmap.h>
+#include <io_storage.h>
+#include <lib/utils.h>
+#include <tools_share/firmware_image_package.h>
+#include "ddr_io_storage.h"
+#include "plat_common.h"
+#include "platform_def.h"
+
+
+/* TBD - Move these defined to the platform_def.h file.
+ * Keeping them for reference here
+ */
+extern uintptr_t backend_dev_handle;
+
+static uint32_t ddr_fip;
+
+static uintptr_t ddr_fip_dev_handle;
+
+static io_block_spec_t ddr_fip_block_spec = {
+	.offset = PLAT_DDR_FIP_OFFSET,
+	.length = PLAT_DDR_FIP_MAX_SIZE
+};
+
+static const io_uuid_spec_t ddr_imem_udimm_1d_uuid_spec = {
+	.uuid = UUID_DDR_IMEM_UDIMM_1D,
+};
+
+static const io_uuid_spec_t ddr_imem_udimm_2d_uuid_spec = {
+	.uuid = UUID_DDR_IMEM_UDIMM_2D,
+};
+
+static const io_uuid_spec_t ddr_dmem_udimm_1d_uuid_spec = {
+	.uuid = UUID_DDR_DMEM_UDIMM_1D,
+};
+
+static const io_uuid_spec_t ddr_dmem_udimm_2d_uuid_spec = {
+	.uuid = UUID_DDR_DMEM_UDIMM_2D,
+};
+
+static const io_uuid_spec_t ddr_imem_rdimm_1d_uuid_spec = {
+	.uuid = UUID_DDR_IMEM_RDIMM_1D,
+};
+
+static const io_uuid_spec_t ddr_imem_rdimm_2d_uuid_spec = {
+	.uuid = UUID_DDR_IMEM_RDIMM_2D,
+};
+
+static const io_uuid_spec_t ddr_dmem_rdimm_1d_uuid_spec = {
+	.uuid = UUID_DDR_DMEM_RDIMM_1D,
+};
+
+static const io_uuid_spec_t ddr_dmem_rdimm_2d_uuid_spec = {
+	.uuid = UUID_DDR_DMEM_RDIMM_2D,
+};
+
+#if TRUSTED_BOARD_BOOT
+static const io_uuid_spec_t ddr_fw_key_cert_uuid_spec = {
+	.uuid = UUID_DDR_FW_KEY_CERT,
+};
+static const io_uuid_spec_t ddr_udimm_fw_cert_uuid_spec = {
+	.uuid = UUID_DDR_UDIMM_FW_CONTENT_CERT,
+};
+static const io_uuid_spec_t ddr_rdimm_fw_cert_uuid_spec = {
+	.uuid = UUID_DDR_RDIMM_FW_CONTENT_CERT,
+};
+#endif
+
+static int open_ddr_fip(const uintptr_t spec);
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+/* By default, ARM platforms load images from the FIP */
+static const struct plat_io_policy ddr_policies[] = {
+	[DDR_FIP_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&backend_dev_handle,
+		(uintptr_t)&ddr_fip_block_spec,
+		NULL
+	},
+	[DDR_IMEM_UDIMM_1D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_imem_udimm_1d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_IMEM_UDIMM_2D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_imem_udimm_2d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_DMEM_UDIMM_1D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_dmem_udimm_1d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_DMEM_UDIMM_2D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_dmem_udimm_2d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_IMEM_RDIMM_1D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_imem_rdimm_1d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_IMEM_RDIMM_2D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_imem_rdimm_2d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_DMEM_RDIMM_1D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_dmem_rdimm_1d_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_DMEM_RDIMM_2D_IMAGE_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_dmem_rdimm_2d_uuid_spec,
+		open_ddr_fip
+	},
+#if TRUSTED_BOARD_BOOT
+	[DDR_FW_KEY_CERT_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_fw_key_cert_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_UDIMM_FW_CONTENT_CERT_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_udimm_fw_cert_uuid_spec,
+		open_ddr_fip
+	},
+	[DDR_RDIMM_FW_CONTENT_CERT_ID - DDR_FIP_IMAGE_ID] = {
+		&ddr_fip_dev_handle,
+		(uintptr_t)&ddr_rdimm_fw_cert_uuid_spec,
+		open_ddr_fip
+	},
+#endif
+};
+
+static int open_ddr_fip(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	/* See if a Firmware Image Package is available */
+	result = io_dev_init(ddr_fip_dev_handle, (uintptr_t)DDR_FIP_IMAGE_ID);
+	if (result == 0) {
+		result = io_open(ddr_fip_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using FIP\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+/* The image can be one of the DDR PHY images, which can be sleected via DDR
+ * policies
+ */
+int plat_get_ddr_fip_image_source(unsigned int image_id, uintptr_t *dev_handle,
+				  uintptr_t *image_spec,
+				  int (*check)(const uintptr_t spec))
+{
+	int result = -1;
+	const struct plat_io_policy *policy;
+
+	if (image_id >= (DDR_FIP_IMAGE_ID + ARRAY_SIZE(ddr_policies))) {
+		return result;
+	}
+
+	policy = &ddr_policies[image_id - DDR_FIP_IMAGE_ID];
+	if (image_id == DDR_FIP_IMAGE_ID) {
+		result = check(policy->image_spec);
+	} else {
+		result = policy->check(policy->image_spec);
+	}
+	if (result == 0) {
+		*image_spec = policy->image_spec;
+		*dev_handle = *(policy->dev_handle);
+	}
+	return result;
+}
+
+int ddr_fip_setup(const io_dev_connector_t *fip_dev_con, unsigned int boot_dev)
+{
+	int io_result;
+	size_t ddr_fip_offset = PLAT_DDR_FIP_OFFSET;
+
+	/* Open connections to ddr fip and cache the handles */
+	io_result = io_dev_open(fip_dev_con, (uintptr_t)&ddr_fip,
+				&ddr_fip_dev_handle);
+	assert(io_result == 0);
+
+	switch (boot_dev) {
+#if QSPI_BOOT
+	case BOOT_DEVICE_QSPI:
+		ddr_fip_offset += NXP_QSPI_FLASH_ADDR;
+		break;
+#endif
+#if NOR_BOOT
+	case BOOT_DEVICE_IFC_NOR:
+		ddr_fip_offset += NXP_NOR_FLASH_ADDR;
+		break;
+#endif
+#if FLEXSPI_NOR_BOOT
+	case BOOT_DEVICE_FLEXSPI_NOR:
+		ddr_fip_offset += NXP_FLEXSPI_FLASH_ADDR;
+		break;
+#endif
+	default:
+		break;
+	}
+
+	ddr_fip_block_spec.offset = ddr_fip_offset;
+
+	return io_result;
+}
diff --git a/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.h b/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.h
new file mode 100644
index 0000000..6df3902
--- /dev/null
+++ b/plat/nxp/common/fip_handler/ddr_fip/ddr_io_storage.h
@@ -0,0 +1,26 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef DDR_IO_STORAGE_H
+#define DDR_IO_STORAGE_H
+
+#include <drivers/io/io_driver.h>
+
+#ifndef PLAT_DDR_FIP_OFFSET
+#define PLAT_DDR_FIP_OFFSET	0x800000
+#endif
+
+#ifndef PLAT_DDR_FIP_MAX_SIZE
+#define PLAT_DDR_FIP_MAX_SIZE	0x32000
+#endif
+
+int ddr_fip_setup(const io_dev_connector_t *fip_dev_con, unsigned int boot_dev);
+int plat_get_ddr_fip_image_source(unsigned int image_id, uintptr_t *dev_handle,
+				  uintptr_t *image_spec,
+				  int (*check)(const uintptr_t spec));
+
+#endif	/*	DDR_IO_STORAGE_H	*/
diff --git a/plat/nxp/common/fip_handler/fuse_fip/fuse.mk b/plat/nxp/common/fip_handler/fuse_fip/fuse.mk
new file mode 100644
index 0000000..d8f5ae6
--- /dev/null
+++ b/plat/nxp/common/fip_handler/fuse_fip/fuse.mk
@@ -0,0 +1,100 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+NEED_FUSE	:= yes
+
+$(eval $(call add_define, PLAT_DEF_FIP_UUID))
+$(eval $(call add_define, POLICY_FUSE_PROVISION))
+$(eval $(call add_define, PLAT_TBBR_IMG_DEF))
+
+$(eval $(call SET_NXP_MAKE_FLAG,IMG_LOADR_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,SFP_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,GPIO_NEEDED,BL2))
+
+FIP_HANDLER_PATH	:=  ${PLAT_COMMON_PATH}/fip_handler
+FIP_HANDLER_COMMON_PATH	:=  ${FIP_HANDLER_PATH}/common
+
+FUSE_SOURCES		:=  ${FIP_HANDLER_PATH}/fuse_fip/fuse_io_storage.c
+
+PLAT_INCLUDES		+=  -I${FIP_HANDLER_COMMON_PATH}\
+			    -I${FIP_HANDLER_PATH}/fuse_fip
+
+FUSE_FIP_NAME		:=	fuse_fip.bin
+
+fip_fuse: ${BUILD_PLAT}/${FUSE_FIP_NAME}
+
+ifeq (${FUSE_PROV_FILE},)
+
+$(shell cp tools/nxp/plat_fiptool/plat_fiptool.mk ${PLAT_DIR})
+
+else
+ifeq (${TRUSTED_BOARD_BOOT},1)
+FUSE_PROV_FILE_SB = $(notdir ${FUSE_PROV_FILE})_prov.sb
+FUSE_FIP_ARGS += --fuse-prov ${BUILD_PLAT}/${FUSE_PROV_FILE_SB}
+FUSE_FIP_DEPS += ${BUILD_PLAT}/${FUSE_PROV_FILE_SB}
+else
+FUSE_FIP_ARGS += --fuse-prov ${FUSE_PROV_FILE}
+FUSE_FIP_DEPS += ${FUSE_PROV_FILE}
+endif
+endif
+
+ifeq (${FUSE_UP_FILE},)
+else
+ifeq (${TRUSTED_BOARD_BOOT},1)
+FUSE_UP_FILE_SB = $(notdir ${FUSE_UP_FILE})_up.sb
+FUSE_FIP_ARGS += --fuse-up ${BUILD_PLAT}/${FUSE_UP_FILE_SB}
+FUSE_FIP_DEPS += ${BUILD_PLAT}/${FUSE_UP_FILE_SB}
+else
+FUSE_FIP_ARGS += --fuse-up ${FUSE_UP_FILE}
+FUSE_FIP_DEPS += ${FUSE_UP_FILE}
+endif
+endif
+
+ifeq (${TRUSTED_BOARD_BOOT},1)
+
+ifeq (${MBEDTLS_DIR},)
+else
+  $(error Error: Trusted Board Boot with X509 certificates not supported with FUSE_PROG build option)
+endif
+
+# Path to CST directory is required to generate the CSF header
+# and prepend it to image before fip image gets generated
+ifeq (${CST_DIR},)
+  $(error Error: CST_DIR not set)
+endif
+
+ifeq (${FUSE_INPUT_FILE},)
+FUSE_INPUT_FILE := $(PLAT_DRIVERS_PATH)/auth/csf_hdr_parser/${CSF_FILE}
+endif
+
+ifeq (${FUSE_PROV_FILE},)
+else
+${BUILD_PLAT}/${FUSE_PROV_FILE_SB}: ${FUSE_PROV_FILE}
+	@echo " Generating CSF Header for $@ $<"
+	$(CST_DIR)/create_hdr_esbc --in $< --out $@ --app_off ${CSF_HDR_SZ} \
+					--app $< ${FUSE_INPUT_FILE}
+endif
+
+ifeq (${FUSE_UP_FILE},)
+else
+${BUILD_PLAT}/${FUSE_UP_FILE_SB}: ${FUSE_UP_FILE}
+	@echo " Generating CSF Header for $@ $<"
+	$(CST_DIR)/create_hdr_esbc --in $< --out $@ --app_off ${CSF_HDR_SZ} \
+					--app $< ${FUSE_INPUT_FILE}
+endif
+
+endif
+
+${BUILD_PLAT}/${FUSE_FIP_NAME}: fiptool ${FUSE_FIP_DEPS}
+ifeq (${FUSE_FIP_DEPS},)
+	$(error "Error: FUSE_PROV_FILE or/and FUSE_UP_FILE needs to point to the right file")
+endif
+	${FIPTOOL} create ${FUSE_FIP_ARGS} $@
+	${FIPTOOL} info $@
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@${ECHO_BLANK_LINE}
diff --git a/plat/nxp/common/fip_handler/fuse_fip/fuse_io.h b/plat/nxp/common/fip_handler/fuse_fip/fuse_io.h
new file mode 100644
index 0000000..e8775d0
--- /dev/null
+++ b/plat/nxp/common/fip_handler/fuse_fip/fuse_io.h
@@ -0,0 +1,27 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+#ifndef FUSE_IO_H
+#define FUSE_IO_H
+
+#include <drivers/io/io_driver.h>
+
+/* Can be overridden from platform_def.h file.
+ */
+#ifndef PLAT_FUSE_FIP_OFFSET
+#define PLAT_FUSE_FIP_OFFSET	0x880000
+#endif
+#ifndef PLAT_FUSE_FIP_MAX_SIZE
+#define PLAT_FUSE_FIP_MAX_SIZE	0x80000
+#endif
+
+int fip_fuse_provisioning(uintptr_t image_buf, uint32_t size);
+int fuse_fip_setup(const io_dev_connector_t *fip_dev_con, unsigned int boot_dev);
+int plat_get_fuse_image_source(unsigned int image_id,
+			       uintptr_t *dev_handle,
+			       uintptr_t *image_spec,
+			       int (*check)(const uintptr_t spec));
+#endif	/*	FUSE_IO_H	*/
diff --git a/plat/nxp/common/fip_handler/fuse_fip/fuse_io_storage.c b/plat/nxp/common/fip_handler/fuse_fip/fuse_io_storage.c
new file mode 100644
index 0000000..017ffcf
--- /dev/null
+++ b/plat/nxp/common/fip_handler/fuse_fip/fuse_io_storage.c
@@ -0,0 +1,223 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <dcfg.h>
+#include <drivers/delay_timer.h>
+#include <fuse_prov.h>
+#include <io_block.h>
+#include <io_driver.h>
+#include <io_fip.h>
+#include <io_memmap.h>
+#include <io_storage.h>
+#include <lib/utils.h>
+#include <nxp_gpio.h>
+#include <sfp.h>
+#include <sfp_error_codes.h>
+#include <tools_share/firmware_image_package.h>
+
+#include "fuse_io.h"
+#include <load_img.h>
+#include <plat/common/platform.h>
+#include "plat_common.h"
+#include "platform_def.h"
+
+extern uintptr_t backend_dev_handle;
+
+static uint32_t fuse_fip;
+
+static uintptr_t fuse_fip_dev_handle;
+
+static io_block_spec_t fuse_fip_block_spec = {
+	.offset = PLAT_FUSE_FIP_OFFSET,
+	.length = PLAT_FUSE_FIP_MAX_SIZE
+};
+
+static const io_uuid_spec_t fuse_prov_uuid_spec = {
+	.uuid = UUID_FUSE_PROV,
+};
+
+static const io_uuid_spec_t fuse_up_uuid_spec = {
+	.uuid = UUID_FUSE_UP,
+};
+
+static int open_fuse_fip(const uintptr_t spec);
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+/* By default, ARM platforms load images from the FIP */
+static const struct plat_io_policy fuse_policies[] = {
+	[FUSE_FIP_IMAGE_ID - FUSE_FIP_IMAGE_ID] = {
+		&backend_dev_handle,
+		(uintptr_t)&fuse_fip_block_spec,
+		NULL
+	},
+	[FUSE_PROV_IMAGE_ID - FUSE_FIP_IMAGE_ID] = {
+		&fuse_fip_dev_handle,
+		(uintptr_t)&fuse_prov_uuid_spec,
+		open_fuse_fip
+	},
+	[FUSE_UP_IMAGE_ID - FUSE_FIP_IMAGE_ID] = {
+		&fuse_fip_dev_handle,
+		(uintptr_t)&fuse_up_uuid_spec,
+		open_fuse_fip
+	}
+};
+
+static int open_fuse_fip(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	/* See if a Firmware Image Package is available */
+	result = io_dev_init(fuse_fip_dev_handle, (uintptr_t)FUSE_FIP_IMAGE_ID);
+	if (result == 0) {
+		result = io_open(fuse_fip_dev_handle,
+				 spec,
+				 &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using FIP\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+/* The image can be one of the DDR PHY images, which can be sleected via DDR
+ * policies
+ */
+int plat_get_fuse_image_source(unsigned int image_id,
+			       uintptr_t *dev_handle,
+			       uintptr_t *image_spec,
+			       int (*check)(const uintptr_t spec))
+{
+	int result;
+	const struct plat_io_policy *policy;
+
+	assert(image_id < (FUSE_FIP_IMAGE_ID + ARRAY_SIZE(fuse_policies)));
+
+	policy = &fuse_policies[image_id - FUSE_FIP_IMAGE_ID];
+
+	if (image_id == FUSE_FIP_IMAGE_ID) {
+		result = check(policy->image_spec);
+	} else {
+		result = policy->check(policy->image_spec);
+	}
+
+	if (result == 0) {
+		*image_spec = policy->image_spec;
+		*dev_handle = *(policy->dev_handle);
+	}
+	return result;
+}
+
+int fuse_fip_setup(const io_dev_connector_t *fip_dev_con, unsigned int boot_dev)
+{
+	int io_result;
+	size_t fuse_fip_offset = PLAT_FUSE_FIP_OFFSET;
+
+	/* Open connections to fuse fip and cache the handles */
+	io_result = io_dev_open(fip_dev_con, (uintptr_t)&fuse_fip,
+				&fuse_fip_dev_handle);
+
+	assert(io_result == 0);
+
+	switch (boot_dev) {
+#if QSPI_BOOT
+	case BOOT_DEVICE_QSPI:
+		fuse_fip_offset += NXP_QSPI_FLASH_ADDR;
+		break;
+#endif
+#if NOR_BOOT
+	case BOOT_DEVICE_IFC_NOR:
+		fuse_fip_offset += NXP_NOR_FLASH_ADDR;
+		break;
+#endif
+#if FLEXSPI_NOR_BOOT
+	case BOOT_DEVICE_FLEXSPI_NOR:
+		fuse_fip_offset += NXP_FLEXSPI_FLASH_ADDR;
+		break;
+#endif
+	default:
+		break;
+	}
+
+	fuse_fip_block_spec.offset = fuse_fip_offset;
+
+	return io_result;
+}
+
+int fip_fuse_provisioning(uintptr_t image_buf, uint32_t size)
+{
+	uint32_t bit_num;
+	uint32_t *gpio_base_addr = NULL;
+	struct fuse_hdr_t *fuse_hdr = NULL;
+	uint8_t barker[] = {0x68U, 0x39U, 0x27U, 0x81U};
+	int ret = -1;
+
+	if (sfp_check_oem_wp() == 0) {
+		ret = load_img(FUSE_PROV_IMAGE_ID, &image_buf, &size);
+		if (ret != 0) {
+			ERROR("Failed to load FUSE PRIV image\n");
+			assert(ret == 0);
+		}
+		fuse_hdr = (struct fuse_hdr_t *)image_buf;
+
+		/* Check barker code */
+		if (memcmp(fuse_hdr->barker, barker, sizeof(barker)) != 0) {
+			ERROR("FUSE Barker code mismatch.\n");
+			error_handler(ERROR_FUSE_BARKER);
+			return 1;
+		}
+
+		/* Check if GPIO pin to be set for POVDD */
+		if (((fuse_hdr->flags >> FLAG_POVDD_SHIFT) & 0x1) != 0) {
+			gpio_base_addr =
+				select_gpio_n_bitnum(fuse_hdr->povdd_gpio,
+						     &bit_num);
+			/*
+			 * Add delay so that Efuse gets the power
+			 * when GPIO is enabled.
+			 */
+			ret = set_gpio_bit(gpio_base_addr, bit_num);
+			mdelay(EFUSE_POWERUP_DELAY_mSec);
+		} else {
+			ret = (board_enable_povdd() == true) ? 0 : PLAT_ERROR_ENABLE_POVDD;
+		}
+		if (ret != 0) {
+			ERROR("Error enabling board POVDD: %d\n", ret);
+			ERROR("Only SFP mirror register will be set.\n");
+		}
+
+		provision_fuses(image_buf, ret == 0);
+
+		 /* Check if GPIO pin to be reset for POVDD */
+		if (((fuse_hdr->flags >> FLAG_POVDD_SHIFT) & 0x1) != 0) {
+			if (gpio_base_addr == NULL) {
+				gpio_base_addr =
+					select_gpio_n_bitnum(
+							fuse_hdr->povdd_gpio,
+							&bit_num);
+			}
+			ret = clr_gpio_bit(gpio_base_addr, bit_num);
+		} else {
+			ret = board_disable_povdd() ? 0 : PLAT_ERROR_DISABLE_POVDD;
+		}
+
+		if (ret != 0) {
+			ERROR("Error disabling board POVDD: %d\n", ret);
+		}
+	}
+	return 0;
+}
diff --git a/plat/nxp/common/img_loadr/img_loadr.mk b/plat/nxp/common/img_loadr/img_loadr.mk
new file mode 100644
index 0000000..f64b1fa
--- /dev/null
+++ b/plat/nxp/common/img_loadr/img_loadr.mk
@@ -0,0 +1,21 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+IMG_LOADR_DRIVERS_PATH	:=  ${PLAT_COMMON_PATH}/img_loadr
+
+IMG_LOADR_SOURCES	:=  $(IMG_LOADR_DRIVERS_PATH)/load_img.c
+PLAT_INCLUDES		+= -I$(IMG_LOADR_DRIVERS_PATH)
+
+ifeq (${BL_COMM_IMG_LOADR_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${IMG_LOADR_SOURCES}
+else
+ifeq (${BL2_IMG_LOADR_NEEDED},yes)
+BL2_SOURCES		+= ${IMG_LOADR_SOURCES}
+endif
+ifeq (${BL31_IMG_LOADR_NEEDED},yes)
+BL31_SOURCES		+= ${IMG_LOADR_SOURCES}
+endif
+endif
diff --git a/plat/nxp/common/img_loadr/load_img.c b/plat/nxp/common/img_loadr/load_img.c
new file mode 100644
index 0000000..c185c36
--- /dev/null
+++ b/plat/nxp/common/img_loadr/load_img.c
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <common/bl_common.h>
+#include <common/desc_image_load.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+
+#include "load_img.h"
+
+/******************************************************************************
+ * This function can be used to load DDR PHY/FUSE Images
+ *
+ * @param [in] image_id		 Image ID to be loaded
+ *
+ * @param [in,out]  image_base   Location at which the image should be loaded
+ *				 In case image is prepended by a CSF header,
+ *				 image_base is pointer to actual image after
+ *				 the header
+ *
+ * @param [in,out]  image_size   User should pass the maximum size of the image
+ *				 possible.(Buffer size starting from image_base)
+ *				 Actual size of the image loaded is returned
+ *				 back.
+ *****************************************************************************/
+int load_img(unsigned int image_id, uintptr_t *image_base,
+		      uint32_t *image_size)
+{
+	int err = 0;
+
+	image_desc_t img_info = {
+		.image_id = image_id,
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_IMAGE_BINARY,
+				VERSION_2, image_info_t, 0),
+#ifdef CSF_HEADER_PREPENDED
+		.image_info.image_base = *image_base - CSF_HDR_SZ,
+		.image_info.image_max_size = *image_size + CSF_HDR_SZ,
+#else
+		.image_info.image_base = *image_base,
+		.image_info.image_max_size = *image_size,
+#endif
+	};
+
+	/* Create MMU entry for the CSF header */
+#if PLAT_XLAT_TABLES_DYNAMIC
+#ifdef CSF_HEADER_PREPENDED
+	mmap_add_dynamic_region(img_info.image_info.image_base,
+			img_info.image_info.image_base,
+			CSF_HDR_SZ,
+			MT_MEMORY | MT_RW | MT_SECURE);
+#endif
+#endif
+
+	VERBOSE("BL2: Loading IMG %d\n", image_id);
+	err = load_auth_image(image_id, &img_info.image_info);
+	if (err != 0) {
+		VERBOSE("Failed to load IMG %d\n", image_id);
+		return err;
+	}
+
+#ifdef CSF_HEADER_PREPENDED
+	*image_base = img_info.image_info.image_base + CSF_HDR_SZ;
+	*image_size = img_info.image_info.image_size - CSF_HDR_SZ;
+#if PLAT_XLAT_TABLES_DYNAMIC
+	mmap_remove_dynamic_region(img_info.image_info.image_base,
+				   CSF_HDR_SZ);
+#endif
+#else
+	*image_base = img_info.image_info.image_base;
+	*image_size = img_info.image_info.image_size;
+#endif
+
+	return err;
+}
diff --git a/plat/nxp/common/img_loadr/load_img.h b/plat/nxp/common/img_loadr/load_img.h
new file mode 100644
index 0000000..6f9de32
--- /dev/null
+++ b/plat/nxp/common/img_loadr/load_img.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef LOAD_IMAGE_H
+#define LOAD_IMAGE_H
+
+int load_img(unsigned int image_id, uintptr_t *image_base,
+		      uint32_t *image_size);
+
+#endif /* LOAD_IMAGE_H */
diff --git a/plat/nxp/common/include/default/ch_2/soc_default_base_addr.h b/plat/nxp/common/include/default/ch_2/soc_default_base_addr.h
new file mode 100644
index 0000000..175a796
--- /dev/null
+++ b/plat/nxp/common/include/default/ch_2/soc_default_base_addr.h
@@ -0,0 +1,69 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SOC_DEFAULT_BASE_ADDR_H
+#define SOC_DEFAULT_BASE_ADDR_H
+
+/* CCSR mmu_def.h */
+#define NXP_CCSR_ADDR			0x01000000
+#define NXP_CCSR_SIZE			0x0F000000
+
+#define NXP_DCSR_ADDR			0x20000000
+#define NXP_DCSR_SIZE			0x4000000
+
+/* Flex-SPI controller address */
+#define NXP_FLEXSPI_ADDR		0x020C0000
+/* QSPI Flash Start address */
+#define NXP_QSPI_FLASH_ADDR		0x40000000
+/* NOR Flash Start address */
+#define NXP_IFC_REGION_ADDR		0x60000000
+#define NXP_NOR_FLASH_ADDR		NXP_IFC_REGION_ADDR
+
+/* MMU 500 soc.c*/
+#define NXP_SMMU_ADDR			0x09000000
+
+#define NXP_SNVS_ADDR			0x01E90000
+
+#define NXP_DCFG_ADDR			0x01EE0000
+#define NXP_SFP_ADDR			0x01E80000
+#define NXP_RCPM_ADDR			0x01EE2000
+#define NXP_CSU_ADDR			0x01510000
+#define NXP_SCFG_ADDR			0x01570000
+#define NXP_DCSR_ADDR			0x20000000
+#define NXP_DCSR_DCFG_ADDR		(NXP_DCSR_ADDR + 0x00140000)
+#define NXP_I2C_ADDR			0x02180000
+#define NXP_ESDHC_ADDR			0x01560000
+#define NXP_UART_ADDR			0x021C0500
+#define NXP_UART1_ADDR			0x021C0600
+
+#define NXP_GPIO1_ADDR			0x02300000
+#define NXP_GPIO2_ADDR			0x02310000
+#define NXP_GPIO3_ADDR			0x02320000
+#define NXP_GPIO4_ADDR			0x02330000
+
+#define NXP_WDOG1_NS_ADDR		0x02390000
+#define NXP_WDOG2_NS_ADDR		0x023A0000
+#define NXP_WDOG1_TZ_ADDR		0x023B0000
+#define NXP_WDOG2_TZ_ADDR		0x023C0000
+
+#define NXP_TIMER_STATUS_ADDR		0x023F0000
+
+#define NXP_GICD_4K_ADDR		0x01401000
+#define NXP_GICC_4K_ADDR		0x01402000
+#define NXP_GICD_64K_ADDR		0x01410000
+#define NXP_GICC_64K_ADDR		0x01420000
+
+#define NXP_CAAM_ADDR			0x01700000
+
+#define NXP_TZC_ADDR			0x01500000
+#define NXP_DDR_ADDR			0x01080000
+
+#define NXP_TIMER_ADDR			0x02B00000
+#define NXP_CCI_ADDR			0x01180000
+#define NXP_RESET_ADDR			0x01E60000
+#define NXP_SEC_REGFILE_ADDR		0x01E88000
+#endif	/*	SOC_DEFAULT_BASE_ADDR_H		*/
diff --git a/plat/nxp/common/include/default/ch_2/soc_default_helper_macros.h b/plat/nxp/common/include/default/ch_2/soc_default_helper_macros.h
new file mode 100644
index 0000000..84f07e6
--- /dev/null
+++ b/plat/nxp/common/include/default/ch_2/soc_default_helper_macros.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SOC_DEFAULT_HELPER_MACROS_H
+#define SOC_DEFAULT_HELPER_MACROS_H
+
+#ifdef NXP_OCRAM_TZPC_ADDR
+
+/* 0x1: means 4 KB
+ * 0x2: means 8 KB
+ */
+#define TZPC_BLOCK_SIZE			0x1000
+#endif
+
+/* DDR controller offsets and defines */
+#ifdef NXP_DDR_ADDR
+
+#define DDR_CFG_2_OFFSET                0x114
+#define CFG_2_FORCE_REFRESH             0x80000000
+
+#endif /* NXP_DDR_ADDR */
+
+ /* Reset block register offsets */
+#ifdef NXP_RESET_ADDR
+
+/* Register Offset */
+#define RST_RSTCR_OFFSET		0x0
+#define RST_RSTRQMR1_OFFSET		0x10
+#define RST_RSTRQSR1_OFFSET		0x18
+#define BRR_OFFSET			0x60
+
+/* helper macros */
+#define RSTRQSR1_SWRR			0x800
+#define RSTRQMR_RPTOE_MASK		(1 << 19)
+
+#endif /* NXP_RESET_ADDR */
+
+/* Secure-Register-File register offsets and bit masks */
+#ifdef NXP_RST_ADDR
+/* Register Offset */
+#define CORE_HOLD_OFFSET		0x140
+#define RSTCNTL_OFFSET			0x180
+
+/* Helper macros */
+#define SW_RST_REQ_INIT			0x1
+#endif
+
+#ifdef NXP_RCPM_ADDR
+/* RCPM Register Offsets */
+#define RCPM_PCPH20SETR_OFFSET		0x0D4
+#define RCPM_PCPH20CLRR_OFFSET		0x0D8
+#define RCPM_POWMGTCSR_OFFSET		0x130
+#define RCPM_IPPDEXPCR0_OFFSET		0x140
+#define RCPM_POWMGTCSR_LPM20_REQ	0x00100000
+#endif /* NXP_RCPM_ADDR */
+
+#define DCFG_SBEESR2_ADDR		0x20140534
+#define DCFG_MBEESR2_ADDR		0x20140544
+/* SBEESR and MBEESR bit mask */
+#define OCRAM_EESR_MASK			0x00000060
+
+#endif	/*	SOC_DEFAULT_HELPER_MACROS_H	*/
diff --git a/plat/nxp/common/include/default/ch_3/soc_default_base_addr.h b/plat/nxp/common/include/default/ch_3/soc_default_base_addr.h
new file mode 100644
index 0000000..e8a7645
--- /dev/null
+++ b/plat/nxp/common/include/default/ch_3/soc_default_base_addr.h
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SOC_DEFAULT_BASE_ADDR_H
+#define SOC_DEFAULT_BASE_ADDR_H
+
+/* CCSR mmu_def.h */
+#define NXP_CCSR_ADDR			0x1000000
+#define NXP_CCSR_SIZE			0xF000000
+
+#define NXP_DCSR_ADDR			0x700000000
+#define NXP_DCSR_SIZE			0x40000000
+
+/* Flex-SPI controller address */
+#define NXP_FLEXSPI_ADDR		0x020C0000
+/* Flex-SPI Flash Start address */
+#define NXP_FLEXSPI_FLASH_ADDR		0x20000000
+
+/* MMU 500 soc.c*/
+#define NXP_SMMU_ADDR			0x05000000
+
+#define NXP_SNVS_ADDR			0x01E90000
+
+#define NXP_DCFG_ADDR			0x01E00000
+#define NXP_PMU_CCSR_ADDR		0x01E30000
+#define NXP_PMU_DCSR_ADDR		0x700123000
+#define NXP_PMU_ADDR                    NXP_PMU_CCSR_ADDR
+#define NXP_SFP_ADDR			0x01E80000
+#define NXP_SCFG_ADDR			0x01FC0000
+#define NXP_I2C_ADDR			0x02000000
+#define NXP_ESDHC_ADDR			0x02140000
+#define NXP_ESDHC2_ADDR			0x02150000
+#define NXP_UART_ADDR			0x021C0000
+#define NXP_UART1_ADDR			0x021D0000
+
+#define NXP_GPIO1_ADDR			0x02300000
+#define NXP_GPIO2_ADDR			0x02310000
+#define NXP_GPIO3_ADDR			0x02320000
+#define NXP_GPIO4_ADDR			0x02330000
+
+#define NXP_WDOG1_NS_ADDR		0x02390000
+#define NXP_WDOG2_NS_ADDR		0x023A0000
+#define NXP_WDOG1_TZ_ADDR		0x023B0000
+#define NXP_WDOG2_TZ_ADDR		0x023C0000
+
+#define NXP_TIMER_STATUS_ADDR		0x023F0000
+
+#define NXP_GICD_ADDR			0x06000000
+#define NXP_GICR_ADDR			0x06200000
+#define NXP_GICR_SGI_ADDR		0x06210000
+
+#define NXP_CAAM_ADDR			0x08000000
+
+#define NXP_TZC_ADDR			0x01100000
+#define NXP_TZC2_ADDR			0x01110000
+#define NXP_TZC3_ADDR			0x01120000
+
+#define NXP_RESET_ADDR			0x01E60000
+#define NXP_SEC_REGFILE_ADDR		0x01E88000
+#endif	/*	SOC_DEFAULT_BASE_ADDR_H		*/
diff --git a/plat/nxp/common/include/default/ch_3_2/soc_default_base_addr.h b/plat/nxp/common/include/default/ch_3_2/soc_default_base_addr.h
new file mode 100644
index 0000000..0a4228b
--- /dev/null
+++ b/plat/nxp/common/include/default/ch_3_2/soc_default_base_addr.h
@@ -0,0 +1,88 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SOC_DEFAULT_BASE_ADDR_H
+#define SOC_DEFAULT_BASE_ADDR_H
+
+/* CCSR mmu_def.h */
+#define NXP_CCSR_ADDR			0x1000000
+#define NXP_CCSR_SIZE			0xF000000
+
+#define NXP_DCSR_ADDR			0x700000000
+#define NXP_DCSR_SIZE			0x40000000
+
+/* Flex-SPI controller address */
+#define NXP_FLEXSPI_ADDR		0x020C0000
+/* Flex-SPI Flash Start address */
+#define NXP_FLEXSPI_FLASH_ADDR		0x20000000
+
+/* MMU 500 soc.c*/
+#define NXP_SMMU_ADDR			0x05000000
+
+/* CCI400 base address */
+#define NXP_CCI_ADDR			0x04090000
+
+#define NXP_SNVS_ADDR			0x01E90000
+
+#define NXP_DCFG_ADDR			0x01E00000
+#define NXP_PMU_CCSR_ADDR		0x01E30000
+#define NXP_PMU_DCSR_ADDR		0x700123000
+#define NXP_PMU_ADDR                    NXP_PMU_CCSR_ADDR
+#define NXP_SFP_ADDR			0x01E80000
+#define NXP_SCFG_ADDR			0x01FC0000
+#define NXP_I2C_ADDR			0x02000000
+#define NXP_ESDHC_ADDR			0x02140000
+#define NXP_ESDHC2_ADDR			0x02150000
+#define NXP_UART_ADDR			0x021C0000
+#define NXP_UART1_ADDR			0x021D0000
+
+#define NXP_GPIO1_ADDR			0x02300000
+#define NXP_GPIO2_ADDR			0x02310000
+#define NXP_GPIO3_ADDR			0x02320000
+#define NXP_GPIO4_ADDR			0x02330000
+
+#define NXP_WDOG1_NS_ADDR		0x02390000
+#define NXP_WDOG2_NS_ADDR		0x023A0000
+#define NXP_WDOG1_TZ_ADDR		0x023B0000
+#define NXP_WDOG2_TZ_ADDR		0x023C0000
+
+#define NXP_TIMER_STATUS_ADDR		0x023F0000
+
+#define NXP_GICD_ADDR			0x06000000
+#define NXP_GICR_ADDR			0x06200000
+#define NXP_GICR_SGI_ADDR		0x06210000
+
+#define NXP_CAAM_ADDR			0x08000000
+
+#define NXP_TZC_ADDR			0x01100000
+#define NXP_TZC2_ADDR			0x01110000
+#define NXP_TZC3_ADDR			0x01120000
+
+#define NXP_TIMER_ADDR			0x023E0000
+
+#define NXP_RESET_ADDR			0x01E60000
+#define NXP_SEC_REGFILE_ADDR		0x01E88000
+#define NXP_RST_ADDR			0x01E88000
+
+#define TPMWAKEMR0_ADDR		0x700123c50
+#define TZPC_BLOCK_SIZE		0x1000
+
+#define NXP_TZC_ADDR			0x01100000
+#define NXP_TZC2_ADDR			0x01110000
+#define NXP_TZC3_ADDR			0x01120000
+#define NXP_TZC4_ADDR			0x01130000
+#define NXP_DDR_ADDR			0x01080000
+#define NXP_DDR2_ADDR			0x01090000
+
+#define NXP_OCRAM_TZPC_ADDR		0x02200000
+
+#define NXP_CCN_ADDR			0x04000000
+#define NXP_CCN_HNI_ADDR		0x04080000
+#define NXP_CCN_HN_F_0_ADDR		0x04200000
+
+#define NXP_EPU_ADDR			0x700060000
+#endif	/*	SOC_DEFAULT_BASE_ADDR_H		*/
diff --git a/plat/nxp/common/include/default/ch_3_2/soc_default_helper_macros.h b/plat/nxp/common/include/default/ch_3_2/soc_default_helper_macros.h
new file mode 100644
index 0000000..1edd28d
--- /dev/null
+++ b/plat/nxp/common/include/default/ch_3_2/soc_default_helper_macros.h
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SOC_DEFAULT_HELPER_MACROS_H
+#define SOC_DEFAULT_HELPER_MACROS_H
+
+#ifdef NXP_OCRAM_TZPC_ADDR
+
+/* 0x1: means 4 KB
+ * 0x2: means 8 KB
+ */
+#define TZPC_BLOCK_SIZE		0x1000
+#endif
+
+/* DDR controller offsets and defines */
+#ifdef NXP_DDR_ADDR
+
+#define DDR_CFG_2_OFFSET                0x114
+#define CFG_2_FORCE_REFRESH             0x80000000
+
+#endif /* NXP_DDR_ADDR */
+
+ /* Reset block register offsets */
+#ifdef NXP_RESET_ADDR
+
+/* Register Offset */
+#define RST_RSTCR_OFFSET		0x0
+#define RST_RSTRQMR1_OFFSET		0x10
+#define RST_RSTRQSR1_OFFSET		0x18
+#define BRR_OFFSET			0x60
+
+/* helper macros */
+#define RSTRQSR1_SWRR			0x800
+#define RSTRQMR_RPTOE_MASK		(1 << 19)
+
+#endif /* NXP_RESET_ADDR */
+
+/* secmon register offsets and bitfields */
+#define SECMON_HPCOMR_OFFSET	0x4
+#define SECMON_HPCOMR_NPSWAEN	0x80000000
+
+/* Secure-Register-File register offsets and bit masks */
+#ifdef NXP_RST_ADDR
+/* Register Offset */
+#define CORE_HOLD_OFFSET		0x140
+#define RSTCNTL_OFFSET			0x180
+
+/* Helper macros */
+#define SW_RST_REQ_INIT			0x1
+#endif
+
+#ifdef NXP_CCN_ADDR
+#define NXP_CCN_HN_F_1_ADDR		0x04210000
+
+#define CCN_HN_F_SAM_NODEID_MASK	0x7f
+#define CCN_HN_F_SNP_DMN_CTL_OFFSET	0x200
+#define CCN_HN_F_SNP_DMN_CTL_SET_OFFSET	0x210
+#define CCN_HN_F_SNP_DMN_CTL_CLR_OFFSET	0x220
+#define CCN_HN_F_SNP_DMN_CTL_MASK	0x80a00
+#define CCN_HNF_NODE_COUNT              8
+#define CCN_HNF_OFFSET                  0x10000
+
+#define SA_AUX_CTRL_REG_OFFSET		0x500
+#define NUM_HNI_NODE			2
+#define CCN_HNI_MEMORY_MAP_SIZE		0x10000
+
+#define PCIeRC_RN_I_NODE_ID_OFFSET	0x8
+#define PoS_CONTROL_REG_OFFSET		0x0
+#define POS_EARLY_WR_COMP_EN		0x20
+#define HNI_POS_EN			0x01
+#define POS_TERMINATE_BARRIERS		0x10
+#define SERIALIZE_DEV_nGnRnE_WRITES	0x200
+#define ENABLE_ERR_SIGNAL_TO_MN		0x4
+#define ENABLE_RESERVE_BIT53		0x400
+#define ENABLE_WUO			0x10
+#endif /* NXP_CCN_ADDR */
+
+#define DCFG_SBEESR2_ADDR		0x00100534
+#define DCFG_MBEESR2_ADDR		0x00100544
+/* SBEESR and MBEESR bit mask */
+#define OCRAM_EESR_MASK			0x00000008
+
+#endif	/*	SOC_DEFAULT_HELPER_MACROS_H	*/
diff --git a/plat/nxp/common/include/default/plat_default_def.h b/plat/nxp/common/include/default/plat_default_def.h
new file mode 100644
index 0000000..43320bb
--- /dev/null
+++ b/plat/nxp/common/include/default/plat_default_def.h
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_DEFAULT_DEF_H
+#define PLAT_DEFAULT_DEF_H
+
+/*
+ * Platform binary types for linking
+ */
+#ifdef __aarch64__
+#define PLATFORM_LINKER_FORMAT          "elf64-littleaarch64"
+#define PLATFORM_LINKER_ARCH            aarch64
+#else
+#define PLATFORM_LINKER_FORMAT          "elf32-littlearm"
+#define PLATFORM_LINKER_ARCH            arm
+#endif /* __aarch64__ */
+
+#define LS_BL31_PLAT_PARAM_VAL		0x0f1e2d3c4b5a6978ULL
+
+/* NXP Platforms have DRAM divided into banks.
+ * DRAM0 Bank:	Maximum size of this bank is fixed to 2GB
+ * DRAM1 Bank:	Greater than 2GB belongs to bank1 and size of bank1 varies from
+ *		one platform to other platform.
+ * DRAMn Bank:
+ *
+ * Except a few, all the platforms have 2GB size as DRAM0 BANK.
+ * Hence common for all the platforms.
+ * For platforms where DRAM0 Size is < 2GB, it is defined in platform_def.h
+ */
+#ifndef PLAT_DEF_DRAM0_SIZE
+#define PLAT_DEF_DRAM0_SIZE	0x80000000	/*  2G */
+#endif
+
+/* This is common for all platforms where: */
+#ifndef NXP_NS_DRAM_ADDR
+#define NXP_NS_DRAM_ADDR	NXP_DRAM0_ADDR
+#endif
+
+/* 1 MB is reserved for dma of sd */
+#ifndef NXP_SD_BLOCK_BUF_SIZE
+#define NXP_SD_BLOCK_BUF_SIZE	(1 * 1024 * 1024)
+#endif
+
+/* 64MB is reserved for Secure memory */
+#ifndef NXP_SECURE_DRAM_SIZE
+#define NXP_SECURE_DRAM_SIZE	(64 * 1024 * 1024)
+#endif
+
+/* 2M Secure EL1 Payload Shared Memory */
+#ifndef NXP_SP_SHRD_DRAM_SIZE
+#define NXP_SP_SHRD_DRAM_SIZE	(2 * 1024 * 1024)
+#endif
+
+#ifndef NXP_NS_DRAM_SIZE
+/* Non secure memory */
+#define NXP_NS_DRAM_SIZE	(PLAT_DEF_DRAM0_SIZE - \
+				(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE))
+#endif
+
+#ifndef NXP_SD_BLOCK_BUF_ADDR
+#define NXP_SD_BLOCK_BUF_ADDR	(NXP_NS_DRAM_ADDR)
+#endif
+
+#ifndef NXP_SECURE_DRAM_ADDR
+#ifdef TEST_BL31
+#define NXP_SECURE_DRAM_ADDR 0
+#else
+#define NXP_SECURE_DRAM_ADDR	(NXP_NS_DRAM_ADDR + PLAT_DEF_DRAM0_SIZE - \
+				(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE))
+#endif
+#endif
+
+#ifndef NXP_SP_SHRD_DRAM_ADDR
+#define NXP_SP_SHRD_DRAM_ADDR	(NXP_NS_DRAM_ADDR + PLAT_DEF_DRAM0_SIZE - \
+				NXP_SP_SHRD_DRAM_SIZE)
+#endif
+
+#ifndef BL31_BASE
+/* 2 MB reserved in secure memory for DDR */
+#define BL31_BASE		NXP_SECURE_DRAM_ADDR
+#endif
+
+#ifndef BL31_SIZE
+#define BL31_SIZE		(0x200000)
+#endif
+
+#ifndef BL31_LIMIT
+#define BL31_LIMIT		(BL31_BASE + BL31_SIZE)
+#endif
+
+/* Put BL32 in secure memory */
+#ifndef BL32_BASE
+#define BL32_BASE		(NXP_SECURE_DRAM_ADDR + BL31_SIZE)
+#endif
+
+#ifndef BL32_LIMIT
+#define BL32_LIMIT		(NXP_SECURE_DRAM_ADDR + \
+				NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE)
+#endif
+
+/* BL33 memory region */
+/* Hardcoded based on current address in u-boot */
+#ifndef BL33_BASE
+#define BL33_BASE		0x82000000
+#endif
+
+#ifndef BL33_LIMIT
+#define BL33_LIMIT		(NXP_NS_DRAM_ADDR + NXP_NS_DRAM_SIZE)
+#endif
+
+/*
+ * FIP image defines - Offset at which FIP Image would be present
+ * Image would include Bl31 , Bl33 and Bl32 (optional)
+ */
+#ifdef POLICY_FUSE_PROVISION
+#ifndef FUSE_BUF
+#define FUSE_BUF		ULL(0x81000000)
+#endif
+
+#ifndef FUSE_SZ
+#define FUSE_SZ			0x80000
+#endif
+#endif
+
+#ifndef MAX_FIP_DEVICES
+#define MAX_FIP_DEVICES		2
+#endif
+
+#ifndef PLAT_FIP_OFFSET
+#define PLAT_FIP_OFFSET		0x100000
+#endif
+
+#ifndef PLAT_FIP_MAX_SIZE
+#define PLAT_FIP_MAX_SIZE	0x400000
+#endif
+
+/* Check if this size can be determined from array size */
+#if defined(IMAGE_BL2)
+#ifndef MAX_MMAP_REGIONS
+#define MAX_MMAP_REGIONS	8
+#endif
+#ifndef MAX_XLAT_TABLES
+#define MAX_XLAT_TABLES		6
+#endif
+#elif defined(IMAGE_BL31)
+#ifndef MAX_MMAP_REGIONS
+#define MAX_MMAP_REGIONS	9
+#endif
+#ifndef MAX_XLAT_TABLES
+#define MAX_XLAT_TABLES		9
+#endif
+#elif defined(IMAGE_BL32)
+#ifndef MAX_MMAP_REGIONS
+#define MAX_MMAP_REGIONS	8
+#endif
+#ifndef MAX_XLAT_TABLES
+#define MAX_XLAT_TABLES		9
+#endif
+#endif
+
+/*
+ * ID of the secure physical generic timer interrupt used by the BL32.
+ */
+#ifndef BL32_IRQ_SEC_PHY_TIMER
+#define BL32_IRQ_SEC_PHY_TIMER	29
+#endif
+
+#endif	/*	PLAT_DEFAULT_DEF_H	*/
diff --git a/plat/nxp/common/nv_storage/nv_storage.mk b/plat/nxp/common/nv_storage/nv_storage.mk
new file mode 100644
index 0000000..dddba5f
--- /dev/null
+++ b/plat/nxp/common/nv_storage/nv_storage.mk
@@ -0,0 +1,29 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# NXP Non-Volatile data flag storage used and then cleared by SW on boot-up
+
+$(eval $(call add_define,NXP_NV_SW_MAINT_LAST_EXEC_DATA))
+
+ifeq ($(NXP_COINED_BB),yes)
+$(eval $(call add_define,NXP_COINED_BB))
+# BL2 : To read the reset cause from LP SECMON GPR register
+# BL31: To write the reset cause to LP SECMON GPR register
+$(eval $(call SET_NXP_MAKE_FLAG,SNVS_NEEDED,BL_COMM))
+
+# BL2: DDR training data is stored on Flexspi NOR.
+ifneq (${BOOT_MODE},flexspi_nor)
+$(eval $(call SET_NXP_MAKE_FLAG,XSPI_NEEDED,BL2))
+endif
+
+else
+$(eval $(call add_define_val,DEFAULT_NV_STORAGE_BASE_ADDR,'${BL2_BIN_XSPI_NOR_END_ADDRESS} - 2 * ${NXP_XSPI_NOR_UNIT_SIZE}'))
+$(eval $(call SET_NXP_MAKE_FLAG,XSPI_NEEDED,BL_COMM))
+endif
+
+NV_STORAGE_INCLUDES	+=  -I${PLAT_COMMON_PATH}/nv_storage
+
+NV_STORAGE_SOURCES	+=  ${PLAT_COMMON_PATH}/nv_storage/plat_nv_storage.c
diff --git a/plat/nxp/common/nv_storage/plat_nv_storage.c b/plat/nxp/common/nv_storage/plat_nv_storage.c
new file mode 100644
index 0000000..7ec4fdb
--- /dev/null
+++ b/plat/nxp/common/nv_storage/plat_nv_storage.c
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stddef.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#ifndef NXP_COINED_BB
+#include <flash_info.h>
+#include <fspi.h>
+#include <fspi_api.h>
+#endif
+#include <lib/mmio.h>
+#ifdef NXP_COINED_BB
+#include <snvs.h>
+#else
+#include <xspi_error_codes.h>
+#endif
+
+#include <plat_nv_storage.h>
+
+/*This structure will be a static structure and
+ * will be populated as first step of BL2 booting-up.
+ * fspi_strorage.c . To be located in the fspi driver folder.
+ */
+
+static nv_app_data_t nv_app_data;
+
+int read_nv_app_data(void)
+{
+	int ret = 0;
+
+#ifdef NXP_COINED_BB
+	uint8_t *nv_app_data_array = (uint8_t *) &nv_app_data;
+	uint8_t offset = 0U;
+
+	ret = snvs_read_app_data();
+	do {
+		nv_app_data_array[offset] = snvs_read_app_data_bit(offset);
+		offset++;
+
+	} while (offset < APP_DATA_MAX_OFFSET);
+	snvs_clear_app_data();
+#else
+	uintptr_t nv_base_addr = NV_STORAGE_BASE_ADDR;
+
+	ret = fspi_init(NXP_FLEXSPI_ADDR, NXP_FLEXSPI_FLASH_ADDR);
+
+	if (ret != XSPI_SUCCESS) {
+		ERROR("Failed to initialized driver flexspi-nor.\n");
+		ERROR("exiting warm-reset request.\n");
+		return -ENODEV;
+	}
+
+	xspi_read(nv_base_addr,
+		  (uint32_t *)&nv_app_data, sizeof(nv_app_data_t));
+	xspi_sector_erase((uint32_t) nv_base_addr,
+				F_SECTOR_ERASE_SZ);
+#endif
+	return ret;
+}
+
+int wr_nv_app_data(int data_offset,
+			uint8_t *data,
+			int data_size)
+{
+	int ret = 0;
+#ifdef NXP_COINED_BB
+#if !TRUSTED_BOARD_BOOT
+	snvs_disable_zeroize_lp_gpr();
+#endif
+	/* In case LP SecMon General purpose register,
+	 * only 1 bit flags can be saved.
+	 */
+	if ((data_size > 1) || (*data != DEFAULT_SET_VALUE)) {
+		ERROR("Only binary value is allowed to be written.\n");
+		ERROR("Use flash instead of SNVS GPR as NV location.\n");
+		return -ENODEV;
+	}
+	snvs_write_app_data_bit(data_offset);
+#else
+	uint8_t read_val[sizeof(nv_app_data_t)];
+	uint8_t ready_to_write_val[sizeof(nv_app_data_t)];
+	uintptr_t nv_base_addr = NV_STORAGE_BASE_ADDR;
+
+	assert((nv_base_addr + data_offset + data_size) > (nv_base_addr + F_SECTOR_ERASE_SZ));
+
+	ret = fspi_init(NXP_FLEXSPI_ADDR, NXP_FLEXSPI_FLASH_ADDR);
+
+	if (ret != XSPI_SUCCESS) {
+		ERROR("Failed to initialized driver flexspi-nor.\n");
+		ERROR("exiting warm-reset request.\n");
+		return -ENODEV;
+	}
+
+	ret = xspi_read(nv_base_addr + data_offset, (uint32_t *)read_val, data_size);
+
+	memset(ready_to_write_val, READY_TO_WRITE_VALUE, ARRAY_SIZE(ready_to_write_val));
+
+	if (memcmp(read_val, ready_to_write_val, data_size) == 0) {
+		xspi_write(nv_base_addr + data_offset, data, data_size);
+	}
+#endif
+
+	return ret;
+}
+
+const nv_app_data_t *get_nv_data(void)
+{
+	return (const nv_app_data_t *) &nv_app_data;
+}
diff --git a/plat/nxp/common/nv_storage/plat_nv_storage.h b/plat/nxp/common/nv_storage/plat_nv_storage.h
new file mode 100644
index 0000000..1f5264a
--- /dev/null
+++ b/plat/nxp/common/nv_storage/plat_nv_storage.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_NV_STRG_H
+#define PLAT_NV_STRG_H
+
+#define DEFAULT_SET_VALUE 0xA1
+#define READY_TO_WRITE_VALUE 0xFF
+
+#ifndef NV_STORAGE_BASE_ADDR
+#define NV_STORAGE_BASE_ADDR DEFAULT_NV_STORAGE_BASE_ADDR
+#endif
+
+typedef struct {
+uint8_t warm_rst_flag;
+uint8_t wdt_rst_flag;
+uint8_t dummy[2];
+} nv_app_data_t;
+
+
+/*below enum and above structure should be in-sync. */
+enum app_data_offset {
+	WARM_RESET_FLAG_OFFSET,
+	WDT_RESET_FLAG_OFFSET,
+	APP_DATA_MAX_OFFSET,
+};
+
+int read_nv_app_data(void);
+
+int wr_nv_app_data(int data_offset,
+			uint8_t *data,
+			int data_size);
+
+const nv_app_data_t *get_nv_data(void);
+
+#endif /* PLAT_NV_STRG_H */
diff --git a/plat/nxp/common/ocram/aarch64/ocram.S b/plat/nxp/common/ocram/aarch64/ocram.S
new file mode 100644
index 0000000..ec53341
--- /dev/null
+++ b/plat/nxp/common/ocram/aarch64/ocram.S
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <asm_macros.S>
+
+#include <soc_default_base_addr.h>
+#include <soc_default_helper_macros.h>
+
+.global ocram_init
+
+/*
+ * void ocram_init(uintptr_t start_addr, size_t size)
+ *
+ * This function will do OCRAM ECC.
+ * OCRAM is initialized with 64-bit writes and then a write
+ * performed to address 0x0010_0534 with the value 0x0000_0008.
+ *
+ * x0: start_addr
+ * x1: size in bytes
+ * Called from C
+ */
+
+func ocram_init
+	/* save the aarch32/64 non-volatile registers */
+	stp	x4,  x5,  [sp, #-16]!
+	stp	x6,  x7,  [sp, #-16]!
+	stp	x8,  x9,  [sp, #-16]!
+	stp	x10, x11, [sp, #-16]!
+	stp	x12, x13, [sp, #-16]!
+	stp	x18, x30, [sp, #-16]!
+
+	/* convert bytes to 64-byte chunks */
+	lsr	x1, x1, #6
+1:
+	/* for each location, read and write-back */
+	dc	ivac, x0
+	dsb	sy
+	ldp	x4, x5, [x0]
+	ldp	x6, x7, [x0, #16]
+	ldp	x8, x9, [x0, #32]
+	ldp	x10, x11, [x0, #48]
+	stp	x4, x5, [x0]
+	stp	x6, x7, [x0, #16]
+	stp	x8, x9, [x0, #32]
+	stp	x10, x11, [x0, #48]
+	dc	cvac, x0
+
+	sub	x1, x1, #1
+	cbz	x1, 2f
+	add	x0, x0, #64
+	b	1b
+2:
+	/* Clear OCRAM ECC status bit in SBEESR2 and MBEESR2 */
+	ldr	w1, =OCRAM_EESR_MASK
+	ldr	x0, =DCFG_SBEESR2_ADDR
+	str	w1, [x0]
+	ldr	x0, =DCFG_MBEESR2_ADDR
+	str	w1, [x0]
+
+	/* restore the aarch32/64 non-volatile registers */
+	ldp	x18, x30, [sp], #16
+	ldp	x12, x13, [sp], #16
+	ldp	x10, x11, [sp], #16
+	ldp	x8,  x9,  [sp], #16
+	ldp	x6,  x7,  [sp], #16
+	ldp	x4,  x5,  [sp], #16
+	ret
+endfunc ocram_init
diff --git a/plat/nxp/common/ocram/ocram.h b/plat/nxp/common/ocram/ocram.h
new file mode 100644
index 0000000..479de61
--- /dev/null
+++ b/plat/nxp/common/ocram/ocram.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef OCRAM_H
+#define OCRAM_H
+
+void ocram_init(uintptr_t start_addr, size_t size);
+
+#endif /* OCRAM_H */
diff --git a/plat/nxp/common/ocram/ocram.mk b/plat/nxp/common/ocram/ocram.mk
new file mode 100644
index 0000000..c77bd4a
--- /dev/null
+++ b/plat/nxp/common/ocram/ocram.mk
@@ -0,0 +1,14 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+PLAT_OCRAM_PATH		:= $(PLAT_COMMON_PATH)/ocram
+
+OCRAM_SOURCES		:= ${PLAT_OCRAM_PATH}/$(ARCH)/ocram.S
+
+BL2_SOURCES		+= ${OCRAM_SOURCES}
+
+PLAT_INCLUDES           += -I${PLAT_COMMON_PATH}/ocram
diff --git a/plat/nxp/common/plat_make_helper/plat_build_macros.mk b/plat/nxp/common/plat_make_helper/plat_build_macros.mk
new file mode 100644
index 0000000..bba5e36
--- /dev/null
+++ b/plat/nxp/common/plat_make_helper/plat_build_macros.mk
@@ -0,0 +1,11 @@
+#
+# Copyright (c) 2020, NXP.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+define	SET_NXP_MAKE_FLAG
+$1	:= yes
+$2_$1	:= yes
+endef
diff --git a/plat/nxp/common/plat_make_helper/plat_common_def.mk b/plat/nxp/common/plat_make_helper/plat_common_def.mk
new file mode 100644
index 0000000..86dacf8
--- /dev/null
+++ b/plat/nxp/common/plat_make_helper/plat_common_def.mk
@@ -0,0 +1,103 @@
+# Copyright 2020-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Include build macros, for example: SET_NXP_MAKE_FLAG
+include plat/nxp/common/plat_make_helper/plat_build_macros.mk
+
+# Adding platform specific defines
+
+$(eval $(call add_define_val,BOARD,'"${BOARD}"'))
+
+ifeq (${POVDD_ENABLE},yes)
+$(eval $(call add_define,CONFIG_POVDD_ENABLE))
+endif
+
+ifneq (${FLASH_TYPE},)
+$(eval $(call add_define,CONFIG_${FLASH_TYPE}))
+endif
+
+ifneq (${XSPI_FLASH_SZ},)
+$(eval $(call add_define_val,NXP_FLEXSPI_FLASH_SIZE,${XSPI_FLASH_SZ}))
+endif
+
+ifneq (${QSPI_FLASH_SZ},)
+$(eval $(call add_define_val,NXP_QSPI_FLASH_SIZE,${QSPI_FLASH_SZ}))
+endif
+
+ifneq (${NOR_FLASH_SZ},)
+$(eval $(call add_define_val,NXP_NOR_FLASH_SIZE,${NOR_FLASH_SZ}))
+endif
+
+
+ifneq (${FSPI_ERASE_4K},)
+$(eval $(call add_define_val,CONFIG_FSPI_ERASE_4K,${FSPI_ERASE_4K}))
+endif
+
+ifneq (${NUM_OF_DDRC},)
+$(eval $(call add_define_val,NUM_OF_DDRC,${NUM_OF_DDRC}))
+endif
+
+ifeq (${CONFIG_DDR_NODIMM},1)
+$(eval $(call add_define,CONFIG_DDR_NODIMM))
+DDRC_NUM_DIMM := 1
+endif
+
+ifneq (${DDRC_NUM_DIMM},)
+$(eval $(call add_define_val,DDRC_NUM_DIMM,${DDRC_NUM_DIMM}))
+endif
+
+ifneq (${DDRC_NUM_CS},)
+$(eval $(call add_define_val,DDRC_NUM_CS,${DDRC_NUM_CS}))
+endif
+
+ifeq (${DDR_ADDR_DEC},yes)
+$(eval $(call add_define,CONFIG_DDR_ADDR_DEC))
+endif
+
+ifeq (${DDR_ECC_EN},yes)
+$(eval $(call add_define,CONFIG_DDR_ECC_EN))
+endif
+
+ifeq (${CONFIG_STATIC_DDR},1)
+$(eval $(call add_define,CONFIG_STATIC_DDR))
+endif
+
+# Platform can control the base address for non-volatile storage.
+#$(eval $(call add_define_val,NV_STORAGE_BASE_ADDR,'${BL2_BIN_XSPI_NOR_END_ADDRESS} - 2 * ${NXP_XSPI_NOR_UNIT_SIZE}'))
+
+ifeq (${WARM_BOOT},yes)
+$(eval $(call add_define_val,PHY_TRAINING_REGS_ON_FLASH,'${BL2_BIN_XSPI_NOR_END_ADDRESS} - ${NXP_XSPI_NOR_UNIT_SIZE}'))
+endif
+
+# Selecting Boot Source for the TFA images.
+define add_boot_mode_define
+    ifeq ($(1),qspi)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,QSPI_NEEDED,BL2))
+        $$(eval $$(call add_define,QSPI_BOOT))
+    else ifeq ($(1),sd)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,SD_MMC_NEEDED,BL2))
+        $$(eval $$(call add_define,SD_BOOT))
+    else ifeq ($(1),emmc)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,SD_MMC_NEEDED,BL2))
+        $$(eval $$(call add_define,EMMC_BOOT))
+    else ifeq ($(1),nor)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,IFC_NOR_NEEDED,BL2))
+        $$(eval $$(call add_define,NOR_BOOT))
+    else ifeq ($(1),nand)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,IFC_NAND_NEEDED,BL2))
+        $$(eval $$(call add_define,NAND_BOOT))
+    else ifeq ($(1),flexspi_nor)
+        $$(eval $$(call SET_NXP_MAKE_FLAG,XSPI_NEEDED,BL2))
+        $$(eval $$(call add_define,FLEXSPI_NOR_BOOT))
+    else
+        $$(error $(PLAT) Cannot Support Boot Mode: $(BOOT_MODE))
+    endif
+endef
+
+ifneq (,$(findstring $(BOOT_MODE),$(SUPPORTED_BOOT_MODE)))
+    $(eval $(call add_boot_mode_define,$(strip $(BOOT_MODE))))
+else
+    $(error $(PLAT) Un-supported Boot Mode = $(BOOT_MODE))
+endif
diff --git a/plat/nxp/common/plat_make_helper/soc_common_def.mk b/plat/nxp/common/plat_make_helper/soc_common_def.mk
new file mode 100644
index 0000000..22cd39a
--- /dev/null
+++ b/plat/nxp/common/plat_make_helper/soc_common_def.mk
@@ -0,0 +1,119 @@
+# Copyright 2020-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Adding SoC specific defines
+
+ifneq (${CACHE_LINE},)
+$(eval $(call add_define_val,PLATFORM_CACHE_LINE_SHIFT,${CACHE_LINE}))
+$(eval CACHE_WRITEBACK_GRANULE=$(shell echo $$((1 << $(CACHE_LINE)))))
+$(eval $(call add_define_val,CACHE_WRITEBACK_GRANULE,$(CACHE_WRITEBACK_GRANULE)))
+endif
+
+ifeq (${INTERCONNECT}, "CCI400")
+$(eval $(call add_define,NXP_HAS_${INTERCONNECT}))
+ICNNCT_ID := 0x420
+$(eval $(call add_define,ICNNCT_ID))
+endif
+
+ifeq (${INTERCONNECT}, "CCN508")
+$(eval $(call add_define,NXP_HAS_CCN508))
+endif
+
+ifneq (${CHASSIS},)
+$(eval $(call add_define,CONFIG_CHASSIS_${CHASSIS}))
+endif
+
+ifneq (${PLAT_DDR_PHY},)
+$(eval $(call add_define,NXP_DDR_${PLAT_DDR_PHY}))
+endif
+
+ifneq (${PHYS_SYS},)
+$(eval $(call add_define,CONFIG_PHYS_64BIT))
+endif
+
+ifneq (${CSF_HDR_SZ},)
+$(eval $(call add_define_val,CSF_HDR_SZ,${CSF_HDR_SZ}))
+endif
+
+ifneq (${OCRAM_START_ADDR},)
+$(eval $(call add_define_val,NXP_OCRAM_ADDR,${OCRAM_START_ADDR}))
+endif
+
+ifneq (${OCRAM_SIZE},)
+$(eval $(call add_define_val,NXP_OCRAM_SIZE,${OCRAM_SIZE}))
+endif
+
+ifneq (${NXP_ROM_RSVD},)
+$(eval $(call add_define_val,NXP_ROM_RSVD,${NXP_ROM_RSVD}))
+endif
+
+ifneq (${BL2_BASE},)
+$(eval $(call add_define_val,BL2_BASE,${BL2_BASE}))
+endif
+
+ifeq (${SEC_MEM_NON_COHERENT},yes)
+$(eval $(call add_define,SEC_MEM_NON_COHERENT))
+endif
+
+ifneq (${NXP_ESDHC_ENDIANNESS},)
+$(eval $(call add_define,NXP_ESDHC_${NXP_ESDHC_ENDIANNESS}))
+endif
+
+ifneq (${NXP_SFP_VER},)
+$(eval $(call add_define,NXP_SFP_VER_${NXP_SFP_VER}))
+endif
+
+ifneq (${NXP_SFP_ENDIANNESS},)
+$(eval $(call add_define,NXP_SFP_${NXP_SFP_ENDIANNESS}))
+endif
+
+ifneq (${NXP_GPIO_ENDIANNESS},)
+$(eval $(call add_define,NXP_GPIO_${NXP_GPIO_ENDIANNESS}))
+endif
+
+ifneq (${NXP_SNVS_ENDIANNESS},)
+$(eval $(call add_define,NXP_SNVS_${NXP_SNVS_ENDIANNESS}))
+endif
+
+ifneq (${NXP_GUR_ENDIANNESS},)
+$(eval $(call add_define,NXP_GUR_${NXP_GUR_ENDIANNESS}))
+endif
+
+ifneq (${NXP_FSPI_ENDIANNESS},)
+$(eval $(call add_define,NXP_FSPI_${NXP_FSPI_ENDIANNESS}))
+endif
+
+ifneq (${NXP_SEC_ENDIANNESS},)
+$(eval $(call add_define,NXP_SEC_${NXP_SEC_ENDIANNESS}))
+endif
+
+ifneq (${NXP_DDR_ENDIANNESS},)
+$(eval $(call add_define,NXP_DDR_${NXP_DDR_ENDIANNESS}))
+endif
+
+ifneq (${NXP_QSPI_ENDIANNESS},)
+$(eval $(call add_define,NXP_QSPI_${NXP_QSPI_ENDIANNESS}))
+endif
+
+ifneq (${NXP_SCFG_ENDIANNESS},)
+$(eval $(call add_define,NXP_SCFG_${NXP_SCFG_ENDIANNESS}))
+endif
+
+ifneq (${NXP_IFC_ENDIANNESS},)
+$(eval $(call add_define,NXP_IFC_${NXP_IFC_ENDIANNESS}))
+endif
+
+ifneq (${NXP_DDR_INTLV_256B},)
+$(eval $(call add_define,NXP_DDR_INTLV_256B))
+endif
+
+ifneq (${PLAT_XLAT_TABLES_DYNAMIC},)
+$(eval $(call add_define,PLAT_XLAT_TABLES_DYNAMIC))
+endif
+
+ifeq (${OCRAM_ECC_EN},yes)
+$(eval $(call add_define,CONFIG_OCRAM_ECC_EN))
+include ${PLAT_COMMON_PATH}/ocram/ocram.mk
+endif
diff --git a/plat/nxp/common/psci/aarch64/psci_utils.S b/plat/nxp/common/psci/aarch64/psci_utils.S
new file mode 100644
index 0000000..ec69aea
--- /dev/null
+++ b/plat/nxp/common/psci/aarch64/psci_utils.S
@@ -0,0 +1,1155 @@
+
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <asm_macros.S>
+#include <assert_macros.S>
+
+#include <lib/psci/psci.h>
+
+#include <bl31_data.h>
+#include <plat_psci.h>
+
+
+#define RESET_RETRY_CNT   800
+#define PSCI_ABORT_CNT	100
+
+#if (SOC_CORE_RELEASE)
+
+.global _psci_cpu_on
+
+/*
+ * int _psci_cpu_on(u_register_t core_mask)
+ * x0   = target cpu core mask
+ *
+ * Called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ *
+ */
+
+func _psci_cpu_on
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x6, x0
+
+	/* x0   = core mask (lsb)
+	 * x6   = core mask (lsb)
+	 */
+
+	/* check if core disabled */
+	bl   _soc_ck_disabled		/* 0-2 */
+	cbnz w0, psci_disabled
+
+	/* check core data area to see if core cannot be turned on
+	 * read the core state
+	 */
+	mov  x0, x6
+	bl   _getCoreState		/* 0-5 */
+	mov  x9, x0
+
+	/* x6   = core mask (lsb)
+	 * x9   = core state (from data area)
+	 */
+
+	cmp  x9, #CORE_DISABLED
+	mov  x0, #PSCI_E_DISABLED
+	b.eq cpu_on_done
+
+	cmp  x9, #CORE_PENDING
+	mov  x0, #PSCI_E_ON_PENDING
+	b.eq cpu_on_done
+
+	cmp  x9, #CORE_RELEASED
+	mov  x0, #PSCI_E_ALREADY_ON
+	b.eq cpu_on_done
+
+8:
+	/* x6   = core mask (lsb)
+	 * x9   = core state (from data area)
+	 */
+
+	cmp  x9, #CORE_WFE
+	b.eq core_in_wfe
+	cmp  x9, #CORE_IN_RESET
+	b.eq core_in_reset
+	cmp  x9, #CORE_OFF
+	b.eq core_is_off
+	cmp  x9, #CORE_OFF_PENDING
+
+	/* if state == CORE_OFF_PENDING, set abort */
+	mov  x0, x6
+	mov  x1, #ABORT_FLAG_DATA
+	mov  x2, #CORE_ABORT_OP
+	bl   _setCoreData		/* 0-3, [13-15] */
+
+	ldr  x3, =PSCI_ABORT_CNT
+7:
+	/* watch for abort to take effect */
+	mov  x0, x6
+	bl   _getCoreState		/* 0-5 */
+	cmp  x0, #CORE_OFF
+	b.eq core_is_off
+	cmp  x0, #CORE_PENDING
+	mov  x0, #PSCI_E_SUCCESS
+	b.eq cpu_on_done
+
+	/* loop til finished */
+	sub  x3, x3, #1
+	cbnz x3, 7b
+
+	/* if we didn't see either CORE_OFF or CORE_PENDING, then this
+	 * core is in CORE_OFF_PENDING - exit with success, as the core will
+	 * respond to the abort request
+	 */
+	mov  x0, #PSCI_E_SUCCESS
+	b    cpu_on_done
+
+/* this is where we start up a core out of reset */
+core_in_reset:
+	/* see if the soc-specific module supports this op */
+	ldr  x7, =SOC_CORE_RELEASE
+	cbnz  x7, 3f
+
+	mov  x0, #PSCI_E_NOT_SUPPORTED
+	b    cpu_on_done
+
+	/* x6   = core mask (lsb) */
+3:
+	/* set core state in data area */
+	mov  x0, x6
+	mov  x1, #CORE_PENDING
+	bl   _setCoreState   			/* 0-3, [13-15] */
+
+	/* release the core from reset */
+	mov   x0, x6
+	bl    _soc_core_release 		/* 0-3 */
+	mov   x0, #PSCI_E_SUCCESS
+	b     cpu_on_done
+
+	/* Start up the core that has been powered-down via CPU_OFF
+	 */
+core_is_off:
+	/* see if the soc-specific module supports this op
+	 */
+	ldr  x7, =SOC_CORE_RESTART
+	cbnz x7, 2f
+
+	mov  x0, #PSCI_E_NOT_SUPPORTED
+	b    cpu_on_done
+
+	/* x6   = core mask (lsb) */
+2:
+	/* set core state in data area */
+	mov  x0, x6
+	mov  x1, #CORE_WAKEUP
+	bl   _setCoreState			/* 0-3, [13-15] */
+
+	/* put the core back into service */
+	mov  x0, x6
+#if (SOC_CORE_RESTART)
+	bl   _soc_core_restart			/* 0-5 */
+#endif
+	mov  x0, #PSCI_E_SUCCESS
+	b    cpu_on_done
+
+/* this is where we release a core that is being held in wfe */
+core_in_wfe:
+	/* x6   = core mask (lsb) */
+
+	/* set core state in data area */
+	mov  x0, x6
+	mov  x1, #CORE_PENDING
+	bl   _setCoreState			/* 0-3, [13-15] */
+	dsb  sy
+	isb
+
+	/* put the core back into service */
+	sev
+	sev
+	isb
+	mov  x0, #PSCI_E_SUCCESS
+
+cpu_on_done:
+	/* restore the aarch32/64 non-volatile registers */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_cpu_on
+
+#endif
+
+
+#if (SOC_CORE_OFF)
+
+.global _psci_cpu_prep_off
+.global _psci_cpu_off_wfi
+
+/*
+ * void _psci_cpu_prep_off(u_register_t core_mask)
+ * this function performs the SoC-specific programming prior
+ * to shutting the core down
+ * x0 = core_mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_cpu_prep_off
+
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x10, x0			/* x10 = core_mask */
+
+	/* the core does not return from cpu_off, so no need
+	 * to save/restore non-volatile registers
+	 */
+
+	/* mask interrupts by setting DAIF[7:4] to 'b1111 */
+	msr DAIFSet, #0xF
+
+	/* read cpuectlr and save current value */
+	mrs   x4, CPUECTLR_EL1
+	mov   x1, #CPUECTLR_DATA
+	mov   x2, x4
+	mov   x0, x10
+	bl    _setCoreData
+
+	/* remove the core from coherency */
+	bic   x4, x4, #CPUECTLR_SMPEN_MASK
+	msr   CPUECTLR_EL1, x4
+
+	/* save scr_el3 */
+	mov  x0, x10
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* x4 = scr_el3 */
+
+	/* secure SGI (FIQ) taken to EL3, set SCR_EL3[FIQ] */
+	orr   x4, x4, #SCR_FIQ_MASK
+	msr   scr_el3, x4
+
+	/* x10 = core_mask */
+
+	/* prep the core for shutdown */
+	mov  x0, x10
+	bl   _soc_core_prep_off
+
+	/* restore the aarch32/64 non-volatile registers */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_cpu_prep_off
+
+/*
+ * void _psci_cpu_off_wfi(u_register_t core_mask, u_register_t resume_addr)
+ *   - this function shuts down the core
+ *   - this function does not return!!
+ */
+
+func _psci_cpu_off_wfi
+	/* save the wakeup address */
+	mov  x29, x1
+
+	/* x0 = core_mask */
+
+	/* shutdown the core */
+	bl   _soc_core_entr_off
+
+	/* branch to resume execution */
+	br   x29
+endfunc _psci_cpu_off_wfi
+
+#endif
+
+
+#if (SOC_CORE_RESTART)
+
+.global _psci_wakeup
+
+/*
+ * void _psci_wakeup(u_register_t core_mask)
+ * this function performs the SoC-specific programming
+ * after a core wakes up from OFF
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_wakeup
+
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x4, x0			/* x4 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x4
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x4 = core mask */
+
+	/* restore CPUECTLR */
+	mov   x0, x4
+	mov   x1, #CPUECTLR_DATA
+	bl    _getCoreData
+	orr   x0, x0, #CPUECTLR_SMPEN_MASK
+	msr   CPUECTLR_EL1, x0
+
+	/* x4 = core mask */
+
+	/* start the core back up */
+	mov   x0, x4
+	bl   _soc_core_exit_off
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_wakeup
+
+#endif
+
+
+#if (SOC_SYSTEM_RESET)
+
+.global _psci_system_reset
+
+func _psci_system_reset
+
+	/* system reset is mandatory
+	 * system reset is soc-specific
+	 * Note: under no circumstances do we return from this call
+	 */
+	bl   _soc_sys_reset
+endfunc _psci_system_reset
+
+#endif
+
+
+#if (SOC_SYSTEM_OFF)
+
+.global _psci_system_off
+
+func _psci_system_off
+
+	/* system off is mandatory
+	 * system off is soc-specific
+	 * Note: under no circumstances do we return from this call */
+	b    _soc_sys_off
+endfunc _psci_system_off
+
+#endif
+
+
+#if (SOC_CORE_STANDBY)
+
+.global _psci_core_entr_stdby
+.global _psci_core_prep_stdby
+.global _psci_core_exit_stdby
+
+/*
+ * void _psci_core_entr_stdby(u_register_t core_mask) - this
+ * is the fast-path for simple core standby
+ */
+
+func _psci_core_entr_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0		/* x5 = core mask */
+
+	/* save scr_el3 */
+	mov  x0, x5
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* x4 = SCR_EL3
+	 * x5 = core mask
+	 */
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* x5 = core mask */
+
+	/* put the core into standby */
+	mov  x0, x5
+	bl   _soc_core_entr_stdby
+
+	/* restore scr_el3 */
+	mov  x0, x5
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_core_entr_stdby
+
+/*
+ * void _psci_core_prep_stdby(u_register_t core_mask) - this
+ * sets up the core to enter standby state thru the normal path
+ */
+
+func _psci_core_prep_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0
+
+	/* x5 = core mask */
+
+	/* save scr_el3 */
+	mov  x0, x5
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* x5 = core mask */
+
+	/* call for any SoC-specific programming */
+	mov  x0, x5
+	bl   _soc_core_prep_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_core_prep_stdby
+
+/*
+ * void _psci_core_exit_stdby(u_register_t core_mask) - this
+ * exits the core from standby state thru the normal path
+ */
+
+func _psci_core_exit_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0
+
+	/* x5 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x5
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x5 = core mask */
+
+	/* perform any SoC-specific programming after standby state */
+	mov  x0, x5
+	bl   _soc_core_exit_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_core_exit_stdby
+
+#endif
+
+
+#if (SOC_CORE_PWR_DWN)
+
+.global _psci_core_prep_pwrdn
+.global _psci_cpu_pwrdn_wfi
+.global _psci_core_exit_pwrdn
+
+/*
+ * void _psci_core_prep_pwrdn_(u_register_t core_mask)
+ * this function prepares the core for power-down
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_core_prep_pwrdn
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x6, x0
+
+	/* x6 = core mask */
+
+	/* mask interrupts by setting DAIF[7:4] to 'b1111 */
+	msr DAIFSet, #0xF
+
+	/* save scr_el3 */
+	mov  x0, x6
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* save cpuectlr */
+	mov  x0, x6
+	mov  x1, #CPUECTLR_DATA
+	mrs  x2, CPUECTLR_EL1
+	bl   _setCoreData
+
+	/* x6 = core mask */
+
+	/* SoC-specific programming for power-down */
+	mov  x0, x6
+	bl  _soc_core_prep_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_core_prep_pwrdn
+
+/*
+ * void _psci_cpu_pwrdn_wfi(u_register_t core_mask, u_register_t resume_addr)
+ * this function powers down the core
+ */
+
+func _psci_cpu_pwrdn_wfi
+	/* save the wakeup address */
+	mov  x29, x1
+
+	/* x0 = core mask */
+
+	/* shutdown the core */
+	bl   _soc_core_entr_pwrdn
+
+	/* branch to resume execution */
+	br   x29
+endfunc _psci_cpu_pwrdn_wfi
+
+/*
+ * void _psci_core_exit_pwrdn_(u_register_t core_mask)
+ * this function cleans up after a core power-down
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_core_exit_pwrdn
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x5, x0			/* x5 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x5
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x5 = core mask */
+
+	/* restore cpuectlr */
+	mov  x0, x5
+	mov  x1, #CPUECTLR_DATA
+	bl   _getCoreData
+	/* make sure smp is set */
+	orr  x0, x0, #CPUECTLR_SMPEN_MASK
+	msr  CPUECTLR_EL1, x0
+
+	/* x5 = core mask */
+
+	/* SoC-specific cleanup */
+	mov  x0, x5
+	bl   _soc_core_exit_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_core_exit_pwrdn
+
+#endif
+
+#if (SOC_CLUSTER_STANDBY)
+
+.global _psci_clstr_prep_stdby
+.global _psci_clstr_exit_stdby
+
+/*
+ * void _psci_clstr_prep_stdby(u_register_t core_mask) - this
+ * sets up the clstr to enter standby state thru the normal path
+ */
+
+func _psci_clstr_prep_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0
+
+	/* x5 = core mask */
+
+	/* save scr_el3 */
+	mov  x0, x5
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* x5 = core mask */
+
+	/* call for any SoC-specific programming */
+	mov  x0, x5
+	bl   _soc_clstr_prep_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_clstr_prep_stdby
+
+/*
+ * void _psci_clstr_exit_stdby(u_register_t core_mask) - this
+ * exits the clstr from standby state thru the normal path
+ */
+
+func _psci_clstr_exit_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0			/* x5 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x5
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x5 = core mask */
+
+	/* perform any SoC-specific programming after standby state */
+	mov  x0, x5
+	bl   _soc_clstr_exit_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_clstr_exit_stdby
+
+#endif
+
+#if (SOC_CLUSTER_PWR_DWN)
+
+.global _psci_clstr_prep_pwrdn
+.global _psci_clstr_exit_pwrdn
+
+/*
+ * void _psci_clstr_prep_pwrdn_(u_register_t core_mask)
+ * this function prepares the cluster+core for power-down
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_clstr_prep_pwrdn
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x6, x0			/* x6 = core mask */
+
+	/* mask interrupts by setting DAIF[7:4] to 'b1111 */
+	msr DAIFSet, #0xF
+
+	/* save scr_el3 */
+	mov  x0, x6
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* save cpuectlr */
+	mov  x0, x6
+	mov  x1, #CPUECTLR_DATA
+	mrs  x2, CPUECTLR_EL1
+	mov  x4, x2
+	bl   _setCoreData
+
+	/* remove core from coherency */
+	bic   x4, x4, #CPUECTLR_SMPEN_MASK
+	msr   CPUECTLR_EL1, x4
+
+	/* x6 = core mask */
+
+	/* SoC-specific programming for power-down */
+	mov  x0, x6
+	bl  _soc_clstr_prep_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_clstr_prep_pwrdn
+
+/*
+ * void _psci_clstr_exit_pwrdn_(u_register_t core_mask)
+ * this function cleans up after a cluster power-down
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_clstr_exit_pwrdn
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x4, x0			/* x4 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x4
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x4 = core mask */
+
+	/* restore cpuectlr */
+	mov  x0, x4
+	mov  x1, #CPUECTLR_DATA
+	bl   _getCoreData
+	/* make sure smp is set */
+	orr  x0, x0, #CPUECTLR_SMPEN_MASK
+	msr  CPUECTLR_EL1, x0
+
+	/* x4 = core mask */
+
+	/* SoC-specific cleanup */
+	mov  x0, x4
+	bl   _soc_clstr_exit_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_clstr_exit_pwrdn
+
+#endif
+
+#if (SOC_SYSTEM_STANDBY)
+
+.global _psci_sys_prep_stdby
+.global _psci_sys_exit_stdby
+
+/*
+ * void _psci_sys_prep_stdby(u_register_t core_mask) - this
+ * sets up the system to enter standby state thru the normal path
+ */
+
+func _psci_sys_prep_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0			/* x5 = core mask */
+
+	/* save scr_el3 */
+	mov  x0, x5
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* x5 = core mask */
+
+	/* call for any SoC-specific programming */
+	mov  x0, x5
+	bl   _soc_sys_prep_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_sys_prep_stdby
+
+/*
+ * void _psci_sys_exit_stdby(u_register_t core_mask) - this
+ * exits the system from standby state thru the normal path
+ */
+
+func _psci_sys_exit_stdby
+	stp  x4,  x5, [sp, #-16]!
+	stp  x6, x30, [sp, #-16]!
+
+	mov  x5, x0
+
+	/* x5 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x5
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x5 = core mask */
+
+	/* perform any SoC-specific programming after standby state */
+	mov  x0, x5
+	bl   _soc_sys_exit_stdby
+
+	ldp  x6,  x30, [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	isb
+	ret
+endfunc _psci_sys_exit_stdby
+
+#endif
+
+#if (SOC_SYSTEM_PWR_DWN)
+
+.global _psci_sys_prep_pwrdn
+.global _psci_sys_pwrdn_wfi
+.global _psci_sys_exit_pwrdn
+
+/*
+ * void _psci_sys_prep_pwrdn_(u_register_t core_mask)
+ * this function prepares the system+core for power-down
+ * x0 = core mask
+ *
+ * called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_sys_prep_pwrdn
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x6, x0			/* x6 = core mask */
+
+	/* mask interrupts by setting DAIF[7:4] to 'b1111 */
+	msr DAIFSet, #0xF
+
+	/* save scr_el3 */
+	mov  x0, x6
+	mrs  x4, SCR_EL3
+	mov  x2, x4
+	mov  x1, #SCR_EL3_DATA
+	bl    _setCoreData
+
+	/* allow interrupts @ EL3 */
+	orr  x4, x4, #(SCR_IRQ_MASK | SCR_FIQ_MASK)
+	msr  SCR_EL3, x4
+
+	/* save cpuectlr */
+	mov  x0, x6
+	mov  x1, #CPUECTLR_DATA
+	mrs  x2, CPUECTLR_EL1
+	mov  x4, x2
+	bl   _setCoreData
+
+	/* remove core from coherency */
+	bic   x4, x4, #CPUECTLR_SMPEN_MASK
+	msr   CPUECTLR_EL1, x4
+
+	/* x6 = core mask */
+
+	/* SoC-specific programming for power-down */
+	mov  x0, x6
+	bl  _soc_sys_prep_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_sys_prep_pwrdn
+
+
+/*
+ * void _psci_sys_pwrdn_wfi(u_register_t core_mask, u_register_t resume_addr)
+ * this function powers down the system
+ */
+
+func _psci_sys_pwrdn_wfi
+	/* save the wakeup address */
+	mov  x29, x1
+
+	/* x0 = core mask */
+
+	/* shutdown the system */
+	bl   _soc_sys_pwrdn_wfi
+
+	/* branch to resume execution */
+	br   x29
+endfunc _psci_sys_pwrdn_wfi
+
+/*
+ * void _psci_sys_exit_pwrdn_(u_register_t core_mask)
+ * this function cleans up after a system power-down
+ * x0 = core mask
+ *
+ * Called from C, so save the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ */
+
+func _psci_sys_exit_pwrdn
+
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x14, x15, [sp, #-16]!
+	stp  x16, x17, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	mov  x4, x0			/* x4 = core mask */
+
+	/* restore scr_el3 */
+	mov  x0, x4
+	mov  x1, #SCR_EL3_DATA
+	bl   _getCoreData
+
+	/* x0 = saved scr_el3 */
+	msr  SCR_EL3, x0
+
+	/* x4 = core mask */
+
+	/* restore cpuectlr */
+	mov  x0, x4
+	mov  x1, #CPUECTLR_DATA
+	bl   _getCoreData
+
+	/* make sure smp is set */
+	orr  x0, x0, #CPUECTLR_SMPEN_MASK
+	msr  CPUECTLR_EL1, x0
+
+	/* x4 = core mask */
+
+	/* SoC-specific cleanup */
+	mov  x0, x4
+	bl   _soc_sys_exit_pwrdn
+
+	/* restore the aarch32/64 non-volatile registers
+	 */
+	ldp  x18, x30, [sp], #16
+	ldp  x16, x17, [sp], #16
+	ldp  x14, x15, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	b    psci_completed
+endfunc _psci_sys_exit_pwrdn
+
+#endif
+
+
+/* psci std returns */
+func psci_disabled
+	ldr  w0, =PSCI_E_DISABLED
+	b    psci_completed
+endfunc psci_disabled
+
+
+func psci_not_present
+	ldr  w0, =PSCI_E_NOT_PRESENT
+	b    psci_completed
+endfunc psci_not_present
+
+
+func psci_on_pending
+	ldr  w0, =PSCI_E_ON_PENDING
+	b    psci_completed
+endfunc psci_on_pending
+
+
+func psci_already_on
+	ldr  w0, =PSCI_E_ALREADY_ON
+	b    psci_completed
+endfunc psci_already_on
+
+
+func psci_failure
+	ldr  w0, =PSCI_E_INTERN_FAIL
+	b    psci_completed
+endfunc psci_failure
+
+
+func psci_unimplemented
+	ldr  w0, =PSCI_E_NOT_SUPPORTED
+	b    psci_completed
+endfunc psci_unimplemented
+
+
+func psci_denied
+	ldr  w0, =PSCI_E_DENIED
+	b    psci_completed
+endfunc psci_denied
+
+
+func psci_invalid
+	ldr  w0, =PSCI_E_INVALID_PARAMS
+	b    psci_completed
+endfunc psci_invalid
+
+
+func psci_success
+	mov  x0, #PSCI_E_SUCCESS
+endfunc psci_success
+
+
+func psci_completed
+	/* x0 = status code */
+	ret
+endfunc psci_completed
diff --git a/plat/nxp/common/psci/include/plat_psci.h b/plat/nxp/common/psci/include/plat_psci.h
new file mode 100644
index 0000000..7fc48fb
--- /dev/null
+++ b/plat/nxp/common/psci/include/plat_psci.h
@@ -0,0 +1,145 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_PSCI_H
+#define PLAT_PSCI_H
+#include <cortex_a53.h>
+#include <cortex_a72.h>
+
+ /* core abort current op */
+#define CORE_ABORT_OP     0x1
+
+ /* psci power levels - these are actually affinity levels
+  * in the psci_power_state_t array
+  */
+#define PLAT_CORE_LVL  PSCI_CPU_PWR_LVL
+#define PLAT_CLSTR_LVL U(1)
+#define PLAT_SYS_LVL   U(2)
+#define PLAT_MAX_LVL   PLAT_SYS_LVL
+
+ /* core state */
+ /* OFF states 0x0 - 0xF */
+#define CORE_IN_RESET     0x0
+#define CORE_DISABLED     0x1
+#define CORE_OFF          0x2
+#define CORE_STANDBY      0x3
+#define CORE_PWR_DOWN     0x4
+#define CORE_WFE          0x6
+#define CORE_WFI          0x7
+#define CORE_LAST	  0x8
+#define CORE_OFF_PENDING  0x9
+#define CORE_WORKING_INIT 0xA
+#define SYS_OFF_PENDING   0xB
+#define SYS_OFF           0xC
+
+ /* ON states 0x10 - 0x1F */
+#define CORE_PENDING      0x10
+#define CORE_RELEASED     0x11
+#define CORE_WAKEUP       0x12
+ /* highest off state */
+#define CORE_OFF_MAX	  0xF
+ /* lowest on state */
+#define CORE_ON_MIN       CORE_PENDING
+
+#define  DAIF_SET_MASK          0x3C0
+#define  SCTLR_I_C_M_MASK       0x00001005
+#define  SCTLR_C_MASK           0x00000004
+#define  SCTLR_I_MASK           0x00001000
+#define  CPUACTLR_L1PCTL_MASK   0x0000E000
+#define  DCSR_RCPM2_BASE        0x20170000
+#define  CPUECTLR_SMPEN_MASK    0x40
+#define  CPUECTLR_SMPEN_EN      0x40
+#define  CPUECTLR_RET_MASK      0x7
+#define  CPUECTLR_RET_SET       0x2
+#define  CPUECTLR_TIMER_MASK    0x7
+#define  CPUECTLR_TIMER_8TICKS  0x2
+#define  CPUECTLR_TIMER_2TICKS  0x1
+#define  SCR_IRQ_MASK           0x2
+#define  SCR_FIQ_MASK           0x4
+
+/* pwr mgmt features supported in the soc-specific code:
+ *   value == 0x0, the soc code does not support this feature
+ *   value != 0x0, the soc code supports this feature
+ */
+#ifndef SOC_CORE_RELEASE
+#define SOC_CORE_RELEASE      0x1
+#endif
+
+#ifndef SOC_CORE_RESTART
+#define SOC_CORE_RESTART      0x1
+#endif
+
+#ifndef SOC_CORE_OFF
+#define SOC_CORE_OFF          0x1
+#endif
+
+#ifndef SOC_CORE_STANDBY
+#define SOC_CORE_STANDBY      0x1
+#endif
+
+#ifndef SOC_CORE_PWR_DWN
+#define SOC_CORE_PWR_DWN      0x1
+#endif
+
+#ifndef SOC_CLUSTER_STANDBY
+#define SOC_CLUSTER_STANDBY   0x1
+#endif
+
+#ifndef SOC_CLUSTER_PWR_DWN
+#define SOC_CLUSTER_PWR_DWN   0x1
+#endif
+
+#ifndef SOC_SYSTEM_STANDBY
+#define SOC_SYSTEM_STANDBY    0x1
+#endif
+
+#ifndef SOC_SYSTEM_PWR_DWN
+#define SOC_SYSTEM_PWR_DWN    0x1
+#endif
+
+#ifndef SOC_SYSTEM_OFF
+#define SOC_SYSTEM_OFF        0x1
+#endif
+
+#ifndef SOC_SYSTEM_RESET
+#define SOC_SYSTEM_RESET      0x1
+#endif
+
+#ifndef SOC_SYSTEM_RESET2
+#define SOC_SYSTEM_RESET2     0x1
+#endif
+
+#ifndef __ASSEMBLER__
+
+void __dead2 _psci_system_reset(void);
+void __dead2 _psci_system_off(void);
+int _psci_cpu_on(u_register_t core_mask);
+void _psci_cpu_prep_off(u_register_t core_mask);
+void __dead2 _psci_cpu_off_wfi(u_register_t core_mask,
+				u_register_t wakeup_address);
+void __dead2 _psci_cpu_pwrdn_wfi(u_register_t core_mask,
+				u_register_t wakeup_address);
+void __dead2 _psci_sys_pwrdn_wfi(u_register_t core_mask,
+				u_register_t wakeup_address);
+void _psci_wakeup(u_register_t core_mask);
+void _psci_core_entr_stdby(u_register_t core_mask);
+void _psci_core_prep_stdby(u_register_t core_mask);
+void _psci_core_exit_stdby(u_register_t core_mask);
+void _psci_core_prep_pwrdn(u_register_t core_mask);
+void _psci_core_exit_pwrdn(u_register_t core_mask);
+void _psci_clstr_prep_stdby(u_register_t core_mask);
+void _psci_clstr_exit_stdby(u_register_t core_mask);
+void _psci_clstr_prep_pwrdn(u_register_t core_mask);
+void _psci_clstr_exit_pwrdn(u_register_t core_mask);
+void _psci_sys_prep_stdby(u_register_t core_mask);
+void _psci_sys_exit_stdby(u_register_t core_mask);
+void _psci_sys_prep_pwrdn(u_register_t core_mask);
+void _psci_sys_exit_pwrdn(u_register_t core_mask);
+
+#endif
+
+#endif /* __PLAT_PSCI_H__ */
diff --git a/plat/nxp/common/psci/plat_psci.c b/plat/nxp/common/psci/plat_psci.c
new file mode 100644
index 0000000..9281e97
--- /dev/null
+++ b/plat/nxp/common/psci/plat_psci.c
@@ -0,0 +1,475 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/debug.h>
+
+#include <plat_gic.h>
+#include <plat_common.h>
+#include <plat_psci.h>
+#ifdef NXP_WARM_BOOT
+#include <plat_warm_rst.h>
+#endif
+
+#include <platform_def.h>
+
+#if (SOC_CORE_OFF || SOC_CORE_PWR_DWN)
+static void __dead2 _no_return_wfi(void)
+{
+_bl31_dead_wfi:
+	wfi();
+	goto _bl31_dead_wfi;
+}
+#endif
+
+#if (SOC_CORE_RELEASE || SOC_CORE_PWR_DWN)
+ /* the entry for core warm boot */
+static uintptr_t warmboot_entry = (uintptr_t) NULL;
+#endif
+
+#if (SOC_CORE_RELEASE)
+static int _pwr_domain_on(u_register_t mpidr)
+{
+	int core_pos = plat_core_pos(mpidr);
+	int rc = PSCI_E_INVALID_PARAMS;
+	u_register_t core_mask;
+
+	if (core_pos >= 0 && core_pos < PLATFORM_CORE_COUNT) {
+
+		_soc_set_start_addr(warmboot_entry);
+
+		dsb();
+		isb();
+
+		core_mask = (1 << core_pos);
+		rc = _psci_cpu_on(core_mask);
+	}
+
+	return (rc);
+}
+#endif
+
+#if (SOC_CORE_OFF)
+static void _pwr_domain_off(const psci_power_state_t *target_state)
+{
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state = _getCoreState(core_mask);
+
+	 /* set core state in internal data */
+	core_state = CORE_OFF_PENDING;
+	_setCoreState(core_mask, core_state);
+
+	_psci_cpu_prep_off(core_mask);
+}
+#endif
+
+#if (SOC_CORE_OFF || SOC_CORE_PWR_DWN)
+static void __dead2 _pwr_down_wfi(const psci_power_state_t *target_state)
+{
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state = _getCoreState(core_mask);
+
+	switch (core_state) {
+#if (SOC_CORE_OFF)
+	case CORE_OFF_PENDING:
+		/* set core state in internal data */
+		core_state = CORE_OFF;
+		_setCoreState(core_mask, core_state);
+
+		 /* turn the core off */
+		_psci_cpu_off_wfi(core_mask, warmboot_entry);
+	break;
+#endif
+#if (SOC_CORE_PWR_DWN)
+	case CORE_PWR_DOWN:
+		 /* power-down the core */
+		_psci_cpu_pwrdn_wfi(core_mask, warmboot_entry);
+		break;
+#endif
+#if (SOC_SYSTEM_PWR_DWN)
+	case SYS_OFF_PENDING:
+		/* set core state in internal data */
+		core_state = SYS_OFF;
+		_setCoreState(core_mask, core_state);
+
+		/* power-down the system */
+		_psci_sys_pwrdn_wfi(core_mask, warmboot_entry);
+		break;
+#endif
+	default:
+		_no_return_wfi();
+	break;
+	}
+}
+#endif
+
+#if (SOC_CORE_RELEASE || SOC_CORE_RESTART)
+static void _pwr_domain_wakeup(const psci_power_state_t *target_state)
+{
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state = _getCoreState(core_mask);
+
+	switch (core_state) {
+	case CORE_PENDING: /* this core is coming out of reset */
+
+		 /* soc per cpu setup */
+		soc_init_percpu();
+
+		 /* gic per cpu setup */
+		plat_gic_pcpu_init();
+
+		 /* set core state in internal data */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+		break;
+
+#if (SOC_CORE_RESTART)
+	case CORE_WAKEUP:
+
+		 /* this core is waking up from OFF */
+		_psci_wakeup(core_mask);
+
+		 /* set core state in internal data */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+
+	break;
+#endif
+	}
+}
+#endif
+
+#if (SOC_CORE_STANDBY)
+static void _pwr_cpu_standby(plat_local_state_t  cpu_state)
+{
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state;
+
+	if (cpu_state == PLAT_MAX_RET_STATE) {
+
+		/* set core state to standby */
+		core_state = CORE_STANDBY;
+		_setCoreState(core_mask, core_state);
+
+		_psci_core_entr_stdby(core_mask);
+
+		/* when we are here, the core is waking up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+	}
+}
+#endif
+
+#if (SOC_CORE_PWR_DWN)
+static void _pwr_suspend(const psci_power_state_t *state)
+{
+
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state;
+
+	if (state->pwr_domain_state[PLAT_MAX_LVL] == PLAT_MAX_OFF_STATE) {
+#if (SOC_SYSTEM_PWR_DWN)
+		_psci_sys_prep_pwrdn(core_mask);
+
+		 /* set core state */
+		core_state = SYS_OFF_PENDING;
+		_setCoreState(core_mask, core_state);
+#endif
+	} else if (state->pwr_domain_state[PLAT_MAX_LVL]
+				== PLAT_MAX_RET_STATE) {
+#if (SOC_SYSTEM_STANDBY)
+		_psci_sys_prep_stdby(core_mask);
+
+		 /* set core state */
+		core_state = CORE_STANDBY;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CLSTR_LVL] ==
+					PLAT_MAX_OFF_STATE) {
+#if (SOC_CLUSTER_PWR_DWN)
+		_psci_clstr_prep_pwrdn(core_mask);
+
+		 /* set core state */
+		core_state = CORE_PWR_DOWN;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CLSTR_LVL] ==
+					PLAT_MAX_RET_STATE) {
+#if (SOC_CLUSTER_STANDBY)
+		_psci_clstr_prep_stdby(core_mask);
+
+		 /* set core state */
+		core_state = CORE_STANDBY;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CORE_LVL] == PLAT_MAX_OFF_STATE) {
+#if (SOC_CORE_PWR_DWN)
+		 /* prep the core for power-down */
+		_psci_core_prep_pwrdn(core_mask);
+
+		 /* set core state */
+		core_state = CORE_PWR_DOWN;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CORE_LVL] == PLAT_MAX_RET_STATE) {
+#if (SOC_CORE_STANDBY)
+		_psci_core_prep_stdby(core_mask);
+
+		 /* set core state */
+		core_state = CORE_STANDBY;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+}
+#endif
+
+#if (SOC_CORE_PWR_DWN)
+static void _pwr_suspend_finish(const psci_power_state_t *state)
+{
+
+	u_register_t core_mask  = plat_my_core_mask();
+	u_register_t core_state;
+
+
+	if (state->pwr_domain_state[PLAT_MAX_LVL] == PLAT_MAX_OFF_STATE) {
+#if (SOC_SYSTEM_PWR_DWN)
+		_psci_sys_exit_pwrdn(core_mask);
+
+		/* when we are here, the core is back up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	} else if (state->pwr_domain_state[PLAT_MAX_LVL]
+				== PLAT_MAX_RET_STATE) {
+#if (SOC_SYSTEM_STANDBY)
+		_psci_sys_exit_stdby(core_mask);
+
+		/* when we are here, the core is waking up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CLSTR_LVL] ==
+						PLAT_MAX_OFF_STATE) {
+#if (SOC_CLUSTER_PWR_DWN)
+		_psci_clstr_exit_pwrdn(core_mask);
+
+		/* when we are here, the core is waking up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CLSTR_LVL] ==
+						PLAT_MAX_RET_STATE) {
+#if (SOC_CLUSTER_STANDBY)
+		_psci_clstr_exit_stdby(core_mask);
+
+		/* when we are here, the core is waking up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CORE_LVL] == PLAT_MAX_OFF_STATE) {
+#if (SOC_CORE_PWR_DWN)
+		_psci_core_exit_pwrdn(core_mask);
+
+		/* when we are here, the core is back up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+	else if (state->pwr_domain_state[PLAT_CORE_LVL] == PLAT_MAX_RET_STATE) {
+#if (SOC_CORE_STANDBY)
+		_psci_core_exit_stdby(core_mask);
+
+		/* when we are here, the core is waking up
+		 * set core state to released
+		 */
+		core_state = CORE_RELEASED;
+		_setCoreState(core_mask, core_state);
+#endif
+	}
+
+}
+#endif
+
+#if (SOC_CORE_STANDBY || SOC_CORE_PWR_DWN)
+
+#define PWR_STATE_TYPE_MASK    0x00010000
+#define PWR_STATE_TYPE_STNDBY  0x0
+#define PWR_STATE_TYPE_PWRDWN  0x00010000
+#define PWR_STATE_LVL_MASK     0x03000000
+#define PWR_STATE_LVL_CORE     0x0
+#define PWR_STATE_LVL_CLSTR    0x01000000
+#define PWR_STATE_LVL_SYS      0x02000000
+#define PWR_STATE_LVL_MAX      0x03000000
+
+ /* turns a requested power state into a target power state
+  * based on SoC capabilities
+  */
+static int _pwr_state_validate(uint32_t pwr_state,
+				    psci_power_state_t *state)
+{
+	int stat   = PSCI_E_INVALID_PARAMS;
+	int pwrdn  = (pwr_state & PWR_STATE_TYPE_MASK);
+	int lvl    = (pwr_state & PWR_STATE_LVL_MASK);
+
+	switch (lvl) {
+	case PWR_STATE_LVL_MAX:
+		if (pwrdn && SOC_SYSTEM_PWR_DWN)
+			state->pwr_domain_state[PLAT_MAX_LVL] =
+				PLAT_MAX_OFF_STATE;
+		else if (SOC_SYSTEM_STANDBY)
+			state->pwr_domain_state[PLAT_MAX_LVL] =
+				PLAT_MAX_RET_STATE;
+		 /* intentional fall-thru condition */
+	case PWR_STATE_LVL_SYS:
+		if (pwrdn && SOC_SYSTEM_PWR_DWN)
+			state->pwr_domain_state[PLAT_SYS_LVL] =
+				PLAT_MAX_OFF_STATE;
+		else if (SOC_SYSTEM_STANDBY)
+			state->pwr_domain_state[PLAT_SYS_LVL] =
+				PLAT_MAX_RET_STATE;
+		 /* intentional fall-thru condition */
+	case PWR_STATE_LVL_CLSTR:
+		if (pwrdn && SOC_CLUSTER_PWR_DWN)
+			state->pwr_domain_state[PLAT_CLSTR_LVL] =
+				PLAT_MAX_OFF_STATE;
+		else if (SOC_CLUSTER_STANDBY)
+			state->pwr_domain_state[PLAT_CLSTR_LVL] =
+				PLAT_MAX_RET_STATE;
+		 /* intentional fall-thru condition */
+	case PWR_STATE_LVL_CORE:
+		stat = PSCI_E_SUCCESS;
+
+		if (pwrdn && SOC_CORE_PWR_DWN)
+			state->pwr_domain_state[PLAT_CORE_LVL] =
+				PLAT_MAX_OFF_STATE;
+		else if (SOC_CORE_STANDBY)
+			state->pwr_domain_state[PLAT_CORE_LVL] =
+				PLAT_MAX_RET_STATE;
+		break;
+	}
+	return (stat);
+}
+
+#endif
+
+#if (SOC_SYSTEM_PWR_DWN)
+static void _pwr_state_sys_suspend(psci_power_state_t *req_state)
+{
+
+	/* if we need to have per-SoC settings, then we need to
+	 * extend this by calling into psci_utils.S and from there
+	 * on down to the SoC.S files
+	 */
+
+	req_state->pwr_domain_state[PLAT_MAX_LVL]   = PLAT_MAX_OFF_STATE;
+	req_state->pwr_domain_state[PLAT_SYS_LVL]   = PLAT_MAX_OFF_STATE;
+	req_state->pwr_domain_state[PLAT_CLSTR_LVL] = PLAT_MAX_OFF_STATE;
+	req_state->pwr_domain_state[PLAT_CORE_LVL]  = PLAT_MAX_OFF_STATE;
+
+}
+#endif
+
+#if defined(NXP_WARM_BOOT) && (SOC_SYSTEM_RESET2)
+static int psci_system_reset2(int is_vendor,
+			      int reset_type,
+			      u_register_t cookie)
+{
+	int ret = 0;
+
+	INFO("Executing the sequence of warm reset.\n");
+	ret = prep_n_execute_warm_reset();
+
+	return ret;
+}
+#endif
+
+static plat_psci_ops_t _psci_pm_ops = {
+#if (SOC_SYSTEM_OFF)
+	.system_off = _psci_system_off,
+#endif
+#if (SOC_SYSTEM_RESET)
+	.system_reset = _psci_system_reset,
+#endif
+#if defined(NXP_WARM_BOOT) && (SOC_SYSTEM_RESET2)
+	.system_reset2 = psci_system_reset2,
+#endif
+#if (SOC_CORE_RELEASE || SOC_CORE_RESTART)
+	 /* core released or restarted */
+	.pwr_domain_on_finish = _pwr_domain_wakeup,
+#endif
+#if (SOC_CORE_OFF)
+	 /* core shutting down */
+	.pwr_domain_off	= _pwr_domain_off,
+#endif
+#if (SOC_CORE_OFF || SOC_CORE_PWR_DWN)
+	.pwr_domain_pwr_down_wfi = _pwr_down_wfi,
+#endif
+#if (SOC_CORE_STANDBY || SOC_CORE_PWR_DWN)
+	 /* cpu_suspend */
+	.validate_power_state = _pwr_state_validate,
+#if (SOC_CORE_STANDBY)
+	.cpu_standby = _pwr_cpu_standby,
+#endif
+#if (SOC_CORE_PWR_DWN)
+	.pwr_domain_suspend        = _pwr_suspend,
+	.pwr_domain_suspend_finish = _pwr_suspend_finish,
+#endif
+#endif
+#if (SOC_SYSTEM_PWR_DWN)
+	.get_sys_suspend_power_state = _pwr_state_sys_suspend,
+#endif
+#if (SOC_CORE_RELEASE)
+	 /* core executing psci_cpu_on */
+	.pwr_domain_on	= _pwr_domain_on
+#endif
+};
+
+#if (SOC_CORE_RELEASE  || SOC_CORE_PWR_DWN)
+int plat_setup_psci_ops(uintptr_t sec_entrypoint,
+			const plat_psci_ops_t **psci_ops)
+{
+	warmboot_entry = sec_entrypoint;
+	*psci_ops = &_psci_pm_ops;
+	return 0;
+}
+
+#else
+
+int plat_setup_psci_ops(uintptr_t sec_entrypoint,
+			const plat_psci_ops_t **psci_ops)
+{
+	*psci_ops = &_psci_pm_ops;
+	return 0;
+}
+#endif
diff --git a/plat/nxp/common/psci/psci.mk b/plat/nxp/common/psci/psci.mk
new file mode 100644
index 0000000..a2791c2
--- /dev/null
+++ b/plat/nxp/common/psci/psci.mk
@@ -0,0 +1,35 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the PSCI files
+#
+# -----------------------------------------------------------------------------
+
+ifeq (${ADD_PSCI},)
+
+ADD_PSCI		:= 1
+PLAT_PSCI_PATH		:= $(PLAT_COMMON_PATH)/psci
+
+PSCI_SOURCES		:= ${PLAT_PSCI_PATH}/plat_psci.c	\
+			   ${PLAT_PSCI_PATH}/$(ARCH)/psci_utils.S	\
+			   plat/common/plat_psci_common.c
+
+PLAT_INCLUDES		+= -I${PLAT_PSCI_PATH}/include
+
+ifeq (${BL_COMM_PSCI_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${PSCI_SOURCES}
+else
+ifeq (${BL2_PSCI_NEEDED},yes)
+BL2_SOURCES		+= ${PSCI_SOURCES}
+endif
+ifeq (${BL31_PSCI_NEEDED},yes)
+BL31_SOURCES		+= ${PSCI_SOURCES}
+endif
+endif
+endif
+# -----------------------------------------------------------------------------
diff --git a/plat/nxp/common/setup/aarch64/ls_bl2_mem_params_desc.c b/plat/nxp/common/setup/aarch64/ls_bl2_mem_params_desc.c
new file mode 100644
index 0000000..7463d47
--- /dev/null
+++ b/plat/nxp/common/setup/aarch64/ls_bl2_mem_params_desc.c
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/bl_common.h>
+#include <common/desc_image_load.h>
+#ifdef CSF_HEADER_PREPENDED
+#include <csf_hdr.h>
+#endif
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+/*******************************************************************************
+ * Following descriptor provides BL image/ep information that gets used
+ * by BL2 to load the images and also subset of this information is
+ * passed to next BL image. The image loading sequence is managed by
+ * populating the images in required loading order. The image execution
+ * sequence is managed by populating the `next_handoff_image_id` with
+ * the next executable image id.
+ ******************************************************************************/
+static bl_mem_params_node_t bl2_mem_params_descs[] = {
+	/* Fill BL31 related information */
+	{
+		.image_id = BL31_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				VERSION_2, entry_point_info_t,
+				SECURE | EXECUTABLE | EP_FIRST_EXE),
+		.ep_info.pc = BL31_BASE,
+		.ep_info.spsr = SPSR_64(MODE_EL3, MODE_SP_ELX,
+				DISABLE_ALL_EXCEPTIONS),
+#if DEBUG
+		.ep_info.args.arg1 = LS_BL31_PLAT_PARAM_VAL,
+#endif
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+			VERSION_2, image_info_t, IMAGE_ATTRIB_PLAT_SETUP),
+#ifdef CSF_HEADER_PREPENDED
+		.image_info.image_base = BL31_BASE - CSF_HDR_SZ,
+		.image_info.image_max_size = (BL31_LIMIT - BL31_BASE) +
+								CSF_HDR_SZ,
+#else
+		.image_info.image_base = BL31_BASE,
+		.image_info.image_max_size = (BL31_LIMIT - BL31_BASE),
+#endif
+
+# ifdef NXP_LOAD_BL32
+		.next_handoff_image_id = BL32_IMAGE_ID,
+# else
+		.next_handoff_image_id = BL33_IMAGE_ID,
+# endif
+	},
+# ifdef NXP_LOAD_BL32
+	/* Fill BL32 related information */
+	{
+		.image_id = BL32_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+			VERSION_2, entry_point_info_t, SECURE | EXECUTABLE),
+		.ep_info.pc = BL32_BASE,
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				VERSION_2, image_info_t, 0),
+#ifdef CSF_HEADER_PREPENDED
+		.image_info.image_base = BL32_BASE - CSF_HDR_SZ,
+		.image_info.image_max_size = (BL32_LIMIT - BL32_BASE) +
+								CSF_HDR_SZ,
+#else
+		.image_info.image_base = BL32_BASE,
+		.image_info.image_max_size = (BL32_LIMIT - BL32_BASE),
+#endif
+		.next_handoff_image_id = BL33_IMAGE_ID,
+	},
+# endif /* BL32_BASE */
+
+	/* Fill BL33 related information */
+	{
+		.image_id = BL33_IMAGE_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+			VERSION_2, entry_point_info_t, NON_SECURE | EXECUTABLE),
+		.ep_info.pc = BL33_BASE,
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				VERSION_2, image_info_t, 0),
+#ifdef CSF_HEADER_PREPENDED
+		.image_info.image_base = BL33_BASE - CSF_HDR_SZ,
+		.image_info.image_max_size = (BL33_LIMIT - BL33_BASE) +
+								 CSF_HDR_SZ,
+#else
+		.image_info.image_base = BL33_BASE,
+		.image_info.image_max_size = BL33_LIMIT - BL33_BASE,
+#endif
+		.ep_info.spsr = SPSR_64(MODE_EL1, MODE_SP_ELX,
+					DISABLE_ALL_EXCEPTIONS),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	}
+};
+
+REGISTER_BL_IMAGE_DESCS(bl2_mem_params_descs)
diff --git a/plat/nxp/common/setup/common.mk b/plat/nxp/common/setup/common.mk
new file mode 100644
index 0000000..1fcf1d0
--- /dev/null
+++ b/plat/nxp/common/setup/common.mk
@@ -0,0 +1,105 @@
+#
+# Copyright 2018-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+###############################################################################
+# Flow begins in BL2 at EL3 mode
+BL2_AT_EL3			:= 1
+
+# Though one core is powered up by default, there are
+# platform specific ways to release more than one core
+COLD_BOOT_SINGLE_CPU		:= 0
+
+PROGRAMMABLE_RESET_ADDRESS	:= 1
+
+USE_COHERENT_MEM		:= 0
+
+# Use generic OID definition (tbbr_oid.h)
+USE_TBBR_DEFS			:= 1
+
+PLAT_XLAT_TABLES_DYNAMIC	:= 0
+
+ENABLE_SVE_FOR_NS		:= 0
+
+ENABLE_STACK_PROTECTOR		:= 0
+
+ERROR_DEPRECATED		:= 0
+
+LS_DISABLE_TRUSTED_WDOG		:= 1
+
+# On ARM platforms, separate the code and read-only data sections to allow
+# mapping the former as executable and the latter as execute-never.
+SEPARATE_CODE_AND_RODATA	:= 1
+
+# Enable new version of image loading on ARM platforms
+LOAD_IMAGE_V2			:= 1
+
+RCW				:= ""
+
+ifneq (${SPD},none)
+$(eval $(call add_define, NXP_LOAD_BL32))
+endif
+
+###############################################################################
+
+PLAT_TOOL_PATH		:=	tools/nxp
+CREATE_PBL_TOOL_PATH	:=	${PLAT_TOOL_PATH}/create_pbl
+PLAT_SETUP_PATH		:=	${PLAT_PATH}/common/setup
+
+PLAT_INCLUDES		+=	-I${PLAT_SETUP_PATH}/include			\
+				-Iinclude/plat/arm/common			\
+				-Iinclude/drivers/arm   			\
+				-Iinclude/lib					\
+				-Iinclude/drivers/io			\
+				-Ilib/psci
+
+# Required without TBBR.
+# To include the defines for DDR PHY Images.
+PLAT_INCLUDES		+=	-Iinclude/common/tbbr
+
+include ${PLAT_SETUP_PATH}/core.mk
+PLAT_BL_COMMON_SOURCES	+= 	${CPU_LIBS} \
+				plat/nxp/common/setup/ls_err.c		\
+				plat/nxp/common/setup/ls_common.c
+
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+PLAT_BL_COMMON_SOURCES	+=	${PLAT_SETUP_PATH}/ls_stack_protector.c
+endif
+
+include lib/xlat_tables_v2/xlat_tables.mk
+
+PLAT_BL_COMMON_SOURCES	+=	${XLAT_TABLES_LIB_SRCS}
+
+BL2_SOURCES		+=	drivers/io/io_fip.c			\
+				drivers/io/io_memmap.c			\
+				drivers/io/io_storage.c			\
+				common/desc_image_load.c 		\
+				plat/nxp/common/setup/ls_image_load.c		\
+				plat/nxp/common/setup/ls_io_storage.c		\
+				plat/nxp/common/setup/ls_bl2_el3_setup.c	\
+				plat/nxp/common/setup/${ARCH}/ls_bl2_mem_params_desc.c
+
+BL31_SOURCES		+=	plat/nxp/common/setup/ls_bl31_setup.c	\
+
+ifeq (${LS_EL3_INTERRUPT_HANDLER}, yes)
+$(eval $(call add_define, LS_EL3_INTERRUPT_HANDLER))
+BL31_SOURCES		+=	plat/nxp/common/setup/ls_interrupt_mgmt.c
+endif
+
+ifeq (${TEST_BL31}, 1)
+BL31_SOURCES		+=	${TEST_SOURCES}
+endif
+
+# Verify build config
+# -------------------
+
+ifneq (${LOAD_IMAGE_V2}, 1)
+  $(error Error: Layerscape needs LOAD_IMAGE_V2=1)
+else
+$(eval $(call add_define,LOAD_IMAGE_V2))
+endif
+
+include $(CREATE_PBL_TOOL_PATH)/create_pbl.mk
diff --git a/plat/nxp/common/setup/core.mk b/plat/nxp/common/setup/core.mk
new file mode 100644
index 0000000..82ce30e
--- /dev/null
+++ b/plat/nxp/common/setup/core.mk
@@ -0,0 +1,22 @@
+# Copyright 2018-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the CORE files
+#
+# -----------------------------------------------------------------------------
+
+CPU_LIBS		:=	lib/cpus/${ARCH}/aem_generic.S
+
+ifeq (,$(filter $(CORE_TYPE),a53 a72))
+$(error "CORE_TYPE not specified or incorrect")
+else
+UPPER_CORE_TYPE=$(shell echo $(CORE_TYPE) | tr a-z A-Z)
+$(eval $(call add_define_val,CPUECTLR_EL1,CORTEX_$(UPPER_CORE_TYPE)_ECTLR_EL1))
+CPU_LIBS		+=	lib/cpus/${ARCH}/cortex_$(CORE_TYPE).S
+endif
+
+# -----------------------------------------------------------------------------
diff --git a/plat/nxp/common/setup/include/bl31_data.h b/plat/nxp/common/setup/include/bl31_data.h
new file mode 100644
index 0000000..dd20d43
--- /dev/null
+++ b/plat/nxp/common/setup/include/bl31_data.h
@@ -0,0 +1,61 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef BL31_DATA_H
+#define	BL31_DATA_H
+
+#define SECURE_DATA_BASE     NXP_OCRAM_ADDR
+#define SECURE_DATA_SIZE     NXP_OCRAM_SIZE
+#define SECURE_DATA_TOP      (SECURE_DATA_BASE + SECURE_DATA_SIZE)
+#define SMC_REGION_SIZE      0x80
+#define SMC_GLBL_BASE        (SECURE_DATA_TOP - SMC_REGION_SIZE)
+#define BC_PSCI_DATA_SIZE    0xC0
+#define BC_PSCI_BASE         (SMC_GLBL_BASE - BC_PSCI_DATA_SIZE)
+#define SECONDARY_TOP        BC_PSCI_BASE
+
+#define SEC_PSCI_DATA_SIZE   0xC0
+#define SEC_REGION_SIZE      SEC_PSCI_DATA_SIZE
+
+/* SMC global data */
+#define BOOTLOC_OFFSET       0x0
+#define BOOT_SVCS_OSET       0x8
+
+/* offset to prefetch disable mask */
+#define PREFETCH_DIS_OFFSET  0x10
+/* must reference last smc global entry */
+#define LAST_SMC_GLBL_OFFSET 0x18
+
+#define SMC_TASK_OFFSET      0xC
+#define TSK_START_OFFSET     0x0
+#define TSK_DONE_OFFSET      0x4
+#define TSK_CORE_OFFSET      0x8
+#define SMC_TASK1_BASE       (SMC_GLBL_BASE + 32)
+#define SMC_TASK2_BASE       (SMC_TASK1_BASE + SMC_TASK_OFFSET)
+#define SMC_TASK3_BASE       (SMC_TASK2_BASE + SMC_TASK_OFFSET)
+#define SMC_TASK4_BASE       (SMC_TASK3_BASE + SMC_TASK_OFFSET)
+
+/* psci data area offsets */
+#define CORE_STATE_DATA    0x0
+#define SPSR_EL3_DATA      0x8
+#define CNTXT_ID_DATA      0x10
+#define START_ADDR_DATA    0x18
+#define LINK_REG_DATA      0x20
+#define GICC_CTLR_DATA     0x28
+#define ABORT_FLAG_DATA    0x30
+#define SCTLR_DATA         0x38
+#define CPUECTLR_DATA      0x40
+#define AUX_01_DATA        0x48  /* usage defined per SoC */
+#define AUX_02_DATA        0x50  /* usage defined per SoC */
+#define AUX_03_DATA        0x58  /* usage defined per SoC */
+#define AUX_04_DATA        0x60  /* usage defined per SoC */
+#define AUX_05_DATA        0x68  /* usage defined per SoC */
+#define AUX_06_DATA        0x70  /* usage defined per SoC */
+#define AUX_07_DATA        0x78  /* usage defined per SoC */
+#define SCR_EL3_DATA       0x80
+#define HCR_EL2_DATA       0x88
+
+#endif /* BL31_DATA_H */
diff --git a/plat/nxp/common/setup/include/ls_interrupt_mgmt.h b/plat/nxp/common/setup/include/ls_interrupt_mgmt.h
new file mode 100644
index 0000000..7dbddfb
--- /dev/null
+++ b/plat/nxp/common/setup/include/ls_interrupt_mgmt.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef LS_EL3_INTRPT_MGMT_H
+#define LS_EL3_INTRPT_MGMT_H
+
+#include <bl31/interrupt_mgmt.h>
+
+#define MAX_INTR_EL3		128
+
+/*
+ * Register handler to specific GIC entrance
+ * for INTR_TYPE_EL3 type of interrupt
+ */
+int request_intr_type_el3(uint32_t id, interrupt_type_handler_t handler);
+
+void ls_el3_interrupt_config(void);
+
+#endif	/*	LS_EL3_INTRPT_MGMT_H	*/
diff --git a/plat/nxp/common/setup/include/mmu_def.h b/plat/nxp/common/setup/include/mmu_def.h
new file mode 100644
index 0000000..2a7771b
--- /dev/null
+++ b/plat/nxp/common/setup/include/mmu_def.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef MMU_MAP_DEF_H
+#define MMU_MAP_DEF_H
+
+#include <lib/xlat_tables/xlat_tables_defs.h>
+
+#include <platform_def.h>
+
+
+#define LS_MAP_CCSR		MAP_REGION_FLAT(NXP_CCSR_ADDR, \
+					NXP_CCSR_SIZE, \
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+#ifdef NXP_DCSR_ADDR
+#define LS_MAP_DCSR		MAP_REGION_FLAT(NXP_DCSR_ADDR, \
+					NXP_DCSR_SIZE, \
+					MT_DEVICE | MT_RW | MT_SECURE)
+#endif
+
+#define LS_MAP_CONSOLE		MAP_REGION_FLAT(NXP_DUART1_ADDR, \
+					NXP_DUART_SIZE, \
+					MT_DEVICE | MT_RW | MT_NS)
+
+#define LS_MAP_OCRAM		MAP_REGION_FLAT(NXP_OCRAM_ADDR, \
+					NXP_OCRAM_SIZE, \
+					MT_DEVICE | MT_RW | MT_SECURE)
+
+#endif /* MMU_MAP_DEF_H */
diff --git a/plat/nxp/common/setup/include/plat_common.h b/plat/nxp/common/setup/include/plat_common.h
new file mode 100644
index 0000000..97a9cb7
--- /dev/null
+++ b/plat/nxp/common/setup/include/plat_common.h
@@ -0,0 +1,150 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_COMMON_H
+#define PLAT_COMMON_H
+
+#include <stdbool.h>
+
+#include <dcfg.h>
+#include <lib/el3_runtime/cpu_data.h>
+
+#include <platform_def.h>
+
+#ifdef IMAGE_BL31
+
+#define BL31_END (uintptr_t)(&__BL31_END__)
+
+/*******************************************************************************
+ * This structure represents the superset of information that can be passed to
+ * BL31 e.g. while passing control to it from BL2. The BL32 parameters will be
+ * populated only if BL2 detects its presence. A pointer to a structure of this
+ * type should be passed in X0 to BL31's cold boot entrypoint.
+ *
+ * Use of this structure and the X0 parameter is not mandatory: the BL31
+ * platform code can use other mechanisms to provide the necessary information
+ * about BL32 and BL33 to the common and SPD code.
+ *
+ * BL31 image information is mandatory if this structure is used. If either of
+ * the optional BL32 and BL33 image information is not provided, this is
+ * indicated by the respective image_info pointers being zero.
+ ******************************************************************************/
+typedef struct bl31_params {
+	param_header_t h;
+	image_info_t *bl31_image_info;
+	entry_point_info_t *bl32_ep_info;
+	image_info_t *bl32_image_info;
+	entry_point_info_t *bl33_ep_info;
+	image_info_t *bl33_image_info;
+} bl31_params_t;
+
+/* BL3 utility functions */
+void ls_bl31_early_platform_setup(void *from_bl2,
+				void *plat_params_from_bl2);
+/* LS Helper functions	*/
+unsigned int plat_my_core_mask(void);
+unsigned int plat_core_mask(u_register_t mpidr);
+unsigned int plat_core_pos(u_register_t mpidr);
+//unsigned int plat_my_core_pos(void);
+
+/* BL31 Data API(s) */
+void _init_global_data(void);
+void _initialize_psci(void);
+uint32_t _getCoreState(u_register_t core_mask);
+void _setCoreState(u_register_t core_mask, u_register_t core_state);
+
+/* SoC defined structure and API(s) */
+void soc_runtime_setup(void);
+void soc_init(void);
+void soc_platform_setup(void);
+void soc_early_platform_setup2(void);
+#endif /* IMAGE_BL31 */
+
+#ifdef IMAGE_BL2
+void soc_early_init(void);
+void soc_mem_access(void);
+void soc_preload_setup(void);
+void soc_bl2_prepare_exit(void);
+
+/* IO storage utility functions */
+int plat_io_setup(void);
+int open_backend(const uintptr_t spec);
+
+void ls_bl2_plat_arch_setup(void);
+void ls_bl2_el3_plat_arch_setup(void);
+
+enum boot_device {
+	BOOT_DEVICE_IFC_NOR,
+	BOOT_DEVICE_IFC_NAND,
+	BOOT_DEVICE_QSPI,
+	BOOT_DEVICE_EMMC,
+	BOOT_DEVICE_SDHC2_EMMC,
+	BOOT_DEVICE_FLEXSPI_NOR,
+	BOOT_DEVICE_FLEXSPI_NAND,
+	BOOT_DEVICE_NONE
+};
+
+enum boot_device get_boot_dev(void);
+
+/* DDR Related functions */
+#if DDR_INIT
+#ifdef NXP_WARM_BOOT
+long long init_ddr(uint32_t wrm_bt_flg);
+#else
+long long init_ddr(void);
+#endif
+#endif
+
+/* Board specific weak functions */
+bool board_enable_povdd(void);
+bool board_disable_povdd(void);
+
+void mmap_add_ddr_region_dynamically(void);
+#endif /* IMAGE_BL2 */
+
+typedef struct {
+	uint64_t addr;
+	uint64_t size;
+} region_info_t;
+
+typedef struct {
+	uint64_t num_dram_regions;
+	uint64_t total_dram_size;
+	region_info_t region[NUM_DRAM_REGIONS];
+} dram_regions_info_t;
+
+dram_regions_info_t *get_dram_regions_info(void);
+
+void ls_setup_page_tables(uintptr_t total_base,
+			size_t total_size,
+			uintptr_t code_start,
+			uintptr_t code_limit,
+			uintptr_t rodata_start,
+			uintptr_t rodata_limit
+#if USE_COHERENT_MEM
+			, uintptr_t coh_start,
+			uintptr_t coh_limit
+#endif
+);
+
+/* Structure to define SoC personality */
+struct soc_type {
+	char name[10];
+	uint32_t version;
+	uint8_t num_clusters;
+	uint8_t cores_per_cluster;
+};
+void get_cluster_info(const struct soc_type *soc_list, uint8_t ps_count,
+		uint8_t *num_clusters, uint8_t *cores_per_cluster);
+
+#define SOC_ENTRY(n, v, ncl, nc) {	\
+		.name = #n,		\
+		.version = SVR_##v,	\
+		.num_clusters = (ncl),	\
+		.cores_per_cluster = (nc)}
+
+#endif /* PLAT_COMMON_H */
diff --git a/plat/nxp/common/setup/include/plat_macros.S b/plat/nxp/common/setup/include/plat_macros.S
new file mode 100644
index 0000000..69a3b08
--- /dev/null
+++ b/plat/nxp/common/setup/include/plat_macros.S
@@ -0,0 +1,22 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_MACROS_S
+#define PLAT_MACROS_S
+
+	/* ---------------------------------------------
+	 * The below required platform porting macro
+	 * prints out relevant GIC and CCI registers
+	 * whenever an unhandled exception is taken in
+	 * BL31.
+	 * Clobbers: x0 - x10, x16, x17, sp
+	 * ---------------------------------------------
+	 */
+	.macro plat_crash_print_regs
+	.endm
+
+#endif /* PLAT_MACROS_S */
diff --git a/plat/nxp/common/setup/ls_bl2_el3_setup.c b/plat/nxp/common/setup/ls_bl2_el3_setup.c
new file mode 100644
index 0000000..6428eb9
--- /dev/null
+++ b/plat/nxp/common/setup/ls_bl2_el3_setup.c
@@ -0,0 +1,300 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <common/desc_image_load.h>
+#include <dcfg.h>
+#ifdef POLICY_FUSE_PROVISION
+#include <fuse_io.h>
+#endif
+#include <mmu_def.h>
+#include <plat_common.h>
+#ifdef NXP_NV_SW_MAINT_LAST_EXEC_DATA
+#include <plat_nv_storage.h>
+#endif
+
+#pragma weak bl2_el3_early_platform_setup
+#pragma weak bl2_el3_plat_arch_setup
+#pragma weak bl2_el3_plat_prepare_exit
+
+static dram_regions_info_t dram_regions_info  = {0};
+
+/*******************************************************************************
+ * Return the pointer to the 'dram_regions_info structure of the DRAM.
+ * This structure is populated after init_ddr().
+ ******************************************************************************/
+dram_regions_info_t *get_dram_regions_info(void)
+{
+	return &dram_regions_info;
+}
+
+#ifdef DDR_INIT
+static void populate_dram_regions_info(void)
+{
+	long long dram_remain_size = dram_regions_info.total_dram_size;
+	uint8_t reg_id = 0U;
+
+	dram_regions_info.region[reg_id].addr = NXP_DRAM0_ADDR;
+	dram_regions_info.region[reg_id].size =
+			dram_remain_size > NXP_DRAM0_MAX_SIZE ?
+				NXP_DRAM0_MAX_SIZE : dram_remain_size;
+
+	if (dram_regions_info.region[reg_id].size != NXP_DRAM0_SIZE) {
+		ERROR("Incorrect DRAM0 size is defined in platform_def.h\n");
+	}
+
+	dram_remain_size -= dram_regions_info.region[reg_id].size;
+	dram_regions_info.region[reg_id].size -= (NXP_SECURE_DRAM_SIZE
+						+ NXP_SP_SHRD_DRAM_SIZE);
+
+	assert(dram_regions_info.region[reg_id].size > 0);
+
+	/* Reducing total dram size by 66MB */
+	dram_regions_info.total_dram_size -= (NXP_SECURE_DRAM_SIZE
+						+ NXP_SP_SHRD_DRAM_SIZE);
+
+#if defined(NXP_DRAM1_ADDR) && defined(NXP_DRAM1_MAX_SIZE)
+	if (dram_remain_size > 0) {
+		reg_id++;
+		dram_regions_info.region[reg_id].addr = NXP_DRAM1_ADDR;
+		dram_regions_info.region[reg_id].size =
+				dram_remain_size > NXP_DRAM1_MAX_SIZE ?
+					NXP_DRAM1_MAX_SIZE : dram_remain_size;
+		dram_remain_size -= dram_regions_info.region[reg_id].size;
+	}
+#endif
+#if defined(NXP_DRAM2_ADDR) && defined(NXP_DRAM2_MAX_SIZE)
+	if (dram_remain_size > 0) {
+		reg_id++;
+		dram_regions_info.region[reg_id].addr = NXP_DRAM1_ADDR;
+		dram_regions_info.region[reg_id].size =
+				dram_remain_size > NXP_DRAM1_MAX_SIZE ?
+					NXP_DRAM1_MAX_SIZE : dram_remain_size;
+		dram_remain_size -= dram_regions_info.region[reg_id].size;
+	}
+#endif
+	reg_id++;
+	dram_regions_info.num_dram_regions = reg_id;
+}
+#endif
+
+#ifdef IMAGE_BL32
+/*******************************************************************************
+ * Gets SPSR for BL32 entry
+ ******************************************************************************/
+static uint32_t ls_get_spsr_for_bl32_entry(void)
+{
+	/*
+	 * The Secure Payload Dispatcher service is responsible for
+	 * setting the SPSR prior to entry into the BL32 image.
+	 */
+	return 0U;
+}
+#endif
+
+/*******************************************************************************
+ * Gets SPSR for BL33 entry
+ ******************************************************************************/
+#ifndef AARCH32
+static uint32_t ls_get_spsr_for_bl33_entry(void)
+{
+	unsigned int mode;
+	uint32_t spsr;
+
+	/* Figure out what mode we enter the non-secure world in */
+	mode = (el_implemented(2) != EL_IMPL_NONE) ? MODE_EL2 : MODE_EL1;
+
+	/*
+	 * TODO: Consider the possibility of specifying the SPSR in
+	 * the FIP ToC and allowing the platform to have a say as
+	 * well.
+	 */
+	spsr = SPSR_64(mode, MODE_SP_ELX, DISABLE_ALL_EXCEPTIONS);
+	return spsr;
+}
+#else
+/*******************************************************************************
+ * Gets SPSR for BL33 entry
+ ******************************************************************************/
+static uint32_t ls_get_spsr_for_bl33_entry(void)
+{
+	unsigned int hyp_status, mode, spsr;
+
+	hyp_status = GET_VIRT_EXT(read_id_pfr1());
+
+	mode = (hyp_status) ? MODE32_hyp : MODE32_svc;
+
+	/*
+	 * TODO: Consider the possibility of specifying the SPSR in
+	 * the FIP ToC and allowing the platform to have a say as
+	 * well.
+	 */
+	spsr = SPSR_MODE32(mode, plat_get_ns_image_entrypoint() & 0x1,
+			SPSR_E_LITTLE, DISABLE_ALL_EXCEPTIONS);
+	return spsr;
+}
+#endif /* AARCH32 */
+
+void bl2_el3_early_platform_setup(u_register_t arg0 __unused,
+				  u_register_t arg1 __unused,
+				  u_register_t arg2 __unused,
+				  u_register_t arg3 __unused)
+{
+	/*
+	 * SoC specific early init
+	 * Any errata handling or SoC specific early initialization can
+	 * be done here
+	 * Set Counter Base Frequency in CNTFID0 and in cntfrq_el0.
+	 * Initialize the interconnect.
+	 * Enable coherency for primary CPU cluster
+	 */
+	soc_early_init();
+
+	/* Initialise the IO layer and register platform IO devices */
+	plat_io_setup();
+
+	if (dram_regions_info.total_dram_size > 0) {
+		populate_dram_regions_info();
+	}
+
+#ifdef NXP_NV_SW_MAINT_LAST_EXEC_DATA
+	read_nv_app_data();
+#if DEBUG
+	const nv_app_data_t *nv_app_data = get_nv_data();
+
+	INFO("Value of warm_reset flag = 0x%x\n", nv_app_data->warm_rst_flag);
+	INFO("Value of WDT flag = 0x%x\n", nv_app_data->wdt_rst_flag);
+#endif
+#endif
+}
+
+/*******************************************************************************
+ * Perform the very early platform specific architectural setup here. At the
+ * moment this is only initializes the mmu in a quick and dirty way.
+ ******************************************************************************/
+void ls_bl2_el3_plat_arch_setup(void)
+{
+	unsigned int flags = 0U;
+	/* Initialise the IO layer and register platform IO devices */
+	ls_setup_page_tables(
+#if SEPARATE_RW_AND_NOLOAD
+			      BL2_START,
+			      BL2_LIMIT - BL2_START,
+#else
+			      BL2_BASE,
+			      (unsigned long)(&__BL2_END__) - BL2_BASE,
+#endif
+			      BL_CODE_BASE,
+			      BL_CODE_END,
+			      BL_RO_DATA_BASE,
+			      BL_RO_DATA_END
+#if USE_COHERENT_MEM
+			      , BL_COHERENT_RAM_BASE,
+			      BL_COHERENT_RAM_END
+#endif
+			      );
+
+	if ((dram_regions_info.region[0].addr == 0)
+		&& (dram_regions_info.total_dram_size == 0)) {
+		flags = XLAT_TABLE_NC;
+	}
+
+#ifdef AARCH32
+	enable_mmu_secure(0);
+#else
+	enable_mmu_el3(flags);
+#endif
+}
+
+void bl2_el3_plat_arch_setup(void)
+{
+	ls_bl2_el3_plat_arch_setup();
+}
+
+void bl2_platform_setup(void)
+{
+	/*
+	 * Perform platform setup before loading the image.
+	 */
+}
+
+/* Handling image information by platform. */
+int ls_bl2_handle_post_image_load(unsigned int image_id)
+{
+	int err = 0;
+	bl_mem_params_node_t *bl_mem_params = get_bl_mem_params_node(image_id);
+
+	assert(bl_mem_params);
+
+	switch (image_id) {
+	case BL31_IMAGE_ID:
+		bl_mem_params->ep_info.args.arg3 =
+					(u_register_t) &dram_regions_info;
+
+		/* Pass the value of PORSR1 register in Argument 4 */
+		bl_mem_params->ep_info.args.arg4 =
+					(u_register_t)read_reg_porsr1();
+		flush_dcache_range((uintptr_t)&dram_regions_info,
+				sizeof(dram_regions_info));
+		break;
+#if defined(AARCH64) && defined(IMAGE_BL32)
+	case BL32_IMAGE_ID:
+		bl_mem_params->ep_info.spsr = ls_get_spsr_for_bl32_entry();
+		break;
+#endif
+	case BL33_IMAGE_ID:
+		/* BL33 expects to receive the primary CPU MPID (through r0) */
+		bl_mem_params->ep_info.args.arg0 = 0xffff & read_mpidr();
+		bl_mem_params->ep_info.spsr = ls_get_spsr_for_bl33_entry();
+		break;
+	}
+
+	return err;
+}
+
+/*******************************************************************************
+ * This function can be used by the platforms to update/use image
+ * information for given `image_id`.
+ ******************************************************************************/
+int bl2_plat_handle_post_image_load(unsigned int image_id)
+{
+	return ls_bl2_handle_post_image_load(image_id);
+}
+
+void bl2_el3_plat_prepare_exit(void)
+{
+	return soc_bl2_prepare_exit();
+}
+
+/* Called to do the dynamic initialization required
+ * before loading the next image.
+ */
+void bl2_plat_preload_setup(void)
+{
+
+	soc_preload_setup();
+
+	if (dram_regions_info.total_dram_size < NXP_DRAM0_SIZE) {
+		NOTICE("ERROR: DRAM0 Size is not correctly configured.");
+		assert(false);
+	}
+
+	if ((dram_regions_info.region[0].addr == 0)
+		&& (dram_regions_info.total_dram_size > 0)) {
+		populate_dram_regions_info();
+
+		mmap_add_ddr_region_dynamically();
+	}
+
+	/* setup the memory region access permissions */
+	soc_mem_access();
+
+#ifdef POLICY_FUSE_PROVISION
+	fip_fuse_provisioning((uintptr_t)FUSE_BUF, FUSE_SZ);
+#endif
+}
diff --git a/plat/nxp/common/setup/ls_bl31_setup.c b/plat/nxp/common/setup/ls_bl31_setup.c
new file mode 100644
index 0000000..bd0ab4f
--- /dev/null
+++ b/plat/nxp/common/setup/ls_bl31_setup.c
@@ -0,0 +1,212 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
+
+#ifdef LS_EL3_INTERRUPT_HANDLER
+#include <ls_interrupt_mgmt.h>
+#endif
+#include <mmu_def.h>
+#include <plat_common.h>
+
+/*
+ * Placeholder variables for copying the arguments that have been passed to
+ * BL31 from BL2.
+ */
+#ifdef TEST_BL31
+#define  SPSR_FOR_EL2H   0x3C9
+#define  SPSR_FOR_EL1H   0x3C5
+#else
+static entry_point_info_t bl31_image_ep_info;
+#endif
+
+static entry_point_info_t bl32_image_ep_info;
+static entry_point_info_t bl33_image_ep_info;
+
+static dram_regions_info_t dram_regions_info = {0};
+static uint64_t rcw_porsr1;
+
+/* Return the pointer to the 'dram_regions_info structure of the DRAM.
+ * This structure is populated after init_ddr().
+ */
+dram_regions_info_t *get_dram_regions_info(void)
+{
+	return &dram_regions_info;
+}
+
+/* Return the RCW.PORSR1 value which was passed in from BL2
+ */
+uint64_t bl31_get_porsr1(void)
+{
+	return rcw_porsr1;
+}
+
+/*
+ * Return pointer to the 'entry_point_info' structure of the next image for the
+ * security state specified:
+ * - BL33 corresponds to the non-secure image type; while
+ * - BL32 corresponds to the secure image type.
+ * - A NULL pointer is returned, if the image does not exist.
+ */
+entry_point_info_t *bl31_plat_get_next_image_ep_info(uint32_t type)
+{
+	entry_point_info_t *next_image_info;
+
+	assert(sec_state_is_valid(type));
+	next_image_info = (type == NON_SECURE)
+			? &bl33_image_ep_info : &bl32_image_ep_info;
+
+#ifdef TEST_BL31
+	next_image_info->pc     = _get_test_entry();
+	next_image_info->spsr   = SPSR_FOR_EL2H;
+	next_image_info->h.attr = NON_SECURE;
+#endif
+
+	if (next_image_info->pc != 0U) {
+		return next_image_info;
+	} else {
+		return NULL;
+	}
+}
+
+/*
+ * Perform any BL31 early platform setup common to NXP platforms.
+ * - Here is an opportunity to copy parameters passed by the calling EL (S-EL1
+ * in BL2 & S-EL3 in BL1) before they are lost (potentially).
+ * - This needs to be done before the MMU is initialized so that the
+ *   memory layout can be used while creating page tables.
+ * - BL2 has flushed this information to memory, in order to fetch latest data.
+ */
+
+void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
+				u_register_t arg2, u_register_t arg3)
+{
+#ifndef TEST_BL31
+	int i = 0;
+	void *from_bl2 = (void *)arg0;
+#endif
+	soc_early_platform_setup2();
+
+#ifdef TEST_BL31
+	dram_regions_info.num_dram_regions  = 2;
+	dram_regions_info.total_dram_size   = 0x100000000;
+	dram_regions_info.region[0].addr    = 0x80000000;
+	dram_regions_info.region[0].size    = 0x80000000;
+	dram_regions_info.region[1].addr    = 0x880000000;
+	dram_regions_info.region[1].size    = 0x80000000;
+
+	bl33_image_ep_info.pc = _get_test_entry();
+#else
+	/*
+	 * Check params passed from BL2 should not be NULL,
+	 */
+	bl_params_t *params_from_bl2 = (bl_params_t *)from_bl2;
+
+	assert(params_from_bl2 != NULL);
+	assert(params_from_bl2->h.type == PARAM_BL_PARAMS);
+	assert(params_from_bl2->h.version >= VERSION_2);
+
+	bl_params_node_t *bl_params = params_from_bl2->head;
+
+	/*
+	 * Copy BL33 and BL32 (if present), entry point information.
+	 * They are stored in Secure RAM, in BL2's address space.
+	 */
+	while (bl_params != NULL) {
+		if (bl_params->image_id == BL31_IMAGE_ID) {
+			bl31_image_ep_info = *bl_params->ep_info;
+			dram_regions_info_t *loc_dram_regions_info =
+			(dram_regions_info_t *) bl31_image_ep_info.args.arg3;
+
+			dram_regions_info.num_dram_regions =
+					loc_dram_regions_info->num_dram_regions;
+			dram_regions_info.total_dram_size =
+					loc_dram_regions_info->total_dram_size;
+			VERBOSE("Number of DRAM Regions = %" PRIx64 "\n",
+					dram_regions_info.num_dram_regions);
+
+			for (i = 0; i < dram_regions_info.num_dram_regions;
+									i++) {
+				dram_regions_info.region[i].addr =
+					loc_dram_regions_info->region[i].addr;
+				dram_regions_info.region[i].size =
+					loc_dram_regions_info->region[i].size;
+				VERBOSE("DRAM%d Size = %" PRIx64 "\n", i,
+					dram_regions_info.region[i].size);
+			}
+			rcw_porsr1 = bl31_image_ep_info.args.arg4;
+		}
+
+		if (bl_params->image_id == BL32_IMAGE_ID) {
+			bl32_image_ep_info = *bl_params->ep_info;
+		}
+
+		if (bl_params->image_id == BL33_IMAGE_ID) {
+			bl33_image_ep_info = *bl_params->ep_info;
+		}
+
+		bl_params = bl_params->next_params_info;
+	}
+#endif /* TEST_BL31 */
+
+	if (bl33_image_ep_info.pc == 0) {
+		panic();
+	}
+
+	/*
+	 * perform basic initialization on the soc
+	 */
+	soc_init();
+}
+
+/*******************************************************************************
+ * Perform any BL31 platform setup common to ARM standard platforms
+ ******************************************************************************/
+void bl31_platform_setup(void)
+{
+	NOTICE("Welcome to %s BL31 Phase\n", BOARD);
+	soc_platform_setup();
+
+	/* Console logs gone missing as part going to
+	 * EL1 for initilizing Bl32 if present.
+	 * console flush is necessary to avoid it.
+	 */
+	(void)console_flush();
+}
+
+void bl31_plat_runtime_setup(void)
+{
+#ifdef LS_EL3_INTERRUPT_HANDLER
+	ls_el3_interrupt_config();
+#endif
+	soc_runtime_setup();
+}
+
+/*******************************************************************************
+ * Perform the very early platform specific architectural setup shared between
+ * ARM standard platforms. This only does basic initialization. Later
+ * architectural setup (bl31_arch_setup()) does not do anything platform
+ * specific.
+ ******************************************************************************/
+void bl31_plat_arch_setup(void)
+{
+
+	ls_setup_page_tables(BL31_BASE,
+			      BL31_END - BL31_BASE,
+			      BL_CODE_BASE,
+			      BL_CODE_END,
+			      BL_RO_DATA_BASE,
+			      BL_RO_DATA_END
+#if USE_COHERENT_MEM
+			      , BL_COHERENT_RAM_BASE,
+			      BL_COHERENT_RAM_END
+#endif
+			      );
+	enable_mmu_el3(0);
+}
diff --git a/plat/nxp/common/setup/ls_common.c b/plat/nxp/common/setup/ls_common.c
new file mode 100644
index 0000000..e7ae060
--- /dev/null
+++ b/plat/nxp/common/setup/ls_common.c
@@ -0,0 +1,264 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <mmu_def.h>
+#include <plat/common/platform.h>
+
+#include "plat_common.h"
+#include "platform_def.h"
+
+const mmap_region_t *plat_ls_get_mmap(void);
+
+/*
+ * Table of memory regions for various BL stages to map using the MMU.
+ * This doesn't include Trusted SRAM as arm_setup_page_tables() already
+ * takes care of mapping it.
+ *
+ * The flash needs to be mapped as writable in order to erase the FIP's Table of
+ * Contents in case of unrecoverable error (see plat_error_handler()).
+ */
+#ifdef IMAGE_BL2
+const mmap_region_t plat_ls_mmap[] = {
+	LS_MAP_CCSR,
+	{0}
+};
+#endif
+
+#ifdef IMAGE_BL31
+const mmap_region_t plat_ls_mmap[] = {
+	LS_MAP_CCSR,
+#ifdef NXP_DCSR_ADDR
+	LS_MAP_DCSR,
+#endif
+	LS_MAP_OCRAM,
+	{0}
+};
+#endif
+#ifdef IMAGE_BL32
+const mmap_region_t plat_ls_mmap[] = {
+	LS_MAP_CCSR,
+	LS_MAP_BL32_SEC_MEM,
+	{0}
+};
+#endif
+
+/* Weak definitions may be overridden in specific NXP SoC */
+#pragma weak plat_get_ns_image_entrypoint
+#pragma weak plat_ls_get_mmap
+
+#if defined(IMAGE_BL31) || !defined(CONFIG_DDR_FIP_IMAGE)
+static void mmap_add_ddr_regions_statically(void)
+{
+	int i = 0;
+	dram_regions_info_t *info_dram_regions = get_dram_regions_info();
+	/* MMU map for Non-Secure DRAM Regions */
+	VERBOSE("DRAM Region %d: %p - %p\n", i,
+			(void *) info_dram_regions->region[i].addr,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				- 1));
+	mmap_add_region(info_dram_regions->region[i].addr,
+			info_dram_regions->region[i].addr,
+			info_dram_regions->region[i].size,
+			MT_MEMORY | MT_RW | MT_NS);
+
+	/* MMU map for Secure DDR Region on DRAM-0 */
+	if (info_dram_regions->region[i].size >
+		(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE)) {
+		VERBOSE("Secure DRAM Region %d: %p - %p\n", i,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				+ NXP_SECURE_DRAM_SIZE
+				+ NXP_SP_SHRD_DRAM_SIZE
+				- 1));
+		mmap_add_region((info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+				(info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+				(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE),
+				MT_MEMORY | MT_RW | MT_SECURE);
+	}
+
+#ifdef IMAGE_BL31
+	for (i = 1; i < info_dram_regions->num_dram_regions; i++) {
+		if (info_dram_regions->region[i].size == 0)
+			break;
+		VERBOSE("DRAM Region %d: %p - %p\n", i,
+			(void *) info_dram_regions->region[i].addr,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				- 1));
+		mmap_add_region(info_dram_regions->region[i].addr,
+				info_dram_regions->region[i].addr,
+				info_dram_regions->region[i].size,
+				MT_MEMORY | MT_RW | MT_NS);
+	}
+#endif
+}
+#endif
+
+#if defined(PLAT_XLAT_TABLES_DYNAMIC)
+void mmap_add_ddr_region_dynamically(void)
+{
+	int i = 0;
+	dram_regions_info_t *info_dram_regions = get_dram_regions_info();
+	/* MMU map for Non-Secure DRAM Regions */
+	VERBOSE("DRAM Region %d: %p - %p\n", i,
+			(void *) info_dram_regions->region[i].addr,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				- 1));
+	mmap_add_dynamic_region(info_dram_regions->region[i].addr,
+			info_dram_regions->region[i].addr,
+			info_dram_regions->region[i].size,
+			MT_MEMORY | MT_RW | MT_NS);
+
+	/* MMU map for Secure DDR Region on DRAM-0 */
+	if (info_dram_regions->region[i].size >
+		(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE)) {
+		VERBOSE("Secure DRAM Region %d: %p - %p\n", i,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				+ NXP_SECURE_DRAM_SIZE
+				+ NXP_SP_SHRD_DRAM_SIZE
+				- 1));
+		mmap_add_dynamic_region((info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+				(info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size),
+				(NXP_SECURE_DRAM_SIZE + NXP_SP_SHRD_DRAM_SIZE),
+				MT_MEMORY | MT_RW | MT_SECURE);
+	}
+
+#ifdef IMAGE_BL31
+	for (i = 1; i < info_dram_regions->num_dram_regions; i++) {
+		if (info_dram_regions->region[i].size == 0) {
+			break;
+		}
+		VERBOSE("DRAM Region %d: %p - %p\n", i,
+			(void *) info_dram_regions->region[i].addr,
+			(void *) (info_dram_regions->region[i].addr
+				+ info_dram_regions->region[i].size
+				- 1));
+		mmap_add_dynamic_region(info_dram_regions->region[i].addr,
+				info_dram_regions->region[i].addr,
+				info_dram_regions->region[i].size,
+				MT_MEMORY | MT_RW | MT_NS);
+	}
+#endif
+}
+#endif
+
+/*
+ * Set up the page tables for the generic and platform-specific memory regions.
+ * The extents of the generic memory regions are specified by the function
+ * arguments and consist of:
+ * - Trusted SRAM seen by the BL image;
+ * - Code section;
+ * - Read-only data section;
+ * - Coherent memory region, if applicable.
+ */
+void ls_setup_page_tables(uintptr_t total_base,
+			   size_t total_size,
+			   uintptr_t code_start,
+			   uintptr_t code_limit,
+			   uintptr_t rodata_start,
+			   uintptr_t rodata_limit
+#if USE_COHERENT_MEM
+			   ,
+			   uintptr_t coh_start,
+			   uintptr_t coh_limit
+#endif
+			   )
+{
+	/*
+	 * Map the Trusted SRAM with appropriate memory attributes.
+	 * Subsequent mappings will adjust the attributes for specific regions.
+	 */
+	VERBOSE("Memory seen by this BL image: %p - %p\n",
+		(void *) total_base, (void *) (total_base + total_size));
+	mmap_add_region(total_base, total_base,
+			total_size,
+			MT_MEMORY | MT_RW | MT_SECURE);
+
+	/* Re-map the code section */
+	VERBOSE("Code region: %p - %p\n",
+		(void *) code_start, (void *) code_limit);
+	mmap_add_region(code_start, code_start,
+			code_limit - code_start,
+			MT_CODE | MT_SECURE);
+
+	/* Re-map the read-only data section */
+	VERBOSE("Read-only data region: %p - %p\n",
+		(void *) rodata_start, (void *) rodata_limit);
+	mmap_add_region(rodata_start, rodata_start,
+			rodata_limit - rodata_start,
+			MT_RO_DATA | MT_SECURE);
+
+#if USE_COHERENT_MEM
+	/* Re-map the coherent memory region */
+	VERBOSE("Coherent region: %p - %p\n",
+		(void *) coh_start, (void *) coh_limit);
+	mmap_add_region(coh_start, coh_start,
+			coh_limit - coh_start,
+			MT_DEVICE | MT_RW | MT_SECURE);
+#endif
+
+	/* Now (re-)map the platform-specific memory regions */
+	mmap_add(plat_ls_get_mmap());
+
+
+#if defined(IMAGE_BL31) || !defined(CONFIG_DDR_FIP_IMAGE)
+	mmap_add_ddr_regions_statically();
+#endif
+
+	/* Create the page tables to reflect the above mappings */
+	init_xlat_tables();
+}
+
+/*******************************************************************************
+ * Returns NXP platform specific memory map regions.
+ ******************************************************************************/
+const mmap_region_t *plat_ls_get_mmap(void)
+{
+	return plat_ls_mmap;
+}
+
+/*
+ * This function get the number of clusters and cores count per cluster
+ * in the SoC.
+ */
+void get_cluster_info(const struct soc_type *soc_list, uint8_t ps_count,
+		uint8_t *num_clusters, uint8_t *cores_per_cluster)
+{
+	const soc_info_t *soc_info = get_soc_info();
+	*num_clusters = NUMBER_OF_CLUSTERS;
+	*cores_per_cluster = CORES_PER_CLUSTER;
+	unsigned int i;
+
+	for (i = 0U; i < ps_count; i++) {
+		if (soc_list[i].version == soc_info->svr_reg.bf_ver.version) {
+			*num_clusters = soc_list[i].num_clusters;
+			*cores_per_cluster = soc_list[i].cores_per_cluster;
+			break;
+		}
+	}
+
+	VERBOSE("NUM of cluster = 0x%x, Cores per cluster = 0x%x\n",
+			*num_clusters, *cores_per_cluster);
+}
diff --git a/plat/nxp/common/setup/ls_err.c b/plat/nxp/common/setup/ls_err.c
new file mode 100644
index 0000000..845cd15
--- /dev/null
+++ b/plat/nxp/common/setup/ls_err.c
@@ -0,0 +1,55 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+
+#if TRUSTED_BOARD_BOOT
+#include <dcfg.h>
+#include <snvs.h>
+#endif
+
+#include "plat_common.h"
+
+/*
+ * Error handler
+ */
+void plat_error_handler(int err)
+{
+#if TRUSTED_BOARD_BOOT
+	uint32_t mode;
+	bool sb = check_boot_mode_secure(&mode);
+#endif
+
+	switch (err) {
+	case -ENOENT:
+	case -EAUTH:
+		printf("Authentication failure\n");
+#if TRUSTED_BOARD_BOOT
+		/* For SB production mode i.e ITS = 1 */
+		if (sb == true) {
+			if (mode == 1U) {
+				transition_snvs_soft_fail();
+			} else {
+				transition_snvs_non_secure();
+			}
+		}
+#endif
+		break;
+	default:
+		/* Unexpected error */
+		break;
+	}
+
+	/* Loop until the watchdog resets the system */
+	for (;;)
+		wfi();
+}
diff --git a/plat/nxp/common/setup/ls_image_load.c b/plat/nxp/common/setup/ls_image_load.c
new file mode 100644
index 0000000..259ab31
--- /dev/null
+++ b/plat/nxp/common/setup/ls_image_load.c
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/desc_image_load.h>
+
+/*******************************************************************************
+ * This function flushes the data structures so that they are visible
+ * in memory for the next BL image.
+ ******************************************************************************/
+void plat_flush_next_bl_params(void)
+{
+	flush_bl_params_desc();
+}
+
+/*******************************************************************************
+ * This function returns the list of loadable images.
+ ******************************************************************************/
+bl_load_info_t *plat_get_bl_image_load_info(void)
+{
+	return get_bl_load_info_from_mem_params_desc();
+}
+
+/*******************************************************************************
+ * This function returns the list of executable images.
+ ******************************************************************************/
+bl_params_t *plat_get_next_bl_params(void)
+{
+	return get_next_bl_params_from_mem_params_desc();
+}
diff --git a/plat/nxp/common/setup/ls_interrupt_mgmt.c b/plat/nxp/common/setup/ls_interrupt_mgmt.c
new file mode 100644
index 0000000..a81cb2b
--- /dev/null
+++ b/plat/nxp/common/setup/ls_interrupt_mgmt.c
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <bl31/interrupt_mgmt.h>
+#include <common/debug.h>
+#include <ls_interrupt_mgmt.h>
+#include <plat/common/platform.h>
+
+static interrupt_type_handler_t type_el3_interrupt_table[MAX_INTR_EL3];
+
+int request_intr_type_el3(uint32_t id, interrupt_type_handler_t handler)
+{
+	/* Validate 'handler' and 'id' parameters */
+	if (!handler || id >= MAX_INTR_EL3) {
+		return -EINVAL;
+	}
+
+	/* Check if a handler has already been registered */
+	if (type_el3_interrupt_table[id] != NULL) {
+		return -EALREADY;
+	}
+
+	type_el3_interrupt_table[id] = handler;
+
+	return 0;
+}
+
+static uint64_t ls_el3_interrupt_handler(uint32_t id, uint32_t flags,
+					  void *handle, void *cookie)
+{
+	uint32_t intr_id;
+	interrupt_type_handler_t handler;
+
+	intr_id = plat_ic_get_pending_interrupt_id();
+
+	INFO("Interrupt recvd is %d\n", intr_id);
+
+	handler = type_el3_interrupt_table[intr_id];
+	if (handler != NULL) {
+		handler(intr_id, flags, handle, cookie);
+	}
+
+	/*
+	 * Mark this interrupt as complete to avoid a interrupt storm.
+	 */
+	plat_ic_end_of_interrupt(intr_id);
+
+	return 0U;
+}
+
+void ls_el3_interrupt_config(void)
+{
+	uint64_t flags = 0U;
+	uint64_t rc;
+
+	set_interrupt_rm_flag(flags, NON_SECURE);
+	rc = register_interrupt_type_handler(INTR_TYPE_EL3,
+					     ls_el3_interrupt_handler, flags);
+	if (rc != 0U) {
+		panic();
+	}
+}
diff --git a/plat/nxp/common/setup/ls_io_storage.c b/plat/nxp/common/setup/ls_io_storage.c
new file mode 100644
index 0000000..0c01765
--- /dev/null
+++ b/plat/nxp/common/setup/ls_io_storage.c
@@ -0,0 +1,519 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <endian.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <common/tbbr/tbbr_img_def.h>
+#include <drivers/io/io_block.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_fip.h>
+#include <drivers/io/io_memmap.h>
+#include <drivers/io/io_storage.h>
+#ifdef FLEXSPI_NOR_BOOT
+#include <flexspi_nor.h>
+#endif
+#if defined(QSPI_BOOT)
+#include <qspi.h>
+#endif
+#if defined(SD_BOOT) || defined(EMMC_BOOT)
+#include <sd_mmc.h>
+#endif
+#include <tools_share/firmware_image_package.h>
+
+#ifdef CONFIG_DDR_FIP_IMAGE
+#include <ddr_io_storage.h>
+#endif
+#ifdef POLICY_FUSE_PROVISION
+#include <fuse_io.h>
+#endif
+#include "plat_common.h"
+#include "platform_def.h"
+
+uint32_t fip_device;
+/* IO devices */
+uintptr_t backend_dev_handle;
+
+static const io_dev_connector_t *fip_dev_con;
+static uintptr_t fip_dev_handle;
+static const io_dev_connector_t *backend_dev_con;
+
+static io_block_spec_t fip_block_spec = {
+	.offset = PLAT_FIP_OFFSET,
+	.length = PLAT_FIP_MAX_SIZE
+};
+
+static const io_uuid_spec_t bl2_uuid_spec = {
+	.uuid = UUID_TRUSTED_BOOT_FIRMWARE_BL2,
+};
+
+static const io_uuid_spec_t fuse_bl2_uuid_spec = {
+	.uuid = UUID_SCP_FIRMWARE_SCP_BL2,
+};
+
+static const io_uuid_spec_t bl31_uuid_spec = {
+	.uuid = UUID_EL3_RUNTIME_FIRMWARE_BL31,
+};
+
+static const io_uuid_spec_t bl32_uuid_spec = {
+	.uuid = UUID_SECURE_PAYLOAD_BL32,
+};
+
+static const io_uuid_spec_t bl33_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FIRMWARE_BL33,
+};
+
+static const io_uuid_spec_t tb_fw_config_uuid_spec = {
+	.uuid = UUID_TB_FW_CONFIG,
+};
+
+static const io_uuid_spec_t hw_config_uuid_spec = {
+	.uuid = UUID_HW_CONFIG,
+};
+
+#if TRUSTED_BOARD_BOOT
+static const io_uuid_spec_t tb_fw_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_BOOT_FW_CERT,
+};
+
+static const io_uuid_spec_t trusted_key_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_KEY_CERT,
+};
+
+static const io_uuid_spec_t fuse_key_cert_uuid_spec = {
+	.uuid = UUID_SCP_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t soc_fw_key_cert_uuid_spec = {
+	.uuid = UUID_SOC_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t tos_fw_key_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_OS_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t nt_fw_key_cert_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FW_KEY_CERT,
+};
+
+static const io_uuid_spec_t fuse_cert_uuid_spec = {
+	.uuid = UUID_SCP_FW_CONTENT_CERT,
+};
+
+static const io_uuid_spec_t soc_fw_cert_uuid_spec = {
+	.uuid = UUID_SOC_FW_CONTENT_CERT,
+};
+
+static const io_uuid_spec_t tos_fw_cert_uuid_spec = {
+	.uuid = UUID_TRUSTED_OS_FW_CONTENT_CERT,
+};
+
+static const io_uuid_spec_t nt_fw_cert_uuid_spec = {
+	.uuid = UUID_NON_TRUSTED_FW_CONTENT_CERT,
+};
+#endif /* TRUSTED_BOARD_BOOT */
+
+static int open_fip(const uintptr_t spec);
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+/* By default, ARM platforms load images from the FIP */
+static const struct plat_io_policy policies[] = {
+	[FIP_IMAGE_ID] = {
+		&backend_dev_handle,
+		(uintptr_t)&fip_block_spec,
+		open_backend
+	},
+	[BL2_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl2_uuid_spec,
+		open_fip
+	},
+	[SCP_BL2_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&fuse_bl2_uuid_spec,
+		open_fip
+	},
+	[BL31_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl31_uuid_spec,
+		open_fip
+	},
+	[BL32_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl32_uuid_spec,
+		open_fip
+	},
+	[BL33_IMAGE_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&bl33_uuid_spec,
+		open_fip
+	},
+	[TB_FW_CONFIG_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tb_fw_config_uuid_spec,
+		open_fip
+	},
+	[HW_CONFIG_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&hw_config_uuid_spec,
+		open_fip
+	},
+#if TRUSTED_BOARD_BOOT
+	[TRUSTED_BOOT_FW_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tb_fw_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&trusted_key_cert_uuid_spec,
+		open_fip
+	},
+	[SCP_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&fuse_key_cert_uuid_spec,
+		open_fip
+	},
+	[SOC_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&soc_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_OS_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tos_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[NON_TRUSTED_FW_KEY_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&nt_fw_key_cert_uuid_spec,
+		open_fip
+	},
+	[SCP_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&fuse_cert_uuid_spec,
+		open_fip
+	},
+	[SOC_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&soc_fw_cert_uuid_spec,
+		open_fip
+	},
+	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&tos_fw_cert_uuid_spec,
+		open_fip
+	},
+	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
+		&fip_dev_handle,
+		(uintptr_t)&nt_fw_cert_uuid_spec,
+		open_fip
+	},
+#endif /* TRUSTED_BOARD_BOOT */
+};
+
+
+/* Weak definitions may be overridden in specific ARM standard platform */
+#pragma weak plat_io_setup
+
+/*
+ * Return an IO device handle and specification which can be used to access
+ */
+static int open_fip(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	/* See if a Firmware Image Package is available */
+	result = io_dev_init(fip_dev_handle, (uintptr_t)FIP_IMAGE_ID);
+	if (result == 0) {
+		result = io_open(fip_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			VERBOSE("Using FIP\n");
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+
+int open_backend(const uintptr_t spec)
+{
+	int result;
+	uintptr_t local_image_handle;
+
+	result = io_dev_init(backend_dev_handle, (uintptr_t)NULL);
+	if (result == 0) {
+		result = io_open(backend_dev_handle, spec, &local_image_handle);
+		if (result == 0) {
+			io_close(local_image_handle);
+		}
+	}
+	return result;
+}
+
+#if defined(SD_BOOT) || defined(EMMC_BOOT)
+static int plat_io_block_setup(size_t fip_offset, uintptr_t block_dev_spec)
+{
+	int io_result;
+
+	fip_block_spec.offset = fip_offset;
+
+	io_result = register_io_dev_block(&backend_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to devices and cache the handles */
+	io_result = io_dev_open(backend_dev_con, block_dev_spec,
+				&backend_dev_handle);
+	assert(io_result == 0);
+
+	return io_result;
+}
+#endif
+
+#if defined(FLEXSPI_NOR_BOOT) || defined(QSPI_BOOT)
+static int plat_io_memmap_setup(size_t fip_offset)
+{
+	int io_result;
+
+	fip_block_spec.offset = fip_offset;
+
+	io_result = register_io_dev_memmap(&backend_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to devices and cache the handles */
+	io_result = io_dev_open(backend_dev_con, (uintptr_t)NULL,
+				&backend_dev_handle);
+	assert(io_result == 0);
+
+	return io_result;
+}
+#endif
+
+static int ls_io_fip_setup(unsigned int boot_dev)
+{
+	int io_result;
+
+	io_result = register_io_dev_fip(&fip_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to devices and cache the handles */
+	io_result = io_dev_open(fip_dev_con, (uintptr_t)&fip_device,
+				&fip_dev_handle);
+	assert(io_result == 0);
+
+#ifdef CONFIG_DDR_FIP_IMAGE
+	/* Open connection to DDR FIP image if available */
+	io_result = ddr_fip_setup(fip_dev_con, boot_dev);
+
+	assert(io_result == 0);
+#endif
+
+#ifdef POLICY_FUSE_PROVISION
+	/* Open connection to FUSE FIP image if available */
+	io_result = fuse_fip_setup(fip_dev_con, boot_dev);
+
+	assert(io_result == 0);
+#endif
+
+	return io_result;
+}
+
+int ls_qspi_io_setup(void)
+{
+#ifdef QSPI_BOOT
+	qspi_io_setup(NXP_QSPI_FLASH_ADDR,
+			NXP_QSPI_FLASH_SIZE,
+			PLAT_FIP_OFFSET);
+	return plat_io_memmap_setup(NXP_QSPI_FLASH_ADDR + PLAT_FIP_OFFSET);
+#else
+	ERROR("QSPI driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+#endif
+}
+
+int emmc_sdhc2_io_setup(void)
+{
+#if defined(EMMC_BOOT) && defined(NXP_ESDHC2_ADDR)
+	uintptr_t block_dev_spec;
+	int ret;
+
+	ret = sd_emmc_init(&block_dev_spec,
+			NXP_ESDHC2_ADDR,
+			NXP_SD_BLOCK_BUF_ADDR,
+			NXP_SD_BLOCK_BUF_SIZE,
+			false);
+	if (ret != 0) {
+		return ret;
+	}
+
+	return plat_io_block_setup(PLAT_FIP_OFFSET, block_dev_spec);
+#else
+	ERROR("EMMC driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+#endif
+}
+
+int emmc_io_setup(void)
+{
+/* On the platforms which only has one ESDHC controller,
+ * eMMC-boot will use the first ESDHC controller.
+ */
+#if defined(SD_BOOT) || defined(EMMC_BOOT)
+	uintptr_t block_dev_spec;
+	int ret;
+
+	ret = sd_emmc_init(&block_dev_spec,
+			NXP_ESDHC_ADDR,
+			NXP_SD_BLOCK_BUF_ADDR,
+			NXP_SD_BLOCK_BUF_SIZE,
+			true);
+	if (ret != 0) {
+		return ret;
+	}
+
+	return plat_io_block_setup(PLAT_FIP_OFFSET, block_dev_spec);
+#else
+	ERROR("SD driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+#endif
+}
+
+int ifc_nor_io_setup(void)
+{
+	ERROR("NOR driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+}
+
+int ifc_nand_io_setup(void)
+{
+	ERROR("NAND driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+}
+
+int ls_flexspi_nor_io_setup(void)
+{
+#ifdef FLEXSPI_NOR_BOOT
+	int ret = 0;
+
+	ret = flexspi_nor_io_setup(NXP_FLEXSPI_FLASH_ADDR,
+				   NXP_FLEXSPI_FLASH_SIZE,
+				   NXP_FLEXSPI_ADDR);
+
+	if (ret != 0) {
+		ERROR("FlexSPI NOR driver initialization error.\n");
+		/* Should never reach here */
+		assert(0);
+		panic();
+		return -1;
+	}
+
+	return plat_io_memmap_setup(NXP_FLEXSPI_FLASH_ADDR + PLAT_FIP_OFFSET);
+#else
+	ERROR("FlexSPI NOR driver not present. Check your BUILD\n");
+
+	/* Should never reach here */
+	assert(false);
+	return -1;
+#endif
+}
+
+static int (* const ls_io_setup_table[])(void) = {
+	[BOOT_DEVICE_IFC_NOR] = ifc_nor_io_setup,
+	[BOOT_DEVICE_IFC_NAND] = ifc_nand_io_setup,
+	[BOOT_DEVICE_QSPI] = ls_qspi_io_setup,
+	[BOOT_DEVICE_EMMC] = emmc_io_setup,
+	[BOOT_DEVICE_SDHC2_EMMC] = emmc_sdhc2_io_setup,
+	[BOOT_DEVICE_FLEXSPI_NOR] = ls_flexspi_nor_io_setup,
+	[BOOT_DEVICE_FLEXSPI_NAND] = ls_flexspi_nor_io_setup,
+};
+
+
+int plat_io_setup(void)
+{
+	int (*io_setup)(void);
+	unsigned int boot_dev = BOOT_DEVICE_NONE;
+	int ret;
+
+	boot_dev = get_boot_dev();
+	if (boot_dev == BOOT_DEVICE_NONE) {
+		ERROR("Boot Device detection failed, Check RCW_SRC\n");
+		return -EINVAL;
+	}
+
+	io_setup = ls_io_setup_table[boot_dev];
+	ret = io_setup();
+	if (ret != 0) {
+		return ret;
+	}
+
+	ret = ls_io_fip_setup(boot_dev);
+	if (ret != 0) {
+		return ret;
+	}
+
+	return 0;
+}
+
+
+/* Return an IO device handle and specification which can be used to access
+ * an image. Use this to enforce platform load policy
+ */
+int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
+			  uintptr_t *image_spec)
+{
+	int result = -1;
+	const struct plat_io_policy *policy;
+
+	if (image_id < ARRAY_SIZE(policies)) {
+
+		policy = &policies[image_id];
+		result = policy->check(policy->image_spec);
+		if (result == 0) {
+			*image_spec = policy->image_spec;
+			*dev_handle = *(policy->dev_handle);
+		}
+	}
+#ifdef CONFIG_DDR_FIP_IMAGE
+	else {
+		VERBOSE("Trying alternative IO\n");
+		result = plat_get_ddr_fip_image_source(image_id, dev_handle,
+						image_spec, open_backend);
+	}
+#endif
+#ifdef POLICY_FUSE_PROVISION
+	if (result != 0) {
+		VERBOSE("Trying FUSE IO\n");
+		result = plat_get_fuse_image_source(image_id, dev_handle,
+						image_spec, open_backend);
+	}
+#endif
+
+	return result;
+}
diff --git a/plat/nxp/common/setup/ls_stack_protector.c b/plat/nxp/common/setup/ls_stack_protector.c
new file mode 100644
index 0000000..ab78f88
--- /dev/null
+++ b/plat/nxp/common/setup/ls_stack_protector.c
@@ -0,0 +1,22 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdint.h>
+
+#include <arch_helpers.h>
+
+#include <plat/common/platform.h>
+
+#define RANDOM_CANARY_VALUE ((u_register_t) 3288484550995823360ULL)
+
+u_register_t plat_get_stack_protector_canary(void)
+{
+	/*
+	 * TBD: Generate Random Number from NXP CAAM Block.
+	 */
+	return RANDOM_CANARY_VALUE ^ read_cntpct_el0();
+}
diff --git a/plat/nxp/common/sip_svc/aarch64/sipsvc.S b/plat/nxp/common/sip_svc/aarch64/sipsvc.S
new file mode 100644
index 0000000..6a47cbf
--- /dev/null
+++ b/plat/nxp/common/sip_svc/aarch64/sipsvc.S
@@ -0,0 +1,152 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <asm_macros.S>
+#include <bl31_data.h>
+
+.global el2_2_aarch32
+.global prefetch_disable
+
+#define  SPSR_EL3_M4     0x10
+#define  SPSR_EL_MASK    0xC
+#define  SPSR_EL2        0x8
+#define  SCR_EL3_4_EL2_AARCH32  0x131
+#define  SPSR32_EL2_LE          0x1DA
+
+#define  MIDR_PARTNUM_START      4
+#define  MIDR_PARTNUM_WIDTH      12
+#define  MIDR_PARTNUM_A53        0xD03
+#define  MIDR_PARTNUM_A57        0xD07
+#define  MIDR_PARTNUM_A72        0xD08
+
+/*
+ * uint64_t el2_2_aarch32(u_register_t smc_id,
+ *                   u_register_t start_addr,
+ *                   u_register_t parm1,
+ *                   u_register_t parm2)
+ * this function allows changing the execution width of EL2 from Aarch64
+ * to Aarch32
+ * Note: MUST be called from EL2 @ Aarch64
+ * in:  x0 = smc function id
+ *      x1 = start address for EL2 @ Aarch32
+ *      x2 = first parameter to pass to EL2 @ Aarch32
+ *      x3 = second parameter to pass to EL2 @ Aarch32
+ * out: x0 = 0,  on success
+ *      x0 = -1, on failure
+ * uses x0, x1, x2, x3
+ */
+func el2_2_aarch32
+
+	/* check that caller is EL2 @ Aarch64 - err return if not */
+	mrs  x0, spsr_el3
+	/* see if we were called from Aarch32 */
+	tst  x0, #SPSR_EL3_M4
+	b.ne 2f
+
+	/* see if we were called from EL2 */
+	and   x0, x0, SPSR_EL_MASK
+	cmp   x0, SPSR_EL2
+	b.ne  2f
+
+	/* set ELR_EL3 */
+	msr  elr_el3, x1
+
+	/* set scr_el3 */
+	mov  x0, #SCR_EL3_4_EL2_AARCH32
+	msr  scr_el3, x0
+
+	/* set sctlr_el2 */
+	ldr   x1, =SCTLR_EL2_RES1
+	msr  sctlr_el2, x1
+
+	/* set spsr_el3 */
+	ldr  x0, =SPSR32_EL2_LE
+	msr  spsr_el3, x0
+
+	/* x2 = parm 1
+	 * x3 = parm2
+	 */
+
+	/* set the parameters to be passed-thru to EL2 @ Aarch32 */
+	mov  x1, x2
+	mov  x2, x3
+
+	/* x1 = parm 1
+	 * x2 = parm2
+	 */
+
+	mov  x0, xzr
+	/* invalidate the icache */
+	ic iallu
+	dsb sy
+	isb
+	b  1f
+2:
+	/* error return */
+	mvn  x0, xzr
+	ret
+1:
+	eret
+endfunc el2_2_aarch32
+
+/*
+ * int prefetch_disable(u_register_t smc_id, u_register_t mask)
+ * this function marks cores which need to have the prefetch disabled -
+ * secondary cores have prefetch disabled when they are released from reset -
+ * the bootcore has prefetch disabled when this call is made
+ * in:  x0 = function id
+ *      x1 = core mask, where bit[0]=core0, bit[1]=core1, etc
+ *           if a bit in the mask is set, then prefetch is disabled for that
+ *           core
+ * out: x0 = SMC_SUCCESS
+ */
+func prefetch_disable
+	stp  x4, x30, [sp, #-16]!
+
+	mov   x3, x1
+
+	/* x1 = core prefetch disable mask */
+	/* x3 = core prefetch disable mask */
+
+	/* store the mask */
+	mov   x0, #PREFETCH_DIS_OFFSET
+	bl   _set_global_data
+
+	/* x3 = core prefetch disable mask */
+
+	/* see if we need to disable prefetch on THIS core */
+	bl   plat_my_core_mask
+
+	/* x0 = core mask lsb */
+	/* x3 = core prefetch disable mask */
+
+	tst   x3, x0
+	b.eq  1f
+
+	/* read midr_el1 */
+	mrs   x1, midr_el1
+
+	/* x1 = midr_el1 */
+
+	mov   x0, xzr
+	bfxil x0, x1, #MIDR_PARTNUM_START, #MIDR_PARTNUM_WIDTH
+
+	/* x0 = part number (a53, a57, a72, etc) */
+
+	/* branch on cpu-specific */
+	cmp   x0, #MIDR_PARTNUM_A57
+	b.eq  1f
+	cmp   x0, #MIDR_PARTNUM_A72
+	b.ne  1f
+
+	bl    _disable_ldstr_pfetch_A72
+	b     1f
+1:
+	ldp   x4, x30, [sp], #16
+	mov   x0, xzr
+	ret
+endfunc prefetch_disable
diff --git a/plat/nxp/common/sip_svc/include/sipsvc.h b/plat/nxp/common/sip_svc/include/sipsvc.h
new file mode 100644
index 0000000..d9e61e9
--- /dev/null
+++ b/plat/nxp/common/sip_svc/include/sipsvc.h
@@ -0,0 +1,80 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef SIPSVC_H
+#define SIPSVC_H
+
+#include <stdint.h>
+
+#define SMC_FUNC_MASK			0x0000ffff
+#define SMC32_PARAM_MASK		0xffffffff
+
+/* SMC function IDs for SiP Service queries */
+#define SIP_SVC_CALL_COUNT		0xff00
+#define SIP_SVC_UID			0xff01
+#define SIP_SVC_VERSION			0xff03
+#define SIP_SVC_PRNG			0xff10
+#define SIP_SVC_RNG			0xff11
+#define SIP_SVC_MEM_BANK		0xff12
+#define SIP_SVC_PREFETCH_DIS		0xff13
+#define SIP_SVC_HUK			0xff14
+#define SIP_SVC_ALLOW_L1L2_ERR		0xff15
+#define SIP_SVC_ALLOW_L2_CLR		0xff16
+#define SIP_SVC_2_AARCH32		0xff17
+#define SIP_SVC_PORSR1			0xff18
+
+/* Layerscape SiP Service Calls version numbers */
+#define LS_SIP_SVC_VERSION_MAJOR	0x0
+#define LS_SIP_SVC_VERSION_MINOR	0x1
+
+/* Number of Layerscape SiP Calls implemented */
+#define LS_COMMON_SIP_NUM_CALLS		10
+
+/* Parameter Type Constants */
+#define SIP_PARAM_TYPE_NONE		0x0
+#define SIP_PARAM_TYPE_VALUE_INPUT	0x1
+#define SIP_PARAM_TYPE_VALUE_OUTPUT	0x2
+#define SIP_PARAM_TYPE_VALUE_INOUT	0x3
+#define SIP_PARAM_TYPE_MEMREF_INPUT	0x5
+#define SIP_PARAM_TYPE_MEMREF_OUTPUT	0x6
+#define SIP_PARAM_TYPE_MEMREF_INOUT	0x7
+
+#define SIP_PARAM_TYPE_MASK		0xF
+
+/*
+ * The macro SIP_PARAM_TYPES can be used to construct a value that you can
+ * compare against an incoming paramTypes to check the type of all the
+ * parameters in one comparison.
+ */
+#define SIP_PARAM_TYPES(t0, t1, t2, t3) \
+		((t0) | ((t1) << 4) | ((t2) << 8) | ((t3) << 12))
+
+/*
+ * The macro SIP_PARAM_TYPE_GET can be used to extract the type of a given
+ * parameter from paramTypes if you need more fine-grained type checking.
+ */
+#define SIP_PARAM_TYPE_GET(t, i)	((((uint32_t)(t)) >> ((i) * 4)) & 0xF)
+
+/*
+ * The macro SIP_PARAM_TYPE_SET can be used to load the type of a given
+ * parameter from paramTypes without specifying all types (SIP_PARAM_TYPES)
+ */
+#define SIP_PARAM_TYPE_SET(t, i)	(((uint32_t)(t) & 0xF) << ((i) * 4))
+
+#define SIP_SVC_RNG_PARAMS		(SIP_PARAM_TYPE_VALUE_INPUT, \
+					 SIP_PARAM_TYPE_MEMREF_OUTPUT, \
+					 SIP_PARAM_TYPE_NONE, \
+					 SIP_PARAM_TYPE_NONE)
+
+/* Layerscape SiP Calls error code */
+enum {
+	LS_SIP_SUCCESS = 0,
+	LS_SIP_INVALID_PARAM = -1,
+	LS_SIP_NOT_SUPPORTED = -2,
+};
+
+#endif /* SIPSVC_H */
diff --git a/plat/nxp/common/sip_svc/sip_svc.c b/plat/nxp/common/sip_svc/sip_svc.c
new file mode 100644
index 0000000..1c8668e
--- /dev/null
+++ b/plat/nxp/common/sip_svc/sip_svc.c
@@ -0,0 +1,194 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <caam.h>
+#include <common/runtime_svc.h>
+#include <dcfg.h>
+#include <lib/mmio.h>
+#include <tools_share/uuid.h>
+
+#include <plat_common.h>
+#include <sipsvc.h>
+
+/* Layerscape SiP Service UUID */
+DEFINE_SVC_UUID2(nxp_sip_svc_uid,
+		 0x871de4ef, 0xedfc, 0x4209, 0xa4, 0x23,
+		 0x8d, 0x23, 0x75, 0x9d, 0x3b, 0x9f);
+
+#pragma weak nxp_plat_sip_handler
+static uintptr_t nxp_plat_sip_handler(unsigned int smc_fid,
+				      u_register_t x1,
+				      u_register_t x2,
+				      u_register_t x3,
+				      u_register_t x4,
+				      void *cookie,
+				      void *handle,
+				      u_register_t flags)
+{
+	ERROR("%s: unhandled SMC (0x%x)\n", __func__, smc_fid);
+	SMC_RET1(handle, SMC_UNK);
+}
+
+uint64_t el2_2_aarch32(u_register_t smc_id, u_register_t start_addr,
+		       u_register_t parm1, u_register_t parm2);
+
+uint64_t prefetch_disable(u_register_t smc_id, u_register_t mask);
+uint64_t bl31_get_porsr1(void);
+
+static void clean_top_32b_of_param(uint32_t smc_fid,
+				   u_register_t *px1,
+				   u_register_t *px2,
+				   u_register_t *px3,
+				   u_register_t *px4)
+{
+	/* if parameters from SMC32. Clean top 32 bits */
+	if (GET_SMC_CC(smc_fid) == SMC_32) {
+		*px1 = *px1 & SMC32_PARAM_MASK;
+		*px2 = *px2 & SMC32_PARAM_MASK;
+		*px3 = *px3 & SMC32_PARAM_MASK;
+		*px4 = *px4 & SMC32_PARAM_MASK;
+	}
+}
+
+/* This function handles Layerscape defined SiP Calls */
+static uintptr_t nxp_sip_handler(unsigned int smc_fid,
+				 u_register_t x1,
+				 u_register_t x2,
+				 u_register_t x3,
+				 u_register_t x4,
+				 void *cookie,
+				 void *handle,
+				 u_register_t flags)
+{
+	uint32_t ns;
+	uint64_t ret;
+	dram_regions_info_t *info_dram_regions;
+
+	/* if parameter is sent from SMC32. Clean top 32 bits */
+	clean_top_32b_of_param(smc_fid, &x1, &x2, &x3, &x4);
+
+	/* Determine which security state this SMC originated from */
+	ns = is_caller_non_secure(flags);
+	if (ns == 0) {
+		/* SiP SMC service secure world's call */
+		;
+	} else {
+		/* SiP SMC service normal world's call */
+		;
+	}
+
+	switch (smc_fid & SMC_FUNC_MASK) {
+	case SIP_SVC_RNG:
+		if (is_sec_enabled() == false) {
+			NOTICE("SEC is disabled.\n");
+			SMC_RET1(handle, SMC_UNK);
+		}
+
+		/* Return zero on failure */
+		ret = get_random((int)x1);
+		if (ret != 0) {
+			SMC_RET2(handle, SMC_OK, ret);
+		} else {
+			SMC_RET1(handle, SMC_UNK);
+		}
+		/* break is not required as SMC_RETx return */
+	case SIP_SVC_HUK:
+		if (is_sec_enabled() == false) {
+			NOTICE("SEC is disabled.\n");
+			SMC_RET1(handle, SMC_UNK);
+		}
+		ret = get_hw_unq_key_blob_hw((uint8_t *) x1, (uint32_t) x2);
+
+		if (ret == SMC_OK) {
+			SMC_RET1(handle, SMC_OK);
+		} else {
+			SMC_RET1(handle, SMC_UNK);
+		}
+		/* break is not required as SMC_RETx return */
+	case SIP_SVC_MEM_BANK:
+		VERBOSE("Handling SMC SIP_SVC_MEM_BANK.\n");
+		info_dram_regions = get_dram_regions_info();
+
+		if (x1 == -1) {
+			SMC_RET2(handle, SMC_OK,
+					info_dram_regions->total_dram_size);
+		} else if (x1 >= info_dram_regions->num_dram_regions) {
+			SMC_RET1(handle, SMC_UNK);
+		} else {
+			SMC_RET3(handle, SMC_OK,
+				info_dram_regions->region[x1].addr,
+				info_dram_regions->region[x1].size);
+		}
+		/* break is not required as SMC_RETx return */
+	case SIP_SVC_PREFETCH_DIS:
+		VERBOSE("In SIP_SVC_PREFETCH_DIS call\n");
+		ret = prefetch_disable(smc_fid, x1);
+		if (ret == SMC_OK) {
+			SMC_RET1(handle, SMC_OK);
+		} else {
+			SMC_RET1(handle, SMC_UNK);
+		}
+		/* break is not required as SMC_RETx return */
+	case SIP_SVC_2_AARCH32:
+		ret = el2_2_aarch32(smc_fid, x1, x2, x3);
+
+		/* In success case, control should not reach here. */
+		NOTICE("SMC: SIP_SVC_2_AARCH32 Failed.\n");
+		SMC_RET1(handle, SMC_UNK);
+		/* break is not required as SMC_RETx return */
+	case SIP_SVC_PORSR1:
+		ret = bl31_get_porsr1();
+		SMC_RET2(handle, SMC_OK, ret);
+		/* break is not required as SMC_RETx return */
+	default:
+		return nxp_plat_sip_handler(smc_fid, x1, x2, x3, x4,
+				cookie, handle, flags);
+	}
+}
+
+/* This function is responsible for handling all SiP calls */
+static uintptr_t sip_smc_handler(unsigned int smc_fid,
+				 u_register_t x1,
+				 u_register_t x2,
+				 u_register_t x3,
+				 u_register_t x4,
+				 void *cookie,
+				 void *handle,
+				 u_register_t flags)
+{
+	switch (smc_fid & SMC_FUNC_MASK) {
+	case SIP_SVC_CALL_COUNT:
+		/* Return the number of Layerscape SiP Service Calls. */
+		SMC_RET1(handle, LS_COMMON_SIP_NUM_CALLS);
+		break;
+	case SIP_SVC_UID:
+		/* Return UID to the caller */
+		SMC_UUID_RET(handle, nxp_sip_svc_uid);
+		break;
+	case SIP_SVC_VERSION:
+		/* Return the version of current implementation */
+		SMC_RET2(handle, LS_SIP_SVC_VERSION_MAJOR,
+			 LS_SIP_SVC_VERSION_MINOR);
+		break;
+	default:
+		return nxp_sip_handler(smc_fid, x1, x2, x3, x4,
+				       cookie, handle, flags);
+	}
+}
+
+/* Define a runtime service descriptor for fast SMC calls */
+DECLARE_RT_SVC(
+	nxp_sip_svc,
+	OEN_SIP_START,
+	OEN_SIP_END,
+	SMC_TYPE_FAST,
+	NULL,
+	sip_smc_handler
+);
diff --git a/plat/nxp/common/sip_svc/sipsvc.mk b/plat/nxp/common/sip_svc/sipsvc.mk
new file mode 100644
index 0000000..c3a57de
--- /dev/null
+++ b/plat/nxp/common/sip_svc/sipsvc.mk
@@ -0,0 +1,35 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# Select the SIP SVC files
+#
+# -----------------------------------------------------------------------------
+
+ifeq (${ADD_SIPSVC},)
+
+ADD_SIPSVC		:= 1
+
+PLAT_SIPSVC_PATH	:= $(PLAT_COMMON_PATH)/sip_svc
+
+SIPSVC_SOURCES		:= ${PLAT_SIPSVC_PATH}/sip_svc.c \
+			   ${PLAT_SIPSVC_PATH}/$(ARCH)/sipsvc.S
+
+PLAT_INCLUDES		+=	-I${PLAT_SIPSVC_PATH}/include
+
+ifeq (${BL_COMM_SIPSVC_NEEDED},yes)
+BL_COMMON_SOURCES	+= ${SIPSVC_SOURCES}
+else
+ifeq (${BL2_SIPSVC_NEEDED},yes)
+BL2_SOURCES		+= ${SIPSVC_SOURCES}
+endif
+ifeq (${BL31_SIPSVC_NEEDED},yes)
+BL31_SOURCES		+= ${SIPSVC_SOURCES}
+endif
+endif
+endif
+# -----------------------------------------------------------------------------
diff --git a/plat/nxp/common/soc_errata/errata.c b/plat/nxp/common/soc_errata/errata.c
new file mode 100644
index 0000000..fb1818a
--- /dev/null
+++ b/plat/nxp/common/soc_errata/errata.c
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <common/debug.h>
+
+#include "errata_list.h"
+
+void soc_errata(void)
+{
+#ifdef ERRATA_SOC_A050426
+	INFO("SoC workaround for Errata A050426 was applied\n");
+	erratum_a050426();
+#endif
+	/*
+	 * The following DDR Erratas workaround are implemented in DDR driver,
+	 * but print information here.
+	 */
+#if ERRATA_DDR_A011396
+	INFO("SoC workaround for DDR Errata A011396 was applied\n");
+#endif
+#if ERRATA_DDR_A050450
+	INFO("SoC workaround for DDR Errata A050450 was applied\n");
+#endif
+}
diff --git a/plat/nxp/common/soc_errata/errata.h b/plat/nxp/common/soc_errata/errata.h
new file mode 100644
index 0000000..b543b4b
--- /dev/null
+++ b/plat/nxp/common/soc_errata/errata.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef ERRATA_H
+#define ERRATA_H
+
+void soc_errata(void);
+
+#endif /* ERRATA_H */
diff --git a/plat/nxp/common/soc_errata/errata.mk b/plat/nxp/common/soc_errata/errata.mk
new file mode 100644
index 0000000..2942615
--- /dev/null
+++ b/plat/nxp/common/soc_errata/errata.mk
@@ -0,0 +1,23 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+# Platform Errata Build flags.
+# These should be enabled by the platform if the erratum workaround needs to be
+# applied.
+
+ERRATA := \
+  ERRATA_SOC_A050426
+
+define enable_errata
+  $(1) ?= 0
+  ifeq ($$($(1)),1)
+    $$(eval $$(call add_define,$(1)))
+    BL2_SOURCES += $(PLAT_COMMON_PATH)/soc_errata/errata_a$(shell echo $(1)|awk -F '_A' '{print $$NF}').c
+  endif
+endef
+
+$(foreach e,$(ERRATA),$(eval $(call enable_errata,$(strip $(e)))))
+
+BL2_SOURCES += $(PLAT_COMMON_PATH)/soc_errata/errata.c
diff --git a/plat/nxp/common/soc_errata/errata_a050426.c b/plat/nxp/common/soc_errata/errata_a050426.c
new file mode 100644
index 0000000..13a0000
--- /dev/null
+++ b/plat/nxp/common/soc_errata/errata_a050426.c
@@ -0,0 +1,415 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <mmio.h>
+
+void erratum_a050426(void)
+{
+	uint32_t i, val3, val4;
+
+	/* Enable BIST to access Internal memory locations */
+	val3 = mmio_read_32(0x700117E60);
+	mmio_write_32(0x700117E60, (val3 | 0x80000001));
+	val4 = mmio_read_32(0x700117E90);
+	mmio_write_32(0x700117E90, (val4 & 0xFFDFFFFF));
+
+	/* wriop Internal Memory.*/
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x706312000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706312400 + (i * 4), 0x55555555);
+		mmio_write_32(0x706312800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706314000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706314400 + (i * 4), 0x55555555);
+		mmio_write_32(0x706314800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706314c00 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x706316000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706320000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706320400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 2U; i++) {
+		mmio_write_32(0x70640a000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x706518000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706519000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x706522000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706522800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706523000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706523800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706524000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706524800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706608000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706608800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706609000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706609800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70660a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70660a800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70660b000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70660b800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70660c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70660c800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 2U; i++) {
+		mmio_write_32(0x706718000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706718800 + (i * 4), 0x55555555);
+	}
+	mmio_write_32(0x706b0a000 + (i * 4), 0x55555555);
+
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x706b0e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706b0e800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 2U; i++) {
+		mmio_write_32(0x706b10000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706b10400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x706b14000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706b14800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706b15000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706b15800 + (i * 4), 0x55555555);
+	}
+	mmio_write_32(0x706e12000 + (i * 4), 0x55555555);
+
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x706e14000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e14800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 2U; i++) {
+		mmio_write_32(0x706e16000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e16400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x706e1a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1a800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1b000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1b800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1c800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1e800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1f000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e1f800 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e20000 + (i * 4), 0x55555555);
+		mmio_write_32(0x706e20800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x707108000 + (i * 4), 0x55555555);
+		mmio_write_32(0x707109000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70710a000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 2U; i++) {
+		mmio_write_32(0x70711c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70711c800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70711d000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70711d800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70711e000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x707120000 + (i * 4), 0x55555555);
+		mmio_write_32(0x707121000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x707122000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725b000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725e400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725e800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725ec00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725f000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70725f400 + (i * 4), 0x55555555);
+		mmio_write_32(0x707340000 + (i * 4), 0x55555555);
+		mmio_write_32(0x707346000 + (i * 4), 0x55555555);
+		mmio_write_32(0x707484000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70748a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70748b000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70748c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70748d000 + (i * 4), 0x55555555);
+	}
+
+	/* EDMA Internal Memory.*/
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70a208000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a208800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a209000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a209800 + (i * 4), 0x55555555);
+	}
+
+	/* PEX1 Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70a508000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70a520000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a528000 + (i * 4), 0x55555555);
+	}
+
+	/* PEX2 Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70a608000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70a620000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a628000 + (i * 4), 0x55555555);
+	}
+
+	/* PEX3 Internal Memory.*/
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70a708000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a728000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a730000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a738000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a748000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a758000 + (i * 4), 0x55555555);
+	}
+
+	/* PEX4 Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70a808000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70a820000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70a828000 + (i * 4), 0x55555555);
+	}
+
+	/* PEX5 Internal Memory.*/
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70aa08000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70aa28000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70aa30000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70aa38000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70aa48000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70aa58000 + (i * 4), 0x55555555);
+	}
+
+	/* PEX6 Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70ab08000 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70ab20000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70ab28000 + (i * 4), 0x55555555);
+	}
+
+	/* QDMA Internal Memory.*/
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70b008000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b00c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b010000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b014000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b018000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b018400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01a400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01d000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01e800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01f000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b01f800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b020000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b020400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b020800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b020c00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b022000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b022400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b024000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b024800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b025000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b025800 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 4U; i++) {
+		mmio_write_32(0x70b026000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b026200 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70b028000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b028800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b029000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70b029800 + (i * 4), 0x55555555);
+	}
+
+	/* lnx1_e1000#0 Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c00a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00a200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00a400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00a600 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00a800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00aa00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00ac00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00ae00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00b000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00b200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00b400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00b600 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00b800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00ba00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00bc00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00be00 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c00c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00c400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00c800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00cc00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00d000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00d400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00d800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00dc00 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c00e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c00f000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012600 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012a00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012c00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c012e00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013600 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013a00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013c00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c013e00 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c014000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c014400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c014800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c014c00 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c015000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c015400 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c015800 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c015c00 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c016000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c017000 + (i * 4), 0x55555555);
+	}
+
+	/* lnx1_xfi Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c108000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c108200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c10a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c10a400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c10c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c10c400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c10e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c10e200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c110000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c110400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c112000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c112400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c114000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c114200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c116000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c116400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c118000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c118400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c11a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c11a200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c11c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c11c400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c11e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c11e400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c120000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c120200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c122000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c122400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c124000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c124400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c126000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c126200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c128000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c128400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c12a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c12a400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c12c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c12c200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c12e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c12e400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c130000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c130400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c132000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c132200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c134000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c134400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c136000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c136400 + (i * 4), 0x55555555);
+	}
+
+	/* lnx2_xfi Internal Memory.*/
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c308000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c308200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c30a000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c30a400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c30c000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c30c400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 3U; i++) {
+		mmio_write_32(0x70c30e000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c30e200 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c310000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c310400 + (i * 4), 0x55555555);
+	}
+	for (i = 0U; i < 5U; i++) {
+		mmio_write_32(0x70c312000 + (i * 4), 0x55555555);
+		mmio_write_32(0x70c312400 + (i * 4), 0x55555555);
+	}
+
+	/* Disable BIST */
+	mmio_write_32(0x700117E60, val3);
+	mmio_write_32(0x700117E90, val4);
+}
diff --git a/plat/nxp/common/soc_errata/errata_list.h b/plat/nxp/common/soc_errata/errata_list.h
new file mode 100644
index 0000000..74d2315
--- /dev/null
+++ b/plat/nxp/common/soc_errata/errata_list.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef ERRATA_LIST_H
+#define ERRATA_LIST_H
+
+#ifdef ERRATA_SOC_A050426
+void erratum_a050426(void);
+#endif
+
+#endif /* ERRATA_LIST_H */
diff --git a/plat/nxp/common/tbbr/csf_tbbr.c b/plat/nxp/common/tbbr/csf_tbbr.c
new file mode 100644
index 0000000..8f38f3e
--- /dev/null
+++ b/plat/nxp/common/tbbr/csf_tbbr.c
@@ -0,0 +1,81 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ *
+ */
+
+#include <errno.h>
+
+#include <common/debug.h>
+#include <csf_hdr.h>
+#include <dcfg.h>
+#include <drivers/auth/crypto_mod.h>
+#include <snvs.h>
+
+#include <plat/common/platform.h>
+#include "plat_common.h"
+
+extern bool rotpk_not_dpld;
+extern uint8_t rotpk_hash_table[MAX_KEY_ENTRIES][SHA256_BYTES];
+extern uint32_t num_rotpk_hash_entries;
+
+/*
+ * In case of secure boot, return ptr of rotpk_hash table in key_ptr and
+ * number of hashes in key_len
+ */
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	uint32_t mode = 0U;
+	*flags = ROTPK_NOT_DEPLOYED;
+
+	/* ROTPK hash table must be available for secure boot */
+	if (rotpk_not_dpld == true) {
+		if (check_boot_mode_secure(&mode) == true) {
+			/* Production mode, don;t continue further */
+			if (mode == 1U) {
+				return -EAUTH;
+			}
+
+			/* For development mode, rotpk flag false
+			 * indicates that SRK hash comparison might
+			 * have failed. This is not fatal error.
+			 * Continue in this case but transition SNVS
+			 * to non-secure state
+			 */
+			transition_snvs_non_secure();
+			return 0;
+		} else {
+			return 0;
+		}
+	}
+
+	/*
+	 * We return the complete hash table and number of entries in
+	 * table for NXP platform specific implementation.
+	 * Here hash is always assume as SHA-256
+	 */
+	*key_ptr = rotpk_hash_table;
+	*key_len = num_rotpk_hash_entries;
+	*flags = ROTPK_IS_HASH;
+
+	return 0;
+}
+
+int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
+{
+	/*
+	 * No support for non-volatile counter. Update the ROT key to protect
+	 * the system against rollback.
+	 */
+	*nv_ctr = 0U;
+
+	return 0;
+}
+
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	return 0;
+}
diff --git a/plat/nxp/common/tbbr/nxp_rotpk.S b/plat/nxp/common/tbbr/nxp_rotpk.S
new file mode 100644
index 0000000..8e084d1
--- /dev/null
+++ b/plat/nxp/common/tbbr/nxp_rotpk.S
@@ -0,0 +1,21 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ *
+ */
+
+#ifndef _CSF_HDR_H_
+
+	.global nxp_rotpk_hash
+	.global nxp_rotpk_hash_end
+	.section .rodata.nxp_rotpk_hash, "a"
+nxp_rotpk_hash:
+	/* DER header */
+	.byte 0x30, 0x31, 0x30, 0x0D, 0x06, 0x09, 0x60, 0x86, 0x48
+	.byte 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0x04, 0x20
+	/* SHA256 */
+	.incbin ROTPK_HASH
+nxp_rotpk_hash_end:
+#endif
diff --git a/plat/nxp/common/tbbr/tbbr.mk b/plat/nxp/common/tbbr/tbbr.mk
new file mode 100644
index 0000000..25852ba
--- /dev/null
+++ b/plat/nxp/common/tbbr/tbbr.mk
@@ -0,0 +1,155 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# For TRUSTED_BOARD_BOOT platforms need to include this makefile
+# Following definations are to be provided by platform.mk file or
+# by user - BL33_INPUT_FILE, BL32_INPUT_FILE, BL31_INPUT_FILE
+
+ifeq ($(CHASSIS), 2)
+include $(PLAT_DRIVERS_PATH)/csu/csu.mk
+CSF_FILE		:=	input_blx_ch${CHASSIS}
+BL2_CSF_FILE		:=	input_bl2_ch${CHASSIS}
+else
+ifeq ($(CHASSIS), 3_2)
+CSF_FILE		:=	input_blx_ch3
+BL2_CSF_FILE		:=	input_bl2_ch${CHASSIS}
+PBI_CSF_FILE		:=	input_pbi_ch${CHASSIS}
+$(eval $(call add_define, CSF_HDR_CH3))
+else
+    $(error -> CHASSIS not set!)
+endif
+endif
+
+PLAT_AUTH_PATH		:=  $(PLAT_DRIVERS_PATH)/auth
+
+
+ifeq (${BL2_INPUT_FILE},)
+    BL2_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${BL2_CSF_FILE}
+endif
+
+ifeq (${PBI_INPUT_FILE},)
+    PBI_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${PBI_CSF_FILE}
+endif
+
+# If MBEDTLS_DIR is not specified, use CSF Header option
+ifeq (${MBEDTLS_DIR},)
+    # Generic image processing filters to prepend CSF header
+    ifeq (${BL33_INPUT_FILE},)
+    BL33_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${CSF_FILE}
+    endif
+
+    ifeq (${BL31_INPUT_FILE},)
+    BL31_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${CSF_FILE}
+    endif
+
+    ifeq (${BL32_INPUT_FILE},)
+    BL32_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${CSF_FILE}
+    endif
+
+    ifeq (${FUSE_INPUT_FILE},)
+    FUSE_INPUT_FILE	:= $(PLAT_AUTH_PATH)/csf_hdr_parser/${CSF_FILE}
+    endif
+
+    PLAT_INCLUDES	+= -I$(PLAT_DRIVERS_PATH)/sfp
+    PLAT_TBBR_SOURCES	+= $(PLAT_AUTH_PATH)/csf_hdr_parser/cot.c	\
+			   $(PLAT_COMMON_PATH)/tbbr/csf_tbbr.c
+    # IMG PARSER here is CSF header parser
+    include $(PLAT_DRIVERS_PATH)/auth/csf_hdr_parser/csf_hdr.mk
+    PLAT_TBBR_SOURCES 	+=	$(CSF_HDR_SOURCES)
+
+    SCP_BL2_PRE_TOOL_FILTER	:= CST_SCP_BL2
+    BL31_PRE_TOOL_FILTER	:= CST_BL31
+    BL32_PRE_TOOL_FILTER	:= CST_BL32
+    BL33_PRE_TOOL_FILTER	:= CST_BL33
+else
+
+    ifeq (${DISABLE_FUSE_WRITE}, 1)
+        $(eval $(call add_define,DISABLE_FUSE_WRITE))
+    endif
+
+    # For Mbedtls currently crypto is not supported via CAAM
+    # enable it when that support is there
+    CAAM_INTEG		:= 0
+    KEY_ALG		:= rsa
+    KEY_SIZE		:= 2048
+
+    $(eval $(call add_define,MBEDTLS_X509))
+    ifeq (${PLAT_DDR_PHY},PHY_GEN2)
+        $(eval $(call add_define,PLAT_DEF_OID))
+    endif
+    include drivers/auth/mbedtls/mbedtls_x509.mk
+
+
+    PLAT_TBBR_SOURCES	+= $(PLAT_AUTH_PATH)/tbbr/tbbr_cot.c \
+			   $(PLAT_COMMON_PATH)/tbbr/nxp_rotpk.S \
+			   $(PLAT_COMMON_PATH)/tbbr/x509_tbbr.c
+
+    #ROTPK key is embedded in BL2 image
+    ifeq (${ROT_KEY},)
+	ROT_KEY		= $(BUILD_PLAT)/rot_key.pem
+    endif
+
+    ifeq (${SAVE_KEYS},1)
+
+        ifeq (${TRUSTED_WORLD_KEY},)
+            TRUSTED_WORLD_KEY = ${BUILD_PLAT}/trusted.pem
+        endif
+
+        ifeq (${NON_TRUSTED_WORLD_KEY},)
+            NON_TRUSTED_WORLD_KEY = ${BUILD_PLAT}/non-trusted.pem
+        endif
+
+        ifeq (${BL31_KEY},)
+            BL31_KEY = ${BUILD_PLAT}/soc.pem
+        endif
+
+        ifeq (${BL32_KEY},)
+            BL32_KEY = ${BUILD_PLAT}/trusted_os.pem
+        endif
+
+        ifeq (${BL33_KEY},)
+            BL33_KEY = ${BUILD_PLAT}/non-trusted_os.pem
+        endif
+
+    endif
+
+    ROTPK_HASH		= $(BUILD_PLAT)/rotpk_sha256.bin
+
+    $(eval $(call add_define_val,ROTPK_HASH,'"$(ROTPK_HASH)"'))
+
+    $(BUILD_PLAT)/bl2/nxp_rotpk.o: $(ROTPK_HASH)
+
+    certificates: $(ROT_KEY)
+    $(ROT_KEY): | $(BUILD_PLAT)
+	@echo "  OPENSSL $@"
+	@if [ ! -f $(ROT_KEY) ]; then \
+		openssl genrsa 2048 > $@ 2>/dev/null; \
+	fi
+
+    $(ROTPK_HASH): $(ROT_KEY)
+	@echo "  OPENSSL $@"
+	$(Q)openssl rsa -in $< -pubout -outform DER 2>/dev/null |\
+	openssl dgst -sha256 -binary > $@ 2>/dev/null
+
+endif #MBEDTLS_DIR
+
+PLAT_INCLUDES		+=	-Iinclude/common/tbbr
+
+# Generic files for authentication framework
+TBBR_SOURCES		+=	drivers/auth/auth_mod.c		\
+				drivers/auth/crypto_mod.c	\
+				drivers/auth/img_parser_mod.c	\
+				plat/common/tbbr/plat_tbbr.c	\
+				${PLAT_TBBR_SOURCES}
+
+# If CAAM_INTEG is not defined (would be scenario with MBED TLS)
+# include mbedtls_crypto
+ifeq (${CAAM_INTEG},0)
+    include drivers/auth/mbedtls/mbedtls_crypto.mk
+else
+    include $(PLAT_DRIVERS_PATH)/crypto/caam/src/auth/auth.mk
+    TBBR_SOURCES	+= ${AUTH_SOURCES}
+endif
diff --git a/plat/nxp/common/tbbr/x509_tbbr.c b/plat/nxp/common/tbbr/x509_tbbr.c
new file mode 100644
index 0000000..ec87674
--- /dev/null
+++ b/plat/nxp/common/tbbr/x509_tbbr.c
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <lib/cassert.h>
+#include <sfp.h>
+#include <tools_share/tbbr_oid.h>
+
+#include <plat/common/platform.h>
+#include "plat_common.h"
+
+extern char nxp_rotpk_hash[], nxp_rotpk_hash_end[];
+
+int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
+			unsigned int *flags)
+{
+	*key_ptr = nxp_rotpk_hash;
+	*key_len = nxp_rotpk_hash_end - nxp_rotpk_hash;
+	*flags = ROTPK_IS_HASH;
+
+	return 0;
+}
+
+int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
+{
+	const char *oid;
+	uint32_t uid_num;
+	uint32_t val = 0U;
+
+	assert(cookie != NULL);
+	assert(nv_ctr != NULL);
+
+	oid = (const char *)cookie;
+	if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		uid_num = 3U;
+	} else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		uid_num = 4U;
+	} else {
+		return 1;
+	}
+
+	val = sfp_read_oem_uid(uid_num);
+
+	INFO("SFP Value read is %x from UID %d\n", val, uid_num);
+	if (val == 0U) {
+		*nv_ctr = 0U;
+	} else {
+		*nv_ctr = (32U - __builtin_clz(val));
+	}
+
+	INFO("NV Counter value for UID %d is %d\n", uid_num, *nv_ctr);
+	return 0;
+
+}
+
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	const char *oid;
+	uint32_t uid_num, sfp_val;
+
+	assert(cookie != NULL);
+
+	/* Counter values upto 32 are supported */
+	if (nv_ctr > 32U) {
+		return 1;
+	}
+
+	oid = (const char *)cookie;
+	if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		uid_num = 3U;
+	} else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		uid_num = 4U;
+	} else {
+		return 1;
+	}
+	sfp_val = (1U << (nv_ctr - 1));
+
+	if (sfp_write_oem_uid(uid_num, sfp_val) == 1) {
+		/* Enable POVDD on board */
+		if (board_enable_povdd()) {
+			sfp_program_fuses();
+		}
+
+		/* Disable POVDD on board */
+		board_disable_povdd();
+	} else {
+		ERROR("Invalid OEM UID sent.\n");
+		return 1;
+	}
+
+	return 0;
+}
+
+int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
+{
+	return get_mbedtls_heap_helper(heap_addr, heap_size);
+}
diff --git a/plat/nxp/common/warm_reset/plat_warm_reset.c b/plat/nxp/common/warm_reset/plat_warm_reset.c
new file mode 100644
index 0000000..966a73c
--- /dev/null
+++ b/plat/nxp/common/warm_reset/plat_warm_reset.c
@@ -0,0 +1,121 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <errno.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#ifndef NXP_COINED_BB
+#include <flash_info.h>
+#include <fspi.h>
+#include <fspi_api.h>
+#endif
+#include <lib/mmio.h>
+#include <lib/psci/psci.h>
+#ifdef NXP_COINED_BB
+#include <snvs.h>
+#endif
+
+#include <plat_nv_storage.h>
+#include "plat_warm_rst.h"
+#include "platform_def.h"
+
+#if defined(IMAGE_BL2)
+
+uint32_t is_warm_boot(void)
+{
+	uint32_t ret = mmio_read_32(NXP_RESET_ADDR + RST_RSTRQSR1_OFFSET)
+				& ~(RSTRQSR1_SWRR);
+
+	const nv_app_data_t *nv_app_data = get_nv_data();
+
+	if (ret == 0U) {
+		INFO("Not a SW(Warm) triggered reset.\n");
+		return 0U;
+	}
+
+	ret = (nv_app_data->warm_rst_flag == WARM_BOOT_SUCCESS) ? 1 : 0;
+
+	if (ret != 0U) {
+		INFO("Warm Reset was triggered..\n");
+	} else {
+		INFO("Warm Reset was not triggered..\n");
+	}
+
+	return ret;
+}
+
+#endif
+
+#if defined(IMAGE_BL31)
+int prep_n_execute_warm_reset(void)
+{
+#ifdef NXP_COINED_BB
+#if !TRUSTED_BOARD_BOOT
+	snvs_disable_zeroize_lp_gpr();
+#endif
+#else
+	int ret;
+	uint8_t warm_reset = WARM_BOOT_SUCCESS;
+
+	ret = fspi_init(NXP_FLEXSPI_ADDR, NXP_FLEXSPI_FLASH_ADDR);
+
+	if (ret != 0) {
+		ERROR("Failed to initialized driver flexspi-nor.\n");
+		ERROR("exiting warm-reset request.\n");
+		return PSCI_E_INTERN_FAIL;
+	}
+
+	/* Sector starting from NV_STORAGE_BASE_ADDR is already
+	 * erased for writing.
+	 */
+
+#if (ERLY_WRM_RST_FLG_FLSH_UPDT)
+	ret = xspi_write((uint32_t)NV_STORAGE_BASE_ADDR,
+			 &warm_reset,
+			 sizeof(warm_reset));
+#else
+	/* Preparation for writing the Warm reset flag. */
+	ret = xspi_wren((uint32_t)NV_STORAGE_BASE_ADDR);
+
+	/* IP Control Register0 - SF Address to be read */
+	fspi_out32((NXP_FLEXSPI_ADDR + FSPI_IPCR0),
+		   (uint32_t) NV_STORAGE_BASE_ADDR);
+
+	while ((fspi_in32(NXP_FLEXSPI_ADDR + FSPI_INTR) &
+		FSPI_INTR_IPTXWE_MASK) == 0) {
+		;
+	}
+	/* Write TX FIFO Data Register */
+	fspi_out32(NXP_FLEXSPI_ADDR + FSPI_TFDR, (uint32_t) warm_reset);
+
+	fspi_out32(NXP_FLEXSPI_ADDR + FSPI_INTR, FSPI_INTR_IPTXWE);
+
+	/* IP Control Register1 - SEQID_WRITE operation, Size = 1 Byte */
+	fspi_out32(NXP_FLEXSPI_ADDR + FSPI_IPCR1,
+		   (uint32_t)(FSPI_WRITE_SEQ_ID << FSPI_IPCR1_ISEQID_SHIFT) |
+		   (uint16_t) sizeof(warm_reset));
+
+	/* Trigger XSPI-IP-Write cmd only if:
+	 *  - Putting DDR in-self refresh mode is successfully.
+	 *    to complete the writing of the warm-reset flag
+	 *    to flash.
+	 *
+	 * This code is as part of assembly.
+	 */
+#endif
+#endif
+	INFO("Doing DDR Self refresh.\n");
+	_soc_sys_warm_reset();
+
+	/* Expected behaviour is to do the power cycle */
+	while (1 != 0)
+		;
+
+	return -1;
+}
+#endif
diff --git a/plat/nxp/common/warm_reset/plat_warm_rst.h b/plat/nxp/common/warm_reset/plat_warm_rst.h
new file mode 100644
index 0000000..e0c39c5
--- /dev/null
+++ b/plat/nxp/common/warm_reset/plat_warm_rst.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_WARM_RST_H
+#define PLAT_WARM_RST_H
+
+#ifndef NXP_COINED_BB
+#define ERLY_WRM_RST_FLG_FLSH_UPDT	0
+#endif
+
+#ifndef __ASSEMBLER__
+
+#if defined(IMAGE_BL2)
+uint32_t is_warm_boot(void);
+#endif
+
+#if defined(IMAGE_BL31)
+int prep_n_execute_warm_reset(void);
+int _soc_sys_warm_reset(void);
+#endif
+
+#endif	/* __ASSEMBLER__ */
+
+#endif	/* PLAT_WARM_RST_H */
diff --git a/plat/nxp/common/warm_reset/warm_reset.mk b/plat/nxp/common/warm_reset/warm_reset.mk
new file mode 100644
index 0000000..236004f
--- /dev/null
+++ b/plat/nxp/common/warm_reset/warm_reset.mk
@@ -0,0 +1,20 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#-----------------------------------------------------------------------------
+ifeq (${WARM_RST_ADDED},)
+
+WARM_RST_ADDED	:=	1
+NXP_NV_SW_MAINT_LAST_EXEC_DATA := yes
+
+$(eval $(call add_define,NXP_WARM_BOOT))
+
+
+WARM_RST_INCLUDES	+=	-I${PLAT_COMMON_PATH}/warm_reset
+WARM_RST_BL31_SOURCES	+=	${PLAT_SOC_PATH}/$(ARCH)/${SOC}_warm_rst.S
+
+WARM_RST_BL_COMM_SOURCES	+=	${PLAT_COMMON_PATH}/warm_reset/plat_warm_reset.c
+
+endif
diff --git a/plat/nxp/soc-ls1028a/aarch64/ls1028a.S b/plat/nxp/soc-ls1028a/aarch64/ls1028a.S
new file mode 100644
index 0000000..404c39e
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/aarch64/ls1028a.S
@@ -0,0 +1,1387 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+	.section .text, "ax"
+
+#include <asm_macros.S>
+
+#include <lib/psci/psci.h>
+#include <nxp_timer.h>
+#include <plat_gic.h>
+#include <pmu.h>
+
+#include <bl31_data.h>
+#include <plat_psci.h>
+#include <platform_def.h>
+
+	.global soc_init_lowlevel
+	.global soc_init_percpu
+	.global _set_platform_security
+	.global _soc_set_start_addr
+
+	.global _soc_core_release
+	.global _soc_ck_disabled
+	.global _soc_core_restart
+	.global _soc_core_prep_off
+	.global _soc_core_entr_off
+	.global _soc_core_exit_off
+	.global _soc_sys_reset
+	.global _soc_sys_off
+	.global _soc_core_prep_stdby
+	.global _soc_core_entr_stdby
+	.global _soc_core_exit_stdby
+	.global _soc_core_prep_pwrdn
+	.global _soc_core_entr_pwrdn
+	.global _soc_core_exit_pwrdn
+	.global _soc_clstr_prep_stdby
+	.global _soc_clstr_exit_stdby
+	.global _soc_clstr_prep_pwrdn
+	.global _soc_clstr_exit_pwrdn
+	.global _soc_sys_prep_stdby
+	.global _soc_sys_exit_stdby
+	.global _soc_sys_prep_pwrdn
+	.global _soc_sys_pwrdn_wfi
+	.global _soc_sys_exit_pwrdn
+
+	.equ TZPCDECPROT_0_SET_BASE, 0x02200804
+	.equ TZPCDECPROT_1_SET_BASE, 0x02200810
+	.equ TZPCDECPROT_2_SET_BASE, 0x0220081C
+
+	.equ TZASC_REGION_ATTRIBUTES_0_0, 0x01100110
+
+/*
+ * This function initialize the soc.
+ * in: void
+ * out: void
+ * uses x0 - x11
+ */
+func soc_init_lowlevel
+	/*
+	 * Called from C, so save the non-volatile regs
+	 * save these as pairs of registers to maintain the
+	 * required 16-byte alignment on the stack
+	 */
+	stp	x4,  x5,  [sp, #-16]!
+	stp	x6,  x7,  [sp, #-16]!
+	stp	x8,  x9,  [sp, #-16]!
+	stp	x10, x11, [sp, #-16]!
+	stp	x12, x13, [sp, #-16]!
+	stp	x18, x30, [sp, #-16]!
+
+	/*
+	 * Make sure the personality has been established by releasing cores
+	 * that are marked "to-be-disabled" from reset
+	 */
+	bl	release_disabled  /* 0-8 */
+
+	/* Set SCRATCHRW7 to 0x0 */
+	ldr	x0, =DCFG_SCRATCHRW7_OFFSET
+	mov	x1, xzr
+	bl	_write_reg_dcfg
+
+	/* Restore the aarch32/64 non-volatile registers */
+	ldp	x18, x30, [sp], #16
+	ldp	x12, x13, [sp], #16
+	ldp	x10, x11, [sp], #16
+	ldp	x8,  x9,  [sp], #16
+	ldp	x6,  x7,  [sp], #16
+	ldp	x4,  x5,  [sp], #16
+	ret
+endfunc soc_init_lowlevel
+
+/*
+ * void soc_init_percpu(void)
+ *
+ * This function performs any soc-specific initialization that is needed on
+ * a per-core basis
+ * in:  none
+ * out: none
+ * uses x0 - x3
+ */
+func soc_init_percpu
+	stp	x4,  x30,  [sp, #-16]!
+
+	bl	plat_my_core_mask
+	mov	x2, x0
+
+	/* x2 = core mask */
+
+	/* see if this core is marked for prefetch disable */
+	mov	x0, #PREFETCH_DIS_OFFSET
+	bl	_get_global_data  /* 0-1 */
+	tst	x0, x2
+	b.eq	1f
+	bl	_disable_ldstr_pfetch_A72  /* 0 */
+1:
+	mov	x0, #NXP_PMU_ADDR
+	bl	enable_timer_base_to_cluster
+
+	ldp	x4,  x30,  [sp], #16
+	ret
+endfunc soc_init_percpu
+
+/*
+ * This function determines if a core is disabled via COREDISABLEDSR
+ * in:  w0  = core_mask_lsb
+ * out: w0  = 0, core not disabled
+ *      w0 != 0, core disabled
+ * uses x0, x1
+ */
+func _soc_ck_disabled
+	/* get base addr of dcfg block */
+	ldr	x1, =NXP_DCFG_ADDR
+
+	/* read COREDISABLEDSR */
+	ldr	w1, [x1, #DCFG_COREDISABLEDSR_OFFSET]
+
+	/* test core bit */
+	and	w0, w1, w0
+
+	ret
+endfunc _soc_ck_disabled
+
+/*
+ * This function sets the security mechanisms in the SoC to implement the
+ * Platform Security Policy
+ */
+func _set_platform_security
+	mov	x3, x30
+
+#if (!SUPPRESS_TZC)
+	/* initialize the tzpc */
+	bl	init_tzpc
+#endif
+
+#if (!SUPPRESS_SEC)
+	/* initialize secmon */
+	bl	initSecMon
+#endif
+
+	mov	x30, x3
+	ret
+endfunc _set_platform_security
+
+/*
+ * Part of CPU_ON
+ *
+ * This function releases a secondary core from reset
+ * in:   x0 = core_mask_lsb
+ * out:  none
+ * uses: x0 - x3
+ */
+_soc_core_release:
+	mov	x3, x30
+
+	/*
+	 * Write to CORE_HOLD to tell the bootrom that we want this core
+	 * to run
+	 */
+	ldr	x1, =NXP_SEC_REGFILE_ADDR
+	str	w0, [x1, #CORE_HOLD_OFFSET]
+
+	/* Read-modify-write BRRL to release core */
+	mov	x1, #NXP_RESET_ADDR
+	ldr	w2, [x1, #BRR_OFFSET]
+	orr	w2, w2, w0
+	str	w2, [x1, #BRR_OFFSET]
+	dsb	sy
+	isb
+
+	/* Send event */
+	sev
+	isb
+
+	mov	x30, x3
+	ret
+
+/*
+ * This function writes a 64-bit address to bootlocptrh/l
+ * in:  x0, 64-bit address to write to BOOTLOCPTRL/H
+ * uses x0, x1, x2
+ */
+func _soc_set_start_addr
+	/* Get the 64-bit base address of the dcfg block */
+	ldr	x2, =NXP_DCFG_ADDR
+
+	/* Write the 32-bit BOOTLOCPTRL register */
+	mov	x1, x0
+	str	w1, [x2, #DCFG_BOOTLOCPTRL_OFFSET]
+
+	/* Write the 32-bit BOOTLOCPTRH register */
+	lsr	x1, x0, #32
+	str	w1, [x2, #DCFG_BOOTLOCPTRH_OFFSET]
+	ret
+endfunc _soc_set_start_addr
+
+/*
+ * Part of CPU_ON
+ *
+ * This function restarts a core shutdown via _soc_core_entr_off
+ * in:  x0 = core mask lsb (of the target cpu)
+ * out: x0 == 0, on success
+ *      x0 != 0, on failure
+ * uses x0 - x6
+ */
+_soc_core_restart:
+	mov	x6, x30
+	mov	x4, x0
+
+	/* pgm GICD_CTLR - enable secure grp0  */
+	mov	x5, #NXP_GICD_ADDR
+	ldr	w2, [x5, #GICD_CTLR_OFFSET]
+	orr	w2, w2, #GICD_CTLR_EN_GRP_0
+	str	w2, [x5, #GICD_CTLR_OFFSET]
+	dsb	sy
+	isb
+
+	/* Poll on RWP til write completes */
+4:
+	ldr	w2, [x5, #GICD_CTLR_OFFSET]
+	tst	w2, #GICD_CTLR_RWP
+	b.ne	4b
+
+	/*
+	 * x4 = core mask lsb
+	 * x5 = gicd base addr
+	 */
+
+	mov	x0, x4
+	bl	get_mpidr_value
+
+	/* Generate target list bit */
+	and	x1, x0, #MPIDR_AFFINITY0_MASK
+	mov	x2, #1
+	lsl	x2, x2, x1
+
+	/* Get the affinity1 field */
+	and	x1, x0, #MPIDR_AFFINITY1_MASK
+	lsl	x1, x1, #8
+	orr	x2, x2, x1
+
+	/* Insert the INTID for SGI15 */
+	orr	x2, x2, #ICC_SGI0R_EL1_INTID
+
+	/* Fire the SGI */
+	msr	ICC_SGI0R_EL1, x2
+	dsb	sy
+	isb
+
+	/* Load '0' on success */
+	mov	x0, xzr
+
+	mov	x30, x6
+	ret
+
+/*
+ * Part of CPU_OFF
+ *
+ * This function programs SoC & GIC registers in preparation for shutting down
+ * the core
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0 - x7
+ */
+_soc_core_prep_off:
+	mov	x8, x30
+	mov	x7, x0
+
+	/* x7 = core mask lsb */
+
+	mrs	x1, CPUECTLR_EL1
+
+	/* Set smp and disable L2 snoops in cpuectlr */
+	orr	x1, x1, #CPUECTLR_SMPEN_EN
+	orr	x1, x1, #CPUECTLR_DISABLE_TWALK_PREFETCH
+	bic	x1, x1, #CPUECTLR_INS_PREFETCH_MASK
+	bic	x1, x1, #CPUECTLR_DAT_PREFETCH_MASK
+
+	/* Set retention control in cpuectlr */
+	bic	x1, x1, #CPUECTLR_TIMER_MASK
+	orr	x1, x1, #CPUECTLR_TIMER_2TICKS
+	msr	CPUECTLR_EL1, x1
+
+	/* Get redistributor rd base addr for this core */
+	mov	x0, x7
+	bl	get_gic_rd_base
+	mov	x6, x0
+
+	/* Get redistributor sgi base addr for this core */
+	mov	x0, x7
+	bl	get_gic_sgi_base
+	mov	x5, x0
+
+	/*
+	 * x5 = gicr sgi base addr
+	 * x6 = gicr rd  base addr
+	 * x7 = core mask lsb
+	 */
+
+	/* Disable SGI 15 at redistributor - GICR_ICENABLER0 */
+	mov	w3, #GICR_ICENABLER0_SGI15
+	str	w3, [x5, #GICR_ICENABLER0_OFFSET]
+2:
+	/* Poll on rwp bit in GICR_CTLR */
+	ldr	w4, [x6, #GICR_CTLR_OFFSET]
+	tst	w4, #GICR_CTLR_RWP
+	b.ne	2b
+
+	/* Disable GRP1 interrupts at cpu interface */
+	msr	ICC_IGRPEN1_EL3, xzr
+
+	/* Disable GRP0 ints at cpu interface */
+	msr	ICC_IGRPEN0_EL1, xzr
+
+	/* Program the redistributor - poll on GICR_CTLR.RWP as needed */
+
+	/* Define SGI 15 as Grp0 - GICR_IGROUPR0 */
+	ldr	w4, [x5, #GICR_IGROUPR0_OFFSET]
+	bic	w4, w4, #GICR_IGROUPR0_SGI15
+	str	w4, [x5, #GICR_IGROUPR0_OFFSET]
+
+	/* Define SGI 15 as Grp0 - GICR_IGRPMODR0 */
+	ldr	w3, [x5, #GICR_IGRPMODR0_OFFSET]
+	bic	w3, w3, #GICR_IGRPMODR0_SGI15
+	str	w3, [x5, #GICR_IGRPMODR0_OFFSET]
+
+	/* Set priority of SGI 15 to highest (0x0) - GICR_IPRIORITYR3 */
+	ldr	w4, [x5, #GICR_IPRIORITYR3_OFFSET]
+	bic	w4, w4, #GICR_IPRIORITYR3_SGI15_MASK
+	str	w4, [x5, #GICR_IPRIORITYR3_OFFSET]
+
+	/* Enable SGI 15 at redistributor - GICR_ISENABLER0 */
+	mov	w3, #GICR_ISENABLER0_SGI15
+	str	w3, [x5, #GICR_ISENABLER0_OFFSET]
+	dsb	sy
+	isb
+3:
+	/* Poll on rwp bit in GICR_CTLR */
+	ldr	w4, [x6, #GICR_CTLR_OFFSET]
+	tst	w4, #GICR_CTLR_RWP
+	b.ne	3b
+
+	/* Quiesce the debug interfaces */
+	mrs	x3, osdlr_el1
+	orr	x3, x3, #OSDLR_EL1_DLK_LOCK
+	msr	osdlr_el1, x3
+	isb
+
+	/* Enable grp0 ints */
+	mov	x3, #ICC_IGRPEN0_EL1_EN
+	msr	ICC_IGRPEN0_EL1, x3
+
+	/*
+	 * x5 = gicr sgi base addr
+	 * x6 = gicr rd  base addr
+	 * x7 = core mask lsb
+	 */
+
+	/* Clear any pending interrupts */
+	mvn	w1, wzr
+	str	w1, [x5, #GICR_ICPENDR0_OFFSET]
+
+	/* Make sure system counter is enabled */
+	ldr	x3, =NXP_TIMER_ADDR
+	ldr	w0, [x3, #SYS_COUNTER_CNTCR_OFFSET]
+	tst	w0, #SYS_COUNTER_CNTCR_EN
+	b.ne	4f
+	orr	w0, w0, #SYS_COUNTER_CNTCR_EN
+	str	w0, [x3, #SYS_COUNTER_CNTCR_OFFSET]
+4:
+	/* Enable the core timer and mask timer interrupt */
+	mov	x1, #CNTP_CTL_EL0_EN
+	orr	x1, x1, #CNTP_CTL_EL0_IMASK
+	msr	cntp_ctl_el0, x1
+
+	isb
+	mov	x30, x8
+	ret
+
+/*
+ * Part of CPU_OFF
+ *
+ * This function performs the final steps to shutdown the core
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0 - x5
+ */
+_soc_core_entr_off:
+	mov	x5, x30
+	mov	x4, x0
+
+	/* x4 = core mask */
+1:
+	/* Enter low-power state by executing wfi */
+	wfi
+
+	/* See if SGI15 woke us up */
+	mrs	x2, ICC_IAR0_EL1
+	mov	x3, #ICC_IAR0_EL1_SGI15
+	cmp	x2, x3
+	b.ne	1b
+
+	/* Deactivate the int */
+	msr	ICC_EOIR0_EL1, x2
+
+	/* x4 = core mask */
+2:
+	/* Check if core has been turned on */
+	mov	x0, x4
+	bl	_getCoreState
+
+	/* x0 = core state */
+
+	cmp	x0, #CORE_WAKEUP
+	b.ne	1b
+
+	/* If we get here, then we have exited the wfi */
+	mov	x30, x5
+	ret
+
+/*
+ * Part of CPU_OFF
+ *
+ * This function starts the process of starting a core back up
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6
+ */
+_soc_core_exit_off:
+	mov	x6, x30
+	mov	x5, x0
+
+	/* Disable forwarding of GRP0 ints at cpu interface */
+	msr	ICC_IGRPEN0_EL1, xzr
+
+	/* Get redistributor sgi base addr for this core */
+	mov	x0, x5
+	bl	get_gic_sgi_base
+	mov	x4, x0
+
+	/* x4 = gicr sgi base addr */
+	/* x5 = core mask */
+
+	/* Disable SGI 15 at redistributor - GICR_ICENABLER0 */
+	mov	w1, #GICR_ICENABLER0_SGI15
+	str	w1, [x4, #GICR_ICENABLER0_OFFSET]
+
+	/* Get redistributor rd base addr for this core */
+	mov	x0, x5
+	bl	get_gic_rd_base
+	mov	x4, x0
+
+	/* x4 = gicr rd  base addr */
+2:
+	/* Poll on rwp bit in GICR_CTLR */
+	ldr	w2, [x4, #GICR_CTLR_OFFSET]
+	tst	w2, #GICR_CTLR_RWP
+	b.ne	2b
+
+	/* x4 = gicr rd  base addr */
+
+	/* Unlock the debug interfaces */
+	mrs	x3, osdlr_el1
+	bic	x3, x3, #OSDLR_EL1_DLK_LOCK
+	msr	osdlr_el1, x3
+	isb
+
+	dsb	sy
+	isb
+	mov	x30, x6
+	ret
+
+/*
+ * This function requests a reset of the entire SOC
+ * in:  none
+ * out: none
+ * uses: x0, x1, x2, x3, x4, x5, x6
+ */
+_soc_sys_reset:
+	mov	x3, x30
+
+	/* Make sure the mask is cleared in the reset request mask register */
+	mov	x0, #RST_RSTRQMR1_OFFSET
+	mov	w1, wzr
+	bl	_write_reg_reset
+
+	/* Set the reset request */
+	mov	x4, #RST_RSTCR_OFFSET
+	mov	x0, x4
+	mov	w1, #RSTCR_RESET_REQ
+	bl	_write_reg_reset
+
+	/* x4 = RST_RSTCR_OFFSET */
+
+	/*
+	 * Just in case this address range is mapped as cacheable,
+	 * flush the write out of the dcaches
+	 */
+	mov	x2, #NXP_RESET_ADDR
+	add	x2, x2, x4
+	dc	cvac, x2
+	dsb	st
+	isb
+
+	/* This function does not return */
+1:
+	wfi
+	b	1b
+
+/*
+ * Part of SYSTEM_OFF
+ *
+ * This function turns off the SoC clocks
+ * Note: this function is not intended to return, and the only allowable
+ *       recovery is POR
+ * in:  none
+ * out: none
+ * uses x0, x1, x2, x3
+ */
+_soc_sys_off:
+	/*
+	 * Disable sec, spi and flexspi
+	 * TBD - Check if eNETC needs to be disabled
+	 */
+	ldr	x2, =NXP_DCFG_ADDR
+	ldr	x0, =DCFG_DEVDISR1_OFFSET
+	ldr	w1, =DCFG_DEVDISR1_SEC
+	str	w1, [x2, x0]
+	ldr	x0, =DCFG_DEVDISR4_OFFSET
+	ldr	w1, =DCFG_DEVDISR4_SPI_QSPI
+	str	w1, [x2, x0]
+
+	/* Set TPMWAKEMR0 */
+	ldr	x0, =TPMWAKEMR0_ADDR
+	mov	w1, #0x1
+	str	w1, [x0]
+
+	/* Disable icache, dcache, mmu @ EL1 */
+	mov	x1, #SCTLR_I_C_M_MASK
+	mrs	x0, sctlr_el1
+	bic	x0, x0, x1
+	msr	sctlr_el1, x0
+
+	/* Disable L2 prefetches */
+	mrs	x0, CPUECTLR_EL1
+	orr	x0, x0, #CPUECTLR_SMPEN_EN
+	bic	x0, x0, #CPUECTLR_TIMER_MASK
+	orr	x0, x0, #CPUECTLR_TIMER_2TICKS
+	msr	CPUECTLR_EL1, x0
+	dsb	sy
+	isb
+
+	/* Disable CCI snoop domain */
+	ldr	x0, =NXP_CCI_ADDR
+	mov	w1, #0x1
+	str	w1, [x0]
+
+	bl	get_pmu_idle_core_mask
+
+	/* x3 = pmu base addr */
+	mov	x3, #NXP_PMU_ADDR
+4:
+	ldr	w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp	w1, w0
+	b.ne	4b
+
+	bl	get_pmu_idle_cluster_mask
+	mov	x3, #NXP_PMU_ADDR
+	str	w0, [x3, #PMU_CLAINACTSETR_OFFSET]
+
+	bl	get_pmu_idle_core_mask
+	mov	x3, #NXP_PMU_ADDR
+1:
+	ldr	w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp	w1, w0
+	b.ne	1b
+
+	bl	get_pmu_flush_cluster_mask
+	mov	x3, #NXP_PMU_ADDR
+	str	w0, [x3, #PMU_CLL2FLUSHSETR_OFFSET]
+2:
+	ldr	w1, [x3, #PMU_CLL2FLUSHSR_OFFSET]
+	cmp	w1, w0
+	b.ne	2b
+
+	str	w0, [x3, #PMU_CLSL2FLUSHCLRR_OFFSET]
+
+	str	w0, [x3, #PMU_CLSINACTSETR_OFFSET]
+
+	mov	x2, #DAIF_SET_MASK
+	mrs	x1, spsr_el1
+	orr	x1, x1, x2
+	msr	spsr_el1, x1
+
+	mrs	x1, spsr_el2
+	orr	x1, x1, x2
+	msr	spsr_el2, x1
+
+	/* Force the debug interface to be quiescent */
+	mrs	x0, osdlr_el1
+	orr	x0, x0, #0x1
+	msr	osdlr_el1, x0
+
+	/* Invalidate all TLB entries at all 3 exception levels */
+	tlbi	alle1
+	tlbi	alle2
+	tlbi	alle3
+
+	/* x3 = pmu base addr */
+
+	/* Request lpm20 */
+	ldr	x0, =PMU_POWMGTCSR_OFFSET
+	ldr	w1, =PMU_POWMGTCSR_VAL
+	str	w1, [x3, x0]
+	isb
+	dsb	sy
+5:
+	wfe
+	b.eq	5b
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+_soc_core_prep_stdby:
+	/* Clear CPUECTLR_EL1[2:0] */
+	mrs	x1, CPUECTLR_EL1
+	bic	x1, x1, #CPUECTLR_TIMER_MASK
+	msr	CPUECTLR_EL1, x1
+
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function puts the calling core into standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0
+ */
+_soc_core_entr_stdby:
+	/* X0 = core mask lsb */
+	dsb	sy
+	isb
+	wfi
+
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+_soc_core_exit_stdby:
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2
+ */
+_soc_core_prep_pwrdn:
+	/* Make sure system counter is enabled */
+	ldr	x2, =NXP_TIMER_ADDR
+	ldr	w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+	tst	w0, #SYS_COUNTER_CNTCR_EN
+	b.ne	1f
+	orr	w0, w0, #SYS_COUNTER_CNTCR_EN
+	str	w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+1:
+	/*
+	 * Enable dynamic retention control (CPUECTLR[2:0])
+	 * Set the SMPEN bit (CPUECTLR[6])
+	 */
+	mrs	x1, CPUECTLR_EL1
+	bic	x1, x1, #CPUECTLR_RET_MASK
+	orr	x1, x1, #CPUECTLR_TIMER_2TICKS
+	orr	x1, x1, #CPUECTLR_SMPEN_EN
+	msr	CPUECTLR_EL1, x1
+
+	isb
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function puts the calling core into a power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0
+ */
+_soc_core_entr_pwrdn:
+	/* X0 = core mask lsb */
+	dsb	sy
+	isb
+	wfi
+
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+_soc_core_exit_pwrdn:
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+_soc_clstr_prep_stdby:
+	/* Clear CPUECTLR_EL1[2:0] */
+	mrs	x1, CPUECTLR_EL1
+	bic	x1, x1, #CPUECTLR_TIMER_MASK
+	msr	CPUECTLR_EL1, x1
+
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+_soc_clstr_exit_stdby:
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2
+ */
+_soc_clstr_prep_pwrdn:
+	/* Make sure system counter is enabled */
+	ldr	x2, =NXP_TIMER_ADDR
+	ldr	w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+	tst	w0, #SYS_COUNTER_CNTCR_EN
+	b.ne	1f
+	orr	w0, w0, #SYS_COUNTER_CNTCR_EN
+	str	w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+1:
+	/*
+	 * Enable dynamic retention control (CPUECTLR[2:0])
+	 * Set the SMPEN bit (CPUECTLR[6])
+	 */
+	mrs	x1, CPUECTLR_EL1
+	bic	x1, x1, #CPUECTLR_RET_MASK
+	orr	x1, x1, #CPUECTLR_TIMER_2TICKS
+	orr	x1, x1, #CPUECTLR_SMPEN_EN
+	msr	CPUECTLR_EL1, x1
+
+	isb
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+_soc_clstr_exit_pwrdn:
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+_soc_sys_prep_stdby:
+	/* Clear CPUECTLR_EL1[2:0] */
+	mrs	x1, CPUECTLR_EL1
+	bic	x1, x1, #CPUECTLR_TIMER_MASK
+	msr	CPUECTLR_EL1, x1
+
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+_soc_sys_exit_stdby:
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs SoC-specific programming prior to
+ * suspend-to-power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2, x3, x4
+ */
+_soc_sys_prep_pwrdn:
+	/* Set retention control */
+	mrs	x0, CPUECTLR_EL1
+	bic	x0, x0, #CPUECTLR_TIMER_MASK
+	orr	x0, x0, #CPUECTLR_TIMER_2TICKS
+	orr	x0, x0, #CPUECTLR_SMPEN_EN
+	msr	CPUECTLR_EL1, x0
+	dsb	sy
+	isb
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function puts the calling core, and potentially the soc, into a
+ * low-power state
+ * in:  x0 = core mask lsb
+ * out: x0 = 0, success
+ *      x0 < 0, failure
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, x13, x14, x15,
+ *      x16, x17, x18
+ */
+_soc_sys_pwrdn_wfi:
+	mov	x18, x30
+
+	mov	x3, #NXP_PMU_ADDR
+
+	/* x3 = pmu base addr */
+
+	/* Backup epu registers to stack */
+	ldr	x2, =NXP_EPU_ADDR
+	ldr	w4, [x2, #EPU_EPIMCR10_OFFSET]
+	ldr	w5, [x2, #EPU_EPCCR10_OFFSET]
+	ldr	w6, [x2, #EPU_EPCTR10_OFFSET]
+	ldr	w7, [x2, #EPU_EPGCR_OFFSET]
+	stp	x4,  x5,  [sp, #-16]!
+	stp	x6,  x7,  [sp, #-16]!
+
+	/*
+	 * x2 = epu base addr
+	 * x3 = pmu base addr
+	 */
+
+	/* Set up EPU event to receive the wake signal from PMU */
+	mov	w4, #EPU_EPIMCR10_VAL
+	mov	w5, #EPU_EPCCR10_VAL
+	mov	w6, #EPU_EPCTR10_VAL
+	mov	w7, #EPU_EPGCR_VAL
+	str	w4, [x2, #EPU_EPIMCR10_OFFSET]
+	str	w5, [x2, #EPU_EPCCR10_OFFSET]
+	str	w6, [x2, #EPU_EPCTR10_OFFSET]
+	str	w7, [x2, #EPU_EPGCR_OFFSET]
+
+	ldr	x2, =NXP_GICD_ADDR
+
+	/*
+	 * x2 = gicd base addr
+	 * x3 = pmu base addr
+	 */
+
+	/* Backup flextimer/mmc/usb interrupt router */
+	ldr	x0, =GICD_IROUTER60_OFFSET
+	ldr	x1, =GICD_IROUTER76_OFFSET
+	ldr	w4, [x2, x0]
+	ldr	w5, [x2, x1]
+	ldr	x0, =GICD_IROUTER112_OFFSET
+	ldr	x1, =GICD_IROUTER113_OFFSET
+	ldr	w6, [x2, x0]
+	ldr	w7, [x2, x1]
+	stp	x4,  x5,  [sp, #-16]!
+	stp	x6,  x7,  [sp, #-16]!
+
+	/*
+	 * x2 = gicd base addr
+	 * x3 = pmu base addr
+	 * x0 = GICD_IROUTER112_OFFSET
+	 * x1 = GICD_IROUTER113_OFFSET
+	 */
+
+	/* Re-route interrupt to cluster 1 */
+	ldr	w4, =GICD_IROUTER_VALUE
+	str	w4, [x2, x0]
+	str	w4, [x2, x1]
+	ldr	x0, =GICD_IROUTER60_OFFSET
+	ldr	x1, =GICD_IROUTER76_OFFSET
+	str	w4, [x2, x0]
+	str	w4, [x2, x1]
+	dsb	sy
+	isb
+
+	/* x3 = pmu base addr */
+
+	/* Disable sec, Check for eNETC, spi and qspi */
+	ldr	x2, =NXP_DCFG_ADDR
+	ldr	x0, =DCFG_DEVDISR1_OFFSET
+	ldr	w1, =DCFG_DEVDISR1_SEC
+	str	w1, [x2, x0]
+
+	ldr	x0, =DCFG_DEVDISR4_OFFSET
+	ldr	w1, =DCFG_DEVDISR4_SPI_QSPI
+	str	w1, [x2, x0]
+
+	/* x3 = pmu base addr */
+
+	/* Set TPMWAKEMR0 */
+	ldr	x0, =TPMWAKEMR0_ADDR
+	mov	w1, #0x1
+	str	w1, [x0]
+
+	/* Disable CCI snoop domain */
+	ldr	x0, =NXP_CCI_ADDR
+	mov	w1, #0x1
+	str	w1, [x0]
+
+	/* Setup retention control */
+	mrs	x0, CPUECTLR_EL1
+	orr	x0, x0, #CPUECTLR_SMPEN_EN
+	orr	x0, x0, #CPUECTLR_TIMER_2TICKS
+	msr	CPUECTLR_EL1, x0
+	dsb	sy
+	isb
+
+	bl	get_pmu_idle_core_mask
+	mov	x3, #NXP_PMU_ADDR
+8:
+	ldr	w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp	w1, w0
+	b.ne	8b
+
+	/* x3 = NXP_PMU_ADDR */
+	/* 1 cluster SoC */
+
+	bl	get_pmu_idle_cluster_mask
+	mov	x3, #NXP_PMU_ADDR
+
+	str	w0, [x3, #PMU_CLAINACTSETR_OFFSET]
+
+	bl	get_pmu_idle_core_mask
+	/* x3 = NXP_PMU_ADDR */
+	mov	x3, #NXP_PMU_ADDR
+1:
+	ldr	w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp	w1, w0
+	b.ne	1b
+
+	/* x3 = NXP_PMU_ADDR */
+	bl	get_pmu_flush_cluster_mask
+	mov	x3, #NXP_PMU_ADDR
+
+	str	w0, [x3, #PMU_CLL2FLUSHSETR_OFFSET]
+
+	/* x3 = NXP_PMU_ADDR */
+2:
+	ldr	w1, [x3, #PMU_CLL2FLUSHSR_OFFSET]
+	cmp	w1, w0
+	b.ne	2b
+
+	/* x3 = NXP_PMU_ADDR */
+
+	str	w0, [x3, #PMU_CLSL2FLUSHCLRR_OFFSET]
+
+	str	w0, [x3, #PMU_CLSINACTSETR_OFFSET]
+
+	/* Force the debug interface to be quiescent */
+	mrs	x0, osdlr_el1
+	orr	x0, x0, #0x1
+	msr	osdlr_el1, x0
+
+	/*
+	 * Enable the WakeRequest signal
+	 * x3 is cpu mask starting from cpu1 to cpu0
+	 */
+	bl	get_tot_num_cores
+	sub	x0, x0, #1
+	mov	x3, #0x1
+	lsl	x3, x3, x0
+2:
+	mov	x0, x3
+	bl	get_gic_rd_base  // 0-2
+	ldr	w1, [x0, #GICR_WAKER_OFFSET]
+	orr	w1, w1, #GICR_WAKER_SLEEP_BIT
+	str	w1, [x0, #GICR_WAKER_OFFSET]
+1:
+	ldr	w1, [x0, #GICR_WAKER_OFFSET]
+	cmp	w1, #GICR_WAKER_ASLEEP
+	b.ne	1b
+
+	lsr	x3, x3, #1
+	cbnz	x3, 2b
+
+	/* Invalidate all TLB entries at all 3 exception levels */
+	tlbi	alle1
+	tlbi	alle2
+	tlbi	alle3
+
+	/* Request lpm20 */
+	mov	x3, #NXP_PMU_ADDR
+	ldr	x0, =PMU_POWMGTCSR_OFFSET
+	ldr	w1, =PMU_POWMGTCSR_VAL
+	str	w1, [x3, x0]
+
+	ldr	x5, =NXP_EPU_ADDR
+4:
+	wfe
+	ldr	w1, [x5, #EPU_EPCTR10_OFFSET]
+	cmp	w1, #0
+	b.eq	4b
+
+	/* x3 = NXP_PMU_ADDR */
+
+	bl	get_pmu_idle_cluster_mask
+	mov	x3, NXP_PMU_ADDR
+
+	/* Re-enable the GPP ACP */
+	str	w0, [x3, #PMU_CLAINACTCLRR_OFFSET]
+	str	w0, [x3, #PMU_CLSINACTCLRR_OFFSET]
+
+	/* x3 = NXP_PMU_ADDR */
+3:
+	ldr	w1, [x3, #PMU_CLAINACTSETR_OFFSET]
+	cbnz	w1, 3b
+4:
+	ldr	w1, [x3, #PMU_CLSINACTSETR_OFFSET]
+	cbnz	w1, 4b
+
+	/*
+	 * Enable the WakeRequest signal on cpu 0-1
+	 * x3 is cpu mask starting from cpu1
+	 */
+	bl	get_tot_num_cores
+	sub	x0, x0, #1
+	mov	x3, #0x1
+	lsl	x3, x3, x0
+2:
+	mov	x0, x3
+	bl	get_gic_rd_base  // 0-2
+	ldr	w1, [x0, #GICR_WAKER_OFFSET]
+	bic	w1, w1, #GICR_WAKER_SLEEP_BIT
+	str	w1, [x0, #GICR_WAKER_OFFSET]
+1:
+	ldr	w1, [x0, #GICR_WAKER_OFFSET]
+	cbnz	w1, 1b
+
+	lsr	x3, x3, #1
+	cbnz	x3, 2b
+
+	/* Enable CCI snoop domain */
+	ldr	x0, =NXP_CCI_ADDR
+	str	wzr, [x0]
+	dsb	sy
+	isb
+
+	ldr	x3, =NXP_EPU_ADDR
+
+	/* x3 = epu base addr */
+
+	/* Enable sec, enetc, spi and qspi */
+	ldr	x2, =NXP_DCFG_ADDR
+	str	wzr, [x2, #DCFG_DEVDISR1_OFFSET]
+	str	wzr, [x2, #DCFG_DEVDISR2_OFFSET]
+	str	wzr, [x2, #DCFG_DEVDISR4_OFFSET]
+
+	/* Restore flextimer/mmc/usb interrupt router */
+	ldr	x3, =NXP_GICD_ADDR
+	ldp	x0, x2, [sp], #16
+	ldr	x1, =GICD_IROUTER113_OFFSET
+	str	w2, [x3, x1]
+	ldr	x1, =GICD_IROUTER112_OFFSET
+	str	w0, [x3, x1]
+	ldp	x0, x2, [sp], #16
+	ldr	x1, =GICD_IROUTER76_OFFSET
+	str	w2, [x3, x1]
+	ldr	x1, =GICD_IROUTER60_OFFSET
+	str	w0, [x3, x1]
+
+	/* Restore EPU registers */
+	ldr	x3, =NXP_EPU_ADDR
+	ldp	x0, x2, [sp], #16
+	str	w2, [x3, #EPU_EPGCR_OFFSET]
+	str	w0, [x3, #EPU_EPCTR10_OFFSET]
+	ldp	x2, x1, [sp], #16
+	str	w1, [x3, #EPU_EPCCR10_OFFSET]
+	str	w2, [x3, #EPU_EPIMCR10_OFFSET]
+
+	dsb	sy
+	isb
+	mov	x30, x18
+	ret
+
+/*
+ * Part of CPU_SUSPEND
+ *
+ * This function performs any SoC-specific cleanup after power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+_soc_sys_exit_pwrdn:
+	/* Enable stack alignment checking */
+	mrs	x1, SCTLR_EL1
+	orr	x1, x1, #0x4
+	msr	SCTLR_EL1, x1
+
+	/* Enable debug interface */
+	mrs	x1, osdlr_el1
+	bic	x1, x1, #OSDLR_EL1_DLK_LOCK
+	msr	osdlr_el1, x1
+
+	/* Enable i-cache */
+	mrs	x1, SCTLR_EL3
+	orr	x1, x1, #SCTLR_I_MASK
+	msr	SCTLR_EL3, x1
+
+	isb
+	ret
+
+/*
+ * This function setc up the TrustZone Address Space Controller (TZASC)
+ * in:  none
+ * out: none
+ * uses x0, x1
+ */
+init_tzpc:
+	/* Set Non Secure access for all devices protected via TZPC */
+	ldr	x1, =TZPCDECPROT_0_SET_BASE   /* decode Protection-0 Set Reg */
+	mov	w0, #0xFF		      /* set decode region to NS, Bits[7:0] */
+	str	w0, [x1]
+
+	ldr	x1, =TZPCDECPROT_1_SET_BASE   /* decode Protection-1 Set Reg */
+	mov	w0, #0xFF		      /* set decode region to NS, Bits[7:0] */
+	str	w0, [x1]
+
+	ldr	x1, =TZPCDECPROT_2_SET_BASE   /* decode Protection-2 Set Reg */
+	mov	w0, #0xFF		      /* set decode region to NS, Bits[7:0] */
+	str	w0, [x1]
+
+	 /* entire SRAM as NS */
+	ldr	x1, =NXP_OCRAM_TZPC_ADDR      /* secure RAM region size Reg */
+	mov	w0, #0x00000000		      /* 0x00000000 = no secure region */
+	str	w0, [x1]
+
+	ret
+
+/*
+ * This function performs any needed initialization on SecMon for
+ * boot services
+ */
+initSecMon:
+	/* Read the register hpcomr */
+	ldr	x1, =NXP_SNVS_ADDR
+	ldr	w0, [x1, #SECMON_HPCOMR_OFFSET]
+	/* Turn off secure access for the privileged registers */
+	orr	w0, w0, #SECMON_HPCOMR_NPSWAEN
+	/* Write back */
+	str	w0, [x1, #SECMON_HPCOMR_OFFSET]
+
+	ret
+
+/*
+ * This function checks to see if cores which are to be disabled have been
+ * released from reset - if not, it releases them
+ * in:  none
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8
+ */
+release_disabled:
+	stp	x18, x30, [sp, #-16]!
+
+	/*
+	 * Get the number of cpus on this device
+	 * Calling the below c function.
+	 * No need to Callee saved registers x9-x15,
+	 * as these registers are not used by the callee
+	 * prior to calling the below C-routine.
+	 */
+	bl	get_tot_num_cores
+	mov	x6, x0
+
+	/* Read COREDISABLESR */
+	mov	x0, #NXP_DCFG_ADDR
+	ldr	w4, [x0, #DCFG_COREDISABLEDSR_OFFSET]
+
+	mov	x0, #NXP_RESET_ADDR
+	ldr	w5, [x0, #BRR_OFFSET]
+
+	/* Load the core mask for the first core */
+	mov	x7, #1
+
+	/*
+	 * x4 = COREDISABLESR
+	 * x5 = BRR
+	 * x6 = loop count
+	 * x7 = core mask bit
+	 */
+2:
+	/* Check if the core is to be disabled */
+	tst	x4, x7
+	b.eq	1f
+
+	/* See if disabled cores have already been released from reset */
+	tst	x5, x7
+	b.ne	1f
+
+	/* If core has not been released, then release it (0-3) */
+	mov	x0, x7
+	bl	_soc_core_release
+
+	/* Record the core state in the data area (0-3) */
+	mov	x0, x7
+	mov	x1, #CORE_DISABLED
+	bl	_setCoreState
+1:
+	/* Decrement the counter */
+	subs	x6, x6, #1
+	b.le	3f
+	/* Shift the core mask to the next core */
+	lsl	x7, x7, #1
+	/* Continue */
+	b	2b
+3:
+	ldp	x18, x30, [sp], #16
+	ret
+
+/*
+ * Write a register in the DCFG block
+ * in:  x0 = offset
+ * in:  w1 = value to write
+ * uses x0, x1, x2
+ */
+_write_reg_dcfg:
+	ldr	x2, =NXP_DCFG_ADDR
+	str	w1, [x2, x0]
+	ret
+
+/*
+ * Read a register in the DCFG block
+ * in:  x0 = offset
+ * out: w0 = value read
+ * uses x0, x1, x2
+ */
+_read_reg_dcfg:
+	ldr	x2, =NXP_DCFG_ADDR
+	ldr	w1, [x2, x0]
+	mov	w0, w1
+	ret
+
+/*
+ * This function returns an mpidr value for a core, given a core_mask_lsb
+ * in:  x0 = core mask lsb
+ * out: x0 = affinity2:affinity1:affinity0, where affinity is 8-bits
+ * uses x0, x1
+ */
+get_mpidr_value:
+	/* Convert a core mask to an SoC core number */
+	clz	w0, w0
+	mov	w1, #31
+	sub	w0, w1, w0
+
+	/* Get the mpidr core number from the SoC core number */
+	mov	w1, wzr
+	tst	x0, #1
+	b.eq	1f
+	orr	w1, w1, #1
+1:
+	/* Extract the cluster number */
+	lsr	w0, w0, #1
+	orr	w0, w1, w0, lsl #8
+
+	ret
+
+/*
+ * This function returns the redistributor base address for the core specified
+ * in x1
+ * in:  x0 - core mask lsb of specified core
+ * out: x0 = redistributor rd base address for specified core
+ * uses x0, x1, x2
+ */
+get_gic_rd_base:
+	/* Get the 0-based core number */
+	clz	w1, w0
+	mov	w2, #0x20
+	sub	w2, w2, w1
+	sub	w2, w2, #1
+
+	/* x2 = core number / loop counter */
+	ldr	x0, =NXP_GICR_ADDR
+	mov	x1, #GIC_RD_OFFSET
+2:
+	cbz	x2, 1f
+	add	x0, x0, x1
+	sub	x2, x2, #1
+	b	2b
+1:
+	ret
+
+/*
+ * This function returns the redistributor base address for the core specified
+ * in x1
+ * in:  x0 - core mask lsb of specified core
+ * out: x0 = redistributor sgi base address for specified core
+ * uses x0, x1, x2
+ */
+get_gic_sgi_base:
+	/* Get the 0-based core number */
+	clz	w1, w0
+	mov	w2, #0x20
+	sub	w2, w2, w1
+	sub	w2, w2, #1
+
+	/* x2 = core number / loop counter */
+	ldr	x0, =NXP_GICR_SGI_ADDR
+	mov	x1, #GIC_SGI_OFFSET
+2:
+	cbz	x2, 1f
+	add	x0, x0, x1
+	sub	x2, x2, #1
+	b	2b
+1:
+	ret
+
+/*
+ * Write a register in the RESET block
+ * in:  x0 = offset
+ * in:  w1 = value to write
+ * uses x0, x1, x2
+ */
+_write_reg_reset:
+	ldr	x2, =NXP_RESET_ADDR
+	str	w1, [x2, x0]
+	ret
+
+/*
+ * Read a register in the RESET block
+ * in:  x0 = offset
+ * out: w0 = value read
+ * uses x0, x1
+ */
+_read_reg_reset:
+	ldr	x1, =NXP_RESET_ADDR
+	ldr	w0, [x1, x0]
+	ret
diff --git a/plat/nxp/soc-ls1028a/aarch64/ls1028a_helpers.S b/plat/nxp/soc-ls1028a/aarch64/ls1028a_helpers.S
new file mode 100644
index 0000000..ec67529
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/aarch64/ls1028a_helpers.S
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+
+#include <platform_def.h>
+
+.globl	plat_secondary_cold_boot_setup
+.globl	plat_is_my_cpu_primary
+.globl	plat_reset_handler
+.globl  platform_mem_init
+
+func platform_mem1_init
+	ret
+endfunc platform_mem1_init
+
+func platform_mem_init
+	ret
+endfunc	platform_mem_init
+
+func apply_platform_errata
+	ret
+endfunc apply_platform_errata
+
+func plat_reset_handler
+	mov	x29, x30
+	bl	apply_platform_errata
+
+#if defined(IMAGE_BL31)
+	ldr	x0, =POLICY_SMMU_PAGESZ_64K
+	cbz	x0, 1f
+	/* Set the SMMU page size in the sACR register */
+	bl	_set_smmu_pagesz_64
+#endif
+1:
+	mov	x30, x29
+	ret
+endfunc plat_reset_handler
+
+/*
+ * void plat_secondary_cold_boot_setup (void);
+ *
+ * This function performs any platform specific actions
+ * needed for a secondary cpu after a cold reset e.g
+ * mark the cpu's presence, mechanism to place it in a
+ * holding pen etc.
+ */
+func plat_secondary_cold_boot_setup
+	/* ls1028a does not do cold boot for secondary CPU */
+cb_panic:
+	b	cb_panic
+endfunc plat_secondary_cold_boot_setup
+
+/*
+ * unsigned int plat_is_my_cpu_primary (void);
+ *
+ * Find out whether the current cpu is the primary
+ * cpu.
+ */
+func plat_is_my_cpu_primary
+	mrs	x0, mpidr_el1
+	and	x0, x0, #(MPIDR_CLUSTER_MASK | MPIDR_CPU_MASK)
+	cmp	x0, 0x0
+	cset	w0, eq
+	ret
+endfunc plat_is_my_cpu_primary
diff --git a/plat/nxp/soc-ls1028a/include/soc.h b/plat/nxp/soc-ls1028a/include/soc.h
new file mode 100644
index 0000000..b1d044a
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/include/soc.h
@@ -0,0 +1,149 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SOC_H
+#define	SOC_H
+
+/* Chassis specific defines - common across SoC's of a particular platform */
+#include <dcfg_lsch3.h>
+#include <soc_default_base_addr.h>
+#include <soc_default_helper_macros.h>
+
+/*
+ * SVR Definition of LS1028A
+ * (not include major and minor rev)
+ * These info is listed in Table B-6. DCFG differences
+ * between LS1028A and LS1027A of LS1028ARM(Reference Manual)
+ */
+#define SVR_LS1017AN		0x870B25
+#define SVR_LS1017AE		0x870B24
+#define SVR_LS1018AN		0x870B21
+#define SVR_LS1018AE		0x870B20
+#define SVR_LS1027AN		0x870B05
+#define SVR_LS1027AE		0x870B04
+#define SVR_LS1028AN		0x870B01
+#define SVR_LS1028AE		0x870B00
+
+/* Number of cores in platform */
+#define PLATFORM_CORE_COUNT		2
+#define NUMBER_OF_CLUSTERS		1
+#define CORES_PER_CLUSTER		2
+
+/* Set to 0 if the clusters are not symmetrical */
+#define SYMMETRICAL_CLUSTERS		1
+
+#define NUM_DRAM_REGIONS		3
+
+#define	NXP_DRAM0_ADDR			0x80000000
+#define NXP_DRAM0_MAX_SIZE		0x80000000	/* 2GB */
+
+#define NXP_DRAM1_ADDR			0x2080000000
+#define NXP_DRAM1_MAX_SIZE		0x1F80000000	/* 126G */
+
+#define NXP_DRAM2_ADDR			0x6000000000
+#define NXP_DRAM2_MAX_SIZE		0x2000000000	/* 128G */
+
+/* DRAM0 Size defined in platform_def.h */
+#define	NXP_DRAM0_SIZE			PLAT_DEF_DRAM0_SIZE
+
+/* CCSR space memory Map  */
+#undef NXP_UART_ADDR
+#define NXP_UART_ADDR			0x021C0500
+
+#undef NXP_UART1_ADDR
+#define NXP_UART1_ADDR			0x021C0600
+
+#undef NXP_WDOG1_TZ_ADDR
+#define NXP_WDOG1_TZ_ADDR		0x023C0000
+
+#undef NXP_GICR_ADDR
+#define NXP_GICR_ADDR			0x06040000
+
+#undef NXP_GICR_SGI_ADDR
+#define NXP_GICR_SGI_ADDR		0x06050000
+
+/* EPU register offsets and values */
+#define EPU_EPGCR_OFFSET              0x0
+#define EPU_EPIMCR10_OFFSET           0x128
+#define EPU_EPCTR10_OFFSET            0xa28
+#define EPU_EPCCR10_OFFSET            0x828
+#define EPU_EPCCR10_VAL               0xb2800000
+#define EPU_EPIMCR10_VAL              0xba000000
+#define EPU_EPCTR10_VAL               0x0
+#define EPU_EPGCR_VAL                 (1 << 31)
+
+/* PORSR1 */
+#define PORSR1_RCW_MASK		0x07800000
+#define PORSR1_RCW_SHIFT	23
+
+#define SDHC1_VAL		0x8
+#define SDHC2_VAL		0x9
+#define I2C1_VAL		0xa
+#define FLEXSPI_NAND2K_VAL	0xc
+#define FLEXSPI_NAND4K_VAL	0xd
+#define FLEXSPI_NOR		0xf
+
+/*
+ * Required LS standard platform porting definitions
+ * for CCI-400
+ */
+#define NXP_CCI_CLUSTER0_SL_IFACE_IX	4
+
+/* Defines required for using XLAT tables from ARM common code */
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ull << 40)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ull << 40)
+
+/* Clock Divisors */
+#define NXP_PLATFORM_CLK_DIVIDER	1
+#define NXP_UART_CLK_DIVIDER		2
+
+/* dcfg register offsets and values */
+#define DCFG_DEVDISR2_ENETC		(1 << 31)
+
+#define MPIDR_AFFINITY0_MASK		0x00FF
+#define MPIDR_AFFINITY1_MASK		0xFF00
+#define CPUECTLR_DISABLE_TWALK_PREFETCH	0x4000000000
+#define CPUECTLR_INS_PREFETCH_MASK	0x1800000000
+#define CPUECTLR_DAT_PREFETCH_MASK	0x0300000000
+#define OSDLR_EL1_DLK_LOCK		0x1
+#define CNTP_CTL_EL0_EN			0x1
+#define CNTP_CTL_EL0_IMASK		0x2
+
+#define SYSTEM_PWR_DOMAINS	1
+#define PLAT_NUM_PWR_DOMAINS	(PLATFORM_CORE_COUNT + \
+				 NUMBER_OF_CLUSTERS  + \
+				 SYSTEM_PWR_DOMAINS)
+
+/* Power state coordination occurs at the system level */
+#define PLAT_PD_COORD_LVL	MPIDR_AFFLVL2
+#define PLAT_MAX_PWR_LVL	PLAT_PD_COORD_LVL
+
+/* Local power state for power domains in Run state */
+#define LS_LOCAL_STATE_RUN	PSCI_LOCAL_STATE_RUN
+
+/* define retention state */
+#define PLAT_MAX_RET_STATE	(PSCI_LOCAL_STATE_RUN + 1)
+#define LS_LOCAL_STATE_RET	PLAT_MAX_RET_STATE
+
+/* define power-down state */
+#define PLAT_MAX_OFF_STATE	(PLAT_MAX_RET_STATE + 1)
+#define LS_LOCAL_STATE_OFF	PLAT_MAX_OFF_STATE
+
+/* One cache line needed for bakery locks on ARM platforms */
+#define PLAT_PERCPU_BAKERY_LOCK_SIZE	(1 * CACHE_WRITEBACK_GRANULE)
+
+#ifndef __ASSEMBLER__
+/* CCI slave interfaces */
+static const int cci_map[] = {
+	NXP_CCI_CLUSTER0_SL_IFACE_IX,
+};
+void soc_init_lowlevel(void);
+void soc_init_percpu(void);
+void _soc_set_start_addr(unsigned long addr);
+void _set_platform_security(void);
+#endif
+
+#endif /* SOC_H */
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/ddr_init.c b/plat/nxp/soc-ls1028a/ls1028ardb/ddr_init.c
new file mode 100644
index 0000000..d82be51
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/ddr_init.c
@@ -0,0 +1,185 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#include <string.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <lib/utils.h>
+
+#include <platform_def.h>
+
+#ifdef CONFIG_STATIC_DDR
+const struct ddr_cfg_regs static_1600 = {
+	.cs[0].config = U(0x80040422),
+	.cs[0].bnds = U(0xFF),
+	.sdram_cfg[0] = U(0xE50C0004),
+	.sdram_cfg[1] = U(0x401100),
+	.timing_cfg[0] = U(0x91550018),
+	.timing_cfg[1] = U(0xBAB40C42),
+	.timing_cfg[2] = U(0x48C111),
+	.timing_cfg[3] = U(0x1111000),
+	.timing_cfg[4] = U(0x2),
+	.timing_cfg[5] = U(0x3401400),
+	.timing_cfg[7] = U(0x23300000),
+	.timing_cfg[8] = U(0x2114600),
+	.sdram_mode[0] = U(0x3010210),
+	.sdram_mode[9] = U(0x4000000),
+	.sdram_mode[8] = U(0x500),
+	.sdram_mode[2] = U(0x10210),
+	.sdram_mode[10] = U(0x400),
+	.sdram_mode[11] = U(0x4000000),
+	.sdram_mode[4] = U(0x10210),
+	.sdram_mode[12] = U(0x400),
+	.sdram_mode[13] = U(0x4000000),
+	.sdram_mode[6] = U(0x10210),
+	.sdram_mode[14] = U(0x400),
+	.sdram_mode[15] = U(0x4000000),
+	.interval = U(0x18600618),
+	.data_init = U(0xdeadbeef),
+	.zq_cntl = U(0x8A090705),
+	.clk_cntl = U(0x2000000),
+	.cdr[0] = U(0x80040000),
+	.cdr[1] = U(0xA181),
+	.wrlvl_cntl[0] = U(0x8675F605),
+	.wrlvl_cntl[1] = U(0x6070700),
+	.wrlvl_cntl[2] = U(0x0000008),
+	.dq_map[0] = U(0x5b65b658),
+	.dq_map[1] = U(0xd96d8000),
+	.dq_map[2] = U(0),
+	.dq_map[3] = U(0x1600000),
+	.debug[28] = U(0x00700046),
+};
+
+unsigned long long board_static_ddr(struct ddr_info *priv)
+{
+	memcpy(&priv->ddr_reg, &static_1600, sizeof(static_1600));
+	return ULL(0x100000000);
+}
+
+#else
+
+static const struct rc_timing rcz[] = {
+	{1600, 8, 5},
+	{}
+};
+
+static const struct board_timing ram[] = {
+	{0x1f, rcz, 0x1020200, 0x00000003},
+};
+
+int ddr_board_options(struct ddr_info *priv)
+{
+	int ret;
+	struct memctl_opt *popts = &priv->opt;
+
+	ret = cal_board_params(priv, ram, ARRAY_SIZE(ram));
+	if (ret != 0) {
+		return ret;
+	}
+
+	popts->bstopre = U(0x40); /* precharge value */
+	popts->half_strength_drive_en = 1;
+	popts->cpo_sample = U(0x46);
+	popts->ddr_cdr1 = DDR_CDR1_DHC_EN |
+			  DDR_CDR1_ODT(DDR_CDR_ODT_80ohm);
+	popts->ddr_cdr2 = DDR_CDR2_ODT(DDR_CDR_ODT_80ohm) |
+			  DDR_CDR2_VREF_OVRD(70); /* Vref = 70% */
+
+	popts->addr_hash = 1; /* address hashing */
+	return 0;
+}
+
+/* DDR model number:  MT40A1G8SA-075:E */
+struct dimm_params ddr_raw_timing = {
+	.n_ranks = U(1),
+	.rank_density = ULL(4294967296),
+	.capacity = ULL(4294967296),
+	.primary_sdram_width = U(32),
+	.ec_sdram_width = U(4),
+	.rdimm = U(0),
+	.mirrored_dimm = U(0),
+	.n_row_addr = U(16),
+	.n_col_addr = U(10),
+	.bank_group_bits = U(2),
+	.edc_config = U(2),
+	.burst_lengths_bitmask = U(0x0c),
+	.tckmin_x_ps = 750,
+	.tckmax_ps = 1900,
+	.caslat_x = U(0x0001FFE00),
+	.taa_ps = 13500,
+	.trcd_ps = 13500,
+	.trp_ps = 13500,
+	.tras_ps = 32000,
+	.trc_ps = 45500,
+	.twr_ps = 15000,
+	.trfc1_ps = 350000,
+	.trfc2_ps = 260000,
+	.trfc4_ps = 160000,
+	.tfaw_ps = 21000,
+	.trrds_ps = 3000,
+	.trrdl_ps = 4900,
+	.tccdl_ps = 5000,
+	.refresh_rate_ps = U(7800000),
+	.dq_mapping[0] = U(0x16),
+	.dq_mapping[1] = U(0x36),
+	.dq_mapping[2] = U(0x16),
+	.dq_mapping[3] = U(0x36),
+	.dq_mapping[4] = U(0x16),
+	.dq_mapping[5] = U(0x36),
+	.dq_mapping[6] = U(0x16),
+	.dq_mapping[7] = U(0x36),
+	.dq_mapping[8] = U(0x16),
+	.dq_mapping[9] = U(0x0),
+	.dq_mapping[10] = U(0x0),
+	.dq_mapping[11] = U(0x0),
+	.dq_mapping[12] = U(0x0),
+	.dq_mapping[13] = U(0x0),
+	.dq_mapping[14] = U(0x0),
+	.dq_mapping[15] = U(0x0),
+	.dq_mapping[16] = U(0x0),
+	.dq_mapping[17] = U(0x0),
+	.dq_mapping_ors = U(0),
+	.rc = U(0x1f),
+};
+
+int ddr_get_ddr_params(struct dimm_params *pdimm,
+			    struct ddr_conf *conf)
+{
+	static const char dimm_model[] = "Fixed DDR on board";
+
+	conf->dimm_in_use[0] = 1;
+	memcpy(pdimm, &ddr_raw_timing, sizeof(struct dimm_params));
+	memcpy(pdimm->mpart, dimm_model, sizeof(dimm_model) - 1);
+
+	return 1;
+}
+#endif
+
+int64_t init_ddr(void)
+{
+	struct ddr_info info;
+	struct sysinfo sys;
+	int64_t dram_size;
+
+	zeromem(&sys, sizeof(sys));
+	get_clocks(&sys);
+	debug("platform clock %lu\n", sys.freq_platform);
+	debug("DDR PLL1 %lu\n", sys.freq_ddr_pll0);
+
+	zeromem(&info, sizeof(struct ddr_info));
+	info.num_ctlrs = 1;
+	info.dimm_on_ctlr = 1;
+	info.clk = get_ddr_freq(&sys, 0);
+	info.ddr[0] = (void *)NXP_DDR_ADDR;
+
+	dram_size = dram_init(&info);
+
+	if (dram_size < 0) {
+		ERROR("DDR init failed.\n");
+	}
+
+	return dram_size;
+}
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/plat_def.h b/plat/nxp/soc-ls1028a/ls1028ardb/plat_def.h
new file mode 100644
index 0000000..63c0219
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/plat_def.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLAT_DEF_H
+#define PLAT_DEF_H
+
+#include <arch.h>
+#include <cortex_a72.h>
+/*
+ * Required without TBBR.
+ * To include the defines for DDR PHY
+ * Images.
+ */
+#include <tbbr_img_def.h>
+
+#include <policy.h>
+#include <soc.h>
+
+
+#define NXP_SYSCLK_FREQ		100000000
+#define NXP_DDRCLK_FREQ		100000000
+
+/* UART related definition */
+#define NXP_CONSOLE_ADDR	NXP_UART_ADDR
+#define NXP_CONSOLE_BAUDRATE	115200
+
+#define NXP_SPD_EEPROM0		0x51
+
+/* Size of cacheable stacks */
+#if defined(IMAGE_BL2)
+#if defined(TRUSTED_BOARD_BOOT)
+#define PLATFORM_STACK_SIZE	0x2000
+#else
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+#elif defined(IMAGE_BL31)
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+
+/* SD block buffer */
+#define NXP_SD_BLOCK_BUF_SIZE	(0xC000)
+
+#ifdef SD_BOOT
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+#else
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE)
+#endif
+#define BL2_TEXT_LIMIT		(BL2_LIMIT)
+
+/* IO defines as needed by IO driver framework */
+#define MAX_IO_DEVICES		4
+#define MAX_IO_BLOCK_DEVICES	1
+#define MAX_IO_HANDLES		4
+
+#define BL31_WDOG_SEC		89
+
+/*
+ * Define properties of Group 1 Secure and Group 0 interrupts as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define PLAT_LS_G1S_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(BL32_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE)
+
+/* SGI 15 and Secure watchdog interrupts assigned to Group 0 */
+#define PLAT_LS_G0_IRQ_PROPS(grp)	\
+	INTR_PROP_DESC(BL31_WDOG_SEC, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(15, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_LEVEL)
+#endif /* PLAT_DEF_H */
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/platform.c b/plat/nxp/soc-ls1028a/ls1028ardb/platform.c
new file mode 100644
index 0000000..65d508c
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/platform.c
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <plat_common.h>
+
+#pragma weak board_enable_povdd
+#pragma weak board_disable_povdd
+
+bool board_enable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
+
+bool board_disable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/platform.mk b/plat/nxp/soc-ls1028a/ls1028ardb/platform.mk
new file mode 100644
index 0000000..c455000
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/platform.mk
@@ -0,0 +1,33 @@
+#
+# Copyright 2020-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Board-specific build parameters
+BOOT_MODE	?=	flexspi_nor
+BOARD		:=	ls1028ardb
+POVDD_ENABLE	:=	no
+WARM_BOOT	:=	no
+
+# DDR build parameters
+NUM_OF_DDRC		:=	1
+CONFIG_DDR_NODIMM	:=	1
+DDR_ECC_EN		:=	yes
+
+# On-board flash
+FLASH_TYPE	:=	MT35XU02G
+XSPI_FLASH_SZ	:=	0x10000000
+
+BL2_SOURCES	+=	${BOARD_PATH}/ddr_init.c \
+			${BOARD_PATH}/platform.c
+
+SUPPORTED_BOOT_MODE	:=	flexspi_nor	\
+				sd		\
+				emmc
+
+# Add platform board build info
+include plat/nxp/common/plat_make_helper/plat_common_def.mk
+
+# Add SoC build info
+include plat/nxp/soc-ls1028a/soc.mk
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/platform_def.h b/plat/nxp/soc-ls1028a/ls1028ardb/platform_def.h
new file mode 100644
index 0000000..bbad293
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/platform_def.h
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include <plat_def.h>
+#include <plat_default_def.h>
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/nxp/soc-ls1028a/ls1028ardb/policy.h b/plat/nxp/soc-ls1028a/ls1028ardb/policy.h
new file mode 100644
index 0000000..67a8b45
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/ls1028ardb/policy.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright 2020-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef POLICY_H
+#define	POLICY_H
+
+/*
+ * Set this to 0x0 to leave the default SMMU page size in sACR
+ * Set this to 0x1 to change the SMMU page size to 64K
+ */
+#define POLICY_SMMU_PAGESZ_64K 0x1
+
+#endif /* POLICY_H */
diff --git a/plat/nxp/soc-ls1028a/soc.c b/plat/nxp/soc-ls1028a/soc.c
new file mode 100644
index 0000000..edfd657
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/soc.c
@@ -0,0 +1,432 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <endian.h>
+
+#include <arch.h>
+#include <caam.h>
+#include <cassert.h>
+#include <cci.h>
+#include <common/debug.h>
+#include <dcfg.h>
+#include <i2c.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <ls_interconnect.h>
+#include <mmio.h>
+#ifdef POLICY_FUSE_PROVISION
+#include <nxp_gpio.h>
+#endif
+#if TRUSTED_BOARD_BOOT
+#include <nxp_smmu.h>
+#endif
+#include <nxp_timer.h>
+#ifdef CONFIG_OCRAM_ECC_EN
+#include <ocram.h>
+#endif
+#include <plat_console.h>
+#include <plat_gic.h>
+#include <plat_tzc400.h>
+#include <pmu.h>
+#include <scfg.h>
+#if defined(NXP_SFP_ENABLED)
+#include <sfp.h>
+#endif
+
+#include <errata.h>
+#include "plat_common.h"
+#include "platform_def.h"
+#include "soc.h"
+
+static dcfg_init_info_t dcfg_init_data = {
+	.g_nxp_dcfg_addr = NXP_DCFG_ADDR,
+	.nxp_sysclk_freq = NXP_SYSCLK_FREQ,
+	.nxp_ddrclk_freq = NXP_DDRCLK_FREQ,
+	.nxp_plat_clk_divider = NXP_PLATFORM_CLK_DIVIDER,
+};
+
+static struct soc_type soc_list[] =  {
+	SOC_ENTRY(LS1017AN, LS1017AN, 1, 1),
+	SOC_ENTRY(LS1017AE, LS1017AE, 1, 1),
+	SOC_ENTRY(LS1018AN, LS1018AN, 1, 1),
+	SOC_ENTRY(LS1018AE, LS1018AE, 1, 1),
+	SOC_ENTRY(LS1027AN, LS1027AN, 1, 2),
+	SOC_ENTRY(LS1027AE, LS1027AE, 1, 2),
+	SOC_ENTRY(LS1028AN, LS1028AN, 1, 2),
+	SOC_ENTRY(LS1028AE, LS1028AE, 1, 2),
+};
+
+CASSERT(NUMBER_OF_CLUSTERS && NUMBER_OF_CLUSTERS <= 256,
+	assert_invalid_ls1028a_cluster_count);
+
+/*
+ * Function returns the base counter frequency
+ * after reading the first entry at CNTFID0 (0x20 offset).
+ *
+ * Function is used by:
+ *   1. ARM common code for PSCI management.
+ *   2. ARM Generic Timer init.
+ *
+ */
+unsigned int plat_get_syscnt_freq2(void)
+{
+	unsigned int counter_base_frequency;
+	/*
+	 * Below register specifies the base frequency of the system counter.
+	 * As per NXP Board Manuals:
+	 * The system counter always works with SYS_REF_CLK/4 frequency clock.
+	 */
+	counter_base_frequency = mmio_read_32(NXP_TIMER_ADDR + CNTFID_OFF);
+
+	return counter_base_frequency;
+}
+
+#ifdef IMAGE_BL2
+
+#ifdef POLICY_FUSE_PROVISION
+static gpio_init_info_t gpio_init_data = {
+	.gpio1_base_addr = NXP_GPIO1_ADDR,
+	.gpio2_base_addr = NXP_GPIO2_ADDR,
+	.gpio3_base_addr = NXP_GPIO3_ADDR,
+};
+#endif
+
+void soc_preload_setup(void)
+{
+}
+
+void soc_early_init(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+#ifdef CONFIG_OCRAM_ECC_EN
+	ocram_init(NXP_OCRAM_ADDR, NXP_OCRAM_SIZE);
+#endif
+	dcfg_init(&dcfg_init_data);
+	enable_timer_base_to_cluster(NXP_PMU_ADDR);
+	enable_core_tb(NXP_PMU_ADDR);
+	dram_regions_info_t *dram_regions_info = get_dram_regions_info();
+
+#ifdef POLICY_FUSE_PROVISION
+	gpio_init(&gpio_init_data);
+	sec_init(NXP_CAAM_ADDR);
+#endif
+
+#if LOG_LEVEL > 0
+	/* Initialize the console to provide early debug support */
+	plat_console_init(NXP_CONSOLE_ADDR,
+				NXP_UART_CLK_DIVIDER, NXP_CONSOLE_BAUDRATE);
+#endif
+	enum  boot_device dev = get_boot_dev();
+	/*
+	 * Mark the buffer for SD in OCRAM as non secure.
+	 * The buffer is assumed to be at end of OCRAM for
+	 * the logic below to calculate TZPC programming
+	 */
+	if (dev == BOOT_DEVICE_EMMC || dev == BOOT_DEVICE_SDHC2_EMMC) {
+		/*
+		 * Calculate the region in OCRAM which is secure
+		 * The buffer for SD needs to be marked non-secure
+		 * to allow SD to do DMA operations on it
+		 */
+		uint32_t secure_region = (NXP_OCRAM_SIZE - NXP_SD_BLOCK_BUF_SIZE);
+		uint32_t mask = secure_region/TZPC_BLOCK_SIZE;
+
+		mmio_write_32(NXP_OCRAM_TZPC_ADDR, mask);
+
+		/* Add the entry for buffer in MMU Table */
+		mmap_add_region(NXP_SD_BLOCK_BUF_ADDR, NXP_SD_BLOCK_BUF_ADDR,
+				NXP_SD_BLOCK_BUF_SIZE, MT_DEVICE | MT_RW | MT_NS);
+	}
+
+#if TRUSTED_BOARD_BOOT
+	uint32_t mode;
+
+	sfp_init(NXP_SFP_ADDR);
+
+	/*
+	 * For secure boot disable SMMU.
+	 * Later when platform security policy comes in picture,
+	 * this might get modified based on the policy
+	 */
+	if (check_boot_mode_secure(&mode) == true) {
+		bypass_smmu(NXP_SMMU_ADDR);
+	}
+
+	/*
+	 * For Mbedtls currently crypto is not supported via CAAM
+	 * enable it when that support is there. In tbbr.mk
+	 * the CAAM_INTEG is set as 0.
+	 */
+#ifndef MBEDTLS_X509
+	/* Initialize the crypto accelerator if enabled */
+	if (is_sec_enabled()) {
+		sec_init(NXP_CAAM_ADDR);
+	} else {
+		INFO("SEC is disabled.\n");
+	}
+#endif
+#endif
+
+	/* Set eDDRTQ for DDR performance */
+	scfg_setbits32((void *)(NXP_SCFG_ADDR + 0x210), 0x1f1f1f1f);
+
+	soc_errata();
+
+	/*
+	 * Initialize Interconnect for this cluster during cold boot.
+	 * No need for locks as no other CPU is active.
+	 */
+	cci_init(NXP_CCI_ADDR, cci_map, ARRAY_SIZE(cci_map));
+
+	/*
+	 * Enable Interconnect coherency for the primary CPU's cluster.
+	 */
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	plat_ls_interconnect_enter_coherency(num_clusters);
+
+	delay_timer_init(NXP_TIMER_ADDR);
+	i2c_init(NXP_I2C_ADDR);
+	dram_regions_info->total_dram_size = init_ddr();
+}
+
+void soc_bl2_prepare_exit(void)
+{
+#if defined(NXP_SFP_ENABLED) && defined(DISABLE_FUSE_WRITE)
+	set_sfp_wr_disable();
+#endif
+}
+
+/*
+ * This function returns the boot device based on RCW_SRC
+ */
+enum boot_device get_boot_dev(void)
+{
+	enum boot_device src = BOOT_DEVICE_NONE;
+	uint32_t porsr1;
+	uint32_t rcw_src;
+
+	porsr1 = read_reg_porsr1();
+
+	rcw_src = (porsr1 & PORSR1_RCW_MASK) >> PORSR1_RCW_SHIFT;
+	switch (rcw_src) {
+	case FLEXSPI_NOR:
+		src = BOOT_DEVICE_FLEXSPI_NOR;
+		INFO("RCW BOOT SRC is FLEXSPI NOR\n");
+		break;
+	case FLEXSPI_NAND2K_VAL:
+	case FLEXSPI_NAND4K_VAL:
+		INFO("RCW BOOT SRC is FLEXSPI NAND\n");
+		src = BOOT_DEVICE_FLEXSPI_NAND;
+		break;
+	case SDHC1_VAL:
+		src = BOOT_DEVICE_EMMC;
+		INFO("RCW BOOT SRC is SD\n");
+		break;
+	case SDHC2_VAL:
+		src = BOOT_DEVICE_SDHC2_EMMC;
+		INFO("RCW BOOT SRC is EMMC\n");
+		break;
+	default:
+		break;
+	}
+
+	return src;
+}
+
+/*
+ * This function sets up access permissions on memory regions
+ ****************************************************************************/
+void soc_mem_access(void)
+{
+	dram_regions_info_t *info_dram_regions = get_dram_regions_info();
+	struct tzc400_reg tzc400_reg_list[MAX_NUM_TZC_REGION];
+	int dram_idx = 0;
+	/* index 0 is reserved for region-0 */
+	int index = 1;
+
+	for (dram_idx = 0; dram_idx < info_dram_regions->num_dram_regions;
+	     dram_idx++) {
+		if (info_dram_regions->region[dram_idx].size == 0) {
+			ERROR("DDR init failure, or");
+			ERROR("DRAM regions not populated correctly.\n");
+			break;
+		}
+
+		index = populate_tzc400_reg_list(tzc400_reg_list,
+				dram_idx, index,
+				info_dram_regions->region[dram_idx].addr,
+				info_dram_regions->region[dram_idx].size,
+				NXP_SECURE_DRAM_SIZE, NXP_SP_SHRD_DRAM_SIZE);
+	}
+
+	mem_access_setup(NXP_TZC_ADDR, index, tzc400_reg_list);
+}
+
+#else
+
+static unsigned char _power_domain_tree_desc[NUMBER_OF_CLUSTERS + 2];
+/*
+ * This function dynamically constructs the topology according to
+ *  SoC Flavor and returns it.
+ */
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+	unsigned int i;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	/*
+	 * The highest level is the system level. The next level is constituted
+	 * by clusters and then cores in clusters.
+	 */
+	_power_domain_tree_desc[0] = 1;
+	_power_domain_tree_desc[1] = num_clusters;
+
+	for (i = 0; i < _power_domain_tree_desc[1]; i++)
+		_power_domain_tree_desc[i + 2] = cores_per_cluster;
+
+	return _power_domain_tree_desc;
+}
+
+/*
+ * This function returns the core count within the cluster corresponding to
+ * `mpidr`.
+ */
+unsigned int plat_ls_get_cluster_core_count(u_register_t mpidr)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	return num_clusters;
+}
+
+void soc_early_platform_setup2(void)
+{
+	dcfg_init(&dcfg_init_data);
+	/* Initialize system level generic timer for Socs */
+	delay_timer_init(NXP_TIMER_ADDR);
+
+#if LOG_LEVEL > 0
+	/* Initialize the console to provide early debug support */
+	plat_console_init(NXP_CONSOLE_ADDR,
+				NXP_UART_CLK_DIVIDER, NXP_CONSOLE_BAUDRATE);
+#endif
+}
+
+void soc_platform_setup(void)
+{
+	/* Initialize the GIC driver, cpu and distributor interfaces */
+	static uintptr_t target_mask_array[PLATFORM_CORE_COUNT];
+	static interrupt_prop_t ls_interrupt_props[] = {
+		PLAT_LS_G1S_IRQ_PROPS(INTR_GROUP1S),
+		PLAT_LS_G0_IRQ_PROPS(INTR_GROUP0)
+	};
+
+	plat_ls_gic_driver_init(NXP_GICD_ADDR, NXP_GICR_ADDR,
+				PLATFORM_CORE_COUNT,
+				ls_interrupt_props,
+				ARRAY_SIZE(ls_interrupt_props),
+				target_mask_array,
+				plat_core_pos);
+
+	plat_ls_gic_init();
+	enable_init_timer();
+}
+
+/* This function initializes the soc from the BL31 module */
+void soc_init(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+
+	/* Low-level init of the soc */
+	soc_init_lowlevel();
+	_init_global_data();
+	soc_init_percpu();
+	_initialize_psci();
+
+	/*
+	 * Initialize Interconnect for this cluster during cold boot.
+	 * No need for locks as no other CPU is active.
+	 */
+	cci_init(NXP_CCI_ADDR, cci_map, ARRAY_SIZE(cci_map));
+
+	/* Enable Interconnect coherency for the primary CPU's cluster. */
+	plat_ls_interconnect_enter_coherency(num_clusters);
+
+	/* Set platform security policies */
+	_set_platform_security();
+
+	/* Init SEC Engine which will be used by SiP */
+	if (is_sec_enabled()) {
+		sec_init(NXP_CAAM_ADDR);
+	} else {
+		INFO("SEC is disabled.\n");
+	}
+}
+
+#ifdef NXP_WDOG_RESTART
+static uint64_t wdog_interrupt_handler(uint32_t id, uint32_t flags,
+					  void *handle, void *cookie)
+{
+	uint8_t data = WDOG_RESET_FLAG;
+
+	wr_nv_app_data(WDT_RESET_FLAG_OFFSET,
+			(uint8_t *)&data, sizeof(data));
+
+	mmio_write_32(NXP_RST_ADDR + RSTCNTL_OFFSET, SW_RST_REQ_INIT);
+
+	return 0;
+}
+#endif
+
+void soc_runtime_setup(void)
+{
+#ifdef NXP_WDOG_RESTART
+	request_intr_type_el3(BL31_NS_WDOG_WS1, wdog_interrupt_handler);
+#endif
+}
+
+/* This function returns the total number of cores in the SoC. */
+unsigned int get_tot_num_cores(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	return (num_clusters * cores_per_cluster);
+}
+
+/* This function returns the PMU IDLE Cluster mask. */
+unsigned int get_pmu_idle_cluster_mask(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	return ((1 << num_clusters) - 2);
+}
+
+/* This function returns the PMU Flush Cluster mask. */
+unsigned int get_pmu_flush_cluster_mask(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list), &num_clusters, &cores_per_cluster);
+	return ((1 << num_clusters) - 2);
+}
+
+/* This function returns the PMU idle core mask. */
+unsigned int get_pmu_idle_core_mask(void)
+{
+	return ((1 << get_tot_num_cores()) - 2);
+}
+
+/* Function to return the SoC SYS CLK */
+unsigned int get_sys_clk(void)
+{
+	return NXP_SYSCLK_FREQ;
+}
+#endif
diff --git a/plat/nxp/soc-ls1028a/soc.def b/plat/nxp/soc-ls1028a/soc.def
new file mode 100644
index 0000000..c23c1bb
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/soc.def
@@ -0,0 +1,97 @@
+#
+# Copyright 2018-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# This file contains the basic architecture definitions that drive the build
+#
+# -----------------------------------------------------------------------------
+
+CORE_TYPE	:=	a72
+
+CACHE_LINE	:=	6
+
+# Set to GIC400 or GIC500
+GIC		:=	GIC500
+
+# Set to CCI400 or CCN504 or CCN508
+INTERCONNECT	:=	CCI400
+
+# Layerscape chassis level - set to 3=LSCH3 or 2=LSCH2
+CHASSIS		:=	3_2
+
+# TZC used is TZC380 or TZC400
+TZC_ID		:=	TZC400
+
+# CONSOLE is NS16550 or PL011
+CONSOLE		:=	NS16550
+
+# DDR PHY generation to be used
+PLAT_DDR_PHY	:=	PHY_GEN1
+
+PHYS_SYS	:=	64
+
+# Max Size of CSF header. Required to define BL2 TEXT LIMIT in soc.def
+# Input to CST create_hdr_esbc tool
+CSF_HDR_SZ	:=	0x3000
+
+# In IMAGE_BL2, compile time flag for handling Cache coherency
+# with CAAM for BL2 running from OCRAM
+SEC_MEM_NON_COHERENT	:=	yes
+
+# OCRAM MAP for BL2
+# Before BL2
+# 0x18000000 - 0x18009fff -> Used by ROM code
+# 0x1800a000 - 0x1800dfff -> CSF header for BL2
+# For FlexSFlexSPI boot
+# 0x1800e000 - 0x18040000 -> Reserved for BL2 binary
+# For SD boot
+# 0x1800e000 - 0x18030000 -> Reserved for BL2 binary
+# 0x18030000 - 0x18040000 -> Reserved for SD buffer
+OCRAM_START_ADDR	:=	0x18000000
+OCRAM_SIZE		:=	0x40000
+
+# Area of OCRAM reserved by ROM code
+NXP_ROM_RSVD	:=	0xa000
+
+# Location of BL2 on OCRAM
+BL2_BASE_ADDR	:=	$(shell echo $$(( $(OCRAM_START_ADDR) + $(NXP_ROM_RSVD) + $(CSF_HDR_SZ) )))
+
+# Covert to HEX to be used by create_pbl.mk
+BL2_BASE	:=	$(shell echo "0x"$$(echo "obase=16; ${BL2_BASE_ADDR}" | bc))
+
+# BL2_HDR_LOC is at  (BL2_BASE + NXP_ROM_RSVD)
+# This value BL2_HDR_LOC + CSF_HDR_SZ should not
+# overalp with BL2_BASE
+# Input to CST create_hdr_isbc tool
+BL2_HDR_LOC	:=	0x1800A000
+
+# SoC ERRATAS to be enabled
+ERRATA_SOC_A008850	:=	1
+
+ERRATA_DDR_A009803	:=	1
+ERRATA_DDR_A009942	:=	1
+ERRATA_DDR_A010165	:=	1
+
+# Enable dynamic memory mapping
+PLAT_XLAT_TABLES_DYNAMIC	:=	1
+
+# Define Endianness of each module
+NXP_GUR_ENDIANNESS	:=	LE
+NXP_DDR_ENDIANNESS	:=	LE
+NXP_SEC_ENDIANNESS	:=	LE
+NXP_SFP_ENDIANNESS	:=	LE
+NXP_SNVS_ENDIANNESS	:=	LE
+NXP_ESDHC_ENDIANNESS	:=	LE
+NXP_QSPI_ENDIANNESS	:=	LE
+NXP_FSPI_ENDIANNESS	:=	LE
+NXP_SCFG_ENDIANNESS	:=	LE
+NXP_GPIO_ENDIANNESS	:=	LE
+
+NXP_SFP_VER		:=	3_4
+
+# OCRAM ECC Enabled
+OCRAM_ECC_EN		:=	yes
diff --git a/plat/nxp/soc-ls1028a/soc.mk b/plat/nxp/soc-ls1028a/soc.mk
new file mode 100644
index 0000000..92d8e98
--- /dev/null
+++ b/plat/nxp/soc-ls1028a/soc.mk
@@ -0,0 +1,113 @@
+#
+# Copyright 2020-2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# SoC-specific build parameters
+SOC			:=	ls1028a
+PLAT_PATH		:=	plat/nxp
+PLAT_COMMON_PATH	:=	plat/nxp/common
+PLAT_DRIVERS_PATH	:=	drivers/nxp
+PLAT_SOC_PATH		:=	${PLAT_PATH}/soc-${SOC}
+BOARD_PATH		:=	${PLAT_SOC_PATH}/${BOARD}
+
+# Get SoC-specific definitions
+include ${PLAT_SOC_PATH}/soc.def
+include ${PLAT_COMMON_PATH}/plat_make_helper/soc_common_def.mk
+include ${PLAT_COMMON_PATH}/plat_make_helper/plat_build_macros.mk
+
+ifeq (${TRUSTED_BOARD_BOOT},1)
+$(eval $(call SET_NXP_MAKE_FLAG,SMMU_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,SFP_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,SNVS_NEEDED,BL2))
+SECURE_BOOT := yes
+endif
+$(eval $(call SET_NXP_MAKE_FLAG,CRYPTO_NEEDED,BL_COMM))
+
+$(eval $(call SET_NXP_MAKE_FLAG,DCFG_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,TIMER_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,INTERCONNECT_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,GIC_NEEDED,BL31))
+$(eval $(call SET_NXP_MAKE_FLAG,CONSOLE_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,PMU_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,DDR_DRIVER_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,TZASC_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,I2C_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,IMG_LOADR_NEEDED,BL2))
+
+# Selecting PSCI & SIP_SVC support
+$(eval $(call SET_NXP_MAKE_FLAG,PSCI_NEEDED,BL31))
+$(eval $(call SET_NXP_MAKE_FLAG,SIPSVC_NEEDED,BL31))
+
+PLAT_INCLUDES		+=	-I${PLAT_COMMON_PATH}/include/default\
+				-I${BOARD_PATH}\
+				-I${PLAT_COMMON_PATH}/include/default/ch_${CHASSIS}\
+				-I${PLAT_SOC_PATH}/include\
+				-I${PLAT_COMMON_PATH}/soc_errata
+
+ifeq (${SECURE_BOOT},yes)
+include ${PLAT_COMMON_PATH}/tbbr/tbbr.mk
+endif
+
+ifeq ($(WARM_BOOT),yes)
+include ${PLAT_COMMON_PATH}/warm_reset/warm_reset.mk
+endif
+
+ifeq (${NXP_NV_SW_MAINT_LAST_EXEC_DATA}, yes)
+include ${PLAT_COMMON_PATH}/nv_storage/nv_storage.mk
+endif
+
+ifeq (${PSCI_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/psci/psci.mk
+endif
+
+ifeq (${SIPSVC_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/sip_svc/sipsvc.mk
+endif
+
+ifeq (${DDR_FIP_IO_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/fip_handler/ddr_fip/ddr_fip_io.mk
+endif
+
+# For fuse-fip & fuse-programming
+ifeq (${FUSE_PROG}, 1)
+include ${PLAT_COMMON_PATH}/fip_handler/fuse_fip/fuse.mk
+endif
+
+ifeq (${IMG_LOADR_NEEDED},yes)
+include $(PLAT_COMMON_PATH)/img_loadr/img_loadr.mk
+endif
+
+# Adding source files for the above selected drivers.
+include ${PLAT_DRIVERS_PATH}/drivers.mk
+
+# Adding SoC specific files
+include ${PLAT_COMMON_PATH}/soc_errata/errata.mk
+
+PLAT_INCLUDES		+=	${NV_STORAGE_INCLUDES}\
+				${WARM_RST_INCLUDES}
+
+BL31_SOURCES		+=	${PLAT_SOC_PATH}/$(ARCH)/${SOC}.S\
+				${WARM_RST_BL31_SOURCES}\
+				${PSCI_SOURCES}\
+				${SIPSVC_SOURCES}\
+				${PLAT_COMMON_PATH}/$(ARCH)/bl31_data.S
+
+PLAT_BL_COMMON_SOURCES	+=	${PLAT_COMMON_PATH}/$(ARCH)/ls_helpers.S\
+				${PLAT_SOC_PATH}/aarch64/${SOC}_helpers.S\
+				${NV_STORAGE_SOURCES}\
+				${WARM_RST_BL_COMM_SOURCES}\
+				${PLAT_SOC_PATH}/soc.c
+
+ifeq (${TEST_BL31}, 1)
+BL31_SOURCES	+=	${PLAT_SOC_PATH}/$(ARCH)/bootmain64.S \
+			${PLAT_SOC_PATH}/$(ARCH)/nonboot64.S
+endif
+
+BL2_SOURCES		+=	${DDR_CNTLR_SOURCES}\
+				${TBBR_SOURCES}\
+				${FUSE_SOURCES}
+
+# Adding TFA setup files
+include ${PLAT_PATH}/common/setup/common.mk
diff --git a/plat/nxp/soc-lx2160a/aarch64/lx2160a.S b/plat/nxp/soc-lx2160a/aarch64/lx2160a.S
new file mode 100644
index 0000000..4679fc2
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/aarch64/lx2160a.S
@@ -0,0 +1,1824 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+.section .text, "ax"
+
+#include <asm_macros.S>
+
+#include <lib/psci/psci.h>
+#include <nxp_timer.h>
+#include <plat_gic.h>
+#include <pmu.h>
+
+#include <bl31_data.h>
+#include <plat_psci.h>
+#include <platform_def.h>
+
+.global soc_init_start
+.global soc_init_percpu
+.global soc_init_finish
+.global _set_platform_security
+.global _soc_set_start_addr
+
+.global _soc_core_release
+.global _soc_ck_disabled
+.global _soc_core_restart
+.global _soc_core_prep_off
+.global _soc_core_entr_off
+.global _soc_core_exit_off
+.global _soc_sys_reset
+.global _soc_sys_off
+.global _soc_core_prep_stdby
+.global _soc_core_entr_stdby
+.global _soc_core_exit_stdby
+.global _soc_core_prep_pwrdn
+.global _soc_core_entr_pwrdn
+.global _soc_core_exit_pwrdn
+.global _soc_clstr_prep_stdby
+.global _soc_clstr_exit_stdby
+.global _soc_clstr_prep_pwrdn
+.global _soc_clstr_exit_pwrdn
+.global _soc_sys_prep_stdby
+.global _soc_sys_exit_stdby
+.global _soc_sys_prep_pwrdn
+.global _soc_sys_pwrdn_wfi
+.global _soc_sys_exit_pwrdn
+
+.equ TZPC_BASE,			  0x02200000
+.equ TZPCDECPROT_0_SET_BASE, 0x02200804
+.equ TZPCDECPROT_1_SET_BASE, 0x02200810
+.equ TZPCDECPROT_2_SET_BASE, 0x0220081C
+
+#define CLUSTER_3_CORES_MASK 0xC0
+#define CLUSTER_3_IN_RESET  1
+#define CLUSTER_3_NORMAL	0
+
+/* cluster 3 handling no longer based on frequency, but rather on RCW[850],
+ * which is bit 18 of RCWSR27
+ */
+#define CLUSTER_3_RCW_BIT  0x40000
+
+/* retry count for clock-stop acks */
+.equ CLOCK_RETRY_CNT,  800
+
+/* disable prefetching in the A72 core */
+#define  CPUACTLR_DIS_LS_HW_PRE	0x100000000000000
+#define  CPUACTLR_DIS_L2_TLB_PRE   0x200000
+
+/* Function starts the initialization tasks of the soc,
+ * using secondary cores if they are available
+ *
+ * Called from C, saving the non-volatile regs
+ * save these as pairs of registers to maintain the
+ * required 16-byte alignment on the stack
+ *
+ * in:
+ * out:
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, x11
+ */
+func soc_init_start
+	stp  x4,  x5,  [sp, #-16]!
+	stp  x6,  x7,  [sp, #-16]!
+	stp  x8,  x9,  [sp, #-16]!
+	stp  x10, x11, [sp, #-16]!
+	stp  x12, x13, [sp, #-16]!
+	stp  x18, x30, [sp, #-16]!
+
+	/* make sure the personality has been
+	 * established by releasing cores that
+	 * are marked "to-be-disabled" from reset
+	 */
+	bl  release_disabled  		/* 0-9 */
+
+	/* init the task flags */
+	bl  _init_task_flags   		/* 0-1 */
+
+	/* set SCRATCHRW7 to 0x0 */
+	ldr  x0, =DCFG_SCRATCHRW7_OFFSET
+	mov  x1, xzr
+	bl   _write_reg_dcfg
+
+1:
+	/* restore the aarch32/64 non-volatile registers */
+	ldp  x18, x30, [sp], #16
+	ldp  x12, x13, [sp], #16
+	ldp  x10, x11, [sp], #16
+	ldp  x8,  x9,  [sp], #16
+	ldp  x6,  x7,  [sp], #16
+	ldp  x4,  x5,  [sp], #16
+	ret
+endfunc soc_init_start
+
+
+/* Function performs any soc-specific initialization that is needed on
+ * a per-core basis.
+ * in:  none
+ * out: none
+ * uses x0, x1, x2, x3
+ */
+func soc_init_percpu
+	stp  x4,  x30,  [sp, #-16]!
+
+	bl   plat_my_core_mask
+	mov  x2, x0				/* x2 = core mask */
+
+	/* Check if this core is marked for prefetch disable
+	 */
+	mov   x0, #PREFETCH_DIS_OFFSET
+	bl	_get_global_data		/* 0-1 */
+	tst   x0, x2
+	b.eq  1f
+	bl	_disable_ldstr_pfetch_A72	/* 0 */
+1:
+	mov  x0, #NXP_PMU_ADDR
+	bl enable_timer_base_to_cluster
+	ldp  x4,  x30,  [sp], #16
+	ret
+endfunc soc_init_percpu
+
+
+/* Function completes the initialization tasks of the soc
+ * in:
+ * out:
+ * uses x0, x1, x2, x3, x4
+ */
+func soc_init_finish
+	stp  x4,  x30,  [sp, #-16]!
+
+	ldp   x4,  x30,  [sp], #16
+	ret
+endfunc soc_init_finish
+
+
+/* Function sets the security mechanisms in the SoC to implement the
+ * Platform Security Policy
+ */
+func _set_platform_security
+	mov  x8, x30
+
+#if (!SUPPRESS_TZC)
+	/* initialize the tzpc */
+	bl   init_tzpc
+#endif
+
+#if (!SUPPRESS_SEC)
+	/* initialize secmon */
+#ifdef NXP_SNVS_ENABLED
+	mov x0, #NXP_SNVS_ADDR
+	bl  init_sec_mon
+#endif
+#endif
+
+	mov  x30, x8
+	ret
+endfunc _set_platform_security
+
+
+/* Function writes a 64-bit address to bootlocptrh/l
+ * in:  x0, 64-bit address to write to BOOTLOCPTRL/H
+ * uses x0, x1, x2
+ */
+func _soc_set_start_addr
+	/* Get the 64-bit base address of the dcfg block */
+	ldr  x2, =NXP_DCFG_ADDR
+
+	/* write the 32-bit BOOTLOCPTRL register */
+	mov  x1, x0
+	str  w1, [x2, #DCFG_BOOTLOCPTRL_OFFSET]
+
+	/* write the 32-bit BOOTLOCPTRH register */
+	lsr  x1, x0, #32
+	str  w1, [x2, #DCFG_BOOTLOCPTRH_OFFSET]
+	ret
+endfunc _soc_set_start_addr
+
+/* Function releases a secondary core from reset
+ * in:   x0 = core_mask_lsb
+ * out:  none
+ * uses: x0, x1, x2, x3
+ */
+func _soc_core_release
+	mov   x3, x30
+
+	ldr  x1, =NXP_SEC_REGFILE_ADDR
+	/* write to CORE_HOLD to tell
+	 * the bootrom that this core is
+	 * expected to run.
+	 */
+	str  w0, [x1, #CORE_HOLD_OFFSET]
+
+	/* read-modify-write BRRL to release core */
+	mov  x1, #NXP_RESET_ADDR
+	ldr  w2, [x1, #BRR_OFFSET]
+
+	/* x0 = core mask */
+	orr  w2, w2, w0
+	str  w2, [x1, #BRR_OFFSET]
+	dsb  sy
+	isb
+
+	/* send event */
+	sev
+	isb
+
+	mov   x30, x3
+	ret
+endfunc _soc_core_release
+
+
+/* Function determines if a core is disabled via COREDISABLEDSR
+ * in:  w0  = core_mask_lsb
+ * out: w0  = 0, core not disabled
+ *	  w0 != 0, core disabled
+ * uses x0, x1
+ */
+func _soc_ck_disabled
+
+	/* get base addr of dcfg block */
+	ldr  x1, =NXP_DCFG_ADDR
+
+	/* read COREDISABLEDSR */
+	ldr  w1, [x1, #DCFG_COREDISABLEDSR_OFFSET]
+
+	/* test core bit */
+	and  w0, w1, w0
+
+	ret
+endfunc _soc_ck_disabled
+
+
+/* Part of CPU_ON
+ * Function restarts a core shutdown via _soc_core_entr_off
+ * in:  x0 = core mask lsb (of the target cpu)
+ * out: x0 == 0, on success
+ *	  x0 != 0, on failure
+ * uses x0, x1, x2, x3, x4, x5, x6
+ */
+func _soc_core_restart
+	mov  x6, x30
+	mov  x4, x0
+
+	/* pgm GICD_CTLR - enable secure grp0  */
+	mov  x5, #NXP_GICD_ADDR
+	ldr  w2, [x5, #GICD_CTLR_OFFSET]
+	orr  w2, w2, #GICD_CTLR_EN_GRP_0
+	str  w2, [x5, #GICD_CTLR_OFFSET]
+	dsb sy
+	isb
+
+	/* poll on RWP til write completes */
+4:
+	ldr  w2, [x5, #GICD_CTLR_OFFSET]
+	tst  w2, #GICD_CTLR_RWP
+	b.ne 4b
+
+	/* x4 = core mask lsb
+	* x5 = gicd base addr
+	*/
+	mov  x0, x4
+	bl   get_mpidr_value
+
+	/* x0 = mpidr of target core
+	* x4 = core mask lsb of target core
+	* x5 = gicd base addr
+	*/
+
+	/* generate target list bit */
+	and  x1, x0, #MPIDR_AFFINITY0_MASK
+	mov  x2, #1
+	lsl  x2, x2, x1
+
+	/* get the affinity1 field */
+	and  x1, x0, #MPIDR_AFFINITY1_MASK
+	lsl  x1, x1, #8
+	orr  x2, x2, x1
+
+	/* insert the INTID for SGI15 */
+	orr  x2, x2, #ICC_SGI0R_EL1_INTID
+
+	/* fire the SGI */
+	msr  ICC_SGI0R_EL1, x2
+	dsb  sy
+	isb
+
+	/* load '0' on success */
+	mov  x0, xzr
+
+	mov  x30, x6
+	ret
+endfunc _soc_core_restart
+
+
+/* Part of CPU_OFF
+ * Function programs SoC & GIC registers in preparation for shutting down
+ * the core
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6, x7
+ */
+func _soc_core_prep_off
+	mov  x8, x30
+	mov  x7, x0		/* x7 = core mask lsb */
+
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+
+	/* set smp and disable L2 snoops in cpuectlr */
+	orr  x1, x1, #CPUECTLR_SMPEN_EN
+	orr  x1, x1, #CPUECTLR_DISABLE_TWALK_PREFETCH
+	bic  x1, x1, #CPUECTLR_INS_PREFETCH_MASK
+	bic  x1, x1, #CPUECTLR_DAT_PREFETCH_MASK
+
+	/* set retention control in cpuectlr */
+	bic  x1, x1, #CPUECTLR_TIMER_MASK
+	orr  x1, x1, #CPUECTLR_TIMER_8TICKS
+	msr  CORTEX_A72_ECTLR_EL1, x1
+
+	/* get redistributor rd base addr for this core */
+	mov  x0, x7
+	bl   get_gic_rd_base
+	mov  x6, x0
+
+	/* get redistributor sgi base addr for this core */
+	mov  x0, x7
+	bl   get_gic_sgi_base
+	mov  x5, x0
+
+	/* x5 = gicr sgi base addr
+ 	 * x6 = gicr rd  base addr
+	 * x7 = core mask lsb
+	 */
+
+	/* disable SGI 15 at redistributor - GICR_ICENABLER0 */
+	mov  w3, #GICR_ICENABLER0_SGI15
+	str  w3, [x5, #GICR_ICENABLER0_OFFSET]
+2:
+	/* poll on rwp bit in GICR_CTLR */
+	ldr  w4, [x6, #GICR_CTLR_OFFSET]
+	tst  w4, #GICR_CTLR_RWP
+	b.ne 2b
+
+	/* disable GRP1 interrupts at cpu interface */
+	msr  ICC_IGRPEN1_EL3, xzr
+
+	/* disable GRP0 ints at cpu interface */
+	msr  ICC_IGRPEN0_EL1, xzr
+
+	/* program the redistributor - poll on GICR_CTLR.RWP as needed */
+
+	/* define SGI 15 as Grp0 - GICR_IGROUPR0 */
+	ldr  w4, [x5, #GICR_IGROUPR0_OFFSET]
+	bic  w4, w4, #GICR_IGROUPR0_SGI15
+	str  w4, [x5, #GICR_IGROUPR0_OFFSET]
+
+	/* define SGI 15 as Grp0 - GICR_IGRPMODR0 */
+	ldr  w3, [x5, #GICR_IGRPMODR0_OFFSET]
+	bic  w3, w3, #GICR_IGRPMODR0_SGI15
+	str  w3, [x5, #GICR_IGRPMODR0_OFFSET]
+
+	/* set priority of SGI 15 to highest (0x0) - GICR_IPRIORITYR3 */
+	ldr  w4, [x5, #GICR_IPRIORITYR3_OFFSET]
+	bic  w4, w4, #GICR_IPRIORITYR3_SGI15_MASK
+	str  w4, [x5, #GICR_IPRIORITYR3_OFFSET]
+
+	/* enable SGI 15 at redistributor - GICR_ISENABLER0 */
+	mov  w3, #GICR_ISENABLER0_SGI15
+	str  w3, [x5, #GICR_ISENABLER0_OFFSET]
+	dsb  sy
+	isb
+3:
+	/* poll on rwp bit in GICR_CTLR */
+	ldr  w4, [x6, #GICR_CTLR_OFFSET]
+	tst  w4, #GICR_CTLR_RWP
+	b.ne 3b
+
+	/* quiesce the debug interfaces */
+	mrs  x3, osdlr_el1
+	orr  x3, x3, #OSDLR_EL1_DLK_LOCK
+	msr  osdlr_el1, x3
+	isb
+
+	/* enable grp0 ints */
+	mov  x3, #ICC_IGRPEN0_EL1_EN
+	msr  ICC_IGRPEN0_EL1, x3
+
+	/* x5 = gicr sgi base addr
+	 * x6 = gicr rd  base addr
+	 * x7 = core mask lsb
+	 */
+
+	/* clear any pending interrupts */
+	mvn  w1, wzr
+	str  w1, [x5, #GICR_ICPENDR0_OFFSET]
+
+	/* make sure system counter is enabled */
+	ldr  x3, =NXP_TIMER_ADDR
+	ldr  w0, [x3, #SYS_COUNTER_CNTCR_OFFSET]
+	tst  w0, #SYS_COUNTER_CNTCR_EN
+	b.ne 4f
+	orr  w0, w0, #SYS_COUNTER_CNTCR_EN
+	str  w0, [x3, #SYS_COUNTER_CNTCR_OFFSET]
+4:
+	/* enable the core timer and mask timer interrupt */
+	mov  x1, #CNTP_CTL_EL0_EN
+	orr  x1, x1, #CNTP_CTL_EL0_IMASK
+	msr  cntp_ctl_el0, x1
+
+	isb
+	mov  x30, x8
+	ret
+endfunc _soc_core_prep_off
+
+
+/* Part of CPU_OFF:
+ * Function performs the final steps to shutdown the core
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5
+ */
+func _soc_core_entr_off
+	mov  x5, x30
+	mov  x4, x0
+
+1:
+	/* enter low-power state by executing wfi */
+	wfi
+
+	/* see if SGI15 woke us up */
+	mrs  x2, ICC_IAR0_EL1
+	mov  x3, #ICC_IAR0_EL1_SGI15
+	cmp  x2, x3
+	b.ne 2f
+
+	/* deactivate the intrrupts. */
+	msr ICC_EOIR0_EL1, x2
+
+2:
+	/* check if core is turned ON */
+	mov  x0, x4
+	/* Fetched the core state in x0 */
+	bl   _getCoreState
+
+	cmp  x0, #CORE_WAKEUP
+	b.ne 1b
+
+	/* Reached here, exited the wfi */
+
+	mov  x30, x5
+	ret
+endfunc _soc_core_entr_off
+
+
+/* Part of CPU_OFF:
+ * Function starts the process of starting a core back up
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6
+ */
+func _soc_core_exit_off
+	mov  x6, x30
+	mov  x5, x0
+
+	/* disable forwarding of GRP0 ints at cpu interface */
+	msr  ICC_IGRPEN0_EL1, xzr
+
+	/* get redistributor sgi base addr for this core */
+	mov  x0, x5
+	bl   get_gic_sgi_base
+	mov  x4, x0
+
+	/* x4 = gicr sgi base addr
+	 * x5 = core mask
+	 */
+
+	/* disable SGI 15 at redistributor - GICR_ICENABLER0 */
+	mov  w1, #GICR_ICENABLER0_SGI15
+	str  w1, [x4, #GICR_ICENABLER0_OFFSET]
+
+	/* get redistributor rd base addr for this core */
+	mov  x0, x5
+	bl   get_gic_rd_base
+	mov  x4, x0
+
+2:
+	/* poll on rwp bit in GICR_CTLR */
+	ldr  w2, [x4, #GICR_CTLR_OFFSET]
+	tst  w2, #GICR_CTLR_RWP
+	b.ne 2b
+
+	/* unlock the debug interfaces */
+	mrs  x3, osdlr_el1
+	bic  x3, x3, #OSDLR_EL1_DLK_LOCK
+	msr  osdlr_el1, x3
+	isb
+
+	dsb sy
+	isb
+	mov  x30, x6
+	ret
+endfunc _soc_core_exit_off
+
+
+/* Function requests a reset of the entire SOC
+ * in:  none
+ * out: none
+ * uses: x0, x1, x2, x3, x4, x5, x6
+ */
+func _soc_sys_reset
+	mov  x6, x30
+
+	ldr  x2, =NXP_RST_ADDR
+	/* clear the RST_REQ_MSK and SW_RST_REQ */
+
+	mov  w0, #0x00000000
+	str  w0, [x2, #RSTCNTL_OFFSET]
+
+	/* initiate the sw reset request */
+	mov  w0, #SW_RST_REQ_INIT
+	str  w0, [x2, #RSTCNTL_OFFSET]
+
+	/* In case this address range is mapped as cacheable,
+	 * flush the write out of the dcaches.
+	 */
+	add  x2, x2, #RSTCNTL_OFFSET
+	dc   cvac, x2
+	dsb  st
+	isb
+
+	/* Function does not return */
+	b  .
+endfunc _soc_sys_reset
+
+
+/* Part of SYSTEM_OFF:
+ * Function turns off the SoC clocks
+ * Note: Function is not intended to return, and the only allowable
+ *	   recovery is POR
+ * in:  none
+ * out: none
+ * uses x0, x1, x2, x3
+ */
+func _soc_sys_off
+
+	/* A-009810: LPM20 entry sequence might cause
+	 * spurious timeout reset request
+	 * workaround: MASK RESET REQ RPTOE
+	 */
+	ldr  x0, =NXP_RESET_ADDR
+	ldr  w1, =RSTRQMR_RPTOE_MASK
+	str  w1, [x0, #RST_RSTRQMR1_OFFSET]
+
+	/* disable sec, QBman, spi and qspi */
+	ldr  x2, =NXP_DCFG_ADDR
+	ldr  x0, =DCFG_DEVDISR1_OFFSET
+	ldr  w1, =DCFG_DEVDISR1_SEC
+	str  w1, [x2, x0]
+	ldr  x0, =DCFG_DEVDISR3_OFFSET
+	ldr  w1, =DCFG_DEVDISR3_QBMAIN
+	str  w1, [x2, x0]
+	ldr  x0, =DCFG_DEVDISR4_OFFSET
+	ldr  w1, =DCFG_DEVDISR4_SPI_QSPI
+	str  w1, [x2, x0]
+
+	/* set TPMWAKEMR0 */
+	ldr  x0, =TPMWAKEMR0_ADDR
+	mov  w1, #0x1
+	str  w1, [x0]
+
+	/* disable icache, dcache, mmu @ EL1 */
+	mov  x1, #SCTLR_I_C_M_MASK
+	mrs  x0, sctlr_el1
+	bic  x0, x0, x1
+	msr  sctlr_el1, x0
+
+	/* disable L2 prefetches */
+	mrs  x0, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_TIMER_MASK
+	orr  x0, x0, #CPUECTLR_SMPEN_EN
+	orr  x0, x0, #CPUECTLR_TIMER_8TICKS
+	msr  CORTEX_A72_ECTLR_EL1, x0
+	isb
+
+	/* disable CCN snoop domain */
+	mov  x1, #NXP_CCN_HN_F_0_ADDR
+	ldr  x0, =CCN_HN_F_SNP_DMN_CTL_MASK
+	str  x0, [x1, #CCN_HN_F_SNP_DMN_CTL_CLR_OFFSET]
+3:
+	ldr  w2, [x1, #CCN_HN_F_SNP_DMN_CTL_OFFSET]
+	cmp  w2, #0x2
+	b.ne 3b
+
+	mov  x3, #NXP_PMU_ADDR
+
+4:
+	ldr  w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp  w1, #PMU_IDLE_CORE_MASK
+	b.ne 4b
+
+	mov  w1, #PMU_IDLE_CLUSTER_MASK
+	str  w1, [x3, #PMU_CLAINACTSETR_OFFSET]
+
+1:
+	ldr  w1, [x3, #PMU_PCPW20SR_OFFSET]
+	cmp  w1, #PMU_IDLE_CORE_MASK
+	b.ne 1b
+
+	mov  w1, #PMU_FLUSH_CLUSTER_MASK
+	str  w1, [x3, #PMU_CLL2FLUSHSETR_OFFSET]
+
+2:
+	ldr  w1, [x3, #PMU_CLL2FLUSHSR_OFFSET]
+	cmp  w1, #PMU_FLUSH_CLUSTER_MASK
+	b.ne 2b
+
+	mov  w1, #PMU_FLUSH_CLUSTER_MASK
+	str  w1, [x3, #PMU_CLSL2FLUSHCLRR_OFFSET]
+
+	mov  w1, #PMU_FLUSH_CLUSTER_MASK
+	str  w1, [x3, #PMU_CLSINACTSETR_OFFSET]
+
+	mov  x2, #DAIF_SET_MASK
+	mrs  x1, spsr_el1
+	orr  x1, x1, x2
+	msr  spsr_el1, x1
+
+	mrs  x1, spsr_el2
+	orr  x1, x1, x2
+	msr  spsr_el2, x1
+
+	/* force the debug interface to be quiescent */
+	mrs  x0, osdlr_el1
+	orr  x0, x0, #0x1
+	msr  osdlr_el1, x0
+
+	/* invalidate all TLB entries at all 3 exception levels */
+	tlbi alle1
+	tlbi alle2
+	tlbi alle3
+
+	/* x3 = pmu base addr */
+
+	/* request lpm20 */
+	ldr  x0, =PMU_POWMGTCSR_OFFSET
+	ldr  w1, =PMU_POWMGTCSR_VAL
+	str  w1, [x3, x0]
+
+5:
+	wfe
+	b.eq  5b
+endfunc _soc_sys_off
+
+
+/* Part of CPU_SUSPEND
+ * Function puts the calling core into standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0
+ */
+func _soc_core_entr_stdby
+
+	dsb  sy
+	isb
+	wfi
+
+	ret
+endfunc _soc_core_entr_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+func _soc_core_prep_stdby
+
+	/* clear CORTEX_A72_ECTLR_EL1[2:0] */
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_TIMER_MASK
+	msr  CORTEX_A72_ECTLR_EL1, x1
+
+	ret
+endfunc _soc_core_prep_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_core_exit_stdby
+
+	ret
+endfunc _soc_core_exit_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_core_prep_pwrdn
+
+	/* make sure system counter is enabled */
+	ldr  x2, =NXP_TIMER_ADDR
+	ldr  w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+	tst  w0, #SYS_COUNTER_CNTCR_EN
+	b.ne 1f
+	orr  w0, w0, #SYS_COUNTER_CNTCR_EN
+	str  w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+1:
+
+	/* enable dynamic retention control (CPUECTLR[2:0])
+	 * set the SMPEN bit (CPUECTLR[6])
+	 */
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_RET_MASK
+	orr  x1, x1, #CPUECTLR_TIMER_8TICKS
+	orr  x1, x1, #CPUECTLR_SMPEN_EN
+	msr  CORTEX_A72_ECTLR_EL1, x1
+
+	isb
+	ret
+endfunc _soc_core_prep_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function puts the calling core into a power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0
+ */
+func _soc_core_entr_pwrdn
+
+	/* X0 = core mask lsb */
+
+	dsb  sy
+	isb
+	wfi
+
+	ret
+endfunc _soc_core_entr_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_core_exit_pwrdn
+
+	ret
+endfunc _soc_core_exit_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+func _soc_clstr_prep_stdby
+
+	/* clear CORTEX_A72_ECTLR_EL1[2:0] */
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_TIMER_MASK
+	msr  CORTEX_A72_ECTLR_EL1, x1
+
+	ret
+endfunc _soc_clstr_prep_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_clstr_exit_stdby
+
+	ret
+endfunc _soc_clstr_exit_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_clstr_prep_pwrdn
+
+	/* make sure system counter is enabled */
+	ldr  x2, =NXP_TIMER_ADDR
+	ldr  w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+	tst  w0, #SYS_COUNTER_CNTCR_EN
+	b.ne 1f
+	orr  w0, w0, #SYS_COUNTER_CNTCR_EN
+	str  w0, [x2, #SYS_COUNTER_CNTCR_OFFSET]
+1:
+
+	/* enable dynamic retention control (CPUECTLR[2:0])
+	 * set the SMPEN bit (CPUECTLR[6])
+	 */
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_RET_MASK
+	orr  x1, x1, #CPUECTLR_TIMER_8TICKS
+	orr  x1, x1, #CPUECTLR_SMPEN_EN
+	msr  CORTEX_A72_ECTLR_EL1, x1
+
+	isb
+	ret
+endfunc _soc_clstr_prep_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after power-down state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_clstr_exit_pwrdn
+
+	ret
+endfunc _soc_clstr_exit_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to standby
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+func _soc_sys_prep_stdby
+
+	/* clear CORTEX_A72_ECTLR_EL1[2:0] */
+	mrs  x1, CORTEX_A72_ECTLR_EL1
+	bic  x1, x1, #CPUECTLR_TIMER_MASK
+	msr  CORTEX_A72_ECTLR_EL1, x1
+	ret
+endfunc _soc_sys_prep_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after standby state
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses none
+ */
+func _soc_sys_exit_stdby
+
+	ret
+endfunc _soc_sys_exit_stdby
+
+
+/* Part of CPU_SUSPEND
+ * Function performs SoC-specific programming prior to
+ * suspend-to-power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0, x1
+ */
+func _soc_sys_prep_pwrdn
+
+	mrs   x1, CORTEX_A72_ECTLR_EL1
+	/* make sure the smp bit is set */
+	orr   x1, x1, #CPUECTLR_SMPEN_MASK
+	/* set the retention control */
+	orr   x1, x1, #CPUECTLR_RET_8CLK
+	/* disable tablewalk prefetch */
+	orr   x1, x1, #CPUECTLR_DISABLE_TWALK_PREFETCH
+	msr   CORTEX_A72_ECTLR_EL1, x1
+	isb
+
+	ret
+endfunc _soc_sys_prep_pwrdn
+
+
+/* Part of CPU_SUSPEND
+ * Function puts the calling core, and potentially the soc, into a
+ * low-power state
+ * in:  x0 = core mask lsb
+ * out: x0 = 0, success
+ *	  x0 < 0, failure
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, x11, x12, x13, x14,
+ *	  x15, x16, x17, x18, x19, x20, x21, x28
+ */
+func _soc_sys_pwrdn_wfi
+	mov  x28, x30
+
+	/* disable cluster snooping in the CCN-508 */
+	ldr  x1, =NXP_CCN_HN_F_0_ADDR
+	ldr  x7, [x1, #CCN_HN_F_SNP_DMN_CTL_OFFSET]
+	mov  x6, #CCN_HNF_NODE_COUNT
+1:
+	str  x7, [x1, #CCN_HN_F_SNP_DMN_CTL_CLR_OFFSET]
+	sub  x6, x6, #1
+	add  x1, x1, #CCN_HNF_OFFSET
+	cbnz x6, 1b
+
+	/* x0  = core mask
+	 * x7  = hnf sdcr
+	 */
+
+	ldr  x1, =NXP_PMU_CCSR_ADDR
+	ldr  x2, =NXP_PMU_DCSR_ADDR
+
+	/* enable the stop-request-override */
+	mov  x3, #PMU_POWMGTDCR0_OFFSET
+	mov  x4, #POWMGTDCR_STP_OV_EN
+	str  w4, [x2, x3]
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x7  = hnf sdcr
+	 */
+
+	/* disable prefetching in the A72 core */
+	mrs  x8, CORTEX_A72_CPUACTLR_EL1
+	tst  x8, #CPUACTLR_DIS_LS_HW_PRE
+	b.ne 2f
+	dsb  sy
+	isb
+	/* disable data prefetch */
+	orr  x16, x8, #CPUACTLR_DIS_LS_HW_PRE
+	/* disable tlb prefetch */
+	orr  x16, x16, #CPUACTLR_DIS_L2_TLB_PRE
+	msr  CORTEX_A72_CPUACTLR_EL1, x16
+	isb
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x7  = hnf sdcr
+	 * x8  = cpuactlr
+	 */
+
+2:
+	/* save hnf-sdcr and cpuactlr to stack */
+	stp  x7,  x8,  [sp, #-16]!
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 */
+
+	/* save the IPSTPCRn registers to stack */
+	mov  x15, #PMU_IPSTPCR0_OFFSET
+	ldr  w9,  [x1, x15]
+	mov  x16, #PMU_IPSTPCR1_OFFSET
+	ldr  w10, [x1, x16]
+	mov  x17, #PMU_IPSTPCR2_OFFSET
+	ldr  w11, [x1, x17]
+	mov  x18, #PMU_IPSTPCR3_OFFSET
+	ldr  w12, [x1, x18]
+	mov  x19, #PMU_IPSTPCR4_OFFSET
+	ldr  w13, [x1, x19]
+	mov  x20, #PMU_IPSTPCR5_OFFSET
+	ldr  w14, [x1, x20]
+
+	stp  x9,  x10,  [sp, #-16]!
+	stp  x11, x12,  [sp, #-16]!
+	stp  x13, x14,  [sp, #-16]!
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x15 = PMU_IPSTPCR0_OFFSET
+	 * x16 = PMU_IPSTPCR1_OFFSET
+	 * x17 = PMU_IPSTPCR2_OFFSET
+	 * x18 = PMU_IPSTPCR3_OFFSET
+	 * x19 = PMU_IPSTPCR4_OFFSET
+	 * x20 = PMU_IPSTPCR5_OFFSET
+	 */
+
+	/* load the full clock mask for IPSTPCR0 */
+	ldr  x3, =DEVDISR1_MASK
+	/* get the exclusions */
+	mov  x21, #PMU_IPPDEXPCR0_OFFSET
+	ldr  w4, [x1, x21]
+	/* apply the exclusions to the mask */
+	bic  w7, w3, w4
+	/* stop the clocks in IPSTPCR0 */
+	str  w7, [x1, x15]
+
+	/* use same procedure for IPSTPCR1-IPSTPCR5 */
+
+	/* stop the clocks in IPSTPCR1 */
+	ldr  x5, =DEVDISR2_MASK
+	mov  x21, #PMU_IPPDEXPCR1_OFFSET
+	ldr  w6, [x1, x21]
+	bic  w8, w5, w6
+	str  w8, [x1, x16]
+
+	/* stop the clocks in IPSTPCR2 */
+	ldr  x3, =DEVDISR3_MASK
+	mov  x21, #PMU_IPPDEXPCR2_OFFSET
+	ldr  w4, [x1, x21]
+	bic  w9, w3, w4
+	str  w9, [x1, x17]
+
+	/* stop the clocks in IPSTPCR3 */
+	ldr  x5,  =DEVDISR4_MASK
+	mov  x21, #PMU_IPPDEXPCR3_OFFSET
+	ldr  w6,  [x1, x21]
+	bic  w10, w5, w6
+	str  w10, [x1, x18]
+
+	/* stop the clocks in IPSTPCR4
+	 *   - exclude the ddr clocks as we are currently executing
+	 *	 out of *some* memory, might be ddr
+	 *   - exclude the OCRAM clk so that we retain any code/data in
+	 *	 OCRAM
+	 *   - may need to exclude the debug clock if we are testing
+	 */
+	ldr  x3, =DEVDISR5_MASK
+	mov  w6, #DEVDISR5_MASK_ALL_MEM
+	bic  w3, w3, w6
+
+	mov  w5, #POLICY_DEBUG_ENABLE
+	cbz  w5, 3f
+	mov  w6, #DEVDISR5_MASK_DBG
+	bic  w3, w3, w6
+3:
+	mov  x21, #PMU_IPPDEXPCR4_OFFSET
+	ldr  w4,  [x1, x21]
+	bic  w11, w3, w4
+	str  w11, [x1, x19]
+
+	/* stop the clocks in IPSTPCR5 */
+	ldr  x5,  =DEVDISR6_MASK
+	mov  x21, #PMU_IPPDEXPCR5_OFFSET
+	ldr  w6,  [x1, x21]
+	bic  w12, w5, w6
+	str  w12, [x1, x20]
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x7  = IPSTPCR0
+	 * x8  = IPSTPCR1
+	 * x9  = IPSTPCR2
+	 * x10 = IPSTPCR3
+	 * x11 = IPSTPCR4
+	 * x12 = IPSTPCR5
+	 */
+
+	/* poll until the clocks are stopped in IPSTPACKSR0 */
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR0_OFFSET
+4:
+	ldr  w5, [x1, x21]
+	cmp  w5, w7
+	b.eq 5f
+	sub  w4, w4, #1
+	cbnz w4, 4b
+
+	/* poll until the clocks are stopped in IPSTPACKSR1 */
+5:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR1_OFFSET
+6:
+	ldr  w5, [x1, x21]
+	cmp  w5, w8
+	b.eq 7f
+	sub  w4, w4, #1
+	cbnz w4, 6b
+
+	/* poll until the clocks are stopped in IPSTPACKSR2 */
+7:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR2_OFFSET
+8:
+	ldr  w5, [x1, x21]
+	cmp  w5, w9
+	b.eq 9f
+	sub  w4, w4, #1
+	cbnz w4, 8b
+
+	/* poll until the clocks are stopped in IPSTPACKSR3 */
+9:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR3_OFFSET
+10:
+	ldr  w5, [x1, x21]
+	cmp  w5, w10
+	b.eq 11f
+	sub  w4, w4, #1
+	cbnz w4, 10b
+
+	/* poll until the clocks are stopped in IPSTPACKSR4 */
+11:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR4_OFFSET
+12:
+	ldr  w5, [x1, x21]
+	cmp  w5, w11
+	b.eq 13f
+	sub  w4, w4, #1
+	cbnz w4, 12b
+
+	/* poll until the clocks are stopped in IPSTPACKSR5 */
+13:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x21, #PMU_IPSTPACKSR5_OFFSET
+14:
+	ldr  w5, [x1, x21]
+	cmp  w5, w12
+	b.eq 15f
+	sub  w4, w4, #1
+	cbnz w4, 14b
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x7  = IPSTPCR0
+	 * x8  = IPSTPCR1
+	 * x9  = IPSTPCR2
+	 * x10 = IPSTPCR3
+	 * x11 = IPSTPCR4
+	 * x12 = IPSTPCR5
+	 */
+
+15:
+	mov  x3, #NXP_DCFG_ADDR
+
+	/* save the devdisr registers to stack */
+	ldr  w13, [x3, #DCFG_DEVDISR1_OFFSET]
+	ldr  w14, [x3, #DCFG_DEVDISR2_OFFSET]
+	ldr  w15, [x3, #DCFG_DEVDISR3_OFFSET]
+	ldr  w16, [x3, #DCFG_DEVDISR4_OFFSET]
+	ldr  w17, [x3, #DCFG_DEVDISR5_OFFSET]
+	ldr  w18, [x3, #DCFG_DEVDISR6_OFFSET]
+
+	stp  x13, x14,  [sp, #-16]!
+	stp  x15, x16,  [sp, #-16]!
+	stp  x17, x18,  [sp, #-16]!
+
+	/* power down the IP in DEVDISR1 - corresponds to IPSTPCR0 */
+	str  w7,  [x3, #DCFG_DEVDISR1_OFFSET]
+
+	/* power down the IP in DEVDISR2 - corresponds to IPSTPCR1 */
+	str  w8, [x3, #DCFG_DEVDISR2_OFFSET]
+
+	/* power down the IP in DEVDISR3 - corresponds to IPSTPCR2 */
+	str  w9,  [x3, #DCFG_DEVDISR3_OFFSET]
+
+	/* power down the IP in DEVDISR4 - corresponds to IPSTPCR3 */
+	str  w10, [x3, #DCFG_DEVDISR4_OFFSET]
+
+	/* power down the IP in DEVDISR5 - corresponds to IPSTPCR4 */
+	str  w11, [x3, #DCFG_DEVDISR5_OFFSET]
+
+	/* power down the IP in DEVDISR6 - corresponds to IPSTPCR5 */
+	str  w12, [x3, #DCFG_DEVDISR6_OFFSET]
+
+	/* setup register values for the cache-only sequence */
+	mov  x4, #NXP_DDR_ADDR
+	mov  x5, #NXP_DDR2_ADDR
+	mov  x6, x11
+	mov  x7, x17
+	ldr  x12, =PMU_CLAINACTSETR_OFFSET
+	ldr  x13, =PMU_CLSINACTSETR_OFFSET
+	ldr  x14, =PMU_CLAINACTCLRR_OFFSET
+	ldr  x15, =PMU_CLSINACTCLRR_OFFSET
+
+	/* x0  = core mask
+	 * x1  = NXP_PMU_CCSR_ADDR
+	 * x2  = NXP_PMU_DCSR_ADDR
+	 * x3  = NXP_DCFG_ADDR
+	 * x4  = NXP_DDR_ADDR
+	 * x5  = NXP_DDR2_ADDR
+	 * w6  = IPSTPCR4
+	 * w7  = DEVDISR5
+	 * x12 = PMU_CLAINACTSETR_OFFSET
+	 * x13 = PMU_CLSINACTSETR_OFFSET
+	 * x14 = PMU_CLAINACTCLRR_OFFSET
+	 * x15 = PMU_CLSINACTCLRR_OFFSET
+	 */
+
+	mov  x8, #POLICY_DEBUG_ENABLE
+	cbnz x8, 29f
+	/* force the debug interface to be quiescent */
+	mrs  x9, OSDLR_EL1
+	orr  x9, x9, #0x1
+	msr  OSDLR_EL1, x9
+
+	/* enter the cache-only sequence */
+29:
+	bl   final_pwrdown
+
+	/* when we are here, the core has come out of wfi and the
+	 * ddr is back up
+	 */
+
+	mov  x8, #POLICY_DEBUG_ENABLE
+	cbnz x8, 30f
+	/* restart the debug interface */
+	mrs  x9, OSDLR_EL1
+	mov  x10, #1
+	bic  x9, x9, x10
+	msr  OSDLR_EL1, x9
+
+	/* get saved DEVDISR regs off stack */
+30:
+	ldp  x17, x18, [sp], #16
+	ldp  x15, x16, [sp], #16
+	ldp  x13, x14, [sp], #16
+	/* restore DEVDISR regs */
+	str  w18, [x3, #DCFG_DEVDISR6_OFFSET]
+	str  w17, [x3, #DCFG_DEVDISR5_OFFSET]
+	str  w16, [x3, #DCFG_DEVDISR4_OFFSET]
+	str  w15, [x3, #DCFG_DEVDISR3_OFFSET]
+	str  w14, [x3, #DCFG_DEVDISR2_OFFSET]
+	str  w13, [x3, #DCFG_DEVDISR1_OFFSET]
+	isb
+
+	/* get saved IPSTPCRn regs off stack */
+	ldp  x13, x14, [sp], #16
+	ldp  x11, x12, [sp], #16
+	ldp  x9,  x10, [sp], #16
+
+	/* restore IPSTPCRn regs */
+	mov  x15, #PMU_IPSTPCR5_OFFSET
+	str  w14, [x1, x15]
+	mov  x16, #PMU_IPSTPCR4_OFFSET
+	str  w13, [x1, x16]
+	mov  x17, #PMU_IPSTPCR3_OFFSET
+	str  w12, [x1, x17]
+	mov  x18, #PMU_IPSTPCR2_OFFSET
+	str  w11, [x1, x18]
+	mov  x19, #PMU_IPSTPCR1_OFFSET
+	str  w10, [x1, x19]
+	mov  x20, #PMU_IPSTPCR0_OFFSET
+	str  w9,  [x1, x20]
+	isb
+
+	/* poll on IPSTPACKCRn regs til IP clocks are restarted */
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR5_OFFSET
+16:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w14
+	cbz  w5, 17f
+	sub  w4, w4, #1
+	cbnz w4, 16b
+
+17:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR4_OFFSET
+18:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w13
+	cbz  w5, 19f
+	sub  w4, w4, #1
+	cbnz w4, 18b
+
+19:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR3_OFFSET
+20:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w12
+	cbz  w5, 21f
+	sub  w4, w4, #1
+	cbnz w4, 20b
+
+21:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR2_OFFSET
+22:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w11
+	cbz  w5, 23f
+	sub  w4, w4, #1
+	cbnz w4, 22b
+
+23:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR1_OFFSET
+24:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w10
+	cbz  w5, 25f
+	sub  w4, w4, #1
+	cbnz w4, 24b
+
+25:
+	mov  w4,  #CLOCK_RETRY_CNT
+	mov  x15, #PMU_IPSTPACKSR0_OFFSET
+26:
+	ldr  w5, [x1, x15]
+	and  w5, w5, w9
+	cbz  w5, 27f
+	sub  w4, w4, #1
+	cbnz w4, 26b
+
+27:
+	/* disable the stop-request-override */
+	mov  x8, #PMU_POWMGTDCR0_OFFSET
+	mov  w9, #POWMGTDCR_STP_OV_EN
+	str  w9, [x2, x8]
+	isb
+
+	/* get hnf-sdcr and cpuactlr off stack */
+	ldp  x7, x8, [sp], #16
+
+	/* restore cpuactlr */
+	msr  CORTEX_A72_CPUACTLR_EL1, x8
+	isb
+
+	/* restore snooping in the hnf nodes */
+	ldr  x9, =NXP_CCN_HN_F_0_ADDR
+	mov  x6, #CCN_HNF_NODE_COUNT
+28:
+	str  x7, [x9, #CCN_HN_F_SNP_DMN_CTL_SET_OFFSET]
+	sub  x6, x6, #1
+	add  x9, x9, #CCN_HNF_OFFSET
+	cbnz x6, 28b
+	isb
+
+	mov  x30, x28
+	ret
+endfunc _soc_sys_pwrdn_wfi
+
+
+/* Part of CPU_SUSPEND
+ * Function performs any SoC-specific cleanup after power-down
+ * in:  x0 = core mask lsb
+ * out: none
+ * uses x0,
+ */
+func _soc_sys_exit_pwrdn
+
+	mrs   x1, CORTEX_A72_ECTLR_EL1
+	/* make sure the smp bit is set */
+	orr   x1, x1, #CPUECTLR_SMPEN_MASK
+	/* clr the retention control */
+	mov   x2, #CPUECTLR_RET_8CLK
+	bic   x1, x1, x2
+	/* enable tablewalk prefetch */
+	mov   x2, #CPUECTLR_DISABLE_TWALK_PREFETCH
+	bic   x1, x1, x2
+	msr   CORTEX_A72_ECTLR_EL1, x1
+	isb
+
+	ret
+endfunc _soc_sys_exit_pwrdn
+
+
+/* Function will pwrdown ddr and the final core - it will do this
+ * by loading itself into the icache and then executing from there
+ * in:
+ *   x0  = core mask
+ *   x1  = NXP_PMU_CCSR_ADDR
+ *   x2  = NXP_PMU_DCSR_ADDR
+ *   x3  = NXP_DCFG_ADDR
+ *   x4  = NXP_DDR_ADDR
+ *   x5  = NXP_DDR2_ADDR
+ *   w6  = IPSTPCR4
+ *   w7  = DEVDISR5
+ *   x12 = PMU_CLAINACTSETR_OFFSET
+ *   x13 = PMU_CLSINACTSETR_OFFSET
+ *   x14 = PMU_CLAINACTCLRR_OFFSET
+ *   x15 = PMU_CLSINACTCLRR_OFFSET
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x13, x14, x15, x16,
+ *	  x17, x18
+ */
+
+/* 4Kb aligned */
+.align 12
+func final_pwrdown
+
+	mov  x0, xzr
+	b	touch_line_0
+start_line_0:
+	mov  x0, #1
+	/* put ddr controller 1 into self-refresh */
+	ldr  w8, [x4, #DDR_CFG_2_OFFSET]
+	orr  w8, w8, #CFG_2_FORCE_REFRESH
+	str  w8, [x4, #DDR_CFG_2_OFFSET]
+
+	/* put ddr controller 2 into self-refresh */
+	ldr  w8, [x5, #DDR_CFG_2_OFFSET]
+	orr  w8, w8, #CFG_2_FORCE_REFRESH
+	str  w8, [x5, #DDR_CFG_2_OFFSET]
+
+	/* stop the clocks in both ddr controllers */
+	mov  w10, #DEVDISR5_MASK_DDR
+	mov  x16, #PMU_IPSTPCR4_OFFSET
+	orr  w9,  w6, w10
+	str  w9,  [x1, x16]
+	isb
+
+	mov  x17, #PMU_IPSTPACKSR4_OFFSET
+touch_line_0:
+	cbz  x0, touch_line_1
+
+start_line_1:
+	/* poll IPSTPACKSR4 until
+	 * ddr controller clocks are stopped.
+	 */
+1:
+	ldr  w8, [x1, x17]
+	and  w8, w8, w10
+	cmp  w8, w10
+	b.ne 1b
+
+	/* shut down power to the ddr controllers */
+	orr w9, w7, #DEVDISR5_MASK_DDR
+	str w9, [x3, #DCFG_DEVDISR5_OFFSET]
+
+	/* disable cluster acp ports */
+	mov  w8, #CLAINACT_DISABLE_ACP
+	str  w8, [x1, x12]
+
+	/* disable skyros ports */
+	mov  w9, #CLSINACT_DISABLE_SKY
+	str  w9, [x1, x13]
+	isb
+
+touch_line_1:
+	cbz  x0, touch_line_2
+
+start_line_2:
+	isb
+3:
+	wfi
+
+	/* if we are here then we are awake
+	 * - bring this device back up
+	 */
+
+	/* enable skyros ports */
+	mov  w9, #CLSINACT_DISABLE_SKY
+	str  w9, [x1, x15]
+
+	/* enable acp ports */
+	mov  w8, #CLAINACT_DISABLE_ACP
+	str  w8, [x1, x14]
+	isb
+
+	/* bring up the ddr controllers */
+	str w7, [x3, #DCFG_DEVDISR5_OFFSET]
+	isb
+	str w6,  [x1, x16]
+	isb
+
+	nop
+touch_line_2:
+	cbz  x0, touch_line_3
+
+start_line_3:
+	/* poll IPSTPACKSR4 until
+	 * ddr controller clocks are running
+	 */
+	mov w10, #DEVDISR5_MASK_DDR
+2:
+	ldr  w8, [x1, x17]
+	and  w8, w8, w10
+	cbnz w8, 2b
+
+	/* take ddr controller 2 out of self-refresh */
+	mov w8, #CFG_2_FORCE_REFRESH
+	ldr w9, [x5, #DDR_CFG_2_OFFSET]
+	bic w9, w9, w8
+	str w9, [x5, #DDR_CFG_2_OFFSET]
+
+	/* take ddr controller 1 out of self-refresh */
+	ldr w9, [x4, #DDR_CFG_2_OFFSET]
+	bic w9, w9, w8
+	str w9, [x4, #DDR_CFG_2_OFFSET]
+	isb
+
+	nop
+	nop
+	nop
+touch_line_3:
+	cbz  x0, start_line_0
+
+	/* execute here after ddr is back up */
+
+	ret
+endfunc final_pwrdown
+
+/* Function returns CLUSTER_3_NORMAL if the cores of cluster 3 are
+ * to be handled normally, and it returns CLUSTER_3_IN_RESET if the cores
+ * are to be held in reset
+ * in:  none
+ * out: x0 = #CLUSTER_3_NORMAL,   cluster 3 treated normal
+ *	  x0 = #CLUSTER_3_IN_RESET, cluster 3 cores held in reset
+ * uses x0, x1, x2
+ */
+func cluster3InReset
+
+	/* default return is treat cores normal */
+	mov  x0, #CLUSTER_3_NORMAL
+
+	/* read RCW_SR27 register */
+	mov  x1, #NXP_DCFG_ADDR
+	ldr  w2, [x1, #RCW_SR27_OFFSET]
+
+	/* test the cluster 3 bit */
+	tst  w2, #CLUSTER_3_RCW_BIT
+	b.eq 1f
+
+	/* if we are here, then the bit was set */
+	mov  x0, #CLUSTER_3_IN_RESET
+1:
+	ret
+endfunc cluster3InReset
+
+
+/* Function checks to see if cores which are to be disabled have been
+ * released from reset - if not, it releases them
+ * Note: there may be special handling of cluster 3 cores depending upon the
+ *	   sys clk frequency
+ * in:  none
+ * out: none
+ * uses x0, x1, x2, x3, x4, x5, x6, x7, x8, x9
+ */
+func release_disabled
+	mov  x9, x30
+
+	/* check if we need to keep cluster 3 cores in reset */
+	bl   cluster3InReset		/*  0-2  */
+	mov  x8, x0
+
+	/* x8 = cluster 3 handling */
+
+	/* read COREDISABLESR */
+	mov  x0, #NXP_DCFG_ADDR
+	ldr  w4, [x0, #DCFG_COREDISABLEDSR_OFFSET]
+	cmp  x8, #CLUSTER_3_IN_RESET
+	b.ne 4f
+
+	/* the cluster 3 cores are to be held in reset, so remove
+	 * them from the disable mask
+	 */
+	bic  x4, x4, #CLUSTER_3_CORES_MASK
+4:
+	/* get the number of cpus on this device */
+	mov   x6, #PLATFORM_CORE_COUNT
+
+	mov  x0, #NXP_RESET_ADDR
+	ldr  w5, [x0, #BRR_OFFSET]
+
+	/* load the core mask for the first core */
+	mov  x7, #1
+
+	/* x4 = COREDISABLESR
+	 * x5 = BRR
+	 * x6 = loop count
+	 * x7 = core mask bit
+	 */
+2:
+	/* check if the core is to be disabled */
+	tst  x4, x7
+	b.eq 1f
+
+	/* see if disabled cores have already been released from reset */
+	tst  x5, x7
+	b.ne 5f
+
+	/* if core has not been released, then release it (0-3) */
+	mov  x0, x7
+	bl   _soc_core_release
+
+	/* record the core state in the data area (0-3) */
+	mov  x0, x7
+	mov  x1, #CORE_STATE_DATA
+	mov  x2, #CORE_DISABLED
+	bl   _setCoreData
+
+1:
+	/* see if this is a cluster 3 core */
+	mov   x3, #CLUSTER_3_CORES_MASK
+	tst   x3, x7
+	b.eq  5f
+
+	/* this is a cluster 3 core - see if it needs to be held in reset */
+	cmp  x8, #CLUSTER_3_IN_RESET
+	b.ne 5f
+
+	/* record the core state as disabled in the data area (0-3) */
+	mov  x0, x7
+	mov  x1, #CORE_STATE_DATA
+	mov  x2, #CORE_DISABLED
+	bl   _setCoreData
+
+5:
+	/* decrement the counter */
+	subs  x6, x6, #1
+	b.le  3f
+
+	/* shift the core mask to the next core */
+	lsl   x7, x7, #1
+	/* continue */
+	b	 2b
+3:
+	cmp  x8, #CLUSTER_3_IN_RESET
+	b.ne 6f
+
+	/* we need to hold the cluster 3 cores in reset,
+	 * so mark them in the COREDISR and COREDISABLEDSR registers as
+	 * "disabled", and the rest of the sw stack will leave them alone
+	 * thinking that they have been disabled
+	 */
+	mov  x0, #NXP_DCFG_ADDR
+	ldr  w1, [x0, #DCFG_COREDISR_OFFSET]
+	orr  w1, w1, #CLUSTER_3_CORES_MASK
+	str  w1, [x0, #DCFG_COREDISR_OFFSET]
+
+	ldr  w2, [x0, #DCFG_COREDISABLEDSR_OFFSET]
+	orr  w2, w2, #CLUSTER_3_CORES_MASK
+	str  w2, [x0, #DCFG_COREDISABLEDSR_OFFSET]
+	dsb  sy
+	isb
+
+#if (PSCI_TEST)
+	/* x0 = NXP_DCFG_ADDR : read COREDISABLESR */
+	ldr  w4, [x0, #DCFG_COREDISABLEDSR_OFFSET]
+	/* read COREDISR */
+	ldr  w3, [x0, #DCFG_COREDISR_OFFSET]
+#endif
+
+6:
+	mov  x30, x9
+	ret
+
+endfunc release_disabled
+
+
+/* Function setc up the TrustZone Address Space Controller (TZASC)
+ * in:  none
+ * out: none
+ * uses x0, x1
+ */
+func init_tzpc
+
+	/* set Non Secure access for all devices protected via TZPC */
+
+	/* decode Protection-0 Set Reg */
+	ldr	x1, =TZPCDECPROT_0_SET_BASE
+	/* set decode region to NS, Bits[7:0] */
+	mov	w0, #0xFF
+	str	w0, [x1]
+
+	/* decode Protection-1 Set Reg */
+	ldr	x1, =TZPCDECPROT_1_SET_BASE
+	/* set decode region to NS, Bits[7:0] */
+	mov	w0, #0xFF
+	str	w0, [x1]
+
+	/* decode Protection-2 Set Reg */
+	ldr	x1, =TZPCDECPROT_2_SET_BASE
+	/* set decode region to NS, Bits[7:0] */
+	mov	w0, #0xFF
+	str	w0, [x1]
+
+	/* entire SRAM as NS */
+	/* secure RAM region size Reg */
+	ldr	x1, =TZPC_BASE
+	/* 0x00000000 = no secure region */
+	mov	w0, #0x00000000
+	str	w0, [x1]
+
+	ret
+endfunc init_tzpc
+
+/* write a register in the DCFG block
+ * in:  x0 = offset
+ * in:  w1 = value to write
+ * uses x0, x1, x2
+ */
+func _write_reg_dcfg
+	ldr  x2, =NXP_DCFG_ADDR
+	str  w1, [x2, x0]
+	ret
+endfunc _write_reg_dcfg
+
+
+/* read a register in the DCFG block
+ * in:  x0 = offset
+ * out: w0 = value read
+ * uses x0, x1, x2
+ */
+func _read_reg_dcfg
+	ldr  x2, =NXP_DCFG_ADDR
+	ldr  w1, [x2, x0]
+	mov  w0, w1
+	ret
+endfunc _read_reg_dcfg
+
+
+/* Function returns an mpidr value for a core, given a core_mask_lsb
+ * in:  x0 = core mask lsb
+ * out: x0 = affinity2:affinity1:affinity0, where affinity is 8-bits
+ * uses x0, x1
+ */
+func get_mpidr_value
+
+	/* convert a core mask to an SoC core number */
+	clz  w0, w0
+	mov  w1, #31
+	sub  w0, w1, w0
+
+	/* get the mpidr core number from the SoC core number */
+	mov  w1, wzr
+	tst  x0, #1
+	b.eq 1f
+	orr  w1, w1, #1
+
+1:
+	/* extract the cluster number */
+	lsr  w0, w0, #1
+	orr  w0, w1, w0, lsl #8
+
+	ret
+endfunc get_mpidr_value
+
+
+/* Function returns the redistributor base address for the core specified
+ * in x1
+ * in:  x0 - core mask lsb of specified core
+ * out: x0 = redistributor rd base address for specified core
+ * uses x0, x1, x2
+ */
+func get_gic_rd_base
+	clz  w1, w0
+	mov  w2, #0x20
+	sub  w2, w2, w1
+	sub  w2, w2, #1
+
+	ldr  x0, =NXP_GICR_ADDR
+	mov  x1, #GIC_RD_OFFSET
+
+	/* x2 = core number
+	 * loop counter
+	 */
+2:
+	cbz  x2, 1f
+	add  x0, x0, x1
+	sub  x2, x2, #1
+	b	2b
+1:
+	ret
+endfunc get_gic_rd_base
+
+
+/* Function returns the redistributor base address for the core specified
+ * in x1
+ * in:  x0 - core mask lsb of specified core
+ * out: x0 = redistributor sgi base address for specified core
+ * uses x0, x1, x2
+ */
+func get_gic_sgi_base
+	clz  w1, w0
+	mov  w2, #0x20
+	sub  w2, w2, w1
+	sub  w2, w2, #1
+
+	ldr  x0, =NXP_GICR_SGI_ADDR
+	mov  x1, #GIC_SGI_OFFSET
+
+	/* loop counter */
+2:
+	cbz  x2, 1f		/* x2 = core number */
+	add  x0, x0, x1
+	sub  x2, x2, #1
+	b	2b
+1:
+	ret
+endfunc get_gic_sgi_base
+
+/* Function writes a register in the RESET block
+ * in:  x0 = offset
+ * in:  w1 = value to write
+ * uses x0, x1, x2
+ */
+func _write_reg_reset
+	ldr  x2, =NXP_RESET_ADDR
+	str  w1, [x2, x0]
+	ret
+endfunc _write_reg_reset
+
+
+/* Function reads a register in the RESET block
+ * in:  x0 = offset
+ * out: w0 = value read
+ * uses x0, x1
+ */
+func _read_reg_reset
+	ldr  x1, =NXP_RESET_ADDR
+	ldr  w0, [x1, x0]
+	ret
+endfunc _read_reg_reset
diff --git a/plat/nxp/soc-lx2160a/aarch64/lx2160a_helpers.S b/plat/nxp/soc-lx2160a/aarch64/lx2160a_helpers.S
new file mode 100644
index 0000000..c364dec
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/aarch64/lx2160a_helpers.S
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+
+#include <platform_def.h>
+
+.globl	plat_secondary_cold_boot_setup
+.globl	plat_is_my_cpu_primary
+.globl	plat_reset_handler
+.globl  platform_mem_init
+
+
+func platform_mem1_init
+	ret
+endfunc platform_mem1_init
+
+
+func platform_mem_init
+	ret
+endfunc	platform_mem_init
+
+
+func apply_platform_errata
+
+	ret
+endfunc apply_platform_errata
+
+
+func plat_reset_handler
+	mov x29, x30
+	bl  apply_platform_errata
+
+#if defined(IMAGE_BL31)
+	ldr x0, =POLICY_SMMU_PAGESZ_64K
+	cbz x0, 1f
+	/* Set the SMMU page size in the sACR register */
+	bl _set_smmu_pagesz_64
+#endif
+1:
+	mov x30, x29
+
+	ret
+endfunc plat_reset_handler
+
+
+/* void plat_secondary_cold_boot_setup (void);
+ *
+ * This function performs any platform specific actions
+ * needed for a secondary cpu after a cold reset e.g
+ * mark the cpu's presence, mechanism to place it in a
+ * holding pen etc.
+ */
+func plat_secondary_cold_boot_setup
+	/* lx2160a does not do cold boot for secondary CPU */
+cb_panic:
+	b	cb_panic
+endfunc plat_secondary_cold_boot_setup
+
+
+/* unsigned int plat_is_my_cpu_primary (void);
+ *
+ * Find out whether the current cpu is the primary
+ * cpu.
+ */
+func plat_is_my_cpu_primary
+	mrs	x0, mpidr_el1
+	and	x0, x0, #(MPIDR_CLUSTER_MASK | MPIDR_CPU_MASK)
+	cmp	x0, 0x0
+	cset	w0, eq
+	ret
+endfunc plat_is_my_cpu_primary
diff --git a/plat/nxp/soc-lx2160a/aarch64/lx2160a_warm_rst.S b/plat/nxp/soc-lx2160a/aarch64/lx2160a_warm_rst.S
new file mode 100644
index 0000000..9dec3f2
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/aarch64/lx2160a_warm_rst.S
@@ -0,0 +1,229 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+.section .text, "ax"
+
+#include <asm_macros.S>
+
+#ifndef NXP_COINED_BB
+#include <flash_info.h>
+#include <fspi.h>
+#endif
+#include <regs.h>
+#ifdef NXP_COINED_BB
+#include <snvs.h>
+#endif
+
+#include <plat_warm_rst.h>
+#include <platform_def.h>
+
+#define SDRAM_CFG	0x110
+#define SDRAM_CFG_2	0x114
+#define SDRAM_MD_CNTL	0x120
+#define SDRAM_INTERVAL	0x124
+#define TIMING_CFG_10	0x258
+#define DEBUG_2		0xF04
+#define DEBUG_26	0xF64
+#define DDR_DSR2	0xB24
+
+#define DDR_CNTRLR_2	0x2
+#define COUNT_100	1000
+
+	.globl	_soc_sys_warm_reset
+	.align 12
+
+func _soc_sys_warm_reset
+	mov  x3, xzr
+	b    touch_line0
+start_line0:
+	mov  x3, #1
+	mov  x2, #NUM_OF_DDRC
+	ldr x1, =NXP_DDR_ADDR
+1:
+	ldr w0, [x1, #SDRAM_CFG]
+	orr w0, w0, #SDRAM_CFG_MEM_HLT
+	str w0, [x1, #SDRAM_CFG]
+2:
+	ldr w0, [x1, #DEBUG_2]
+	and w0, w0, #DDR_DBG_2_MEM_IDLE
+	cbz w0, 2b
+
+	ldr w0, [x1, #DEBUG_26]
+	orr w0, w0, #DDR_DEBUG_26_BIT_12
+	orr w0, w0, #DDR_DEBUG_26_BIT_13
+	orr w0, w0, #DDR_DEBUG_26_BIT_14
+touch_line0:
+	cbz x3, touch_line1
+
+	orr w0, w0, #DDR_DEBUG_26_BIT_15
+	orr w0, w0, #DDR_DEBUG_26_BIT_16
+	str w0, [x1, #DEBUG_26]
+
+	ldr w0, [x1, #SDRAM_CFG_2]
+	orr w0, w0, #SDRAM_CFG2_FRC_SR
+	str w0,  [x1, #SDRAM_CFG_2]
+
+3:
+	ldr w0, [x1, #DDR_DSR2]
+	orr w0, w0, #DDR_DSR_2_PHY_INIT_CMPLT
+	str w0, [x1, #DDR_DSR2]
+	ldr w0, [x1, #DDR_DSR2]
+        and w0, w0, #DDR_DSR_2_PHY_INIT_CMPLT
+	cbnz w0, 3b
+
+	ldr w0, [x1, #SDRAM_INTERVAL]
+	and w0, w0, #SDRAM_INTERVAL_REFINT_CLEAR
+	str w0, [x1, #SDRAM_INTERVAL]
+touch_line1:
+	cbz x3, touch_line2
+
+	ldr w0, [x1, #SDRAM_MD_CNTL]
+	orr w0, w0, #MD_CNTL_CKE(1)
+	orr w0, w0, #MD_CNTL_MD_EN
+	str w0, [x1, #SDRAM_MD_CNTL]
+
+	ldr w0, [x1, #TIMING_CFG_10]
+	orr w0, w0, #DDR_TIMING_CFG_10_T_STAB
+	str w0, [x1, #TIMING_CFG_10]
+
+	ldr w0, [x1, #SDRAM_CFG_2]
+	and w0, w0, #SDRAM_CFG2_FRC_SR_CLEAR
+	str w0, [x1, #SDRAM_CFG_2]
+
+4:
+	ldr w0, [x1, #DDR_DSR2]
+        and w0, w0, #DDR_DSR_2_PHY_INIT_CMPLT
+        cbz w0, 4b
+	nop
+touch_line2:
+	cbz x3, touch_line3
+
+	ldr w0, [x1, #DEBUG_26]
+	orr w0, w0, #DDR_DEBUG_26_BIT_25
+	and w0, w0, #DDR_DEBUG_26_BIT_24_CLEAR
+	str w0, [x1, #DEBUG_26]
+
+	cmp x2, #DDR_CNTRLR_2
+	b.ne 5f
+	ldr x1, =NXP_DDR2_ADDR
+	mov x2, xzr
+	b 1b
+
+5:
+	mov x5, xzr
+6:
+	add x5, x5, #1
+	cmp x5, #COUNT_100
+	b.ne 6b
+	nop
+touch_line3:
+	cbz x3, touch_line4
+#ifdef NXP_COINED_BB
+        ldr  x1, =NXP_SNVS_ADDR
+        ldr  w0, [x1, #NXP_APP_DATA_LP_GPR_OFFSET]
+
+	/* On Warm Boot is enabled, then zeroth bit
+	 * of SNVS LP GPR register 0 will used
+	 * to save the status of warm-reset as a cause.
+	 */
+        orr  w0, w0, #(1 << NXP_LPGPR_ZEROTH_BIT)
+
+        /* write back */
+        str  w0, [x1, #NXP_APP_DATA_LP_GPR_OFFSET]
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+touch_line4:
+	cbz x3, touch_line6
+#elif !(ERLY_WRM_RST_FLG_FLSH_UPDT)
+        ldr  x1, =NXP_FLEXSPI_ADDR
+        ldr  w0, [x1, #FSPI_IPCMD]
+        orr  w0, w0, #FSPI_IPCMD_TRG_MASK
+        str  w0, [x1, #FSPI_IPCMD]
+7:
+        ldr  w0, [x1, #FSPI_INTR]
+        and  w0, w0, #FSPI_INTR_IPCMDDONE_MASK
+        cmp  w0, #0
+        b.eq 7b
+
+        ldr  w0, [x1, #FSPI_IPTXFCR]
+        orr  w0, w0, #FSPI_IPTXFCR_CLR
+        str  w0, [x1, #FSPI_IPTXFCR]
+
+        ldr  w0, [x1, #FSPI_INTR]
+        orr  w0, w0, #FSPI_INTR_IPCMDDONE_MASK
+        str  w0, [x1, #FSPI_INTR]
+	nop
+touch_line4:
+        cbz x3, touch_line5
+        /* flexspi driver has an api
+         * is_flash_busy().
+         * Impelementation of the api will not
+         * fit-in in 1 cache line.
+         * instead a nop-cycles are introduced to
+         * simulate the wait time for flash write
+         * completion.
+         *
+         * Note: This wait time varies from flash to flash.
+         */
+
+        mov    x0, #FLASH_WR_COMP_WAIT_BY_NOP_COUNT
+8:
+        sub x0, x0, #1
+        nop
+        cmp x0, #0
+        b.ne    8b
+        nop
+        nop
+        nop
+        nop
+        nop
+        nop
+        nop
+        nop
+        nop
+touch_line5:
+        cbz x3, touch_line6
+#endif
+        ldr  x2, =NXP_RST_ADDR
+	/* clear the RST_REQ_MSK and SW_RST_REQ */
+	mov  w0, #0x00000000
+	str  w0, [x2, #RSTCNTL_OFFSET]
+
+	/* initiate the sw reset request */
+	mov  w0, #SW_RST_REQ_INIT
+        str  w0, [x2, #RSTCNTL_OFFSET]
+
+        /* In case this address range is mapped as cacheable,
+         * flush the write out of the dcaches.
+         */
+        add  x2, x2, #RSTCNTL_OFFSET
+        dc   cvac, x2
+        dsb  st
+        isb
+
+        /* Function does not return */
+        b  .
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+	nop
+touch_line6:
+	cbz x3, start_line0
+
+endfunc _soc_sys_warm_reset
diff --git a/plat/nxp/soc-lx2160a/ddr_fip.mk b/plat/nxp/soc-lx2160a/ddr_fip.mk
new file mode 100644
index 0000000..f14a9e8
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/ddr_fip.mk
@@ -0,0 +1,97 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+DDR_PHY_BIN_PATH	?=	./ddr-phy-binary/lx2160a
+
+ifeq (${DDR_IMEM_UDIMM_1D},)
+    DDR_IMEM_UDIMM_1D	:=	${DDR_PHY_BIN_PATH}/ddr4_pmu_train_imem.bin
+endif
+
+ifeq (${DDR_IMEM_UDIMM_2D},)
+    DDR_IMEM_UDIMM_2D	:=	${DDR_PHY_BIN_PATH}/ddr4_2d_pmu_train_imem.bin
+endif
+
+ifeq (${DDR_DMEM_UDIMM_1D},)
+    DDR_DMEM_UDIMM_1D	:=	${DDR_PHY_BIN_PATH}/ddr4_pmu_train_dmem.bin
+endif
+
+ifeq (${DDR_DMEM_UDIMM_2D},)
+    DDR_DMEM_UDIMM_2D	:=	${DDR_PHY_BIN_PATH}/ddr4_2d_pmu_train_dmem.bin
+endif
+
+ifeq (${DDR_IMEM_RDIMM_1D},)
+    DDR_IMEM_RDIMM_1D	:=	${DDR_PHY_BIN_PATH}/ddr4_rdimm_pmu_train_imem.bin
+endif
+
+ifeq (${DDR_IMEM_RDIMM_2D},)
+    DDR_IMEM_RDIMM_2D	:=	${DDR_PHY_BIN_PATH}/ddr4_rdimm2d_pmu_train_imem.bin
+endif
+
+ifeq (${DDR_DMEM_RDIMM_1D},)
+    DDR_DMEM_RDIMM_1D	:=	${DDR_PHY_BIN_PATH}/ddr4_rdimm_pmu_train_dmem.bin
+endif
+
+ifeq (${DDR_DMEM_RDIMM_2D},)
+    DDR_DMEM_RDIMM_2D	:=	${DDR_PHY_BIN_PATH}/ddr4_rdimm2d_pmu_train_dmem.bin
+endif
+
+$(shell mkdir -p '${BUILD_PLAT}')
+
+ifeq (${DDR_FIP_NAME},)
+ifeq (${TRUSTED_BOARD_BOOT},1)
+	DDR_FIP_NAME	:= ddr_fip_sec.bin
+else
+	DDR_FIP_NAME	:= ddr_fip.bin
+endif
+endif
+
+ifneq (${TRUSTED_BOARD_BOOT},1)
+
+DDR_FIP_ARGS += --ddr-immem-udimm-1d ${DDR_IMEM_UDIMM_1D} \
+		--ddr-immem-udimm-2d ${DDR_IMEM_UDIMM_2D} \
+		--ddr-dmmem-udimm-1d ${DDR_DMEM_UDIMM_1D} \
+		--ddr-dmmem-udimm-2d ${DDR_DMEM_UDIMM_2D} \
+		--ddr-immem-rdimm-1d ${DDR_IMEM_RDIMM_1D} \
+		--ddr-immem-rdimm-2d ${DDR_IMEM_RDIMM_2D} \
+		--ddr-dmmem-rdimm-1d ${DDR_DMEM_RDIMM_1D} \
+		--ddr-dmmem-rdimm-2d ${DDR_DMEM_RDIMM_2D}
+endif
+
+
+ifeq (${TRUSTED_BOARD_BOOT},1)
+ifeq (${MBEDTLS_DIR},)
+include plat/nxp/soc-lx2160a/ddr_sb.mk
+else
+include plat/nxp/soc-lx2160a/ddr_tbbr.mk
+
+# Variables for use with Certificate Generation Tool
+CRTTOOLPATH	?=	tools/cert_create
+CRTTOOL		?=	${CRTTOOLPATH}/cert_create${BIN_EXT}
+
+ifneq (${GENERATE_COT},0)
+ddr_certificates: ${DDR_CRT_DEPS} ${CRTTOOL}
+	${Q}${CRTTOOL} ${DDR_CRT_ARGS}
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@echo "DDR certificates can be found in ${BUILD_PLAT}"
+	@${ECHO_BLANK_LINE}
+endif
+endif
+endif
+
+# Variables for use with Firmware Image Package
+FIPTOOLPATH	?=	tools/fiptool
+FIPTOOL		?=	${FIPTOOLPATH}/fiptool${BIN_EXT}
+
+${BUILD_PLAT}/${DDR_FIP_NAME}: ${DDR_FIP_DEPS} ${FIPTOOL}
+	$(eval ${CHECK_DDR_FIP_CMD})
+	${Q}${FIPTOOL} create ${DDR_FIP_ARGS} $@
+	${Q}${FIPTOOL} info $@
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@${ECHO_BLANK_LINE}
+
+fip_ddr: ${BUILD_PLAT}/${DDR_FIP_NAME}
diff --git a/plat/nxp/soc-lx2160a/ddr_sb.mk b/plat/nxp/soc-lx2160a/ddr_sb.mk
new file mode 100644
index 0000000..c11651e
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/ddr_sb.mk
@@ -0,0 +1,43 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifneq (${TRUSTED_BOARD_BOOT},0)
+
+ifeq (${GENERATE_COT},0)
+
+DDR_FIP_ARGS += --ddr-immem-udimm-1d ${DDR_IMEM_UDIMM_1D}.sb \
+		--ddr-immem-udimm-2d ${DDR_IMEM_UDIMM_2D}.sb \
+		--ddr-dmmem-udimm-1d ${DDR_DMEM_UDIMM_1D}.sb \
+		--ddr-dmmem-udimm-2d ${DDR_DMEM_UDIMM_2D}.sb \
+		--ddr-immem-rdimm-1d ${DDR_IMEM_RDIMM_1D}.sb \
+		--ddr-immem-rdimm-2d ${DDR_IMEM_RDIMM_2D}.sb \
+		--ddr-dmmem-rdimm-1d ${DDR_DMEM_RDIMM_1D}.sb \
+		--ddr-dmmem-rdimm-2d ${DDR_DMEM_RDIMM_2D}.sb
+endif
+
+UDIMM_DEPS = ${DDR_IMEM_UDIMM_1D}.sb ${DDR_IMEM_UDIMM_2D}.sb ${DDR_DMEM_UDIMM_1D}.sb ${DDR_DMEM_UDIMM_2D}.sb
+RDIMM_DEPS = ${DDR_IMEM_RDIMM_1D}.sb ${DDR_IMEM_RDIMM_2D}.sb ${DDR_DMEM_RDIMM_1D}.sb ${DDR_DMEM_RDIMM_2D}.sb
+DDR_FIP_DEPS += ${UDIMM_DEPS}
+DDR_FIP_DEPS += ${RDIMM_DEPS}
+
+# Max Size of CSF header (CSF_HDR_SZ = 0x3000).
+# Image will be appended at this offset of the header.
+# Path to CST directory is required to generate the CSF header,
+# and prepend it to image before fip image gets generated
+ifeq (${CST_DIR},)
+  $(error Error: CST_DIR not set)
+endif
+
+ifeq (${DDR_INPUT_FILE},)
+DDR_INPUT_FILE:= drivers/nxp/auth/csf_hdr_parser/${CSF_FILE}
+endif
+
+%.sb: %
+	@echo " Generating CSF Header for $@ $<"
+	$(CST_DIR)/create_hdr_esbc --in $< --out $@ --app_off ${CSF_HDR_SZ} \
+					--app $< ${DDR_INPUT_FILE}
+
+endif
diff --git a/plat/nxp/soc-lx2160a/ddr_tbbr.mk b/plat/nxp/soc-lx2160a/ddr_tbbr.mk
new file mode 100644
index 0000000..deb475b
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/ddr_tbbr.mk
@@ -0,0 +1,95 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# This file defines the keys and certificates that must be created to establish
+# a Chain of Trust for the DDR FW. These definitions include the
+# command line options passed to the cert_create and fiptool commands for DDR FW.
+# A DDR FW key is used for signing the DDR Firmware. The DDR key is authenticated
+# by the Trusted World Key. Two content certificates are created:
+# For DDR RDIMM Images [ signed by DDR FW Key]
+# For DDR UDIMM Images [ signed by DDR FW Key]
+#
+# Expected environment:
+#
+#   BUILD_PLAT: output directory
+#
+# Build options added by this file:
+#
+#   KEY_ALG
+#   KEY_SIZE
+#   TRUSTED_WORLD_KEY
+#   NON_TRUSTED_WORLD_KEY
+#
+
+# Copy the tbbr.mk from PLAT_TOOL_PATH/cert_create_helper
+# to the ${PLAT_DIR}. So that cert_create is enabled
+# to create certificates for DDR
+$(shell cp ${PLAT_TOOL_PATH}/cert_create_helper/cert_create_tbbr.mk ${PLAT_DIR})
+
+# Certificate generation tool default parameters
+DDR_FW_CERT		:=	${BUILD_PLAT}/ddr_fw_key_cert.crt
+
+# Default non-volatile counter values (overridable by the platform)
+TFW_NVCTR_VAL		?=	0
+NTFW_NVCTR_VAL		?=	0
+
+# Pass the non-volatile counters to the cert_create tool
+$(eval $(call CERT_ADD_CMD_OPT,${TFW_NVCTR_VAL},--tfw-nvctr,DDR_))
+
+$(shell mkdir -p '${BUILD_PLAT}')
+
+ifeq (${DDR_KEY},)
+DDR_KEY=${BUILD_PLAT}/ddr.pem
+endif
+
+ifeq (${TRUSTED_KEY_CERT},)
+$(info Generating: Trusted key certificate as part of DDR cert creation)
+TRUSTED_KEY_CERT	:=	${BUILD_PLAT}/trusted_key.crt
+$(eval $(call TOOL_ADD_PAYLOAD,${TRUSTED_KEY_CERT},--trusted-key-cert,))
+$(eval $(call TOOL_ADD_PAYLOAD,${TRUSTED_KEY_CERT},--trusted-key-cert,,DDR_))
+else
+$(info Using: Trusted key certificate as part of DDR cert creation)
+DDR_FIP_ARGS += --trusted-key-cert ${TRUSTED_KEY_CERT}
+endif
+
+# Add the keys to the cert_create command line options (private keys are NOT
+# packed in the FIP). Developers can use their own keys by specifying the proper
+# build option in the command line when building the Trusted Firmware
+$(if ${KEY_ALG},$(eval $(call CERT_ADD_CMD_OPT,${KEY_ALG},--key-alg,DDR_)))
+$(if ${KEY_SIZE},$(eval $(call CERT_ADD_CMD_OPT,${KEY_SIZE},--key-size,DDR_)))
+$(if ${HASH_ALG},$(eval $(call CERT_ADD_CMD_OPT,${HASH_ALG},--hash-alg,DDR_)))
+$(if ${ROT_KEY},$(eval $(call CERT_ADD_CMD_OPT,${ROT_KEY},--rot-key,DDR_)))
+$(if ${TRUSTED_WORLD_KEY},$(eval $(call CERT_ADD_CMD_OPT,${TRUSTED_WORLD_KEY},--trusted-world-key,DDR_)))
+$(if ${NON_TRUSTED_WORLD_KEY},$(eval $(call CERT_ADD_CMD_OPT,${NON_TRUSTED_WORLD_KEY},--non-trusted-world-key, DDR_)))
+
+# Add the DDR CoT (key cert + img cert)
+$(if ${DDR_KEY},$(eval $(call CERT_ADD_CMD_OPT,${DDR_KEY},--ddr-fw-key,DDR_)))
+$(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/ddr_fw_key.crt,--ddr-fw-key-cert,,DDR_))
+$(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/ddr_udimm_fw_content.crt,--ddr-udimm-fw-cert,,DDR_))
+$(eval $(call TOOL_ADD_PAYLOAD,${BUILD_PLAT}/ddr_rdimm_fw_content.crt,--ddr-rdimm-fw-cert,,DDR_))
+
+$(eval $(call TOOL_ADD_IMG,DDR_IMEM_UDIMM_1D,--ddr-immem-udimm-1d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_IMEM_UDIMM_2D,--ddr-immem-udimm-2d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_DMEM_UDIMM_1D,--ddr-dmmem-udimm-1d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_DMEM_UDIMM_2D,--ddr-dmmem-udimm-2d,DDR_))
+
+$(eval $(call TOOL_ADD_IMG,DDR_IMEM_RDIMM_1D,--ddr-immem-rdimm-1d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_IMEM_RDIMM_2D,--ddr-immem-rdimm-2d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_DMEM_RDIMM_1D,--ddr-dmmem-rdimm-1d,DDR_))
+$(eval $(call TOOL_ADD_IMG,DDR_DMEM_RDIMM_2D,--ddr-dmmem-rdimm-2d,DDR_))
+
+DDR_FIP_DEPS += ddr_certificates
+
+# Process TBB related flags
+ifneq (${GENERATE_COT},0)
+        # Common cert_create options
+        ifneq (${CREATE_KEYS},0)
+                $(eval DDR_CRT_ARGS += -n)
+                ifneq (${SAVE_KEYS},0)
+                       $(eval DDR_CRT_ARGS += -k)
+                endif
+        endif
+endif
diff --git a/plat/nxp/soc-lx2160a/include/soc.h b/plat/nxp/soc-lx2160a/include/soc.h
new file mode 100644
index 0000000..7cc4a03
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/include/soc.h
@@ -0,0 +1,141 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef _SOC_H
+#define	_SOC_H
+
+/* Chassis specific defines - common across SoC's of a particular platform */
+#include <dcfg_lsch3.h>
+#include <soc_default_base_addr.h>
+#include <soc_default_helper_macros.h>
+
+
+#define NUM_DRAM_REGIONS		3
+#define	NXP_DRAM0_ADDR			0x80000000
+#define NXP_DRAM0_MAX_SIZE		0x80000000	/*  2 GB  */
+
+#define NXP_DRAM1_ADDR			0x2080000000
+#define NXP_DRAM1_MAX_SIZE		0x1F80000000	/* 126 G */
+
+#define NXP_DRAM2_ADDR			0x6000000000
+#define NXP_DRAM2_MAX_SIZE		0x2000000000	/* 128G */
+
+/*DRAM0 Size defined in platform_def.h */
+#define	NXP_DRAM0_SIZE			PLAT_DEF_DRAM0_SIZE
+
+#define DDR_PLL_FIX
+#define NXP_DDR_PHY1_ADDR		0x01400000
+#define NXP_DDR_PHY2_ADDR		0x01600000
+
+#if defined(IMAGE_BL31)
+#define LS_SYS_TIMCTL_BASE		0x2890000
+
+#ifdef LS_SYS_TIMCTL_BASE
+#define PLAT_LS_NSTIMER_FRAME_ID	0
+#define LS_CONFIG_CNTACR		1
+#endif
+#endif
+
+/* Start: Macros used by soc.c: get_boot_dev */
+#define PORSR1_RCW_MASK		0x07800000
+#define PORSR1_RCW_SHIFT	23
+
+#define SDHC1_VAL		0x8
+#define SDHC2_VAL		0x9
+#define I2C1_VAL		0xa
+#define FLEXSPI_NAND2K_VAL	0xc
+#define FLEXSPI_NAND4K_VAL	0xd
+#define FLEXSPI_NOR		0xf
+/* End: Macros used by soc.c: get_boot_dev */
+
+/* SVR Definition (not include major and minor rev) */
+#define SVR_LX2160A		0x873601
+#define SVR_LX2120A		0x873621
+#define SVR_LX2080A		0x873603
+
+/* Number of cores in platform */
+/* Used by common code for array initialization */
+#define NUMBER_OF_CLUSTERS		8
+#define CORES_PER_CLUSTER		2
+#define PLATFORM_CORE_COUNT		NUMBER_OF_CLUSTERS * CORES_PER_CLUSTER
+
+/*
+ * Required LS standard platform porting definitions
+ * for CCN-508
+ */
+#define PLAT_CLUSTER_TO_CCN_ID_MAP 11, 15, 27, 31, 12, 28, 16, 0
+#define PLAT_6CLUSTER_TO_CCN_ID_MAP 11, 15, 27, 31, 12, 28
+
+
+/* Defines required for using XLAT tables from ARM common code */
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ull << 40)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ull << 40)
+
+/* Clock Divisors */
+#define NXP_PLATFORM_CLK_DIVIDER	2
+#define NXP_UART_CLK_DIVIDER		4
+
+/* Start: Macros used by lx2160a.S */
+#define MPIDR_AFFINITY0_MASK			0x00FF
+#define MPIDR_AFFINITY1_MASK			0xFF00
+#define CPUECTLR_DISABLE_TWALK_PREFETCH		0x4000000000
+#define CPUECTLR_INS_PREFETCH_MASK		0x1800000000
+#define CPUECTLR_DAT_PREFETCH_MASK		0x0300000000
+#define CPUECTLR_RET_8CLK			0x2
+#define OSDLR_EL1_DLK_LOCK			0x1
+#define CNTP_CTL_EL0_EN				0x1
+#define CNTP_CTL_EL0_IMASK			0x2
+/* set to 0 if the clusters are not symmetrical */
+#define SYMMETRICAL_CLUSTERS			1
+/* End: Macros used by lx2160a.S */
+
+/* Start: Macros used by lib/psci files */
+#define SYSTEM_PWR_DOMAINS 1
+#define PLAT_NUM_PWR_DOMAINS   (PLATFORM_CORE_COUNT + \
+				NUMBER_OF_CLUSTERS  + \
+				SYSTEM_PWR_DOMAINS)
+
+/* Power state coordination occurs at the system level */
+#define PLAT_MAX_PWR_LVL  MPIDR_AFFLVL2
+
+/* define retention state */
+#define PLAT_MAX_RET_STATE  (PSCI_LOCAL_STATE_RUN + 1)
+
+/* define power-down state */
+#define PLAT_MAX_OFF_STATE  (PLAT_MAX_RET_STATE + 1)
+/* End: Macros used by lib/psci files */
+
+/* Some data must be aligned on the biggest cache line size in the platform.
+ * This is known only to the platform as it might have a combination of
+ * integrated and external caches.
+ *
+ * CACHE_WRITEBACK_GRANULE is defined in soc.def
+ *
+ * One cache line needed for bakery locks on ARM platforms
+ */
+#define PLAT_PERCPU_BAKERY_LOCK_SIZE (1 * CACHE_WRITEBACK_GRANULE)
+
+#ifndef WDOG_RESET_FLAG
+#define WDOG_RESET_FLAG DEFAULT_SET_VALUE
+#endif
+
+#ifndef WARM_BOOT_SUCCESS
+#define WARM_BOOT_SUCCESS DEFAULT_SET_VALUE
+#endif
+
+#ifndef __ASSEMBLER__
+
+void set_base_freq_CNTFID0(void);
+void soc_init_start(void);
+void soc_init_finish(void);
+void soc_init_percpu(void);
+void _soc_set_start_addr(unsigned long addr);
+void _set_platform_security(void);
+
+#endif
+
+#endif /* _SOC_H */
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/ddr_init.c b/plat/nxp/soc-lx2160a/lx2160aqds/ddr_init.c
new file mode 100644
index 0000000..d44733c
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/ddr_init.c
@@ -0,0 +1,355 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <lib/utils.h>
+#include <load_img.h>
+
+#include "plat_common.h"
+#include <platform_def.h>
+
+#ifdef CONFIG_STATIC_DDR
+
+const struct ddr_cfg_regs static_3200 = {
+	.cs[0].bnds = U(0x03FF),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFFAA0018),
+	.timing_cfg[1] = U(0x646A8844),
+	.timing_cfg[2] = U(0x00058022),
+	.timing_cfg[3] = U(0x13622100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x07401400),
+	.timing_cfg[7] = U(0x3BB00000),
+	.timing_cfg[8] = U(0x0944AC00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010C50),
+	.sdram_mode[1] = U(0x00280400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x10240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x30C00000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct ddr_cfg_regs static_2900 = {
+	.cs[0].bnds = U(0x03FF),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFF990018),
+	.timing_cfg[1] = U(0x4F4A4844),
+	.timing_cfg[2] = U(0x0005601F),
+	.timing_cfg[3] = U(0x125F2100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x07401400),
+	.timing_cfg[7] = U(0x3AA00000),
+	.timing_cfg[8] = U(0x09449B00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010C50),
+	.sdram_mode[1] = U(0x00280400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x10240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x2C2E0000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct ddr_cfg_regs static_2600 = {
+	.cs[0].bnds = U(0x03FF),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFF880018),
+	.timing_cfg[1] = U(0x2A24F444),
+	.timing_cfg[2] = U(0x007141DC),
+	.timing_cfg[3] = U(0x125B2100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x06401400),
+	.timing_cfg[7] = U(0x28800000),
+	.timing_cfg[8] = U(0x07338A00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010A70),
+	.sdram_mode[1] = U(0x00200400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x0C240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x279C0000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct dimm_params static_dimm = {
+	.rdimm = U(0),
+	.primary_sdram_width = U(64),
+	.ec_sdram_width = U(8),
+	.n_ranks = U(2),
+	.device_width = U(8),
+	.mirrored_dimm = U(1),
+};
+
+/* Sample code using two UDIMM MT18ASF1G72AZ-2G6B1, on each DDR controller */
+unsigned long long board_static_ddr(struct ddr_info *priv)
+{
+	(void)memcpy(&priv->ddr_reg, &static_2900, sizeof(static_2900));
+	(void)memcpy(&priv->dimm, &static_dimm, sizeof(static_dimm));
+	priv->conf.cs_on_dimm[0] = 0x3;
+	ddr_board_options(priv);
+	compute_ddr_phy(priv);
+
+	return ULL(0x400000000);
+}
+
+#elif defined(CONFIG_DDR_NODIMM)
+/*
+ * Sample code to bypass reading SPD. This is a sample, not recommended
+ * for boards with slots. DDR model number: UDIMM MT18ASF1G72AZ-2G6B1.
+ */
+
+const struct dimm_params ddr_raw_timing = {
+	.n_ranks = U(2),
+	.rank_density = U(4294967296u),
+	.capacity = U(8589934592u),
+	.primary_sdram_width = U(64),
+	.ec_sdram_width = U(8),
+	.device_width = U(8),
+	.die_density = U(0x4),
+	.rdimm = U(0),
+	.mirrored_dimm = U(1),
+	.n_row_addr = U(15),
+	.n_col_addr = U(10),
+	.bank_addr_bits = U(0),
+	.bank_group_bits = U(2),
+	.edc_config = U(2),
+	.burst_lengths_bitmask = U(0x0c),
+	.tckmin_x_ps = 750,
+	.tckmax_ps = 1600,
+	.caslat_x = U(0x00FFFC00),
+	.taa_ps = 13750,
+	.trcd_ps = 13750,
+	.trp_ps = 13750,
+	.tras_ps = 32000,
+	.trc_ps = 457500,
+	.twr_ps = 15000,
+	.trfc1_ps = 260000,
+	.trfc2_ps = 160000,
+	.trfc4_ps = 110000,
+	.tfaw_ps = 21000,
+	.trrds_ps = 3000,
+	.trrdl_ps = 4900,
+	.tccdl_ps = 5000,
+	.refresh_rate_ps = U(7800000),
+};
+
+int ddr_get_ddr_params(struct dimm_params *pdimm,
+			    struct ddr_conf *conf)
+{
+	static const char dimm_model[] = "Fixed DDR on board";
+
+	conf->dimm_in_use[0] = 1;	/* Modify accordingly */
+	memcpy(pdimm, &ddr_raw_timing, sizeof(struct dimm_params));
+	memcpy(pdimm->mpart, dimm_model, sizeof(dimm_model) - 1);
+
+	/* valid DIMM mask, change accordingly, together with dimm_on_ctlr. */
+	return 0x5;
+}
+#endif	/* CONFIG_DDR_NODIMM */
+
+int ddr_board_options(struct ddr_info *priv)
+{
+	struct memctl_opt *popts = &priv->opt;
+	const struct ddr_conf *conf = &priv->conf;
+
+	popts->vref_dimm = U(0x24);		/* range 1, 83.4% */
+	popts->rtt_override = 0;
+	popts->rtt_park = U(240);
+	popts->otf_burst_chop_en = 0;
+	popts->burst_length = U(DDR_BL8);
+	popts->trwt_override = U(1);
+	popts->bstopre = U(0);			/* auto precharge */
+	popts->addr_hash = 1;
+
+	/* Set ODT impedance on PHY side */
+	switch (conf->cs_on_dimm[1]) {
+	case 0xc:	/* Two slots dual rank */
+	case 0x4:	/* Two slots single rank, not valid for interleaving */
+		popts->trwt = U(0xf);
+		popts->twrt = U(0x7);
+		popts->trrt = U(0x7);
+		popts->twwt = U(0x7);
+		popts->vref_phy = U(0x6B);	/* 83.6% */
+		popts->odt = U(60);
+		popts->phy_tx_impedance = U(28);
+		break;
+	case 0:		/* One slot used */
+	default:
+		popts->trwt = U(0x3);
+		popts->twrt = U(0x3);
+		popts->trrt = U(0x3);
+		popts->twwt = U(0x3);
+		popts->vref_phy = U(0x60);	/* 75% */
+		popts->odt = U(48);
+		popts->phy_tx_impedance = U(28);
+		break;
+	}
+
+	return 0;
+}
+
+#ifdef NXP_WARM_BOOT
+long long init_ddr(uint32_t wrm_bt_flg)
+#else
+long long init_ddr(void)
+#endif
+{
+	int spd_addr[] = {0x51U, 0x52U, 0x53U, 0x54U};
+	struct ddr_info info;
+	struct sysinfo sys;
+	long long dram_size;
+
+	zeromem(&sys, sizeof(sys));
+	if (get_clocks(&sys) == 1) {
+		ERROR("System clocks are not set.\n");
+		panic();
+	}
+	debug("platform clock %lu\n", sys.freq_platform);
+	debug("DDR PLL1 %lu\n", sys.freq_ddr_pll0);
+	debug("DDR PLL2 %lu\n", sys.freq_ddr_pll1);
+
+	zeromem(&info, sizeof(info));
+
+	/* Set two DDRC. Unused DDRC will be removed automatically. */
+	info.num_ctlrs = NUM_OF_DDRC;
+	info.spd_addr = spd_addr;
+	info.ddr[0] = (void *)NXP_DDR_ADDR;
+	info.ddr[1] = (void *)NXP_DDR2_ADDR;
+	info.phy[0] = (void *)NXP_DDR_PHY1_ADDR;
+	info.phy[1] = (void *)NXP_DDR_PHY2_ADDR;
+	info.clk = get_ddr_freq(&sys, 0);
+	info.img_loadr = load_img;
+	info.phy_gen2_fw_img_buf = PHY_GEN2_FW_IMAGE_BUFFER;
+	if (info.clk == 0) {
+		info.clk = get_ddr_freq(&sys, 1);
+	}
+	info.dimm_on_ctlr = DDRC_NUM_DIMM;
+
+	info.warm_boot_flag = DDR_WRM_BOOT_NT_SUPPORTED;
+#ifdef NXP_WARM_BOOT
+	info.warm_boot_flag = DDR_COLD_BOOT;
+	if (wrm_bt_flg != 0U) {
+		info.warm_boot_flag = DDR_WARM_BOOT;
+	} else {
+		info.warm_boot_flag = DDR_COLD_BOOT;
+	}
+#endif
+
+	dram_size = dram_init(&info
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+		    , NXP_CCN_HN_F_0_ADDR
+#endif
+		    );
+
+
+	if (dram_size < 0) {
+		ERROR("DDR init failed.\n");
+	}
+
+	return dram_size;
+}
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/plat_def.h b/plat/nxp/soc-lx2160a/lx2160aqds/plat_def.h
new file mode 100644
index 0000000..f480f92
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/plat_def.h
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_DEF_H
+#define PLAT_DEF_H
+
+#include <arch.h>
+#include <cortex_a72.h>
+/* Required without TBBR.
+ * To include the defines for DDR PHY
+ * Images.
+ */
+#include <tbbr_img_def.h>
+
+#include <policy.h>
+#include <soc.h>
+
+#if defined(IMAGE_BL31)
+#define LS_SYS_TIMCTL_BASE		0x2890000
+#define PLAT_LS_NSTIMER_FRAME_ID	0
+#define LS_CONFIG_CNTACR		1
+#endif
+
+#define NXP_SYSCLK_FREQ		100000000
+#define NXP_DDRCLK_FREQ		100000000
+
+/* UART related definition */
+#define NXP_CONSOLE_ADDR	NXP_UART_ADDR
+#define NXP_CONSOLE_BAUDRATE	115200
+
+/* Size of cacheable stacks */
+#if defined(IMAGE_BL2)
+#if defined(TRUSTED_BOARD_BOOT)
+#define PLATFORM_STACK_SIZE	0x2000
+#else
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+#elif defined(IMAGE_BL31)
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+
+/* SD block buffer */
+#define NXP_SD_BLOCK_BUF_SIZE	(0x8000)
+#define NXP_SD_BLOCK_BUF_ADDR	(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+
+#ifdef SD_BOOT
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+#else
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE)
+#endif
+
+/* IO defines as needed by IO driver framework */
+#define MAX_IO_DEVICES		4
+#define MAX_IO_BLOCK_DEVICES	1
+#define MAX_IO_HANDLES		4
+
+#define PHY_GEN2_FW_IMAGE_BUFFER	(NXP_OCRAM_ADDR + CSF_HDR_SZ)
+
+/*
+ * FIP image defines - Offset at which FIP Image would be present
+ * Image would include Bl31 , Bl33 and Bl32 (optional)
+ */
+#ifdef POLICY_FUSE_PROVISION
+#define MAX_FIP_DEVICES		3
+#endif
+
+#ifndef MAX_FIP_DEVICES
+#define MAX_FIP_DEVICES		2
+#endif
+
+/*
+ * ID of the secure physical generic timer interrupt used by the BL32.
+ */
+#define BL32_IRQ_SEC_PHY_TIMER	29
+
+#define BL31_WDOG_SEC		89
+
+#define BL31_NS_WDOG_WS1	108
+
+/*
+ * Define properties of Group 1 Secure and Group 0 interrupts as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define PLAT_LS_G1S_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(BL32_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE)
+
+/* SGI 15 and Secure watchdog interrupts assigned to Group 0 */
+#define NXP_IRQ_SEC_SGI_7		15
+
+#define PLAT_LS_G0_IRQ_PROPS(grp)	\
+	INTR_PROP_DESC(BL31_WDOG_SEC, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(BL31_NS_WDOG_WS1, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(NXP_IRQ_SEC_SGI_7, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_LEVEL)
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/platform.c b/plat/nxp/soc-lx2160a/lx2160aqds/platform.c
new file mode 100644
index 0000000..b00adb5
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/platform.c
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <plat_common.h>
+
+#pragma weak board_enable_povdd
+#pragma weak board_disable_povdd
+
+bool board_enable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
+
+bool board_disable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/platform.mk b/plat/nxp/soc-lx2160a/lx2160aqds/platform.mk
new file mode 100644
index 0000000..226b22b
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/platform.mk
@@ -0,0 +1,51 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# board-specific build parameters
+
+BOOT_MODE	?= 	flexspi_nor
+BOARD		?=	lx2160aqds
+POVDD_ENABLE	:=	no
+NXP_COINED_BB	:=	no
+
+ # DDR Compilation Configs
+NUM_OF_DDRC	:=	1
+DDRC_NUM_DIMM	:=	1
+DDRC_NUM_CS	:=	2
+DDR_ECC_EN	:=	yes
+ #enable address decoding feature
+DDR_ADDR_DEC	:=	yes
+APPLY_MAX_CDD	:=	yes
+
+# DDR Errata
+ERRATA_DDR_A011396	:= 1
+ERRATA_DDR_A050450	:= 1
+
+ # On-Board Flash Details
+FLASH_TYPE	:=	MT35XU512A
+XSPI_FLASH_SZ	:=	0x10000000
+NXP_XSPI_NOR_UNIT_SIZE		:=	0x20000
+BL2_BIN_XSPI_NOR_END_ADDRESS	:=	0x100000
+# CONFIG_FSPI_ERASE_4K is required to erase 4K sector sizes. This
+# config is enabled for future use cases.
+FSPI_ERASE_4K	:= 0
+
+# Platform specific features.
+WARM_BOOT	:=	yes
+
+# Adding Platform files build files
+BL2_SOURCES	+=	${BOARD_PATH}/ddr_init.c\
+			${BOARD_PATH}/platform.c
+
+SUPPORTED_BOOT_MODE	:=	flexspi_nor	\
+				sd		\
+				emmc
+
+# Adding platform board build info
+include plat/nxp/common/plat_make_helper/plat_common_def.mk
+
+# Adding SoC build info
+include plat/nxp/soc-lx2160a/soc.mk
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/platform_def.h b/plat/nxp/soc-lx2160a/lx2160aqds/platform_def.h
new file mode 100644
index 0000000..5fa774e
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/platform_def.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include "plat_def.h"
+#include "plat_default_def.h"
+
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2160aqds/policy.h b/plat/nxp/soc-lx2160a/lx2160aqds/policy.h
new file mode 100644
index 0000000..05d23e2
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160aqds/policy.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef	POLICY_H
+#define	POLICY_H
+
+/* Following defines affect the PLATFORM SECURITY POLICY */
+
+/* set this to 0x0 if the platform is not using/responding to ECC errors
+ * set this to 0x1 if ECC is being used (we have to do some init)
+ */
+#define	POLICY_USING_ECC	0x0
+
+/* Set this to 0x0 to leave the default SMMU page size in sACR
+ * Set this to 0x1 to change the SMMU page size to 64K
+ */
+#define	POLICY_SMMU_PAGESZ_64K	0x1
+
+/*
+ * POLICY_PERF_WRIOP = 0 : No Performance enhancement for WRIOP RN-I
+ * POLICY_PERF_WRIOP = 1 : No Performance enhancement for WRIOP RN-I = 7
+ * POLICY_PERF_WRIOP = 2 : No Performance enhancement for WRIOP RN-I = 23
+ */
+#define	POLICY_PERF_WRIOP	0
+
+/*
+ * set this to '1' if the debug clocks need to remain enabled during
+ * system entry to low-power (LPM20) - this should only be necessary
+ * for testing and NEVER set for normal production
+ */
+#define	POLICY_DEBUG_ENABLE	0
+
+
+#endif /* POLICY_H */
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/ddr_init.c b/plat/nxp/soc-lx2160a/lx2160ardb/ddr_init.c
new file mode 100644
index 0000000..8669b1d
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/ddr_init.c
@@ -0,0 +1,212 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <lib/utils.h>
+#include <load_img.h>
+
+#include "plat_common.h"
+#include <platform_def.h>
+
+#ifdef CONFIG_STATIC_DDR
+const struct ddr_cfg_regs static_1600 = {
+	.cs[0].config = U(0xA8050322),
+	.cs[1].config = U(0x80000322),
+	.cs[0].bnds = U(0x3FF),
+	.cs[1].bnds = U(0x3FF),
+	.sdram_cfg[0] = U(0xE5044000),
+	.sdram_cfg[1] = U(0x401011),
+	.timing_cfg[0] = U(0xFF550018),
+	.timing_cfg[1] = U(0xBAB48C42),
+	.timing_cfg[2] = U(0x48C111),
+	.timing_cfg[3] = U(0x10C1000),
+	.timing_cfg[4] = U(0x2),
+	.timing_cfg[5] = U(0x3401400),
+	.timing_cfg[7] = U(0x13300000),
+	.timing_cfg[8] = U(0x2114600),
+	.sdram_mode[0] = U(0x6010210),
+	.sdram_mode[8] = U(0x500),
+	.sdram_mode[9] = U(0x4240000),
+	.interval = U(0x18600000),
+	.data_init = U(0xDEADBEEF),
+	.zq_cntl = U(0x8A090705),
+};
+
+const struct dimm_params static_dimm = {
+	.rdimm = U(0),
+	.primary_sdram_width = U(64),
+	.ec_sdram_width = U(8),
+	.n_ranks = U(2),
+	.device_width = U(8),
+	.mirrored_dimm = U(1),
+};
+
+/* Sample code using two UDIMM MT18ASF1G72AZ-2G6B1, on each DDR controller */
+unsigned long long board_static_ddr(struct ddr_info *priv)
+{
+	memcpy(&priv->ddr_reg, &static_1600, sizeof(static_1600));
+	memcpy(&priv->dimm, &static_dimm, sizeof(static_dimm));
+	priv->conf.cs_on_dimm[0] = 0x3;
+	ddr_board_options(priv);
+	compute_ddr_phy(priv);
+
+	return ULL(0x400000000);
+}
+
+#elif defined(CONFIG_DDR_NODIMM)
+/*
+ * Sample code to bypass reading SPD. This is a sample, not recommended
+ * for boards with slots. DDR model number: UDIMM MT18ASF1G72AZ-2G6B1.
+ */
+
+const struct dimm_params ddr_raw_timing = {
+	.n_ranks = U(2),
+	.rank_density = U(4294967296u),
+	.capacity = U(8589934592u),
+	.primary_sdram_width = U(64),
+	.ec_sdram_width = U(8),
+	.device_width = U(8),
+	.die_density = U(0x4),
+	.rdimm = U(0),
+	.mirrored_dimm = U(1),
+	.n_row_addr = U(15),
+	.n_col_addr = U(10),
+	.bank_addr_bits = U(0),
+	.bank_group_bits = U(2),
+	.edc_config = U(2),
+	.burst_lengths_bitmask = U(0x0c),
+	.tckmin_x_ps = 750,
+	.tckmax_ps = 1600,
+	.caslat_x = U(0x00FFFC00),
+	.taa_ps = 13750,
+	.trcd_ps = 13750,
+	.trp_ps = 13750,
+	.tras_ps = 32000,
+	.trc_ps = 457500,
+	.twr_ps = 15000,
+	.trfc1_ps = 260000,
+	.trfc2_ps = 160000,
+	.trfc4_ps = 110000,
+	.tfaw_ps = 21000,
+	.trrds_ps = 3000,
+	.trrdl_ps = 4900,
+	.tccdl_ps = 5000,
+	.refresh_rate_ps = U(7800000),
+};
+
+int ddr_get_ddr_params(struct dimm_params *pdimm,
+			    struct ddr_conf *conf)
+{
+	static const char dimm_model[] = "Fixed DDR on board";
+
+	conf->dimm_in_use[0] = 1;	/* Modify accordingly */
+	memcpy(pdimm, &ddr_raw_timing, sizeof(struct dimm_params));
+	memcpy(pdimm->mpart, dimm_model, sizeof(dimm_model) - 1);
+
+	/* valid DIMM mask, change accordingly, together with dimm_on_ctlr. */
+	return 0x5;
+}
+#endif	/* CONFIG_DDR_NODIMM */
+
+int ddr_board_options(struct ddr_info *priv)
+{
+	struct memctl_opt *popts = &priv->opt;
+	const struct ddr_conf *conf = &priv->conf;
+
+	popts->vref_dimm = U(0x24);		/* range 1, 83.4% */
+	popts->rtt_override = 0;
+	popts->rtt_park = U(240);
+	popts->otf_burst_chop_en = 0;
+	popts->burst_length = U(DDR_BL8);
+	popts->trwt_override = U(1);
+	popts->bstopre = U(0);			/* auto precharge */
+	popts->addr_hash = 1;
+
+	/* Set ODT impedance on PHY side */
+	switch (conf->cs_on_dimm[1]) {
+	case 0xc:	/* Two slots dual rank */
+	case 0x4:	/* Two slots single rank, not valid for interleaving */
+		popts->trwt = U(0xf);
+		popts->twrt = U(0x7);
+		popts->trrt = U(0x7);
+		popts->twwt = U(0x7);
+		popts->vref_phy = U(0x6B);	/* 83.6% */
+		popts->odt = U(60);
+		popts->phy_tx_impedance = U(28);
+		break;
+	case 0:		/* One slot used */
+	default:
+		popts->trwt = U(0x3);
+		popts->twrt = U(0x3);
+		popts->trrt = U(0x3);
+		popts->twwt = U(0x3);
+		popts->vref_phy = U(0x60);	/* 75% */
+		popts->odt = U(48);
+		popts->phy_tx_impedance = U(28);
+		break;
+	}
+
+	return 0;
+}
+
+long long init_ddr(void)
+{
+	int spd_addr[] = { 0x51, 0x52, 0x53, 0x54 };
+	struct ddr_info info;
+	struct sysinfo sys;
+	long long dram_size;
+
+	zeromem(&sys, sizeof(sys));
+	if (get_clocks(&sys) != 0) {
+		ERROR("System clocks are not set\n");
+		panic();
+	}
+	debug("platform clock %lu\n", sys.freq_platform);
+	debug("DDR PLL1 %lu\n", sys.freq_ddr_pll0);
+	debug("DDR PLL2 %lu\n", sys.freq_ddr_pll1);
+
+	zeromem(&info, sizeof(info));
+
+	/* Set two DDRC. Unused DDRC will be removed automatically. */
+	info.num_ctlrs = NUM_OF_DDRC;
+	info.spd_addr = spd_addr;
+	info.ddr[0] = (void *)NXP_DDR_ADDR;
+	info.ddr[1] = (void *)NXP_DDR2_ADDR;
+	info.phy[0] = (void *)NXP_DDR_PHY1_ADDR;
+	info.phy[1] = (void *)NXP_DDR_PHY2_ADDR;
+	info.clk = get_ddr_freq(&sys, 0);
+	info.img_loadr = load_img;
+	info.phy_gen2_fw_img_buf = PHY_GEN2_FW_IMAGE_BUFFER;
+	if (info.clk == 0) {
+		info.clk = get_ddr_freq(&sys, 1);
+	}
+	info.dimm_on_ctlr = DDRC_NUM_DIMM;
+
+	info.warm_boot_flag = DDR_WRM_BOOT_NT_SUPPORTED;
+
+	dram_size = dram_init(&info
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+		    , NXP_CCN_HN_F_0_ADDR
+#endif
+		    );
+
+
+	if (dram_size < 0) {
+		ERROR("DDR init failed.\n");
+	}
+
+	return dram_size;
+}
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/plat_def.h b/plat/nxp/soc-lx2160a/lx2160ardb/plat_def.h
new file mode 100644
index 0000000..02f51e7
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/plat_def.h
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_DEF_H
+#define PLAT_DEF_H
+
+#include <arch.h>
+#include <cortex_a72.h>
+/* Required without TBBR.
+ * To include the defines for DDR PHY
+ * Images.
+ */
+#include <tbbr_img_def.h>
+
+#include <policy.h>
+#include <soc.h>
+
+#if defined(IMAGE_BL31)
+#define LS_SYS_TIMCTL_BASE		0x2890000
+#define PLAT_LS_NSTIMER_FRAME_ID	0
+#define LS_CONFIG_CNTACR		1
+#endif
+
+#define NXP_SYSCLK_FREQ		100000000
+#define NXP_DDRCLK_FREQ		100000000
+
+/* UART related definition */
+#define NXP_CONSOLE_ADDR	NXP_UART_ADDR
+#define NXP_CONSOLE_BAUDRATE	115200
+
+/* Size of cacheable stacks */
+#if defined(IMAGE_BL2)
+#if defined(TRUSTED_BOARD_BOOT)
+#define PLATFORM_STACK_SIZE	0x2000
+#else
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+#elif defined(IMAGE_BL31)
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+
+/* SD block buffer */
+#define NXP_SD_BLOCK_BUF_SIZE	(0x8000)
+#define NXP_SD_BLOCK_BUF_ADDR	(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+
+#ifdef SD_BOOT
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+#else
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE)
+#endif
+
+/* IO defines as needed by IO driver framework */
+#define MAX_IO_DEVICES		4
+#define MAX_IO_BLOCK_DEVICES	1
+#define MAX_IO_HANDLES		4
+
+#define PHY_GEN2_FW_IMAGE_BUFFER	(NXP_OCRAM_ADDR + CSF_HDR_SZ)
+
+/*
+ * FIP image defines - Offset at which FIP Image would be present
+ * Image would include Bl31 , Bl33 and Bl32 (optional)
+ */
+#ifdef POLICY_FUSE_PROVISION
+#define MAX_FIP_DEVICES		3
+#endif
+
+#ifndef MAX_FIP_DEVICES
+#define MAX_FIP_DEVICES		2
+#endif
+
+/*
+ * ID of the secure physical generic timer interrupt used by the BL32.
+ */
+#define BL32_IRQ_SEC_PHY_TIMER	29
+
+#define BL31_WDOG_SEC		89
+
+#define BL31_NS_WDOG_WS1	108
+
+/*
+ * Define properties of Group 1 Secure and Group 0 interrupts as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define PLAT_LS_G1S_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(BL32_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE)
+
+/* SGI 15 and Secure watchdog interrupts assigned to Group 0 */
+#define NXP_IRQ_SEC_SGI_7		15
+
+#define PLAT_LS_G0_IRQ_PROPS(grp)	\
+	INTR_PROP_DESC(BL31_WDOG_SEC, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(BL31_NS_WDOG_WS1, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(NXP_IRQ_SEC_SGI_7, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_LEVEL)
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/platform.c b/plat/nxp/soc-lx2160a/lx2160ardb/platform.c
new file mode 100644
index 0000000..b00adb5
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/platform.c
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <plat_common.h>
+
+#pragma weak board_enable_povdd
+#pragma weak board_disable_povdd
+
+bool board_enable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
+
+bool board_disable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/platform.mk b/plat/nxp/soc-lx2160a/lx2160ardb/platform.mk
new file mode 100644
index 0000000..ffb5fad
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/platform.mk
@@ -0,0 +1,51 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# board-specific build parameters
+
+BOOT_MODE	?= 	flexspi_nor
+BOARD		?=	lx2160ardb
+POVDD_ENABLE	:=	no
+NXP_COINED_BB	:=	no
+
+ # DDR Compilation Configs
+NUM_OF_DDRC	:=	2
+DDRC_NUM_DIMM	:=	2
+DDRC_NUM_CS	:=	4
+DDR_ECC_EN	:=	yes
+ #enable address decoding feature
+DDR_ADDR_DEC	:=	yes
+APPLY_MAX_CDD	:=	yes
+
+# DDR Errata
+ERRATA_DDR_A011396	:= 1
+ERRATA_DDR_A050450	:= 1
+
+ # On-Board Flash Details
+FLASH_TYPE	:=	MT35XU512A
+XSPI_FLASH_SZ	:=	0x10000000
+NXP_XSPI_NOR_UNIT_SIZE		:=	0x20000
+BL2_BIN_XSPI_NOR_END_ADDRESS	:=	0x100000
+# CONFIG_FSPI_ERASE_4K is required to erase 4K sector sizes. This
+# config is enabled for future use cases.
+FSPI_ERASE_4K	:= 0
+
+ # Platform specific features.
+WARM_BOOT	:=	no
+
+ # Adding Platform files build files
+BL2_SOURCES	+=	${BOARD_PATH}/ddr_init.c\
+			${BOARD_PATH}/platform.c
+
+SUPPORTED_BOOT_MODE	:=	flexspi_nor	\
+				sd		\
+				emmc
+
+# Adding platform board build info
+include plat/nxp/common/plat_make_helper/plat_common_def.mk
+
+ # Adding SoC build info
+include plat/nxp/soc-lx2160a/soc.mk
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/platform_def.h b/plat/nxp/soc-lx2160a/lx2160ardb/platform_def.h
new file mode 100644
index 0000000..6660998
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/platform_def.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include "plat_def.h"
+#include "plat_default_def.h"
+
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2160ardb/policy.h b/plat/nxp/soc-lx2160a/lx2160ardb/policy.h
new file mode 100644
index 0000000..19ad6db
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2160ardb/policy.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef POLICY_H
+#define	POLICY_H
+
+/* Following defines affect the PLATFORM SECURITY POLICY */
+
+/* set this to 0x0 if the platform is not using/responding to ECC errors
+ * set this to 0x1 if ECC is being used (we have to do some init)
+ */
+#define  POLICY_USING_ECC 0x0
+
+/* Set this to 0x0 to leave the default SMMU page size in sACR
+ * Set this to 0x1 to change the SMMU page size to 64K
+ */
+#define POLICY_SMMU_PAGESZ_64K 0x1
+
+/*
+ * POLICY_PERF_WRIOP = 0 : No Performance enhancement for WRIOP RN-I
+ * POLICY_PERF_WRIOP = 1 : No Performance enhancement for WRIOP RN-I = 7
+ * POLICY_PERF_WRIOP = 2 : No Performance enhancement for WRIOP RN-I = 23
+ */
+#define POLICY_PERF_WRIOP 0
+
+/*
+ * set this to '1' if the debug clocks need to remain enabled during
+ * system entry to low-power (LPM20) - this should only be necessary
+ * for testing and NEVER set for normal production
+ */
+#define POLICY_DEBUG_ENABLE 0
+
+
+#endif /* POLICY_H */
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/ddr_init.c b/plat/nxp/soc-lx2160a/lx2162aqds/ddr_init.c
new file mode 100644
index 0000000..73bcc93
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/ddr_init.c
@@ -0,0 +1,354 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <ddr.h>
+#include <lib/utils.h>
+#include <load_img.h>
+
+#include "plat_common.h"
+#include <platform_def.h>
+
+#ifdef CONFIG_STATIC_DDR
+
+const struct ddr_cfg_regs static_3200 = {
+	.cs[0].bnds = U(0x03FFU),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFFAA0018),
+	.timing_cfg[1] = U(0x646A8844),
+	.timing_cfg[2] = U(0x00058022),
+	.timing_cfg[3] = U(0x13622100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x07401400),
+	.timing_cfg[7] = U(0x3BB00000),
+	.timing_cfg[8] = U(0x0944AC00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010C50),
+	.sdram_mode[1] = U(0x00280400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x10240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x30C00000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct ddr_cfg_regs static_2900 = {
+	.cs[0].bnds = U(0x03FF),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFF990018),
+	.timing_cfg[1] = U(0x4F4A4844),
+	.timing_cfg[2] = U(0x0005601F),
+	.timing_cfg[3] = U(0x125F2100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x07401400),
+	.timing_cfg[7] = U(0x3AA00000),
+	.timing_cfg[8] = U(0x09449B00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010C50),
+	.sdram_mode[1] = U(0x00280400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x10240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x2C2E0000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct ddr_cfg_regs static_2600 = {
+	.cs[0].bnds = U(0x03FF),
+	.cs[1].bnds = U(0x03FF),
+	.cs[0].config = U(0x80050422),
+	.cs[1].config = U(0x80000422),
+	.cs[2].bnds = U(0x00),
+	.cs[3].bnds = U(0x00),
+	.cs[2].config = U(0x00),
+	.cs[3].config = U(0x00),
+	.timing_cfg[0] = U(0xFF880018),
+	.timing_cfg[1] = U(0x2A24F444),
+	.timing_cfg[2] = U(0x007141DC),
+	.timing_cfg[3] = U(0x125B2100),
+	.timing_cfg[4] = U(0x02),
+	.timing_cfg[5] = U(0x06401400),
+	.timing_cfg[7] = U(0x28800000),
+	.timing_cfg[8] = U(0x07338A00),
+	.sdram_cfg[0] = U(0x65044008),
+	.sdram_cfg[1] = U(0x00401011),
+	.sdram_cfg[2] = U(0x00),
+	.sdram_mode[0] = U(0x06010A70),
+	.sdram_mode[1] = U(0x00200400),
+	.sdram_mode[2] = U(0x00),
+	.sdram_mode[3] = U(0x00),
+	.sdram_mode[4] = U(0x00),
+	.sdram_mode[5] = U(0x00),
+	.sdram_mode[6] = U(0x00),
+	.sdram_mode[7] = U(0x00),
+	.sdram_mode[8] = U(0x0500),
+	.sdram_mode[9] = U(0x0C240000),
+	.sdram_mode[10] = U(0x00),
+	.sdram_mode[11] = U(0x00),
+	.sdram_mode[12] = U(0x00),
+	.sdram_mode[13] = U(0x00),
+	.sdram_mode[14] = U(0x00),
+	.sdram_mode[15] = U(0x00),
+	.md_cntl = U(0x00),
+	.interval = U(0x279C0000),
+	.data_init = U(0xDEADBEEF),
+	.init_addr = U(0x00),
+	.zq_cntl = U(0x8A090705),
+	.sdram_rcw[0] = U(0x00),
+	.sdram_rcw[1] = U(0x00),
+	.sdram_rcw[2] = U(0x00),
+	.sdram_rcw[3] = U(0x00),
+	.sdram_rcw[4] = U(0x00),
+	.sdram_rcw[5] = U(0x00),
+	.err_disable = U(0x00),
+	.err_int_en = U(0x00),
+};
+
+const struct dimm_params static_dimm = {
+	.rdimm = 0U,
+	.primary_sdram_width = 64U,
+	.ec_sdram_width = 8U,
+	.n_ranks = 2U,
+	.device_width = 8U,
+	.mirrored_dimm = 1U,
+};
+
+/* Sample code using two UDIMM MT18ASF1G72AZ-2G6B1, on each DDR controller */
+unsigned long long board_static_ddr(struct ddr_info *priv)
+{
+	memcpy(&priv->ddr_reg, &static_2900, sizeof(static_2900));
+	memcpy(&priv->dimm, &static_dimm, sizeof(static_dimm));
+	priv->conf.cs_on_dimm[0] = 0x3;
+	ddr_board_options(priv);
+	compute_ddr_phy(priv);
+
+	return ULL(0x400000000);
+}
+
+#elif defined(CONFIG_DDR_NODIMM)
+/*
+ * Sample code to bypass reading SPD. This is a sample, not recommended
+ * for boards with slots. DDR model number: UDIMM MT18ASF1G72AZ-2G6B1.
+ */
+struct dimm_params ddr_raw_timing = {
+	.n_ranks = 2U,
+	.rank_density = U(0x200000000),
+	.capacity = U(0x400000000),
+	.primary_sdram_width = 64U,
+	.ec_sdram_width = 8U,
+	.device_width = 8U,
+	.die_density = U(0x5),
+	.rdimm = 0U,
+	.mirrored_dimm = 1U,
+	.n_row_addr = 16U,
+	.n_col_addr = 10U,
+	.bank_addr_bits = 0U,
+	.bank_group_bits = 2U,
+	.edc_config = 2U,
+	.burst_lengths_bitmask = U(0x0c),
+	.tckmin_x_ps = 625,
+	.tckmax_ps = 1600,
+	.caslat_x = U(0x15FFFC00),
+	.taa_ps = 13750,
+	.trcd_ps = 13750,
+	.trp_ps = 13750,
+	.tras_ps = 32000,
+	.trc_ps = 457500,
+	.twr_ps = 15000,
+	.trfc1_ps = 350000,
+	.trfc2_ps = 260000,
+	.trfc4_ps = 160000,
+	.tfaw_ps = 21000,
+	.trrds_ps = 2500,
+	.trrdl_ps = 4900,
+	.tccdl_ps = 5000,
+	.refresh_rate_ps = 7800000U,
+};
+
+int ddr_get_ddr_params(struct dimm_params *pdimm,
+		       struct ddr_conf *conf)
+{
+	static const char dimm_model[] = "Fixed DDR on board";
+
+	conf->dimm_in_use[0] = 1;	/* Modify accordingly */
+	memcpy(pdimm, &ddr_raw_timing, sizeof(struct dimm_params));
+	memcpy(pdimm->mpart, dimm_model, sizeof(dimm_model) - 1);
+
+	/* valid DIMM mask, change accordingly, together with dimm_on_ctlr. */
+	return 0x5;
+}
+#endif	/* CONFIG_DDR_NODIMM */
+
+int ddr_board_options(struct ddr_info *priv)
+{
+	struct memctl_opt *popts = &priv->opt;
+	const struct ddr_conf *conf = &priv->conf;
+
+	popts->vref_dimm = U(0x19);		/* range 1, 83.4% */
+	popts->rtt_override = 1U;
+	popts->rtt_override_value = 0x5U;	/* RTT being used as 60 ohm */
+	popts->rtt_park = 120U;
+	popts->otf_burst_chop_en = 0;
+	popts->burst_length = DDR_BL8;
+	popts->trwt_override = 1U;
+	popts->bstopre = 0U;			/* auto precharge */
+	popts->addr_hash = 1;
+
+	/* Set ODT impedance on PHY side */
+	switch (conf->cs_on_dimm[1]) {
+	case 0xc:	/* Two slots dual rank */
+	case 0x4:	/* Two slots single rank, not valid for interleaving */
+		popts->trwt = U(0xf);
+		popts->twrt = U(0x7);
+		popts->trrt = U(0x7);
+		popts->twwt = U(0x7);
+		popts->vref_phy = U(0x6B);	/* 83.6% */
+		popts->odt = 60U;
+		popts->phy_tx_impedance = 28U;
+		break;
+	case 0:		/* Ont slot used */
+	default:
+		popts->trwt = U(0x3);
+		popts->twrt = U(0x3);
+		popts->trrt = U(0x3);
+		popts->twwt = U(0x3);
+		popts->vref_phy = U(0x5D);		/* 72% */
+		popts->odt = 60U;
+		popts->phy_tx_impedance = 28U;
+		break;
+	}
+
+	return 0;
+}
+
+#ifdef NXP_WARM_BOOT
+long long init_ddr(uint32_t wrm_bt_flg)
+#else
+long long init_ddr(void)
+#endif
+{
+	int spd_addr[] = { 0x51, 0x52, 0x53, 0x54 };
+	struct ddr_info info;
+	struct sysinfo sys;
+	long long dram_size;
+
+	zeromem(&sys, sizeof(sys));
+	if (get_clocks(&sys) != 0) {
+		ERROR("System clocks are not set\n");
+		panic();
+	}
+	debug("platform clock %lu\n", sys.freq_platform);
+	debug("DDR PLL1 %lu\n", sys.freq_ddr_pll0);
+	debug("DDR PLL2 %lu\n", sys.freq_ddr_pll1);
+
+	zeromem(&info, sizeof(info));
+
+	/* Set two DDRC. Unused DDRC will be removed automatically. */
+	info.num_ctlrs = NUM_OF_DDRC;
+	info.spd_addr = spd_addr;
+	info.ddr[0] = (void *)NXP_DDR_ADDR;
+	info.ddr[1] = (void *)NXP_DDR2_ADDR;
+	info.phy[0] = (void *)NXP_DDR_PHY1_ADDR;
+	info.phy[1] = (void *)NXP_DDR_PHY2_ADDR;
+	info.clk = get_ddr_freq(&sys, 0);
+	info.img_loadr = load_img;
+	info.phy_gen2_fw_img_buf = PHY_GEN2_FW_IMAGE_BUFFER;
+	if (info.clk == 0) {
+		info.clk = get_ddr_freq(&sys, 1);
+	}
+	info.dimm_on_ctlr = DDRC_NUM_DIMM;
+
+	info.warm_boot_flag = DDR_WRM_BOOT_NT_SUPPORTED;
+#ifdef NXP_WARM_BOOT
+	if (wrm_bt_flg != 0) {
+		info.warm_boot_flag = DDR_WARM_BOOT;
+	} else {
+		info.warm_boot_flag = DDR_COLD_BOOT;
+	}
+#endif
+
+	dram_size = dram_init(&info
+#if defined(NXP_HAS_CCN504) || defined(NXP_HAS_CCN508)
+				    , NXP_CCN_HN_F_0_ADDR
+#endif
+			);
+
+
+	if (dram_size < 0) {
+		ERROR("DDR init failed.\n");
+	}
+
+	return dram_size;
+}
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/plat_def.h b/plat/nxp/soc-lx2160a/lx2162aqds/plat_def.h
new file mode 100644
index 0000000..de2d244
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/plat_def.h
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLAT_DEF_H
+#define PLAT_DEF_H
+
+#include <arch.h>
+#include <cortex_a72.h>
+/* Required without TBBR.
+ * To include the defines for DDR PHY
+ * Images.
+ */
+#include <tbbr_img_def.h>
+
+#include <policy.h>
+#include <soc.h>
+
+#if defined(IMAGE_BL31)
+#define LS_SYS_TIMCTL_BASE		0x2890000
+#define PLAT_LS_NSTIMER_FRAME_ID	0
+#define LS_CONFIG_CNTACR		1
+#endif
+
+#define NXP_SYSCLK_FREQ		100000000
+#define NXP_DDRCLK_FREQ		100000000
+
+/* UART related definition */
+#define NXP_CONSOLE_ADDR	NXP_UART_ADDR
+#define NXP_CONSOLE_BAUDRATE	115200
+
+/* Size of cacheable stacks */
+#if defined(IMAGE_BL2)
+#if defined(TRUSTED_BOARD_BOOT)
+#define PLATFORM_STACK_SIZE	0x2000
+#else
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+#elif defined(IMAGE_BL31)
+#define PLATFORM_STACK_SIZE	0x1000
+#endif
+
+/* SD block buffer */
+#define NXP_SD_BLOCK_BUF_SIZE	(0x8000)
+#define NXP_SD_BLOCK_BUF_ADDR	(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+
+#ifdef SD_BOOT
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE \
+				- NXP_SD_BLOCK_BUF_SIZE)
+#else
+#define BL2_LIMIT		(NXP_OCRAM_ADDR + NXP_OCRAM_SIZE)
+#endif
+
+/* IO defines as needed by IO driver framework */
+#define MAX_IO_DEVICES		4
+#define MAX_IO_BLOCK_DEVICES	1
+#define MAX_IO_HANDLES		4
+
+#define PHY_GEN2_FW_IMAGE_BUFFER	(NXP_OCRAM_ADDR + CSF_HDR_SZ)
+
+/*
+ * FIP image defines - Offset at which FIP Image would be present
+ * Image would include Bl31 , Bl33 and Bl32 (optional)
+ */
+#ifdef POLICY_FUSE_PROVISION
+#define MAX_FIP_DEVICES		3
+#endif
+
+#ifndef MAX_FIP_DEVICES
+#define MAX_FIP_DEVICES		2
+#endif
+
+/*
+ * ID of the secure physical generic timer interrupt used by the BL32.
+ */
+#define BL32_IRQ_SEC_PHY_TIMER	29
+
+#define BL31_WDOG_SEC		89
+
+#define BL31_NS_WDOG_WS1	108
+
+/*
+ * Define properties of Group 1 Secure and Group 0 interrupts as per GICv3
+ * terminology. On a GICv2 system or mode, the lists will be merged and treated
+ * as Group 0 interrupts.
+ */
+#define PLAT_LS_G1S_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(BL32_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE)
+
+/* SGI 15 and Secure watchdog interrupts assigned to Group 0 */
+#define NXP_IRQ_SEC_SGI_7		15
+
+#define PLAT_LS_G0_IRQ_PROPS(grp)	\
+	INTR_PROP_DESC(BL31_WDOG_SEC, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(BL31_NS_WDOG_WS1, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
+	INTR_PROP_DESC(NXP_IRQ_SEC_SGI_7, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_LEVEL)
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/platform.c b/plat/nxp/soc-lx2160a/lx2162aqds/platform.c
new file mode 100644
index 0000000..7622cf0
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/platform.c
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <plat_common.h>
+
+#pragma weak board_enable_povdd
+#pragma weak board_disable_povdd
+
+bool board_enable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
+
+bool board_disable_povdd(void)
+{
+#ifdef CONFIG_POVDD_ENABLE
+	return true;
+#else
+	return false;
+#endif
+}
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/platform.mk b/plat/nxp/soc-lx2160a/lx2162aqds/platform.mk
new file mode 100644
index 0000000..2b4712c
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/platform.mk
@@ -0,0 +1,52 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# board-specific build parameters
+
+BOOT_MODE	?= 	flexspi_nor
+BOARD		?=	lx2162aqds
+POVDD_ENABLE	:=	no
+NXP_COINED_BB	:=	no
+
+ # DDR Compilation Configs
+NUM_OF_DDRC	:=	1
+DDRC_NUM_DIMM	:=	1
+DDRC_NUM_CS	:=	2
+DDR_ECC_EN	:=	yes
+ #enable address decoding feature
+DDR_ADDR_DEC	:=	yes
+APPLY_MAX_CDD	:=	yes
+
+# DDR Errata
+ERRATA_DDR_A011396	:= 1
+ERRATA_DDR_A050450	:= 1
+
+
+# On-Board Flash Details
+FLASH_TYPE	:=	MT35XU512A
+XSPI_FLASH_SZ	:=	0x10000000
+NXP_XSPI_NOR_UNIT_SIZE		:=	0x20000
+BL2_BIN_XSPI_NOR_END_ADDRESS	:=	0x100000
+# CONFIG_FSPI_ERASE_4K is required to erase 4K sector sizes. This
+# config is enabled for future use cases.
+FSPI_ERASE_4K	:= 0
+
+# Platform specific features.
+WARM_BOOT	:=	yes
+
+# Adding Platform files build files
+BL2_SOURCES	+=	${BOARD_PATH}/ddr_init.c\
+			${BOARD_PATH}/platform.c
+
+SUPPORTED_BOOT_MODE	:=	flexspi_nor	\
+				sd		\
+				emmc
+
+# Adding platform board build info
+include plat/nxp/common/plat_make_helper/plat_common_def.mk
+
+# Adding SoC build info
+include plat/nxp/soc-lx2160a/soc.mk
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/platform_def.h b/plat/nxp/soc-lx2160a/lx2162aqds/platform_def.h
new file mode 100644
index 0000000..5fa774e
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/platform_def.h
@@ -0,0 +1,14 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#include "plat_def.h"
+#include "plat_default_def.h"
+
+#endif
diff --git a/plat/nxp/soc-lx2160a/lx2162aqds/policy.h b/plat/nxp/soc-lx2160a/lx2162aqds/policy.h
new file mode 100644
index 0000000..1095f38
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/lx2162aqds/policy.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2018-2020 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#ifndef POLICY_H
+#define	POLICY_H
+
+/* Following defines affect the PLATFORM SECURITY POLICY */
+
+/* set this to 0x0 if the platform is not using/responding to ECC errors
+ * set this to 0x1 if ECC is being used (we have to do some init)
+ */
+#define  POLICY_USING_ECC 0x0
+
+/* Set this to 0x0 to leave the default SMMU page size in sACR
+ * Set this to 0x1 to change the SMMU page size to 64K
+ */
+#define POLICY_SMMU_PAGESZ_64K 0x1
+
+/*
+ * POLICY_PERF_WRIOP = 0 : No Performance enhancement for WRIOP RN-I
+ * POLICY_PERF_WRIOP = 1 : No Performance enhancement for WRIOP RN-I = 7
+ * POLICY_PERF_WRIOP = 2 : No Performance enhancement for WRIOP RN-I = 23
+ */
+#define POLICY_PERF_WRIOP 0
+
+/*
+ * set this to '1' if the debug clocks need to remain enabled during
+ * system entry to low-power (LPM20) - this should only be necessary
+ * for testing and NEVER set for normal production
+ */
+#define POLICY_DEBUG_ENABLE 0
+
+
+#endif /* POLICY_H */
diff --git a/plat/nxp/soc-lx2160a/soc.c b/plat/nxp/soc-lx2160a/soc.c
new file mode 100644
index 0000000..2209fda
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/soc.c
@@ -0,0 +1,509 @@
+/*
+ * Copyright 2018-2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <assert.h>
+
+#include <arch.h>
+#include <bl31/interrupt_mgmt.h>
+#include <caam.h>
+#include <cassert.h>
+#include <ccn.h>
+#include <common/debug.h>
+#include <dcfg.h>
+#ifdef I2C_INIT
+#include <i2c.h>
+#endif
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <ls_interconnect.h>
+#ifdef POLICY_FUSE_PROVISION
+#include <nxp_gpio.h>
+#endif
+#if TRUSTED_BOARD_BOOT
+#include <nxp_smmu.h>
+#endif
+#include <nxp_timer.h>
+#include <plat_console.h>
+#include <plat_gic.h>
+#include <plat_tzc400.h>
+#include <pmu.h>
+#if defined(NXP_SFP_ENABLED)
+#include <sfp.h>
+#endif
+
+#include <errata.h>
+#include <ls_interrupt_mgmt.h>
+#include "plat_common.h"
+#ifdef NXP_NV_SW_MAINT_LAST_EXEC_DATA
+#include <plat_nv_storage.h>
+#endif
+#ifdef NXP_WARM_BOOT
+#include <plat_warm_rst.h>
+#endif
+#include "platform_def.h"
+#include "soc.h"
+
+static struct soc_type soc_list[] =  {
+	SOC_ENTRY(LX2160A, LX2160A, 8, 2),
+	SOC_ENTRY(LX2080A, LX2080A, 8, 1),
+	SOC_ENTRY(LX2120A, LX2120A, 6, 2),
+};
+
+static dcfg_init_info_t dcfg_init_data = {
+			.g_nxp_dcfg_addr = NXP_DCFG_ADDR,
+			.nxp_sysclk_freq = NXP_SYSCLK_FREQ,
+			.nxp_ddrclk_freq = NXP_DDRCLK_FREQ,
+			.nxp_plat_clk_divider = NXP_PLATFORM_CLK_DIVIDER,
+		};
+static const unsigned char master_to_6rn_id_map[] = {
+	PLAT_6CLUSTER_TO_CCN_ID_MAP
+};
+
+static const unsigned char master_to_rn_id_map[] = {
+	PLAT_CLUSTER_TO_CCN_ID_MAP
+};
+
+CASSERT(ARRAY_SIZE(master_to_rn_id_map) == NUMBER_OF_CLUSTERS,
+		assert_invalid_cluster_count_for_ccn_variant);
+
+static const ccn_desc_t plat_six_cluster_ccn_desc = {
+	.periphbase = NXP_CCN_ADDR,
+	.num_masters = ARRAY_SIZE(master_to_6rn_id_map),
+	.master_to_rn_id_map = master_to_6rn_id_map
+};
+
+static const ccn_desc_t plat_ccn_desc = {
+	.periphbase = NXP_CCN_ADDR,
+	.num_masters = ARRAY_SIZE(master_to_rn_id_map),
+	.master_to_rn_id_map = master_to_rn_id_map
+};
+
+/******************************************************************************
+ * Function returns the base counter frequency
+ * after reading the first entry at CNTFID0 (0x20 offset).
+ *
+ * Function is used by:
+ *   1. ARM common code for PSCI management.
+ *   2. ARM Generic Timer init.
+ *
+ *****************************************************************************/
+unsigned int plat_get_syscnt_freq2(void)
+{
+	unsigned int counter_base_frequency;
+	/*
+	 * Below register specifies the base frequency of the system counter.
+	 * As per NXP Board Manuals:
+	 * The system counter always works with SYS_REF_CLK/4 frequency clock.
+	 *
+	 *
+	 */
+	counter_base_frequency = mmio_read_32(NXP_TIMER_ADDR + CNTFID_OFF);
+
+	return counter_base_frequency;
+}
+
+#ifdef IMAGE_BL2
+
+#ifdef POLICY_FUSE_PROVISION
+static gpio_init_info_t gpio_init_data = {
+	.gpio1_base_addr = NXP_GPIO1_ADDR,
+	.gpio2_base_addr = NXP_GPIO2_ADDR,
+	.gpio3_base_addr = NXP_GPIO3_ADDR,
+	.gpio4_base_addr = NXP_GPIO4_ADDR,
+};
+#endif
+
+static void soc_interconnect_config(void)
+{
+	unsigned long long val = 0x0U;
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list),
+			&num_clusters, &cores_per_cluster);
+
+	if (num_clusters == 6U) {
+		ccn_init(&plat_six_cluster_ccn_desc);
+	} else {
+		ccn_init(&plat_ccn_desc);
+	}
+
+	/*
+	 * Enable Interconnect coherency for the primary CPU's cluster.
+	 */
+	plat_ls_interconnect_enter_coherency(num_clusters);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 13, PCIeRC_RN_I_NODE_ID_OFFSET);
+	val |= (1 << 17);
+	ccn_write_node_reg(NODE_TYPE_HNI, 13, PCIeRC_RN_I_NODE_ID_OFFSET, val);
+
+	/* PCIe is Connected to RN-I 17 which is connected to HN-I 13. */
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 30, PCIeRC_RN_I_NODE_ID_OFFSET);
+	val |= (1 << 17);
+	ccn_write_node_reg(NODE_TYPE_HNI, 30, PCIeRC_RN_I_NODE_ID_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 13, SA_AUX_CTRL_REG_OFFSET);
+	val |= SERIALIZE_DEV_nGnRnE_WRITES;
+	ccn_write_node_reg(NODE_TYPE_HNI, 13, SA_AUX_CTRL_REG_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 30, SA_AUX_CTRL_REG_OFFSET);
+	val &= ~(ENABLE_RESERVE_BIT53);
+	val |= SERIALIZE_DEV_nGnRnE_WRITES;
+	ccn_write_node_reg(NODE_TYPE_HNI, 30, SA_AUX_CTRL_REG_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 13, PoS_CONTROL_REG_OFFSET);
+	val &= ~(HNI_POS_EN);
+	ccn_write_node_reg(NODE_TYPE_HNI, 13, PoS_CONTROL_REG_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 30, PoS_CONTROL_REG_OFFSET);
+	val &= ~(HNI_POS_EN);
+	ccn_write_node_reg(NODE_TYPE_HNI, 30, PoS_CONTROL_REG_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 13, SA_AUX_CTRL_REG_OFFSET);
+	val &= ~(POS_EARLY_WR_COMP_EN);
+	ccn_write_node_reg(NODE_TYPE_HNI, 13, SA_AUX_CTRL_REG_OFFSET, val);
+
+	val = ccn_read_node_reg(NODE_TYPE_HNI, 30, SA_AUX_CTRL_REG_OFFSET);
+	val &= ~(POS_EARLY_WR_COMP_EN);
+	ccn_write_node_reg(NODE_TYPE_HNI, 30, SA_AUX_CTRL_REG_OFFSET, val);
+
+#if POLICY_PERF_WRIOP
+	uint16_t wriop_rni = 0U;
+
+	if (POLICY_PERF_WRIOP == 1) {
+		wriop_rni = 7U;
+	} else if (POLICY_PERF_WRIOP == 2) {
+		wriop_rni = 23U;
+	} else {
+		ERROR("Incorrect WRIOP selected.\n");
+		panic();
+	}
+
+	val = ccn_read_node_reg(NODE_TYPE_RNI, wriop_rni,
+				SA_AUX_CTRL_REG_OFFSET);
+	val |= ENABLE_WUO;
+	ccn_write_node_reg(NODE_TYPE_HNI, wriop_rni, SA_AUX_CTRL_REG_OFFSET,
+			   val);
+#else
+	val = ccn_read_node_reg(NODE_TYPE_RNI, 17, SA_AUX_CTRL_REG_OFFSET);
+	val |= ENABLE_WUO;
+	ccn_write_node_reg(NODE_TYPE_RNI, 17, SA_AUX_CTRL_REG_OFFSET, val);
+#endif
+}
+
+
+void soc_preload_setup(void)
+{
+	dram_regions_info_t *info_dram_regions = get_dram_regions_info();
+#if defined(NXP_WARM_BOOT)
+	bool warm_reset = is_warm_boot();
+#endif
+	info_dram_regions->total_dram_size =
+#if defined(NXP_WARM_BOOT)
+						init_ddr(warm_reset);
+#else
+						init_ddr();
+#endif
+}
+
+/*******************************************************************************
+ * This function implements soc specific erratas
+ * This is called before DDR is initialized or MMU is enabled
+ ******************************************************************************/
+void soc_early_init(void)
+{
+	dcfg_init(&dcfg_init_data);
+#ifdef POLICY_FUSE_PROVISION
+	gpio_init(&gpio_init_data);
+	sec_init(NXP_CAAM_ADDR);
+#endif
+#if LOG_LEVEL > 0
+	/* Initialize the console to provide early debug support */
+	plat_console_init(NXP_CONSOLE_ADDR,
+				NXP_UART_CLK_DIVIDER, NXP_CONSOLE_BAUDRATE);
+#endif
+
+	enable_timer_base_to_cluster(NXP_PMU_ADDR);
+	soc_interconnect_config();
+
+	enum  boot_device dev = get_boot_dev();
+	/* Mark the buffer for SD in OCRAM as non secure.
+	 * The buffer is assumed to be at end of OCRAM for
+	 * the logic below to calculate TZPC programming
+	 */
+	if (dev == BOOT_DEVICE_EMMC || dev == BOOT_DEVICE_SDHC2_EMMC) {
+		/* Calculate the region in OCRAM which is secure
+		 * The buffer for SD needs to be marked non-secure
+		 * to allow SD to do DMA operations on it
+		 */
+		uint32_t secure_region = (NXP_OCRAM_SIZE
+						- NXP_SD_BLOCK_BUF_SIZE);
+		uint32_t mask = secure_region/TZPC_BLOCK_SIZE;
+
+		mmio_write_32(NXP_OCRAM_TZPC_ADDR, mask);
+
+		/* Add the entry for buffer in MMU Table */
+		mmap_add_region(NXP_SD_BLOCK_BUF_ADDR, NXP_SD_BLOCK_BUF_ADDR,
+				NXP_SD_BLOCK_BUF_SIZE,
+				MT_DEVICE | MT_RW | MT_NS);
+	}
+
+	soc_errata();
+
+#if (TRUSTED_BOARD_BOOT) || defined(POLICY_FUSE_PROVISION)
+	sfp_init(NXP_SFP_ADDR);
+#endif
+
+#if TRUSTED_BOARD_BOOT
+	uint32_t mode;
+
+	/* For secure boot disable SMMU.
+	 * Later when platform security policy comes in picture,
+	 * this might get modified based on the policy
+	 */
+	if (check_boot_mode_secure(&mode) == true) {
+		bypass_smmu(NXP_SMMU_ADDR);
+	}
+
+	/* For Mbedtls currently crypto is not supported via CAAM
+	 * enable it when that support is there. In tbbr.mk
+	 * the CAAM_INTEG is set as 0.
+	 */
+
+#ifndef MBEDTLS_X509
+	/* Initialize the crypto accelerator if enabled */
+	if (is_sec_enabled() == false)
+		INFO("SEC is disabled.\n");
+	else
+		sec_init(NXP_CAAM_ADDR);
+#endif
+#endif
+
+	/*
+	 * Initialize system level generic timer for Layerscape Socs.
+	 */
+	delay_timer_init(NXP_TIMER_ADDR);
+	i2c_init(NXP_I2C_ADDR);
+}
+
+void soc_bl2_prepare_exit(void)
+{
+#if defined(NXP_SFP_ENABLED) && defined(DISABLE_FUSE_WRITE)
+	set_sfp_wr_disable();
+#endif
+}
+
+/*****************************************************************************
+ * This function returns the boot device based on RCW_SRC
+ ****************************************************************************/
+enum boot_device get_boot_dev(void)
+{
+	enum boot_device src = BOOT_DEVICE_NONE;
+	uint32_t porsr1;
+	uint32_t rcw_src;
+
+	porsr1 = read_reg_porsr1();
+
+	rcw_src = (porsr1 & PORSR1_RCW_MASK) >> PORSR1_RCW_SHIFT;
+
+	switch (rcw_src) {
+	case FLEXSPI_NOR:
+		src = BOOT_DEVICE_FLEXSPI_NOR;
+		INFO("RCW BOOT SRC is FLEXSPI NOR\n");
+		break;
+	case FLEXSPI_NAND2K_VAL:
+	case FLEXSPI_NAND4K_VAL:
+		INFO("RCW BOOT SRC is FLEXSPI NAND\n");
+		src = BOOT_DEVICE_FLEXSPI_NAND;
+		break;
+	case SDHC1_VAL:
+		src = BOOT_DEVICE_EMMC;
+		INFO("RCW BOOT SRC is SD\n");
+		break;
+	case SDHC2_VAL:
+		src = BOOT_DEVICE_SDHC2_EMMC;
+		INFO("RCW BOOT SRC is EMMC\n");
+		break;
+	default:
+		break;
+	}
+
+	return src;
+}
+
+
+void soc_mem_access(void)
+{
+	const devdisr5_info_t *devdisr5_info = get_devdisr5_info();
+	dram_regions_info_t *info_dram_regions = get_dram_regions_info();
+	struct tzc400_reg tzc400_reg_list[MAX_NUM_TZC_REGION];
+	int dram_idx, index = 0U;
+
+	for (dram_idx = 0U; dram_idx < info_dram_regions->num_dram_regions;
+	     dram_idx++) {
+		if (info_dram_regions->region[dram_idx].size == 0) {
+			ERROR("DDR init failure, or");
+			ERROR("DRAM regions not populated correctly.\n");
+			break;
+		}
+
+		index = populate_tzc400_reg_list(tzc400_reg_list,
+				dram_idx, index,
+				info_dram_regions->region[dram_idx].addr,
+				info_dram_regions->region[dram_idx].size,
+				NXP_SECURE_DRAM_SIZE, NXP_SP_SHRD_DRAM_SIZE);
+	}
+
+	if (devdisr5_info->ddrc1_present != 0) {
+		INFO("DDR Controller 1.\n");
+		mem_access_setup(NXP_TZC_ADDR, index,
+				tzc400_reg_list);
+		mem_access_setup(NXP_TZC3_ADDR, index,
+				tzc400_reg_list);
+	}
+	if (devdisr5_info->ddrc2_present != 0) {
+		INFO("DDR Controller 2.\n");
+		mem_access_setup(NXP_TZC2_ADDR, index,
+				tzc400_reg_list);
+		mem_access_setup(NXP_TZC4_ADDR, index,
+				tzc400_reg_list);
+	}
+}
+
+#else
+const unsigned char _power_domain_tree_desc[] = {1, 8, 2, 2, 2, 2, 2, 2, 2, 2};
+
+CASSERT(NUMBER_OF_CLUSTERS && NUMBER_OF_CLUSTERS <= 256,
+		assert_invalid_lx2160a_cluster_count);
+
+/******************************************************************************
+ * This function returns the SoC topology
+ ****************************************************************************/
+
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+
+	return _power_domain_tree_desc;
+}
+
+/*******************************************************************************
+ * This function returns the core count within the cluster corresponding to
+ * `mpidr`.
+ ******************************************************************************/
+unsigned int plat_ls_get_cluster_core_count(u_register_t mpidr)
+{
+	return CORES_PER_CLUSTER;
+}
+
+
+void soc_early_platform_setup2(void)
+{
+	dcfg_init(&dcfg_init_data);
+	/*
+	 * Initialize system level generic timer for Socs
+	 */
+	delay_timer_init(NXP_TIMER_ADDR);
+
+#if LOG_LEVEL > 0
+	/* Initialize the console to provide early debug support */
+	plat_console_init(NXP_CONSOLE_ADDR,
+			  NXP_UART_CLK_DIVIDER, NXP_CONSOLE_BAUDRATE);
+#endif
+}
+
+void soc_platform_setup(void)
+{
+	/* Initialize the GIC driver, cpu and distributor interfaces */
+	static uintptr_t target_mask_array[PLATFORM_CORE_COUNT];
+	static interrupt_prop_t ls_interrupt_props[] = {
+		PLAT_LS_G1S_IRQ_PROPS(INTR_GROUP1S),
+		PLAT_LS_G0_IRQ_PROPS(INTR_GROUP0)
+	};
+
+	plat_ls_gic_driver_init(NXP_GICD_ADDR, NXP_GICR_ADDR,
+				PLATFORM_CORE_COUNT,
+				ls_interrupt_props,
+				ARRAY_SIZE(ls_interrupt_props),
+				target_mask_array,
+				plat_core_pos);
+
+	plat_ls_gic_init();
+	enable_init_timer();
+#ifdef LS_SYS_TIMCTL_BASE
+	ls_configure_sys_timer(LS_SYS_TIMCTL_BASE,
+			       LS_CONFIG_CNTACR,
+			       PLAT_LS_NSTIMER_FRAME_ID);
+#endif
+}
+
+/*******************************************************************************
+ * This function initializes the soc from the BL31 module
+ ******************************************************************************/
+void soc_init(void)
+{
+	uint8_t num_clusters, cores_per_cluster;
+
+	get_cluster_info(soc_list, ARRAY_SIZE(soc_list),
+			&num_clusters, &cores_per_cluster);
+
+	/* low-level init of the soc */
+	soc_init_start();
+	soc_init_percpu();
+	_init_global_data();
+	_initialize_psci();
+
+	if (ccn_get_part0_id(NXP_CCN_ADDR) != CCN_508_PART0_ID) {
+		ERROR("Unrecognized CCN variant detected.");
+		ERROR("Only CCN-508 is supported\n");
+		panic();
+	}
+
+	if (num_clusters == 6U) {
+		ccn_init(&plat_six_cluster_ccn_desc);
+	} else {
+		ccn_init(&plat_ccn_desc);
+	}
+
+	plat_ls_interconnect_enter_coherency(num_clusters);
+
+	/* Set platform security policies */
+	_set_platform_security();
+
+	 /* make sure any parallel init tasks are finished */
+	soc_init_finish();
+
+	/* Initialize the crypto accelerator if enabled */
+	if (is_sec_enabled() == false) {
+		INFO("SEC is disabled.\n");
+	} else {
+		sec_init(NXP_CAAM_ADDR);
+	}
+
+}
+
+#ifdef NXP_WDOG_RESTART
+static uint64_t wdog_interrupt_handler(uint32_t id, uint32_t flags,
+					  void *handle, void *cookie)
+{
+	uint8_t data = WDOG_RESET_FLAG;
+
+	wr_nv_app_data(WDT_RESET_FLAG_OFFSET,
+		       (uint8_t *)&data, sizeof(data));
+
+	mmio_write_32(NXP_RST_ADDR + RSTCNTL_OFFSET, SW_RST_REQ_INIT);
+
+	return 0;
+}
+#endif
+
+void soc_runtime_setup(void)
+{
+
+#ifdef NXP_WDOG_RESTART
+	request_intr_type_el3(BL31_NS_WDOG_WS1, wdog_interrupt_handler);
+#endif
+}
+#endif
diff --git a/plat/nxp/soc-lx2160a/soc.def b/plat/nxp/soc-lx2160a/soc.def
new file mode 100644
index 0000000..24d1d13
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/soc.def
@@ -0,0 +1,111 @@
+#
+# Copyright (c) 2015, 2016 Freescale Semiconductor, Inc.
+# Copyright 2017-2020 NXP Semiconductors
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+#------------------------------------------------------------------------------
+#
+# This file contains the basic architecture definitions that drive the build
+#
+# -----------------------------------------------------------------------------
+
+CORE_TYPE	:=	a72
+
+CACHE_LINE	:=	6
+
+# set to GIC400 or GIC500
+GIC		:=	GIC500
+
+# set to CCI400 or CCN504 or CCN508
+INTERCONNECT	:=	CCN508
+
+# indicate layerscape chassis level - set to 3=LSCH3 or 2=LSCH2
+CHASSIS		:=	3_2
+
+# TZC IP Details TZC used is TZC380 or TZC400
+TZC_ID		:=	TZC400
+
+# CONSOLE Details available is NS16550 or PL011
+CONSOLE		:=	PL011
+
+# Select the DDR PHY generation to be used
+PLAT_DDR_PHY	:=	PHY_GEN2
+
+PHYS_SYS	:=	64
+
+# Area of OCRAM reserved by ROM code
+NXP_ROM_RSVD	:= 0xa000
+
+# Max Size of CSF header. Required to define BL2 TEXT LIMIT in soc.def
+# Input to CST create_hdr_esbc tool
+CSF_HDR_SZ	:= 0x3000
+
+NXP_SFP_VER	:= 3_4
+
+# In IMAGE_BL2, compile time flag for handling Cache coherency
+# with CAAM for BL2 running from OCRAM
+SEC_MEM_NON_COHERENT	:= yes
+
+# Defining the endianness for NXP ESDHC
+NXP_ESDHC_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP SFP
+NXP_SFP_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP GPIO
+NXP_GPIO_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP SNVS
+NXP_SNVS_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP CCSR GUR register
+NXP_GUR_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP FSPI register
+NXP_FSPI_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP SEC
+NXP_SEC_ENDIANNESS	:= LE
+
+# Defining the endianness for NXP DDR
+NXP_DDR_ENDIANNESS	:= LE
+
+NXP_DDR_INTLV_256B	:= 1
+
+# OCRAM MAP for BL2
+# Before BL2
+# 0x18000000 - 0x18009fff -> Used by ROM code
+# 0x1800a000 - 0x1800dfff -> CSF header for BL2
+# (The above area i.e 0x18000000 - 0x1800dfff is available
+#  for DDR PHY images scratch pad region during BL2 run time)
+# For FlexSPI boot
+# 0x1800e000 - 0x18040000 -> Reserved for BL2 binary
+# For SD boot
+# 0x1800e000 - 0x18030000 -> Reserved for BL2 binary
+# 0x18030000 - 0x18040000 -> Reserved for SD buffer
+OCRAM_START_ADDR := 0x18000000
+OCRAM_SIZE := 0x40000
+
+# Location of BL2 on OCRAM
+BL2_BASE_ADDR	:=	$(shell echo $$(( $(OCRAM_START_ADDR) + $(NXP_ROM_RSVD) + $(CSF_HDR_SZ) )))
+# Covert to HEX to be used by create_pbl.mk
+BL2_BASE	:=	$(shell echo "0x"$$(echo "obase=16; ${BL2_BASE_ADDR}" | bc))
+
+# BL2_HDR_LOC is at  (OCRAM_ADDR + NXP_ROM_RSVD)
+# This value BL2_HDR_LOC + CSF_HDR_SZ should not overalp with BL2_BASE
+BL2_HDR_LOC_HDR	?=	$(shell echo $$(( $(OCRAM_START_ADDR) + $(NXP_ROM_RSVD) )))
+# Covert to HEX to be used by create_pbl.mk
+BL2_HDR_LOC	:=	$$(echo "obase=16; ${BL2_HDR_LOC_HDR}" | bc)
+
+# SoC ERRATAS to be enabled
+#
+# Core Errata
+ERRATA_A72_859971	:= 1
+
+# SoC Errata
+ERRATA_SOC_A050426	:= 1
+
+# enable dynamic memory mapping
+PLAT_XLAT_TABLES_DYNAMIC :=	1
diff --git a/plat/nxp/soc-lx2160a/soc.mk b/plat/nxp/soc-lx2160a/soc.mk
new file mode 100644
index 0000000..75a3af2
--- /dev/null
+++ b/plat/nxp/soc-lx2160a/soc.mk
@@ -0,0 +1,174 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+
+ # SoC-specific build parameters
+SOC		:=	lx2160a
+PLAT_PATH	:=	plat/nxp
+PLAT_COMMON_PATH:=	plat/nxp/common
+PLAT_DRIVERS_PATH:=	drivers/nxp
+PLAT_SOC_PATH	:=	${PLAT_PATH}/soc-${SOC}
+BOARD_PATH	:=	${PLAT_SOC_PATH}/${BOARD}
+
+ # get SoC-specific defnitions
+include ${PLAT_SOC_PATH}/soc.def
+include ${PLAT_COMMON_PATH}/plat_make_helper/soc_common_def.mk
+include ${PLAT_COMMON_PATH}/plat_make_helper/plat_build_macros.mk
+
+ # SoC-specific
+NXP_WDOG_RESTART	:= yes
+
+
+ # Selecting dependent module,
+ # Selecting dependent drivers, and
+ # Adding defines.
+
+ # for features enabled above.
+ifeq (${NXP_WDOG_RESTART}, yes)
+NXP_NV_SW_MAINT_LAST_EXEC_DATA := yes
+LS_EL3_INTERRUPT_HANDLER := yes
+$(eval $(call add_define, NXP_WDOG_RESTART))
+endif
+
+
+ # For Security Features
+DISABLE_FUSE_WRITE	:= 1
+ifeq (${TRUSTED_BOARD_BOOT}, 1)
+ifeq (${GENERATE_COT},1)
+# Save Keys to be used by DDR FIP image
+SAVE_KEYS=1
+endif
+$(eval $(call SET_NXP_MAKE_FLAG,SMMU_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,SFP_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,SNVS_NEEDED,BL2))
+# Used by create_pbl tool to
+# create bl2_<boot_mode>_sec.pbl image
+SECURE_BOOT	:= yes
+endif
+$(eval $(call SET_NXP_MAKE_FLAG,CRYPTO_NEEDED,BL_COMM))
+
+
+ # Selecting Drivers for SoC
+$(eval $(call SET_NXP_MAKE_FLAG,DCFG_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,TIMER_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,INTERCONNECT_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,GIC_NEEDED,BL31))
+$(eval $(call SET_NXP_MAKE_FLAG,CONSOLE_NEEDED,BL_COMM))
+$(eval $(call SET_NXP_MAKE_FLAG,PMU_NEEDED,BL_COMM))
+
+$(eval $(call SET_NXP_MAKE_FLAG,DDR_DRIVER_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,TZASC_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,I2C_NEEDED,BL2))
+$(eval $(call SET_NXP_MAKE_FLAG,IMG_LOADR_NEEDED,BL2))
+
+
+ # Selecting PSCI & SIP_SVC support
+$(eval $(call SET_NXP_MAKE_FLAG,PSCI_NEEDED,BL31))
+$(eval $(call SET_NXP_MAKE_FLAG,SIPSVC_NEEDED,BL31))
+
+
+ # Selecting Boot Source for the TFA images.
+ifeq (${BOOT_MODE}, flexspi_nor)
+$(eval $(call SET_NXP_MAKE_FLAG,XSPI_NEEDED,BL2))
+$(eval $(call add_define,FLEXSPI_NOR_BOOT))
+else
+ifeq (${BOOT_MODE}, sd)
+$(eval $(call SET_NXP_MAKE_FLAG,SD_MMC_NEEDED,BL2))
+$(eval $(call add_define,SD_BOOT))
+else
+ifeq (${BOOT_MODE}, emmc)
+$(eval $(call SET_NXP_MAKE_FLAG,SD_MMC_NEEDED,BL2))
+$(eval $(call add_define,EMMC_BOOT))
+else
+$(error Un-supported Boot Mode = ${BOOT_MODE})
+endif
+endif
+endif
+
+
+ # Separate DDR-FIP image to be loaded.
+$(eval $(call SET_NXP_MAKE_FLAG,DDR_FIP_IO_NEEDED,BL2))
+
+
+# Source File Addition
+# #####################
+
+PLAT_INCLUDES		+=	-I${PLAT_COMMON_PATH}/include/default\
+				-I${BOARD_PATH}\
+				-I${PLAT_COMMON_PATH}/include/default/ch_${CHASSIS}\
+				-I${PLAT_SOC_PATH}/include\
+				-I${PLAT_COMMON_PATH}/soc_errata
+
+ifeq (${SECURE_BOOT},yes)
+include ${PLAT_COMMON_PATH}/tbbr/tbbr.mk
+endif
+
+ifeq ($(WARM_BOOT),yes)
+include ${PLAT_COMMON_PATH}/warm_reset/warm_reset.mk
+endif
+
+ifeq (${NXP_NV_SW_MAINT_LAST_EXEC_DATA}, yes)
+include ${PLAT_COMMON_PATH}/nv_storage/nv_storage.mk
+endif
+
+ifeq (${PSCI_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/psci/psci.mk
+endif
+
+ifeq (${SIPSVC_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/sip_svc/sipsvc.mk
+endif
+
+ifeq (${DDR_FIP_IO_NEEDED}, yes)
+include ${PLAT_COMMON_PATH}/fip_handler/ddr_fip/ddr_fip_io.mk
+endif
+
+ # for fuse-fip & fuse-programming
+ifeq (${FUSE_PROG}, 1)
+include ${PLAT_COMMON_PATH}/fip_handler/fuse_fip/fuse.mk
+endif
+
+ifeq (${IMG_LOADR_NEEDED},yes)
+include $(PLAT_COMMON_PATH)/img_loadr/img_loadr.mk
+endif
+
+ # Adding source files for the above selected drivers.
+include ${PLAT_DRIVERS_PATH}/drivers.mk
+
+ # Adding SoC specific files
+include ${PLAT_COMMON_PATH}/soc_errata/errata.mk
+
+PLAT_INCLUDES		+=	${NV_STORAGE_INCLUDES}\
+				${WARM_RST_INCLUDES}
+
+BL31_SOURCES		+=	${PLAT_SOC_PATH}/$(ARCH)/${SOC}.S\
+				${WARM_RST_BL31_SOURCES}\
+				${PSCI_SOURCES}\
+				${SIPSVC_SOURCES}\
+				${PLAT_COMMON_PATH}/$(ARCH)/bl31_data.S
+
+PLAT_BL_COMMON_SOURCES	+=	${PLAT_COMMON_PATH}/$(ARCH)/ls_helpers.S\
+				${PLAT_SOC_PATH}/aarch64/${SOC}_helpers.S\
+				${NV_STORAGE_SOURCES}\
+				${WARM_RST_BL_COMM_SOURCES}\
+				${PLAT_SOC_PATH}/soc.c
+
+ifeq (${TEST_BL31}, 1)
+BL31_SOURCES		+=	${PLAT_SOC_PATH}/$(ARCH)/bootmain64.S\
+				${PLAT_SOC_PATH}/$(ARCH)/nonboot64.S
+endif
+
+BL2_SOURCES		+=	${DDR_CNTLR_SOURCES}\
+				${TBBR_SOURCES}\
+				${FUSE_SOURCES}
+
+
+ # Adding TFA setup files
+include ${PLAT_PATH}/common/setup/common.mk
+
+
+ # Adding source files to generate separate DDR FIP image
+include ${PLAT_SOC_PATH}/ddr_fip.mk
diff --git a/plat/qemu/common/aarch64/plat_helpers.S b/plat/qemu/common/aarch64/plat_helpers.S
index b546173..08b2817 100644
--- a/plat/qemu/common/aarch64/plat_helpers.S
+++ b/plat/qemu/common/aarch64/plat_helpers.S
@@ -32,7 +32,8 @@
 func plat_qemu_calc_core_pos
 	and	x1, x0, #MPIDR_CPU_MASK
 	and	x0, x0, #MPIDR_CLUSTER_MASK
-	add	x0, x1, x0, LSR #6
+	add	x0, x1, x0, LSR #(MPIDR_AFFINITY_BITS -\
+				  PLATFORM_CPU_PER_CLUSTER_SHIFT)
 	ret
 endfunc plat_qemu_calc_core_pos
 
diff --git a/plat/qemu/common/qemu_bl31_setup.c b/plat/qemu/common/qemu_bl31_setup.c
index 4d36b03..4f60eb1 100644
--- a/plat/qemu/common/qemu_bl31_setup.c
+++ b/plat/qemu/common/qemu_bl31_setup.c
@@ -7,6 +7,7 @@
 #include <assert.h>
 
 #include <common/bl_common.h>
+#include <drivers/arm/pl061_gpio.h>
 #include <plat/common/platform.h>
 
 #include "qemu_private.h"
@@ -69,9 +70,18 @@
 			      BL_COHERENT_RAM_BASE, BL_COHERENT_RAM_END);
 }
 
+static void qemu_gpio_init(void)
+{
+#ifdef SECURE_GPIO_BASE
+	pl061_gpio_init();
+	pl061_gpio_register(SECURE_GPIO_BASE, 0);
+#endif
+}
+
 void bl31_platform_setup(void)
 {
 	plat_qemu_gic_init();
+	qemu_gpio_init();
 }
 
 unsigned int plat_get_syscnt_freq2(void)
diff --git a/plat/qemu/common/qemu_common.c b/plat/qemu/common/qemu_common.c
index 7f8e4c4..47ec791 100644
--- a/plat/qemu/common/qemu_common.c
+++ b/plat/qemu/common/qemu_common.c
@@ -26,7 +26,7 @@
 #ifdef DEVICE2_BASE
 #define MAP_DEVICE2	MAP_REGION_FLAT(DEVICE2_BASE,			\
 					DEVICE2_SIZE,			\
-					MT_DEVICE | MT_RO | MT_SECURE)
+					MT_DEVICE | MT_RW | MT_SECURE)
 #endif
 
 #define MAP_SHARED_RAM	MAP_REGION_FLAT(SHARED_RAM_BASE,		\
@@ -93,7 +93,11 @@
 #ifdef MAP_DEVICE1
 	MAP_DEVICE1,
 #endif
+#ifdef MAP_DEVICE2
+	MAP_DEVICE2,
+#endif
 #if SPM_MM
+	MAP_NS_DRAM0,
 	QEMU_SPM_BUF_EL3_MMAP,
 #else
 	MAP_BL32_MEM,
@@ -108,6 +112,9 @@
 #ifdef MAP_DEVICE1
 	MAP_DEVICE1,
 #endif
+#ifdef MAP_DEVICE2
+	MAP_DEVICE2,
+#endif
 	{0}
 };
 #endif
diff --git a/plat/qemu/common/qemu_pm.c b/plat/qemu/common/qemu_pm.c
index cf80009..c2b5091 100644
--- a/plat/qemu/common/qemu_pm.c
+++ b/plat/qemu/common/qemu_pm.c
@@ -12,6 +12,7 @@
 #include <lib/psci/psci.h>
 #include <lib/semihosting.h>
 #include <plat/common/platform.h>
+#include <drivers/gpio.h>
 
 #include "qemu_private.h"
 
@@ -201,16 +202,31 @@
 /*******************************************************************************
  * Platform handlers to shutdown/reboot the system
  ******************************************************************************/
+
 static void __dead2 qemu_system_off(void)
 {
+#ifdef SECURE_GPIO_BASE
+	ERROR("QEMU System Power off: with GPIO.\n");
+	gpio_set_direction(SECURE_GPIO_POWEROFF, GPIO_DIR_OUT);
+	gpio_set_value(SECURE_GPIO_POWEROFF, GPIO_LEVEL_LOW);
+	gpio_set_value(SECURE_GPIO_POWEROFF, GPIO_LEVEL_HIGH);
+#else
 	semihosting_exit(ADP_STOPPED_APPLICATION_EXIT, 0);
 	ERROR("QEMU System Off: semihosting call unexpectedly returned.\n");
+#endif
 	panic();
 }
 
 static void __dead2 qemu_system_reset(void)
 {
+	ERROR("QEMU System Reset: with GPIO.\n");
+#ifdef SECURE_GPIO_BASE
+	gpio_set_direction(SECURE_GPIO_RESET, GPIO_DIR_OUT);
+	gpio_set_value(SECURE_GPIO_RESET, GPIO_LEVEL_LOW);
+	gpio_set_value(SECURE_GPIO_RESET, GPIO_LEVEL_HIGH);
+#else
 	ERROR("QEMU System Reset: operation not handled.\n");
+#endif
 	panic();
 }
 
diff --git a/plat/qemu/common/qemu_spm.c b/plat/qemu/common/qemu_spm.c
index e9ab1a5..c66f47e 100644
--- a/plat/qemu/common/qemu_spm.c
+++ b/plat/qemu/common/qemu_spm.c
@@ -3,7 +3,12 @@
  * Copyright (c) 2020, Linaro Limited and Contributors. All rights reserved.
  */
 
+#include <libfdt.h>
+
 #include <bl31/ehf.h>
+#include <common/debug.h>
+#include <common/fdt_fixup.h>
+#include <common/fdt_wrappers.h>
 #include <lib/xlat_tables/xlat_tables_compat.h>
 #include <services/spm_mm_partition.h>
 
@@ -14,31 +19,20 @@
 					DEVICE1_SIZE,			\
 					MT_DEVICE | MT_RW | MT_SECURE | MT_USER)
 
-const mmap_region_t plat_qemu_secure_partition_mmap[] = {
-	MAP_DEVICE1_EL0, /* for the UART */
+mmap_region_t plat_qemu_secure_partition_mmap[] = {
+	QEMU_SP_IMAGE_NS_BUF_MMAP,	/* must be placed at first entry */
+	MAP_DEVICE1_EL0,		/* for the UART */
 	QEMU_SP_IMAGE_MMAP,
 	QEMU_SPM_BUF_EL0_MMAP,
-	QEMU_SP_IMAGE_NS_BUF_MMAP,
 	QEMU_SP_IMAGE_RW_MMAP,
+	MAP_SECURE_VARSTORE,
 	{0}
 };
 
-/*
- * Boot information passed to a secure partition during initialisation.
- * Linear indices in MP information will be filled at runtime.
- */
-static spm_mm_mp_info_t sp_mp_info[] = {
-	[0] = {0x80000000, 0},
-	[1] = {0x80000001, 0},
-	[2] = {0x80000002, 0},
-	[3] = {0x80000003, 0},
-	[4] = {0x80000004, 0},
-	[5] = {0x80000005, 0},
-	[6] = {0x80000006, 0},
-	[7] = {0x80000007, 0}
-};
+/* Boot information passed to a secure partition during initialisation. */
+static spm_mm_mp_info_t sp_mp_info[PLATFORM_CORE_COUNT];
 
-const spm_mm_boot_info_t plat_qemu_secure_partition_boot_info = {
+spm_mm_boot_info_t plat_qemu_secure_partition_boot_info = {
 	.h.type              = PARAM_SP_IMAGE_BOOT_INFO,
 	.h.version           = VERSION_1,
 	.h.size              = sizeof(spm_mm_boot_info_t),
@@ -65,17 +59,89 @@
 	EHF_PRI_DESC(QEMU_PRI_BITS, PLAT_SP_PRI)
 };
 
+static void qemu_initialize_mp_info(spm_mm_mp_info_t *mp_info)
+{
+	unsigned int i, j;
+	spm_mm_mp_info_t *tmp = mp_info;
+
+	for (i = 0; i < PLATFORM_CLUSTER_COUNT; i++) {
+		for (j = 0; j < PLATFORM_MAX_CPUS_PER_CLUSTER; j++) {
+			tmp->mpidr = (0x80000000 | (i << MPIDR_AFF1_SHIFT)) + j;
+			/*
+			 * Linear indices and flags will be filled
+			 * in the spm_mm service.
+			 */
+			tmp->linear_id = 0;
+			tmp->flags = 0;
+			tmp++;
+		}
+	}
+}
+
+int dt_add_ns_buf_node(uintptr_t *base)
+{
+	uintptr_t addr;
+	size_t size;
+	uintptr_t ns_buf_addr;
+	int node;
+	int err;
+	void *fdt = (void *)ARM_PRELOADED_DTB_BASE;
+
+	err = fdt_open_into(fdt, fdt, PLAT_QEMU_DT_MAX_SIZE);
+	if (err < 0) {
+		ERROR("Invalid Device Tree at %p: error %d\n", fdt, err);
+		return err;
+	}
+
+	/*
+	 * reserved-memory for standaloneMM non-secure buffer
+	 * is allocated at the top of the first system memory region.
+	 */
+	node = fdt_path_offset(fdt, "/memory");
+
+	err = fdt_get_reg_props_by_index(fdt, node, 0, &addr, &size);
+	if (err < 0) {
+		ERROR("Failed to get the memory node information\n");
+		return err;
+	}
+	INFO("System RAM @ 0x%lx - 0x%lx\n", addr, addr + size - 1);
+
+	ns_buf_addr = addr + (size - PLAT_QEMU_SP_IMAGE_NS_BUF_SIZE);
+	INFO("reserved-memory for spm-mm @ 0x%lx - 0x%llx\n", ns_buf_addr,
+	     ns_buf_addr + PLAT_QEMU_SP_IMAGE_NS_BUF_SIZE - 1);
+
+	err = fdt_add_reserved_memory(fdt, "ns-buf-spm-mm", ns_buf_addr,
+				      PLAT_QEMU_SP_IMAGE_NS_BUF_SIZE);
+	if (err < 0) {
+		ERROR("Failed to add the reserved-memory node\n");
+		return err;
+	}
+
+	*base = ns_buf_addr;
+	return 0;
+}
+
 /* Plug in QEMU exceptions to Exception Handling Framework. */
 EHF_REGISTER_PRIORITIES(qemu_exceptions, ARRAY_SIZE(qemu_exceptions),
 			QEMU_PRI_BITS);
 
 const mmap_region_t *plat_get_secure_partition_mmap(void *cookie)
 {
+	uintptr_t ns_buf_base;
+
+	dt_add_ns_buf_node(&ns_buf_base);
+
+	plat_qemu_secure_partition_mmap[0].base_pa = ns_buf_base;
+	plat_qemu_secure_partition_mmap[0].base_va = ns_buf_base;
+	plat_qemu_secure_partition_boot_info.sp_ns_comm_buf_base = ns_buf_base;
+
 	return plat_qemu_secure_partition_mmap;
 }
 
 const spm_mm_boot_info_t *
 plat_get_secure_partition_boot_info(void *cookie)
 {
+	qemu_initialize_mp_info(sp_mp_info);
+
 	return &plat_qemu_secure_partition_boot_info;
 }
diff --git a/plat/qemu/common/qemu_stack_protector.c b/plat/qemu/common/qemu_stack_protector.c
index c226158..15ce3d6 100644
--- a/plat/qemu/common/qemu_stack_protector.c
+++ b/plat/qemu/common/qemu_stack_protector.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,17 +7,25 @@
 #include <stdint.h>
 
 #include <arch_helpers.h>
+#include <arch_features.h>
 #include <plat/common/platform.h>
 
 #define RANDOM_CANARY_VALUE ((u_register_t) 3288484550995823360ULL)
 
 u_register_t plat_get_stack_protector_canary(void)
 {
+#if ENABLE_FEAT_RNG
+	/* Use the RNDR instruction if the CPU supports it */
+	if (is_armv8_5_rng_present()) {
+		return read_rndr();
+	}
+#endif
+
 	/*
-	 * Ideally, a random number should be returned instead of the
+	 * Ideally, a random number should be returned above. If a random
+	 * number generator is not supported, return instead a
 	 * combination of a timer's value and a compile-time constant.
-	 * As the virt platform does not have any random number generator,
-	 * this is better than nothing but not necessarily really secure.
+	 * This is better than nothing but not necessarily really secure.
 	 */
 	return RANDOM_CANARY_VALUE ^ read_cntpct_el0();
 }
diff --git a/plat/qemu/qemu/include/platform_def.h b/plat/qemu/qemu/include/platform_def.h
index 9109056..dbc47eb 100644
--- a/plat/qemu/qemu/include/platform_def.h
+++ b/plat/qemu/qemu/include/platform_def.h
@@ -24,6 +24,14 @@
 #define PLATFORM_CLUSTER1_CORE_COUNT	U(0)
 #else
 #define PLATFORM_MAX_CPUS_PER_CLUSTER	U(4)
+/*
+ * Define the number of cores per cluster used in calculating core position.
+ * The cluster number is shifted by this value and added to the core ID,
+ * so its value represents log2(cores/cluster).
+ * Default is 2**(2) = 4 cores per cluster.
+ */
+#define PLATFORM_CPU_PER_CLUSTER_SHIFT	U(2)
+
 #define PLATFORM_CLUSTER_COUNT		U(2)
 #define PLATFORM_CLUSTER0_CORE_COUNT	PLATFORM_MAX_CPUS_PER_CLUSTER
 #define PLATFORM_CLUSTER1_CORE_COUNT	PLATFORM_MAX_CPUS_PER_CLUSTER
@@ -72,8 +80,8 @@
 #define SEC_ROM_BASE			0x00000000
 #define SEC_ROM_SIZE			0x00020000
 
-#define NS_DRAM0_BASE			0x40000000
-#define NS_DRAM0_SIZE			0x3de00000
+#define NS_DRAM0_BASE			ULL(0x40000000)
+#define NS_DRAM0_SIZE			ULL(0xc0000000)
 
 #define SEC_SRAM_BASE			0x0e000000
 #define SEC_SRAM_SIZE			0x00100000
@@ -81,6 +89,11 @@
 #define SEC_DRAM_BASE			0x0e100000
 #define SEC_DRAM_SIZE			0x2ff00000
 
+#define SECURE_GPIO_BASE		0x090b0000
+#define SECURE_GPIO_SIZE		0x00001000
+#define SECURE_GPIO_POWEROFF		0
+#define SECURE_GPIO_RESET		1
+
 /* Load pageable part of OP-TEE 2MB above secure DRAM base */
 #define QEMU_OPTEE_PAGEABLE_LOAD_BASE	(SEC_DRAM_BASE + 0x00200000)
 #define QEMU_OPTEE_PAGEABLE_LOAD_SIZE	0x00400000
@@ -202,7 +215,7 @@
 #define DEVICE0_BASE			0x08000000
 #define DEVICE0_SIZE			0x01000000
 #define DEVICE1_BASE			0x09000000
-#define DEVICE1_SIZE			0x00041000
+#define DEVICE1_SIZE			0x00c00000
 
 /*
  * GIC related constants
diff --git a/plat/qemu/qemu/platform.mk b/plat/qemu/qemu/platform.mk
index 14bf049..a3b353f 100644
--- a/plat/qemu/qemu/platform.mk
+++ b/plat/qemu/qemu/platform.mk
@@ -107,7 +107,10 @@
 ifeq (${ARM_ARCH_MAJOR},8)
 BL1_SOURCES		+=	lib/cpus/aarch64/aem_generic.S		\
 				lib/cpus/aarch64/cortex_a53.S		\
-				lib/cpus/aarch64/cortex_a57.S
+				lib/cpus/aarch64/cortex_a57.S		\
+				lib/cpus/aarch64/cortex_a72.S		\
+				lib/cpus/aarch64/qemu_max.S		\
+
 else
 BL1_SOURCES		+=	lib/cpus/${ARCH}/cortex_a15.S
 endif
@@ -135,9 +138,9 @@
 BL2_SOURCES		+=	drivers/io/io_encrypted.c
 endif
 
-QEMU_GICV2_SOURCES	:=	drivers/arm/gic/v2/gicv2_helpers.c	\
-				drivers/arm/gic/v2/gicv2_main.c		\
-				drivers/arm/gic/common/gic_common.c	\
+# Include GICv2 driver files
+include drivers/arm/gic/v2/gicv2.mk
+QEMU_GICV2_SOURCES	:=	${GICV2_SOURCES}			\
 				plat/common/plat_gicv2.c		\
 				${PLAT_QEMU_COMMON_PATH}/qemu_gicv2.c
 
@@ -160,9 +163,13 @@
 BL31_SOURCES		+=	lib/cpus/aarch64/aem_generic.S		\
 				lib/cpus/aarch64/cortex_a53.S		\
 				lib/cpus/aarch64/cortex_a57.S		\
+				lib/cpus/aarch64/cortex_a72.S		\
+				lib/cpus/aarch64/qemu_max.S		\
 				lib/semihosting/semihosting.c		\
 				lib/semihosting/${ARCH}/semihosting_call.S \
 				plat/common/plat_psci_common.c		\
+				drivers/arm/pl061/pl061_gpio.c		\
+				drivers/gpio/gpio.c			\
 				${PLAT_QEMU_COMMON_PATH}/qemu_pm.c			\
 				${PLAT_QEMU_COMMON_PATH}/topology.c			\
 				${PLAT_QEMU_COMMON_PATH}/aarch64/plat_helpers.S	\
diff --git a/plat/qemu/qemu_sbsa/include/platform_def.h b/plat/qemu/qemu_sbsa/include/platform_def.h
index 7634005..d971ebe 100644
--- a/plat/qemu/qemu_sbsa/include/platform_def.h
+++ b/plat/qemu/qemu_sbsa/include/platform_def.h
@@ -16,13 +16,17 @@
 
 #define PLATFORM_STACK_SIZE		0x1000
 
-#define PLATFORM_MAX_CPUS_PER_CLUSTER	U(4)
-#define PLATFORM_CLUSTER_COUNT		U(2)
-#define PLATFORM_CLUSTER0_CORE_COUNT	PLATFORM_MAX_CPUS_PER_CLUSTER
-#define PLATFORM_CLUSTER1_CORE_COUNT	PLATFORM_MAX_CPUS_PER_CLUSTER
-#define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER0_CORE_COUNT + \
-					 PLATFORM_CLUSTER1_CORE_COUNT)
-
+#define PLATFORM_MAX_CPUS_PER_CLUSTER	U(8)
+/*
+ * Define the number of cores per cluster used in calculating core position.
+ * The cluster number is shifted by this value and added to the core ID,
+ * so its value represents log2(cores/cluster).
+ * Default is 2**(3) = 8 cores per cluster.
+ */
+#define PLATFORM_CPU_PER_CLUSTER_SHIFT	U(3)
+#define PLATFORM_CLUSTER_COUNT		U(64)
+#define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER_COUNT * \
+					PLATFORM_MAX_CPUS_PER_CLUSTER)
 #define QEMU_PRIMARY_CPU		U(0)
 
 #define PLAT_NUM_PWR_DOMAINS		(PLATFORM_CLUSTER_COUNT + \
@@ -85,7 +89,7 @@
  */
 
 #define SHARED_RAM_BASE			SEC_SRAM_BASE
-#define SHARED_RAM_SIZE			0x00001000
+#define SHARED_RAM_SIZE			0x00002000
 
 #define PLAT_QEMU_TRUSTED_MAILBOX_BASE	SHARED_RAM_BASE
 #define PLAT_QEMU_TRUSTED_MAILBOX_SIZE	(8 + PLAT_QEMU_HOLD_SIZE)
@@ -130,7 +134,7 @@
  * Put BL3-1 at the top of the Trusted SRAM. BL31_BASE is calculated using the
  * current BL3-1 debug size plus a little space for growth.
  */
-#define BL31_SIZE			0x50000
+#define BL31_SIZE			0x300000
 #define BL31_BASE			(BL31_LIMIT - BL31_SIZE)
 #define BL31_LIMIT			(BL1_RW_BASE)
 #define BL31_PROGBITS_LIMIT		BL1_RW_BASE
@@ -157,17 +161,17 @@
 #define PLAT_VIRT_ADDR_SPACE_SIZE	(1ull << 42)
 #if SPM_MM
 #define MAX_MMAP_REGIONS		12
-#define MAX_XLAT_TABLES			11
+#define MAX_XLAT_TABLES			12
 #else
 #define MAX_MMAP_REGIONS		11
-#define MAX_XLAT_TABLES			10
+#define MAX_XLAT_TABLES			11
 #endif
 #define MAX_IO_DEVICES			3
 #define MAX_IO_HANDLES			4
 
 #if SPM_MM && defined(IMAGE_BL31)
 # define PLAT_SP_IMAGE_MMAP_REGIONS	30
-# define PLAT_SP_IMAGE_MAX_XLAT_TABLES	20
+# define PLAT_SP_IMAGE_MAX_XLAT_TABLES	50
 #endif
 
 /*
@@ -203,7 +207,10 @@
 #define DEVICE0_SIZE			0x04080000
 /* This is map from NORMAL_UART up to SECURE_UART_MM */
 #define DEVICE1_BASE			0x60000000
-#define DEVICE1_SIZE			0x00041000
+#define DEVICE1_SIZE			0x10041000
+/* This is a map for SECURE_EC */
+#define DEVICE2_BASE			0x50000000
+#define DEVICE2_SIZE			0x00001000
 
 /*
  * GIC related constants
@@ -300,10 +307,13 @@
 /*
  * Shared memory between Normal world and S-EL0 for
  * passing data during service requests. It will be marked as RW and NS.
+ * This buffer is allocated at the top of NS_DRAM, the base address is
+ * overridden in SPM initialization.
  */
 #define PLAT_QEMU_SP_IMAGE_NS_BUF_BASE	(PLAT_QEMU_DT_BASE +		\
 						PLAT_QEMU_DT_MAX_SIZE)
-#define PLAT_QEMU_SP_IMAGE_NS_BUF_SIZE	ULL(0x10000)
+#define PLAT_QEMU_SP_IMAGE_NS_BUF_SIZE	ULL(0x200000)
+
 #define QEMU_SP_IMAGE_NS_BUF_MMAP	MAP_REGION2( \
 					PLAT_QEMU_SP_IMAGE_NS_BUF_BASE, \
 					PLAT_QEMU_SP_IMAGE_NS_BUF_BASE, \
@@ -334,6 +344,19 @@
 					MT_USER, \
 					PAGE_SIZE)
 
+/*
+ * Secure variable storage is located at Secure Flash.
+ */
+#if SPM_MM
+#define QEMU_SECURE_VARSTORE_BASE 0x01000000
+#define QEMU_SECURE_VARSTORE_SIZE 0x00100000
+#define MAP_SECURE_VARSTORE		MAP_REGION_FLAT( \
+					QEMU_SECURE_VARSTORE_BASE, \
+					QEMU_SECURE_VARSTORE_SIZE, \
+					MT_DEVICE | MT_RW | \
+					MT_SECURE | MT_USER)
+#endif
+
 /* Total number of memory regions with distinct properties */
 #define PLAT_QEMU_SP_IMAGE_NUM_MEM_REGIONS	6
 
diff --git a/plat/qemu/qemu_sbsa/platform.mk b/plat/qemu/qemu_sbsa/platform.mk
index 9be56a3..5a6b1e1 100644
--- a/plat/qemu/qemu_sbsa/platform.mk
+++ b/plat/qemu/qemu_sbsa/platform.mk
@@ -1,9 +1,11 @@
 #
-# Copyright (c) 2019-2020, Linaro Limited and Contributors. All rights reserved.
+# Copyright (c) 2019-2021, Linaro Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include common/fdt_wrappers.mk
+
 CRASH_REPORTING	:=	1
 
 include lib/libfdt/libfdt.mk
@@ -47,7 +49,9 @@
 				${PLAT_QEMU_COMMON_PATH}/${ARCH}/plat_helpers.S	\
 				${PLAT_QEMU_COMMON_PATH}/qemu_bl1_setup.c
 
-BL1_SOURCES		+=	lib/cpus/aarch64/cortex_a57.S
+BL1_SOURCES		+=	lib/cpus/aarch64/cortex_a57.S			\
+				lib/cpus/aarch64/cortex_a72.S			\
+				lib/cpus/aarch64/qemu_max.S			\
 
 BL2_SOURCES		+=	drivers/io/io_semihosting.c			\
 				drivers/io/io_storage.c				\
@@ -74,14 +78,20 @@
 				${PLAT_QEMU_COMMON_PATH}/qemu_gicv3.c
 
 BL31_SOURCES		+=	lib/cpus/aarch64/cortex_a57.S			\
+				lib/cpus/aarch64/cortex_a72.S			\
+				lib/cpus/aarch64/qemu_max.S			\
 				lib/semihosting/semihosting.c			\
 				lib/semihosting/${ARCH}/semihosting_call.S	\
 				plat/common/plat_psci_common.c			\
-				${PLAT_QEMU_COMMON_PATH}/qemu_pm.c		\
-				${PLAT_QEMU_COMMON_PATH}/topology.c		\
+				${PLAT_QEMU_PATH}/sbsa_pm.c			\
+				${PLAT_QEMU_PATH}/sbsa_topology.c		\
 				${PLAT_QEMU_COMMON_PATH}/aarch64/plat_helpers.S	\
 				${PLAT_QEMU_COMMON_PATH}/qemu_bl31_setup.c	\
+				common/fdt_fixup.c				\
 				${QEMU_GIC_SOURCES}
+
+BL31_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
 ifeq (${SPM_MM},1)
 	BL31_SOURCES		+=	${PLAT_QEMU_COMMON_PATH}/qemu_spm.c
 endif
diff --git a/plat/qemu/qemu_sbsa/sbsa_pm.c b/plat/qemu/qemu_sbsa/sbsa_pm.c
new file mode 100644
index 0000000..8d1e1d4
--- /dev/null
+++ b/plat/qemu/qemu_sbsa/sbsa_pm.c
@@ -0,0 +1,237 @@
+/*
+ * Copyright (c) 2020, Nuvia Inc
+ * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+
+#include <arch_helpers.h>
+#include <assert.h>
+#include <lib/mmio.h>
+#include <lib/psci/psci.h>
+#include <plat/common/platform.h>
+
+#include <platform_def.h>
+#include "sbsa_private.h"
+
+#define ADP_STOPPED_APPLICATION_EXIT 0x20026
+
+/*
+ * Define offset and commands for the fake EC device
+ */
+#define SBSA_SECURE_EC_OFFSET 0x50000000
+
+#define SBSA_SECURE_EC_CMD_SHUTDOWN 0x01
+#define SBSA_SECURE_EC_CMD_REBOOT   0x02
+
+/*
+ * The secure entry point to be used on warm reset.
+ */
+static unsigned long secure_entrypoint;
+
+/* Make composite power state parameter till power level 0 */
+#if PSCI_EXTENDED_STATE_ID
+
+#define qemu_make_pwrstate_lvl0(lvl0_state, pwr_lvl, type) \
+		(((lvl0_state) << PSTATE_ID_SHIFT) | \
+		 ((type) << PSTATE_TYPE_SHIFT))
+#else
+#define qemu_make_pwrstate_lvl0(lvl0_state, pwr_lvl, type) \
+		(((lvl0_state) << PSTATE_ID_SHIFT) | \
+		 ((pwr_lvl) << PSTATE_PWR_LVL_SHIFT) | \
+		 ((type) << PSTATE_TYPE_SHIFT))
+#endif /* PSCI_EXTENDED_STATE_ID */
+
+
+#define qemu_make_pwrstate_lvl1(lvl1_state, lvl0_state, pwr_lvl, type) \
+		(((lvl1_state) << PLAT_LOCAL_PSTATE_WIDTH) | \
+		 qemu_make_pwrstate_lvl0(lvl0_state, pwr_lvl, type))
+
+
+
+/*
+ *  The table storing the valid idle power states. Ensure that the
+ *  array entries are populated in ascending order of state-id to
+ *  enable us to use binary search during power state validation.
+ *  The table must be terminated by a NULL entry.
+ */
+static const unsigned int qemu_pm_idle_states[] = {
+	/* State-id - 0x01 */
+	qemu_make_pwrstate_lvl1(PLAT_LOCAL_STATE_RUN, PLAT_LOCAL_STATE_RET,
+				MPIDR_AFFLVL0, PSTATE_TYPE_STANDBY),
+	/* State-id - 0x02 */
+	qemu_make_pwrstate_lvl1(PLAT_LOCAL_STATE_RUN, PLAT_LOCAL_STATE_OFF,
+				MPIDR_AFFLVL0, PSTATE_TYPE_POWERDOWN),
+	/* State-id - 0x22 */
+	qemu_make_pwrstate_lvl1(PLAT_LOCAL_STATE_OFF, PLAT_LOCAL_STATE_OFF,
+				MPIDR_AFFLVL1, PSTATE_TYPE_POWERDOWN),
+	0
+};
+
+/*******************************************************************************
+ * Platform handler called to check the validity of the power state
+ * parameter. The power state parameter has to be a composite power state.
+ ******************************************************************************/
+static int qemu_validate_power_state(unsigned int power_state,
+				psci_power_state_t *req_state)
+{
+	unsigned int state_id;
+	unsigned int i;
+
+	assert(req_state != NULL);
+
+	/*
+	 *  Currently we are using a linear search for finding the matching
+	 *  entry in the idle power state array. This can be made a binary
+	 *  search if the number of entries justifies the additional complexity.
+	 */
+	for (i = 0U; qemu_pm_idle_states[i] != 0U; i++) {
+		if (power_state == qemu_pm_idle_states[i]) {
+			break;
+		}
+	}
+
+	/* Return error if entry not found in the idle state array */
+	if (qemu_pm_idle_states[i] == 0U) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	i = 0U;
+	state_id = psci_get_pstate_id(power_state);
+
+	/* Parse the State ID and populate the state info parameter */
+	while (state_id != 0U) {
+		req_state->pwr_domain_state[i++] = state_id &
+						PLAT_LOCAL_PSTATE_MASK;
+		state_id >>= PLAT_LOCAL_PSTATE_WIDTH;
+	}
+
+	return PSCI_E_SUCCESS;
+}
+
+/*******************************************************************************
+ * Platform handler called when a CPU is about to enter standby.
+ ******************************************************************************/
+static void qemu_cpu_standby(plat_local_state_t cpu_state)
+{
+
+	assert(cpu_state == PLAT_LOCAL_STATE_RET);
+
+	/*
+	 * Enter standby state
+	 * dsb is good practice before using wfi to enter low power states
+	 */
+	dsb();
+	wfi();
+}
+
+/*******************************************************************************
+ * Platform handler called when a power domain is about to be turned on. The
+ * mpidr determines the CPU to be turned on.
+ ******************************************************************************/
+static int qemu_pwr_domain_on(u_register_t mpidr)
+{
+	int pos = plat_core_pos_by_mpidr(mpidr);
+	uint64_t *hold_base = (uint64_t *)PLAT_QEMU_HOLD_BASE;
+
+	if (pos < 0) {
+		return PSCI_E_INVALID_PARAMS;
+	}
+
+	hold_base[pos] = PLAT_QEMU_HOLD_STATE_GO;
+	dsb();
+	sev();
+
+	return PSCI_E_SUCCESS;
+}
+
+/*******************************************************************************
+ * Platform handler called when a power domain is about to be turned off. The
+ * target_state encodes the power state that each level should transition to.
+ ******************************************************************************/
+static void qemu_pwr_domain_off(const psci_power_state_t *target_state)
+{
+	qemu_pwr_gic_off();
+}
+
+void __dead2 plat_secondary_cold_boot_setup(void);
+
+static void __dead2
+qemu_pwr_domain_pwr_down_wfi(const psci_power_state_t *target_state)
+{
+	disable_mmu_el3();
+	plat_secondary_cold_boot_setup();
+}
+
+/*******************************************************************************
+ * Platform handler called when a power domain is about to be suspended. The
+ * target_state encodes the power state that each level should transition to.
+ ******************************************************************************/
+void qemu_pwr_domain_suspend(const psci_power_state_t *target_state)
+{
+	assert(false);
+}
+
+/*******************************************************************************
+ * Platform handler called when a power domain has just been powered on after
+ * being turned off earlier. The target_state encodes the low power state that
+ * each level has woken up from.
+ ******************************************************************************/
+void qemu_pwr_domain_on_finish(const psci_power_state_t *target_state)
+{
+	assert(target_state->pwr_domain_state[MPIDR_AFFLVL0] ==
+					PLAT_LOCAL_STATE_OFF);
+
+	qemu_pwr_gic_on_finish();
+}
+
+/*******************************************************************************
+ * Platform handler called when a power domain has just been powered on after
+ * having been suspended earlier. The target_state encodes the low power state
+ * that each level has woken up from.
+ ******************************************************************************/
+void qemu_pwr_domain_suspend_finish(const psci_power_state_t *target_state)
+{
+	assert(false);
+}
+
+/*******************************************************************************
+ * Platform handlers to shutdown/reboot the system
+ ******************************************************************************/
+static void __dead2 qemu_system_off(void)
+{
+	mmio_write_32(SBSA_SECURE_EC_OFFSET, SBSA_SECURE_EC_CMD_SHUTDOWN);
+	panic();
+}
+
+static void __dead2 qemu_system_reset(void)
+{
+	mmio_write_32(SBSA_SECURE_EC_OFFSET, SBSA_SECURE_EC_CMD_REBOOT);
+	panic();
+}
+
+static const plat_psci_ops_t plat_qemu_psci_pm_ops = {
+	.cpu_standby = qemu_cpu_standby,
+	.pwr_domain_on = qemu_pwr_domain_on,
+	.pwr_domain_off = qemu_pwr_domain_off,
+	.pwr_domain_pwr_down_wfi = qemu_pwr_domain_pwr_down_wfi,
+	.pwr_domain_suspend = qemu_pwr_domain_suspend,
+	.pwr_domain_on_finish = qemu_pwr_domain_on_finish,
+	.pwr_domain_suspend_finish = qemu_pwr_domain_suspend_finish,
+	.system_off = qemu_system_off,
+	.system_reset = qemu_system_reset,
+	.validate_power_state = qemu_validate_power_state
+};
+
+int plat_setup_psci_ops(uintptr_t sec_entrypoint,
+			const plat_psci_ops_t **psci_ops)
+{
+	uintptr_t *mailbox = (uintptr_t *)PLAT_QEMU_TRUSTED_MAILBOX_BASE;
+
+	*mailbox = sec_entrypoint;
+	secure_entrypoint = (unsigned long)sec_entrypoint;
+	*psci_ops = &plat_qemu_psci_pm_ops;
+
+	return 0;
+}
diff --git a/plat/qemu/qemu_sbsa/sbsa_private.h b/plat/qemu/qemu_sbsa/sbsa_private.h
new file mode 100644
index 0000000..a9f4601
--- /dev/null
+++ b/plat/qemu/qemu_sbsa/sbsa_private.h
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2020, Nuvia Inc
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef SBSA_PRIVATE_H
+#define SBSA_PRIVATE_H
+
+#include <stdint.h>
+
+unsigned int plat_qemu_calc_core_pos(u_register_t mpidr);
+
+void qemu_pwr_gic_on_finish(void);
+void qemu_pwr_gic_off(void);
+
+#endif /* SBSA_PRIVATE_H */
diff --git a/plat/qemu/qemu_sbsa/sbsa_topology.c b/plat/qemu/qemu_sbsa/sbsa_topology.c
new file mode 100644
index 0000000..bd8d16b
--- /dev/null
+++ b/plat/qemu/qemu_sbsa/sbsa_topology.c
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2020, Nuvia Inc
+ * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <common/debug.h>
+
+#include <platform_def.h>
+#include "sbsa_private.h"
+
+/* The power domain tree descriptor */
+static unsigned char power_domain_tree_desc[PLATFORM_CLUSTER_COUNT + 1];
+
+/*******************************************************************************
+ * This function returns the sbsa-ref default topology tree information.
+ ******************************************************************************/
+const unsigned char *plat_get_power_domain_tree_desc(void)
+{
+	unsigned int i;
+
+	power_domain_tree_desc[0] = PLATFORM_CLUSTER_COUNT;
+
+	for (i = 0U; i < PLATFORM_CLUSTER_COUNT; i++) {
+		power_domain_tree_desc[i + 1] = PLATFORM_MAX_CPUS_PER_CLUSTER;
+	}
+
+	return power_domain_tree_desc;
+}
+
+/*******************************************************************************
+ * This function implements a part of the critical interface between the psci
+ * generic layer and the platform that allows the former to query the platform
+ * to convert an MPIDR to a unique linear index. An error code (-1) is returned
+ * in case the MPIDR is invalid.
+ ******************************************************************************/
+int plat_core_pos_by_mpidr(u_register_t mpidr)
+{
+	unsigned int cluster_id, cpu_id;
+
+	mpidr &= MPIDR_AFFINITY_MASK;
+	if ((mpidr & ~(MPIDR_CLUSTER_MASK | MPIDR_CPU_MASK)) != 0U) {
+		ERROR("Invalid MPIDR\n");
+		return -1;
+	}
+
+	cluster_id = (mpidr >> MPIDR_AFF1_SHIFT) & MPIDR_AFFLVL_MASK;
+	cpu_id = (mpidr >> MPIDR_AFF0_SHIFT) & MPIDR_AFFLVL_MASK;
+
+	if (cluster_id >= PLATFORM_CLUSTER_COUNT) {
+		ERROR("cluster_id >= PLATFORM_CLUSTER_COUNT define\n");
+		return -1;
+	}
+
+	if (cpu_id >= PLATFORM_MAX_CPUS_PER_CLUSTER) {
+		ERROR("cpu_id >= PLATFORM_MAX_CPUS_PER_CLUSTER define\n");
+		return -1;
+	}
+
+	return plat_qemu_calc_core_pos(mpidr);
+}
diff --git a/plat/qti/common/inc/qti_cpu.h b/plat/qti/common/inc/qti_cpu.h
index 3eda02b..3316f7b 100644
--- a/plat/qti/common/inc/qti_cpu.h
+++ b/plat/qti/common/inc/qti_cpu.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,4 +13,10 @@
 /* KRYO-4xx Silver MIDR */
 #define QTI_KRYO4_SILVER_MIDR	0x517F805D
 
+/* KRYO-6xx Gold MIDR */
+#define QTI_KRYO6_GOLD_MIDR	0x412FD410
+
+/* KRYO-6xx Silver MIDR */
+#define QTI_KRYO6_SILVER_MIDR	0x412FD050
+
 #endif /* QTI_CPU_H */
diff --git a/plat/qti/common/src/aarch64/qti_kryo6_gold.S b/plat/qti/common/src/aarch64/qti_kryo6_gold.S
new file mode 100644
index 0000000..db1a304
--- /dev/null
+++ b/plat/qti/common/src/aarch64/qti_kryo6_gold.S
@@ -0,0 +1,83 @@
+/*
+ * Copyright (c) 2015-2018, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <cpu_macros.S>
+
+#include <plat_macros.S>
+#include <qti_cpu.h>
+
+	.p2align 3
+
+/* -------------------------------------------------
+ * The CPU Ops reset function for Kryo-3 Gold
+ * -------------------------------------------------
+ */
+func qti_kryo6_gold_reset_func
+#if IMAGE_BL31 && WORKAROUND_CVE_2017_5715
+	adr	x0, wa_cve_2017_5715_bpiall_vbar
+	msr	vbar_el3, x0
+	isb
+#endif
+
+	mov	x19, x30
+
+	bl	qtiseclib_kryo6_gold_reset_asm
+
+	ret	x19
+
+endfunc qti_kryo6_gold_reset_func
+
+/* ----------------------------------------------------
+ * The CPU Ops core power down function for Kryo-3 Gold
+ * ----------------------------------------------------
+ */
+func qti_kryo6_gold_core_pwr_dwn
+	ret
+endfunc qti_kryo6_gold_core_pwr_dwn
+
+/* -------------------------------------------------------
+ * The CPU Ops cluster power down function for Kryo-3 Gold
+ * -------------------------------------------------------
+ */
+func qti_kryo6_gold_cluster_pwr_dwn
+	ret
+endfunc qti_kryo6_gold_cluster_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Kryo4 Gold. Must follow AAPCS.
+ */
+func qti_kryo6_gold_errata_report
+	/* TODO : Need to add support. Required only for debug bl31 image.*/
+	ret
+endfunc qti_kryo6_gold_errata_report
+#endif
+
+/* ---------------------------------------------
+ * This function provides kryo4_gold 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.qti_kryo4_gold_regs, "aS"
+qti_kryo6_gold_regs:  /* The ASCII list of register names to be reported */
+	.asciz	""
+
+func qti_kryo6_gold_cpu_reg_dump
+	adr	x6, qti_kryo6_gold_regs
+	ret
+endfunc qti_kryo6_gold_cpu_reg_dump
+
+declare_cpu_ops	qti_kryo6_gold, QTI_KRYO6_GOLD_MIDR,	\
+		qti_kryo6_gold_reset_func,		\
+		qti_kryo6_gold_core_pwr_dwn,	\
+		qti_kryo6_gold_cluster_pwr_dwn
diff --git a/plat/qti/common/src/aarch64/qti_kryo6_silver.S b/plat/qti/common/src/aarch64/qti_kryo6_silver.S
new file mode 100644
index 0000000..2d189f2
--- /dev/null
+++ b/plat/qti/common/src/aarch64/qti_kryo6_silver.S
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2015-2018, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <cpu_macros.S>
+
+#include <plat_macros.S>
+#include <qti_cpu.h>
+
+	.p2align 3
+
+/* -------------------------------------------------
+ * The CPU Ops reset function for Kryo-3 Silver
+ * -------------------------------------------------
+ */
+func qti_kryo6_silver_reset_func
+	mov	x19, x30
+
+	bl	qtiseclib_kryo6_silver_reset_asm
+
+	ret	x19
+
+endfunc qti_kryo6_silver_reset_func
+
+/* ------------------------------------------------------
+ * The CPU Ops core power down function for Kryo-3 Silver
+ * ------------------------------------------------------
+ */
+func qti_kryo6_silver_core_pwr_dwn
+	ret
+endfunc qti_kryo6_silver_core_pwr_dwn
+
+/* ---------------------------------------------------------
+ * The CPU Ops cluster power down function for Kryo-3 Silver
+ * ---------------------------------------------------------
+ */
+func qti_kryo6_silver_cluster_pwr_dwn
+	ret
+endfunc qti_kryo6_silver_cluster_pwr_dwn
+
+#if REPORT_ERRATA
+/*
+ * Errata printing function for Kryo4 Silver. Must follow AAPCS.
+ */
+func qti_kryo6_silver_errata_report
+	/* TODO : Need to add support. Required only for debug bl31 image.*/
+	ret
+endfunc qti_kryo6_silver_errata_report
+#endif
+
+
+/* ---------------------------------------------
+ * This function provides kryo4_silver 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.qti_kryo4_silver_regs, "aS"
+qti_kryo6_silver_regs:  /* The ASCII list of register names to be reported */
+	.asciz	""
+
+func qti_kryo6_silver_cpu_reg_dump
+	adr	x6, qti_kryo6_silver_regs
+	ret
+endfunc qti_kryo6_silver_cpu_reg_dump
+
+
+declare_cpu_ops	qti_kryo6_silver, QTI_KRYO6_SILVER_MIDR,	\
+		qti_kryo6_silver_reset_func,		\
+		qti_kryo6_silver_core_pwr_dwn,		\
+		qti_kryo6_silver_cluster_pwr_dwn
diff --git a/plat/qti/common/src/pm8998.c b/plat/qti/common/src/pm8998.c
deleted file mode 100644
index b189a8b..0000000
--- a/plat/qti/common/src/pm8998.c
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 2020, Google LLC. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <drivers/delay_timer.h>
-
-#include <qti_plat.h>
-#include <spmi_arb.h>
-
-/*
- * This driver implements PON support for PM8998-compatible PMICs. This can
- * include other part numbers like PM6150.
- */
-
-#define PON_PS_HOLD_RESET_CTL		0x85a
-#define RESET_TYPE_WARM_RESET		1
-#define RESET_TYPE_SHUTDOWN		4
-
-#define PON_PS_HOLD_RESET_CTL2		0x85b
-#define S2_RESET_EN			BIT(7)
-
-static void configure_ps_hold(uint32_t reset_type)
-{
-	/* QTI recommends disabling reset for 10 cycles before reconfiguring. */
-	spmi_arb_write8(PON_PS_HOLD_RESET_CTL2, 0);
-	mdelay(1);
-
-	spmi_arb_write8(PON_PS_HOLD_RESET_CTL, reset_type);
-	spmi_arb_write8(PON_PS_HOLD_RESET_CTL2, S2_RESET_EN);
-	mdelay(1);
-}
-
-void qti_pmic_prepare_reset(void)
-{
-	configure_ps_hold(RESET_TYPE_WARM_RESET);
-}
-
-void qti_pmic_prepare_shutdown(void)
-{
-	configure_ps_hold(RESET_TYPE_SHUTDOWN);
-}
diff --git a/plat/qti/common/src/pm_ps_hold.c b/plat/qti/common/src/pm_ps_hold.c
new file mode 100644
index 0000000..208345c
--- /dev/null
+++ b/plat/qti/common/src/pm_ps_hold.c
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2020, Google LLC. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <drivers/delay_timer.h>
+
+#include <qti_plat.h>
+#include <spmi_arb.h>
+
+/*
+ * This driver implements PON support for PM8998-compatible PMICs. This can
+ * include other part numbers like PM6150.
+ */
+
+#define RESET_TYPE_WARM_RESET		1
+#define RESET_TYPE_SHUTDOWN		4
+
+#define S2_RESET_EN			BIT(7)
+
+static void configure_ps_hold(uint32_t reset_type)
+{
+	/* QTI recommends disabling reset for 10 cycles before reconfiguring. */
+	spmi_arb_write8(PON_PS_HOLD_RESET_CTL2, 0);
+	mdelay(1);
+
+	spmi_arb_write8(PON_PS_HOLD_RESET_CTL, reset_type);
+	spmi_arb_write8(PON_PS_HOLD_RESET_CTL2, S2_RESET_EN);
+	mdelay(1);
+}
+
+void qti_pmic_prepare_reset(void)
+{
+	configure_ps_hold(RESET_TYPE_WARM_RESET);
+}
+
+void qti_pmic_prepare_shutdown(void)
+{
+	configure_ps_hold(RESET_TYPE_SHUTDOWN);
+}
diff --git a/plat/qti/common/src/qti_common.c b/plat/qti/common/src/qti_common.c
index 9355eb7..da0eaec 100644
--- a/plat/qti/common/src/qti_common.c
+++ b/plat/qti/common/src/qti_common.c
@@ -176,14 +176,14 @@
 }
 
 /*****************************************************************************
- * plat_smccc_feature_available() - This function checks whether SMCCC feature
+ * plat_is_smccc_feature_available() - This function checks whether SMCCC feature
  *                                  is availabile for the platform or not.
  * @fid: SMCCC function id
  *
  * Return SMC_ARCH_CALL_SUCCESS if SMCCC feature is available and
  * SMC_ARCH_CALL_NOT_SUPPORTED otherwise.
  *****************************************************************************/
-int32_t plat_smccc_feature_available(u_register_t fid)
+int32_t plat_is_smccc_feature_available(u_register_t fid)
 {
 	switch (fid) {
 	case SMCCC_ARCH_SOC_ID:
diff --git a/plat/qti/common/src/qti_gic_v3.c b/plat/qti/common/src/qti_gic_v3.c
index a5e0ae7..f00267a 100644
--- a/plat/qti/common/src/qti_gic_v3.c
+++ b/plat/qti/common/src/qti_gic_v3.c
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2018-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -72,6 +72,16 @@
 	INTR_PROP_DESC(QTISECLIB_INT_ID_MMSS_NOC_ERROR,
 		       GIC_HIGHEST_SEC_PRIORITY, INTR_GROUP0,
 		       GIC_INTR_CFG_EDGE),
+#ifdef QTISECLIB_INT_ID_LPASS_AGNOC_ERROR
+	INTR_PROP_DESC(QTISECLIB_INT_ID_LPASS_AGNOC_ERROR, GIC_HIGHEST_SEC_PRIORITY,
+		       INTR_GROUP0,
+		       GIC_INTR_CFG_EDGE),
+#endif
+#ifdef QTISECLIB_INT_ID_NSP_NOC_ERROR
+	INTR_PROP_DESC(QTISECLIB_INT_ID_NSP_NOC_ERROR, GIC_HIGHEST_SEC_PRIORITY,
+		       INTR_GROUP0,
+		       GIC_INTR_CFG_EDGE),
+#endif
 };
 
 const gicv3_driver_data_t qti_gic_data = {
diff --git a/plat/qti/common/src/qti_syscall.c b/plat/qti/common/src/qti_syscall.c
index a7601b6..d8e5be9 100644
--- a/plat/qti/common/src/qti_syscall.c
+++ b/plat/qti/common/src/qti_syscall.c
@@ -21,6 +21,7 @@
 #include <qti_plat.h>
 #include <qti_secure_io_cfg.h>
 #include <qtiseclib_interface.h>
+
 /*
  * SIP service - SMC function IDs for SiP Service queries
  *
@@ -29,7 +30,7 @@
 #define	QTI_SIP_SVC_UID_ID				U(0x0200ff01)
 /*							0x8200ff02 is reserved*/
 #define	QTI_SIP_SVC_VERSION_ID				U(0x0200ff03)
-
+#define QTI_SIP_SVC_AVAILABLE_ID			U(0x02000601)
 /*
  * Syscall's to allow Non Secure world accessing peripheral/IO memory
  * those are secure/proteced BUT not required to be secure.
@@ -83,6 +84,22 @@
 	return false;
 }
 
+static bool qti_check_syscall_availability(u_register_t smc_fid)
+{
+	switch (smc_fid) {
+	case QTI_SIP_SVC_CALL_COUNT_ID:
+	case QTI_SIP_SVC_UID_ID:
+	case QTI_SIP_SVC_VERSION_ID:
+	case QTI_SIP_SVC_AVAILABLE_ID:
+	case QTI_SIP_SVC_SECURE_IO_READ_ID:
+	case QTI_SIP_SVC_SECURE_IO_WRITE_ID:
+	case QTI_SIP_SVC_MEM_ASSIGN_ID:
+		return true;
+	default:
+		return false;
+	}
+}
+
 bool qti_mem_assign_validate_param(memprot_info_t *mem_info,
 				   u_register_t u_num_mappings,
 				   uint32_t *source_vm_list,
@@ -315,6 +332,18 @@
 				 QTI_SIP_SVC_VERSION_MINOR);
 			break;
 		}
+	case QTI_SIP_SVC_AVAILABLE_ID:
+		{
+			if (x1 != 1) {
+				SMC_RET1(handle, QTI_SIP_INVALID_PARAM);
+			}
+			if (qti_check_syscall_availability(x2) == true) {
+				SMC_RET2(handle, QTI_SIP_SUCCESS, 1);
+			} else {
+				SMC_RET2(handle, QTI_SIP_SUCCESS, 0);
+			}
+			break;
+		}
 	case QTI_SIP_SVC_SECURE_IO_READ_ID:
 		{
 			if ((x1 == QTI_SIP_SVC_SECURE_IO_READ_PARAM_ID) &&
diff --git a/plat/qti/common/src/spmi_arb.c b/plat/qti/common/src/spmi_arb.c
index 16e85a6..4213ed1 100644
--- a/plat/qti/common/src/spmi_arb.c
+++ b/plat/qti/common/src/spmi_arb.c
@@ -10,8 +10,8 @@
 
 #include <spmi_arb.h>
 
-#define REG_APID_MAP(apid)	(0x0C440900U + 4U * i)
-#define NUM_APID		0x80
+#define REG_APID_MAP(apid)	(0x0C440900U + sizeof(uint32_t) * apid)
+#define NUM_APID		((0x1100U - 0x900U) / sizeof(uint32_t))
 
 #define PPID_MASK		(0xfffU << 8)
 
diff --git a/plat/qti/qtiseclib/inc/qtiseclib_interface.h b/plat/qti/qtiseclib/inc/qtiseclib_interface.h
index 315bd6b..babed1b 100644
--- a/plat/qti/qtiseclib/inc/qtiseclib_interface.h
+++ b/plat/qti/qtiseclib/inc/qtiseclib_interface.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -50,6 +50,14 @@
 void qtiseclib_kryo4_gold_reset_asm(void);
 
 /*
+ * Execute CPU (Kryo46 gold) specific reset handler / system initialization.
+ * This takes care of executing required CPU errata's.
+ *
+ * Clobbers: x0 - x16
+ */
+void qtiseclib_kryo6_gold_reset_asm(void);
+
+/*
  * Execute CPU (Kryo4 silver) specific reset handler / system initialization.
  * This takes care of executing required CPU errata's.
  *
@@ -58,6 +66,14 @@
 void qtiseclib_kryo4_silver_reset_asm(void);
 
 /*
+ * Execute CPU (Kryo6 silver) specific reset handler / system initialization.
+ * This takes care of executing required CPU errata's.
+ *
+ * Clobbers: x0 - x16
+ */
+void qtiseclib_kryo6_silver_reset_asm(void);
+
+/*
  * C Api's
  */
 void qtiseclib_bl31_platform_setup(void);
diff --git a/plat/qti/qtiseclib/inc/sc7280/qtiseclib_defs_plat.h b/plat/qti/qtiseclib/inc/sc7280/qtiseclib_defs_plat.h
new file mode 100644
index 0000000..b3d309f
--- /dev/null
+++ b/plat/qti/qtiseclib/inc/sc7280/qtiseclib_defs_plat.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef __QTISECLIB_DEFS_PLAT_H__
+#define __QTISECLIB_DEFS_PLAT_H__
+
+#define QTISECLIB_PLAT_CLUSTER_COUNT	1
+#define QTISECLIB_PLAT_CORE_COUNT	8
+
+#define BL31_BASE						0xC0000000
+#define BL31_SIZE						0x00100000
+
+/*----------------------------------------------------------------------------*/
+/* AOP CMD DB  address space for mapping */
+/*----------------------------------------------------------------------------*/
+#define QTI_AOP_CMD_DB_BASE			0x80860000
+#define QTI_AOP_CMD_DB_SIZE			0x00020000
+
+/* Chipset specific secure interrupt number/ID defs. */
+#define QTISECLIB_INT_ID_SEC_WDOG_BARK			(0x204)
+#define QTISECLIB_INT_ID_NON_SEC_WDOG_BITE		(0x21)
+
+#define QTISECLIB_INT_ID_VMIDMT_ERR_CLT_SEC		(0xE6)
+#define QTISECLIB_INT_ID_VMIDMT_ERR_CLT_NONSEC		(0xE7)
+#define QTISECLIB_INT_ID_VMIDMT_ERR_CFG_SEC		(0xE8)
+#define QTISECLIB_INT_ID_VMIDMT_ERR_CFG_NONSEC		(0xE9)
+
+#define QTISECLIB_INT_ID_XPU_SEC			(0xE3)
+#define QTISECLIB_INT_ID_XPU_NON_SEC			(0xE4)
+
+//NOC INterrupt
+#define QTISECLIB_INT_ID_A1_NOC_ERROR			(0xC9)
+#define QTISECLIB_INT_ID_A2_NOC_ERROR			(0xEA)
+#define QTISECLIB_INT_ID_CONFIG_NOC_ERROR		(0xE2)
+#define QTISECLIB_INT_ID_DC_NOC_ERROR			(0x122)
+#define QTISECLIB_INT_ID_MEM_NOC_ERROR			(0x6C)
+#define QTISECLIB_INT_ID_SYSTEM_NOC_ERROR		(0xC8)
+#define QTISECLIB_INT_ID_MMSS_NOC_ERROR			(0xBA)
+#define QTISECLIB_INT_ID_LPASS_AGNOC_ERROR		(0x143)
+#define QTISECLIB_INT_ID_NSP_NOC_ERROR			(0x1CE)
+
+#endif /* __QTISECLIB_DEFS_PLAT_H__ */
diff --git a/plat/qti/qtiseclib/src/qtiseclib_cb_interface.c b/plat/qti/qtiseclib/src/qtiseclib_cb_interface.c
index bb552c6..c4cd259 100644
--- a/plat/qti/qtiseclib/src/qtiseclib_cb_interface.c
+++ b/plat/qti/qtiseclib/src/qtiseclib_cb_interface.c
@@ -132,6 +132,10 @@
 	void *ctx;
 
 	ctx = cm_get_context(NON_SECURE);
+	if (ctx) {
+		/* nothing to be done w/o ns context */
+		return;
+	}
 
 	qti_ns_ctx->spsr_el3 =
 	    read_ctx_reg(get_el3state_ctx(ctx), CTX_SPSR_EL3);
diff --git a/plat/qti/sc7180/inc/platform_def.h b/plat/qti/sc7180/inc/platform_def.h
index b0798a6..e3dc811 100644
--- a/plat/qti/sc7180/inc/platform_def.h
+++ b/plat/qti/sc7180/inc/platform_def.h
@@ -190,5 +190,10 @@
 #define QTI_SOC_REVISION_REG			0x1FC8000
 #define QTI_SOC_REVISION_MASK			U(0xFFFF)
 /*----------------------------------------------------------------------------*/
+/* LC PON register offsets */
+/*----------------------------------------------------------------------------*/
+#define PON_PS_HOLD_RESET_CTL			0x85a
+#define PON_PS_HOLD_RESET_CTL2			0x85b
+/*----------------------------------------------------------------------------*/
 
 #endif /* PLATFORM_DEF_H */
diff --git a/plat/qti/sc7180/platform.mk b/plat/qti/sc7180/platform.mk
index ec560d0..141e2c3 100644
--- a/plat/qti/sc7180/platform.mk
+++ b/plat/qti/sc7180/platform.mk
@@ -51,7 +51,7 @@
 				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_kryo4_silver.S	\
 				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_kryo4_gold.S	\
 				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_uart_console.S	\
-				$(QTI_PLAT_PATH)/common/src/pm8998.c			\
+				$(QTI_PLAT_PATH)/common/src/pm_ps_hold.c			\
 				$(QTI_PLAT_PATH)/common/src/qti_stack_protector.c	\
 				$(QTI_PLAT_PATH)/common/src/qti_common.c		\
 				$(QTI_PLAT_PATH)/common/src/qti_bl31_setup.c		\
diff --git a/plat/qti/sc7280/inc/platform_def.h b/plat/qti/sc7280/inc/platform_def.h
new file mode 100644
index 0000000..da7eddc
--- /dev/null
+++ b/plat/qti/sc7280/inc/platform_def.h
@@ -0,0 +1,199 @@
+/*
+ * Copyright (c) 2018, Arm Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+/* Enable the dynamic translation tables library. */
+#define PLAT_XLAT_TABLES_DYNAMIC	1
+
+#include <common_def.h>
+
+#include <qti_board_def.h>
+#include <qtiseclib_defs_plat.h>
+
+/*----------------------------------------------------------------------------*/
+
+/*----------------------------------------------------------------------------*/
+/*
+ * MPIDR_PRIMARY_CPU
+ * You just need to have the correct core_affinity_val i.e. [7:0]
+ * and cluster_affinity_val i.e. [15:8]
+ * the other bits will be ignored
+ */
+/*----------------------------------------------------------------------------*/
+#define MPIDR_PRIMARY_CPU	0x0000
+/*----------------------------------------------------------------------------*/
+
+#define QTI_PWR_LVL0		MPIDR_AFFLVL0
+#define QTI_PWR_LVL1		MPIDR_AFFLVL1
+#define QTI_PWR_LVL2		MPIDR_AFFLVL2
+#define QTI_PWR_LVL3		MPIDR_AFFLVL3
+
+/*
+ *  Macros for local power states encoded by State-ID field
+ *  within the power-state parameter.
+ */
+/* Local power state for power domains in Run state. */
+#define QTI_LOCAL_STATE_RUN	0
+/*
+ * Local power state for clock-gating. Valid only for CPU and not cluster power
+ * domains
+ */
+#define QTI_LOCAL_STATE_STB	1
+/*
+ * Local power state for retention. Valid for CPU and cluster power
+ * domains
+ */
+#define QTI_LOCAL_STATE_RET	2
+/*
+ * Local power state for OFF/power down. Valid for CPU, cluster, RSC and PDC
+ * power domains
+ */
+#define QTI_LOCAL_STATE_OFF	3
+/*
+ * Local power state for DEEPOFF/power rail down. Valid for CPU, cluster and RSC
+ * power domains
+ */
+#define QTI_LOCAL_STATE_DEEPOFF	4
+
+/*
+ * This macro defines the deepest retention state possible. A higher state
+ * id will represent an invalid or a power down state.
+ */
+#define PLAT_MAX_RET_STATE	QTI_LOCAL_STATE_RET
+
+/*
+ * This macro defines the deepest power down states possible. Any state ID
+ * higher than this is invalid.
+ */
+#define PLAT_MAX_OFF_STATE	QTI_LOCAL_STATE_DEEPOFF
+
+/******************************************************************************
+ * Required platform porting definitions common to all ARM standard platforms
+ *****************************************************************************/
+
+/*
+ * Platform specific page table and MMU setup constants.
+ */
+#define MAX_MMAP_REGIONS	(PLAT_QTI_MMAP_ENTRIES)
+
+#define PLAT_PHY_ADDR_SPACE_SIZE	(1ull << 36)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(1ull << 36)
+
+#define ARM_CACHE_WRITEBACK_SHIFT	6
+
+/*
+ * Some data must be aligned on the biggest cache line size in the platform.
+ * This is known only to the platform as it might have a combination of
+ * integrated and external caches.
+ */
+#define CACHE_WRITEBACK_GRANULE		(1 << ARM_CACHE_WRITEBACK_SHIFT)
+
+/*
+ * One cache line needed for bakery locks on ARM platforms
+ */
+#define PLAT_PERCPU_BAKERY_LOCK_SIZE	(1 * CACHE_WRITEBACK_GRANULE)
+
+/*----------------------------------------------------------------------------*/
+/* PSCI power domain topology definitions */
+/*----------------------------------------------------------------------------*/
+/* One domain each to represent RSC and PDC level */
+#define PLAT_PDC_COUNT			1
+#define PLAT_RSC_COUNT			1
+
+/* There is one top-level FCM cluster */
+#define PLAT_CLUSTER_COUNT		1
+
+/* No. of cores in the FCM cluster */
+#define PLAT_CLUSTER0_CORE_COUNT	8
+
+#define PLATFORM_CORE_COUNT		(PLAT_CLUSTER0_CORE_COUNT)
+
+#define PLAT_NUM_PWR_DOMAINS		(PLAT_PDC_COUNT +\
+					PLAT_RSC_COUNT	+\
+					PLAT_CLUSTER_COUNT	+\
+					PLATFORM_CORE_COUNT)
+
+#define PLAT_MAX_PWR_LVL		3
+
+/*****************************************************************************/
+/* Memory mapped Generic timer interfaces  */
+/*****************************************************************************/
+
+/*----------------------------------------------------------------------------*/
+/* GIC-600 constants */
+/*----------------------------------------------------------------------------*/
+#define BASE_GICD_BASE		0x17A00000
+#define BASE_GICR_BASE		0x17A60000
+#define BASE_GICC_BASE		0x0
+#define BASE_GICH_BASE		0x0
+#define BASE_GICV_BASE		0x0
+
+#define QTI_GICD_BASE		BASE_GICD_BASE
+#define QTI_GICR_BASE		BASE_GICR_BASE
+#define QTI_GICC_BASE		BASE_GICC_BASE
+
+/*----------------------------------------------------------------------------*/
+
+/*----------------------------------------------------------------------------*/
+/* UART related constants. */
+/*----------------------------------------------------------------------------*/
+/* BASE ADDRESS OF DIFFERENT REGISTER SPACES IN HW */
+#define GENI4_CFG				0x0
+#define GENI4_IMAGE_REGS			0x100
+#define GENI4_DATA				0x600
+
+/* COMMON STATUS/CONFIGURATION REGISTERS AND MASKS */
+#define GENI_STATUS_REG				(GENI4_CFG + 0x00000040)
+#define GENI_STATUS_M_GENI_CMD_ACTIVE_MASK	(0x1)
+#define UART_TX_TRANS_LEN_REG			(GENI4_IMAGE_REGS + 0x00000170)
+/* MASTER/TX ENGINE REGISTERS */
+#define GENI_M_CMD0_REG				(GENI4_DATA + 0x00000000)
+/* FIFO, STATUS REGISTERS AND MASKS */
+#define GENI_TX_FIFOn_REG			(GENI4_DATA + 0x00000100)
+
+#define GENI_M_CMD_TX				(0x08000000)
+
+/*----------------------------------------------------------------------------*/
+/* Device address space for mapping. Excluding starting 4K */
+/*----------------------------------------------------------------------------*/
+#define QTI_DEVICE_BASE				0x1000
+#define QTI_DEVICE_SIZE				(0x80000000 - QTI_DEVICE_BASE)
+
+/*******************************************************************************
+ * BL31 specific defines.
+ ******************************************************************************/
+/*
+ * Put BL31 at DDR as per memory map. BL31_BASE is calculated using the
+ * current BL31 debug size plus a little space for growth.
+ */
+#define BL31_LIMIT				(BL31_BASE + BL31_SIZE)
+
+/*----------------------------------------------------------------------------*/
+/* AOSS registers */
+/*----------------------------------------------------------------------------*/
+#define QTI_PS_HOLD_REG				0x0C264000
+/*----------------------------------------------------------------------------*/
+/* AOP CMD DB  address space for mapping */
+/*----------------------------------------------------------------------------*/
+#define QTI_AOP_CMD_DB_BASE			0x80860000
+#define QTI_AOP_CMD_DB_SIZE			0x00020000
+/*----------------------------------------------------------------------------*/
+/* SOC hw version register */
+/*----------------------------------------------------------------------------*/
+#define QTI_SOC_VERSION				U(0x7280)
+#define QTI_SOC_VERSION_MASK			U(0xFFFF)
+#define QTI_SOC_REVISION_REG			0x1FC8000
+#define QTI_SOC_REVISION_MASK			U(0xFFFF)
+/*----------------------------------------------------------------------------*/
+/* LC PON register offsets */
+/*----------------------------------------------------------------------------*/
+#define PON_PS_HOLD_RESET_CTL			0x852
+#define PON_PS_HOLD_RESET_CTL2			0x853
+/*----------------------------------------------------------------------------*/
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/qti/sc7280/inc/qti_rng_io.h b/plat/qti/sc7280/inc/qti_rng_io.h
new file mode 100644
index 0000000..0f41fd6
--- /dev/null
+++ b/plat/qti/sc7280/inc/qti_rng_io.h
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef QTI_RNG_IO_H
+#define QTI_RNG_IO_H
+
+#define SEC_PRNG_STATUS			0x10D1004
+#define SEC_PRNG_STATUS_DATA_AVAIL_BMSK	0x1
+#define SEC_PRNG_DATA_OUT		0x10D1000
+
+
+#endif /* QTI_RNG_IO_H */
+
diff --git a/plat/qti/sc7280/inc/qti_secure_io_cfg.h b/plat/qti/sc7280/inc/qti_secure_io_cfg.h
new file mode 100644
index 0000000..058c5b5
--- /dev/null
+++ b/plat/qti/sc7280/inc/qti_secure_io_cfg.h
@@ -0,0 +1,30 @@
+/*
+ * Copyright (c) 2019-2021, The Linux Foundation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef QTI_SECURE_IO_CFG_H
+#define QTI_SECURE_IO_CFG_H
+
+#include <stdint.h>
+
+/*
+ * List of peripheral/IO memory areas that are protected from
+ * non-secure world but not required to be secure.
+ */
+
+#define APPS_SMMU_TBU_PWR_STATUS		0x15002204
+#define APPS_SMMU_CUSTOM_CFG			0x15002300
+#define APPS_SMMU_STATS_SYNC_INV_TBU_ACK	0x150025DC
+#define APPS_SMMU_SAFE_SEC_CFG			0x15002648
+#define APPS_SMMU_MMU2QSS_AND_SAFE_WAIT_CNTR	0x15002670
+
+static const uintptr_t qti_secure_io_allowed_regs[] = {
+	APPS_SMMU_TBU_PWR_STATUS,
+	APPS_SMMU_CUSTOM_CFG,
+	APPS_SMMU_STATS_SYNC_INV_TBU_ACK,
+	APPS_SMMU_SAFE_SEC_CFG,
+	APPS_SMMU_MMU2QSS_AND_SAFE_WAIT_CNTR,
+};
+
+#endif /* QTI_SECURE_IO_CFG_H */
diff --git a/plat/qti/sc7280/platform.mk b/plat/qti/sc7280/platform.mk
new file mode 100644
index 0000000..bc2c221
--- /dev/null
+++ b/plat/qti/sc7280/platform.mk
@@ -0,0 +1,119 @@
+#
+# Copyright (c) 2017-2018, Arm Limited and Contributors. All rights reserved.
+# Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Make for SC7280 QTI platform.
+
+QTI_PLAT_PATH		:=	plat/qti
+CHIPSET			:=	${PLAT}
+
+# Turn On Separate code & data.
+SEPARATE_CODE_AND_RODATA	:=	1
+USE_COHERENT_MEM		:=	1
+WARMBOOT_ENABLE_DCACHE_EARLY	:=	1
+
+# Disable the PSCI platform compatibility layer
+ENABLE_PLAT_COMPAT		:=	0
+
+# Enable PSCI v1.0 extended state ID format
+PSCI_EXTENDED_STATE_ID	:=  1
+ARM_RECOM_STATE_ID_ENC  :=  1
+
+COLD_BOOT_SINGLE_CPU		:=	1
+PROGRAMMABLE_RESET_ADDRESS	:=	1
+
+RESET_TO_BL31			:=	0
+
+MULTI_CONSOLE_API		:=	1
+
+QTI_SDI_BUILD := 0
+$(eval $(call assert_boolean,QTI_SDI_BUILD))
+$(eval $(call add_define,QTI_SDI_BUILD))
+
+#disable CTX_INCLUDE_AARCH32_REGS to support sc7280 gold cores
+override CTX_INCLUDE_AARCH32_REGS	:=	0
+WORKAROUND_CVE_2017_5715		:=      0
+DYNAMIC_WORKAROUND_CVE_2018_3639	:=      1
+# Enable stack protector.
+ENABLE_STACK_PROTECTOR := strong
+
+
+QTI_EXTERNAL_INCLUDES	:=	-I${QTI_PLAT_PATH}/${CHIPSET}/inc			\
+				-I${QTI_PLAT_PATH}/common/inc				\
+				-I${QTI_PLAT_PATH}/common/inc/$(ARCH)			\
+				-I${QTI_PLAT_PATH}/qtiseclib/inc			\
+				-I${QTI_PLAT_PATH}/qtiseclib/inc/${CHIPSET}			\
+
+QTI_BL31_SOURCES	:=	$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_helpers.S	\
+				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_kryo6_silver.S	\
+				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_kryo6_gold.S	\
+				$(QTI_PLAT_PATH)/common/src/$(ARCH)/qti_uart_console.S	\
+				$(QTI_PLAT_PATH)/common/src/pm_ps_hold.c			\
+				$(QTI_PLAT_PATH)/common/src/qti_stack_protector.c	\
+				$(QTI_PLAT_PATH)/common/src/qti_common.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_bl31_setup.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_gic_v3.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_interrupt_svc.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_syscall.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_topology.c		\
+				$(QTI_PLAT_PATH)/common/src/qti_pm.c			\
+				$(QTI_PLAT_PATH)/common/src/qti_rng.c			\
+				$(QTI_PLAT_PATH)/common/src/spmi_arb.c			\
+				$(QTI_PLAT_PATH)/qtiseclib/src/qtiseclib_cb_interface.c	\
+
+
+PLAT_INCLUDES		:=	-Iinclude/plat/common/					\
+
+PLAT_INCLUDES		+=	${QTI_EXTERNAL_INCLUDES}
+
+include lib/xlat_tables_v2/xlat_tables.mk
+PLAT_BL_COMMON_SOURCES	+=	${XLAT_TABLES_LIB_SRCS}					\
+				plat/common/aarch64/crash_console_helpers.S    \
+				common/desc_image_load.c			\
+				lib/bl_aux_params/bl_aux_params.c		\
+
+include lib/coreboot/coreboot.mk
+
+#PSCI Sources.
+PSCI_SOURCES		:=	plat/common/plat_psci_common.c				\
+
+# GIC-600 configuration
+GICV3_SUPPORT_GIC600	:=	1
+# Include GICv3 driver files
+include drivers/arm/gic/v3/gicv3.mk
+
+#Timer sources
+TIMER_SOURCES		:=	drivers/delay_timer/generic_delay_timer.c	\
+				drivers/delay_timer/delay_timer.c		\
+
+#GIC sources.
+GIC_SOURCES		:=	plat/common/plat_gicv3.c			\
+				${GICV3_SOURCES}				\
+
+BL31_SOURCES		+=	${QTI_BL31_SOURCES}					\
+				${PSCI_SOURCES}						\
+				${GIC_SOURCES}						\
+				${TIMER_SOURCES}					\
+
+LIB_QTI_PATH	:=	${QTI_PLAT_PATH}/qtiseclib/lib/${CHIPSET}
+
+
+# Override this on the command line to point to the qtiseclib library which
+# will be available in coreboot.org
+QTISECLIB_PATH ?=
+
+ifeq ($(QTISECLIB_PATH),)
+# if No lib then use stub implementation for qtiseclib interface
+$(warning QTISECLIB_PATH is not provided while building, using stub implementation. \
+		Please refer docs/plat/qti.rst for more details \
+		THIS FIRMWARE WILL NOT BOOT!)
+BL31_SOURCES	+=	plat/qti/qtiseclib/src/qtiseclib_interface_stub.c
+else
+# use library provided by QTISECLIB_PATH
+LDFLAGS += -L $(dir $(QTISECLIB_PATH))
+LDLIBS += -l$(patsubst lib%.a,%,$(notdir $(QTISECLIB_PATH)))
+endif
+
diff --git a/plat/renesas/common/aarch64/plat_helpers.S b/plat/renesas/common/aarch64/plat_helpers.S
new file mode 100644
index 0000000..21c3bed
--- /dev/null
+++ b/plat/renesas/common/aarch64/plat_helpers.S
@@ -0,0 +1,396 @@
+/*
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <arch.h>
+#include <asm_macros.S>
+#include <common/bl_common.h>
+#include <common/runtime_svc.h>
+#include <cortex_a57.h>
+#include <platform_def.h>
+
+#include "rcar_def.h"
+
+	.globl	plat_get_my_entrypoint
+	.extern	plat_set_my_stack
+	.globl	platform_mem_init
+
+	.globl	plat_crash_console_init
+	.globl	plat_crash_console_putc
+	.globl	plat_crash_console_flush
+	.globl	plat_invalidate_icache
+	.globl	plat_report_exception
+	.globl	plat_secondary_reset
+	.globl	plat_reset_handler
+	.globl	plat_my_core_pos
+	.extern	rcar_log_init
+
+	.extern console_rcar_init
+	.extern console_rcar_putc
+	.extern console_rcar_flush
+
+#if IMAGE_BL2
+	#define	INT_ID_MASK	(0x3ff)
+	.extern bl2_interrupt_error_type
+	.extern bl2_interrupt_error_id
+	.globl  bl2_enter_bl31
+	.extern gicv2_acknowledge_interrupt
+	.extern rcar_swdt_exec
+#endif
+
+	/* -----------------------------------------------------
+	 * void platform_get_core_pos (mpidr)
+	 * -----------------------------------------------------
+	 */
+func platform_get_core_pos
+	and     x1, x0, #MPIDR_CPU_MASK
+	and     x0, x0, #MPIDR_CLUSTER_MASK
+	add     x0, x1, x0, LSR #6
+	ret
+endfunc platform_get_core_pos
+
+	/* -----------------------------------------------------
+	 * void platform_my_core_pos
+	 * -----------------------------------------------------
+	 */
+func plat_my_core_pos
+	mrs     x0, mpidr_el1
+	b	platform_get_core_pos
+endfunc plat_my_core_pos
+
+	/* -----------------------------------------------------
+	 * void platform_get_my_entrypoint (unsigned int mpid);
+	 *
+	 * Main job of this routine is to distinguish between
+	 * a cold and warm boot.
+	 * On a cold boot the secondaries first wait for the
+	 * platform to be initialized after which they are
+	 * hotplugged in. The primary proceeds to perform the
+	 * platform initialization.
+	 * On a warm boot, each cpu jumps to the address in its
+	 * mailbox.
+	 *
+	 * TODO: Not a good idea to save lr in a temp reg
+	 * -----------------------------------------------------
+	 */
+func plat_get_my_entrypoint
+	mrs	x0, mpidr_el1
+	mov	x9, x30 /* lr */
+
+#if defined(IMAGE_BL2)
+	/* always cold boot on bl2 */
+	mov	x0, #0
+	ret	x9
+#else
+       ldr 	x1, =BOOT_KIND_BASE
+       ldr	x21, [x1]
+
+	/* Check the reset info */
+	and	x1, x21, #0x000c
+	cmp	x1, #0x0008
+	beq	el3_panic
+	cmp	x1, #0x000c
+	beq	el3_panic
+
+	/* Check the boot kind */
+	and	x1, x21, #0x0003
+	cmp	x1, #0x0002
+	beq	el3_panic
+	cmp	x1, #0x0003
+	beq	el3_panic
+
+	/* warm boot or cold boot */
+	and	x1, x21, #1
+	cmp	x1, #0
+	bne	warm_reset
+
+	/* Cold boot */
+	mov	x0, #0
+	b	exit
+
+warm_reset:
+	/* --------------------------------------------------------------------
+	 * A per-cpu mailbox is maintained in the trusted SDRAM. Its flushed out
+	 * of the caches after every update using normal memory so its safe to
+	 * read it here with SO attributes
+	 * ---------------------------------------------------------------------
+	 */
+	ldr	x10, =MBOX_BASE
+	bl	platform_get_core_pos
+	lsl	x0, x0, #CACHE_WRITEBACK_SHIFT
+	ldr	x0, [x10, x0]
+	cbz	x0, _panic
+exit:
+	ret	x9
+_panic:
+	b	do_panic
+#endif
+
+endfunc plat_get_my_entrypoint
+
+	/* ---------------------------------------------
+	 * plat_secondary_reset
+	 *
+	 * ---------------------------------------------
+	 */
+func plat_secondary_reset
+	mrs	x0, sctlr_el3
+	bic	x0, x0, #SCTLR_EE_BIT
+	msr	sctlr_el3, x0
+	isb
+
+	mrs	x0, cptr_el3
+	bic	w0, w0, #TCPAC_BIT
+	bic	w0, w0, #TTA_BIT
+	bic	w0, w0, #TFP_BIT
+	msr	cptr_el3, x0
+
+	mov_imm	x0, PARAMS_BASE
+	mov_imm	x2, BL31_BASE
+       ldr x3, =BOOT_KIND_BASE
+	mov x1, #0x1
+	str x1, [x3]
+	br	x2	/* jump to BL31 */
+	nop
+	nop
+	nop
+endfunc plat_secondary_reset
+
+	/* ---------------------------------------------
+	 * plat_enter_bl31
+	 *
+	 * ---------------------------------------------
+	 */
+func bl2_enter_bl31
+	mov	x20, x0
+        /*
+         * MMU needs to be disabled because both BL2 and BL31 execute
+         * in EL3, and therefore share the same address space.
+         * BL31 will initialize the address space according to its
+         * own requirement.
+         */
+#if RCAR_BL2_DCACHE == 1
+	/* Disable mmu and data cache */
+	bl	disable_mmu_el3
+	/* Data cache clean and invalidate */
+	mov	x0, #DCCISW
+	bl	dcsw_op_all
+	/* TLB invalidate all, EL3 */
+	tlbi	alle3
+#endif /* RCAR_BL2_DCACHE == 1 */
+	bl	disable_mmu_icache_el3
+	/* Invalidate instruction cache */
+	ic	iallu
+	dsb	sy
+	isb
+	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
+	msr	elr_el3, x0
+	msr	spsr_el3, x1
+	exception_return
+endfunc bl2_enter_bl31
+
+	/* -----------------------------------------------------
+	 * void platform_mem_init (void);
+	 *
+	 * Zero out the mailbox registers in the shared memory
+	 * and set the rcar_boot_kind_flag.
+	 * The mmu is turned off right now and only the primary can
+	 * ever execute this code. Secondaries will read the
+	 * mailboxes using SO accesses.
+	 * -----------------------------------------------------
+	 */
+func platform_mem_init
+#if !IMAGE_BL2
+	ldr	x0, =MBOX_BASE
+	mov	w1, #PLATFORM_CORE_COUNT
+loop:
+	str	xzr, [x0], #CACHE_WRITEBACK_GRANULE
+	subs	w1, w1, #1
+	b.gt	loop
+#endif
+	ret
+endfunc platform_mem_init
+
+	/* ---------------------------------------------
+	 * void plat_report_exception(unsigned int type)
+	 * Function to report an unhandled exception
+	 * with platform-specific means.
+	 * ---------------------------------------------
+	 */
+func plat_report_exception
+	/* Switch to SP_EL0 */
+	msr	spsel, #0
+#if IMAGE_BL2
+	mov	w1, #FIQ_SP_EL0
+	cmp	w0, w1
+	beq	rep_exec_fiq_elx
+	b	rep_exec_panic_type
+rep_exec_fiq_elx:
+	bl	gicv2_acknowledge_interrupt
+	mov	x2, #INT_ID_MASK
+	and	x0, x0, x2
+	mov	x1, #ARM_IRQ_SEC_WDT
+	cmp	x0, x1
+	bne	rep_exec_panic_id
+	mrs	x0, ELR_EL3
+	b	rcar_swdt_exec
+rep_exec_panic_type:
+	/* x0 is interrupt TYPE */
+	b	bl2_interrupt_error_type
+rep_exec_panic_id:
+	/* x0 is interrupt ID */
+	b	bl2_interrupt_error_id
+rep_exec_end:
+#endif
+	ret
+endfunc plat_report_exception
+
+	/* ---------------------------------------------
+	 * int plat_crash_console_init(void)
+	 * Function to initialize log area
+	 * ---------------------------------------------
+	 */
+func plat_crash_console_init
+#if IMAGE_BL2
+	mov	x0, #0
+#else
+	mov	x1, sp
+	mov_imm	x2, RCAR_CRASH_STACK
+	mov	sp, x2
+	str	x1, [sp, #-16]!
+	str	x30, [sp, #-16]!
+	bl	console_rcar_init
+	ldr	x30, [sp], #16
+	ldr	x1, [sp], #16
+	mov	sp, x1
+#endif
+	ret
+endfunc plat_crash_console_init
+
+	/* ---------------------------------------------
+	 * int plat_crash_console_putc(int c)
+	 * Function to store a character to log area
+	 * ---------------------------------------------
+	 */
+func plat_crash_console_putc
+	mov	x1, sp
+	mov_imm	x2, RCAR_CRASH_STACK
+	mov	sp, x2
+	str	x1, [sp, #-16]!
+	str	x30, [sp, #-16]!
+	str	x3, [sp, #-16]!
+	str	x4, [sp, #-16]!
+	str	x5, [sp, #-16]!
+	str	x6, [sp, #-16]!
+	str	x7, [sp, #-16]!
+	bl	console_rcar_putc
+	ldr	x7, [sp], #16
+	ldr	x6, [sp], #16
+	ldr	x5, [sp], #16
+	ldr	x4, [sp], #16
+	ldr	x3, [sp], #16
+	ldr	x30, [sp], #16
+	ldr	x1, [sp], #16
+	mov	sp, x1
+	ret
+endfunc plat_crash_console_putc
+
+	/* ---------------------------------------------
+	 * void plat_crash_console_flush()
+	 * ---------------------------------------------
+	 */
+func plat_crash_console_flush
+	b	console_rcar_flush
+endfunc plat_crash_console_flush
+
+	/* --------------------------------------------------------------------
+	 * void plat_reset_handler(void);
+	 *
+	 * Before adding code in this function, refer to the guidelines in
+	 * docs/firmware-design.md to determine whether the code should reside
+	 * within the FIRST_RESET_HANDLER_CALL block or not.
+	 *
+	 * For R-Car H3:
+	 * - Set the L2 Tag RAM latency to 2 (i.e. 3 cycles) for Cortex-A57
+	 * - Set the L2 Data setup latency to 1 (i.e. 1 cycles) for Cortex-A57
+	 * - Set the L2 Data RAM latency to 3 (i.e. 4 cycles) for Cortex-A57
+	 * For R-Car M3/M3N:
+	 * - Set the L2 Tag RAM latency to 2 (i.e. 3 cycles) for Cortex-A57
+	 * - Set the L2 Data setup latency to 0 (i.e. 0 cycles) for Cortex-A57
+	 * - Set the L2 Data RAM latency to 3 (i.e. 4 cycles) for Cortex-A57
+	 *
+	 * --------------------------------------------------------------------
+	 */
+func plat_reset_handler
+	/*
+	 * On R-Car H3    :  x2 := 0
+	 * On R-Car M3/M3N:  x2 := 1
+	 */
+	/* read PRR */
+	ldr	x0, =0xFFF00044
+	ldr	w0, [x0]
+	ubfx	w0, w0, 8, 8
+	/* H3? */
+	cmp	w0, #0x4F
+	b.eq	RCARH3
+	/* set R-Car M3/M3N */
+	mov	x2, #1
+	b	CHK_A5x
+RCARH3:
+	/* set R-Car H3 */
+	mov	x2, #0
+	/* --------------------------------------------------------------------
+	 * Determine whether this code is executed on a Cortex-A53 or on a
+	 * Cortex-A57 core.
+	 * --------------------------------------------------------------------
+	 */
+CHK_A5x:
+	mrs	x0, midr_el1
+	ubfx	x1, x0, MIDR_PN_SHIFT, #12
+	cmp     w1, #((CORTEX_A57_MIDR >> MIDR_PN_SHIFT) & MIDR_PN_MASK)
+	b.eq	A57
+	ret
+A57:
+	/* Get data from CORTEX_A57_L2CTLR_EL1	*/
+	mrs	x0, CORTEX_A57_L2CTLR_EL1
+	/*
+	 * On R-Car H3/M3/M3N
+	 *
+	 * L2 Tag RAM latency is bit8-6 of CORTEX_A57_L2CTLR_EL1
+	 * L2 Data RAM setup is bit5 of CORTEX_A57_L2CTLR_EL1
+	 * L2 Data RAM latency is bit2-0 of CORTEX_A57_L2CTLR_EL1
+	 */
+	/* clear bit of L2 RAM	*/
+	/* ~(0x1e7) -> x1	*/
+	mov	x1, #0x1e7
+	neg	x1, x1
+	/* clear bit of L2 RAM -> x0 */
+	and	x0, x0, x1
+	/* L2 Tag RAM latency (3 cycles) */
+	orr	x0, x0, #0x2 << 6
+	/* If M3/M3N then L2 RAM setup is 0 */
+	cbnz	x2, M3_L2
+	/* L2 Data RAM setup (1 cycle) */
+	orr	x0, x0, #0x1 << 5
+M3_L2:
+	/* L2 Data RAM latency (4 cycles) */
+	orr	x0, x0, #0x3
+	/* Store data to L2CTLR_EL1 */
+	msr	CORTEX_A57_L2CTLR_EL1, x0
+apply_l2_ram_latencies:
+	ret
+endfunc plat_reset_handler
+
+	/* ---------------------------------------------
+	 * void plat_invalidate_icache(void)
+	 * Instruction Cache Invalidate All to PoU
+	 * ---------------------------------------------
+	 */
+func plat_invalidate_icache
+	ic	iallu
+
+	ret
+endfunc plat_invalidate_icache
diff --git a/plat/renesas/rcar/aarch64/platform_common.c b/plat/renesas/common/aarch64/platform_common.c
similarity index 100%
rename from plat/renesas/rcar/aarch64/platform_common.c
rename to plat/renesas/common/aarch64/platform_common.c
diff --git a/plat/renesas/common/bl2_cpg_init.c b/plat/renesas/common/bl2_cpg_init.c
new file mode 100644
index 0000000..a545f71
--- /dev/null
+++ b/plat/renesas/common/bl2_cpg_init.c
@@ -0,0 +1,408 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/debug.h>
+#include <lib/mmio.h>
+
+#include "cpg_registers.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+
+static void bl2_secure_cpg_init(void);
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3) || \
+	(RCAR_LSI == RCAR_H3N) || (RCAR_LSI == RZ_G2H)
+static void bl2_realtime_cpg_init_h3(void);
+static void bl2_system_cpg_init_h3(void);
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3) || (RCAR_LSI == RZ_G2M)
+static void bl2_realtime_cpg_init_m3(void);
+static void bl2_system_cpg_init_m3(void);
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N) || (RCAR_LSI == RZ_G2N)
+static void bl2_realtime_cpg_init_m3n(void);
+static void bl2_system_cpg_init_m3n(void);
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_V3M)
+static void bl2_realtime_cpg_init_v3m(void);
+static void bl2_system_cpg_init_v3m(void);
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RZ_G2E)
+static void bl2_realtime_cpg_init_e3(void);
+static void bl2_system_cpg_init_e3(void);
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_D3)
+static void bl2_system_cpg_init_d3(void);
+#endif
+
+typedef struct {
+	uintptr_t adr;
+	uint32_t val;
+} reg_setting_t;
+
+static void bl2_secure_cpg_init(void)
+{
+	uint32_t stop_cr2, reset_cr2;
+	uint32_t stop_cr4, reset_cr4;
+	uint32_t stop_cr5, reset_cr5;
+
+#if (RCAR_LSI == RCAR_D3)
+	reset_cr2 = 0x00000000U;
+	stop_cr2 = 0xFFFFFFFFU;
+#elif (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RZ_G2E)
+	reset_cr2 = 0x10000000U;
+	stop_cr2 = 0xEFFFFFFFU;
+#else
+	reset_cr2 = 0x14000000U;
+	stop_cr2 = 0xEBFFFFFFU;
+#endif
+
+#if (RCAR_LSI == RCAR_D3)
+	reset_cr4 = 0x00000000U;
+	stop_cr4 = 0xFFFFFFFFU;
+	reset_cr5 = 0x00000000U;
+	stop_cr5 = 0xFFFFFFFFU;
+#else
+	reset_cr4 = 0x80000003U;
+	stop_cr4 = 0x7FFFFFFFU;
+	reset_cr5 = 0x40000000U;
+	stop_cr5 = 0xBFFFFFFFU;
+#endif
+
+	/* Secure Module Stop Control Registers */
+	cpg_write(SCMSTPCR0, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR2, stop_cr2);
+	cpg_write(SCMSTPCR3, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR4, stop_cr4);
+	cpg_write(SCMSTPCR5, stop_cr5);
+	cpg_write(SCMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR8, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR9, 0xFFFDFFFFU);
+	cpg_write(SCMSTPCR10, 0xFFFFFFFFU);
+	cpg_write(SCMSTPCR11, 0xFFFFFFFFU);
+
+	/* Secure Software Reset Access Enable Control Registers */
+	cpg_write(SCSRSTECR0, 0x00000000U);
+	cpg_write(SCSRSTECR1, 0x00000000U);
+	cpg_write(SCSRSTECR2, reset_cr2);
+	cpg_write(SCSRSTECR3, 0x00000000U);
+	cpg_write(SCSRSTECR4, reset_cr4);
+	cpg_write(SCSRSTECR5, reset_cr5);
+	cpg_write(SCSRSTECR6, 0x00000000U);
+	cpg_write(SCSRSTECR7, 0x00000000U);
+	cpg_write(SCSRSTECR8, 0x00000000U);
+	cpg_write(SCSRSTECR9, 0x00020000U);
+	cpg_write(SCSRSTECR10, 0x00000000U);
+	cpg_write(SCSRSTECR11, 0x00000000U);
+}
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3) || \
+	(RCAR_LSI == RCAR_H3N) || (RCAR_LSI == RZ_G2H)
+static void bl2_realtime_cpg_init_h3(void)
+{
+	uint32_t cut = mmio_read_32(RCAR_PRR) & PRR_CUT_MASK;
+	uint32_t cr0, cr8;
+
+	cr0 = (cut == PRR_PRODUCT_10 || cut == PRR_PRODUCT_11) ?
+	    0x00200000U : 0x00210000U;
+	cr8 = (cut == PRR_PRODUCT_10 || cut == PRR_PRODUCT_11) ?
+	    0x01F1FFF4U : 0x01F1FFF7U;
+
+	cpg_write(RMSTPCR0, cr0);
+	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR2, 0x040E0FDCU);
+	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR4, 0x80000004U);
+	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR8, cr8);
+	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
+	cpg_write(RMSTPCR10, 0xFFFEFFE0U);
+	cpg_write(RMSTPCR11, 0x000000B7U);
+}
+
+static void bl2_system_cpg_init_h3(void)
+{
+	/** System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00210000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x040E2FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x80000000U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x01F1FFF5U);
+	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
+	cpg_write(SMSTPCR11, 0x000000B7U);
+}
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3) || (RCAR_LSI == RZ_G2M)
+static void bl2_realtime_cpg_init_m3(void)
+{
+	/* Realtime Module Stop Control Registers */
+	cpg_write(RMSTPCR0, 0x00200000U);
+	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR2, 0x040E0FDCU);
+	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR4, 0x80000004U);
+	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR8, 0x01F1FFF7U);
+	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
+	cpg_write(RMSTPCR10, 0xFFFEFFE0U);
+	cpg_write(RMSTPCR11, 0x000000B7U);
+}
+
+static void bl2_system_cpg_init_m3(void)
+{
+	/* System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00200000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x040E2FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x80000000U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x01F1FFF7U);
+	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
+	cpg_write(SMSTPCR11, 0x000000B7U);
+}
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N)  || (RCAR_LSI == RZ_G2N)
+static void bl2_realtime_cpg_init_m3n(void)
+{
+	/* Realtime Module Stop Control Registers */
+	cpg_write(RMSTPCR0, 0x00210000U);
+	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR2, 0x040E0FDCU);
+	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR4, 0x80000004U);
+	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR8, 0x00F1FFF7U);
+	cpg_write(RMSTPCR9, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR10, 0xFFFFFFE0U);
+	cpg_write(RMSTPCR11, 0x000000B7U);
+}
+
+static void bl2_system_cpg_init_m3n(void)
+{
+	/* System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00210000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x040E2FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x80000000U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x00F1FFF7U);
+	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR10, 0xFFFFFFE0U);
+	cpg_write(SMSTPCR11, 0x000000B7U);
+}
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_V3M)
+static void bl2_realtime_cpg_init_v3m(void)
+{
+	/* Realtime Module Stop Control Registers */
+	cpg_write(RMSTPCR0, 0x00230000U);
+	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR2, 0x14062FD8U);
+	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR4, 0x80000184U);
+	cpg_write(RMSTPCR5, 0x83FFFFFFU);
+	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR8, 0x7FF3FFF4U);
+	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
+}
+
+static void bl2_system_cpg_init_v3m(void)
+{
+	/* System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00210000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x340E2FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x80000000U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x01F1FFF5U);
+	cpg_write(SMSTPCR9, 0xFFFFFFFEU);
+}
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RZ_G2E)
+static void bl2_realtime_cpg_init_e3(void)
+{
+	/* Realtime Module Stop Control Registers */
+	cpg_write(RMSTPCR0, 0x00210000U);
+	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR2, 0x000E0FDCU);
+	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR4, 0x80000004U);
+	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(RMSTPCR8, 0x00F1FFF7U);
+	cpg_write(RMSTPCR9, 0xFFFFFFDFU);
+	cpg_write(RMSTPCR10, 0xFFFFFFE8U);
+	cpg_write(RMSTPCR11, 0x000000B7U);
+}
+
+static void bl2_system_cpg_init_e3(void)
+{
+	/* System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00210000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x000E2FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x80000000U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x00F1FFF7U);
+	cpg_write(SMSTPCR9, 0xFFFFFFDFU);
+	cpg_write(SMSTPCR10, 0xFFFFFFE8U);
+	cpg_write(SMSTPCR11, 0x000000B7U);
+}
+#endif
+
+#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_D3)
+static void bl2_system_cpg_init_d3(void)
+{
+	/* System Module Stop Control Registers */
+	cpg_write(SMSTPCR0, 0x00010000U);
+	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR2, 0x00060FDCU);
+	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
+	cpg_write(SMSTPCR4, 0x00000080U | (mmio_read_32(SMSTPCR4) & 0x4));
+	cpg_write(SMSTPCR5, 0x83FFFFFFU);
+	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
+	cpg_write(SMSTPCR8, 0x00F1FFF7U);
+	cpg_write(SMSTPCR9, 0xF3F5E016U);
+	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
+	cpg_write(SMSTPCR11, 0x000000B7U);
+}
+#endif
+
+void bl2_cpg_init(void)
+{
+	uint32_t boot_cpu = mmio_read_32(RCAR_MODEMR) & MODEMR_BOOT_CPU_MASK;
+#if RCAR_LSI == RCAR_AUTO
+	uint32_t product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
+#endif
+	bl2_secure_cpg_init();
+
+	if (boot_cpu == MODEMR_BOOT_CPU_CA57 ||
+	    boot_cpu == MODEMR_BOOT_CPU_CA53) {
+#if RCAR_LSI == RCAR_AUTO
+
+		switch (product) {
+		case PRR_PRODUCT_H3:
+			bl2_realtime_cpg_init_h3();
+			break;
+		case PRR_PRODUCT_M3:
+			bl2_realtime_cpg_init_m3();
+			break;
+		case PRR_PRODUCT_M3N:
+			bl2_realtime_cpg_init_m3n();
+			break;
+		case PRR_PRODUCT_V3M:
+			bl2_realtime_cpg_init_v3m();
+			break;
+		case PRR_PRODUCT_E3:
+			bl2_realtime_cpg_init_e3();
+			break;
+		case PRR_PRODUCT_D3:
+			/* no need */
+			break;
+		default:
+			panic();
+			break;
+		}
+#elif (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N) || (RCAR_LSI == RZ_G2H)
+		bl2_realtime_cpg_init_h3();
+#elif (RCAR_LSI == RCAR_M3) || (RCAR_LSI == RZ_G2M)
+		bl2_realtime_cpg_init_m3();
+#elif RCAR_LSI == RCAR_M3N || (RCAR_LSI == RZ_G2N)
+		bl2_realtime_cpg_init_m3n();
+#elif RCAR_LSI == RCAR_V3M
+		bl2_realtime_cpg_init_v3m();
+#elif RCAR_LSI == RCAR_E3 || RCAR_LSI == RZ_G2E
+		bl2_realtime_cpg_init_e3();
+#elif RCAR_LSI == RCAR_D3
+		/* no need */
+#else
+#error "Don't have CPG initialize routine(unknown)."
+#endif
+	}
+}
+
+void bl2_system_cpg_init(void)
+{
+#if RCAR_LSI == RCAR_AUTO
+	uint32_t product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
+
+	switch (product) {
+	case PRR_PRODUCT_H3:
+		bl2_system_cpg_init_h3();
+		break;
+	case PRR_PRODUCT_M3:
+		bl2_system_cpg_init_m3();
+		break;
+	case PRR_PRODUCT_M3N:
+		bl2_system_cpg_init_m3n();
+		break;
+	case PRR_PRODUCT_V3M:
+		bl2_system_cpg_init_v3m();
+		break;
+	case PRR_PRODUCT_E3:
+		bl2_system_cpg_init_e3();
+		break;
+	case PRR_PRODUCT_D3:
+		bl2_system_cpg_init_d3();
+		break;
+	default:
+		panic();
+		break;
+	}
+#elif (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N) || (RCAR_LSI == RZ_G2H)
+	bl2_system_cpg_init_h3();
+#elif (RCAR_LSI == RCAR_M3) || (RCAR_LSI == RZ_G2M)
+	bl2_system_cpg_init_m3();
+#elif RCAR_LSI == RCAR_M3N  || (RCAR_LSI == RZ_G2N)
+	bl2_system_cpg_init_m3n();
+#elif RCAR_LSI == RCAR_V3M
+	bl2_system_cpg_init_v3m();
+#elif RCAR_LSI == RCAR_E3 || RCAR_LSI == RZ_G2E
+	bl2_system_cpg_init_e3();
+#elif RCAR_LSI == RCAR_D3
+	bl2_system_cpg_init_d3();
+#else
+#error "Don't have CPG initialize routine(unknown)."
+#endif
+}
diff --git a/plat/renesas/rcar/bl2_interrupt_error.c b/plat/renesas/common/bl2_interrupt_error.c
similarity index 100%
rename from plat/renesas/rcar/bl2_interrupt_error.c
rename to plat/renesas/common/bl2_interrupt_error.c
diff --git a/plat/renesas/rcar/bl2_plat_mem_params_desc.c b/plat/renesas/common/bl2_plat_mem_params_desc.c
similarity index 100%
rename from plat/renesas/rcar/bl2_plat_mem_params_desc.c
rename to plat/renesas/common/bl2_plat_mem_params_desc.c
diff --git a/plat/renesas/common/bl2_secure_setting.c b/plat/renesas/common/bl2_secure_setting.c
new file mode 100644
index 0000000..2f8b001
--- /dev/null
+++ b/plat/renesas/common/bl2_secure_setting.c
@@ -0,0 +1,362 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <lib/mmio.h>
+#include <lib/utils_def.h>
+
+#include "axi_registers.h"
+#include "lifec_registers.h"
+#include "micro_delay.h"
+
+static void lifec_security_setting(void);
+static void axi_security_setting(void);
+
+static const struct {
+	uint32_t reg;
+	uint32_t val;
+} lifec[] = {
+	/*
+	 * LIFEC0 (SECURITY) settings
+	 * Security attribute setting for master ports
+	 * Bit 0: ARM realtime core (Cortex-R7) master port
+	 *        0: Non-Secure
+	 */
+	{ SEC_SRC, 0x0000001EU },
+	/*
+	 * Security attribute setting for slave ports 0 to 15
+	 *      {SEC_SEL0,              0xFFFFFFFFU},
+	 *      {SEC_SEL1,              0xFFFFFFFFU},
+	 *	{SEC_SEL2,              0xFFFFFFFFU},
+	 * Bit19: AXI-Bus (Main Memory domain AXI) slave ports
+	 *        0: registers accessed from secure resource only
+	 * Bit 9: DBSC4 register access slave ports.
+	 *        0: registers accessed from secure resource only.
+	 */
+#if (LIFEC_DBSC_PROTECT_ENABLE == 1)
+	{ SEC_SEL3, 0xFFF7FDFFU },
+#else /* LIFEC_DBSC_PROTECT_ENABLE == 1 */
+	{ SEC_SEL3, 0xFFFFFFFFU },
+#endif /* LIFEC_DBSC_PROTECT_ENABLE == 1 */
+	/*
+	 *	{SEC_SEL4,              0xFFFFFFFFU},
+	 * Bit 6: Boot ROM slave ports.
+	 *        0: registers accessed from secure resource only
+	 */
+	{ SEC_SEL5, 0xFFFFFFBFU },
+	/*
+	 * Bit13: SCEG PKA (secure APB) slave ports
+	 *        0: registers accessed from secure resource only
+	 *        1: Reserved[R-Car E3/D3]
+	 * Bit12: SCEG PKA (public APB) slave ports
+	 *	  0: registers accessed from secure resource only
+	 *	  1: Reserved[R-Car E3/D3]
+	 * Bit10: SCEG Secure Core slave ports
+	 *	  0: registers accessed from secure resource only
+	 */
+#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
+	{ SEC_SEL6, 0xFFFFFBFFU },
+#else /*  (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3) */
+	{ SEC_SEL6, 0xFFFFCBFFU },
+#endif /*  (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3) */
+	/*
+	 *	{SEC_SEL7,              0xFFFFFFFFU},
+	 *	{SEC_SEL8,              0xFFFFFFFFU},
+	 *	{SEC_SEL9,              0xFFFFFFFFU},
+	 *	{SEC_SEL10,             0xFFFFFFFFU},
+	 *	{SEC_SEL11,             0xFFFFFFFFU},
+	 *	{SEC_SEL12,             0xFFFFFFFFU},
+	 * Bit22: RPC slave ports.
+	 *	  0: registers accessed from secure resource only.
+	 */
+#if (RCAR_RPC_HYPERFLASH_LOCKED == 1)
+	{ SEC_SEL13, 0xFFBFFFFFU },
+#endif /* (RCAR_RPC_HYPERFLASH_LOCKED == 1) */
+	/*
+	 * Bit27: System Timer (SCMT) slave ports
+	 *	  0: registers accessed from secure resource only
+	 * Bit26: System Watchdog Timer (SWDT) slave ports
+	 *	  0: registers accessed from secure resource only
+	 */
+	{ SEC_SEL14, 0xF3FFFFFFU },
+	/*
+	 * Bit13: RST slave ports.
+	 *	  0: registers accessed from secure resource only
+	 * Bit 7: Life Cycle 0 slave ports
+	 *	  0: registers accessed from secure resource only
+	 */
+	{ SEC_SEL15, 0xFFFFFF3FU },
+	/*
+	 * Security group 0 attribute setting for master ports 0
+	 * Security group 1 attribute setting for master ports 0
+	 *	{SEC_GRP0CR0,           0x00000000U},
+	 *	{SEC_GRP1CR0,           0x00000000U},
+	 * Security group 0 attribute setting for master ports 1
+	 * Security group 1 attribute setting for master ports 1
+	 *	{SEC_GRP0CR1,           0x00000000U},
+	 *	{SEC_GRP1CR1,           0x00000000U},
+	 * Security group 0 attribute setting for master ports 2
+	 * Security group 1 attribute setting for master ports 2
+	 * Bit17: SCEG Secure Core master ports.
+	 *	  SecurityGroup3
+	 */
+	{ SEC_GRP0CR2, 0x00020000U },
+	{ SEC_GRP1CR2, 0x00020000U },
+	/*
+	 * Security group 0 attribute setting for master ports 3
+	 * Security group 1 attribute setting for master ports 3
+	 *	{SEC_GRP0CR3,           0x00000000U},
+	 *	{SEC_GRP1CR3,           0x00000000U},
+	 * Security group 0 attribute setting for slave ports 0
+	 * Security group 1 attribute setting for slave ports 0
+	 *	{SEC_GRP0COND0,         0x00000000U},
+	 *	{SEC_GRP1COND0,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 1
+	 * Security group 1 attribute setting for slave ports 1
+	 *	{SEC_GRP0COND1,         0x00000000U},
+	 *	{SEC_GRP1COND1,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 2
+	 * Security group 1 attribute setting for slave ports 2
+	 *	{SEC_GRP0COND2,         0x00000000U},
+	 *	{SEC_GRP1COND2,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 3
+	 * Security group 1 attribute setting for slave ports 3
+	 * Bit19: AXI-Bus (Main Memory domain AXI) slave ports.
+	 *	  SecurityGroup3
+	 * Bit 9: DBSC4 register access slave ports.
+	 *        SecurityGroup3
+	 */
+#if (LIFEC_DBSC_PROTECT_ENABLE == 1)
+	{ SEC_GRP0COND3, 0x00080200U },
+	{ SEC_GRP1COND3, 0x00080200U },
+#else /* (LIFEC_DBSC_PROTECT_ENABLE == 1) */
+	{ SEC_GRP0COND3, 0x00000000U },
+	{ SEC_GRP1COND3, 0x00000000U },
+#endif /* (LIFEC_DBSC_PROTECT_ENABLE == 1) */
+	/*
+	 * Security group 0 attribute setting for slave ports 4
+	 * Security group 1 attribute setting for slave ports 4
+	 *	{SEC_GRP0COND4,         0x00000000U},
+	 *	{SEC_GRP1COND4,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 5
+	 * Security group 1 attribute setting for slave ports 5
+	 * Bit 6: Boot ROM slave ports
+	 *	  SecurityGroup3
+	 */
+	{ SEC_GRP0COND5, 0x00000040U },
+	{ SEC_GRP1COND5, 0x00000040U },
+	/*
+	 * Security group 0 attribute setting for slave ports 6
+	 * Security group 1 attribute setting for slave ports 6
+	 * Bit13: SCEG PKA (secure APB) slave ports
+	 *	  SecurityGroup3
+	 *	  Reserved[R-Car E3/D3]
+	 * Bit12: SCEG PKA (public APB) slave ports
+	 *	  SecurityGroup3
+	 *	  Reserved[R-Car E3/D3]
+	 * Bit10: SCEG Secure Core slave ports
+	 *	  SecurityGroup3
+	 */
+#if RCAR_LSI == RCAR_E3 || RCAR_LSI == RCAR_D3
+	{ SEC_GRP0COND6, 0x00000400U },
+	{ SEC_GRP1COND6, 0x00000400U },
+#else /* RCAR_LSI == RCAR_E3 */
+	{ SEC_GRP0COND6, 0x00003400U },
+	{ SEC_GRP1COND6, 0x00003400U },
+#endif /* RCAR_LSI == RCAR_E3 */
+	/*
+	 * Security group 0 attribute setting for slave ports 7
+	 * Security group 1 attribute setting for slave ports 7
+	 *	{SEC_GRP0COND7,         0x00000000U},
+	 *	{SEC_GRP1COND7,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 8
+	 * Security group 1 attribute setting for slave ports 8
+	 *	{SEC_GRP0COND8,         0x00000000U},
+	 *	{SEC_GRP1COND8,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 9
+	 * Security group 1 attribute setting for slave ports 9
+	 *	{SEC_GRP0COND9,         0x00000000U},
+	 *	{SEC_GRP1COND9,         0x00000000U},
+	 * Security group 0 attribute setting for slave ports 10
+	 * Security group 1 attribute setting for slave ports 10
+	 *	{SEC_GRP0COND10,        0x00000000U},
+	 *	{SEC_GRP1COND10,        0x00000000U},
+	 * Security group 0 attribute setting for slave ports 11
+	 * Security group 1 attribute setting for slave ports 11
+	 *	{SEC_GRP0COND11,        0x00000000U},
+	 *	{SEC_GRP1COND11,        0x00000000U},
+	 * Security group 0 attribute setting for slave ports 12
+	 * Security group 1 attribute setting for slave ports 12
+	 *	{SEC_GRP0COND12,        0x00000000U},
+	 *	{SEC_GRP1COND12,        0x00000000U},
+	 * Security group 0 attribute setting for slave ports 13
+	 * Security group 1 attribute setting for slave ports 13
+	 * Bit22: RPC slave ports.
+	 *	  SecurityGroup3
+	 */
+#if (RCAR_RPC_HYPERFLASH_LOCKED == 1)
+	    { SEC_GRP0COND13,     0x00400000U },
+	    { SEC_GRP1COND13,     0x00400000U },
+#endif /* (RCAR_RPC_HYPERFLASH_LOCKED == 1) */
+	/*
+	 * Security group 0 attribute setting for slave ports 14
+	 * Security group 1 attribute setting for slave ports 14
+	 * Bit26: System Timer (SCMT) slave ports
+	 *	  SecurityGroup3
+	 * Bit27: System Watchdog Timer (SWDT) slave ports
+	 *	  SecurityGroup3
+	 */
+	{ SEC_GRP0COND14, 0x0C000000U },
+	{ SEC_GRP1COND14, 0x0C000000U },
+	/*
+	 * Security group 0 attribute setting for slave ports 15
+	 * Security group 1 attribute setting for slave ports 15
+	 * Bit13: RST slave ports
+	 *	  SecurityGroup3
+	 * Bit 7: Life Cycle 0 slave ports
+	 *	  SecurityGroup3
+	 * Bit 6: TDBG slave ports
+	 *	  SecurityGroup3
+	 */
+	{ SEC_GRP0COND15, 0x000000C0U },
+	{ SEC_GRP1COND15, 0x000000C0U },
+	/*
+	 * Security write protection attribute setting slave ports 0
+	 *	{SEC_READONLY0,         0x00000000U},
+	 * Security write protection attribute setting slave ports 1
+	 *	{SEC_READONLY1,         0x00000000U},
+	 * Security write protection attribute setting slave ports 2
+	 *	{SEC_READONLY2,         0x00000000U},
+	 * Security write protection attribute setting slave ports 3
+	 *	{SEC_READONLY3,         0x00000000U},
+	 * Security write protection attribute setting slave ports 4
+	 *	{SEC_READONLY4,         0x00000000U},
+	 * Security write protection attribute setting slave ports 5
+	 *	{SEC_READONLY5,         0x00000000U},
+	 * Security write protection attribute setting slave ports 6
+	 *	{SEC_READONLY6,         0x00000000U},
+	 * Security write protection attribute setting slave ports 7
+	 *	{SEC_READONLY7,         0x00000000U},
+	 * Security write protection attribute setting slave ports 8
+	 *	{SEC_READONLY8,         0x00000000U},
+	 * Security write protection attribute setting slave ports 9
+	 *	{SEC_READONLY9,         0x00000000U},
+	 * Security write protection attribute setting slave ports 10
+	 *	{SEC_READONLY10,        0x00000000U},
+	 * Security write protection attribute setting slave ports 11
+	 *	{SEC_READONLY11,        0x00000000U},
+	 * Security write protection attribute setting slave ports 12
+	 *	{SEC_READONLY12,        0x00000000U},
+	 * Security write protection attribute setting slave ports 13
+	 *	{SEC_READONLY13,        0x00000000U},
+	 * Security write protection attribute setting slave ports 14
+	 *	{SEC_READONLY14,        0x00000000U},
+	 * Security write protection attribute setting slave ports 15
+	 *	{SEC_READONLY15,        0x00000000U}
+	 */
+};
+
+/* AXI settings */
+static const struct {
+	uint32_t reg;
+	uint32_t val;
+} axi[] = {
+	/*
+	 * DRAM protection
+	 * AXI dram protected area division
+	 */
+	{AXI_DPTDIVCR0,  0x0E0403F0U},
+	{AXI_DPTDIVCR1,  0x0E0407E0U},
+	{AXI_DPTDIVCR2,  0x0E080000U},
+	{AXI_DPTDIVCR3,  0x0E080000U},
+	{AXI_DPTDIVCR4,  0x0E080000U},
+	{AXI_DPTDIVCR5,  0x0E080000U},
+	{AXI_DPTDIVCR6,  0x0E080000U},
+	{AXI_DPTDIVCR7,  0x0E080000U},
+	{AXI_DPTDIVCR8,  0x0E080000U},
+	{AXI_DPTDIVCR9,  0x0E080000U},
+	{AXI_DPTDIVCR10, 0x0E080000U},
+	{AXI_DPTDIVCR11, 0x0E080000U},
+	{AXI_DPTDIVCR12, 0x0E080000U},
+	{AXI_DPTDIVCR13, 0x0E080000U},
+	{AXI_DPTDIVCR14, 0x0E080000U},
+	/* AXI dram protected area setting */
+	{AXI_DPTCR0,  0x0E000000U},
+	{AXI_DPTCR1,  0x0E000E0EU},
+	{AXI_DPTCR2,  0x0E000000U},
+	{AXI_DPTCR3,  0x0E000000U},
+	{AXI_DPTCR4,  0x0E000000U},
+	{AXI_DPTCR5,  0x0E000000U},
+	{AXI_DPTCR6,  0x0E000000U},
+	{AXI_DPTCR7,  0x0E000000U},
+	{AXI_DPTCR8,  0x0E000000U},
+	{AXI_DPTCR9,  0x0E000000U},
+	{AXI_DPTCR10, 0x0E000000U},
+	{AXI_DPTCR11, 0x0E000000U},
+	{AXI_DPTCR12, 0x0E000000U},
+	{AXI_DPTCR13, 0x0E000000U},
+	{AXI_DPTCR14, 0x0E000000U},
+	{AXI_DPTCR15, 0x0E000000U},
+	/*
+	 * SRAM ptotection
+	 * AXI sram protected area division
+	 */
+	{AXI_SPTDIVCR0,  0x0E0E6304U},
+	{AXI_SPTDIVCR1,  0x0E0E6360U},
+	{AXI_SPTDIVCR2,  0x0E0E6360U},
+	{AXI_SPTDIVCR3,  0x0E0E6360U},
+	{AXI_SPTDIVCR4,  0x0E0E6360U},
+	{AXI_SPTDIVCR5,  0x0E0E6360U},
+	{AXI_SPTDIVCR6,  0x0E0E6360U},
+	{AXI_SPTDIVCR7,  0x0E0E6360U},
+	{AXI_SPTDIVCR8,  0x0E0E6360U},
+	{AXI_SPTDIVCR9,  0x0E0E6360U},
+	{AXI_SPTDIVCR10, 0x0E0E6360U},
+	{AXI_SPTDIVCR11, 0x0E0E6360U},
+	{AXI_SPTDIVCR12, 0x0E0E6360U},
+	{AXI_SPTDIVCR13, 0x0E0E6360U},
+	{AXI_SPTDIVCR14, 0x0E0E6360U},
+	/* AXI sram protected area setting */
+	{AXI_SPTCR0,  0x0E000E0EU},
+	{AXI_SPTCR1,  0x0E000000U},
+	{AXI_SPTCR2,  0x0E000000U},
+	{AXI_SPTCR3,  0x0E000000U},
+	{AXI_SPTCR4,  0x0E000000U},
+	{AXI_SPTCR5,  0x0E000000U},
+	{AXI_SPTCR6,  0x0E000000U},
+	{AXI_SPTCR7,  0x0E000000U},
+	{AXI_SPTCR8,  0x0E000000U},
+	{AXI_SPTCR9,  0x0E000000U},
+	{AXI_SPTCR10, 0x0E000000U},
+	{AXI_SPTCR11, 0x0E000000U},
+	{AXI_SPTCR12, 0x0E000000U},
+	{AXI_SPTCR13, 0x0E000000U},
+	{AXI_SPTCR14, 0x0E000000U},
+	{AXI_SPTCR15, 0x0E000000U}
+};
+
+static void lifec_security_setting(void)
+{
+	uint32_t i;
+
+	for (i = 0; i < ARRAY_SIZE(lifec); i++)
+		mmio_write_32(lifec[i].reg, lifec[i].val);
+}
+
+/* SRAM/DRAM protection setting */
+static void axi_security_setting(void)
+{
+	uint32_t i;
+
+	for (i = 0; i < ARRAY_SIZE(axi); i++)
+		mmio_write_32(axi[i].reg, axi[i].val);
+}
+
+void bl2_secure_setting(void)
+{
+	lifec_security_setting();
+	axi_security_setting();
+	rcar_micro_delay(10U);
+}
diff --git a/plat/renesas/common/bl31_plat_setup.c b/plat/renesas/common/bl31_plat_setup.c
new file mode 100644
index 0000000..93798ac
--- /dev/null
+++ b/plat/renesas/common/bl31_plat_setup.c
@@ -0,0 +1,132 @@
+/*
+ * Copyright (c) 2013-2014, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <arch.h>
+#include <arch_helpers.h>
+#include <bl31/bl31.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/arm/cci.h>
+#include <drivers/console.h>
+#include <lib/mmio.h>
+#include <plat/common/platform.h>
+
+#include "pwrc.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+#include "rcar_version.h"
+
+static const uint64_t BL31_RO_BASE		= BL_CODE_BASE;
+static const uint64_t BL31_RO_LIMIT		= BL_CODE_END;
+
+#if USE_COHERENT_MEM
+static const uint64_t BL31_COHERENT_RAM_BASE	= BL_COHERENT_RAM_BASE;
+static const uint64_t BL31_COHERENT_RAM_LIMIT	= BL_COHERENT_RAM_END;
+#endif /* USE_COHERENT_MEM */
+
+extern void plat_rcar_gic_driver_init(void);
+extern void plat_rcar_gic_init(void);
+
+u_register_t rcar_boot_mpidr;
+
+static int cci_map[] = {
+	CCI500_CLUSTER0_SL_IFACE_IX_FOR_M3,
+	CCI500_CLUSTER1_SL_IFACE_IX_FOR_M3
+};
+
+void plat_cci_init(void)
+{
+	uint32_t prd;
+
+	prd = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+
+	if (PRR_PRODUCT_H3_CUT10 == prd || PRR_PRODUCT_H3_CUT11 == prd) {
+		cci_map[0U] = CCI500_CLUSTER0_SL_IFACE_IX;
+		cci_map[1U] = CCI500_CLUSTER1_SL_IFACE_IX;
+	}
+
+	cci_init(RCAR_CCI_BASE, cci_map, ARRAY_SIZE(cci_map));
+}
+
+void plat_cci_enable(void)
+{
+	cci_enable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr()));
+}
+
+void plat_cci_disable(void)
+{
+	cci_disable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr()));
+}
+
+struct entry_point_info *bl31_plat_get_next_image_ep_info(uint32_t type)
+{
+	bl2_to_bl31_params_mem_t *from_bl2 = (bl2_to_bl31_params_mem_t *)
+					     PARAMS_BASE;
+	entry_point_info_t *next_image_info;
+
+	next_image_info = (type == NON_SECURE) ?
+		&from_bl2->bl33_ep_info : &from_bl2->bl32_ep_info;
+
+	return next_image_info->pc ? next_image_info : NULL;
+}
+
+void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
+				u_register_t arg2, u_register_t arg3)
+{
+	rcar_console_runtime_init();
+
+	NOTICE("BL3-1 : Rev.%s\n", version_of_renesas);
+
+#if RCAR_LSI != RCAR_D3
+	if (rcar_pwrc_get_cluster() == RCAR_CLUSTER_A53A57) {
+		plat_cci_init();
+		plat_cci_enable();
+	}
+#endif /* RCAR_LSI != RCAR_D3 */
+}
+
+void bl31_plat_arch_setup(void)
+{
+	rcar_configure_mmu_el3(BL31_BASE,
+			       BL31_LIMIT - BL31_BASE,
+			       BL31_RO_BASE, BL31_RO_LIMIT
+#if USE_COHERENT_MEM
+			       , BL31_COHERENT_RAM_BASE, BL31_COHERENT_RAM_LIMIT
+#endif /* USE_COHERENT_MEM */
+	    );
+	rcar_pwrc_code_copy_to_system_ram();
+}
+
+void bl31_platform_setup(void)
+{
+	plat_rcar_gic_driver_init();
+	plat_rcar_gic_init();
+
+	/* enable the system level generic timer */
+	mmio_write_32(RCAR_CNTC_BASE + CNTCR_OFF, CNTCR_FCREQ(U(0)) | CNTCR_EN);
+
+	rcar_pwrc_setup();
+#if 0
+	/*
+	 * TODO: there is a broad number of rcar-gen3 SoC configurations; to
+	 * support all of them, Renesas use the pwrc driver to discover what
+	 * cores are on/off before announcing the topology.
+	 * This code hasnt been ported yet
+	 */
+
+	rcar_setup_topology();
+#endif
+
+	/*
+	 * mask should match the kernel's MPIDR_HWID_BITMASK so the core can be
+	 * identified during cpuhotplug (check the kernel's psci migrate set of
+	 * functions
+	 */
+	rcar_boot_mpidr = read_mpidr_el1() & 0x0000ffffU;
+}
diff --git a/plat/renesas/common/common.mk b/plat/renesas/common/common.mk
new file mode 100644
index 0000000..0d88d65
--- /dev/null
+++ b/plat/renesas/common/common.mk
@@ -0,0 +1,139 @@
+#
+# Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+PROGRAMMABLE_RESET_ADDRESS	:= 0
+COLD_BOOT_SINGLE_CPU		:= 1
+ARM_CCI_PRODUCT_ID		:= 500
+TRUSTED_BOARD_BOOT		:= 1
+RESET_TO_BL31			:= 1
+GENERATE_COT			:= 1
+BL2_AT_EL3			:= 1
+ENABLE_SVE_FOR_NS		:= 0
+MULTI_CONSOLE_API		:= 1
+
+CRASH_REPORTING			:= 1
+HANDLE_EA_EL3_FIRST		:= 1
+
+$(eval $(call add_define,PLAT_EXTRA_LD_SCRIPT))
+
+ifeq (${SPD},none)
+  SPD_NONE:=1
+  $(eval $(call add_define,SPD_NONE))
+endif
+
+# LSI setting common define
+RCAR_H3:=0
+RCAR_M3:=1
+RCAR_M3N:=2
+RCAR_E3:=3
+RCAR_H3N:=4
+RCAR_D3:=5
+RCAR_V3M:=6
+RCAR_AUTO:=99
+RZ_G2M:=100
+RZ_G2H:=101
+RZ_G2N:=102
+RZ_G2E:=103
+$(eval $(call add_define,RCAR_H3))
+$(eval $(call add_define,RCAR_M3))
+$(eval $(call add_define,RCAR_M3N))
+$(eval $(call add_define,RCAR_E3))
+$(eval $(call add_define,RCAR_H3N))
+$(eval $(call add_define,RCAR_D3))
+$(eval $(call add_define,RCAR_V3M))
+$(eval $(call add_define,RCAR_AUTO))
+$(eval $(call add_define,RZ_G2M))
+$(eval $(call add_define,RZ_G2H))
+$(eval $(call add_define,RZ_G2N))
+$(eval $(call add_define,RZ_G2E))
+
+RCAR_CUT_10:=0
+RCAR_CUT_11:=1
+RCAR_CUT_13:=3
+RCAR_CUT_20:=10
+RCAR_CUT_30:=20
+$(eval $(call add_define,RCAR_CUT_10))
+$(eval $(call add_define,RCAR_CUT_11))
+$(eval $(call add_define,RCAR_CUT_13))
+$(eval $(call add_define,RCAR_CUT_20))
+$(eval $(call add_define,RCAR_CUT_30))
+
+# Enable workarounds for selected Cortex-A53 erratas.
+ERRATA_A53_835769  := 1
+ERRATA_A53_843419  := 1
+ERRATA_A53_855873  := 1
+ERRATA_A53_1530924 := 1
+
+# Enable workarounds for selected Cortex-A57 erratas.
+ERRATA_A57_859972  := 1
+ERRATA_A57_813419  := 1
+ERRATA_A57_1319537 := 1
+
+PLAT_INCLUDES	:=	-Iplat/renesas/common/include/registers	\
+			-Iplat/renesas/common/include		\
+			-Iplat/renesas/common
+
+PLAT_BL_COMMON_SOURCES	:=	drivers/renesas/common/iic_dvfs/iic_dvfs.c \
+				plat/renesas/common/rcar_common.c
+
+include drivers/arm/gic/v2/gicv2.mk
+RCAR_GIC_SOURCES	:=	${GICV2_SOURCES} \
+				plat/common/plat_gicv2.c
+
+BL2_SOURCES	+=	${RCAR_GIC_SOURCES}				\
+			lib/cpus/aarch64/cortex_a53.S			\
+			lib/cpus/aarch64/cortex_a57.S			\
+			${LIBFDT_SRCS}					\
+			common/desc_image_load.c			\
+			plat/renesas/common/aarch64/platform_common.c	\
+			plat/renesas/common/aarch64/plat_helpers.S	\
+			plat/renesas/common/bl2_interrupt_error.c	\
+			plat/renesas/common/bl2_secure_setting.c	\
+			plat/renesas/common/plat_storage.c		\
+			plat/renesas/common/bl2_plat_mem_params_desc.c	\
+			plat/renesas/common/plat_image_load.c		\
+			plat/renesas/common/bl2_cpg_init.c		\
+			drivers/renesas/common/console/rcar_printf.c	\
+			drivers/renesas/common/scif/scif.S		\
+			drivers/renesas/common/common.c			\
+			drivers/renesas/common/io/io_emmcdrv.c		\
+			drivers/renesas/common/io/io_memdrv.c		\
+			drivers/renesas/common/io/io_rcar.c		\
+			drivers/renesas/common/auth/auth_mod.c		\
+			drivers/renesas/common/rpc/rpc_driver.c		\
+			drivers/renesas/common/dma/dma_driver.c		\
+			drivers/renesas/common/avs/avs_driver.c		\
+			drivers/renesas/common/delay/micro_delay.c	\
+			drivers/renesas/common/emmc/emmc_interrupt.c	\
+			drivers/renesas/common/emmc/emmc_utility.c	\
+			drivers/renesas/common/emmc/emmc_mount.c	\
+			drivers/renesas/common/emmc/emmc_init.c		\
+			drivers/renesas/common/emmc/emmc_read.c		\
+			drivers/renesas/common/emmc/emmc_cmd.c		\
+			drivers/renesas/common/watchdog/swdt.c		\
+			drivers/renesas/common/rom/rom_api.c		\
+			drivers/io/io_storage.c
+
+BL31_SOURCES	+=	${RCAR_GIC_SOURCES}				\
+			lib/cpus/aarch64/cortex_a53.S			\
+			lib/cpus/aarch64/cortex_a57.S			\
+			plat/common/plat_psci_common.c			\
+			plat/renesas/common/plat_topology.c		\
+			plat/renesas/common/aarch64/plat_helpers.S	\
+			plat/renesas/common/aarch64/platform_common.c	\
+			plat/renesas/common/bl31_plat_setup.c		\
+			plat/renesas/common/plat_pm.c			\
+			drivers/renesas/common/console/rcar_console.S	\
+			drivers/renesas/common/console/rcar_printf.c	\
+			drivers/renesas/common/delay/micro_delay.c	\
+			drivers/renesas/common/pwrc/call_sram.S		\
+			drivers/renesas/common/pwrc/pwrc.c		\
+			drivers/renesas/common/common.c			\
+			drivers/arm/cci/cci.c
+
+include lib/xlat_tables_v2/xlat_tables.mk
+include drivers/auth/mbedtls/mbedtls_crypto.mk
+PLAT_BL_COMMON_SOURCES	+=	${XLAT_TABLES_LIB_SRCS}
diff --git a/plat/renesas/rcar/include/plat.ld.S b/plat/renesas/common/include/plat.ld.S
similarity index 100%
rename from plat/renesas/rcar/include/plat.ld.S
rename to plat/renesas/common/include/plat.ld.S
diff --git a/plat/renesas/rcar/include/plat_macros.S b/plat/renesas/common/include/plat_macros.S
similarity index 100%
rename from plat/renesas/rcar/include/plat_macros.S
rename to plat/renesas/common/include/plat_macros.S
diff --git a/plat/renesas/common/include/platform_def.h b/plat/renesas/common/include/platform_def.h
new file mode 100644
index 0000000..1213a3c
--- /dev/null
+++ b/plat/renesas/common/include/platform_def.h
@@ -0,0 +1,200 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PLATFORM_DEF_H
+#define PLATFORM_DEF_H
+
+#ifndef __ASSEMBLER__
+#include <stdlib.h>
+#endif
+
+#include <arch.h>
+
+#include "rcar_def.h"
+
+/*******************************************************************************
+ * Platform binary types for linking
+ ******************************************************************************/
+#define PLATFORM_LINKER_FORMAT          "elf64-littleaarch64"
+#define PLATFORM_LINKER_ARCH            aarch64
+
+/*******************************************************************************
+ * Generic platform constants
+ ******************************************************************************/
+ #define FIRMWARE_WELCOME_STR	"Booting Rcar-gen3 Trusted Firmware\n"
+
+/* Size of cacheable stacks */
+#if IMAGE_BL1
+#if TRUSTED_BOARD_BOOT
+#define PLATFORM_STACK_SIZE	U(0x1000)
+#else
+#define PLATFORM_STACK_SIZE	U(0x440)
+#endif
+#elif IMAGE_BL2
+#if TRUSTED_BOARD_BOOT
+#define PLATFORM_STACK_SIZE	U(0x1000)
+#else
+#define PLATFORM_STACK_SIZE	U(0x400)
+#endif
+#elif IMAGE_BL31
+#define PLATFORM_STACK_SIZE	U(0x400)
+#elif IMAGE_BL32
+#define PLATFORM_STACK_SIZE	U(0x440)
+#endif
+
+#define BL332_IMAGE_ID		(NS_BL2U_IMAGE_ID + 1)
+#define BL333_IMAGE_ID		(NS_BL2U_IMAGE_ID + 2)
+#define BL334_IMAGE_ID		(NS_BL2U_IMAGE_ID + 3)
+#define BL335_IMAGE_ID		(NS_BL2U_IMAGE_ID + 4)
+#define BL336_IMAGE_ID		(NS_BL2U_IMAGE_ID + 5)
+#define BL337_IMAGE_ID		(NS_BL2U_IMAGE_ID + 6)
+#define BL338_IMAGE_ID		(NS_BL2U_IMAGE_ID + 7)
+
+#define BL332_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 8)
+#define BL333_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 9)
+#define BL334_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 10)
+#define BL335_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 11)
+#define BL336_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 12)
+#define BL337_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 13)
+#define BL338_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 14)
+
+#define BL332_CERT_ID		(NS_BL2U_IMAGE_ID + 15)
+#define BL333_CERT_ID		(NS_BL2U_IMAGE_ID + 16)
+#define BL334_CERT_ID		(NS_BL2U_IMAGE_ID + 17)
+#define BL335_CERT_ID		(NS_BL2U_IMAGE_ID + 18)
+#define BL336_CERT_ID		(NS_BL2U_IMAGE_ID + 19)
+#define BL337_CERT_ID		(NS_BL2U_IMAGE_ID + 20)
+#define BL338_CERT_ID		(NS_BL2U_IMAGE_ID + 21)
+
+/* io drivers id */
+#define FLASH_DEV_ID		U(0)
+#define EMMC_DEV_ID		U(1)
+
+/*
+ * R-Car H3 Cortex-A57
+ * L1:I/48KB(16KBx3way) D/32KB(16KBx2way) L2:2MB(128KBx16way)
+ *          Cortex-A53
+ * L1:I/32KB(16KBx2way) D/32KB(8KBx4way) L2:512KB(32KBx16way)
+ */
+#define PLATFORM_CACHE_LINE_SIZE	64
+#define PLATFORM_CLUSTER_COUNT		U(2)
+#define PLATFORM_CLUSTER0_CORE_COUNT	U(4)
+#define PLATFORM_CLUSTER1_CORE_COUNT	U(4)
+#define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER1_CORE_COUNT + \
+					 PLATFORM_CLUSTER0_CORE_COUNT)
+#define PLATFORM_MAX_CPUS_PER_CLUSTER	U(4)
+
+#define PLAT_MAX_PWR_LVL		MPIDR_AFFLVL2
+#define PLAT_NUM_PWR_DOMAINS		(PLATFORM_CORE_COUNT + \
+					 PLATFORM_CLUSTER_COUNT + 1)
+
+#define PLAT_MAX_RET_STATE		U(1)
+#define PLAT_MAX_OFF_STATE		U(2)
+
+#define MAX_IO_DEVICES			U(3)
+#define MAX_IO_HANDLES			U(4)
+
+/*
+ ******************************************************************************
+ * BL2 specific defines.
+ ******************************************************************************
+ * Put BL2 just below BL3-1. BL2_BASE is calculated using the current BL2 debug
+ * size plus a little space for growth.
+ */
+#define RCAR_SYSRAM_BASE		U(0xE6300000)
+#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
+#define BL2_LIMIT			U(0xE6320000)
+#else
+#define BL2_LIMIT			U(0xE6360000)
+#endif
+
+#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
+#define BL2_BASE			U(0xE6304000)
+#define BL2_IMAGE_LIMIT			U(0xE6318000)
+#elif (RCAR_LSI == RCAR_V3M)
+#define BL2_BASE			U(0xE6344000)
+#define BL2_IMAGE_LIMIT			U(0xE636E800)
+#else
+#define BL2_BASE			U(0xE6304000)
+#define BL2_IMAGE_LIMIT			U(0xE632E800)
+#endif
+#define RCAR_SYSRAM_SIZE		(BL2_BASE - RCAR_SYSRAM_BASE)
+
+/*
+ ******************************************************************************
+ * BL31 specific defines.
+ ******************************************************************************
+ * Put BL3-1 at the top of the Trusted SRAM. BL31_BASE is calculated using the
+ * current BL3-1 debug size plus a little space for growth.
+ */
+#define BL31_BASE		(RCAR_TRUSTED_SRAM_BASE)
+#define BL31_LIMIT		(RCAR_TRUSTED_SRAM_BASE + \
+				 RCAR_TRUSTED_SRAM_SIZE)
+#define RCAR_BL31_LOG_BASE	(0x44040000)
+#define RCAR_BL31_SDRAM_BTM	(RCAR_BL31_LOG_BASE + 0x14000)
+#define RCAR_BL31_LOG_SIZE	(RCAR_BL31_SDRAM_BTM - RCAR_BL31_LOG_BASE)
+#define BL31_SRAM_BASE		(DEVICE_SRAM_BASE)
+#define BL31_SRAM_LIMIT		(DEVICE_SRAM_BASE + DEVICE_SRAM_SIZE)
+
+/*******************************************************************************
+ * BL32 specific defines.
+ ******************************************************************************/
+#ifndef SPD_NONE
+#define BL32_BASE		U(0x44100000)
+#define BL32_LIMIT		(BL32_BASE + U(0x200000))
+#endif
+
+/*******************************************************************************
+ * BL33
+ ******************************************************************************/
+#define BL33_BASE		DRAM1_NS_BASE
+#define BL33_COMP_SIZE		U(0x200000)
+#define BL33_COMP_BASE		(BL33_BASE - BL33_COMP_SIZE)
+
+/*******************************************************************************
+ * Platform specific page table and MMU setup constants
+ ******************************************************************************/
+#if IMAGE_BL1
+#define MAX_XLAT_TABLES		U(2)
+#elif IMAGE_BL2
+#define MAX_XLAT_TABLES		U(5)
+#elif IMAGE_BL31
+#define MAX_XLAT_TABLES		U(4)
+#elif IMAGE_BL32
+#define MAX_XLAT_TABLES		U(3)
+#endif
+
+#if IMAGE_BL2
+#define PLAT_PHY_ADDR_SPACE_SIZE	(ULL(1) << 40)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(ULL(1) << 40)
+#else
+#define PLAT_PHY_ADDR_SPACE_SIZE	(ULL(1) << 32)
+#define PLAT_VIRT_ADDR_SPACE_SIZE	(ULL(1) << 32)
+#endif
+
+#define MAX_MMAP_REGIONS	(RCAR_MMAP_ENTRIES + RCAR_BL_REGIONS)
+
+/*******************************************************************************
+ * Declarations and constants to access the mailboxes safely. Each mailbox is
+ * aligned on the biggest cache line size in the platform. This is known only
+ * to the platform as it might have a combination of integrated and external
+ * caches. Such alignment ensures that two mailboxes do not sit on the same cache
+ * line at any cache level. They could belong to different cpus/clusters &
+ * get written while being protected by different locks causing corruption of
+ * a valid mailbox address.
+ ******************************************************************************/
+#define CACHE_WRITEBACK_SHIFT   (6)
+#define CACHE_WRITEBACK_GRANULE (1 << CACHE_WRITEBACK_SHIFT)
+
+/*******************************************************************************
+ * Size of the per-cpu data in bytes that should be reserved in the generic
+ * per-cpu data structure for the RCAR port.
+ ******************************************************************************/
+#if !USE_COHERENT_MEM
+#define PLAT_PCPU_DATA_SIZE	(2)
+#endif
+
+#endif /* PLATFORM_DEF_H */
diff --git a/plat/renesas/common/include/rcar_def.h b/plat/renesas/common/include/rcar_def.h
new file mode 100644
index 0000000..2cd26ed
--- /dev/null
+++ b/plat/renesas/common/include/rcar_def.h
@@ -0,0 +1,313 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RCAR_DEF_H
+#define RCAR_DEF_H
+
+#include <common/tbbr/tbbr_img_def.h>
+#include <lib/utils_def.h>
+
+#define RCAR_PRIMARY_CPU		0x0
+#define RCAR_TRUSTED_SRAM_BASE		0x44000000
+#define RCAR_TRUSTED_SRAM_SIZE		0x0003E000
+#define RCAR_SHARED_MEM_BASE		(RCAR_TRUSTED_SRAM_BASE + \
+					RCAR_TRUSTED_SRAM_SIZE)
+#define RCAR_SHARED_MEM_SIZE		U(0x00001000)
+#define FLASH0_BASE			U(0x08000000)
+#define FLASH0_SIZE			U(0x04000000)
+#define FLASH_MEMORY_SIZE		U(0x04000000)	/* hyper flash */
+#define FLASH_TRANS_SIZE_UNIT		U(0x00000100)
+#define DEVICE_RCAR_BASE		U(0xE6000000)
+#define DEVICE_RCAR_SIZE		U(0x00300000)
+#define DEVICE_RCAR_BASE2		U(0xE6360000)
+#define DEVICE_RCAR_SIZE2		U(0x19CA0000)
+#define DEVICE_SRAM_BASE		U(0xE6300000)
+#define DEVICE_SRAM_SIZE		U(0x00002000)
+#define DEVICE_SRAM_STACK_BASE		(DEVICE_SRAM_BASE + DEVICE_SRAM_SIZE)
+#define DEVICE_SRAM_STACK_SIZE		U(0x00001000)
+#define DRAM_LIMIT			ULL(0x0000010000000000)
+#define DRAM1_BASE			U(0x40000000)
+#define DRAM1_SIZE			U(0x80000000)
+#define DRAM1_NS_BASE			(DRAM1_BASE + U(0x10000000))
+#define DRAM1_NS_SIZE			(DRAM1_SIZE - DRAM1_NS_BASE)
+#define DRAM_40BIT_BASE			ULL(0x0400000000)
+#define DRAM_40BIT_SIZE			ULL(0x0400000000)
+#define DRAM_PROTECTED_BASE		ULL(0x43F00000)
+#define DRAM_40BIT_PROTECTED_BASE	ULL(0x0403F00000)
+#define DRAM_PROTECTED_SIZE		ULL(0x03F00000)
+#define RCAR_BL31_CRASH_BASE		U(0x4403F000)
+#define RCAR_BL31_CRASH_SIZE		U(0x00001000)
+/* Entrypoint mailboxes */
+#define MBOX_BASE			RCAR_SHARED_MEM_BASE
+#define MBOX_SIZE			0x200
+/* Base address where parameters to BL31 are stored */
+#define PARAMS_BASE			(MBOX_BASE + MBOX_SIZE)
+#define BOOT_KIND_BASE			(RCAR_SHARED_MEM_BASE + \
+					RCAR_SHARED_MEM_SIZE - 0x100)
+/*
+ * The number of regions like RO(code), coherent and data required by
+ * different BL stages which need to be mapped in the MMU
+ */
+#if USE_COHERENT_MEM
+#define RCAR_BL_REGIONS			(3)
+#else
+#define RCAR_BL_REGIONS			(2)
+#endif
+/*
+ * The RCAR_MAX_MMAP_REGIONS depends on the number of entries in rcar_mmap[]
+ * defined for each BL stage in rcar_common.c.
+ */
+#if IMAGE_BL2
+#define RCAR_MMAP_ENTRIES		(9)
+#endif
+#if IMAGE_BL31
+#define RCAR_MMAP_ENTRIES		(9)
+#endif
+#if IMAGE_BL2
+#define REG1_BASE			U(0xE6400000)
+#define REG1_SIZE			U(0x04C00000)
+#define ROM0_BASE			U(0xEB100000)
+#define ROM0_SIZE			U(0x00028000)
+#define REG2_BASE			U(0xEC000000)
+#define REG2_SIZE			U(0x14000000)
+#endif
+/* BL33  */
+#define NS_IMAGE_OFFSET			(DRAM1_BASE + U(0x09000000))
+/* BL31 */
+#define RCAR_DEVICE_BASE		DEVICE_RCAR_BASE
+#define RCAR_DEVICE_SIZE		(0x1A000000)
+#define RCAR_LOG_RES_SIZE		(64)
+#define RCAR_LOG_HEADER_SIZE		(16)
+#define RCAR_LOG_OTHER_SIZE		(RCAR_LOG_HEADER_SIZE + \
+					RCAR_LOG_RES_SIZE)
+#define RCAR_BL31_LOG_MAX		(RCAR_BL31_LOG_SIZE - \
+					RCAR_LOG_OTHER_SIZE)
+#define RCAR_CRASH_STACK		RCAR_BL31_CRASH_BASE
+#define AARCH64_SPACE_BASE		ULL(0x00000000000)
+#define AARCH64_SPACE_SIZE		ULL(0x10000000000)
+/* CCI related constants */
+#define CCI500_BASE				U(0xF1200000)
+#define CCI500_CLUSTER0_SL_IFACE_IX		(2)
+#define CCI500_CLUSTER1_SL_IFACE_IX		(3)
+#define CCI500_CLUSTER0_SL_IFACE_IX_FOR_M3	(1)
+#define CCI500_CLUSTER1_SL_IFACE_IX_FOR_M3	(2)
+#define RCAR_CCI_BASE				CCI500_BASE
+/* GIC */
+#define RCAR_GICD_BASE			U(0xF1010000)
+#define RCAR_GICR_BASE			U(0xF1010000)
+#define RCAR_GICC_BASE			U(0xF1020000)
+#define RCAR_GICH_BASE			U(0xF1040000)
+#define RCAR_GICV_BASE			U(0xF1060000)
+#define ARM_IRQ_SEC_PHY_TIMER		U(29)
+#define ARM_IRQ_SEC_SGI_0		U(8)
+#define ARM_IRQ_SEC_SGI_1		U(9)
+#define ARM_IRQ_SEC_SGI_2		U(10)
+#define ARM_IRQ_SEC_SGI_3		U(11)
+#define ARM_IRQ_SEC_SGI_4		U(12)
+#define ARM_IRQ_SEC_SGI_5		U(13)
+#define ARM_IRQ_SEC_SGI_6		U(14)
+#define ARM_IRQ_SEC_SGI_7		U(15)
+#define ARM_IRQ_SEC_RPC			U(70)
+#define ARM_IRQ_SEC_TIMER		U(166)
+#define ARM_IRQ_SEC_TIMER_UP		U(171)
+#define ARM_IRQ_SEC_WDT			U(173)
+#define ARM_IRQ_SEC_CRYPT		U(102)
+#define ARM_IRQ_SEC_CRYPT_SecPKA	U(97)
+#define ARM_IRQ_SEC_CRYPT_PubPKA	U(98)
+/* Timer control */
+#define RCAR_CNTC_BASE		U(0xE6080000)
+/* Reset */
+#define RCAR_MODEMR		U(0xE6160060)	/* Mode pin             */
+#define RCAR_CA57RESCNT		U(0xE6160040)	/* Reset control A57    */
+#define RCAR_CA53RESCNT		U(0xE6160044)	/* Reset control A53    */
+#define RCAR_SRESCR		U(0xE6160110)	/* Soft Power On Reset  */
+#define RCAR_CA53WUPCR		U(0xE6151010)	/* Wake-up control A53  */
+#define RCAR_CA57WUPCR		U(0xE6152010)	/* Wake-up control A57  */
+#define RCAR_CA53PSTR		U(0xE6151040)	/* Power status A53     */
+#define RCAR_CA57PSTR		U(0xE6152040)	/* Power status A57     */
+#define RCAR_CA53CPU0CR		U(0xE6151100)	/* CPU control  A53     */
+#define RCAR_CA57CPU0CR		U(0xE6152100)	/* CPU control  A57     */
+#define RCAR_CA53CPUCMCR	U(0xE6151184)	/* Common power A53     */
+#define RCAR_CA57CPUCMCR	U(0xE6152184)	/* Common power A57     */
+#define RCAR_WUPMSKCA57		U(0xE6180014)	/* Wake-up mask A57     */
+#define RCAR_WUPMSKCA53		U(0xE6180018)	/* Wake-up mask A53     */
+/* SYSC	*/
+#define RCAR_PWRSR3		U(0xE6180140)	/* Power stat A53-SCU   */
+#define RCAR_PWRSR5		U(0xE61801C0)	/* Power stat A57-SCU   */
+#define RCAR_SYSCIER		U(0xE618000C)	/* Interrupt enable     */
+#define RCAR_SYSCIMR		U(0xE6180010)	/* Interrupt mask       */
+#define RCAR_SYSCSR		U(0xE6180000)	/* SYSC status          */
+#define RCAR_PWRONCR3		U(0xE618014C)	/* Power resume A53-SCU */
+#define RCAR_PWRONCR5		U(0xE61801CC)	/* Power resume A57-SCU */
+#define RCAR_PWROFFCR3		U(0xE6180144)	/* Power shutoff A53-SCU */
+#define RCAR_PWROFFCR5		U(0xE61801C4)	/* Power shutoff A57-SCU */
+#define RCAR_PWRER3		U(0xE6180154)	/* shutoff/resume error */
+#define RCAR_PWRER5		U(0xE61801D4)	/* shutoff/resume error */
+#define RCAR_SYSCISR		U(0xE6180004)	/* Interrupt status     */
+#define RCAR_SYSCISCR		U(0xE6180008)	/* Interrupt stat clear */
+#define RCAR_SYSCEXTMASK	U(0xE61802F8)	/* External Request Mask */
+						/* H3/H3-N, M3 v3.0, M3-N, E3 */
+/* Product register */
+#define RCAR_PRR			U(0xFFF00044)
+#define RCAR_M3_CUT_VER11		U(0x00000010)	/* M3 Ver.1.1/Ver.1.2 */
+#define RCAR_D3_CUT_VER10		U(0x00000000)	/* D3 Ver.1.0 */
+#define RCAR_D3_CUT_VER11		U(0x00000010)	/* D3 Ver.1.1 */
+#define RCAR_MAJOR_MASK			U(0x000000F0)
+#define RCAR_MINOR_MASK			U(0x0000000F)
+#define PRR_PRODUCT_SHIFT		U(8)
+#define RCAR_MAJOR_SHIFT		U(4)
+#define RCAR_MINOR_SHIFT		U(0)
+#define RCAR_MAJOR_OFFSET		U(1)
+#define RCAR_M3_MINOR_OFFSET		U(2)
+#define PRR_PRODUCT_H3_CUT10		(PRR_PRODUCT_H3 | U(0x00))	/* 1.0 */
+#define PRR_PRODUCT_H3_CUT11		(PRR_PRODUCT_H3 | U(0x01))	/* 1.1 */
+#define PRR_PRODUCT_H3_CUT20		(PRR_PRODUCT_H3 | U(0x10))	/* 2.0 */
+#define PRR_PRODUCT_M3_CUT10		(PRR_PRODUCT_M3 | U(0x00))	/* 1.0 */
+#define PRR_PRODUCT_M3_CUT11		(PRR_PRODUCT_M3 | U(0x10))
+#define PRR				0xFFF00044U
+#define PRR_PRODUCT_MASK		0x00007F00U
+#define PRR_CUT_MASK			0x000000FFU
+#define PRR_PRODUCT_H3			0x00004F00U	/* R-Car H3 */
+#define PRR_PRODUCT_M3			0x00005200U	/* R-Car M3-W */
+#define PRR_PRODUCT_V3M			0x00005400U	/* R-Car V3M */
+#define PRR_PRODUCT_M3N			0x00005500U	/* R-Car M3-N */
+#define PRR_PRODUCT_V3H			0x00005600U	/* R-Car V3H */
+#define PRR_PRODUCT_E3			0x00005700U	/* R-Car E3 */
+#define PRR_PRODUCT_D3			0x00005800U	/* R-Car D3 */
+#define PRR_PRODUCT_10			0x00U		/* Ver.1.0 */
+#define PRR_PRODUCT_11			0x01U		/* Ver.1.1 */
+#define PRR_PRODUCT_20			0x10U		/* Ver.2.0 */
+#define PRR_PRODUCT_21			0x11U		/* Ver.2.1 */
+#define PRR_PRODUCT_30			0x20U		/* Ver.3.0 */
+#define RCAR_CPU_MASK_CA57		U(0x80000000)
+#define RCAR_CPU_MASK_CA53		U(0x04000000)
+#define RCAR_CPU_HAVE_CA57		U(0x00000000)
+#define RCAR_CPU_HAVE_CA53		U(0x00000000)
+#define RCAR_SSCG_MASK			U(0x1000)	/* MD12 */
+#define RCAR_SSCG_ENABLE		U(0x1000)
+/* MD pin information */
+#define MODEMR_BOOT_CPU_MASK		U(0x000000C0)
+#define MODEMR_BOOT_CPU_CR7		U(0x000000C0)
+#define MODEMR_BOOT_CPU_CA57		U(0x00000000)
+#define MODEMR_BOOT_CPU_CA53		U(0x00000040)
+#define MODEMR_BOOT_DEV_MASK		U(0x0000001E)
+#define MODEMR_BOOT_DEV_HYPERFLASH160	U(0x00000004)
+#define MODEMR_BOOT_DEV_HYPERFLASH80	U(0x00000006)
+#define MODEMR_BOOT_DEV_QSPI_FLASH40	U(0x00000008)
+#define MODEMR_BOOT_DEV_QSPI_FLASH80	U(0x0000000C)
+#define MODEMR_BOOT_DEV_EMMC_25X1	U(0x0000000A)
+#define MODEMR_BOOT_DEV_EMMC_50X8	U(0x0000001A)
+#define MODEMR_BOOT_PLL_MASK		U(0x00006000)
+#define MODEMR_BOOT_PLL_SHIFT		U(13)
+/* Memory mapped Generic timer interfaces */
+#define ARM_SYS_CNTCTL_BASE		RCAR_CNTC_BASE
+/* MODEMR PLL masks and bitfield values */
+#define CHECK_MD13_MD14			U(0x6000)
+#define MD14_MD13_TYPE_0		U(0x0000)	/* MD14=0 MD13=0 */
+#define MD14_MD13_TYPE_1		U(0x2000)	/* MD14=0 MD13=1 */
+#define MD14_MD13_TYPE_2		U(0x4000)	/* MD14=1 MD13=0 */
+#define MD14_MD13_TYPE_3		U(0x6000)	/* MD14=1 MD13=1 */
+/* Frequency of EXTAL(Hz) */
+#define EXTAL_MD14_MD13_TYPE_0		U(8333300)	/* MD14=0 MD13=0 */
+#define EXTAL_MD14_MD13_TYPE_1		U(10000000)	/* MD14=0 MD13=1 */
+#define EXTAL_MD14_MD13_TYPE_2		U(12500000)	/* MD14=1 MD13=0 */
+#define EXTAL_MD14_MD13_TYPE_3		U(16666600)	/* MD14=1 MD13=1 */
+#define EXTAL_SALVATOR_XS		U(8320000)	/* Salvator-XS */
+#define EXTAL_EBISU			U(24000000)	/* Ebisu */
+#define EXTAL_DRAAK			U(24000000)	/* Draak */
+/* CPG write protect registers	*/
+#define CPGWPR_PASSWORD			(0x5A5AFFFFU)
+#define CPGWPCR_PASSWORD		(0xA5A50000U)
+/* CA5x Debug Resource control registers */
+#define CPG_CA57DBGRCR			(CPG_BASE + 0x2180U)
+#define CPG_CA53DBGRCR			(CPG_BASE + 0x1180U)
+#define DBGCPUPREN			((uint32_t)1U << 19U)
+#define CPG_PLL0CR			(CPG_BASE + 0x00D8U)
+#define CPG_PLL2CR			(CPG_BASE + 0x002CU)
+#define CPG_PLL4CR			(CPG_BASE + 0x01F4U)
+#define CPG_CPGWPCR			(CPG_BASE + 0x0904U)
+/* RST Registers */
+#define RST_BASE			(0xE6160000U)
+#define RST_WDTRSTCR			(RST_BASE + 0x0054U)
+#define RST_MODEMR			(RST_BASE + 0x0060U)
+#define WDTRSTCR_PASSWORD		(0xA55A0000U)
+#define WDTRSTCR_RWDT_RSTMSK		((uint32_t)1U << 0U)
+/* MFIS Registers */
+#define MFISWPCNTR_PASSWORD		(0xACCE0000U)
+#define MFISWPCNTR			(0xE6260900U)
+/* IPMMU registers */
+#define IPMMU_MM_BASE			(0xE67B0000U)
+#define IPMMUMM_IMSCTLR			(IPMMU_MM_BASE + 0x0500U)
+#define IPMMUMM_IMAUXCTLR		(IPMMU_MM_BASE + 0x0504U)
+#define IPMMUMM_IMSCTLR_ENABLE		(0xC0000000U)
+#define IPMMUMM_IMAUXCTLR_NMERGE40_BIT	(0x01000000U)
+#define IMSCTLR_DISCACHE		(0xE0000000U)
+#define IPMMU_VP0_BASE			(0xFE990000U)
+#define IPMMUVP0_IMSCTLR		(IPMMU_VP0_BASE + 0x0500U)
+#define IPMMU_VI0_BASE			(0xFEBD0000U)
+#define IPMMUVI0_IMSCTLR		(IPMMU_VI0_BASE + 0x0500U)
+#define IPMMU_VI1_BASE			(0xFEBE0000U)
+#define IPMMUVI1_IMSCTLR		(IPMMU_VI1_BASE + 0x0500U)
+#define IPMMU_PV0_BASE			(0xFD800000U)
+#define IPMMUPV0_IMSCTLR		(IPMMU_PV0_BASE + 0x0500U)
+#define IPMMU_PV1_BASE			(0xFD950000U)
+#define IPMMUPV1_IMSCTLR		(IPMMU_PV1_BASE + 0x0500U)
+#define IPMMU_PV2_BASE			(0xFD960000U)
+#define IPMMUPV2_IMSCTLR		(IPMMU_PV2_BASE + 0x0500U)
+#define IPMMU_PV3_BASE			(0xFD970000U)
+#define IPMMUPV3_IMSCTLR		(IPMMU_PV3_BASE + 0x0500U)
+#define IPMMU_HC_BASE			(0xE6570000U)
+#define IPMMUHC_IMSCTLR			(IPMMU_HC_BASE + 0x0500U)
+#define IPMMU_RT_BASE			(0xFFC80000U)
+#define IPMMURT_IMSCTLR			(IPMMU_RT_BASE + 0x0500U)
+#define IPMMU_MP_BASE			(0xEC670000U)
+#define IPMMUMP_IMSCTLR			(IPMMU_MP_BASE + 0x0500U)
+#define IPMMU_DS0_BASE			(0xE6740000U)
+#define IPMMUDS0_IMSCTLR		(IPMMU_DS0_BASE + 0x0500U)
+#define IPMMU_DS1_BASE			(0xE7740000U)
+#define IPMMUDS1_IMSCTLR		(IPMMU_DS1_BASE + 0x0500U)
+/* ARMREG registers */
+#define P_ARMREG_SEC_CTRL		(0xE62711F0U)
+#define P_ARMREG_SEC_CTRL_PROT		(0x00000001U)
+/* MIDR */
+#define MIDR_CA57			(0x0D07U << MIDR_PN_SHIFT)
+#define MIDR_CA53			(0x0D03U << MIDR_PN_SHIFT)
+/* for SuspendToRAM */
+#define GPIO_BASE			(0xE6050000U)
+#define GPIO_INDT1			(GPIO_BASE + 0x100CU)
+#define GPIO_INDT3			(GPIO_BASE + 0x300CU)
+#define GPIO_INDT6			(GPIO_BASE + 0x540CU)
+#define GPIO_OUTDT1			(GPIO_BASE + 0x1008U)
+#define GPIO_OUTDT3			(GPIO_BASE + 0x3008U)
+#define GPIO_OUTDT6			(GPIO_BASE + 0x5408U)
+#define RCAR_COLD_BOOT			(0x00U)
+#define RCAR_WARM_BOOT			(0x01U)
+#if PMIC_ROHM_BD9571 && RCAR_SYSTEM_RESET_KEEPON_DDR
+#define KEEP10_MAGIC		(0x55U)
+#endif
+/* lossy registers */
+#define LOSSY_PARAMS_BASE		(0x47FD7000U)
+#define AXI_DCMPAREACRA0		(0xE6784100U)
+#define AXI_DCMPAREACRB0		(0xE6784104U)
+#define LOSSY_ENABLE			(0x80000000U)
+#define LOSSY_DISABLE			(0x00000000U)
+#define LOSSY_FMT_YUVPLANAR		(0x00000000U)
+#define LOSSY_FMT_YUV422INTLV		(0x20000000U)
+#define LOSSY_FMT_ARGB8888		(0x40000000U)
+#define LOSSY_ST_ADDR0			(0x54000000U)
+#define LOSSY_END_ADDR0			(0x57000000U)
+#define LOSSY_FMT0			LOSSY_FMT_YUVPLANAR
+#define LOSSY_ENA_DIS0			LOSSY_ENABLE
+#define LOSSY_ST_ADDR1			0x0U
+#define LOSSY_END_ADDR1			0x0U
+#define LOSSY_FMT1			LOSSY_FMT_ARGB8888
+#define LOSSY_ENA_DIS1			LOSSY_DISABLE
+#define LOSSY_ST_ADDR2			0x0U
+#define LOSSY_END_ADDR2			0x0U
+#define LOSSY_FMT2			LOSSY_FMT_YUV422INTLV
+#define LOSSY_ENA_DIS2			LOSSY_DISABLE
+
+#endif /* RCAR_DEF_H */
diff --git a/plat/renesas/common/include/rcar_private.h b/plat/renesas/common/include/rcar_private.h
new file mode 100644
index 0000000..36f4ca5
--- /dev/null
+++ b/plat/renesas/common/include/rcar_private.h
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RCAR_PRIVATE_H
+#define RCAR_PRIVATE_H
+
+#include <common/bl_common.h>
+#include <lib/bakery_lock.h>
+#include <lib/el3_runtime/cpu_data.h>
+
+#include <platform_def.h>
+
+typedef volatile struct mailbox {
+	unsigned long value __aligned(CACHE_WRITEBACK_GRANULE);
+} mailbox_t;
+
+/*
+ * This structure represents the superset of information that is passed to
+ * BL31 e.g. while passing control to it from BL2 which is bl31_params
+ * and bl31_plat_params and its elements
+ */
+typedef struct bl2_to_bl31_params_mem {
+	image_info_t bl32_image_info;
+	image_info_t bl33_image_info;
+	entry_point_info_t bl33_ep_info;
+	entry_point_info_t bl32_ep_info;
+} bl2_to_bl31_params_mem_t;
+
+#if USE_COHERENT_MEM
+#define RCAR_INSTANTIATE_LOCK	DEFINE_BAKERY_LOCK(rcar_lock);
+#define rcar_lock_init()	bakery_lock_init(&rcar_lock)
+#define rcar_lock_get()		bakery_lock_get(&rcar_lock)
+#define rcar_lock_release()	bakery_lock_release(&rcar_lock)
+#else
+/*
+ * Constants to specify how many bakery locks this platform implements. These
+ * are used if the platform chooses not to use coherent memory for bakery lock
+ * data structures.
+ */
+#define RCAR_MAX_BAKERIES	2
+#define RCAR_PWRC_BAKERY_ID	0
+
+/*
+ * Definition of structure which holds platform specific per-cpu data. Currently
+ * it holds only the bakery lock information for each cpu. Constants to
+ * specify how many bakeries this platform implements and bakery ids are
+ * specified in rcar_def.h
+ */
+typedef struct rcar_cpu_data {
+	bakery_info_t pcpu_bakery_info[RCAR_MAX_BAKERIES];
+} rcar_cpu_data_t;
+
+#define RCAR_CPU_DATA_LOCK_OFFSET	\
+	__builtin_offsetof(rcar_cpu_data_t, pcpu_bakery_info)
+/*
+ * Helper macros for bakery lock api when using the above rcar_cpu_data_t for
+ * bakery lock data structures. It assumes that the bakery_info is at the
+ * beginning of the platform specific per-cpu data.
+ */
+#define rcar_lock_init(_lock_arg)
+
+#define rcar_lock_get(_lock_arg)					\
+	bakery_lock_get(_lock_arg,					\
+		CPU_DATA_PLAT_PCPU_OFFSET + RCAR_CPU_DATA_LOCK_OFFSET)
+
+#define rcar_lock_release(_lock_arg)					\
+	bakery_lock_release(_lock_arg,					\
+		CPU_DATA_PLAT_PCPU_OFFSET + RCAR_CPU_DATA_LOCK_OFFSET)
+/*
+ * Ensure that the size of the RCAR specific per-cpu data structure and the size
+ * of the memory allocated in generic per-cpu data for the platform are the same
+ */
+CASSERT(sizeof(rcar_cpu_data_t) == PLAT_PCPU_DATA_SIZE,
+	rcar_pcpu_data_size_mismatch);
+#endif
+/*
+ * Function and variable prototypes
+ */
+void rcar_configure_mmu_el3(unsigned long total_base,
+			    unsigned long total_size,
+			    unsigned long ro_start, unsigned long ro_limit
+#if USE_COHERENT_MEM
+			    , unsigned long coh_start, unsigned long coh_limit
+#endif
+			    );
+
+void rcar_setup_topology(void);
+void rcar_cci_disable(void);
+void rcar_cci_enable(void);
+void rcar_cci_init(void);
+
+void plat_invalidate_icache(void);
+void plat_cci_disable(void);
+void plat_cci_enable(void);
+void plat_cci_init(void);
+
+void mstpcr_write(uint32_t mstpcr, uint32_t mstpsr, uint32_t target_bit);
+void cpg_write(uintptr_t regadr, uint32_t regval);
+
+void rcar_console_boot_init(void);
+void rcar_console_boot_end(void);
+void rcar_console_runtime_init(void);
+void rcar_console_runtime_end(void);
+
+#endif /* RCAR_PRIVATE_H */
diff --git a/plat/renesas/common/include/rcar_version.h b/plat/renesas/common/include/rcar_version.h
new file mode 100644
index 0000000..173111d
--- /dev/null
+++ b/plat/renesas/common/include/rcar_version.h
@@ -0,0 +1,17 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RCAR_VERSION_H
+#define RCAR_VERSION_H
+
+#include <arch_helpers.h>
+
+#define VERSION_OF_RENESAS		"3.0.0"
+#define VERSION_OF_RENESAS_MAXLEN	128
+
+extern const uint8_t version_of_renesas[VERSION_OF_RENESAS_MAXLEN];
+
+#endif /* RCAR_VERSION_H */
diff --git a/plat/renesas/rcar/include/registers/axi_registers.h b/plat/renesas/common/include/registers/axi_registers.h
similarity index 100%
rename from plat/renesas/rcar/include/registers/axi_registers.h
rename to plat/renesas/common/include/registers/axi_registers.h
diff --git a/plat/renesas/common/include/registers/cpg_registers.h b/plat/renesas/common/include/registers/cpg_registers.h
new file mode 100644
index 0000000..5d2bb9e
--- /dev/null
+++ b/plat/renesas/common/include/registers/cpg_registers.h
@@ -0,0 +1,142 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef CPG_REGISTERS_H
+#define CPG_REGISTERS_H
+
+/* CPG base address */
+#define	CPG_BASE	(0xE6150000U)
+
+/* CPG system module stop control 2 */
+#define CPG_SMSTPCR2	(CPG_BASE + 0x0138U)
+/* CPG software reset 2 */
+#define CPG_SRCR2	(CPG_BASE + 0x00B0U)
+/* CPG module stop status 2 */
+#define CPG_MSTPSR2	(CPG_BASE + 0x0040U)
+/* CPG module stop status 2 */
+#define CPG_MSTPSR3	(CPG_BASE + 0x0048U)
+/* CPG write protect */
+#define CPG_CPGWPR	(CPG_BASE + 0x0900U)
+/* CPG write protect control */
+#define CPG_CPGWPCR	(CPG_BASE + 0x0904U)
+/* CPG system module stop control 9 */
+#define CPG_SMSTPCR9    (CPG_BASE + 0x0994U)
+/* CPG module stop status 9 */
+#define CPG_MSTPSR9     (CPG_BASE + 0x09A4U)
+/* SDHI2 clock frequency control register */
+#define	CPG_SD2CKCR	(CPG_BASE + 0x0268U)
+/* SDHI3 clock frequency control register */
+#define CPG_SD3CKCR	(CPG_BASE + 0x026CU)
+
+/* CPG (SECURITY) registers */
+
+/* Secure Module Stop Control Register 0 */
+#define	SCMSTPCR0	(CPG_BASE + 0x0B20U)
+/* Secure Module Stop Control Register 1 */
+#define	SCMSTPCR1	(CPG_BASE + 0x0B24U)
+/* Secure Module Stop Control Register 2 */
+#define	SCMSTPCR2	(CPG_BASE + 0x0B28U)
+/* Secure Module Stop Control Register 3 */
+#define	SCMSTPCR3	(CPG_BASE + 0x0B2CU)
+/* Secure Module Stop Control Register 4 */
+#define	SCMSTPCR4	(CPG_BASE + 0x0B30U)
+/* Secure Module Stop Control Register 5 */
+#define	SCMSTPCR5	(CPG_BASE + 0x0B34U)
+/* Secure Module Stop Control Register 6 */
+#define	SCMSTPCR6	(CPG_BASE + 0x0B38U)
+/* Secure Module Stop Control Register 7 */
+#define	SCMSTPCR7	(CPG_BASE + 0x0B3CU)
+/* Secure Module Stop Control Register 8 */
+#define	SCMSTPCR8	(CPG_BASE + 0x0B40U)
+/* Secure Module Stop Control Register 9 */
+#define	SCMSTPCR9	(CPG_BASE + 0x0B44U)
+/* Secure Module Stop Control Register 10 */
+#define	SCMSTPCR10	(CPG_BASE + 0x0B48U)
+/* Secure Module Stop Control Register 11 */
+#define	SCMSTPCR11	(CPG_BASE + 0x0B4CU)
+
+/* CPG (SECURITY) registers */
+
+/* Secure Software Reset Access Enable Control Register 0 */
+#define	SCSRSTECR0	(CPG_BASE + 0x0B80U)
+/* Secure Software Reset Access Enable Control Register 1 */
+#define	SCSRSTECR1	(CPG_BASE + 0x0B84U)
+/* Secure Software Reset Access Enable Control Register 2 */
+#define	SCSRSTECR2	(CPG_BASE + 0x0B88U)
+/* Secure Software Reset Access Enable Control Register 3 */
+#define	SCSRSTECR3	(CPG_BASE + 0x0B8CU)
+/* Secure Software Reset Access Enable Control Register 4 */
+#define	SCSRSTECR4	(CPG_BASE + 0x0B90U)
+/* Secure Software Reset Access Enable Control Register 5 */
+#define	SCSRSTECR5	(CPG_BASE + 0x0B94U)
+/* Secure Software Reset Access Enable Control Register 6 */
+#define	SCSRSTECR6	(CPG_BASE + 0x0B98U)
+/* Secure Software Reset Access Enable Control Register 7 */
+#define	SCSRSTECR7	(CPG_BASE + 0x0B9CU)
+/* Secure Software Reset Access Enable Control Register 8 */
+#define	SCSRSTECR8	(CPG_BASE + 0x0BA0U)
+/* Secure Software Reset Access Enable Control Register 9 */
+#define	SCSRSTECR9	(CPG_BASE + 0x0BA4U)
+/* Secure Software Reset Access Enable Control Register 10 */
+#define	SCSRSTECR10	(CPG_BASE + 0x0BA8U)
+/* Secure Software Reset Access Enable Control Register 11 */
+#define	SCSRSTECR11	(CPG_BASE + 0x0BACU)
+
+/* CPG (REALTIME) registers */
+
+/* Realtime Module Stop Control Register 0 */
+#define	RMSTPCR0	(CPG_BASE + 0x0110U)
+/* Realtime Module Stop Control Register 1 */
+#define	RMSTPCR1	(CPG_BASE + 0x0114U)
+/* Realtime Module Stop Control Register 2 */
+#define	RMSTPCR2	(CPG_BASE + 0x0118U)
+/* Realtime Module Stop Control Register 3 */
+#define	RMSTPCR3	(CPG_BASE + 0x011CU)
+/* Realtime Module Stop Control Register 4 */
+#define	RMSTPCR4	(CPG_BASE + 0x0120U)
+/* Realtime Module Stop Control Register 5 */
+#define	RMSTPCR5	(CPG_BASE + 0x0124U)
+/* Realtime Module Stop Control Register 6 */
+#define	RMSTPCR6	(CPG_BASE + 0x0128U)
+/* Realtime Module Stop Control Register 7 */
+#define	RMSTPCR7	(CPG_BASE + 0x012CU)
+/* Realtime Module Stop Control Register 8 */
+#define	RMSTPCR8	(CPG_BASE + 0x0980U)
+/* Realtime Module Stop Control Register 9 */
+#define	RMSTPCR9	(CPG_BASE + 0x0984U)
+/* Realtime Module Stop Control Register 10 */
+#define	RMSTPCR10	(CPG_BASE + 0x0988U)
+/* Realtime Module Stop Control Register 11 */
+#define	RMSTPCR11	(CPG_BASE + 0x098CU)
+
+/* CPG (SYSTEM) registers */
+
+/* System Module Stop Control Register 0 */
+#define	SMSTPCR0	(CPG_BASE + 0x0130U)
+/* System Module Stop Control Register 1 */
+#define	SMSTPCR1	(CPG_BASE + 0x0134U)
+/* System Module Stop Control Register 2 */
+#define	SMSTPCR2	(CPG_BASE + 0x0138U)
+/* System Module Stop Control Register 3 */
+#define	SMSTPCR3	(CPG_BASE + 0x013CU)
+/* System Module Stop Control Register 4 */
+#define	SMSTPCR4	(CPG_BASE + 0x0140U)
+/* System Module Stop Control Register 5 */
+#define	SMSTPCR5	(CPG_BASE + 0x0144U)
+/* System Module Stop Control Register 6 */
+#define	SMSTPCR6	(CPG_BASE + 0x0148U)
+/* System Module Stop Control Register 7 */
+#define	SMSTPCR7	(CPG_BASE + 0x014CU)
+/* System Module Stop Control Register 8 */
+#define	SMSTPCR8	(CPG_BASE + 0x0990U)
+/* System Module Stop Control Register 9 */
+#define	SMSTPCR9	(CPG_BASE + 0x0994U)
+/* System Module Stop Control Register 10 */
+#define	SMSTPCR10	(CPG_BASE + 0x0998U)
+/* System Module Stop Control Register 11 */
+#define	SMSTPCR11	(CPG_BASE + 0x099CU)
+
+#endif /* CPG_REGISTERS_H */
diff --git a/plat/renesas/common/include/registers/lifec_registers.h b/plat/renesas/common/include/registers/lifec_registers.h
new file mode 100644
index 0000000..5f49e52
--- /dev/null
+++ b/plat/renesas/common/include/registers/lifec_registers.h
@@ -0,0 +1,144 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef LIFEC_REGISTERS_H
+#define LIFEC_REGISTERS_H
+
+#define LIFEC_SEC_BASE	(0xE6110000U)
+
+#define SEC_SRC		(LIFEC_SEC_BASE + 0x0008U)
+#define SEC_SEL0	(LIFEC_SEC_BASE + 0x0030U)
+#define SEC_SEL1	(LIFEC_SEC_BASE + 0x0034U)
+#define SEC_SEL2	(LIFEC_SEC_BASE + 0x0038U)
+#define SEC_SEL3	(LIFEC_SEC_BASE + 0x003CU)
+#define SEC_SEL4	(LIFEC_SEC_BASE + 0x0058U)
+#define SEC_SEL5	(LIFEC_SEC_BASE + 0x005CU)
+#define SEC_SEL6	(LIFEC_SEC_BASE + 0x0060U)
+#define SEC_SEL7	(LIFEC_SEC_BASE + 0x0064U)
+#define SEC_SEL8	(LIFEC_SEC_BASE + 0x0068U)
+#define SEC_SEL9	(LIFEC_SEC_BASE + 0x006CU)
+#define SEC_SEL10	(LIFEC_SEC_BASE + 0x0070U)
+#define SEC_SEL11	(LIFEC_SEC_BASE + 0x0074U)
+#define SEC_SEL12	(LIFEC_SEC_BASE + 0x0078U)
+#define SEC_SEL13	(LIFEC_SEC_BASE + 0x007CU)
+#define SEC_SEL14	(LIFEC_SEC_BASE + 0x0080U)
+#define SEC_SEL15	(LIFEC_SEC_BASE + 0x0084U)
+#define SEC_GRP0CR0	(LIFEC_SEC_BASE + 0x0138U)
+#define SEC_GRP1CR0	(LIFEC_SEC_BASE + 0x013CU)
+#define SEC_GRP0CR1	(LIFEC_SEC_BASE + 0x0140U)
+#define SEC_GRP1CR1	(LIFEC_SEC_BASE + 0x0144U)
+#define SEC_GRP0CR2	(LIFEC_SEC_BASE + 0x0148U)
+#define SEC_GRP1CR2	(LIFEC_SEC_BASE + 0x014CU)
+#define SEC_GRP0CR3	(LIFEC_SEC_BASE + 0x0150U)
+#define SEC_GRP1CR3	(LIFEC_SEC_BASE + 0x0154U)
+#define SEC_GRP0COND0	(LIFEC_SEC_BASE + 0x0158U)
+#define SEC_GRP1COND0	(LIFEC_SEC_BASE + 0x015CU)
+#define SEC_GRP0COND1	(LIFEC_SEC_BASE + 0x0160U)
+#define SEC_GRP1COND1	(LIFEC_SEC_BASE + 0x0164U)
+#define SEC_GRP0COND2	(LIFEC_SEC_BASE + 0x0168U)
+#define SEC_GRP1COND2	(LIFEC_SEC_BASE + 0x016CU)
+#define SEC_GRP0COND3	(LIFEC_SEC_BASE + 0x0170U)
+#define SEC_GRP1COND3	(LIFEC_SEC_BASE + 0x0174U)
+#define SEC_GRP0COND4	(LIFEC_SEC_BASE + 0x0178U)
+#define SEC_GRP1COND4	(LIFEC_SEC_BASE + 0x017CU)
+#define SEC_GRP0COND5	(LIFEC_SEC_BASE + 0x0180U)
+#define SEC_GRP1COND5	(LIFEC_SEC_BASE + 0x0184U)
+#define SEC_GRP0COND6	(LIFEC_SEC_BASE + 0x0188U)
+#define SEC_GRP1COND6	(LIFEC_SEC_BASE + 0x018CU)
+#define SEC_GRP0COND7	(LIFEC_SEC_BASE + 0x0190U)
+#define SEC_GRP1COND7	(LIFEC_SEC_BASE + 0x0194U)
+#define SEC_GRP0COND8	(LIFEC_SEC_BASE + 0x0198U)
+#define SEC_GRP1COND8	(LIFEC_SEC_BASE + 0x019CU)
+#define SEC_GRP0COND9	(LIFEC_SEC_BASE + 0x01A0U)
+#define SEC_GRP1COND9	(LIFEC_SEC_BASE + 0x01A4U)
+#define SEC_GRP0COND10	(LIFEC_SEC_BASE + 0x01A8U)
+#define SEC_GRP1COND10	(LIFEC_SEC_BASE + 0x01ACU)
+#define SEC_GRP0COND11	(LIFEC_SEC_BASE + 0x01B0U)
+#define SEC_GRP1COND11	(LIFEC_SEC_BASE + 0x01B4U)
+#define SEC_GRP0COND12	(LIFEC_SEC_BASE + 0x01B8U)
+#define SEC_GRP1COND12	(LIFEC_SEC_BASE + 0x01BCU)
+#define SEC_GRP0COND13	(LIFEC_SEC_BASE + 0x01C0U)
+#define SEC_GRP1COND13	(LIFEC_SEC_BASE + 0x01C4U)
+#define SEC_GRP0COND14	(LIFEC_SEC_BASE + 0x01C8U)
+#define SEC_GRP1COND14	(LIFEC_SEC_BASE + 0x01CCU)
+#define SEC_GRP0COND15	(LIFEC_SEC_BASE + 0x01D0U)
+#define SEC_GRP1COND15	(LIFEC_SEC_BASE + 0x01D4U)
+#define SEC_READONLY0	(LIFEC_SEC_BASE + 0x01D8U)
+#define SEC_READONLY1	(LIFEC_SEC_BASE + 0x01DCU)
+#define SEC_READONLY2	(LIFEC_SEC_BASE + 0x01E0U)
+#define SEC_READONLY3	(LIFEC_SEC_BASE + 0x01E4U)
+#define SEC_READONLY4	(LIFEC_SEC_BASE + 0x01E8U)
+#define SEC_READONLY5	(LIFEC_SEC_BASE + 0x01ECU)
+#define SEC_READONLY6	(LIFEC_SEC_BASE + 0x01F0U)
+#define SEC_READONLY7	(LIFEC_SEC_BASE + 0x01F4U)
+#define SEC_READONLY8	(LIFEC_SEC_BASE + 0x01F8U)
+#define SEC_READONLY9	(LIFEC_SEC_BASE + 0x01FCU)
+#define SEC_READONLY10	(LIFEC_SEC_BASE + 0x0200U)
+#define SEC_READONLY11	(LIFEC_SEC_BASE + 0x0204U)
+#define SEC_READONLY12	(LIFEC_SEC_BASE + 0x0208U)
+#define SEC_READONLY13	(LIFEC_SEC_BASE + 0x020CU)
+#define SEC_READONLY14	(LIFEC_SEC_BASE + 0x0210U)
+#define SEC_READONLY15	(LIFEC_SEC_BASE + 0x0214U)
+
+#define LIFEC_SAFE_BASE	(0xE6120000U)
+#define SAFE_GRP0CR0	(LIFEC_SAFE_BASE + 0x0138U)
+#define SAFE_GRP1CR0	(LIFEC_SAFE_BASE + 0x013CU)
+#define SAFE_GRP0CR1	(LIFEC_SAFE_BASE + 0x0140U)
+#define SAFE_GRP1CR1	(LIFEC_SAFE_BASE + 0x0144U)
+#define SAFE_GRP0CR2	(LIFEC_SAFE_BASE + 0x0148U)
+#define SAFE_GRP1CR2	(LIFEC_SAFE_BASE + 0x014CU)
+#define SAFE_GRP0CR3	(LIFEC_SAFE_BASE + 0x0150U)
+#define SAFE_GRP1CR3	(LIFEC_SAFE_BASE + 0x0154U)
+#define SAFE_GRP0COND0	(LIFEC_SAFE_BASE + 0x0158U)
+#define SAFE_GRP1COND0	(LIFEC_SAFE_BASE + 0x015CU)
+#define SAFE_GRP0COND1	(LIFEC_SAFE_BASE + 0x0160U)
+#define SAFE_GRP1COND1	(LIFEC_SAFE_BASE + 0x0164U)
+#define SAFE_GRP0COND2	(LIFEC_SAFE_BASE + 0x0168U)
+#define SAFE_GRP1COND2	(LIFEC_SAFE_BASE + 0x016CU)
+#define SAFE_GRP0COND3	(LIFEC_SAFE_BASE + 0x0170U)
+#define SAFE_GRP1COND3	(LIFEC_SAFE_BASE + 0x0174U)
+#define SAFE_GRP0COND4	(LIFEC_SAFE_BASE + 0x0178U)
+#define SAFE_GRP1COND4	(LIFEC_SAFE_BASE + 0x017CU)
+#define SAFE_GRP0COND5	(LIFEC_SAFE_BASE + 0x0180U)
+#define SAFE_GRP1COND5	(LIFEC_SAFE_BASE + 0x0184U)
+#define SAFE_GRP0COND6	(LIFEC_SAFE_BASE + 0x0188U)
+#define SAFE_GRP1COND6	(LIFEC_SAFE_BASE + 0x018CU)
+#define SAFE_GRP0COND7	(LIFEC_SAFE_BASE + 0x0190U)
+#define SAFE_GRP1COND7	(LIFEC_SAFE_BASE + 0x0194U)
+#define SAFE_GRP0COND8	(LIFEC_SAFE_BASE + 0x0198U)
+#define SAFE_GRP1COND8	(LIFEC_SAFE_BASE + 0x019CU)
+#define SAFE_GRP0COND9	(LIFEC_SAFE_BASE + 0x01A0U)
+#define SAFE_GRP1COND9	(LIFEC_SAFE_BASE + 0x01A4U)
+#define SAFE_GRP0COND10	(LIFEC_SAFE_BASE + 0x01A8U)
+#define SAFE_GRP1COND10	(LIFEC_SAFE_BASE + 0x01ACU)
+#define SAFE_GRP0COND11	(LIFEC_SAFE_BASE + 0x01B0U)
+#define SAFE_GRP1COND11	(LIFEC_SAFE_BASE + 0x01B4U)
+#define SAFE_GRP0COND12	(LIFEC_SAFE_BASE + 0x01B8U)
+#define SAFE_GRP1COND12	(LIFEC_SAFE_BASE + 0x01BCU)
+#define SAFE_GRP0COND13	(LIFEC_SAFE_BASE + 0x01C0U)
+#define SAFE_GRP1COND13	(LIFEC_SAFE_BASE + 0x01C4U)
+#define SAFE_GRP0COND14	(LIFEC_SAFE_BASE + 0x01C8U)
+#define SAFE_GRP1COND14	(LIFEC_SAFE_BASE + 0x01CCU)
+#define SAFE_GRP0COND15	(LIFEC_SAFE_BASE + 0x01D0U)
+#define SAFE_GRP1COND15	(LIFEC_SAFE_BASE + 0x01D4U)
+#define SAFE_READONLY0	(LIFEC_SAFE_BASE + 0x01D8U)
+#define SAFE_READONLY1	(LIFEC_SAFE_BASE + 0x01DCU)
+#define SAFE_READONLY2	(LIFEC_SAFE_BASE + 0x01E0U)
+#define SAFE_READONLY3	(LIFEC_SAFE_BASE + 0x01E4U)
+#define SAFE_READONLY4	(LIFEC_SAFE_BASE + 0x01E8U)
+#define SAFE_READONLY5	(LIFEC_SAFE_BASE + 0x01ECU)
+#define SAFE_READONLY6	(LIFEC_SAFE_BASE + 0x01F0U)
+#define SAFE_READONLY7	(LIFEC_SAFE_BASE + 0x01F4U)
+#define SAFE_READONLY8	(LIFEC_SAFE_BASE + 0x01F8U)
+#define SAFE_READONLY9	(LIFEC_SAFE_BASE + 0x01FCU)
+#define SAFE_READONLY10	(LIFEC_SAFE_BASE + 0x0200U)
+#define SAFE_READONLY11	(LIFEC_SAFE_BASE + 0x0204U)
+#define SAFE_READONLY12	(LIFEC_SAFE_BASE + 0x0208U)
+#define SAFE_READONLY13	(LIFEC_SAFE_BASE + 0x020CU)
+#define SAFE_READONLY14	(LIFEC_SAFE_BASE + 0x0210U)
+#define SAFE_READONLY15	(LIFEC_SAFE_BASE + 0x0214U)
+
+#endif /* LIFEC_REGISTERS_H */
diff --git a/plat/renesas/rcar/plat_image_load.c b/plat/renesas/common/plat_image_load.c
similarity index 100%
rename from plat/renesas/rcar/plat_image_load.c
rename to plat/renesas/common/plat_image_load.c
diff --git a/plat/renesas/common/plat_pm.c b/plat/renesas/common/plat_pm.c
new file mode 100644
index 0000000..1d4a7f6
--- /dev/null
+++ b/plat/renesas/common/plat_pm.c
@@ -0,0 +1,318 @@
+/*
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+
+#include <arch_helpers.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <drivers/arm/cci.h>
+#include <drivers/arm/gicv2.h>
+#include <lib/bakery_lock.h>
+#include <lib/mmio.h>
+#include <lib/psci/psci.h>
+#include <plat/common/platform.h>
+
+#include "iic_dvfs.h"
+#include "platform_def.h"
+#include "pwrc.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+#if RCAR_GEN3_ULCB
+#include "ulcb_cpld.h"
+#endif /* RCAR_GEN3_ULCB */
+
+#define DVFS_SET_VID_0V		(0x00)
+#define P_ALL_OFF		(0x80)
+#define KEEPON_DDR1C		(0x08)
+#define KEEPON_DDR0C		(0x04)
+#define KEEPON_DDR1		(0x02)
+#define KEEPON_DDR0		(0x01)
+
+#define SYSTEM_PWR_STATE(s)	((s)->pwr_domain_state[PLAT_MAX_PWR_LVL])
+#define CLUSTER_PWR_STATE(s)	((s)->pwr_domain_state[MPIDR_AFFLVL1])
+#define CORE_PWR_STATE(s)	((s)->pwr_domain_state[MPIDR_AFFLVL0])
+
+extern void rcar_pwrc_restore_generic_timer(uint64_t *stack);
+extern void plat_rcar_gic_driver_init(void);
+extern void plat_rcar_gic_init(void);
+extern u_register_t rcar_boot_mpidr;
+
+static uintptr_t rcar_sec_entrypoint;
+
+static void rcar_program_mailbox(uint64_t mpidr, uint64_t address)
+{
+	mailbox_t *rcar_mboxes = (mailbox_t *) MBOX_BASE;
+	uint64_t linear_id = plat_core_pos_by_mpidr(mpidr);
+	unsigned long range;
+
+	rcar_mboxes[linear_id].value = address;
+	range = (unsigned long)&rcar_mboxes[linear_id];
+
+	flush_dcache_range(range, sizeof(range));
+}
+
+static void rcar_cpu_standby(plat_local_state_t cpu_state)
+{
+	u_register_t scr_el3 = read_scr_el3();
+
+	write_scr_el3(scr_el3 | SCR_IRQ_BIT);
+	dsb();
+	wfi();
+	write_scr_el3(scr_el3);
+}
+
+static int rcar_pwr_domain_on(u_register_t mpidr)
+{
+	rcar_program_mailbox(mpidr, rcar_sec_entrypoint);
+	rcar_pwrc_cpuon(mpidr);
+
+	return PSCI_E_SUCCESS;
+}
+
+static void rcar_pwr_domain_on_finish(const psci_power_state_t *target_state)
+{
+	uint32_t cluster_type = rcar_pwrc_get_cluster();
+	unsigned long mpidr = read_mpidr_el1();
+
+	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE)
+		if (cluster_type == RCAR_CLUSTER_A53A57)
+			plat_cci_enable();
+
+	rcar_pwrc_disable_interrupt_wakeup(mpidr);
+	rcar_program_mailbox(mpidr, 0);
+
+	gicv2_cpuif_enable();
+	gicv2_pcpu_distif_init();
+}
+
+static void rcar_pwr_domain_off(const psci_power_state_t *target_state)
+{
+#if RCAR_LSI != RCAR_D3
+	uint32_t cluster_type = rcar_pwrc_get_cluster();
+#endif
+	unsigned long mpidr = read_mpidr_el1();
+
+	gicv2_cpuif_disable();
+	rcar_pwrc_cpuoff(mpidr);
+
+#if RCAR_LSI != RCAR_D3
+	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE) {
+		if (cluster_type == RCAR_CLUSTER_A53A57)
+			plat_cci_disable();
+
+		rcar_pwrc_clusteroff(mpidr);
+	}
+#endif
+}
+
+static void rcar_pwr_domain_suspend(const psci_power_state_t *target_state)
+{
+	uint32_t cluster_type = rcar_pwrc_get_cluster();
+	unsigned long mpidr = read_mpidr_el1();
+
+	if (CORE_PWR_STATE(target_state) != PLAT_MAX_OFF_STATE)
+		return;
+
+	rcar_program_mailbox(mpidr, rcar_sec_entrypoint);
+	rcar_pwrc_enable_interrupt_wakeup(mpidr);
+	gicv2_cpuif_disable();
+	rcar_pwrc_cpuoff(mpidr);
+
+	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE) {
+		if (cluster_type == RCAR_CLUSTER_A53A57)
+			plat_cci_disable();
+
+		rcar_pwrc_clusteroff(mpidr);
+	}
+}
+
+static void rcar_pwr_domain_suspend_finish(const psci_power_state_t
+					   *target_state)
+{
+	uint32_t cluster_type = rcar_pwrc_get_cluster();
+
+	if (SYSTEM_PWR_STATE(target_state) != PLAT_MAX_OFF_STATE)
+		goto finish;
+
+	plat_rcar_gic_driver_init();
+	plat_rcar_gic_init();
+
+	if (cluster_type == RCAR_CLUSTER_A53A57)
+		plat_cci_init();
+
+	rcar_pwrc_restore_timer_state();
+	rcar_pwrc_setup();
+	rcar_pwrc_code_copy_to_system_ram();
+
+#if RCAR_SYSTEM_SUSPEND
+	rcar_pwrc_init_suspend_to_ram();
+#endif
+finish:
+	rcar_pwr_domain_on_finish(target_state);
+}
+
+static void __dead2 rcar_pwr_domain_pwr_down_wfi(const psci_power_state_t *target_state)
+{
+#if RCAR_SYSTEM_SUSPEND
+	if (SYSTEM_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE)
+		rcar_pwrc_suspend_to_ram();
+#endif
+	wfi();
+
+	ERROR("RCAR Power Down: operation not handled.\n");
+	panic();
+}
+
+static void __dead2 rcar_system_off(void)
+{
+#if PMIC_ROHM_BD9571
+#if PMIC_LEVEL_MODE
+	if (rcar_iic_dvfs_send(PMIC, DVFS_SET_VID, DVFS_SET_VID_0V))
+		ERROR("BL3-1:Failed the SYSTEM-OFF.\n");
+#else
+	if (rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, P_ALL_OFF))
+		ERROR("BL3-1:Failed the SYSTEM-RESET.\n");
+#endif
+#else
+	uint64_t cpu = read_mpidr_el1() & 0x0000ffff;
+	int32_t rtn_on;
+
+	rtn_on = rcar_pwrc_cpu_on_check(cpu);
+
+	if (cpu == rcar_boot_mpidr)
+		panic();
+
+	if (rtn_on)
+		panic();
+
+	rcar_pwrc_cpuoff(cpu);
+	rcar_pwrc_clusteroff(cpu);
+
+#endif /* PMIC_ROHM_BD9571 */
+	wfi();
+	ERROR("RCAR System Off: operation not handled.\n");
+	panic();
+}
+
+static void __dead2 rcar_system_reset(void)
+{
+#if PMIC_ROHM_BD9571
+#if PMIC_LEVEL_MODE
+#if RCAR_SYSTEM_RESET_KEEPON_DDR
+	uint8_t mode;
+	int32_t error;
+
+	error = rcar_iic_dvfs_send(PMIC, REG_KEEP10, KEEP10_MAGIC);
+	if (error) {
+		ERROR("Failed send KEEP10 magic ret=%d\n", error);
+		goto done;
+	}
+
+	error = rcar_iic_dvfs_receive(PMIC, BKUP_MODE_CNT, &mode);
+	if (error) {
+		ERROR("Failed receive BKUP_Mode_Cnt ret=%d\n", error);
+		goto done;
+	}
+
+	mode |= KEEPON_DDR1C | KEEPON_DDR0C | KEEPON_DDR1 | KEEPON_DDR0;
+	error = rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, mode);
+	if (error) {
+		ERROR("Failed send KEEPON_DDRx ret=%d\n", error);
+		goto done;
+	}
+
+	rcar_pwrc_set_suspend_to_ram();
+done:
+#else
+	if (rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, P_ALL_OFF))
+		ERROR("BL3-1:Failed the SYSTEM-RESET.\n");
+#endif
+#else
+#if (RCAR_GEN3_ULCB == 1)
+	rcar_cpld_reset_cpu();
+#endif
+#endif
+#else
+	rcar_pwrc_system_reset();
+#endif
+	wfi();
+
+	ERROR("RCAR System Reset: operation not handled.\n");
+	panic();
+}
+
+static int rcar_validate_power_state(unsigned int power_state,
+				    psci_power_state_t *req_state)
+{
+	unsigned int pwr_lvl = psci_get_pstate_pwrlvl(power_state);
+	unsigned int pstate = psci_get_pstate_type(power_state);
+	uint32_t i;
+
+	if (pstate == PSTATE_TYPE_STANDBY) {
+		if (pwr_lvl != MPIDR_AFFLVL0)
+			return PSCI_E_INVALID_PARAMS;
+
+		req_state->pwr_domain_state[MPIDR_AFFLVL0] = PLAT_MAX_RET_STATE;
+	} else {
+		for (i = MPIDR_AFFLVL0; i <= pwr_lvl; i++)
+			req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
+	}
+
+	if (psci_get_pstate_id(power_state))
+		return PSCI_E_INVALID_PARAMS;
+
+	return PSCI_E_SUCCESS;
+}
+
+#if RCAR_SYSTEM_SUSPEND
+static void rcar_get_sys_suspend_power_state(psci_power_state_t *req_state)
+{
+	unsigned long mpidr = read_mpidr_el1() & 0x0000ffffU;
+	int i;
+
+	if (mpidr != rcar_boot_mpidr)
+		goto deny;
+
+	for (i = MPIDR_AFFLVL0; i <= PLAT_MAX_PWR_LVL; i++)
+		req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
+
+	return;
+deny:
+	/* deny system suspend entry */
+	req_state->pwr_domain_state[PLAT_MAX_PWR_LVL] = PSCI_LOCAL_STATE_RUN;
+	for (i = MPIDR_AFFLVL0; i < PLAT_MAX_PWR_LVL; i++)
+		req_state->pwr_domain_state[i] = PLAT_MAX_RET_STATE;
+}
+#endif
+
+static const plat_psci_ops_t rcar_plat_psci_ops = {
+	.cpu_standby			= rcar_cpu_standby,
+	.pwr_domain_on			= rcar_pwr_domain_on,
+	.pwr_domain_off			= rcar_pwr_domain_off,
+	.pwr_domain_suspend		= rcar_pwr_domain_suspend,
+	.pwr_domain_on_finish		= rcar_pwr_domain_on_finish,
+	.pwr_domain_suspend_finish	= rcar_pwr_domain_suspend_finish,
+	.system_off			= rcar_system_off,
+	.system_reset			= rcar_system_reset,
+	.validate_power_state		= rcar_validate_power_state,
+	.pwr_domain_pwr_down_wfi	= rcar_pwr_domain_pwr_down_wfi,
+#if RCAR_SYSTEM_SUSPEND
+	.get_sys_suspend_power_state	= rcar_get_sys_suspend_power_state,
+#endif
+};
+
+int plat_setup_psci_ops(uintptr_t sec_entrypoint, const plat_psci_ops_t **psci_ops)
+{
+	*psci_ops = &rcar_plat_psci_ops;
+	rcar_sec_entrypoint = sec_entrypoint;
+
+#if RCAR_SYSTEM_SUSPEND
+	rcar_pwrc_init_suspend_to_ram();
+#endif
+	return 0;
+}
+
diff --git a/plat/renesas/common/plat_storage.c b/plat/renesas/common/plat_storage.c
new file mode 100644
index 0000000..6524561
--- /dev/null
+++ b/plat/renesas/common/plat_storage.c
@@ -0,0 +1,417 @@
+/*
+ * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_storage.h>
+#include <drivers/io/io_semihosting.h>
+
+#include "io_common.h"
+#include "io_memdrv.h"
+#include "io_emmcdrv.h"
+#include "io_private.h"
+#include "io_rcar.h"
+#include <platform_def.h>
+
+static uintptr_t emmcdrv_dev_handle;
+static uintptr_t memdrv_dev_handle;
+static uintptr_t rcar_dev_handle;
+
+static uintptr_t boot_io_drv_id;
+
+static const io_block_spec_t rcar_block_spec = {
+	.offset = FLASH0_BASE,
+	.length = FLASH0_SIZE
+};
+
+static const io_block_spec_t bl2_file_spec = {
+	.offset = BL2_IMAGE_ID,
+};
+
+static const io_block_spec_t bl31_file_spec = {
+	.offset = BL31_IMAGE_ID,
+};
+
+static const io_block_spec_t bl32_file_spec = {
+	.offset = BL32_IMAGE_ID,
+};
+
+static const io_block_spec_t bl33_file_spec = {
+	.offset = BL33_IMAGE_ID,
+};
+
+static const io_block_spec_t bl332_file_spec = {
+	.offset = BL332_IMAGE_ID,
+};
+
+static const io_block_spec_t bl333_file_spec = {
+	.offset = BL333_IMAGE_ID,
+};
+
+static const io_block_spec_t bl334_file_spec = {
+	.offset = BL334_IMAGE_ID,
+};
+
+static const io_block_spec_t bl335_file_spec = {
+	.offset = BL335_IMAGE_ID,
+};
+
+static const io_block_spec_t bl336_file_spec = {
+	.offset = BL336_IMAGE_ID,
+};
+
+static const io_block_spec_t bl337_file_spec = {
+	.offset = BL337_IMAGE_ID,
+};
+
+static const io_block_spec_t bl338_file_spec = {
+	.offset = BL338_IMAGE_ID,
+};
+
+#if TRUSTED_BOARD_BOOT
+static const io_block_spec_t trusted_key_cert_file_spec = {
+	.offset = TRUSTED_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl31_key_cert_file_spec = {
+	.offset = SOC_FW_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl32_key_cert_file_spec = {
+	.offset = TRUSTED_OS_FW_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl33_key_cert_file_spec = {
+	.offset = NON_TRUSTED_FW_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl332_key_cert_file_spec = {
+	.offset = BL332_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl333_key_cert_file_spec = {
+	.offset = BL333_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl334_key_cert_file_spec = {
+	.offset = BL334_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl335_key_cert_file_spec = {
+	.offset = BL335_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl336_key_cert_file_spec = {
+	.offset = BL336_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl337_key_cert_file_spec = {
+	.offset = BL337_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl338_key_cert_file_spec = {
+	.offset = BL338_KEY_CERT_ID,
+};
+
+static const io_block_spec_t bl31_cert_file_spec = {
+	.offset = SOC_FW_CONTENT_CERT_ID,
+};
+
+static const io_block_spec_t bl32_cert_file_spec = {
+	.offset = TRUSTED_OS_FW_CONTENT_CERT_ID,
+};
+
+static const io_block_spec_t bl33_cert_file_spec = {
+	.offset = NON_TRUSTED_FW_CONTENT_CERT_ID,
+};
+
+static const io_block_spec_t bl332_cert_file_spec = {
+	.offset = BL332_CERT_ID,
+};
+
+static const io_block_spec_t bl333_cert_file_spec = {
+	.offset = BL333_CERT_ID,
+};
+
+static const io_block_spec_t bl334_cert_file_spec = {
+	.offset = BL334_CERT_ID,
+};
+
+static const io_block_spec_t bl335_cert_file_spec = {
+	.offset = BL335_CERT_ID,
+};
+
+static const io_block_spec_t bl336_cert_file_spec = {
+	.offset = BL336_CERT_ID,
+};
+
+static const io_block_spec_t bl337_cert_file_spec = {
+	.offset = BL337_CERT_ID,
+};
+
+static const io_block_spec_t bl338_cert_file_spec = {
+	.offset = BL338_CERT_ID,
+};
+#endif
+
+static int32_t open_emmcdrv(const uintptr_t spec);
+static int32_t open_memmap(const uintptr_t spec);
+static int32_t open_rcar(const uintptr_t spec);
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int32_t (*check)(const uintptr_t spec);
+};
+
+static const struct plat_io_policy policies[] = {
+	[FIP_IMAGE_ID] = {
+			  &memdrv_dev_handle,
+			  (uintptr_t) &rcar_block_spec,
+			  &open_memmap},
+	[BL2_IMAGE_ID] = {
+			  &rcar_dev_handle,
+			  (uintptr_t) &bl2_file_spec,
+			  &open_rcar},
+	[BL31_IMAGE_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl31_file_spec,
+			   &open_rcar},
+	[BL32_IMAGE_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl32_file_spec,
+			   &open_rcar},
+	[BL33_IMAGE_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl33_file_spec,
+			   &open_rcar},
+	[BL332_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl332_file_spec,
+			    &open_rcar},
+	[BL333_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl333_file_spec,
+			    &open_rcar},
+	[BL334_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl334_file_spec,
+			    &open_rcar},
+	[BL335_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl335_file_spec,
+			    &open_rcar},
+	[BL336_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl336_file_spec,
+			    &open_rcar},
+	[BL337_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl337_file_spec,
+			    &open_rcar},
+	[BL338_IMAGE_ID] = {
+			    &rcar_dev_handle,
+			    (uintptr_t) &bl338_file_spec,
+			    &open_rcar},
+#if TRUSTED_BOARD_BOOT
+	[TRUSTED_KEY_CERT_ID] = {
+				 &rcar_dev_handle,
+				 (uintptr_t) &trusted_key_cert_file_spec,
+				 &open_rcar},
+	[SOC_FW_KEY_CERT_ID] = {
+				&rcar_dev_handle,
+				(uintptr_t) &bl31_key_cert_file_spec,
+				&open_rcar},
+	[TRUSTED_OS_FW_KEY_CERT_ID] = {
+				       &rcar_dev_handle,
+				       (uintptr_t) &bl32_key_cert_file_spec,
+				       &open_rcar},
+	[NON_TRUSTED_FW_KEY_CERT_ID] = {
+					&rcar_dev_handle,
+					(uintptr_t) &bl33_key_cert_file_spec,
+					&open_rcar},
+	[BL332_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl332_key_cert_file_spec,
+			       &open_rcar},
+	[BL333_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl333_key_cert_file_spec,
+			       &open_rcar},
+	[BL334_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl334_key_cert_file_spec,
+			       &open_rcar},
+	[BL335_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl335_key_cert_file_spec,
+			       &open_rcar},
+	[BL336_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl336_key_cert_file_spec,
+			       &open_rcar},
+	[BL337_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl337_key_cert_file_spec,
+			       &open_rcar},
+	[BL338_KEY_CERT_ID] = {
+			       &rcar_dev_handle,
+			       (uintptr_t) &bl338_key_cert_file_spec,
+			       &open_rcar},
+	[SOC_FW_CONTENT_CERT_ID] = {
+				    &rcar_dev_handle,
+				    (uintptr_t) &bl31_cert_file_spec,
+				    &open_rcar},
+	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
+					   &rcar_dev_handle,
+					   (uintptr_t) &bl32_cert_file_spec,
+					   &open_rcar},
+	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
+					    &rcar_dev_handle,
+					    (uintptr_t) &bl33_cert_file_spec,
+					    &open_rcar},
+	[BL332_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl332_cert_file_spec,
+			   &open_rcar},
+	[BL333_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl333_cert_file_spec,
+			   &open_rcar},
+	[BL334_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl334_cert_file_spec,
+			   &open_rcar},
+	[BL335_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl335_cert_file_spec,
+			   &open_rcar},
+	[BL336_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl336_cert_file_spec,
+			   &open_rcar},
+	[BL337_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl337_cert_file_spec,
+			   &open_rcar},
+	[BL338_CERT_ID] = {
+			   &rcar_dev_handle,
+			   (uintptr_t) &bl338_cert_file_spec,
+			   &open_rcar}, {
+#else
+					{
+#endif
+					 0, 0, 0}
+};
+
+static io_drv_spec_t io_drv_spec_memdrv = {
+	FLASH0_BASE,
+	FLASH0_SIZE,
+	0,
+};
+
+static io_drv_spec_t io_drv_spec_emmcdrv = {
+	0,
+	0,
+	0,
+};
+
+static struct plat_io_policy drv_policies[] __attribute__ ((section(".data"))) = {
+	/* FLASH_DEV_ID */
+	{ &memdrv_dev_handle, (uintptr_t) &io_drv_spec_memdrv, &open_memmap, },
+	/* EMMC_DEV_ID */
+	{ &emmcdrv_dev_handle, (uintptr_t) &io_drv_spec_emmcdrv, &open_emmcdrv, }
+};
+
+static int32_t open_rcar(const uintptr_t spec)
+{
+	return io_dev_init(rcar_dev_handle, boot_io_drv_id);
+}
+
+static int32_t open_memmap(const uintptr_t spec)
+{
+	uintptr_t handle;
+	int32_t result;
+
+	result = io_dev_init(memdrv_dev_handle, 0);
+	if (result != IO_SUCCESS)
+		return result;
+
+	result = io_open(memdrv_dev_handle, spec, &handle);
+	if (result == IO_SUCCESS)
+		io_close(handle);
+
+	return result;
+}
+
+static int32_t open_emmcdrv(const uintptr_t spec)
+{
+	return io_dev_init(emmcdrv_dev_handle, 0);
+}
+
+void rcar_io_setup(void)
+{
+	const io_dev_connector_t *memmap;
+	const io_dev_connector_t *rcar;
+
+	boot_io_drv_id = FLASH_DEV_ID;
+
+	rcar_register_io_dev(&rcar);
+	rcar_register_io_dev_memdrv(&memmap);
+	io_dev_open(rcar, 0, &rcar_dev_handle);
+	io_dev_open(memmap, 0, &memdrv_dev_handle);
+}
+
+void rcar_io_emmc_setup(void)
+{
+	const io_dev_connector_t *rcar;
+	const io_dev_connector_t *emmc;
+
+	boot_io_drv_id = EMMC_DEV_ID;
+
+	rcar_register_io_dev(&rcar);
+	rcar_register_io_dev_emmcdrv(&emmc);
+	io_dev_open(rcar, 0, &rcar_dev_handle);
+	io_dev_open(emmc, 0, &emmcdrv_dev_handle);
+}
+
+int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
+			  uintptr_t *image_spec)
+{
+	const struct plat_io_policy *policy;
+	int result;
+
+	policy = &policies[image_id];
+
+	result = policy->check(policy->image_spec);
+	if (result != IO_SUCCESS)
+		return result;
+
+	*image_spec = policy->image_spec;
+	*dev_handle = *(policy->dev_handle);
+
+	return IO_SUCCESS;
+}
+
+int32_t plat_get_drv_source(uint32_t io_drv_id, uintptr_t *dev_handle,
+			    uintptr_t *image_spec)
+{
+	const struct plat_io_policy *policy;
+	int32_t result;
+
+	policy = &drv_policies[io_drv_id];
+
+	result = policy->check(policy->image_spec);
+	if (result != IO_SUCCESS)
+		return result;
+
+	*image_spec = policy->image_spec;
+	*dev_handle = *(policy->dev_handle);
+
+	return IO_SUCCESS;
+}
diff --git a/plat/renesas/rcar/plat_topology.c b/plat/renesas/common/plat_topology.c
similarity index 100%
rename from plat/renesas/rcar/plat_topology.c
rename to plat/renesas/common/plat_topology.c
diff --git a/plat/renesas/common/rcar_common.c b/plat/renesas/common/rcar_common.c
new file mode 100644
index 0000000..df4c30c
--- /dev/null
+++ b/plat/renesas/common/rcar_common.c
@@ -0,0 +1,99 @@
+/*
+ * Copyright (c) 2019-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <arch_helpers.h>
+#include <drivers/console.h>
+#include <lib/xlat_tables/xlat_mmu_helpers.h>
+#include <plat/common/platform.h>
+
+#include <lib/mmio.h>
+#include <cpg_registers.h>
+
+#define MSTP318			(1 << 18)
+#define MSTP319			(1 << 19)
+#define PMSR			0x5c
+#define PMSR_L1FAEG		(1U << 31)
+#define PMSR_PMEL1RX		(1 << 23)
+#define PMCTLR			0x60
+#define PMSR_L1IATN		(1U << 31)
+
+static int rcar_pcie_fixup(unsigned int controller)
+{
+	uint32_t rcar_pcie_base[] = { 0xfe011000, 0xee811000 };
+	uint32_t addr = rcar_pcie_base[controller];
+	uint32_t cpg, pmsr;
+	int ret = 0;
+
+	/* Test if PCIECx is enabled */
+	cpg = mmio_read_32(CPG_MSTPSR3);
+	if (cpg & (MSTP318 << !controller))
+		return ret;
+
+	pmsr = mmio_read_32(addr + PMSR);
+
+	if ((pmsr & PMSR_PMEL1RX) && ((pmsr & 0x70000) != 0x30000)) {
+		/* Fix applicable */
+		mmio_write_32(addr + PMCTLR, PMSR_L1IATN);
+		while (!(mmio_read_32(addr + PMSR) & PMSR_L1FAEG))
+			;
+		mmio_write_32(addr + PMSR, PMSR_L1FAEG | PMSR_PMEL1RX);
+		ret = 1;
+	}
+
+	return ret;
+}
+
+/* RAS functions common to AArch64 ARM platforms */
+void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
+		void *handle, uint64_t flags)
+{
+	unsigned int fixed = 0;
+
+	fixed |= rcar_pcie_fixup(0);
+	fixed |= rcar_pcie_fixup(1);
+
+	if (fixed)
+		return;
+
+	plat_default_ea_handler(ea_reason, syndrome, cookie, handle, flags);
+}
+
+#include <drivers/renesas/rcar/console/console.h>
+
+static console_t rcar_boot_console;
+static console_t rcar_runtime_console;
+
+void rcar_console_boot_init(void)
+{
+	int ret;
+
+	ret = console_rcar_register(0, 0, 0, &rcar_boot_console);
+	if (!ret)
+		panic();
+
+	console_set_scope(&rcar_boot_console, CONSOLE_FLAG_BOOT);
+}
+
+void rcar_console_boot_end(void)
+{
+}
+
+void rcar_console_runtime_init(void)
+{
+	int ret;
+
+	ret = console_rcar_register(1, 0, 0, &rcar_runtime_console);
+	if (!ret)
+		panic();
+
+	console_set_scope(&rcar_boot_console, CONSOLE_FLAG_RUNTIME);
+}
+
+void rcar_console_runtime_end(void)
+{
+}
diff --git a/plat/renesas/rcar/aarch64/plat_helpers.S b/plat/renesas/rcar/aarch64/plat_helpers.S
deleted file mode 100644
index ec21f25..0000000
--- a/plat/renesas/rcar/aarch64/plat_helpers.S
+++ /dev/null
@@ -1,392 +0,0 @@
-/*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <arch.h>
-#include <asm_macros.S>
-#include <common/bl_common.h>
-#include <common/runtime_svc.h>
-#include <cortex_a57.h>
-#include <platform_def.h>
-
-#include "rcar_def.h"
-
-	.globl	plat_get_my_entrypoint
-	.extern	plat_set_my_stack
-	.globl	platform_mem_init
-
-	.globl	plat_crash_console_init
-	.globl	plat_crash_console_putc
-	.globl	plat_crash_console_flush
-	.globl	plat_invalidate_icache
-	.globl	plat_report_exception
-	.globl	plat_secondary_reset
-	.globl	plat_reset_handler
-	.globl	plat_my_core_pos
-	.extern	rcar_log_init
-
-	.extern console_rcar_init
-	.extern console_rcar_putc
-	.extern console_rcar_flush
-
-#if IMAGE_BL2
-	#define	INT_ID_MASK	(0x3ff)
-	.extern bl2_interrupt_error_type
-	.extern bl2_interrupt_error_id
-	.globl  bl2_enter_bl31
-	.extern gicv2_acknowledge_interrupt
-	.extern rcar_swdt_exec
-#endif
-
-	/* -----------------------------------------------------
-	 * void platform_get_core_pos (mpidr)
-	 * -----------------------------------------------------
-	 */
-func platform_get_core_pos
-	and     x1, x0, #MPIDR_CPU_MASK
-	and     x0, x0, #MPIDR_CLUSTER_MASK
-	add     x0, x1, x0, LSR #6
-	ret
-endfunc platform_get_core_pos
-
-	/* -----------------------------------------------------
-	 * void platform_my_core_pos
-	 * -----------------------------------------------------
-	 */
-func plat_my_core_pos
-	mrs     x0, mpidr_el1
-	b	platform_get_core_pos
-endfunc plat_my_core_pos
-
-	/* -----------------------------------------------------
-	 * void platform_get_my_entrypoint (unsigned int mpid);
-	 *
-	 * Main job of this routine is to distinguish between
-	 * a cold and warm boot.
-	 * On a cold boot the secondaries first wait for the
-	 * platform to be initialized after which they are
-	 * hotplugged in. The primary proceeds to perform the
-	 * platform initialization.
-	 * On a warm boot, each cpu jumps to the address in its
-	 * mailbox.
-	 *
-	 * TODO: Not a good idea to save lr in a temp reg
-	 * -----------------------------------------------------
-	 */
-func plat_get_my_entrypoint
-	mrs	x0, mpidr_el1
-	mov	x9, x30 /* lr */
-
-#if defined(IMAGE_BL2)
-	/* always cold boot on bl2 */
-	mov	x0, #0
-	ret	x9
-#else
-       ldr 	x1, =BOOT_KIND_BASE
-       ldr	x21, [x1]
-
-	/* Check the reset info */
-	and	x1, x21, #0x000c
-	cmp	x1, #0x0008
-	beq	el3_panic
-	cmp	x1, #0x000c
-	beq	el3_panic
-
-	/* Check the boot kind */
-	and	x1, x21, #0x0003
-	cmp	x1, #0x0002
-	beq	el3_panic
-	cmp	x1, #0x0003
-	beq	el3_panic
-
-	/* warm boot or cold boot */
-	and	x1, x21, #1
-	cmp	x1, #0
-	bne	warm_reset
-
-	/* Cold boot */
-	mov	x0, #0
-	b	exit
-
-warm_reset:
-	/* --------------------------------------------------------------------
-	 * A per-cpu mailbox is maintained in the trusted SDRAM. Its flushed out
-	 * of the caches after every update using normal memory so its safe to
-	 * read it here with SO attributes
-	 * ---------------------------------------------------------------------
-	 */
-	ldr	x10, =MBOX_BASE
-	bl	platform_get_core_pos
-	lsl	x0, x0, #CACHE_WRITEBACK_SHIFT
-	ldr	x0, [x10, x0]
-	cbz	x0, _panic
-exit:
-	ret	x9
-_panic:
-	b	do_panic
-#endif
-
-endfunc plat_get_my_entrypoint
-
-	/* ---------------------------------------------
-	 * plat_secondary_reset
-	 *
-	 * ---------------------------------------------
-	 */
-func plat_secondary_reset
-	mrs	x0, sctlr_el3
-	bic	x0, x0, #SCTLR_EE_BIT
-	msr	sctlr_el3, x0
-	isb
-
-	mrs	x0, cptr_el3
-	bic	w0, w0, #TCPAC_BIT
-	bic	w0, w0, #TTA_BIT
-	bic	w0, w0, #TFP_BIT
-	msr	cptr_el3, x0
-
-	mov_imm	x0, PARAMS_BASE
-	mov_imm	x2, BL31_BASE
-       ldr x3, =BOOT_KIND_BASE
-	mov x1, #0x1
-	str x1, [x3]
-	br	x2	/* jump to BL31 */
-	nop
-	nop
-	nop
-endfunc plat_secondary_reset
-
-	/* ---------------------------------------------
-	 * plat_enter_bl31
-	 *
-	 * ---------------------------------------------
-	 */
-func bl2_enter_bl31
-	mov	x20, x0
-        /*
-         * MMU needs to be disabled because both BL2 and BL31 execute
-         * in EL3, and therefore share the same address space.
-         * BL31 will initialize the address space according to its
-         * own requirement.
-         */
-#if RCAR_BL2_DCACHE == 1
-	/* Disable mmu and data cache */
-	bl	disable_mmu_el3
-	/* Data cache clean and invalidate */
-	mov	x0, #DCCISW
-	bl	dcsw_op_all
-	/* TLB invalidate all, EL3 */
-	tlbi	alle3
-#endif /* RCAR_BL2_DCACHE == 1 */
-	bl	disable_mmu_icache_el3
-	/* Invalidate instruction cache */
-	ic	iallu
-	dsb	sy
-	isb
-	ldp	x0, x1, [x20, #ENTRY_POINT_INFO_PC_OFFSET]
-	msr	elr_el3, x0
-	msr	spsr_el3, x1
-	exception_return
-endfunc bl2_enter_bl31
-
-	/* -----------------------------------------------------
-	 * void platform_mem_init (void);
-	 *
-	 * Zero out the mailbox registers in the shared memory
-	 * and set the rcar_boot_kind_flag.
-	 * The mmu is turned off right now and only the primary can
-	 * ever execute this code. Secondaries will read the
-	 * mailboxes using SO accesses.
-	 * -----------------------------------------------------
-	 */
-func platform_mem_init
-#if !IMAGE_BL2
-	ldr	x0, =MBOX_BASE
-	mov	w1, #PLATFORM_CORE_COUNT
-loop:
-	str	xzr, [x0], #CACHE_WRITEBACK_GRANULE
-	subs	w1, w1, #1
-	b.gt	loop
-#endif
-	ret
-endfunc platform_mem_init
-
-	/* ---------------------------------------------
-	 * void plat_report_exception(unsigned int type)
-	 * Function to report an unhandled exception
-	 * with platform-specific means.
-	 * ---------------------------------------------
-	 */
-func plat_report_exception
-	/* Switch to SP_EL0 */
-	msr	spsel, #0
-#if IMAGE_BL2
-	mov	w1, #FIQ_SP_EL0
-	cmp	w0, w1
-	beq	rep_exec_fiq_elx
-	b	rep_exec_panic_type
-rep_exec_fiq_elx:
-	bl	gicv2_acknowledge_interrupt
-	mov	x2, #INT_ID_MASK
-	and	x0, x0, x2
-	mov	x1, #ARM_IRQ_SEC_WDT
-	cmp	x0, x1
-	bne	rep_exec_panic_id
-	mrs	x0, ELR_EL3
-	b	rcar_swdt_exec
-rep_exec_panic_type:
-	/* x0 is interrupt TYPE */
-	b	bl2_interrupt_error_type
-rep_exec_panic_id:
-	/* x0 is interrupt ID */
-	b	bl2_interrupt_error_id
-rep_exec_end:
-#endif
-	ret
-endfunc plat_report_exception
-
-	/* ---------------------------------------------
-	 * int plat_crash_console_init(void)
-	 * Function to initialize log area
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_init
-#if IMAGE_BL2
-	mov	x0, #0
-#else
-	mov	x1, sp
-	mov_imm	x2, RCAR_CRASH_STACK
-	mov	sp, x2
-	str	x1, [sp, #-16]!
-	str	x30, [sp, #-16]!
-	bl	console_rcar_init
-	ldr	x30, [sp], #16
-	ldr	x1, [sp], #16
-	mov	sp, x1
-#endif
-	ret
-endfunc plat_crash_console_init
-
-	/* ---------------------------------------------
-	 * int plat_crash_console_putc(int c)
-	 * Function to store a character to log area
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_putc
-	mov	x1, sp
-	mov_imm	x2, RCAR_CRASH_STACK
-	mov	sp, x2
-	str	x1, [sp, #-16]!
-	str	x30, [sp, #-16]!
-	str	x3, [sp, #-16]!
-	str	x4, [sp, #-16]!
-	str	x5, [sp, #-16]!
-	bl	console_rcar_putc
-	ldr	x5, [sp], #16
-	ldr	x4, [sp], #16
-	ldr	x3, [sp], #16
-	ldr	x30, [sp], #16
-	ldr	x1, [sp], #16
-	mov	sp, x1
-	ret
-endfunc plat_crash_console_putc
-
-	/* ---------------------------------------------
-	 * void plat_crash_console_flush()
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_flush
-	b	console_rcar_flush
-endfunc plat_crash_console_flush
-
-	/* --------------------------------------------------------------------
-	 * void plat_reset_handler(void);
-	 *
-	 * Before adding code in this function, refer to the guidelines in
-	 * docs/firmware-design.md to determine whether the code should reside
-	 * within the FIRST_RESET_HANDLER_CALL block or not.
-	 *
-	 * For R-Car H3:
-	 * - Set the L2 Tag RAM latency to 2 (i.e. 3 cycles) for Cortex-A57
-	 * - Set the L2 Data setup latency to 1 (i.e. 1 cycles) for Cortex-A57
-	 * - Set the L2 Data RAM latency to 3 (i.e. 4 cycles) for Cortex-A57
-	 * For R-Car M3/M3N:
-	 * - Set the L2 Tag RAM latency to 2 (i.e. 3 cycles) for Cortex-A57
-	 * - Set the L2 Data setup latency to 0 (i.e. 0 cycles) for Cortex-A57
-	 * - Set the L2 Data RAM latency to 3 (i.e. 4 cycles) for Cortex-A57
-	 *
-	 * --------------------------------------------------------------------
-	 */
-func plat_reset_handler
-	/*
-	 * On R-Car H3    :  x2 := 0
-	 * On R-Car M3/M3N:  x2 := 1
-	 */
-	/* read PRR */
-	ldr	x0, =0xFFF00044
-	ldr	w0, [x0]
-	ubfx	w0, w0, 8, 8
-	/* H3? */
-	cmp	w0, #0x4F
-	b.eq	RCARH3
-	/* set R-Car M3/M3N */
-	mov	x2, #1
-	b	CHK_A5x
-RCARH3:
-	/* set R-Car H3 */
-	mov	x2, #0
-	/* --------------------------------------------------------------------
-	 * Determine whether this code is executed on a Cortex-A53 or on a
-	 * Cortex-A57 core.
-	 * --------------------------------------------------------------------
-	 */
-CHK_A5x:
-	mrs	x0, midr_el1
-	ubfx	x1, x0, MIDR_PN_SHIFT, #12
-	cmp     w1, #((CORTEX_A57_MIDR >> MIDR_PN_SHIFT) & MIDR_PN_MASK)
-	b.eq	A57
-	ret
-A57:
-	/* Get data from CORTEX_A57_L2CTLR_EL1	*/
-	mrs	x0, CORTEX_A57_L2CTLR_EL1
-	/*
-	 * On R-Car H3/M3/M3N
-	 *
-	 * L2 Tag RAM latency is bit8-6 of CORTEX_A57_L2CTLR_EL1
-	 * L2 Data RAM setup is bit5 of CORTEX_A57_L2CTLR_EL1
-	 * L2 Data RAM latency is bit2-0 of CORTEX_A57_L2CTLR_EL1
-	 */
-	/* clear bit of L2 RAM	*/
-	/* ~(0x1e7) -> x1	*/
-	mov	x1, #0x1e7
-	neg	x1, x1
-	/* clear bit of L2 RAM -> x0 */
-	and	x0, x0, x1
-	/* L2 Tag RAM latency (3 cycles) */
-	orr	x0, x0, #0x2 << 6
-	/* If M3/M3N then L2 RAM setup is 0 */
-	cbnz	x2, M3_L2
-	/* L2 Data RAM setup (1 cycle) */
-	orr	x0, x0, #0x1 << 5
-M3_L2:
-	/* L2 Data RAM latency (4 cycles) */
-	orr	x0, x0, #0x3
-	/* Store data to L2CTLR_EL1 */
-	msr	CORTEX_A57_L2CTLR_EL1, x0
-apply_l2_ram_latencies:
-	ret
-endfunc plat_reset_handler
-
-	/* ---------------------------------------------
-	 * void plat_invalidate_icache(void)
-	 * Instruction Cache Invalidate All to PoU
-	 * ---------------------------------------------
-	 */
-func plat_invalidate_icache
-	ic	iallu
-
-	ret
-endfunc plat_invalidate_icache
diff --git a/plat/renesas/rcar/bl2_cpg_init.c b/plat/renesas/rcar/bl2_cpg_init.c
deleted file mode 100644
index c3ca9ea..0000000
--- a/plat/renesas/rcar/bl2_cpg_init.c
+++ /dev/null
@@ -1,424 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <common/debug.h>
-#include <lib/mmio.h>
-
-#include "rcar_def.h"
-#include "cpg_registers.h"
-#include "rcar_private.h"
-
-static void bl2_secure_cpg_init(void);
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N)
-static void bl2_realtime_cpg_init_h3(void);
-static void bl2_system_cpg_init_h3(void);
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3)
-static void bl2_realtime_cpg_init_m3(void);
-static void bl2_system_cpg_init_m3(void);
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N)
-static void bl2_realtime_cpg_init_m3n(void);
-static void bl2_system_cpg_init_m3n(void);
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_V3M)
-static void bl2_realtime_cpg_init_v3m(void);
-static void bl2_system_cpg_init_v3m(void);
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_E3)
-static void bl2_realtime_cpg_init_e3(void);
-static void bl2_system_cpg_init_e3(void);
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_D3)
-static void bl2_realtime_cpg_init_d3(void);
-static void bl2_system_cpg_init_d3(void);
-#endif
-
-typedef struct {
-	uintptr_t adr;
-	uint32_t val;
-} reg_setting_t;
-
-static void bl2_secure_cpg_init(void)
-{
-	uint32_t stop_cr2, reset_cr2;
-	uint32_t stop_cr4, reset_cr4;
-	uint32_t stop_cr5, reset_cr5;
-
-#if (RCAR_LSI == RCAR_D3)
-	reset_cr2 = 0x00000000U;
-	stop_cr2 = 0xFFFFFFFFU;
-#elif (RCAR_LSI == RCAR_E3)
-	reset_cr2 = 0x10000000U;
-	stop_cr2 = 0xEFFFFFFFU;
-#else
-	reset_cr2 = 0x14000000U;
-	stop_cr2 = 0xEBFFFFFFU;
-#endif
-
-#if (RCAR_LSI == RCAR_D3)
-	reset_cr4 = 0x00000000U;
-	stop_cr4 = 0xFFFFFFFFU;
-	reset_cr5 = 0x00000000U;
-	stop_cr5 = 0xFFFFFFFFU;
-#else
-	reset_cr4 = 0x80000003U;
-	stop_cr4 = 0x7FFFFFFFU;
-	reset_cr5 = 0x40000000U;
-	stop_cr5 = 0xBFFFFFFFU;
-#endif
-
-	/** Secure Module Stop Control Registers */
-	cpg_write(SCMSTPCR0, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR2, stop_cr2);
-	cpg_write(SCMSTPCR3, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR4, stop_cr4);
-	cpg_write(SCMSTPCR5, stop_cr5);
-	cpg_write(SCMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR8, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR9, 0xFFFDFFFFU);
-	cpg_write(SCMSTPCR10, 0xFFFFFFFFU);
-	cpg_write(SCMSTPCR11, 0xFFFFFFFFU);
-
-	/** Secure Software Reset Access Enable Control Registers */
-	cpg_write(SCSRSTECR0, 0x00000000U);
-	cpg_write(SCSRSTECR1, 0x00000000U);
-	cpg_write(SCSRSTECR2, reset_cr2);
-	cpg_write(SCSRSTECR3, 0x00000000U);
-	cpg_write(SCSRSTECR4, reset_cr4);
-	cpg_write(SCSRSTECR5, reset_cr5);
-	cpg_write(SCSRSTECR6, 0x00000000U);
-	cpg_write(SCSRSTECR7, 0x00000000U);
-	cpg_write(SCSRSTECR8, 0x00000000U);
-	cpg_write(SCSRSTECR9, 0x00020000U);
-	cpg_write(SCSRSTECR10, 0x00000000U);
-	cpg_write(SCSRSTECR11, 0x00000000U);
-}
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N)
-static void bl2_realtime_cpg_init_h3(void)
-{
-	uint32_t cut = mmio_read_32(RCAR_PRR) & PRR_CUT_MASK;
-	uint32_t cr0, cr8;
-
-	cr0 = (cut == PRR_PRODUCT_10 || cut == PRR_PRODUCT_11) ?
-	    0x00200000U : 0x00210000U;
-	cr8 = (cut == PRR_PRODUCT_10 || cut == PRR_PRODUCT_11) ?
-	    0x01F1FFF4U : 0x01F1FFF7U;
-
-	cpg_write(RMSTPCR0, cr0);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x040E0FDCU);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000004U);
-	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, cr8);
-	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
-	cpg_write(RMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(RMSTPCR11, 0x000000B7U);
-}
-
-static void bl2_system_cpg_init_h3(void)
-{
-	/** System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00210000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x040E2FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x80000004U);
-	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x01F1FFF5U);
-	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(SMSTPCR11, 0x000000B7U);
-}
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3)
-static void bl2_realtime_cpg_init_m3(void)
-{
-	/** Realtime Module Stop Control Registers */
-	cpg_write(RMSTPCR0, 0x00200000U);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x040E0FDCU);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000004U);
-	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, 0x01F1FFF7U);
-	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
-	cpg_write(RMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(RMSTPCR11, 0x000000B7U);
-}
-
-static void bl2_system_cpg_init_m3(void)
-{
-	/** System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00200000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x040E2FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x80000004U);
-	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x01F1FFF7U);
-	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(SMSTPCR11, 0x000000B7U);
-}
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N)
-static void bl2_realtime_cpg_init_m3n(void)
-{
-	/** Realtime Module Stop Control Registers */
-	cpg_write(RMSTPCR0, 0x00210000U);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x040E0FDCU);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000004U);
-	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, 0x00F1FFF7U);
-	cpg_write(RMSTPCR9, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR10, 0xFFFFFFE0U);
-	cpg_write(RMSTPCR11, 0x000000B7U);
-}
-
-static void bl2_system_cpg_init_m3n(void)
-{
-	/* System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00210000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x040E2FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x80000004U);
-	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x00F1FFF7U);
-	cpg_write(SMSTPCR9, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR10, 0xFFFFFFE0U);
-	cpg_write(SMSTPCR11, 0x000000B7U);
-}
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_V3M)
-static void bl2_realtime_cpg_init_v3m(void)
-{
-	/* Realtime Module Stop Control Registers */
-	cpg_write(RMSTPCR0, 0x00230000U);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x14062FD8U);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000184U);
-	cpg_write(RMSTPCR5, 0x83FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, 0x7FF3FFF4U);
-	cpg_write(RMSTPCR9, 0xFFFFFFFEU);
-}
-
-static void bl2_system_cpg_init_v3m(void)
-{
-	/* System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00210000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x340E2FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x80000004U);
-	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x01F1FFF5U);
-	cpg_write(SMSTPCR9, 0xFFFFFFFEU);
-}
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_E3)
-static void bl2_realtime_cpg_init_e3(void)
-{
-	/* Realtime Module Stop Control Registers */
-	cpg_write(RMSTPCR0, 0x00210000U);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x000E0FDCU);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000004U);
-	cpg_write(RMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, 0x00F1FFF7U);
-	cpg_write(RMSTPCR9, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR10, 0xFFFFFFE8U);
-	cpg_write(RMSTPCR11, 0x000000B7U);
-}
-
-static void bl2_system_cpg_init_e3(void)
-{
-	/* System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00210000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x000E2FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x80000004U);
-	cpg_write(SMSTPCR5, 0xC3FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x00F1FFF7U);
-	cpg_write(SMSTPCR9, 0xFFFFFFDFU);
-	cpg_write(SMSTPCR10, 0xFFFFFFE8U);
-	cpg_write(SMSTPCR11, 0x000000B7U);
-}
-#endif
-
-#if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_D3)
-static void bl2_realtime_cpg_init_d3(void)
-{
-	/* Realtime Module Stop Control Registers */
-	cpg_write(RMSTPCR0, 0x00010000U);
-	cpg_write(RMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR2, 0x00060FDCU);
-	cpg_write(RMSTPCR3, 0xFFFFFFDFU);
-	cpg_write(RMSTPCR4, 0x80000184U);
-	cpg_write(RMSTPCR5, 0x83FFFFFFU);
-	cpg_write(RMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(RMSTPCR8, 0x00F1FFF7U);
-	cpg_write(RMSTPCR9, 0xF3F5E016U);
-	cpg_write(RMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(RMSTPCR11, 0x000000B7U);
-}
-
-static void bl2_system_cpg_init_d3(void)
-{
-	/* System Module Stop Control Registers */
-	cpg_write(SMSTPCR0, 0x00010000U);
-	cpg_write(SMSTPCR1, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR2, 0x00060FDCU);
-	cpg_write(SMSTPCR3, 0xFFFFFBDFU);
-	cpg_write(SMSTPCR4, 0x00000084U);
-	cpg_write(SMSTPCR5, 0x83FFFFFFU);
-	cpg_write(SMSTPCR6, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR7, 0xFFFFFFFFU);
-	cpg_write(SMSTPCR8, 0x00F1FFF7U);
-	cpg_write(SMSTPCR9, 0xF3F5E016U);
-	cpg_write(SMSTPCR10, 0xFFFEFFE0U);
-	cpg_write(SMSTPCR11, 0x000000B7U);
-}
-#endif
-
-void bl2_cpg_init(void)
-{
-	uint32_t boot_cpu = mmio_read_32(RCAR_MODEMR) & MODEMR_BOOT_CPU_MASK;
-#if RCAR_LSI == RCAR_AUTO
-	uint32_t product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
-#endif
-	bl2_secure_cpg_init();
-
-	if (boot_cpu == MODEMR_BOOT_CPU_CA57 ||
-	    boot_cpu == MODEMR_BOOT_CPU_CA53) {
-#if RCAR_LSI == RCAR_AUTO
-
-		switch (product) {
-		case PRR_PRODUCT_H3:
-			bl2_realtime_cpg_init_h3();
-			break;
-		case PRR_PRODUCT_M3:
-			bl2_realtime_cpg_init_m3();
-			break;
-		case PRR_PRODUCT_M3N:
-			bl2_realtime_cpg_init_m3n();
-			break;
-		case PRR_PRODUCT_V3M:
-			bl2_realtime_cpg_init_v3m();
-			break;
-		case PRR_PRODUCT_E3:
-			bl2_realtime_cpg_init_e3();
-			break;
-		case PRR_PRODUCT_D3:
-			bl2_realtime_cpg_init_d3();
-			break;
-		default:
-			panic();
-			break;
-		}
-#elif (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N)
-		bl2_realtime_cpg_init_h3();
-#elif RCAR_LSI == RCAR_M3
-		bl2_realtime_cpg_init_m3();
-#elif RCAR_LSI == RCAR_M3N
-		bl2_realtime_cpg_init_m3n();
-#elif RCAR_LSI == RCAR_V3M
-		bl2_realtime_cpg_init_v3m();
-#elif RCAR_LSI == RCAR_E3
-		bl2_realtime_cpg_init_e3();
-#elif RCAR_LSI == RCAR_D3
-		bl2_realtime_cpg_init_d3();
-#else
-#error "Don't have CPG initialize routine(unknown)."
-#endif
-	}
-}
-
-void bl2_system_cpg_init(void)
-{
-#if RCAR_LSI == RCAR_AUTO
-	uint32_t product = mmio_read_32(RCAR_PRR) & PRR_PRODUCT_MASK;
-
-	switch (product) {
-	case PRR_PRODUCT_H3:
-		bl2_system_cpg_init_h3();
-		break;
-	case PRR_PRODUCT_M3:
-		bl2_system_cpg_init_m3();
-		break;
-	case PRR_PRODUCT_M3N:
-		bl2_system_cpg_init_m3n();
-		break;
-	case PRR_PRODUCT_V3M:
-		bl2_system_cpg_init_v3m();
-		break;
-	case PRR_PRODUCT_E3:
-		bl2_system_cpg_init_e3();
-		break;
-	case PRR_PRODUCT_D3:
-		bl2_system_cpg_init_d3();
-		break;
-	default:
-		panic();
-		break;
-	}
-#elif (RCAR_LSI == RCAR_H3) || (RCAR_LSI == RCAR_H3N)
-	bl2_system_cpg_init_h3();
-#elif RCAR_LSI == RCAR_M3
-	bl2_system_cpg_init_m3();
-#elif RCAR_LSI == RCAR_M3N
-	bl2_system_cpg_init_m3n();
-#elif RCAR_LSI == RCAR_V3M
-	bl2_system_cpg_init_v3m();
-#elif RCAR_LSI == RCAR_E3
-	bl2_system_cpg_init_e3();
-#elif RCAR_LSI == RCAR_D3
-	bl2_system_cpg_init_d3();
-#else
-#error "Don't have CPG initialize routine(unknown)."
-#endif
-}
diff --git a/plat/renesas/rcar/bl2_plat_setup.c b/plat/renesas/rcar/bl2_plat_setup.c
index add2a4f..bbfa169 100644
--- a/plat/renesas/rcar/bl2_plat_setup.c
+++ b/plat/renesas/rcar/bl2_plat_setup.c
@@ -1,9 +1,11 @@
 /*
- * Copyright (c) 2018-2020, Renesas Electronics Corporation. All rights reserved.
+ * Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <libfdt.h>
@@ -15,12 +17,16 @@
 #include <common/bl_common.h>
 #include <common/debug.h>
 #include <common/desc_image_load.h>
+#include <common/image_decompress.h>
 #include <drivers/console.h>
 #include <drivers/io/io_driver.h>
 #include <drivers/io/io_storage.h>
 #include <lib/mmio.h>
 #include <lib/xlat_tables/xlat_tables_defs.h>
 #include <plat/common/platform.h>
+#if RCAR_GEN3_BL33_GZIP == 1
+#include <tf_gunzip.h>
+#endif
 
 #include "avs_driver.h"
 #include "boot_init_dram.h"
@@ -259,9 +265,6 @@
 	if (product == PRR_PRODUCT_H3 && PRR_PRODUCT_20 > cut)
 		goto tlb;
 
-	if (product == PRR_PRODUCT_D3)
-		goto tlb;
-
 	/* Disable MFIS write protection */
 	mmio_write_32(MFISWPCNTR, MFISWPCNTR_PASSWORD | 1);
 
@@ -357,16 +360,29 @@
 #endif
 }
 
+#if RCAR_GEN3_BL33_GZIP == 1
+void bl2_plat_preload_setup(void)
+{
+	image_decompress_init(BL33_COMP_BASE, BL33_COMP_SIZE, gunzip);
+}
+#endif
+
 int bl2_plat_handle_pre_image_load(unsigned int image_id)
 {
 	u_register_t *boot_kind = (void *) BOOT_KIND_BASE;
 	bl_mem_params_node_t *bl_mem_params;
 
+	bl_mem_params = get_bl_mem_params_node(image_id);
+
+#if RCAR_GEN3_BL33_GZIP == 1
+	if (image_id == BL33_IMAGE_ID) {
+		image_decompress_prepare(&bl_mem_params->image_info);
+	}
+#endif
+
 	if (image_id != BL31_IMAGE_ID)
 		return 0;
 
-	bl_mem_params = get_bl_mem_params_node(image_id);
-
 	if (is_ddr_backup_mode() == RCAR_COLD_BOOT)
 		goto cold_boot;
 
@@ -433,6 +449,19 @@
 			sizeof(entry_point_info_t));
 		break;
 	case BL33_IMAGE_ID:
+#if RCAR_GEN3_BL33_GZIP == 1
+		if ((mmio_read_32(BL33_COMP_BASE) & 0xffff) == 0x8b1f) {
+			/* decompress gzip-compressed image */
+			ret = image_decompress(&bl_mem_params->image_info);
+			if (ret != 0) {
+				return ret;
+			}
+		} else {
+			/* plain image, copy it in place */
+			memcpy((void *)BL33_BASE, (void *)BL33_COMP_BASE,
+				bl_mem_params->image_info.image_size);
+		}
+#endif
 		memcpy(&params->bl33_ep_info, &bl_mem_params->ep_info,
 			sizeof(entry_point_info_t));
 		break;
@@ -535,12 +564,75 @@
 	}
 }
 
-static void bl2_advertise_dram_entries(uint64_t dram_config[8])
+static void bl2_add_rpc_node(void)
+{
+#if (RCAR_RPC_HYPERFLASH_LOCKED == 0)
+	int ret, node;
+
+	node = ret = fdt_add_subnode(fdt, 0, "soc");
+	if (ret < 0) {
+		goto err;
+	}
+
+	node = ret = fdt_add_subnode(fdt, node, "rpc@ee200000");
+	if (ret < 0) {
+		goto err;
+	}
+
+	ret = fdt_setprop_string(fdt, node, "status", "okay");
+	if (ret < 0) {
+		goto err;
+	}
+
+	return;
+err:
+	NOTICE("BL2: Cannot add RPC node to FDT (ret=%i)\n", ret);
+	panic();
+#endif
+}
+
+static void bl2_add_dram_entry(uint64_t start, uint64_t size)
 {
 	char nodename[32] = { 0 };
-	uint64_t start, size;
 	uint64_t fdtsize;
-	int ret, node, chan;
+	int ret, node;
+
+	fdtsize = cpu_to_fdt64(size);
+
+	snprintf(nodename, sizeof(nodename), "memory@");
+	unsigned_num_print(start, 16, nodename + strlen(nodename));
+	node = ret = fdt_add_subnode(fdt, 0, nodename);
+	if (ret < 0) {
+		goto err;
+	}
+
+	ret = fdt_setprop_string(fdt, node, "device_type", "memory");
+	if (ret < 0) {
+		goto err;
+	}
+
+	ret = fdt_setprop_u64(fdt, node, "reg", start);
+	if (ret < 0) {
+		goto err;
+	}
+
+	ret = fdt_appendprop(fdt, node, "reg", &fdtsize,
+			     sizeof(fdtsize));
+	if (ret < 0) {
+		goto err;
+	}
+
+	return;
+err:
+	NOTICE("BL2: Cannot add memory node [%" PRIx64 " - %" PRIx64 "] to FDT (ret=%i)\n",
+		start, start + size - 1, ret);
+	panic();
+}
+
+static void bl2_advertise_dram_entries(uint64_t dram_config[8])
+{
+	uint64_t start, size, size32;
+	int chan;
 
 	for (chan = 0; chan < 4; chan++) {
 		start = dram_config[2 * chan];
@@ -548,7 +640,7 @@
 		if (!size)
 			continue;
 
-		NOTICE("BL2: CH%d: %llx - %llx, %lld %siB\n",
+		NOTICE("BL2: CH%d: %" PRIx64 " - %" PRIx64 ", %" PRId64 " %siB\n",
 			chan, start, start + size - 1,
 			(size >> 30) ? : size >> 20,
 			(size >> 30) ? "G" : "M");
@@ -568,39 +660,43 @@
 
 		/*
 		 * Channel 0 is mapped in 32bit space and the first
-		 * 128 MiB are reserved
+		 * 128 MiB are reserved and the maximum size is 2GiB.
 		 */
 		if (chan == 0) {
-			start = 0x48000000;
-			size -= 0x8000000;
+			/* Limit the 32bit entry to 2 GiB - 128 MiB */
+			size32 = size - 0x8000000U;
+			if (size32 >= 0x78000000U) {
+				size32 = 0x78000000U;
+			}
+
+			/* Emit 32bit entry, up to 2 GiB - 128 MiB long. */
+			bl2_add_dram_entry(0x48000000, size32);
+
+			/*
+			 * If channel 0 is less than 2 GiB long, the
+			 * entire memory fits into the 32bit space entry,
+			 * so move on to the next channel.
+			 */
+			if (size <= 0x80000000U) {
+				continue;
+			}
+
+			/*
+			 * If channel 0 is more than 2 GiB long, emit
+			 * another entry which covers the rest of the
+			 * memory in channel 0, in the 64bit space.
+			 *
+			 * Start of this new entry is at 2 GiB offset
+			 * from the beginning of the 64bit channel 0
+			 * address, size is 2 GiB shorter than total
+			 * size of the channel.
+			 */
+			start += 0x80000000U;
+			size -= 0x80000000U;
 		}
 
-		fdtsize = cpu_to_fdt64(size);
-
-		snprintf(nodename, sizeof(nodename), "memory@");
-		unsigned_num_print(start, 16, nodename + strlen(nodename));
-		node = ret = fdt_add_subnode(fdt, 0, nodename);
-		if (ret < 0)
-			goto err;
-
-		ret = fdt_setprop_string(fdt, node, "device_type", "memory");
-		if (ret < 0)
-			goto err;
-
-		ret = fdt_setprop_u64(fdt, node, "reg", start);
-		if (ret < 0)
-			goto err;
-
-		ret = fdt_appendprop(fdt, node, "reg", &fdtsize,
-				     sizeof(fdtsize));
-		if (ret < 0)
-			goto err;
+		bl2_add_dram_entry(start, size);
 	}
-
-	return;
-err:
-	NOTICE("BL2: Cannot add memory node to FDT (ret=%i)\n", ret);
-	panic();
 }
 
 static void bl2_advertise_dram_size(uint32_t product)
@@ -611,6 +707,7 @@
 		[4] = 0x600000000ULL,
 		[6] = 0x700000000ULL,
 	};
+	uint32_t cut = mmio_read_32(RCAR_PRR) & PRR_CUT_MASK;
 
 	switch (product) {
 	case PRR_PRODUCT_H3:
@@ -636,20 +733,31 @@
 		break;
 
 	case PRR_PRODUCT_M3:
+		if (cut < PRR_PRODUCT_30) {
 #if (RCAR_GEN3_ULCB == 1)
-		/* 2GB(1GBx2 2ch split) */
-		dram_config[1] = 0x40000000ULL;
-		dram_config[5] = 0x40000000ULL;
+			/* 2GB(1GBx2 2ch split) */
+			dram_config[1] = 0x40000000ULL;
+			dram_config[5] = 0x40000000ULL;
 #else
-		/* 4GB(2GBx2 2ch split) */
-		dram_config[1] = 0x80000000ULL;
-		dram_config[5] = 0x80000000ULL;
+			/* 4GB(2GBx2 2ch split) */
+			dram_config[1] = 0x80000000ULL;
+			dram_config[5] = 0x80000000ULL;
 #endif
+		} else {
+			/* 8GB(2GBx4 2ch split) */
+			dram_config[1] = 0x100000000ULL;
+			dram_config[5] = 0x100000000ULL;
+		}
 		break;
 
 	case PRR_PRODUCT_M3N:
+#if (RCAR_DRAM_LPDDR4_MEMCONF == 2)
+		/* 4GB(4GBx1) */
+		dram_config[1] = 0x100000000ULL;
+#elif (RCAR_DRAM_LPDDR4_MEMCONF == 1)
 		/* 2GB(1GBx2) */
 		dram_config[1] = 0x80000000ULL;
+#endif
 		break;
 
 	case PRR_PRODUCT_V3M:
@@ -795,6 +903,14 @@
 				str,
 				(reg & RCAR_MINOR_MASK) + RCAR_M3_MINOR_OFFSET);
 		}
+	} else if (product == PRR_PRODUCT_D3) {
+		if (RCAR_D3_CUT_VER10 == (reg & PRR_CUT_MASK)) {
+			NOTICE("BL2: PRR is R-Car %s Ver.1.0\n", str);
+		} else  if (RCAR_D3_CUT_VER11 == (reg & PRR_CUT_MASK)) {
+			NOTICE("BL2: PRR is R-Car %s Ver.1.1\n", str);
+		} else {
+			NOTICE("BL2: PRR is R-Car %s Ver.X.X\n", str);
+		}
 	} else {
 		major = (reg & RCAR_MAJOR_MASK) >> RCAR_MAJOR_SHIFT;
 		major = major + RCAR_MAJOR_OFFSET;
@@ -802,7 +918,7 @@
 		NOTICE("BL2: PRR is R-Car %s Ver.%d.%d\n", str, major, minor);
 	}
 
-	if (product == PRR_PRODUCT_E3) {
+	if (PRR_PRODUCT_E3 == product || PRR_PRODUCT_D3 == product) {
 		reg = mmio_read_32(RCAR_MODEMR);
 		sscg = reg & RCAR_SSCG_MASK;
 		str = sscg == RCAR_SSCG_ENABLE ? sscg_on : sscg_off;
@@ -866,10 +982,6 @@
 		str = boot_emmc25x1;
 		break;
 	case MODEMR_BOOT_DEV_EMMC_50X8:
-#if RCAR_LSI == RCAR_D3
-		ERROR("BL2: Failed to Initialize. eMMC is not supported.\n");
-		panic();
-#endif
 		str = boot_emmc50x8;
 		break;
 	default:
@@ -935,6 +1047,9 @@
 	/* Add platform compatible string */
 	bl2_populate_compatible_string(fdt);
 
+	/* Enable RPC if unlocked */
+	bl2_add_rpc_node();
+
 	/* Print DRAM layout */
 	bl2_advertise_dram_size(product);
 
diff --git a/plat/renesas/rcar/bl2_secure_setting.c b/plat/renesas/rcar/bl2_secure_setting.c
deleted file mode 100644
index 7473df5..0000000
--- a/plat/renesas/rcar/bl2_secure_setting.c
+++ /dev/null
@@ -1,352 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <lib/mmio.h>
-#include <lib/utils_def.h>
-
-#include "axi_registers.h"
-#include "lifec_registers.h"
-#include "micro_delay.h"
-
-static void lifec_security_setting(void);
-static void axi_security_setting(void);
-
-static const struct {
-	uint32_t reg;
-	uint32_t val;
-} lifec[] = {
-	/** LIFEC0 (SECURITY) settings					*/
-	/* Security attribute setting for master ports                  */
-	/* Bit 0: ARM realtime core (Cortex-R7) master port             */
-	/*       0: Non-Secure                                          */
-	{
-	SEC_SRC, 0x0000001EU},
-	/** Security attribute setting for slave ports 0 to 15		*/
-	    /*      {SEC_SEL0,              0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL1,              0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL2,              0xFFFFFFFFU},                   */
-	    /* Bit19: AXI-Bus (Main Memory domain AXI) slave ports          */
-	    /*        0: registers accessed from secure resource only       */
-	    /* Bit 9: DBSC4 register access slave ports.                    */
-	    /*        0: registers accessed from secure resource only.      */
-#if (LIFEC_DBSC_PROTECT_ENABLE == 1)
-	{
-	SEC_SEL3, 0xFFF7FDFFU},
-#else
-	{
-	SEC_SEL3, 0xFFFFFFFFU},
-#endif
-	    /*      {SEC_SEL4,              0xFFFFFFFFU},                   */
-	    /* Bit 6: Boot ROM slave ports.                                 */
-	    /*        0: registers accessed from secure resource only       */
-	{
-	SEC_SEL5, 0xFFFFFFBFU},
-	    /* Bit13: SCEG PKA (secure APB) slave ports                     */
-	    /*        0: registers accessed from secure resource only       */
-	    /*        1: Reserved[R-Car E3]                                 */
-	    /* Bit12: SCEG PKA (public APB) slave ports                     */
-	    /*        0: registers accessed from secure resource only       */
-	    /*        1: Reserved[R-Car E3]                                 */
-	    /* Bit10: SCEG Secure Core slave ports                          */
-	    /*        0: registers accessed from secure resource only       */
-#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
-	{
-	SEC_SEL6, 0xFFFFFBFFU},
-#else
-	{
-	SEC_SEL6, 0xFFFFCBFFU},
-#endif
-	    /*      {SEC_SEL7,              0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL8,              0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL9,              0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL10,             0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL11,             0xFFFFFFFFU},                   */
-	    /*      {SEC_SEL12,             0xFFFFFFFFU},                   */
-	    /* Bit22: RPC slave ports.                                      */
-	    /*        0: registers accessed from secure resource only.      */
-#if (RCAR_RPC_HYPERFLASH_LOCKED == 1)
-	    {SEC_SEL13,          0xFFBFFFFFU},
-#endif
-	    /* Bit27: System Timer (SCMT) slave ports                       */
-	    /*        0: registers accessed from secure resource only       */
-	    /* Bit26: System Watchdog Timer (SWDT) slave ports              */
-	    /*        0: registers accessed from secure resource only       */
-	{
-	SEC_SEL14, 0xF3FFFFFFU},
-	    /* Bit13: RST slave ports. */
-	    /*        0: registers accessed from secure resource only       */
-	    /* Bit 7: Life Cycle 0 slave ports                              */
-	    /*        0: registers accessed from secure resource only       */
-	{
-	SEC_SEL15, 0xFFFFFF3FU},
-	/** Security group 0 attribute setting for master ports 0	*/
-	/** Security group 1 attribute setting for master ports 0	*/
-	    /*      {SEC_GRP0CR0,           0x00000000U},                   */
-	    /*      {SEC_GRP1CR0,           0x00000000U},                   */
-	/** Security group 0 attribute setting for master ports 1	*/
-	/** Security group 1 attribute setting for master ports 1	*/
-	    /*      {SEC_GRP0CR1,           0x00000000U},                   */
-	    /*      {SEC_GRP1CR1,           0x00000000U},                   */
-	/** Security group 0 attribute setting for master ports 2 	*/
-	/** Security group 1 attribute setting for master ports 2 	*/
-	    /* Bit17: SCEG Secure Core master ports.                        */
-	    /*        SecurityGroup3                                        */
-	{
-	SEC_GRP0CR2, 0x00020000U}, {
-	SEC_GRP1CR2, 0x00020000U},
-	/** Security group 0 attribute setting for master ports 3 	*/
-	/** Security group 1 attribute setting for master ports 3 	*/
-	    /*      {SEC_GRP0CR3,           0x00000000U},                   */
-	    /*      {SEC_GRP1CR3,           0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 0 	*/
-	/** Security group 1 attribute setting for slave ports 0 	*/
-	    /*      {SEC_GRP0COND0,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND0,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 1 	*/
-	/** Security group 1 attribute setting for slave ports 1 	*/
-	    /*      {SEC_GRP0COND1,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND1,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 2 	*/
-	/** Security group 1 attribute setting for slave ports 2 	*/
-	    /*      {SEC_GRP0COND2,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND2,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 3	*/
-	/** Security group 1 attribute setting for slave ports 3	*/
-	    /* Bit19: AXI-Bus (Main Memory domain AXI) slave ports.         */
-	    /*        SecurityGroup3                                        */
-	    /* Bit 9: DBSC4 register access slave ports.                    */
-	    /*        SecurityGroup3                                        */
-#if (LIFEC_DBSC_PROTECT_ENABLE == 1)
-	{
-	SEC_GRP0COND3, 0x00080200U}, {
-	SEC_GRP1COND3, 0x00080200U},
-#else
-	{
-	SEC_GRP0COND3, 0x00000000U}, {
-	SEC_GRP1COND3, 0x00000000U},
-#endif
-	/** Security group 0 attribute setting for slave ports 4	*/
-	/** Security group 1 attribute setting for slave ports 4	*/
-	    /*      {SEC_GRP0COND4,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND4,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 5	*/
-	/** Security group 1 attribute setting for slave ports 5	*/
-	    /* Bit 6: Boot ROM slave ports                                  */
-	    /*        SecurityGroup3                                        */
-	{
-	SEC_GRP0COND5, 0x00000040U}, {
-	SEC_GRP1COND5, 0x00000040U},
-	/** Security group 0 attribute setting for slave ports 6	*/
-	/** Security group 1 attribute setting for slave ports 6	*/
-	    /* Bit13: SCEG PKA (secure APB) slave ports                     */
-	    /*        SecurityGroup3                                        */
-	    /*        Reserved[R-Car E3]                                    */
-	    /* Bit12: SCEG PKA (public APB) slave ports                     */
-	    /*        SecurityGroup3                                        */
-	    /*        Reserved[R-Car E3]                                    */
-	    /* Bit10: SCEG Secure Core slave ports                          */
-	    /*        SecurityGroup3                                        */
-#if RCAR_LSI == RCAR_E3
-	{
-	SEC_GRP0COND6, 0x00000400U}, {
-	SEC_GRP1COND6, 0x00000400U},
-#else
-	{
-	SEC_GRP0COND6, 0x00003400U}, {
-	SEC_GRP1COND6, 0x00003400U},
-#endif
-	/** Security group 0 attribute setting for slave ports 7	*/
-	/** Security group 1 attribute setting for slave ports 7	*/
-	    /*      {SEC_GRP0COND7,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND7,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 8	*/
-	/** Security group 1 attribute setting for slave ports 8	*/
-	    /*      {SEC_GRP0COND8,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND8,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 9	*/
-	/** Security group 1 attribute setting for slave ports 9	*/
-	    /*      {SEC_GRP0COND9,         0x00000000U},                   */
-	    /*      {SEC_GRP1COND9,         0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 10	*/
-	/** Security group 1 attribute setting for slave ports 10	*/
-	    /*      {SEC_GRP0COND10,        0x00000000U},                   */
-	    /*      {SEC_GRP1COND10,        0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 11	*/
-	/** Security group 1 attribute setting for slave ports 11	*/
-	    /*      {SEC_GRP0COND11,        0x00000000U},                   */
-	    /*      {SEC_GRP1COND11,        0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 12	*/
-	/** Security group 1 attribute setting for slave ports 12	*/
-	    /*      {SEC_GRP0COND12,        0x00000000U},                   */
-	    /*      {SEC_GRP1COND12,        0x00000000U},                   */
-	/** Security group 0 attribute setting for slave ports 13	*/
-	/** Security group 1 attribute setting for slave ports 13	*/
-	    /* Bit22: RPC slave ports.                                      */
-	    /*        SecurityGroup3                                        */
-#if (RCAR_RPC_HYPERFLASH_LOCKED == 1)
-	    {SEC_GRP0COND13,     0x00400000U},
-	    {SEC_GRP1COND13,     0x00400000U},
-#endif
-	/** Security group 0 attribute setting for slave ports 14	*/
-	/** Security group 1 attribute setting for slave ports 14	*/
-	    /* Bit26: System Timer (SCMT) slave ports                       */
-	    /*        SecurityGroup3                                        */
-	    /* Bit27: System Watchdog Timer (SWDT) slave ports              */
-	    /*        SecurityGroup3                                        */
-	{
-	SEC_GRP0COND14, 0x0C000000U}, {
-	SEC_GRP1COND14, 0x0C000000U},
-	/** Security group 0 attribute setting for slave ports 15	*/
-	/** Security group 1 attribute setting for slave ports 15 	*/
-	    /* Bit13: RST slave ports                                       */
-	    /*        SecurityGroup3                                        */
-	    /* Bit 7: Life Cycle 0 slave ports                              */
-	    /*        SecurityGroup3                                        */
-	    /* Bit 6: TDBG slave ports                                      */
-	    /*        SecurityGroup3                                        */
-	{
-	SEC_GRP0COND15, 0x000000C0U}, {
-	SEC_GRP1COND15, 0x000000C0U},
-	/** Security write protection attribute setting slave ports 0	*/
-	    /*      {SEC_READONLY0,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 1	*/
-	    /*      {SEC_READONLY1,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 2	*/
-	    /*      {SEC_READONLY2,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 3	*/
-	    /*      {SEC_READONLY3,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 4	*/
-	    /*      {SEC_READONLY4,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 5	*/
-	    /*      {SEC_READONLY5,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 6	*/
-	    /*      {SEC_READONLY6,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 7	*/
-	    /*      {SEC_READONLY7,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 8	*/
-	    /*      {SEC_READONLY8,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 9	*/
-	    /*      {SEC_READONLY9,         0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 10	*/
-	    /*      {SEC_READONLY10,        0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 11	*/
-	    /*      {SEC_READONLY11,        0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 12	*/
-	    /*      {SEC_READONLY12,        0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 13	*/
-	    /*      {SEC_READONLY13,        0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 14	*/
-	    /*      {SEC_READONLY14,        0x00000000U},                   */
-	/** Security write protection attribute setting slave ports 15	*/
-	    /*      {SEC_READONLY15,        0x00000000U}                    */
-};
-
-/* AXI settings */
-static const struct {
-	uint32_t reg;
-	uint32_t val;
-} axi[] = {
-	/* DRAM protection                      */
-	/* AXI dram protected area division     */
-	{
-	AXI_DPTDIVCR0,  0x0E0403F0U}, {
-	AXI_DPTDIVCR1,  0x0E0407E0U}, {
-	AXI_DPTDIVCR2,  0x0E080000U}, {
-	AXI_DPTDIVCR3,  0x0E080000U}, {
-	AXI_DPTDIVCR4,  0x0E080000U}, {
-	AXI_DPTDIVCR5,  0x0E080000U}, {
-	AXI_DPTDIVCR6,  0x0E080000U}, {
-	AXI_DPTDIVCR7,  0x0E080000U}, {
-	AXI_DPTDIVCR8,  0x0E080000U}, {
-	AXI_DPTDIVCR9,  0x0E080000U}, {
-	AXI_DPTDIVCR10, 0x0E080000U}, {
-	AXI_DPTDIVCR11, 0x0E080000U}, {
-	AXI_DPTDIVCR12, 0x0E080000U}, {
-	AXI_DPTDIVCR13, 0x0E080000U}, {
-	AXI_DPTDIVCR14, 0x0E080000U},
-	    /* AXI dram protected area setting      */
-	{
-	AXI_DPTCR0,  0x0E000000U}, {
-	AXI_DPTCR1,  0x0E000E0EU}, {
-	AXI_DPTCR2,  0x0E000000U}, {
-	AXI_DPTCR3,  0x0E000000U}, {
-	AXI_DPTCR4,  0x0E000000U}, {
-	AXI_DPTCR5,  0x0E000000U}, {
-	AXI_DPTCR6,  0x0E000000U}, {
-	AXI_DPTCR7,  0x0E000000U}, {
-	AXI_DPTCR8,  0x0E000000U}, {
-	AXI_DPTCR9,  0x0E000000U}, {
-	AXI_DPTCR10, 0x0E000000U}, {
-	AXI_DPTCR11, 0x0E000000U}, {
-	AXI_DPTCR12, 0x0E000000U}, {
-	AXI_DPTCR13, 0x0E000000U}, {
-	AXI_DPTCR14, 0x0E000000U}, {
-	AXI_DPTCR15, 0x0E000000U},
-	    /* SRAM ptotection                      */
-	    /* AXI sram protected area division     */
-	{
-	AXI_SPTDIVCR0,  0x0E0E6304U}, {
-	AXI_SPTDIVCR1,  0x0E0E6360U}, {
-	AXI_SPTDIVCR2,  0x0E0E6360U}, {
-	AXI_SPTDIVCR3,  0x0E0E6360U}, {
-	AXI_SPTDIVCR4,  0x0E0E6360U}, {
-	AXI_SPTDIVCR5,  0x0E0E6360U}, {
-	AXI_SPTDIVCR6,  0x0E0E6360U}, {
-	AXI_SPTDIVCR7,  0x0E0E6360U}, {
-	AXI_SPTDIVCR8,  0x0E0E6360U}, {
-	AXI_SPTDIVCR9,  0x0E0E6360U}, {
-	AXI_SPTDIVCR10, 0x0E0E6360U}, {
-	AXI_SPTDIVCR11, 0x0E0E6360U}, {
-	AXI_SPTDIVCR12, 0x0E0E6360U}, {
-	AXI_SPTDIVCR13, 0x0E0E6360U}, {
-	AXI_SPTDIVCR14, 0x0E0E6360U},
-	    /* AXI sram protected area setting      */
-	{
-	AXI_SPTCR0,  0x0E000E0EU}, {
-	AXI_SPTCR1,  0x0E000000U}, {
-	AXI_SPTCR2,  0x0E000000U}, {
-	AXI_SPTCR3,  0x0E000000U}, {
-	AXI_SPTCR4,  0x0E000000U}, {
-	AXI_SPTCR5,  0x0E000000U}, {
-	AXI_SPTCR6,  0x0E000000U}, {
-	AXI_SPTCR7,  0x0E000000U}, {
-	AXI_SPTCR8,  0x0E000000U}, {
-	AXI_SPTCR9,  0x0E000000U}, {
-	AXI_SPTCR10, 0x0E000000U}, {
-	AXI_SPTCR11, 0x0E000000U}, {
-	AXI_SPTCR12, 0x0E000000U}, {
-	AXI_SPTCR13, 0x0E000000U}, {
-	AXI_SPTCR14, 0x0E000000U}, {
-	AXI_SPTCR15, 0x0E000000U}
-};
-
-static void lifec_security_setting(void)
-{
-	uint32_t i;
-
-	for (i = 0; i < ARRAY_SIZE(lifec); i++)
-		mmio_write_32(lifec[i].reg, lifec[i].val);
-}
-
-/* SRAM/DRAM protection setting */
-static void axi_security_setting(void)
-{
-	uint32_t i;
-
-	for (i = 0; i < ARRAY_SIZE(axi); i++)
-		mmio_write_32(axi[i].reg, axi[i].val);
-}
-
-void bl2_secure_setting(void)
-{
-	const uint32_t delay = 10;
-
-	lifec_security_setting();
-	axi_security_setting();
-	rcar_micro_delay(delay);
-
-	return;
-}
diff --git a/plat/renesas/rcar/bl31_plat_setup.c b/plat/renesas/rcar/bl31_plat_setup.c
deleted file mode 100644
index 7bc0d8e..0000000
--- a/plat/renesas/rcar/bl31_plat_setup.c
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Copyright (c) 2013-2014, ARM Limited and Contributors. All rights reserved.
- * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <stddef.h>
-
-#include <arch.h>
-#include <arch_helpers.h>
-#include <bl31/bl31.h>
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/arm/cci.h>
-#include <drivers/console.h>
-#include <lib/mmio.h>
-#include <plat/common/platform.h>
-
-#include "pwrc.h"
-#include "rcar_def.h"
-#include "rcar_private.h"
-#include "rcar_version.h"
-
-static const uint64_t BL31_RO_BASE		= BL_CODE_BASE;
-static const uint64_t BL31_RO_LIMIT		= BL_CODE_END;
-
-#if USE_COHERENT_MEM
-static const uint64_t BL31_COHERENT_RAM_BASE	= BL_COHERENT_RAM_BASE;
-static const uint64_t BL31_COHERENT_RAM_LIMIT	= BL_COHERENT_RAM_END;
-#endif
-
-extern void plat_rcar_gic_driver_init(void);
-extern void plat_rcar_gic_init(void);
-
-u_register_t rcar_boot_mpidr;
-
-static int cci_map[] = {
-	CCI500_CLUSTER0_SL_IFACE_IX_FOR_M3,
-	CCI500_CLUSTER1_SL_IFACE_IX_FOR_M3
-};
-
-void plat_cci_init(void)
-{
-	uint32_t prd;
-
-	prd = mmio_read_32(RCAR_PRR) & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
-
-	if (PRR_PRODUCT_H3_CUT10 == prd || PRR_PRODUCT_H3_CUT11 == prd) {
-		cci_map[0U] = CCI500_CLUSTER0_SL_IFACE_IX;
-		cci_map[1U] = CCI500_CLUSTER1_SL_IFACE_IX;
-	}
-
-	cci_init(RCAR_CCI_BASE, cci_map, ARRAY_SIZE(cci_map));
-}
-
-void plat_cci_enable(void)
-{
-	cci_enable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr()));
-}
-
-void plat_cci_disable(void)
-{
-	cci_disable_snoop_dvm_reqs(MPIDR_AFFLVL1_VAL(read_mpidr()));
-}
-
-struct entry_point_info *bl31_plat_get_next_image_ep_info(uint32_t type)
-{
-	bl2_to_bl31_params_mem_t *from_bl2 = (bl2_to_bl31_params_mem_t *)
-					     PARAMS_BASE;
-	entry_point_info_t *next_image_info;
-
-	next_image_info = (type == NON_SECURE) ?
-		&from_bl2->bl33_ep_info : &from_bl2->bl32_ep_info;
-
-	return next_image_info->pc ? next_image_info : NULL;
-}
-
-void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1,
-				u_register_t arg2, u_register_t arg3)
-{
-	rcar_console_runtime_init();
-
-	NOTICE("BL3-1 : Rev.%s\n", version_of_renesas);
-
-#if RCAR_LSI != RCAR_D3
-	if (RCAR_CLUSTER_A53A57 == rcar_pwrc_get_cluster()) {
-		plat_cci_init();
-		plat_cci_enable();
-	}
-#endif
-}
-
-void bl31_plat_arch_setup(void)
-{
-	rcar_configure_mmu_el3(BL31_BASE,
-			       BL31_LIMIT - BL31_BASE,
-			       BL31_RO_BASE, BL31_RO_LIMIT
-#if USE_COHERENT_MEM
-			       , BL31_COHERENT_RAM_BASE, BL31_COHERENT_RAM_LIMIT
-#endif
-	    );
-	rcar_pwrc_code_copy_to_system_ram();
-}
-
-void bl31_platform_setup(void)
-{
-	plat_rcar_gic_driver_init();
-	plat_rcar_gic_init();
-
-	/* enable the system level generic timer */
-	mmio_write_32(RCAR_CNTC_BASE + CNTCR_OFF, CNTCR_FCREQ(U(0)) | CNTCR_EN);
-
-	rcar_pwrc_setup();
-#if 0
-	/* TODO: there is a broad number of rcar-gen3 SoC configurations; to
-	   support all of them, Renesas use the pwrc driver to discover what
-	   cores are on/off before announcing the topology.
-	   This code hasnt been ported yet
-	   */
-
-	rcar_setup_topology();
-#endif
-
-	/* mask should match the kernel's MPIDR_HWID_BITMASK so the core can be
-	   identified during cpuhotplug (check the kernel's psci migrate set of
-	   functions */
-	rcar_boot_mpidr = read_mpidr_el1() & 0x0000ffffU;
-}
diff --git a/plat/renesas/rcar/include/platform_def.h b/plat/renesas/rcar/include/platform_def.h
deleted file mode 100644
index b7f0ca1..0000000
--- a/plat/renesas/rcar/include/platform_def.h
+++ /dev/null
@@ -1,195 +0,0 @@
-/*
- * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef PLATFORM_DEF_H
-#define PLATFORM_DEF_H
-
-#ifndef __ASSEMBLER__
-#include <stdlib.h>
-#endif
-
-#include <arch.h>
-
-#include "rcar_def.h"
-
-/*******************************************************************************
- * Platform binary types for linking
- ******************************************************************************/
-#define PLATFORM_LINKER_FORMAT          "elf64-littleaarch64"
-#define PLATFORM_LINKER_ARCH            aarch64
-
-/*******************************************************************************
- * Generic platform constants
- ******************************************************************************/
- #define FIRMWARE_WELCOME_STR	"Booting Rcar-gen3 Trusted Firmware\n"
-
-/* Size of cacheable stacks */
-#if IMAGE_BL1
-#if TRUSTED_BOARD_BOOT
-#define PLATFORM_STACK_SIZE 	U(0x1000)
-#else
-#define PLATFORM_STACK_SIZE 	U(0x440)
-#endif
-#elif IMAGE_BL2
-#if TRUSTED_BOARD_BOOT
-#define PLATFORM_STACK_SIZE 	U(0x1000)
-#else
-#define PLATFORM_STACK_SIZE 	U(0x400)
-#endif
-#elif IMAGE_BL31
-#define PLATFORM_STACK_SIZE 	U(0x400)
-#elif IMAGE_BL32
-#define PLATFORM_STACK_SIZE 	U(0x440)
-#endif
-
-#define BL332_IMAGE_ID		(NS_BL2U_IMAGE_ID + 1)
-#define BL333_IMAGE_ID		(NS_BL2U_IMAGE_ID + 2)
-#define BL334_IMAGE_ID		(NS_BL2U_IMAGE_ID + 3)
-#define BL335_IMAGE_ID		(NS_BL2U_IMAGE_ID + 4)
-#define BL336_IMAGE_ID		(NS_BL2U_IMAGE_ID + 5)
-#define BL337_IMAGE_ID		(NS_BL2U_IMAGE_ID + 6)
-#define BL338_IMAGE_ID		(NS_BL2U_IMAGE_ID + 7)
-
-#define BL332_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 8)
-#define BL333_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 9)
-#define BL334_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 10)
-#define BL335_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 11)
-#define BL336_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 12)
-#define BL337_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 13)
-#define BL338_KEY_CERT_ID	(NS_BL2U_IMAGE_ID + 14)
-
-#define BL332_CERT_ID		(NS_BL2U_IMAGE_ID + 15)
-#define BL333_CERT_ID		(NS_BL2U_IMAGE_ID + 16)
-#define BL334_CERT_ID		(NS_BL2U_IMAGE_ID + 17)
-#define BL335_CERT_ID		(NS_BL2U_IMAGE_ID + 18)
-#define BL336_CERT_ID		(NS_BL2U_IMAGE_ID + 19)
-#define BL337_CERT_ID		(NS_BL2U_IMAGE_ID + 20)
-#define BL338_CERT_ID		(NS_BL2U_IMAGE_ID + 21)
-
-/* io drivers id */
-#define FLASH_DEV_ID		U(0)
-#define EMMC_DEV_ID		U(1)
-
-/*
- * R-Car H3 Cortex-A57
- * L1:I/48KB(16KBx3way) D/32KB(16KBx2way) L2:2MB(128KBx16way)
- *          Cortex-A53
- * L1:I/32KB(16KBx2way) D/32KB(8KBx4way) L2:512KB(32KBx16way)
- */
-#define PLATFORM_CACHE_LINE_SIZE	64
-#define PLATFORM_CLUSTER_COUNT		U(2)
-#define PLATFORM_CLUSTER0_CORE_COUNT	U(4)
-#define PLATFORM_CLUSTER1_CORE_COUNT	U(4)
-#define PLATFORM_CORE_COUNT		(PLATFORM_CLUSTER1_CORE_COUNT + \
-					 PLATFORM_CLUSTER0_CORE_COUNT)
-#define PLATFORM_MAX_CPUS_PER_CLUSTER	U(4)
-
-#define PLAT_MAX_PWR_LVL		MPIDR_AFFLVL2
-#define PLAT_NUM_PWR_DOMAINS		(PLATFORM_CORE_COUNT + \
-					 PLATFORM_CLUSTER_COUNT + 1)
-
-#define PLAT_MAX_RET_STATE		U(1)
-#define PLAT_MAX_OFF_STATE		U(2)
-
-#define MAX_IO_DEVICES			U(3)
-#define MAX_IO_HANDLES			U(4)
-
-/*******************************************************************************
- * BL2 specific defines.
- ******************************************************************************/
-/* Put BL2 just below BL3-1. BL2_BASE is calculated using the current BL2 debug
- * size plus a little space for growth. */
-#define RCAR_SYSRAM_BASE		U(0xE6300000)
-#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
-#define BL2_LIMIT			U(0xE6320000)
-#else
-#define BL2_LIMIT			U(0xE6360000)
-#endif
-
-#if (RCAR_LSI == RCAR_E3) || (RCAR_LSI == RCAR_D3)
-#define BL2_BASE			U(0xE6304000)
-#define BL2_IMAGE_LIMIT			U(0xE6318000)
-#elif (RCAR_LSI == RCAR_V3M)
-#define BL2_BASE			U(0xE6344000)
-#define BL2_IMAGE_LIMIT			U(0xE636E800)
-#else
-#define BL2_BASE			U(0xE6304000)
-#define BL2_IMAGE_LIMIT			U(0xE632E800)
-#endif
-#define RCAR_SYSRAM_SIZE		(BL2_BASE - RCAR_SYSRAM_BASE)
-
-/*******************************************************************************
- * BL31 specific defines.
- ******************************************************************************/
-/* Put BL3-1 at the top of the Trusted SRAM. BL31_BASE is calculated using the
- * current BL3-1 debug size plus a little space for growth. */
-#define BL31_BASE		(RCAR_TRUSTED_SRAM_BASE)
-#define BL31_LIMIT		(RCAR_TRUSTED_SRAM_BASE + \
-				 RCAR_TRUSTED_SRAM_SIZE)
-#define	RCAR_BL31_LOG_BASE	(0x44040000)
-#define	RCAR_BL31_SDRAM_BTM	(RCAR_BL31_LOG_BASE + 0x14000)
-#define	RCAR_BL31_LOG_SIZE	(RCAR_BL31_SDRAM_BTM - RCAR_BL31_LOG_BASE)
-#define BL31_SRAM_BASE		(DEVICE_SRAM_BASE)
-#define BL31_SRAM_LIMIT		(DEVICE_SRAM_BASE + DEVICE_SRAM_SIZE)
-
-/*******************************************************************************
- * BL32 specific defines.
- ******************************************************************************/
-#ifndef SPD_NONE
-#define BL32_BASE		U(0x44100000)
-#define BL32_LIMIT		(BL32_BASE + U(0x100000))
-#endif
-
-/*******************************************************************************
- * BL33
- ******************************************************************************/
-#define BL33_BASE		DRAM1_NS_BASE
-
-
-/*******************************************************************************
- * Platform specific page table and MMU setup constants
- ******************************************************************************/
-#if IMAGE_BL1
-#define MAX_XLAT_TABLES		U(2)
-#elif IMAGE_BL2
-#define MAX_XLAT_TABLES		U(5)
-#elif IMAGE_BL31
-#define MAX_XLAT_TABLES		U(4)
-#elif IMAGE_BL32
-#define MAX_XLAT_TABLES		U(3)
-#endif
-
-#if IMAGE_BL2
-#define PLAT_PHY_ADDR_SPACE_SIZE	(ULL(1) << 40)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(ULL(1) << 40)
-#else
-#define PLAT_PHY_ADDR_SPACE_SIZE	(ULL(1) << 32)
-#define PLAT_VIRT_ADDR_SPACE_SIZE	(ULL(1) << 32)
-#endif
-
-#define MAX_MMAP_REGIONS	(RCAR_MMAP_ENTRIES + RCAR_BL_REGIONS)
-
-/*******************************************************************************
- * Declarations and constants to access the mailboxes safely. Each mailbox is
- * aligned on the biggest cache line size in the platform. This is known only
- * to the platform as it might have a combination of integrated and external
- * caches. Such alignment ensures that two maiboxes do not sit on the same cache
- * line at any cache level. They could belong to different cpus/clusters &
- * get written while being protected by different locks causing corruption of
- * a valid mailbox address.
- ******************************************************************************/
-#define CACHE_WRITEBACK_SHIFT   (6)
-#define CACHE_WRITEBACK_GRANULE (1 << CACHE_WRITEBACK_SHIFT)
-
-/*******************************************************************************
- * Size of the per-cpu data in bytes that should be reserved in the generic
- * per-cpu data structure for the RCAR port.
- ******************************************************************************/
-#if !USE_COHERENT_MEM
-#define PLAT_PCPU_DATA_SIZE	(2)
-#endif
-
-#endif /* PLATFORM_DEF_H */
diff --git a/plat/renesas/rcar/include/rcar_def.h b/plat/renesas/rcar/include/rcar_def.h
deleted file mode 100644
index 0ffbfe9..0000000
--- a/plat/renesas/rcar/include/rcar_def.h
+++ /dev/null
@@ -1,306 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef RCAR_DEF_H
-#define RCAR_DEF_H
-
-#include <common/tbbr/tbbr_img_def.h>
-#include <lib/utils_def.h>
-
-#define RCAR_PRIMARY_CPU		0x0
-#define RCAR_TRUSTED_SRAM_BASE		0x44000000
-#define RCAR_TRUSTED_SRAM_SIZE		0x0003E000
-#define RCAR_SHARED_MEM_BASE		(RCAR_TRUSTED_SRAM_BASE + \
-					RCAR_TRUSTED_SRAM_SIZE)
-#define RCAR_SHARED_MEM_SIZE		U(0x00001000)
-#define FLASH0_BASE			U(0x08000000)
-#define FLASH0_SIZE			U(0x04000000)
-#define FLASH_MEMORY_SIZE		U(0x04000000)	/* hyper flash */
-#define FLASH_TRANS_SIZE_UNIT		U(0x00000100)
-#define DEVICE_RCAR_BASE		U(0xE6000000)
-#define DEVICE_RCAR_SIZE		U(0x00300000)
-#define DEVICE_RCAR_BASE2		U(0xE6360000)
-#define DEVICE_RCAR_SIZE2		U(0x19CA0000)
-#define DEVICE_SRAM_BASE		U(0xE6300000)
-#define DEVICE_SRAM_SIZE		U(0x00002000)
-#define DEVICE_SRAM_STACK_BASE		(DEVICE_SRAM_BASE + DEVICE_SRAM_SIZE)
-#define DEVICE_SRAM_STACK_SIZE		U(0x00001000)
-#define DRAM_LIMIT			ULL(0x0000010000000000)
-#define DRAM1_BASE			U(0x40000000)
-#define DRAM1_SIZE			U(0x80000000)
-#define DRAM1_NS_BASE			(DRAM1_BASE + U(0x10000000))
-#define DRAM1_NS_SIZE			(DRAM1_SIZE - DRAM1_NS_BASE)
-#define	DRAM_40BIT_BASE			ULL(0x0400000000)
-#define	DRAM_40BIT_SIZE			ULL(0x0400000000)
-#define	DRAM_PROTECTED_BASE		ULL(0x43F00000)
-#define	DRAM_40BIT_PROTECTED_BASE	ULL(0x0403F00000)
-#define	DRAM_PROTECTED_SIZE		ULL(0x03F00000)
-#define	RCAR_BL31_CRASH_BASE		U(0x4403F000)
-#define	RCAR_BL31_CRASH_SIZE		U(0x00001000)
-/* Entrypoint mailboxes */
-#define MBOX_BASE			RCAR_SHARED_MEM_BASE
-#define MBOX_SIZE			0x200
-/* Base address where parameters to BL31 are stored */
-#define PARAMS_BASE			(MBOX_BASE + MBOX_SIZE)
-#define BOOT_KIND_BASE			(RCAR_SHARED_MEM_BASE + \
-					RCAR_SHARED_MEM_SIZE - 0x100)
-/* The number of regions like RO(code), coherent and data required by
- * different BL stages which need to be mapped in the MMU */
-#if USE_COHERENT_MEM
-#define RCAR_BL_REGIONS			(3)
-#else
-#define RCAR_BL_REGIONS			(2)
-#endif
-/* The RCAR_MAX_MMAP_REGIONS depend on the number of entries in rcar_mmap[]
- * defined for each BL stage in rcar_common.c. */
-#if IMAGE_BL2
-#define RCAR_MMAP_ENTRIES		(9)
-#endif
-#if IMAGE_BL31
-#define RCAR_MMAP_ENTRIES		(9)
-#endif
-#if IMAGE_BL2
-#define REG1_BASE			U(0xE6400000)
-#define REG1_SIZE			U(0x04C00000)
-#define ROM0_BASE			U(0xEB100000)
-#define ROM0_SIZE			U(0x00028000)
-#define REG2_BASE			U(0xEC000000)
-#define REG2_SIZE			U(0x14000000)
-#endif
-/* BL33  */
-#define NS_IMAGE_OFFSET			(DRAM1_BASE + U(0x09000000))
-/* BL31 */
-#define	RCAR_DEVICE_BASE		DEVICE_RCAR_BASE
-#define	RCAR_DEVICE_SIZE		(0x1A000000)
-#define	RCAR_LOG_RES_SIZE		(512/8)
-#define	RCAR_LOG_HEADER_SIZE		(16)
-#define	RCAR_LOG_OTHER_SIZE		(RCAR_LOG_HEADER_SIZE + \
-					RCAR_LOG_RES_SIZE)
-#define	RCAR_BL31_LOG_MAX		(RCAR_BL31_LOG_SIZE - \
-					RCAR_LOG_OTHER_SIZE)
-#define	RCAR_CRASH_STACK		RCAR_BL31_CRASH_BASE
-#define	AARCH64_SPACE_BASE		ULL(0x00000000000)
-#define	AARCH64_SPACE_SIZE		ULL(0x10000000000)
-/* CCI related constants */
-#define CCI500_BASE				U(0xF1200000)
-#define CCI500_CLUSTER0_SL_IFACE_IX		(2)
-#define CCI500_CLUSTER1_SL_IFACE_IX		(3)
-#define CCI500_CLUSTER0_SL_IFACE_IX_FOR_M3	(1)
-#define CCI500_CLUSTER1_SL_IFACE_IX_FOR_M3	(2)
-#define	RCAR_CCI_BASE				CCI500_BASE
-/* GIC */
-#define RCAR_GICD_BASE			U(0xF1010000)
-#define RCAR_GICR_BASE			U(0xF1010000)
-#define RCAR_GICC_BASE			U(0xF1020000)
-#define RCAR_GICH_BASE			U(0xF1040000)
-#define RCAR_GICV_BASE			U(0xF1060000)
-#define ARM_IRQ_SEC_PHY_TIMER		U(29)
-#define ARM_IRQ_SEC_SGI_0		U(8)
-#define ARM_IRQ_SEC_SGI_1		U(9)
-#define ARM_IRQ_SEC_SGI_2		U(10)
-#define ARM_IRQ_SEC_SGI_3		U(11)
-#define ARM_IRQ_SEC_SGI_4		U(12)
-#define ARM_IRQ_SEC_SGI_5		U(13)
-#define ARM_IRQ_SEC_SGI_6		U(14)
-#define ARM_IRQ_SEC_SGI_7		U(15)
-#define	ARM_IRQ_SEC_RPC			U(70)
-#define	ARM_IRQ_SEC_TIMER		U(166)
-#define	ARM_IRQ_SEC_TIMER_UP		U(171)
-#define	ARM_IRQ_SEC_WDT			U(173)
-#define	ARM_IRQ_SEC_CRYPT		U(102)
-#define	ARM_IRQ_SEC_CRYPT_SecPKA	U(97)
-#define	ARM_IRQ_SEC_CRYPT_PubPKA	U(98)
-/* Timer control */
-#define	RCAR_CNTC_BASE		U(0xE6080000)
-/* Reset */
-#define	RCAR_CPGWPR		U(0xE6150900)	/* CPG write protect    */
-#define	RCAR_MODEMR		U(0xE6160060)	/* Mode pin             */
-#define	RCAR_CA57RESCNT		U(0xE6160040)	/* Reset control A57    */
-#define	RCAR_CA53RESCNT		U(0xE6160044)	/* Reset control A53    */
-#define	RCAR_SRESCR		U(0xE6160110)	/* Soft Power On Reset  */
-#define	RCAR_CA53WUPCR		U(0xE6151010)	/* Wake-up control A53  */
-#define	RCAR_CA57WUPCR		U(0xE6152010)	/* Wake-up control A57  */
-#define	RCAR_CA53PSTR		U(0xE6151040)	/* Power status A53     */
-#define	RCAR_CA57PSTR		U(0xE6152040)	/* Power status A57     */
-#define	RCAR_CA53CPU0CR		U(0xE6151100)	/* CPU control  A53     */
-#define	RCAR_CA57CPU0CR		U(0xE6152100)	/* CPU control  A57     */
-#define	RCAR_CA53CPUCMCR	U(0xE6151184)	/* Common power A53     */
-#define	RCAR_CA57CPUCMCR	U(0xE6152184)	/* Common power A57     */
-#define	RCAR_WUPMSKCA57		U(0xE6180014)	/* Wake-up mask A57     */
-#define	RCAR_WUPMSKCA53		U(0xE6180018)	/* Wake-up mask A53     */
-/* SYSC	*/
-#define	RCAR_PWRSR3		U(0xE6180140)	/* Power stat A53-SCU   */
-#define	RCAR_PWRSR5		U(0xE61801C0)	/* Power stat A57-SCU   */
-#define	RCAR_SYSCIER		U(0xE618000C)	/* Interrupt enable     */
-#define	RCAR_SYSCIMR		U(0xE6180010)	/* Interrupt mask       */
-#define	RCAR_SYSCSR		U(0xE6180000)	/* SYSC status          */
-#define	RCAR_PWRONCR3		U(0xE618014C)	/* Power resume A53-SCU */
-#define	RCAR_PWRONCR5		U(0xE61801CC)	/* Power resume A57-SCU */
-#define	RCAR_PWROFFCR3		U(0xE6180144)	/* Power shutof A53-SCU */
-#define	RCAR_PWROFFCR5		U(0xE61801C4)	/* Power shutof A57-SCU */
-#define	RCAR_PWRER3		U(0xE6180154)	/* shutoff/resume error */
-#define	RCAR_PWRER5		U(0xE61801D4)	/* shutoff/resume error */
-#define	RCAR_SYSCISR		U(0xE6180004)	/* Interrupt status     */
-#define	RCAR_SYSCISCR		U(0xE6180008)	/* Interrupt stat clear */
-/* Product register */
-#define	RCAR_PRR			U(0xFFF00044)
-#define RCAR_M3_CUT_VER11		U(0x00000010)	/* M3 Ver.1.1/Ver.1.2 */
-#define RCAR_MAJOR_MASK			U(0x000000F0)
-#define RCAR_MINOR_MASK			U(0x0000000F)
-#define PRR_PRODUCT_SHIFT		U(8)
-#define RCAR_MAJOR_SHIFT		U(4)
-#define RCAR_MINOR_SHIFT		U(0)
-#define RCAR_MAJOR_OFFSET		U(1)
-#define RCAR_M3_MINOR_OFFSET		U(2)
-#define PRR_PRODUCT_H3_CUT10		(PRR_PRODUCT_H3 | U(0x00))	/* 1.0 */
-#define PRR_PRODUCT_H3_CUT11		(PRR_PRODUCT_H3 | U(0x01))	/* 1.1 */
-#define PRR_PRODUCT_H3_CUT20		(PRR_PRODUCT_H3 | U(0x10))	/* 2.0 */
-#define PRR_PRODUCT_M3_CUT10		(PRR_PRODUCT_M3 | U(0x00))	/* 1.0 */
-#define PRR_PRODUCT_M3_CUT11		(PRR_PRODUCT_M3 | U(0x10))
-#define PRR				0xFFF00044U
-#define PRR_PRODUCT_MASK		0x00007F00U
-#define PRR_CUT_MASK			0x000000FFU
-#define PRR_PRODUCT_H3			0x00004F00U	/* R-Car H3 */
-#define PRR_PRODUCT_M3			0x00005200U	/* R-Car M3-W */
-#define PRR_PRODUCT_V3M			0x00005400U	/* R-Car V3M */
-#define PRR_PRODUCT_M3N			0x00005500U	/* R-Car M3-N */
-#define PRR_PRODUCT_V3H			0x00005600U	/* R-Car V3H */
-#define PRR_PRODUCT_E3			0x00005700U	/* R-Car E3 */
-#define PRR_PRODUCT_D3			0x00005800U	/* R-Car D3 */
-#define PRR_PRODUCT_10			0x00U		/* Ver.1.0 */
-#define PRR_PRODUCT_11			0x01U		/* Ver.1.1 */
-#define PRR_PRODUCT_20			0x10U		/* Ver.2.0 */
-#define PRR_PRODUCT_21			0x11U		/* Ver.2.1 */
-#define PRR_PRODUCT_30			0x20U		/* Ver.3.0 */
-#define RCAR_CPU_MASK_CA57		U(0x80000000)
-#define RCAR_CPU_MASK_CA53		U(0x04000000)
-#define RCAR_CPU_HAVE_CA57		U(0x00000000)
-#define RCAR_CPU_HAVE_CA53		U(0x00000000)
-#define RCAR_SSCG_MASK			U(0x1000)	/* MD12 */
-#define RCAR_SSCG_ENABLE		U(0x1000)
-/* MD pin information */
-#define MODEMR_BOOT_CPU_MASK		U(0x000000C0)
-#define MODEMR_BOOT_CPU_CR7		U(0x000000C0)
-#define MODEMR_BOOT_CPU_CA57		U(0x00000000)
-#define MODEMR_BOOT_CPU_CA53		U(0x00000040)
-#define MODEMR_BOOT_DEV_MASK		U(0x0000001E)
-#define MODEMR_BOOT_DEV_HYPERFLASH160	U(0x00000004)
-#define MODEMR_BOOT_DEV_HYPERFLASH80	U(0x00000006)
-#define MODEMR_BOOT_DEV_QSPI_FLASH40	U(0x00000008)
-#define MODEMR_BOOT_DEV_QSPI_FLASH80	U(0x0000000C)
-#define MODEMR_BOOT_DEV_EMMC_25X1	U(0x0000000A)
-#define MODEMR_BOOT_DEV_EMMC_50X8	U(0x0000001A)
-#define MODEMR_BOOT_PLL_MASK		U(0x00006000)
-#define MODEMR_BOOT_PLL_SHIFT		U(13)
-/* Memory mapped Generic timer interfaces */
-#define ARM_SYS_CNTCTL_BASE		RCAR_CNTC_BASE
-/* MODEMR PLL masks and bitfield values */
-#define	CHECK_MD13_MD14			U(0x6000)
-#define	MD14_MD13_TYPE_0		U(0x0000)	/* MD14=0 MD13=0 */
-#define	MD14_MD13_TYPE_1		U(0x2000)	/* MD14=0 MD13=1 */
-#define	MD14_MD13_TYPE_2		U(0x4000)	/* MD14=1 MD13=0 */
-#define	MD14_MD13_TYPE_3		U(0x6000)	/* MD14=1 MD13=1 */
-/* Frequency of EXTAL(Hz) */
-#define	EXTAL_MD14_MD13_TYPE_0		U(8333300)	/* MD14=0 MD13=0 */
-#define	EXTAL_MD14_MD13_TYPE_1		U(10000000)	/* MD14=0 MD13=1 */
-#define	EXTAL_MD14_MD13_TYPE_2		U(12500000)	/* MD14=1 MD13=0 */
-#define	EXTAL_MD14_MD13_TYPE_3		U(16666600)	/* MD14=1 MD13=1 */
-#define	EXTAL_SALVATOR_XS		U(8320000)	/* Salvator-XS */
-#define EXTAL_EBISU			U(24000000)	/* Ebisu */
-#define EXTAL_DRAAK			U(24000000)	/* Draak */
-/* CPG write protect registers 	*/
-#define	CPGWPR_PASSWORD			(0x5A5AFFFFU)
-#define	CPGWPCR_PASSWORD		(0xA5A50000U)
-/* CA5x Debug Resource control registers */
-#define	CPG_CA57DBGRCR			(CPG_BASE + 0x2180U)
-#define	CPG_CA53DBGRCR			(CPG_BASE + 0x1180U)
-#define	DBGCPUPREN			((uint32_t)1U << 19U)
-#define	CPG_PLL0CR			(CPG_BASE + 0x00D8U)
-#define	CPG_PLL2CR			(CPG_BASE + 0x002CU)
-#define	CPG_PLL4CR			(CPG_BASE + 0x01F4U)
-#define CPG_CPGWPCR			(CPG_BASE + 0x0904U)
-/* RST Registers */
-#define	RST_BASE			(0xE6160000U)
-#define	RST_WDTRSTCR			(RST_BASE + 0x0054U)
-#define RST_MODEMR			(RST_BASE + 0x0060U)
-#define	WDTRSTCR_PASSWORD		(0xA55A0000U)
-#define	WDTRSTCR_RWDT_RSTMSK		((uint32_t)1U << 0U)
-/* MFIS Registers */
-#define	MFISWPCNTR_PASSWORD		(0xACCE0000U)
-#define	MFISWPCNTR			(0xE6260900U)
-/* IPMMU registers */
-#define IPMMU_MM_BASE			(0xE67B0000U)
-#define IPMMUMM_IMSCTLR			(IPMMU_MM_BASE + 0x0500U)
-#define IPMMUMM_IMAUXCTLR		(IPMMU_MM_BASE + 0x0504U)
-#define IPMMUMM_IMSCTLR_ENABLE		(0xC0000000U)
-#define IPMMUMM_IMAUXCTLR_NMERGE40_BIT	(0x01000000U)
-#define IMSCTLR_DISCACHE		(0xE0000000U)
-#define IPMMU_VP0_BASE			(0xFE990000U)
-#define IPMMUVP0_IMSCTLR		(IPMMU_VP0_BASE + 0x0500U)
-#define IPMMU_VI0_BASE			(0xFEBD0000U)
-#define IPMMUVI0_IMSCTLR		(IPMMU_VI0_BASE + 0x0500U)
-#define IPMMU_VI1_BASE			(0xFEBE0000U)
-#define IPMMUVI1_IMSCTLR		(IPMMU_VI1_BASE + 0x0500U)
-#define IPMMU_PV0_BASE			(0xFD800000U)
-#define IPMMUPV0_IMSCTLR		(IPMMU_PV0_BASE + 0x0500U)
-#define IPMMU_PV1_BASE			(0xFD950000U)
-#define IPMMUPV1_IMSCTLR		(IPMMU_PV1_BASE + 0x0500U)
-#define IPMMU_PV2_BASE			(0xFD960000U)
-#define IPMMUPV2_IMSCTLR		(IPMMU_PV2_BASE + 0x0500U)
-#define IPMMU_PV3_BASE			(0xFD970000U)
-#define IPMMUPV3_IMSCTLR		(IPMMU_PV3_BASE + 0x0500U)
-#define IPMMU_HC_BASE			(0xE6570000U)
-#define IPMMUHC_IMSCTLR			(IPMMU_HC_BASE + 0x0500U)
-#define IPMMU_RT_BASE			(0xFFC80000U)
-#define IPMMURT_IMSCTLR			(IPMMU_RT_BASE + 0x0500U)
-#define IPMMU_MP_BASE			(0xEC670000U)
-#define IPMMUMP_IMSCTLR			(IPMMU_MP_BASE + 0x0500U)
-#define IPMMU_DS0_BASE			(0xE6740000U)
-#define IPMMUDS0_IMSCTLR		(IPMMU_DS0_BASE + 0x0500U)
-#define IPMMU_DS1_BASE			(0xE7740000U)
-#define IPMMUDS1_IMSCTLR		(IPMMU_DS1_BASE + 0x0500U)
-/* ARMREG registers */
-#define	P_ARMREG_SEC_CTRL		(0xE62711F0U)
-#define	P_ARMREG_SEC_CTRL_PROT		(0x00000001U)
-/* MIDR */
-#define MIDR_CA57			(0x0D07U << MIDR_PN_SHIFT)
-#define MIDR_CA53			(0x0D03U << MIDR_PN_SHIFT)
-/* for SuspendToRAM */
-#define GPIO_BASE			(0xE6050000U)
-#define GPIO_INDT1			(GPIO_BASE + 0x100CU)
-#define GPIO_INDT3			(GPIO_BASE + 0x300CU)
-#define GPIO_INDT6			(GPIO_BASE + 0x540CU)
-#define GPIO_OUTDT1			(GPIO_BASE + 0x1008U)
-#define GPIO_OUTDT3			(GPIO_BASE + 0x3008U)
-#define GPIO_OUTDT6			(GPIO_BASE + 0x5408U)
-#define RCAR_COLD_BOOT			(0x00U)
-#define RCAR_WARM_BOOT			(0x01U)
-#if PMIC_ROHM_BD9571 && RCAR_SYSTEM_RESET_KEEPON_DDR
-#define	KEEP10_MAGIC		(0x55U)
-#endif
-/* lossy registers */
-#define LOSSY_PARAMS_BASE 		(0x47FD7000U)
-#define	AXI_DCMPAREACRA0		(0xE6784100U)
-#define	AXI_DCMPAREACRB0		(0xE6784104U)
-#define LOSSY_ENABLE			(0x80000000U)
-#define LOSSY_DISABLE			(0x00000000U)
-#define LOSSY_FMT_YUVPLANAR		(0x00000000U)
-#define LOSSY_FMT_YUV422INTLV		(0x20000000U)
-#define LOSSY_FMT_ARGB8888		(0x40000000U)
-#define	LOSSY_ST_ADDR0			(0x54000000U)
-#define	LOSSY_END_ADDR0			(0x57000000U)
-#define	LOSSY_FMT0			LOSSY_FMT_YUVPLANAR
-#define	LOSSY_ENA_DIS0			LOSSY_ENABLE
-#define	LOSSY_ST_ADDR1			0x0U
-#define	LOSSY_END_ADDR1			0x0U
-#define	LOSSY_FMT1			LOSSY_FMT_ARGB8888
-#define	LOSSY_ENA_DIS1			LOSSY_DISABLE
-#define	LOSSY_ST_ADDR2			0x0U
-#define	LOSSY_END_ADDR2			0x0U
-#define	LOSSY_FMT2			LOSSY_FMT_YUV422INTLV
-#define	LOSSY_ENA_DIS2			LOSSY_DISABLE
-
-#endif /* RCAR_DEF_H */
diff --git a/plat/renesas/rcar/include/rcar_private.h b/plat/renesas/rcar/include/rcar_private.h
deleted file mode 100644
index a76c023..0000000
--- a/plat/renesas/rcar/include/rcar_private.h
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef RCAR_PRIVATE_H
-#define RCAR_PRIVATE_H
-
-#include <platform_def.h>
-
-#include <common/bl_common.h>
-#include <lib/bakery_lock.h>
-#include <lib/el3_runtime/cpu_data.h>
-
-typedef volatile struct mailbox {
-	unsigned long value __aligned(CACHE_WRITEBACK_GRANULE);
-} mailbox_t;
-
-/*
- * This structure represents the superset of information that is passed to
- * BL31 e.g. while passing control to it from BL2 which is bl31_params
- * and bl31_plat_params and its elements
- */
-typedef struct bl2_to_bl31_params_mem {
-	image_info_t bl32_image_info;
-	image_info_t bl33_image_info;
-	entry_point_info_t bl33_ep_info;
-	entry_point_info_t bl32_ep_info;
-} bl2_to_bl31_params_mem_t;
-
-#if USE_COHERENT_MEM
-#define RCAR_INSTANTIATE_LOCK	DEFINE_BAKERY_LOCK(rcar_lock);
-#define rcar_lock_init()	bakery_lock_init(&rcar_lock)
-#define rcar_lock_get()		bakery_lock_get(&rcar_lock)
-#define rcar_lock_release()	bakery_lock_release(&rcar_lock)
-#else
-/*
- * Constants to specify how many bakery locks this platform implements. These
- * are used if the platform chooses not to use coherent memory for bakery lock
- * data structures.
- */
-#define RCAR_MAX_BAKERIES	2
-#define RCAR_PWRC_BAKERY_ID	0
-
-/*
- * Definition of structure which holds platform specific per-cpu data. Currently
- * it holds only the bakery lock information for each cpu. Constants to
- * specify how many bakeries this platform implements and bakery ids are
- * specified in rcar_def.h
- */
-typedef struct rcar_cpu_data {
-	bakery_info_t pcpu_bakery_info[RCAR_MAX_BAKERIES];
-} rcar_cpu_data_t;
-
-#define RCAR_CPU_DATA_LOCK_OFFSET	\
-	__builtin_offsetof(rcar_cpu_data_t, pcpu_bakery_info)
-/*
- * Helper macros for bakery lock api when using the above rcar_cpu_data_t for
- * bakery lock data structures. It assumes that the bakery_info is at the
- * beginning of the platform specific per-cpu data.
- */
-#define rcar_lock_init(_lock_arg)
-
-#define rcar_lock_get(_lock_arg) 					\
-	bakery_lock_get(_lock_arg, 					\
-		CPU_DATA_PLAT_PCPU_OFFSET + RCAR_CPU_DATA_LOCK_OFFSET)
-
-#define rcar_lock_release(_lock_arg)					\
-	bakery_lock_release(_lock_arg,	    				\
-		CPU_DATA_PLAT_PCPU_OFFSET + RCAR_CPU_DATA_LOCK_OFFSET)
-/* Ensure that the size of the RCAR specific per-cpu data structure and the size
- * of the memory allocated in generic per-cpu data for the platform are the same
- */
-CASSERT(PLAT_PCPU_DATA_SIZE == sizeof(rcar_cpu_data_t),
-	rcar_pcpu_data_size_mismatch);
-#endif
-/*
- * Function and variable prototypes
- */
-void rcar_configure_mmu_el3(unsigned long total_base,
-			    unsigned long total_size,
-			    unsigned long ro_start, unsigned long ro_limit
-#if USE_COHERENT_MEM
-			    , unsigned long coh_start, unsigned long coh_limit
-#endif
-    );
-
-void rcar_setup_topology(void);
-void rcar_cci_disable(void);
-void rcar_cci_enable(void);
-void rcar_cci_init(void);
-
-void plat_invalidate_icache(void);
-void plat_cci_disable(void);
-void plat_cci_enable(void);
-void plat_cci_init(void);
-
-void mstpcr_write(uint32_t mstpcr, uint32_t mstpsr, uint32_t target_bit);
-void cpg_write(uintptr_t regadr, uint32_t regval);
-
-void rcar_console_boot_init(void);
-void rcar_console_boot_end(void);
-void rcar_console_runtime_init(void);
-void rcar_console_runtime_end(void);
-
-#endif /* RCAR_PRIVATE_H */
diff --git a/plat/renesas/rcar/include/rcar_version.h b/plat/renesas/rcar/include/rcar_version.h
deleted file mode 100644
index 67cbd71..0000000
--- a/plat/renesas/rcar/include/rcar_version.h
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef RCAR_VERSION_H
-#define RCAR_VERSION_H
-
-#include <arch_helpers.h>
-
-#define VERSION_OF_RENESAS		"2.0.6"
-#define VERSION_OF_RENESAS_MAXLEN	128
-
-extern const uint8_t version_of_renesas[VERSION_OF_RENESAS_MAXLEN];
-
-#endif /* RCAR_VERSION_H */
diff --git a/plat/renesas/rcar/include/registers/cpg_registers.h b/plat/renesas/rcar/include/registers/cpg_registers.h
deleted file mode 100644
index 0d698d9..0000000
--- a/plat/renesas/rcar/include/registers/cpg_registers.h
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef CPG_REGISTERS_H
-#define CPG_REGISTERS_H
-
-/* CPG base address */
-#define	CPG_BASE	(0xE6150000U)
-
-/* CPG system module stop control 2 */
-#define CPG_SMSTPCR2	(CPG_BASE + 0x0138U)
-/* CPG software reset 2 */
-#define CPG_SRCR2	(CPG_BASE + 0x00B0U)
-/* CPG module stop status 2 */
-#define CPG_MSTPSR2	(CPG_BASE + 0x0040U)
-/* CPG write protect */
-#define CPG_CPGWPR	(CPG_BASE + 0x0900U)
-/* CPG write protect control */
-#define CPG_CPGWPCR	(CPG_BASE + 0x0904U)
-/* CPG system module stop control 9 */
-#define CPG_SMSTPCR9    (CPG_BASE + 0x0994U)
-/* CPG module stop status 9 */
-#define CPG_MSTPSR9     (CPG_BASE + 0x09A4U)
-
-/* CPG (SECURITY) registers */
-
-/* Secure Module Stop Control Register 0 */
-#define	SCMSTPCR0	(CPG_BASE + 0x0B20U)
-/* Secure Module Stop Control Register 1 */
-#define	SCMSTPCR1	(CPG_BASE + 0x0B24U)
-/* Secure Module Stop Control Register 2 */
-#define	SCMSTPCR2	(CPG_BASE + 0x0B28U)
-/* Secure Module Stop Control Register 3 */
-#define	SCMSTPCR3	(CPG_BASE + 0x0B2CU)
-/* Secure Module Stop Control Register 4 */
-#define	SCMSTPCR4	(CPG_BASE + 0x0B30U)
-/* Secure Module Stop Control Register 5 */
-#define	SCMSTPCR5	(CPG_BASE + 0x0B34U)
-/* Secure Module Stop Control Register 6 */
-#define	SCMSTPCR6	(CPG_BASE + 0x0B38U)
-/* Secure Module Stop Control Register 7 */
-#define	SCMSTPCR7	(CPG_BASE + 0x0B3CU)
-/* Secure Module Stop Control Register 8 */
-#define	SCMSTPCR8	(CPG_BASE + 0x0B40U)
-/* Secure Module Stop Control Register 9 */
-#define	SCMSTPCR9	(CPG_BASE + 0x0B44U)
-/* Secure Module Stop Control Register 10 */
-#define	SCMSTPCR10	(CPG_BASE + 0x0B48U)
-/* Secure Module Stop Control Register 11 */
-#define	SCMSTPCR11	(CPG_BASE + 0x0B4CU)
-
-/* CPG (SECURITY) registers */
-
-/* Secure Software Reset Access Enable Control Register 0 */
-#define	SCSRSTECR0	(CPG_BASE + 0x0B80U)
-/* Secure Software Reset Access Enable Control Register 1 */
-#define	SCSRSTECR1	(CPG_BASE + 0x0B84U)
-/* Secure Software Reset Access Enable Control Register 2 */
-#define	SCSRSTECR2	(CPG_BASE + 0x0B88U)
-/* Secure Software Reset Access Enable Control Register 3 */
-#define	SCSRSTECR3	(CPG_BASE + 0x0B8CU)
-/* Secure Software Reset Access Enable Control Register 4 */
-#define	SCSRSTECR4	(CPG_BASE + 0x0B90U)
-/* Secure Software Reset Access Enable Control Register 5 */
-#define	SCSRSTECR5	(CPG_BASE + 0x0B94U)
-/* Secure Software Reset Access Enable Control Register 6 */
-#define	SCSRSTECR6	(CPG_BASE + 0x0B98U)
-/* Secure Software Reset Access Enable Control Register 7 */
-#define	SCSRSTECR7	(CPG_BASE + 0x0B9CU)
-/* Secure Software Reset Access Enable Control Register 8 */
-#define	SCSRSTECR8	(CPG_BASE + 0x0BA0U)
-/* Secure Software Reset Access Enable Control Register 9 */
-#define	SCSRSTECR9	(CPG_BASE + 0x0BA4U)
-/* Secure Software Reset Access Enable Control Register 10 */
-#define	SCSRSTECR10	(CPG_BASE + 0x0BA8U)
-/* Secure Software Reset Access Enable Control Register 11 */
-#define	SCSRSTECR11	(CPG_BASE + 0x0BACU)
-
-/* CPG (REALTIME) registers */
-
-/* Realtime Module Stop Control Register 0 */
-#define	RMSTPCR0	(CPG_BASE + 0x0110U)
-/* Realtime Module Stop Control Register 1 */
-#define	RMSTPCR1	(CPG_BASE + 0x0114U)
-/* Realtime Module Stop Control Register 2 */
-#define	RMSTPCR2	(CPG_BASE + 0x0118U)
-/* Realtime Module Stop Control Register 3 */
-#define	RMSTPCR3	(CPG_BASE + 0x011CU)
-/* Realtime Module Stop Control Register 4 */
-#define	RMSTPCR4	(CPG_BASE + 0x0120U)
-/* Realtime Module Stop Control Register 5 */
-#define	RMSTPCR5	(CPG_BASE + 0x0124U)
-/* Realtime Module Stop Control Register 6 */
-#define	RMSTPCR6	(CPG_BASE + 0x0128U)
-/* Realtime Module Stop Control Register 7 */
-#define	RMSTPCR7	(CPG_BASE + 0x012CU)
-/* Realtime Module Stop Control Register 8 */
-#define	RMSTPCR8	(CPG_BASE + 0x0980U)
-/* Realtime Module Stop Control Register 9 */
-#define	RMSTPCR9	(CPG_BASE + 0x0984U)
-/* Realtime Module Stop Control Register 10 */
-#define	RMSTPCR10	(CPG_BASE + 0x0988U)
-/* Realtime Module Stop Control Register 11 */
-#define	RMSTPCR11	(CPG_BASE + 0x098CU)
-
-/* CPG (SYSTEM) registers */
-
-/* System Module Stop Control Register 0 */
-#define	SMSTPCR0	(CPG_BASE + 0x0130U)
-/* System Module Stop Control Register 1 */
-#define	SMSTPCR1	(CPG_BASE + 0x0134U)
-/* System Module Stop Control Register 2 */
-#define	SMSTPCR2	(CPG_BASE + 0x0138U)
-/* System Module Stop Control Register 3 */
-#define	SMSTPCR3	(CPG_BASE + 0x013CU)
-/* System Module Stop Control Register 4 */
-#define	SMSTPCR4	(CPG_BASE + 0x0140U)
-/* System Module Stop Control Register 5 */
-#define	SMSTPCR5	(CPG_BASE + 0x0144U)
-/* System Module Stop Control Register 6 */
-#define	SMSTPCR6	(CPG_BASE + 0x0148U)
-/* System Module Stop Control Register 7 */
-#define	SMSTPCR7	(CPG_BASE + 0x014CU)
-/* System Module Stop Control Register 8 */
-#define	SMSTPCR8	(CPG_BASE + 0x0990U)
-/* System Module Stop Control Register 9 */
-#define	SMSTPCR9	(CPG_BASE + 0x0994U)
-/* System Module Stop Control Register 10 */
-#define	SMSTPCR10	(CPG_BASE + 0x0998U)
-/* System Module Stop Control Register 11 */
-#define	SMSTPCR11	(CPG_BASE + 0x099CU)
-
-#endif /* CPG_REGISTERS_H */
diff --git a/plat/renesas/rcar/include/registers/lifec_registers.h b/plat/renesas/rcar/include/registers/lifec_registers.h
deleted file mode 100644
index de78760..0000000
--- a/plat/renesas/rcar/include/registers/lifec_registers.h
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#ifndef LIFEC_REGISTERS_H
-#define LIFEC_REGISTERS_H
-
-#define	LIFEC_SEC_BASE	(0xE6110000U)
-
-#define	SEC_SRC		(LIFEC_SEC_BASE + 0x0008U)
-#define	SEC_SEL0	(LIFEC_SEC_BASE + 0x0030U)
-#define	SEC_SEL1	(LIFEC_SEC_BASE + 0x0034U)
-#define	SEC_SEL2	(LIFEC_SEC_BASE + 0x0038U)
-#define	SEC_SEL3	(LIFEC_SEC_BASE + 0x003CU)
-#define	SEC_SEL4	(LIFEC_SEC_BASE + 0x0058U)
-#define	SEC_SEL5	(LIFEC_SEC_BASE + 0x005CU)
-#define SEC_SEL6	(LIFEC_SEC_BASE + 0x0060U)
-#define	SEC_SEL7	(LIFEC_SEC_BASE + 0x0064U)
-#define	SEC_SEL8	(LIFEC_SEC_BASE + 0x0068U)
-#define	SEC_SEL9	(LIFEC_SEC_BASE + 0x006CU)
-#define	SEC_SEL10	(LIFEC_SEC_BASE + 0x0070U)
-#define	SEC_SEL11	(LIFEC_SEC_BASE + 0x0074U)
-#define	SEC_SEL12	(LIFEC_SEC_BASE + 0x0078U)
-#define	SEC_SEL13	(LIFEC_SEC_BASE + 0x007CU)
-#define	SEC_SEL14	(LIFEC_SEC_BASE + 0x0080U)
-#define	SEC_SEL15	(LIFEC_SEC_BASE + 0x0084U)
-#define	SEC_GRP0CR0	(LIFEC_SEC_BASE + 0x0138U)
-#define	SEC_GRP1CR0	(LIFEC_SEC_BASE + 0x013CU)
-#define	SEC_GRP0CR1	(LIFEC_SEC_BASE + 0x0140U)
-#define	SEC_GRP1CR1	(LIFEC_SEC_BASE + 0x0144U)
-#define	SEC_GRP0CR2	(LIFEC_SEC_BASE + 0x0148U)
-#define	SEC_GRP1CR2	(LIFEC_SEC_BASE + 0x014CU)
-#define	SEC_GRP0CR3	(LIFEC_SEC_BASE + 0x0150U)
-#define	SEC_GRP1CR3	(LIFEC_SEC_BASE + 0x0154U)
-#define	SEC_GRP0COND0	(LIFEC_SEC_BASE + 0x0158U)
-#define	SEC_GRP1COND0	(LIFEC_SEC_BASE + 0x015CU)
-#define	SEC_GRP0COND1	(LIFEC_SEC_BASE + 0x0160U)
-#define	SEC_GRP1COND1	(LIFEC_SEC_BASE + 0x0164U)
-#define	SEC_GRP0COND2	(LIFEC_SEC_BASE + 0x0168U)
-#define	SEC_GRP1COND2	(LIFEC_SEC_BASE + 0x016CU)
-#define	SEC_GRP0COND3	(LIFEC_SEC_BASE + 0x0170U)
-#define	SEC_GRP1COND3	(LIFEC_SEC_BASE + 0x0174U)
-#define	SEC_GRP0COND4	(LIFEC_SEC_BASE + 0x0178U)
-#define	SEC_GRP1COND4	(LIFEC_SEC_BASE + 0x017CU)
-#define	SEC_GRP0COND5	(LIFEC_SEC_BASE + 0x0180U)
-#define	SEC_GRP1COND5	(LIFEC_SEC_BASE + 0x0184U)
-#define	SEC_GRP0COND6	(LIFEC_SEC_BASE + 0x0188U)
-#define	SEC_GRP1COND6	(LIFEC_SEC_BASE + 0x018CU)
-#define	SEC_GRP0COND7	(LIFEC_SEC_BASE + 0x0190U)
-#define	SEC_GRP1COND7	(LIFEC_SEC_BASE + 0x0194U)
-#define	SEC_GRP0COND8	(LIFEC_SEC_BASE + 0x0198U)
-#define	SEC_GRP1COND8	(LIFEC_SEC_BASE + 0x019CU)
-#define	SEC_GRP0COND9	(LIFEC_SEC_BASE + 0x01A0U)
-#define	SEC_GRP1COND9	(LIFEC_SEC_BASE + 0x01A4U)
-#define	SEC_GRP0COND10	(LIFEC_SEC_BASE + 0x01A8U)
-#define	SEC_GRP1COND10	(LIFEC_SEC_BASE + 0x01ACU)
-#define	SEC_GRP0COND11	(LIFEC_SEC_BASE + 0x01B0U)
-#define	SEC_GRP1COND11	(LIFEC_SEC_BASE + 0x01B4U)
-#define	SEC_GRP0COND12	(LIFEC_SEC_BASE + 0x01B8U)
-#define	SEC_GRP1COND12	(LIFEC_SEC_BASE + 0x01BCU)
-#define	SEC_GRP0COND13	(LIFEC_SEC_BASE + 0x01C0U)
-#define	SEC_GRP1COND13	(LIFEC_SEC_BASE + 0x01C4U)
-#define	SEC_GRP0COND14	(LIFEC_SEC_BASE + 0x01C8U)
-#define	SEC_GRP1COND14	(LIFEC_SEC_BASE + 0x01CCU)
-#define	SEC_GRP0COND15	(LIFEC_SEC_BASE + 0x01D0U)
-#define	SEC_GRP1COND15	(LIFEC_SEC_BASE + 0x01D4U)
-#define	SEC_READONLY0	(LIFEC_SEC_BASE + 0x01D8U)
-#define	SEC_READONLY1	(LIFEC_SEC_BASE + 0x01DCU)
-#define	SEC_READONLY2	(LIFEC_SEC_BASE + 0x01E0U)
-#define	SEC_READONLY3	(LIFEC_SEC_BASE + 0x01E4U)
-#define	SEC_READONLY4	(LIFEC_SEC_BASE + 0x01E8U)
-#define	SEC_READONLY5	(LIFEC_SEC_BASE + 0x01ECU)
-#define	SEC_READONLY6	(LIFEC_SEC_BASE + 0x01F0U)
-#define	SEC_READONLY7	(LIFEC_SEC_BASE + 0x01F4U)
-#define	SEC_READONLY8	(LIFEC_SEC_BASE + 0x01F8U)
-#define	SEC_READONLY9	(LIFEC_SEC_BASE + 0x01FCU)
-#define	SEC_READONLY10	(LIFEC_SEC_BASE + 0x0200U)
-#define	SEC_READONLY11	(LIFEC_SEC_BASE + 0x0204U)
-#define	SEC_READONLY12	(LIFEC_SEC_BASE + 0x0208U)
-#define	SEC_READONLY13	(LIFEC_SEC_BASE + 0x020CU)
-#define	SEC_READONLY14	(LIFEC_SEC_BASE + 0x0210U)
-#define	SEC_READONLY15	(LIFEC_SEC_BASE + 0x0214U)
-
-#define	LIFEC_SAFE_BASE	(0xE6120000U)
-#define	SAFE_GRP0CR0	(LIFEC_SAFE_BASE + 0x0138U)
-#define	SAFE_GRP1CR0	(LIFEC_SAFE_BASE + 0x013CU)
-#define	SAFE_GRP0CR1	(LIFEC_SAFE_BASE + 0x0140U)
-#define	SAFE_GRP1CR1	(LIFEC_SAFE_BASE + 0x0144U)
-#define	SAFE_GRP0CR2	(LIFEC_SAFE_BASE + 0x0148U)
-#define	SAFE_GRP1CR2	(LIFEC_SAFE_BASE + 0x014CU)
-#define	SAFE_GRP0CR3	(LIFEC_SAFE_BASE + 0x0150U)
-#define	SAFE_GRP1CR3	(LIFEC_SAFE_BASE + 0x0154U)
-#define	SAFE_GRP0COND0	(LIFEC_SAFE_BASE + 0x0158U)
-#define	SAFE_GRP1COND0	(LIFEC_SAFE_BASE + 0x015CU)
-#define	SAFE_GRP0COND1	(LIFEC_SAFE_BASE + 0x0160U)
-#define	SAFE_GRP1COND1	(LIFEC_SAFE_BASE + 0x0164U)
-#define	SAFE_GRP0COND2	(LIFEC_SAFE_BASE + 0x0168U)
-#define	SAFE_GRP1COND2	(LIFEC_SAFE_BASE + 0x016CU)
-#define	SAFE_GRP0COND3	(LIFEC_SAFE_BASE + 0x0170U)
-#define	SAFE_GRP1COND3	(LIFEC_SAFE_BASE + 0x0174U)
-#define	SAFE_GRP0COND4	(LIFEC_SAFE_BASE + 0x0178U)
-#define	SAFE_GRP1COND4	(LIFEC_SAFE_BASE + 0x017CU)
-#define	SAFE_GRP0COND5	(LIFEC_SAFE_BASE + 0x0180U)
-#define	SAFE_GRP1COND5	(LIFEC_SAFE_BASE + 0x0184U)
-#define	SAFE_GRP0COND6	(LIFEC_SAFE_BASE + 0x0188U)
-#define	SAFE_GRP1COND6	(LIFEC_SAFE_BASE + 0x018CU)
-#define	SAFE_GRP0COND7	(LIFEC_SAFE_BASE + 0x0190U)
-#define	SAFE_GRP1COND7	(LIFEC_SAFE_BASE + 0x0194U)
-#define	SAFE_GRP0COND8	(LIFEC_SAFE_BASE + 0x0198U)
-#define	SAFE_GRP1COND8	(LIFEC_SAFE_BASE + 0x019CU)
-#define	SAFE_GRP0COND9	(LIFEC_SAFE_BASE + 0x01A0U)
-#define	SAFE_GRP1COND9	(LIFEC_SAFE_BASE + 0x01A4U)
-#define	SAFE_GRP0COND10	(LIFEC_SAFE_BASE + 0x01A8U)
-#define	SAFE_GRP1COND10	(LIFEC_SAFE_BASE + 0x01ACU)
-#define	SAFE_GRP0COND11	(LIFEC_SAFE_BASE + 0x01B0U)
-#define	SAFE_GRP1COND11	(LIFEC_SAFE_BASE + 0x01B4U)
-#define	SAFE_GRP0COND12	(LIFEC_SAFE_BASE + 0x01B8U)
-#define	SAFE_GRP1COND12	(LIFEC_SAFE_BASE + 0x01BCU)
-#define	SAFE_GRP0COND13	(LIFEC_SAFE_BASE + 0x01C0U)
-#define	SAFE_GRP1COND13	(LIFEC_SAFE_BASE + 0x01C4U)
-#define	SAFE_GRP0COND14	(LIFEC_SAFE_BASE + 0x01C8U)
-#define	SAFE_GRP1COND14	(LIFEC_SAFE_BASE + 0x01CCU)
-#define	SAFE_GRP0COND15	(LIFEC_SAFE_BASE + 0x01D0U)
-#define	SAFE_GRP1COND15	(LIFEC_SAFE_BASE + 0x01D4U)
-#define	SAFE_READONLY0	(LIFEC_SAFE_BASE + 0x01D8U)
-#define	SAFE_READONLY1	(LIFEC_SAFE_BASE + 0x01DCU)
-#define	SAFE_READONLY2	(LIFEC_SAFE_BASE + 0x01E0U)
-#define	SAFE_READONLY3	(LIFEC_SAFE_BASE + 0x01E4U)
-#define	SAFE_READONLY4	(LIFEC_SAFE_BASE + 0x01E8U)
-#define	SAFE_READONLY5	(LIFEC_SAFE_BASE + 0x01ECU)
-#define	SAFE_READONLY6	(LIFEC_SAFE_BASE + 0x01F0U)
-#define	SAFE_READONLY7	(LIFEC_SAFE_BASE + 0x01F4U)
-#define	SAFE_READONLY8	(LIFEC_SAFE_BASE + 0x01F8U)
-#define	SAFE_READONLY9	(LIFEC_SAFE_BASE + 0x01FCU)
-#define	SAFE_READONLY10	(LIFEC_SAFE_BASE + 0x0200U)
-#define	SAFE_READONLY11	(LIFEC_SAFE_BASE + 0x0204U)
-#define	SAFE_READONLY12	(LIFEC_SAFE_BASE + 0x0208U)
-#define	SAFE_READONLY13	(LIFEC_SAFE_BASE + 0x020CU)
-#define	SAFE_READONLY14	(LIFEC_SAFE_BASE + 0x0210U)
-#define	SAFE_READONLY15	(LIFEC_SAFE_BASE + 0x0214U)
-
-#endif /* LIFEC_REGISTERS_H */
diff --git a/plat/renesas/rcar/plat_pm.c b/plat/renesas/rcar/plat_pm.c
deleted file mode 100644
index 6fc47b9..0000000
--- a/plat/renesas/rcar/plat_pm.c
+++ /dev/null
@@ -1,309 +0,0 @@
-/*
- * Copyright (c) 2015-2020, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <errno.h>
-
-#include <platform_def.h>
-
-#include <arch_helpers.h>
-#include <common/bl_common.h>
-#include <common/debug.h>
-#include <drivers/arm/cci.h>
-#include <drivers/arm/gicv2.h>
-#include <lib/bakery_lock.h>
-#include <lib/mmio.h>
-#include <lib/psci/psci.h>
-#include <plat/common/platform.h>
-
-#include "iic_dvfs.h"
-#include "pwrc.h"
-#include "rcar_def.h"
-#include "rcar_private.h"
-#include "ulcb_cpld.h"
-
-#define	DVFS_SET_VID_0V		(0x00)
-#define	P_ALL_OFF		(0x80)
-#define	KEEPON_DDR1C		(0x08)
-#define	KEEPON_DDR0C		(0x04)
-#define	KEEPON_DDR1		(0x02)
-#define	KEEPON_DDR0		(0x01)
-
-#define SYSTEM_PWR_STATE(s)	((s)->pwr_domain_state[PLAT_MAX_PWR_LVL])
-#define CLUSTER_PWR_STATE(s)	((s)->pwr_domain_state[MPIDR_AFFLVL1])
-#define CORE_PWR_STATE(s)	((s)->pwr_domain_state[MPIDR_AFFLVL0])
-
-extern void rcar_pwrc_restore_generic_timer(uint64_t *stack);
-extern void plat_rcar_gic_driver_init(void);
-extern void plat_rcar_gic_init(void);
-extern u_register_t rcar_boot_mpidr;
-
-static uintptr_t rcar_sec_entrypoint;
-
-static void rcar_program_mailbox(uint64_t mpidr, uint64_t address)
-{
-	mailbox_t *rcar_mboxes = (mailbox_t *) MBOX_BASE;
-	uint64_t linear_id = plat_core_pos_by_mpidr(mpidr);
-	unsigned long range;
-
-	rcar_mboxes[linear_id].value = address;
-	range = (unsigned long)&rcar_mboxes[linear_id];
-
-	flush_dcache_range(range, sizeof(range));
-}
-
-static void rcar_cpu_standby(plat_local_state_t cpu_state)
-{
-	u_register_t scr_el3 = read_scr_el3();
-
-	write_scr_el3(scr_el3 | SCR_IRQ_BIT);
-	dsb();
-	wfi();
-	write_scr_el3(scr_el3);
-}
-
-static int rcar_pwr_domain_on(u_register_t mpidr)
-{
-	rcar_program_mailbox(mpidr, rcar_sec_entrypoint);
-	rcar_pwrc_cpuon(mpidr);
-
-	return PSCI_E_SUCCESS;
-}
-
-static void rcar_pwr_domain_on_finish(const psci_power_state_t *target_state)
-{
-	uint32_t cluster_type = rcar_pwrc_get_cluster();
-	unsigned long mpidr = read_mpidr_el1();
-
-	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE)
-		if (cluster_type == RCAR_CLUSTER_A53A57)
-			plat_cci_enable();
-
-	rcar_pwrc_disable_interrupt_wakeup(mpidr);
-	rcar_program_mailbox(mpidr, 0);
-
-	gicv2_cpuif_enable();
-	gicv2_pcpu_distif_init();
-}
-
-static void rcar_pwr_domain_off(const psci_power_state_t *target_state)
-{
-#if RCAR_LSI != RCAR_D3
-	uint32_t cluster_type = rcar_pwrc_get_cluster();
-#endif
-	unsigned long mpidr = read_mpidr_el1();
-
-	gicv2_cpuif_disable();
-	rcar_pwrc_cpuoff(mpidr);
-
-#if RCAR_LSI != RCAR_D3
-	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE) {
-		if (cluster_type == RCAR_CLUSTER_A53A57)
-			plat_cci_disable();
-
-		rcar_pwrc_clusteroff(mpidr);
-	}
-#endif
-}
-
-static void rcar_pwr_domain_suspend(const psci_power_state_t *target_state)
-{
-	uint32_t cluster_type = rcar_pwrc_get_cluster();
-	unsigned long mpidr = read_mpidr_el1();
-
-	if (CORE_PWR_STATE(target_state) != PLAT_MAX_OFF_STATE)
-		return;
-
-	rcar_program_mailbox(mpidr, rcar_sec_entrypoint);
-	rcar_pwrc_enable_interrupt_wakeup(mpidr);
-	gicv2_cpuif_disable();
-	rcar_pwrc_cpuoff(mpidr);
-
-	if (CLUSTER_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE) {
-		if (cluster_type == RCAR_CLUSTER_A53A57)
-			plat_cci_disable();
-
-		rcar_pwrc_clusteroff(mpidr);
-	}
-
-#if RCAR_SYSTEM_SUSPEND
-	if (SYSTEM_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE)
-		rcar_pwrc_suspend_to_ram();
-#endif
-}
-
-static void rcar_pwr_domain_suspend_finish(const psci_power_state_t
-					   *target_state)
-{
-	uint32_t cluster_type = rcar_pwrc_get_cluster();
-
-	if (SYSTEM_PWR_STATE(target_state) != PLAT_MAX_OFF_STATE)
-		goto finish;
-
-	plat_rcar_gic_driver_init();
-	plat_rcar_gic_init();
-
-	if (cluster_type == RCAR_CLUSTER_A53A57)
-		plat_cci_init();
-
-	rcar_pwrc_restore_timer_state();
-	rcar_pwrc_setup();
-	rcar_pwrc_code_copy_to_system_ram();
-
-#if RCAR_SYSTEM_SUSPEND
-	rcar_pwrc_init_suspend_to_ram();
-#endif
-finish:
-	rcar_pwr_domain_on_finish(target_state);
-}
-
-static void __dead2 rcar_system_off(void)
-{
-#if PMIC_ROHM_BD9571
-#if PMIC_LEVEL_MODE
-	if (rcar_iic_dvfs_send(PMIC, DVFS_SET_VID, DVFS_SET_VID_0V))
-		ERROR("BL3-1:Failed the SYSTEM-OFF.\n");
-#else
-	if (rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, P_ALL_OFF))
-		ERROR("BL3-1:Failed the SYSTEM-RESET.\n");
-#endif
-#else
-	uint64_t cpu = read_mpidr_el1() & 0x0000ffff;
-	int32_t rtn_on;
-
-	rtn_on = rcar_pwrc_cpu_on_check(cpu);
-
-	if (cpu == rcar_boot_mpidr)
-		panic();
-
-	if (rtn_on)
-		panic();
-
-	rcar_pwrc_cpuoff(cpu);
-	rcar_pwrc_clusteroff(cpu);
-
-#endif /* PMIC_ROHM_BD9571 */
-	wfi();
-	ERROR("RCAR System Off: operation not handled.\n");
-	panic();
-}
-
-static void __dead2 rcar_system_reset(void)
-{
-#if PMIC_ROHM_BD9571
-#if PMIC_LEVEL_MODE
-#if RCAR_SYSTEM_RESET_KEEPON_DDR
-	uint8_t mode;
-	int32_t error;
-
-	error = rcar_iic_dvfs_send(PMIC, REG_KEEP10, KEEP10_MAGIC);
-	if (error) {
-		ERROR("Failed send KEEP10 magic ret=%d \n", error);
-		goto done;
-	}
-
-	error = rcar_iic_dvfs_receive(PMIC, BKUP_MODE_CNT, &mode);
-	if (error) {
-		ERROR("Failed recieve BKUP_Mode_Cnt ret=%d \n", error);
-		goto done;
-	}
-
-	mode |= KEEPON_DDR1C | KEEPON_DDR0C | KEEPON_DDR1 | KEEPON_DDR0;
-	error = rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, mode);
-	if (error) {
-		ERROR("Failed send KEEPON_DDRx ret=%d \n", error);
-		goto done;
-	}
-
-	rcar_pwrc_set_suspend_to_ram();
-done:
-#else
-	if (rcar_iic_dvfs_send(PMIC, BKUP_MODE_CNT, P_ALL_OFF))
-		ERROR("BL3-1:Failed the SYSTEM-RESET.\n");
-#endif
-#else
-#if (RCAR_GEN3_ULCB == 1)
-	rcar_cpld_reset_cpu();
-#endif
-#endif
-#else
-	rcar_pwrc_system_reset();
-#endif
-	wfi();
-
-	ERROR("RCAR System Reset: operation not handled.\n");
-	panic();
-}
-
-static int rcar_validate_power_state(unsigned int power_state,
-				    psci_power_state_t *req_state)
-{
-	unsigned int pwr_lvl = psci_get_pstate_pwrlvl(power_state);
-	unsigned int pstate = psci_get_pstate_type(power_state);
-	uint32_t i;
-
-	if (pstate == PSTATE_TYPE_STANDBY) {
-		if (pwr_lvl != MPIDR_AFFLVL0)
-			return PSCI_E_INVALID_PARAMS;
-
-		req_state->pwr_domain_state[MPIDR_AFFLVL0] = PLAT_MAX_RET_STATE;
-	} else {
-		for (i = MPIDR_AFFLVL0; i <= pwr_lvl; i++)
-			req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
-	}
-
-	if (psci_get_pstate_id(power_state))
-		return PSCI_E_INVALID_PARAMS;
-
-	return PSCI_E_SUCCESS;
-}
-
-#if RCAR_SYSTEM_SUSPEND
-static void rcar_get_sys_suspend_power_state(psci_power_state_t *req_state)
-{
-	unsigned long mpidr = read_mpidr_el1() & 0x0000ffffU;
-	int i;
-
-	if (mpidr != rcar_boot_mpidr)
-		goto deny;
-
-	for (i = MPIDR_AFFLVL0; i <= PLAT_MAX_PWR_LVL; i++)
-		req_state->pwr_domain_state[i] = PLAT_MAX_OFF_STATE;
-
-	return;
-deny:
-	/* deny system suspend entry */
-	req_state->pwr_domain_state[PLAT_MAX_PWR_LVL] = PSCI_LOCAL_STATE_RUN;
-	for (i = MPIDR_AFFLVL0; i < PLAT_MAX_PWR_LVL; i++)
-		req_state->pwr_domain_state[i] = PLAT_MAX_RET_STATE;
-}
-#endif
-
-static const plat_psci_ops_t rcar_plat_psci_ops = {
-	.cpu_standby			= rcar_cpu_standby,
-	.pwr_domain_on			= rcar_pwr_domain_on,
-	.pwr_domain_off			= rcar_pwr_domain_off,
-	.pwr_domain_suspend		= rcar_pwr_domain_suspend,
-	.pwr_domain_on_finish		= rcar_pwr_domain_on_finish,
-	.pwr_domain_suspend_finish	= rcar_pwr_domain_suspend_finish,
-	.system_off			= rcar_system_off,
-	.system_reset			= rcar_system_reset,
-	.validate_power_state		= rcar_validate_power_state,
-#if RCAR_SYSTEM_SUSPEND
-	.get_sys_suspend_power_state 	= rcar_get_sys_suspend_power_state,
-#endif
-};
-
-int plat_setup_psci_ops(uintptr_t sec_entrypoint, const plat_psci_ops_t **psci_ops)
-{
-	*psci_ops = &rcar_plat_psci_ops;
-	rcar_sec_entrypoint = sec_entrypoint;
-
-#if RCAR_SYSTEM_SUSPEND
-	rcar_pwrc_init_suspend_to_ram();
-#endif
-	return 0;
-}
-
diff --git a/plat/renesas/rcar/plat_storage.c b/plat/renesas/rcar/plat_storage.c
deleted file mode 100644
index 05e3d9f..0000000
--- a/plat/renesas/rcar/plat_storage.c
+++ /dev/null
@@ -1,423 +0,0 @@
-/*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <string.h>
-
-#include <platform_def.h>
-
-#include <common/debug.h>
-#include <drivers/io/io_driver.h>
-#include <drivers/io/io_storage.h>
-#include <drivers/io/io_semihosting.h>
-
-#include "io_common.h"
-#include "io_rcar.h"
-#include "io_memdrv.h"
-#include "io_emmcdrv.h"
-#include "io_private.h"
-
-static uintptr_t emmcdrv_dev_handle;
-static uintptr_t memdrv_dev_handle;
-static uintptr_t rcar_dev_handle;
-
-static uintptr_t boot_io_drv_id;
-
-static const io_block_spec_t rcar_block_spec = {
-	.offset = FLASH0_BASE,
-	.length = FLASH0_SIZE
-};
-
-static const io_block_spec_t bl2_file_spec = {
-	.offset = BL2_IMAGE_ID,
-};
-
-static const io_block_spec_t bl31_file_spec = {
-	.offset = BL31_IMAGE_ID,
-};
-
-static const io_block_spec_t bl32_file_spec = {
-	.offset = BL32_IMAGE_ID,
-};
-
-static const io_block_spec_t bl33_file_spec = {
-	.offset = BL33_IMAGE_ID,
-};
-
-static const io_block_spec_t bl332_file_spec = {
-	.offset = BL332_IMAGE_ID,
-};
-
-static const io_block_spec_t bl333_file_spec = {
-	.offset = BL333_IMAGE_ID,
-};
-
-static const io_block_spec_t bl334_file_spec = {
-	.offset = BL334_IMAGE_ID,
-};
-
-static const io_block_spec_t bl335_file_spec = {
-	.offset = BL335_IMAGE_ID,
-};
-
-static const io_block_spec_t bl336_file_spec = {
-	.offset = BL336_IMAGE_ID,
-};
-
-static const io_block_spec_t bl337_file_spec = {
-	.offset = BL337_IMAGE_ID,
-};
-
-static const io_block_spec_t bl338_file_spec = {
-	.offset = BL338_IMAGE_ID,
-};
-
-#if TRUSTED_BOARD_BOOT
-static const io_block_spec_t trusted_key_cert_file_spec = {
-	.offset = TRUSTED_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl31_key_cert_file_spec = {
-	.offset = SOC_FW_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl32_key_cert_file_spec = {
-	.offset = TRUSTED_OS_FW_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl33_key_cert_file_spec = {
-	.offset = NON_TRUSTED_FW_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl332_key_cert_file_spec = {
-	.offset = BL332_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl333_key_cert_file_spec = {
-	.offset = BL333_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl334_key_cert_file_spec = {
-	.offset = BL334_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl335_key_cert_file_spec = {
-	.offset = BL335_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl336_key_cert_file_spec = {
-	.offset = BL336_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl337_key_cert_file_spec = {
-	.offset = BL337_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl338_key_cert_file_spec = {
-	.offset = BL338_KEY_CERT_ID,
-};
-
-static const io_block_spec_t bl31_cert_file_spec = {
-	.offset = SOC_FW_CONTENT_CERT_ID,
-};
-
-static const io_block_spec_t bl32_cert_file_spec = {
-	.offset = TRUSTED_OS_FW_CONTENT_CERT_ID,
-};
-
-static const io_block_spec_t bl33_cert_file_spec = {
-	.offset = NON_TRUSTED_FW_CONTENT_CERT_ID,
-};
-
-static const io_block_spec_t bl332_cert_file_spec = {
-	.offset = BL332_CERT_ID,
-};
-
-static const io_block_spec_t bl333_cert_file_spec = {
-	.offset = BL333_CERT_ID,
-};
-
-static const io_block_spec_t bl334_cert_file_spec = {
-	.offset = BL334_CERT_ID,
-};
-
-static const io_block_spec_t bl335_cert_file_spec = {
-	.offset = BL335_CERT_ID,
-};
-
-static const io_block_spec_t bl336_cert_file_spec = {
-	.offset = BL336_CERT_ID,
-};
-
-static const io_block_spec_t bl337_cert_file_spec = {
-	.offset = BL337_CERT_ID,
-};
-
-static const io_block_spec_t bl338_cert_file_spec = {
-	.offset = BL338_CERT_ID,
-};
-#endif
-
-static int32_t open_emmcdrv(const uintptr_t spec);
-static int32_t open_memmap(const uintptr_t spec);
-static int32_t open_rcar(const uintptr_t spec);
-
-struct plat_io_policy {
-	uintptr_t *dev_handle;
-	uintptr_t image_spec;
-	 int32_t(*check) (const uintptr_t spec);
-};
-
-static const struct plat_io_policy policies[] = {
-	[FIP_IMAGE_ID] = {
-			  &memdrv_dev_handle,
-			  (uintptr_t) &rcar_block_spec,
-			  &open_memmap},
-	[BL2_IMAGE_ID] = {
-			  &rcar_dev_handle,
-			  (uintptr_t) &bl2_file_spec,
-			  &open_rcar},
-	[BL31_IMAGE_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl31_file_spec,
-			   &open_rcar},
-	[BL32_IMAGE_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl32_file_spec,
-			   &open_rcar},
-	[BL33_IMAGE_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl33_file_spec,
-			   &open_rcar},
-	[BL332_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl332_file_spec,
-			    &open_rcar},
-	[BL333_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl333_file_spec,
-			    &open_rcar},
-	[BL334_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl334_file_spec,
-			    &open_rcar},
-	[BL335_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl335_file_spec,
-			    &open_rcar},
-	[BL336_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl336_file_spec,
-			    &open_rcar},
-	[BL337_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl337_file_spec,
-			    &open_rcar},
-	[BL338_IMAGE_ID] = {
-			    &rcar_dev_handle,
-			    (uintptr_t) &bl338_file_spec,
-			    &open_rcar},
-#if TRUSTED_BOARD_BOOT
-	[TRUSTED_KEY_CERT_ID] = {
-				 &rcar_dev_handle,
-				 (uintptr_t) &trusted_key_cert_file_spec,
-				 &open_rcar},
-	[SOC_FW_KEY_CERT_ID] = {
-				&rcar_dev_handle,
-				(uintptr_t) &bl31_key_cert_file_spec,
-				&open_rcar},
-	[TRUSTED_OS_FW_KEY_CERT_ID] = {
-				       &rcar_dev_handle,
-				       (uintptr_t) &bl32_key_cert_file_spec,
-				       &open_rcar},
-	[NON_TRUSTED_FW_KEY_CERT_ID] = {
-					&rcar_dev_handle,
-					(uintptr_t) &bl33_key_cert_file_spec,
-					&open_rcar},
-	[BL332_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl332_key_cert_file_spec,
-			       &open_rcar},
-	[BL333_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl333_key_cert_file_spec,
-			       &open_rcar},
-	[BL334_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl334_key_cert_file_spec,
-			       &open_rcar},
-	[BL335_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl335_key_cert_file_spec,
-			       &open_rcar},
-	[BL336_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl336_key_cert_file_spec,
-			       &open_rcar},
-	[BL337_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl337_key_cert_file_spec,
-			       &open_rcar},
-	[BL338_KEY_CERT_ID] = {
-			       &rcar_dev_handle,
-			       (uintptr_t) &bl338_key_cert_file_spec,
-			       &open_rcar},
-	[SOC_FW_CONTENT_CERT_ID] = {
-				    &rcar_dev_handle,
-				    (uintptr_t) &bl31_cert_file_spec,
-				    &open_rcar},
-	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
-					   &rcar_dev_handle,
-					   (uintptr_t) &bl32_cert_file_spec,
-					   &open_rcar},
-	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
-					    &rcar_dev_handle,
-					    (uintptr_t) &bl33_cert_file_spec,
-					    &open_rcar},
-	[BL332_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl332_cert_file_spec,
-			   &open_rcar},
-	[BL333_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl333_cert_file_spec,
-			   &open_rcar},
-	[BL334_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl334_cert_file_spec,
-			   &open_rcar},
-	[BL335_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl335_cert_file_spec,
-			   &open_rcar},
-	[BL336_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl336_cert_file_spec,
-			   &open_rcar},
-	[BL337_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl337_cert_file_spec,
-			   &open_rcar},
-	[BL338_CERT_ID] = {
-			   &rcar_dev_handle,
-			   (uintptr_t) &bl338_cert_file_spec,
-			   &open_rcar}, {
-#else
-				   {
-#endif
-					 0, 0, 0}
-};
-
-static io_drv_spec_t io_drv_spec_memdrv = {
-	FLASH0_BASE,
-	FLASH0_SIZE,
-	0,
-};
-
-static io_drv_spec_t io_drv_spec_emmcdrv = {
-	0,
-	0,
-	0,
-};
-
-static struct plat_io_policy drv_policies[]
-    __attribute__ ((section(".data"))) = {
-	/* FLASH_DEV_ID */
-	{
-	&memdrv_dev_handle,
-		    (uintptr_t) &io_drv_spec_memdrv, &open_memmap,},
-	    /* EMMC_DEV_ID */
-	{
-	&emmcdrv_dev_handle,
-		    (uintptr_t) &io_drv_spec_emmcdrv, &open_emmcdrv,}
-};
-
-static int32_t open_rcar(const uintptr_t spec)
-{
-	return io_dev_init(rcar_dev_handle, boot_io_drv_id);
-}
-
-static int32_t open_memmap(const uintptr_t spec)
-{
-	uintptr_t handle;
-	int32_t result;
-
-	result = io_dev_init(memdrv_dev_handle, 0);
-	if (result != IO_SUCCESS)
-		return result;
-
-	result = io_open(memdrv_dev_handle, spec, &handle);
-	if (result == IO_SUCCESS)
-		io_close(handle);
-
-	return result;
-}
-
-static int32_t open_emmcdrv(const uintptr_t spec)
-{
-	return io_dev_init(emmcdrv_dev_handle, 0);
-}
-
-void rcar_io_setup(void)
-{
-	const io_dev_connector_t *memmap;
-	const io_dev_connector_t *rcar;
-
-	boot_io_drv_id = FLASH_DEV_ID;
-
-	rcar_register_io_dev(&rcar);
-	rcar_register_io_dev_memdrv(&memmap);
-	io_dev_open(rcar, 0, &rcar_dev_handle);
-	io_dev_open(memmap, 0, &memdrv_dev_handle);
-}
-
-void rcar_io_emmc_setup(void)
-{
-	const io_dev_connector_t *rcar;
-	const io_dev_connector_t *emmc;
-
-	boot_io_drv_id = EMMC_DEV_ID;
-
-	rcar_register_io_dev(&rcar);
-	rcar_register_io_dev_emmcdrv(&emmc);
-	io_dev_open(rcar, 0, &rcar_dev_handle);
-	io_dev_open(emmc, 0, &emmcdrv_dev_handle);
-}
-
-int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
-			  uintptr_t *image_spec)
-{
-	const struct plat_io_policy *policy;
-	int result;
-
-	policy = &policies[image_id];
-
-	result = policy->check(policy->image_spec);
-	if (result != IO_SUCCESS)
-		return result;
-
-	*image_spec = policy->image_spec;
-	*dev_handle = *(policy->dev_handle);
-
-	return IO_SUCCESS;
-}
-
-int32_t plat_get_drv_source(uint32_t io_drv_id, uintptr_t *dev_handle,
-			    uintptr_t *image_spec)
-{
-	const struct plat_io_policy *policy;
-	int32_t result;
-
-	policy = &drv_policies[io_drv_id];
-
-	result = policy->check(policy->image_spec);
-	if (result != IO_SUCCESS)
-		return result;
-
-	*image_spec = policy->image_spec;
-	*dev_handle = *(policy->dev_handle);
-
-	return IO_SUCCESS;
-}
diff --git a/plat/renesas/rcar/platform.mk b/plat/renesas/rcar/platform.mk
index 4c41dd3..670d499 100644
--- a/plat/renesas/rcar/platform.mk
+++ b/plat/renesas/rcar/platform.mk
@@ -1,56 +1,10 @@
 #
-# Copyright (c) 2018-2019, Renesas Electronics Corporation. All rights reserved.
+# Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
-PROGRAMMABLE_RESET_ADDRESS	:= 0
-COLD_BOOT_SINGLE_CPU		:= 1
-ARM_CCI_PRODUCT_ID		:= 500
-TRUSTED_BOARD_BOOT		:= 1
-RESET_TO_BL31			:= 1
-GENERATE_COT			:= 1
-BL2_AT_EL3			:= 1
-ENABLE_SVE_FOR_NS		:= 0
-MULTI_CONSOLE_API		:= 1
-
-CRASH_REPORTING			:= 1
-HANDLE_EA_EL3_FIRST		:= 1
-
-$(eval $(call add_define,PLAT_EXTRA_LD_SCRIPT))
-
-ifeq (${SPD},none)
-  SPD_NONE:=1
-  $(eval $(call add_define,SPD_NONE))
-endif
-
-# LSI setting common define
-RCAR_H3:=0
-RCAR_M3:=1
-RCAR_M3N:=2
-RCAR_E3:=3
-RCAR_H3N:=4
-RCAR_D3:=5
-RCAR_V3M:=6
-RCAR_AUTO:=99
-$(eval $(call add_define,RCAR_H3))
-$(eval $(call add_define,RCAR_M3))
-$(eval $(call add_define,RCAR_M3N))
-$(eval $(call add_define,RCAR_E3))
-$(eval $(call add_define,RCAR_H3N))
-$(eval $(call add_define,RCAR_D3))
-$(eval $(call add_define,RCAR_V3M))
-$(eval $(call add_define,RCAR_AUTO))
-RCAR_CUT_10:=0
-RCAR_CUT_11:=1
-RCAR_CUT_13:=3
-RCAR_CUT_20:=10
-RCAR_CUT_30:=20
-$(eval $(call add_define,RCAR_CUT_10))
-$(eval $(call add_define,RCAR_CUT_11))
-$(eval $(call add_define,RCAR_CUT_13))
-$(eval $(call add_define,RCAR_CUT_20))
-$(eval $(call add_define,RCAR_CUT_30))
+include plat/renesas/common/common.mk
 
 ifndef LSI
   $(error "Error: Unknown LSI. Please use LSI=<LSI name> to specify the LSI")
@@ -291,6 +245,12 @@
 endif
 $(eval $(call add_define,RCAR_DRAM_LPDDR4_MEMCONF))
 
+# Process RCAR_DRAM_MEMRANK flag
+ifndef RCAR_DRAM_MEMRANK
+RCAR_DRAM_MEMRANK :=0
+endif
+$(eval $(call add_define,RCAR_DRAM_MEMRANK))
+
 # Process RCAR_DRAM_DDR3L_MEMCONF flag
 ifndef RCAR_DRAM_DDR3L_MEMCONF
 RCAR_DRAM_DDR3L_MEMCONF :=1
@@ -326,6 +286,11 @@
 endif
 $(eval $(call add_define,RCAR_SYSTEM_RESET_KEEPON_DDR))
 
+ifndef RCAR_GEN3_BL33_GZIP
+RCAR_GEN3_BL33_GZIP := 0
+endif
+$(eval $(call add_define,RCAR_GEN3_BL33_GZIP))
+
 # RCAR_SYSTEM_RESET_KEEPON_DDR requires power control of PMIC etc.
 # When executing SYSTEM_SUSPEND other than Salvator-X, Salvator-XS and Ebisu,
 # processing equivalent to that implemented in PMIC_ROHM_BD9571 is necessary.
@@ -339,105 +304,39 @@
   endif
 endif
 
-# Enable workarounds for selected Cortex-A53 erratas.
-ERRATA_A53_835769  := 1
-ERRATA_A53_843419  := 1
-ERRATA_A53_855873  := 1
-
-# Enable workarounds for selected Cortex-A57 erratas.
-ERRATA_A57_859972  := 1
-ERRATA_A57_813419  := 1
-
-include drivers/renesas/rcar/ddr/ddr.mk
+include drivers/renesas/common/ddr/ddr.mk
 include drivers/renesas/rcar/qos/qos.mk
 include drivers/renesas/rcar/pfc/pfc.mk
 include lib/libfdt/libfdt.mk
 
-PLAT_INCLUDES	:=	-Idrivers/renesas/rcar/ddr		\
+PLAT_INCLUDES	+=	-Idrivers/renesas/common/ddr		\
 			-Idrivers/renesas/rcar/qos		\
-			-Idrivers/renesas/rcar/iic_dvfs		\
 			-Idrivers/renesas/rcar/board		\
 			-Idrivers/renesas/rcar/cpld/		\
-			-Idrivers/renesas/rcar/avs		\
-			-Idrivers/renesas/rcar/delay		\
-			-Idrivers/renesas/rcar/rom		\
-			-Idrivers/renesas/rcar/scif		\
-			-Idrivers/renesas/rcar/emmc		\
-			-Idrivers/renesas/rcar/pwrc		\
-			-Idrivers/renesas/rcar/io		\
-			-Iplat/renesas/rcar/include/registers	\
-			-Iplat/renesas/rcar/include		\
-			-Iplat/renesas/rcar
+			-Idrivers/renesas/common		\
+			-Idrivers/renesas/common/iic_dvfs	\
+			-Idrivers/renesas/common/avs		\
+			-Idrivers/renesas/common/delay		\
+			-Idrivers/renesas/common/rom		\
+			-Idrivers/renesas/common/scif		\
+			-Idrivers/renesas/common/emmc		\
+			-Idrivers/renesas/common/pwrc		\
+			-Idrivers/renesas/common/io
 
-PLAT_BL_COMMON_SOURCES	:=	drivers/renesas/rcar/iic_dvfs/iic_dvfs.c \
-				plat/renesas/rcar/rcar_common.c
+BL2_SOURCES	+=	plat/renesas/rcar/bl2_plat_setup.c	\
+			drivers/renesas/rcar/board/board.c
 
-RCAR_GIC_SOURCES	:=	drivers/arm/gic/common/gic_common.c	\
-				drivers/arm/gic/v2/gicv2_main.c		\
-				drivers/arm/gic/v2/gicv2_helpers.c	\
-				plat/common/plat_gicv2.c
+ifeq (${RCAR_GEN3_BL33_GZIP},1)
+include lib/zlib/zlib.mk
 
-BL2_SOURCES	+=	${RCAR_GIC_SOURCES}				\
-			lib/cpus/aarch64/cortex_a53.S			\
-			lib/cpus/aarch64/cortex_a57.S			\
-			${LIBFDT_SRCS}					\
-			common/desc_image_load.c			\
-			plat/renesas/rcar/aarch64/platform_common.c	\
-			plat/renesas/rcar/aarch64/plat_helpers.S	\
-			plat/renesas/rcar/bl2_interrupt_error.c		\
-			plat/renesas/rcar/bl2_secure_setting.c		\
-			plat/renesas/rcar/bl2_plat_setup.c		\
-			plat/renesas/rcar/plat_storage.c		\
-			plat/renesas/rcar/bl2_plat_mem_params_desc.c	\
-			plat/renesas/rcar/plat_image_load.c		\
-			plat/renesas/rcar/bl2_cpg_init.c		\
-			drivers/renesas/rcar/console/rcar_printf.c	\
-			drivers/renesas/rcar/scif/scif.S		\
-			drivers/renesas/rcar/common.c			\
-			drivers/renesas/rcar/io/io_emmcdrv.c		\
-			drivers/renesas/rcar/io/io_memdrv.c		\
-			drivers/renesas/rcar/io/io_rcar.c		\
-			drivers/renesas/rcar/auth/auth_mod.c		\
-			drivers/renesas/rcar/rpc/rpc_driver.c		\
-			drivers/renesas/rcar/dma/dma_driver.c		\
-			drivers/renesas/rcar/avs/avs_driver.c		\
-			drivers/renesas/rcar/delay/micro_delay.c	\
-			drivers/renesas/rcar/emmc/emmc_interrupt.c	\
-			drivers/renesas/rcar/emmc/emmc_utility.c	\
-			drivers/renesas/rcar/emmc/emmc_mount.c		\
-			drivers/renesas/rcar/emmc/emmc_init.c		\
-			drivers/renesas/rcar/emmc/emmc_read.c		\
-			drivers/renesas/rcar/emmc/emmc_cmd.c		\
-			drivers/renesas/rcar/watchdog/swdt.c		\
-			drivers/renesas/rcar/rom/rom_api.c		\
-			drivers/renesas/rcar/board/board.c		\
-			drivers/io/io_storage.c
-
-BL31_SOURCES	+=	${RCAR_GIC_SOURCES}				\
-			lib/cpus/aarch64/cortex_a53.S			\
-			lib/cpus/aarch64/cortex_a57.S			\
-			plat/common/plat_psci_common.c			\
-			plat/renesas/rcar/plat_topology.c		\
-			plat/renesas/rcar/aarch64/plat_helpers.S	\
-			plat/renesas/rcar/aarch64/platform_common.c	\
-			plat/renesas/rcar/bl31_plat_setup.c		\
-			plat/renesas/rcar/plat_pm.c			\
-			drivers/renesas/rcar/console/rcar_console.S	\
-			drivers/renesas/rcar/console/rcar_printf.c	\
-			drivers/renesas/rcar/delay/micro_delay.c	\
-			drivers/renesas/rcar/pwrc/call_sram.S		\
-			drivers/renesas/rcar/pwrc/pwrc.c		\
-			drivers/renesas/rcar/common.c			\
-			drivers/arm/cci/cci.c
+BL2_SOURCES	+=	common/image_decompress.c               \
+			$(ZLIB_SOURCES)
+endif
 
 ifeq (${RCAR_GEN3_ULCB},1)
 BL31_SOURCES		+=	drivers/renesas/rcar/cpld/ulcb_cpld.c
 endif
 
-include lib/xlat_tables_v2/xlat_tables.mk
-include drivers/auth/mbedtls/mbedtls_crypto.mk
-PLAT_BL_COMMON_SOURCES	+=	${XLAT_TABLES_LIB_SRCS}
-
 # build the layout images for the bootrom and the necessary srecords
 rcar: rcar_layout_tool rcar_srecord
 distclean realclean clean: clean_layout_tool clean_srecord
diff --git a/plat/renesas/rcar/rcar_common.c b/plat/renesas/rcar/rcar_common.c
deleted file mode 100644
index dec7229..0000000
--- a/plat/renesas/rcar/rcar_common.c
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright (c) 2019, Renesas Electronics Corporation. All rights reserved.
- *
- * SPDX-License-Identifier: BSD-3-Clause
- */
-
-#include <assert.h>
-
-#include <arch_helpers.h>
-#include <drivers/console.h>
-#include <lib/xlat_tables/xlat_mmu_helpers.h>
-#include <plat/common/platform.h>
-
-#include <lib/mmio.h>
-
-#define CPG_BASE		0xE6150000
-#define CPG_MSTPSR3		0x0048
-#define MSTP318			(1 << 18)
-#define MSTP319			(1 << 19)
-#define PMSR			0x5c
-#define PMSR_L1FAEG		(1U << 31)
-#define PMSR_PMEL1RX		(1 << 23)
-#define PMCTLR			0x60
-#define PMSR_L1IATN		(1U << 31)
-
-static int rcar_pcie_fixup(unsigned int controller)
-{
-	uint32_t rcar_pcie_base[] = { 0xfe011000, 0xee811000 };
-	uint32_t addr = rcar_pcie_base[controller];
-	uint32_t cpg, pmsr;
-	int ret = 0;
-
-	/* Test if PCIECx is enabled */
-	cpg = mmio_read_32(CPG_BASE + CPG_MSTPSR3);
-	if (cpg & (MSTP318 << !controller))
-		return ret;
-
-	pmsr = mmio_read_32(addr + PMSR);
-
-	if ((pmsr & PMSR_PMEL1RX) && ((pmsr & 0x70000) != 0x30000)) {
-		/* Fix applicable */
-		mmio_write_32(addr + PMCTLR, PMSR_L1IATN);
-		while (!(mmio_read_32(addr + PMSR) & PMSR_L1FAEG))
-			;
-		mmio_write_32(addr + PMSR, PMSR_L1FAEG | PMSR_PMEL1RX);
-		ret = 1;
-	}
-
-	return ret;
-}
-
-/* RAS functions common to AArch64 ARM platforms */
-void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie,
-		void *handle, uint64_t flags)
-{
-	unsigned int fixed = 0;
-
-	fixed |= rcar_pcie_fixup(0);
-	fixed |= rcar_pcie_fixup(1);
-
-	if (fixed)
-		return;
-
-	ERROR("Unhandled External Abort received on 0x%lx at EL3!\n",
-			read_mpidr_el1());
-	ERROR(" exception reason=%u syndrome=0x%llx\n", ea_reason, syndrome);
-
-	panic();
-}
-
-#include <drivers/renesas/rcar/console/console.h>
-
-static console_t rcar_boot_console;
-static console_t rcar_runtime_console;
-
-void rcar_console_boot_init(void)
-{
-	int ret;
-
-	ret = console_rcar_register(0, 0, 0, &rcar_boot_console);
-	if (!ret)
-		panic();
-
-	console_set_scope(&rcar_boot_console, CONSOLE_FLAG_BOOT);
-}
-
-void rcar_console_boot_end(void)
-{
-}
-
-void rcar_console_runtime_init(void)
-{
-	int ret;
-
-	ret = console_rcar_register(1, 0, 0, &rcar_runtime_console);
-	if (!ret)
-		panic();
-
-	console_set_scope(&rcar_boot_console, CONSOLE_FLAG_RUNTIME);
-}
-
-void rcar_console_runtime_end(void)
-{
-}
diff --git a/plat/renesas/rzg/bl2_plat_setup.c b/plat/renesas/rzg/bl2_plat_setup.c
new file mode 100644
index 0000000..e9dbd20
--- /dev/null
+++ b/plat/renesas/rzg/bl2_plat_setup.c
@@ -0,0 +1,1020 @@
+/*
+ * Copyright (c) 2020-2021, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <inttypes.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <bl1/bl1.h>
+#include <common/bl_common.h>
+#include <common/debug.h>
+#include <common/desc_image_load.h>
+#include <drivers/console.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_storage.h>
+#include <libfdt.h>
+#include <lib/mmio.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+#include <platform_def.h>
+#include <plat/common/platform.h>
+
+#include "avs_driver.h"
+#include "board.h"
+#include "boot_init_dram.h"
+#include "cpg_registers.h"
+#include "emmc_def.h"
+#include "emmc_hal.h"
+#include "emmc_std.h"
+#include "io_common.h"
+#include "io_rcar.h"
+#include "qos_init.h"
+#include "rcar_def.h"
+#include "rcar_private.h"
+#include "rcar_version.h"
+#include "rom_api.h"
+
+#define MAX_DRAM_CHANNELS 4
+/*
+ * DDR ch0 has a shadow area mapped in 32bit address space.
+ * Physical address 0x4_0000_0000 - 0x4_7fff_ffff in 64bit space
+ * is mapped to 0x4000_0000 - 0xbfff_ffff in 32bit space.
+ */
+#define MAX_DRAM_SIZE_CH0_32BIT_ADDR_SPACE 0x80000000ULL
+
+#if RCAR_BL2_DCACHE == 1
+/*
+ * Following symbols are only used during plat_arch_setup() only
+ * when RCAR_BL2_DCACHE is enabled.
+ */
+static const uint64_t BL2_RO_BASE		= BL_CODE_BASE;
+static const uint64_t BL2_RO_LIMIT		= BL_CODE_END;
+
+#if USE_COHERENT_MEM
+static const uint64_t BL2_COHERENT_RAM_BASE	= BL_COHERENT_RAM_BASE;
+static const uint64_t BL2_COHERENT_RAM_LIMIT	= BL_COHERENT_RAM_END;
+#endif /* USE_COHERENT_MEM */
+
+#endif /* RCAR_BL2_DCACHE */
+
+extern void plat_rcar_gic_driver_init(void);
+extern void plat_rcar_gic_init(void);
+extern void bl2_enter_bl31(const struct entry_point_info *bl_ep_info);
+extern void bl2_system_cpg_init(void);
+extern void bl2_secure_setting(void);
+extern void bl2_cpg_init(void);
+extern void rcar_io_emmc_setup(void);
+extern void rcar_io_setup(void);
+extern void rcar_swdt_release(void);
+extern void rcar_swdt_init(void);
+extern void rcar_rpc_init(void);
+extern void rcar_dma_init(void);
+extern void rzg_pfc_init(void);
+
+static void bl2_init_generic_timer(void);
+
+/* RZ/G2 product check */
+#if RCAR_LSI == RZ_G2M
+#define TARGET_PRODUCT			PRR_PRODUCT_M3
+#define TARGET_NAME			"RZ/G2M"
+#elif RCAR_LSI == RZ_G2H
+#define TARGET_PRODUCT			PRR_PRODUCT_H3
+#define TARGET_NAME			"RZ/G2H"
+#elif RCAR_LSI == RZ_G2N
+#define TARGET_PRODUCT			PRR_PRODUCT_M3N
+#define TARGET_NAME			"RZ/G2N"
+#elif RCAR_LSI == RZ_G2E
+#define TARGET_PRODUCT			PRR_PRODUCT_E3
+#define TARGET_NAME			"RZ/G2E"
+#elif RCAR_LSI == RCAR_AUTO
+#define TARGET_NAME			"RZ/G2M"
+#endif /* RCAR_LSI == RZ_G2M */
+
+#if (RCAR_LSI == RZ_G2E)
+#define GPIO_INDT			(GPIO_INDT6)
+#define GPIO_BKUP_TRG_SHIFT		((uint32_t)1U << 13U)
+#else
+#define GPIO_INDT			(GPIO_INDT1)
+#define GPIO_BKUP_TRG_SHIFT		(1U << 8U)
+#endif /* RCAR_LSI == RZ_G2E */
+
+CASSERT((PARAMS_BASE + sizeof(bl2_to_bl31_params_mem_t) + 0x100)
+	 < (RCAR_SHARED_MEM_BASE + RCAR_SHARED_MEM_SIZE),
+	assert_bl31_params_do_not_fit_in_shared_memory);
+
+static meminfo_t bl2_tzram_layout __aligned(CACHE_WRITEBACK_GRANULE);
+
+/* FDT with DRAM configuration */
+uint64_t fdt_blob[PAGE_SIZE_4KB / sizeof(uint64_t)];
+static void *fdt = (void *)fdt_blob;
+
+static void unsigned_num_print(uint64_t unum, unsigned int radix, char *string)
+{
+	/* Just need enough space to store 64 bit decimal integer */
+	char num_buf[20];
+	int i = 0;
+	unsigned int rem;
+
+	do {
+		rem = unum % radix;
+		if (rem < 0xaU) {
+			num_buf[i] = '0' + rem;
+		} else {
+			num_buf[i] = 'a' + (rem - 0xaU);
+		}
+		i++;
+		unum /= radix;
+	} while (unum > 0U);
+
+	while (--i >= 0) {
+		*string++ = num_buf[i];
+	}
+	*string = 0;
+}
+
+#if RCAR_LOSSY_ENABLE == 1
+typedef struct bl2_lossy_info {
+	uint32_t magic;
+	uint32_t a0;
+	uint32_t b0;
+} bl2_lossy_info_t;
+
+static void bl2_lossy_gen_fdt(uint32_t no, uint64_t start_addr,
+			      uint64_t end_addr, uint32_t format,
+			      uint32_t enable, int fcnlnode)
+{
+	const uint64_t fcnlsize = cpu_to_fdt64(end_addr - start_addr);
+	char nodename[40] = { 0 };
+	int ret, node;
+
+	/* Ignore undefined addresses */
+	if (start_addr == 0UL && end_addr == 0UL) {
+		return;
+	}
+
+	snprintf(nodename, sizeof(nodename), "lossy-decompression@");
+	unsigned_num_print(start_addr, 16, nodename + strlen(nodename));
+
+	node = ret = fdt_add_subnode(fdt, fcnlnode, nodename);
+	if (ret < 0) {
+		NOTICE("BL2: Cannot create FCNL node (ret=%i)\n", ret);
+		panic();
+	}
+
+	ret = fdt_setprop_string(fdt, node, "compatible",
+				 "renesas,lossy-decompression");
+	if (ret < 0) {
+		NOTICE("BL2: Cannot add FCNL compat string %s (ret=%i)\n",
+		       "renesas,lossy-decompression", ret);
+		panic();
+	}
+
+	ret = fdt_appendprop_string(fdt, node, "compatible",
+				    "shared-dma-pool");
+	if (ret < 0) {
+		NOTICE("BL2: Cannot append FCNL compat string %s (ret=%i)\n",
+		       "shared-dma-pool", ret);
+		panic();
+	}
+
+	ret = fdt_setprop_u64(fdt, node, "reg", start_addr);
+	if (ret < 0) {
+		NOTICE("BL2: Cannot add FCNL reg prop (ret=%i)\n", ret);
+		panic();
+	}
+
+	ret = fdt_appendprop(fdt, node, "reg", &fcnlsize, sizeof(fcnlsize));
+	if (ret < 0) {
+		NOTICE("BL2: Cannot append FCNL reg size prop (ret=%i)\n", ret);
+		panic();
+	}
+
+	ret = fdt_setprop(fdt, node, "no-map", NULL, 0);
+	if (ret < 0) {
+		NOTICE("BL2: Cannot add FCNL no-map prop (ret=%i)\n", ret);
+		panic();
+	}
+
+	ret = fdt_setprop_u32(fdt, node, "renesas,formats", format);
+	if (ret < 0) {
+		NOTICE("BL2: Cannot add FCNL formats prop (ret=%i)\n", ret);
+		panic();
+	}
+}
+
+static void bl2_lossy_setting(uint32_t no, uint64_t start_addr,
+			      uint64_t end_addr, uint32_t format,
+			      uint32_t enable, int fcnlnode)
+{
+	bl2_lossy_info_t info;
+	uint32_t reg;
+
+	bl2_lossy_gen_fdt(no, start_addr, end_addr, format, enable, fcnlnode);
+
+	reg = format | (start_addr >> 20);
+	mmio_write_32(AXI_DCMPAREACRA0 + 0x8U * no, reg);
+	mmio_write_32(AXI_DCMPAREACRB0 + 0x8U * no, end_addr >> 20);
+	mmio_write_32(AXI_DCMPAREACRA0 + 0x8U * no, reg | enable);
+
+	info.magic = 0x12345678U;
+	info.a0 = mmio_read_32(AXI_DCMPAREACRA0 + 0x8U * no);
+	info.b0 = mmio_read_32(AXI_DCMPAREACRB0 + 0x8U * no);
+
+	mmio_write_32(LOSSY_PARAMS_BASE + sizeof(info) * no, info.magic);
+	mmio_write_32(LOSSY_PARAMS_BASE + sizeof(info) * no + 0x4U, info.a0);
+	mmio_write_32(LOSSY_PARAMS_BASE + sizeof(info) * no + 0x8U, info.b0);
+
+	NOTICE("     Entry %d: DCMPAREACRAx:0x%x DCMPAREACRBx:0x%x\n", no,
+	       mmio_read_32(AXI_DCMPAREACRA0 + 0x8U * no),
+	       mmio_read_32(AXI_DCMPAREACRB0 + 0x8U * no));
+}
+#endif /* RCAR_LOSSY_ENABLE == 1 */
+
+void bl2_plat_flush_bl31_params(void)
+{
+	uint32_t product_cut, product, cut;
+	uint32_t boot_dev, boot_cpu;
+	uint32_t reg;
+
+	reg = mmio_read_32(RCAR_MODEMR);
+	boot_dev = reg & MODEMR_BOOT_DEV_MASK;
+
+	if (boot_dev == MODEMR_BOOT_DEV_EMMC_25X1 ||
+	    boot_dev == MODEMR_BOOT_DEV_EMMC_50X8) {
+		emmc_terminate();
+	}
+
+	if ((reg & MODEMR_BOOT_CPU_MASK) != MODEMR_BOOT_CPU_CR7) {
+		bl2_secure_setting();
+	}
+
+	reg = mmio_read_32(RCAR_PRR);
+	product_cut = reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+	product = reg & PRR_PRODUCT_MASK;
+	cut = reg & PRR_CUT_MASK;
+
+	if (!((product == PRR_PRODUCT_M3 && cut < PRR_PRODUCT_30) ||
+	      (product == PRR_PRODUCT_H3 && cut < PRR_PRODUCT_20))) {
+		/* Disable MFIS write protection */
+		mmio_write_32(MFISWPCNTR, MFISWPCNTR_PASSWORD | 1U);
+	}
+
+	reg = mmio_read_32(RCAR_MODEMR);
+	boot_cpu = reg & MODEMR_BOOT_CPU_MASK;
+	if (boot_cpu == MODEMR_BOOT_CPU_CA57 ||
+	    boot_cpu == MODEMR_BOOT_CPU_CA53) {
+		if (product_cut == PRR_PRODUCT_H3_CUT20) {
+			mmio_write_32(IPMMUVI0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUVI1_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV1_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV2_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV3_IMSCTLR, IMSCTLR_DISCACHE);
+		} else if (product_cut == (PRR_PRODUCT_M3N | PRR_PRODUCT_10) ||
+			   product_cut == (PRR_PRODUCT_M3N | PRR_PRODUCT_11)) {
+			mmio_write_32(IPMMUVI0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV0_IMSCTLR, IMSCTLR_DISCACHE);
+		} else if ((product_cut == (PRR_PRODUCT_E3 | PRR_PRODUCT_10)) ||
+			   (product_cut == (PRR_PRODUCT_E3 | PRR_PRODUCT_11))) {
+			mmio_write_32(IPMMUVI0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUVP0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUPV0_IMSCTLR, IMSCTLR_DISCACHE);
+		}
+
+		if (product_cut == (PRR_PRODUCT_H3_CUT20) ||
+		    product_cut == (PRR_PRODUCT_M3N | PRR_PRODUCT_10) ||
+		    product_cut == (PRR_PRODUCT_M3N | PRR_PRODUCT_11) ||
+		    product_cut == (PRR_PRODUCT_E3 | PRR_PRODUCT_10)) {
+			mmio_write_32(IPMMUHC_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMURT_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUMP_IMSCTLR, IMSCTLR_DISCACHE);
+
+			mmio_write_32(IPMMUDS0_IMSCTLR, IMSCTLR_DISCACHE);
+			mmio_write_32(IPMMUDS1_IMSCTLR, IMSCTLR_DISCACHE);
+		}
+	}
+
+	mmio_write_32(IPMMUMM_IMSCTLR, IPMMUMM_IMSCTLR_ENABLE);
+	mmio_write_32(IPMMUMM_IMAUXCTLR, IPMMUMM_IMAUXCTLR_NMERGE40_BIT);
+
+	rcar_swdt_release();
+	bl2_system_cpg_init();
+
+#if RCAR_BL2_DCACHE == 1
+	/* Disable data cache (clean and invalidate) */
+	disable_mmu_el3();
+#endif /* RCAR_BL2_DCACHE == 1 */
+}
+
+static uint32_t is_ddr_backup_mode(void)
+{
+#if RCAR_SYSTEM_SUSPEND
+	static uint32_t reason = RCAR_COLD_BOOT;
+	static uint32_t once;
+
+	if (once != 0U) {
+		return reason;
+	}
+
+	once = 1;
+	if ((mmio_read_32(GPIO_INDT) & GPIO_BKUP_TRG_SHIFT) == 0U) {
+		return reason;
+	}
+
+	reason = RCAR_WARM_BOOT;
+	return reason;
+#else /* RCAR_SYSTEM_SUSPEND */
+	return RCAR_COLD_BOOT;
+#endif /* RCAR_SYSTEM_SUSPEND */
+}
+
+int bl2_plat_handle_pre_image_load(unsigned int image_id)
+{
+	u_register_t *boot_kind = (void *)BOOT_KIND_BASE;
+	bl_mem_params_node_t *bl_mem_params;
+
+	if (image_id != BL31_IMAGE_ID) {
+		return 0;
+	}
+
+	bl_mem_params = get_bl_mem_params_node(image_id);
+
+	if (is_ddr_backup_mode() != RCAR_COLD_BOOT) {
+		*boot_kind  = RCAR_WARM_BOOT;
+		flush_dcache_range(BOOT_KIND_BASE, sizeof(*boot_kind));
+
+		console_flush();
+		bl2_plat_flush_bl31_params();
+
+		/* will not return */
+		bl2_enter_bl31(&bl_mem_params->ep_info);
+	}
+
+	*boot_kind  = RCAR_COLD_BOOT;
+	flush_dcache_range(BOOT_KIND_BASE, sizeof(*boot_kind));
+
+	return 0;
+}
+
+static uint64_t rzg_get_dest_addr_from_cert(uint32_t certid, uintptr_t *dest)
+{
+	uint32_t cert, len;
+	int err;
+
+	err = rcar_get_certificate(certid, &cert);
+	if (err != 0) {
+		ERROR("%s : cert file load error", __func__);
+		return 1U;
+	}
+
+	rcar_read_certificate((uint64_t)cert, &len, dest);
+
+	return 0U;
+}
+
+int bl2_plat_handle_post_image_load(unsigned int image_id)
+{
+	static bl2_to_bl31_params_mem_t *params;
+	bl_mem_params_node_t *bl_mem_params;
+	uintptr_t dest;
+	uint64_t ret;
+
+	if (params == NULL) {
+		params = (bl2_to_bl31_params_mem_t *)PARAMS_BASE;
+		memset((void *)PARAMS_BASE, 0, sizeof(*params));
+	}
+
+	bl_mem_params = get_bl_mem_params_node(image_id);
+
+	switch (image_id) {
+	case BL31_IMAGE_ID:
+		ret = rzg_get_dest_addr_from_cert(SOC_FW_CONTENT_CERT_ID,
+						  &dest);
+		if (ret == 0U) {
+			bl_mem_params->image_info.image_base = dest;
+		}
+		break;
+	case BL32_IMAGE_ID:
+		ret = rzg_get_dest_addr_from_cert(TRUSTED_OS_FW_CONTENT_CERT_ID,
+						  &dest);
+		if (ret == 0U) {
+			bl_mem_params->image_info.image_base = dest;
+		}
+
+		memcpy(&params->bl32_ep_info, &bl_mem_params->ep_info,
+		       sizeof(entry_point_info_t));
+		break;
+	case BL33_IMAGE_ID:
+		memcpy(&params->bl33_ep_info, &bl_mem_params->ep_info,
+		       sizeof(entry_point_info_t));
+		break;
+	default:
+		break;
+	}
+
+	return 0;
+}
+
+struct meminfo *bl2_plat_sec_mem_layout(void)
+{
+	return &bl2_tzram_layout;
+}
+
+static void bl2_populate_compatible_string(void *dt)
+{
+	uint32_t board_type;
+	uint32_t board_rev;
+	uint32_t reg;
+	int ret;
+
+	fdt_setprop_u32(dt, 0, "#address-cells", 2);
+	fdt_setprop_u32(dt, 0, "#size-cells", 2);
+
+	/* Populate compatible string */
+	rzg_get_board_type(&board_type, &board_rev);
+	switch (board_type) {
+	case BOARD_HIHOPE_RZ_G2M:
+		ret = fdt_setprop_string(dt, 0, "compatible",
+					 "hoperun,hihope-rzg2m");
+		break;
+	case BOARD_HIHOPE_RZ_G2H:
+		ret = fdt_setprop_string(dt, 0, "compatible",
+					 "hoperun,hihope-rzg2h");
+		break;
+	case BOARD_HIHOPE_RZ_G2N:
+		ret = fdt_setprop_string(dt, 0, "compatible",
+					 "hoperun,hihope-rzg2n");
+		break;
+	case BOARD_EK874_RZ_G2E:
+		ret = fdt_setprop_string(dt, 0, "compatible",
+					 "si-linux,cat874");
+		break;
+	default:
+		NOTICE("BL2: Cannot set compatible string, board unsupported\n");
+		panic();
+		break;
+	}
+
+	if (ret < 0) {
+		NOTICE("BL2: Cannot set compatible string (ret=%i)\n", ret);
+		panic();
+	}
+
+	reg = mmio_read_32(RCAR_PRR);
+	switch (reg & PRR_PRODUCT_MASK) {
+	case PRR_PRODUCT_M3:
+		ret = fdt_appendprop_string(dt, 0, "compatible",
+					    "renesas,r8a774a1");
+		break;
+	case PRR_PRODUCT_H3:
+		ret = fdt_appendprop_string(dt, 0, "compatible",
+					    "renesas,r8a774e1");
+		break;
+	case PRR_PRODUCT_M3N:
+		ret = fdt_appendprop_string(dt, 0, "compatible",
+					    "renesas,r8a774b1");
+		break;
+	case PRR_PRODUCT_E3:
+		ret = fdt_appendprop_string(dt, 0, "compatible",
+					    "renesas,r8a774c0");
+		break;
+	default:
+		NOTICE("BL2: Cannot set compatible string, SoC unsupported\n");
+		panic();
+		break;
+	}
+
+	if (ret < 0) {
+		NOTICE("BL2: Cannot set compatible string (ret=%i)\n", ret);
+		panic();
+	}
+}
+
+static int bl2_add_memory_node(uint64_t start, uint64_t size)
+{
+	char nodename[32] = { 0 };
+	uint64_t fdtsize;
+	int ret, node;
+
+	fdtsize = cpu_to_fdt64(size);
+
+	snprintf(nodename, sizeof(nodename), "memory@");
+	unsigned_num_print(start, 16, nodename + strlen(nodename));
+	node = ret = fdt_add_subnode(fdt, 0, nodename);
+	if (ret < 0) {
+		return ret;
+	}
+
+	ret = fdt_setprop_string(fdt, node, "device_type", "memory");
+	if (ret < 0) {
+		return ret;
+	}
+
+	ret = fdt_setprop_u64(fdt, node, "reg", start);
+	if (ret < 0) {
+		return ret;
+	}
+
+	return fdt_appendprop(fdt, node, "reg", &fdtsize, sizeof(fdtsize));
+}
+
+static void bl2_advertise_dram_entries(uint64_t dram_config[8])
+{
+	uint64_t start, size;
+	int ret, chan;
+
+	for (chan = 0; chan < MAX_DRAM_CHANNELS; chan++) {
+		start = dram_config[2 * chan];
+		size = dram_config[2 * chan + 1];
+		if (size == 0U) {
+			continue;
+		}
+
+		NOTICE("BL2: CH%d: %" PRIx64 " - %" PRIx64 ", %" PRId64 " %siB\n",
+		       chan, start, start + size - 1U,
+		       (size >> 30) ? : size >> 20,
+		       (size >> 30) ? "G" : "M");
+	}
+
+	/*
+	 * We add the DT nodes in reverse order here. The fdt_add_subnode()
+	 * adds the DT node before the first existing DT node, so we have
+	 * to add them in reverse order to get nodes sorted by address in
+	 * the resulting DT.
+	 */
+	for (chan = MAX_DRAM_CHANNELS - 1; chan >= 0; chan--) {
+		start = dram_config[2 * chan];
+		size = dram_config[2 * chan + 1];
+		if (size == 0U) {
+			continue;
+		}
+
+		/*
+		 * Channel 0 is mapped in 32bit space and the first
+		 * 128 MiB are reserved
+		 */
+		if (chan == 0) {
+			/*
+			 * Maximum DDR size in Channel 0 for 32 bit space is 2GB, Add DT node
+			 * for remaining region in 64 bit address space
+			 */
+			if (size > MAX_DRAM_SIZE_CH0_32BIT_ADDR_SPACE) {
+				start = dram_config[chan] + MAX_DRAM_SIZE_CH0_32BIT_ADDR_SPACE;
+				size -= MAX_DRAM_SIZE_CH0_32BIT_ADDR_SPACE;
+				ret = bl2_add_memory_node(start, size);
+				if (ret < 0) {
+					goto err;
+				}
+			}
+			start = 0x48000000U;
+			size -= 0x8000000U;
+		}
+
+		ret = bl2_add_memory_node(start, size);
+		if (ret < 0) {
+			goto err;
+		}
+	}
+
+	return;
+err:
+	NOTICE("BL2: Cannot add memory node to FDT (ret=%i)\n", ret);
+	panic();
+}
+
+static void bl2_advertise_dram_size(uint32_t product)
+{
+	uint64_t dram_config[8] = {
+		[0] = 0x400000000ULL,
+		[2] = 0x500000000ULL,
+		[4] = 0x600000000ULL,
+		[6] = 0x700000000ULL,
+	};
+
+	switch (product) {
+	case PRR_PRODUCT_M3:
+		/* 4GB(2GBx2 2ch split) */
+		dram_config[1] = 0x80000000ULL;
+		dram_config[5] = 0x80000000ULL;
+		break;
+	case PRR_PRODUCT_H3:
+#if (RCAR_DRAM_LPDDR4_MEMCONF == 0)
+		/* 4GB(1GBx4) */
+		dram_config[1] = 0x40000000ULL;
+		dram_config[3] = 0x40000000ULL;
+		dram_config[5] = 0x40000000ULL;
+		dram_config[7] = 0x40000000ULL;
+#elif (RCAR_DRAM_LPDDR4_MEMCONF == 1) && (RCAR_DRAM_CHANNEL == 5) && \
+	(RCAR_DRAM_SPLIT == 2)
+		/* 4GB(2GBx2 2ch split) */
+		dram_config[1] = 0x80000000ULL;
+		dram_config[3] = 0x80000000ULL;
+#elif (RCAR_DRAM_LPDDR4_MEMCONF == 1) && (RCAR_DRAM_CHANNEL == 15)
+		/* 8GB(2GBx4: default) */
+		dram_config[1] = 0x80000000ULL;
+		dram_config[3] = 0x80000000ULL;
+		dram_config[5] = 0x80000000ULL;
+		dram_config[7] = 0x80000000ULL;
+#endif /* RCAR_DRAM_LPDDR4_MEMCONF == 0 */
+		break;
+	case PRR_PRODUCT_M3N:
+		/* 4GB(4GBx1) */
+		dram_config[1] = 0x100000000ULL;
+		break;
+	case PRR_PRODUCT_E3:
+#if (RCAR_DRAM_DDR3L_MEMCONF == 0)
+		/* 1GB(512MBx2) */
+		dram_config[1] = 0x40000000ULL;
+#elif (RCAR_DRAM_DDR3L_MEMCONF == 1)
+		/* 2GB(512MBx4) */
+		dram_config[1] = 0x80000000ULL;
+#elif (RCAR_DRAM_DDR3L_MEMCONF == 2)
+		/* 4GB(1GBx4) */
+		dram_config[1] = 0x100000000ULL;
+#endif /* RCAR_DRAM_DDR3L_MEMCONF == 0 */
+		break;
+	default:
+		NOTICE("BL2: Detected invalid DRAM entries\n");
+		break;
+	}
+
+	bl2_advertise_dram_entries(dram_config);
+}
+
+void bl2_el3_early_platform_setup(u_register_t arg1, u_register_t arg2,
+				  u_register_t arg3, u_register_t arg4)
+{
+	uint32_t reg, midr, boot_dev, boot_cpu, type, rev;
+	uint32_t product, product_cut, major, minor;
+	int32_t ret;
+	const char *str;
+	const char *unknown = "unknown";
+	const char *cpu_ca57 = "CA57";
+	const char *cpu_ca53 = "CA53";
+	const char *product_g2e = "G2E";
+	const char *product_g2h = "G2H";
+	const char *product_g2m = "G2M";
+	const char *product_g2n = "G2N";
+	const char *boot_hyper80 = "HyperFlash(80MHz)";
+	const char *boot_qspi40 = "QSPI Flash(40MHz)";
+	const char *boot_qspi80 = "QSPI Flash(80MHz)";
+	const char *boot_emmc25x1 = "eMMC(25MHz x1)";
+	const char *boot_emmc50x8 = "eMMC(50MHz x8)";
+#if (RCAR_LSI == RZ_G2E)
+	uint32_t sscg;
+	const char *sscg_on = "PLL1 SSCG Clock select";
+	const char *sscg_off = "PLL1 nonSSCG Clock select";
+	const char *boot_hyper160 = "HyperFlash(150MHz)";
+#else
+	const char *boot_hyper160 = "HyperFlash(160MHz)";
+#endif /* RCAR_LSI == RZ_G2E */
+#if RZG_LCS_STATE_DETECTION_ENABLE
+	uint32_t lcs;
+	const char *lcs_secure = "SE";
+	const char *lcs_cm = "CM";
+	const char *lcs_dm = "DM";
+	const char *lcs_sd = "SD";
+	const char *lcs_fa = "FA";
+#endif /* RZG_LCS_STATE_DETECTION_ENABLE */
+
+#if (RCAR_LOSSY_ENABLE == 1)
+	int fcnlnode;
+#endif /* (RCAR_LOSSY_ENABLE == 1) */
+
+	bl2_init_generic_timer();
+
+	reg = mmio_read_32(RCAR_MODEMR);
+	boot_dev = reg & MODEMR_BOOT_DEV_MASK;
+	boot_cpu = reg & MODEMR_BOOT_CPU_MASK;
+
+	bl2_cpg_init();
+
+	if (boot_cpu == MODEMR_BOOT_CPU_CA57 ||
+	    boot_cpu == MODEMR_BOOT_CPU_CA53) {
+		rzg_pfc_init();
+		rcar_console_boot_init();
+	}
+
+	plat_rcar_gic_driver_init();
+	plat_rcar_gic_init();
+	rcar_swdt_init();
+
+	/* FIQ interrupts are taken to EL3 */
+	write_scr_el3(read_scr_el3() | SCR_FIQ_BIT);
+
+	write_daifclr(DAIF_FIQ_BIT);
+
+	reg = read_midr();
+	midr = reg & (MIDR_PN_MASK << MIDR_PN_SHIFT);
+	switch (midr) {
+	case MIDR_CA57:
+		str = cpu_ca57;
+		break;
+	case MIDR_CA53:
+		str = cpu_ca53;
+		break;
+	default:
+		str = unknown;
+		break;
+	}
+
+	NOTICE("BL2: RZ/G2 Initial Program Loader(%s) Rev.%s\n", str,
+	       version_of_renesas);
+
+	reg = mmio_read_32(RCAR_PRR);
+	product_cut = reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK);
+	product = reg & PRR_PRODUCT_MASK;
+
+	switch (product) {
+	case PRR_PRODUCT_M3:
+		str = product_g2m;
+		break;
+	case PRR_PRODUCT_H3:
+		str = product_g2h;
+		break;
+	case PRR_PRODUCT_M3N:
+		str = product_g2n;
+		break;
+	case PRR_PRODUCT_E3:
+		str = product_g2e;
+		break;
+	default:
+		str = unknown;
+		break;
+	}
+
+	if ((product == PRR_PRODUCT_M3) &&
+	    ((reg & RCAR_MAJOR_MASK) == PRR_PRODUCT_20)) {
+		if ((reg & PRR_CUT_MASK) == RCAR_M3_CUT_VER11) {
+			/* M3 Ver.1.1 or Ver.1.2 */
+			NOTICE("BL2: PRR is RZ/%s Ver.1.1 / Ver.1.2\n", str);
+		} else {
+			NOTICE("BL2: PRR is RZ/%s Ver.1.%d\n", str,
+				(reg & RCAR_MINOR_MASK) + RCAR_M3_MINOR_OFFSET);
+		}
+	} else {
+		major = (reg & RCAR_MAJOR_MASK) >> RCAR_MAJOR_SHIFT;
+		major = major + RCAR_MAJOR_OFFSET;
+		minor = reg & RCAR_MINOR_MASK;
+		NOTICE("BL2: PRR is RZ/%s Ver.%d.%d\n", str, major, minor);
+	}
+
+#if (RCAR_LSI == RZ_G2E)
+	if (product == PRR_PRODUCT_E3) {
+		reg = mmio_read_32(RCAR_MODEMR);
+		sscg = reg & RCAR_SSCG_MASK;
+		str = sscg == RCAR_SSCG_ENABLE ? sscg_on : sscg_off;
+		NOTICE("BL2: %s\n", str);
+	}
+#endif /* RCAR_LSI == RZ_G2E */
+
+	rzg_get_board_type(&type, &rev);
+
+	switch (type) {
+	case BOARD_HIHOPE_RZ_G2M:
+	case BOARD_HIHOPE_RZ_G2H:
+	case BOARD_HIHOPE_RZ_G2N:
+	case BOARD_EK874_RZ_G2E:
+		break;
+	default:
+		type = BOARD_UNKNOWN;
+		break;
+	}
+
+	if (type == BOARD_UNKNOWN || rev == BOARD_REV_UNKNOWN) {
+		NOTICE("BL2: Board is %s Rev.---\n", GET_BOARD_NAME(type));
+	} else {
+		NOTICE("BL2: Board is %s Rev.%d.%d\n",
+		       GET_BOARD_NAME(type),
+		       GET_BOARD_MAJOR(rev), GET_BOARD_MINOR(rev));
+	}
+
+#if RCAR_LSI != RCAR_AUTO
+	if (product != TARGET_PRODUCT) {
+		ERROR("BL2: IPL was been built for the %s.\n", TARGET_NAME);
+		ERROR("BL2: Please write the correct IPL to flash memory.\n");
+		panic();
+	}
+#endif /* RCAR_LSI != RCAR_AUTO */
+	rcar_avs_init();
+	rcar_avs_setting();
+
+	switch (boot_dev) {
+	case MODEMR_BOOT_DEV_HYPERFLASH160:
+		str = boot_hyper160;
+		break;
+	case MODEMR_BOOT_DEV_HYPERFLASH80:
+		str = boot_hyper80;
+		break;
+	case MODEMR_BOOT_DEV_QSPI_FLASH40:
+		str = boot_qspi40;
+		break;
+	case MODEMR_BOOT_DEV_QSPI_FLASH80:
+		str = boot_qspi80;
+		break;
+	case MODEMR_BOOT_DEV_EMMC_25X1:
+		str = boot_emmc25x1;
+		break;
+	case MODEMR_BOOT_DEV_EMMC_50X8:
+		str = boot_emmc50x8;
+		break;
+	default:
+		str = unknown;
+		break;
+	}
+	NOTICE("BL2: Boot device is %s\n", str);
+
+	rcar_avs_setting();
+
+#if RZG_LCS_STATE_DETECTION_ENABLE
+	reg = rcar_rom_get_lcs(&lcs);
+	if (reg != 0U) {
+		str = unknown;
+		goto lcm_state;
+	}
+
+	switch (lcs) {
+	case LCS_CM:
+		str = lcs_cm;
+		break;
+	case LCS_DM:
+		str = lcs_dm;
+		break;
+	case LCS_SD:
+		str = lcs_sd;
+		break;
+	case LCS_SE:
+		str = lcs_secure;
+		break;
+	case LCS_FA:
+		str = lcs_fa;
+		break;
+	default:
+		str = unknown;
+		break;
+	}
+
+lcm_state:
+	NOTICE("BL2: LCM state is %s\n", str);
+#endif /* RZG_LCS_STATE_DETECTION_ENABLE */
+
+	rcar_avs_end();
+	is_ddr_backup_mode();
+
+	bl2_tzram_layout.total_base = BL31_BASE;
+	bl2_tzram_layout.total_size = BL31_LIMIT - BL31_BASE;
+
+	if (boot_cpu == MODEMR_BOOT_CPU_CA57 ||
+	    boot_cpu == MODEMR_BOOT_CPU_CA53) {
+		ret = rcar_dram_init();
+		if (ret != 0) {
+			NOTICE("BL2: Failed to DRAM initialize (%d).\n", ret);
+			panic();
+		}
+		rzg_qos_init();
+	}
+
+	/* Set up FDT */
+	ret = fdt_create_empty_tree(fdt, sizeof(fdt_blob));
+	if (ret != 0) {
+		NOTICE("BL2: Cannot allocate FDT for U-Boot (ret=%i)\n", ret);
+		panic();
+	}
+
+	/* Add platform compatible string */
+	bl2_populate_compatible_string(fdt);
+
+	/* Print DRAM layout */
+	bl2_advertise_dram_size(product);
+
+	if (boot_dev == MODEMR_BOOT_DEV_EMMC_25X1 ||
+	    boot_dev == MODEMR_BOOT_DEV_EMMC_50X8) {
+		if (rcar_emmc_init() != EMMC_SUCCESS) {
+			NOTICE("BL2: Failed to eMMC driver initialize.\n");
+			panic();
+		}
+		rcar_emmc_memcard_power(EMMC_POWER_ON);
+		if (rcar_emmc_mount() != EMMC_SUCCESS) {
+			NOTICE("BL2: Failed to eMMC mount operation.\n");
+			panic();
+		}
+	} else {
+		rcar_rpc_init();
+		rcar_dma_init();
+	}
+
+	reg = mmio_read_32(RST_WDTRSTCR);
+	reg &= ~WDTRSTCR_RWDT_RSTMSK;
+	reg |= WDTRSTCR_PASSWORD;
+	mmio_write_32(RST_WDTRSTCR, reg);
+
+	mmio_write_32(CPG_CPGWPR, CPGWPR_PASSWORD);
+	mmio_write_32(CPG_CPGWPCR, CPGWPCR_PASSWORD);
+
+	reg = mmio_read_32(RCAR_PRR);
+	if ((reg & RCAR_CPU_MASK_CA57) == RCAR_CPU_HAVE_CA57) {
+		mmio_write_32(CPG_CA57DBGRCR,
+			      DBGCPUPREN | mmio_read_32(CPG_CA57DBGRCR));
+	}
+
+	if ((reg & RCAR_CPU_MASK_CA53) == RCAR_CPU_HAVE_CA53) {
+		mmio_write_32(CPG_CA53DBGRCR,
+			      DBGCPUPREN | mmio_read_32(CPG_CA53DBGRCR));
+	}
+
+	if (product_cut == PRR_PRODUCT_H3_CUT10) {
+		reg = mmio_read_32(CPG_PLL2CR);
+		reg &= ~((uint32_t)1 << 5);
+		mmio_write_32(CPG_PLL2CR, reg);
+
+		reg = mmio_read_32(CPG_PLL4CR);
+		reg &= ~((uint32_t)1 << 5);
+		mmio_write_32(CPG_PLL4CR, reg);
+
+		reg = mmio_read_32(CPG_PLL0CR);
+		reg &= ~((uint32_t)1 << 12);
+		mmio_write_32(CPG_PLL0CR, reg);
+	}
+#if (RCAR_LOSSY_ENABLE == 1)
+	NOTICE("BL2: Lossy Decomp areas\n");
+
+	fcnlnode = fdt_add_subnode(fdt, 0, "reserved-memory");
+	if (fcnlnode < 0) {
+		NOTICE("BL2: Cannot create reserved mem node (ret=%i)\n",
+		       fcnlnode);
+		panic();
+	}
+
+	bl2_lossy_setting(0, LOSSY_ST_ADDR0, LOSSY_END_ADDR0,
+			  LOSSY_FMT0, LOSSY_ENA_DIS0, fcnlnode);
+	bl2_lossy_setting(1, LOSSY_ST_ADDR1, LOSSY_END_ADDR1,
+			  LOSSY_FMT1, LOSSY_ENA_DIS1, fcnlnode);
+	bl2_lossy_setting(2, LOSSY_ST_ADDR2, LOSSY_END_ADDR2,
+			  LOSSY_FMT2, LOSSY_ENA_DIS2, fcnlnode);
+#endif /* RCAR_LOSSY_ENABLE */
+
+	fdt_pack(fdt);
+	NOTICE("BL2: FDT at %p\n", fdt);
+
+	if (boot_dev == MODEMR_BOOT_DEV_EMMC_25X1 ||
+	    boot_dev == MODEMR_BOOT_DEV_EMMC_50X8) {
+		rcar_io_emmc_setup();
+	} else {
+		rcar_io_setup();
+	}
+}
+
+void bl2_el3_plat_arch_setup(void)
+{
+#if RCAR_BL2_DCACHE == 1
+	NOTICE("BL2: D-Cache enable\n");
+	rcar_configure_mmu_el3(BL2_BASE,
+			       BL2_END - BL2_BASE,
+			       BL2_RO_BASE, BL2_RO_LIMIT
+#if USE_COHERENT_MEM
+			       , BL2_COHERENT_RAM_BASE, BL2_COHERENT_RAM_LIMIT
+#endif /* USE_COHERENT_MEM */
+	    );
+#endif /* RCAR_BL2_DCACHE == 1 */
+}
+
+void bl2_platform_setup(void)
+{
+	/*
+	 * Place holder for performing any platform initialization specific
+	 * to BL2.
+	 */
+}
+
+static void bl2_init_generic_timer(void)
+{
+#if RCAR_LSI == RZ_G2E
+	uint32_t reg_cntfid = EXTAL_EBISU;
+#else
+	uint32_t reg_cntfid;
+	uint32_t modemr;
+	uint32_t modemr_pll;
+	uint32_t pll_table[] = {
+		EXTAL_MD14_MD13_TYPE_0,	/* MD14/MD13 : 0b00 */
+		EXTAL_MD14_MD13_TYPE_1,	/* MD14/MD13 : 0b01 */
+		EXTAL_MD14_MD13_TYPE_2,	/* MD14/MD13 : 0b10 */
+		EXTAL_MD14_MD13_TYPE_3	/* MD14/MD13 : 0b11 */
+	};
+
+	modemr = mmio_read_32(RCAR_MODEMR);
+	modemr_pll = (modemr & MODEMR_BOOT_PLL_MASK);
+
+	/* Set frequency data in CNTFID0 */
+	reg_cntfid = pll_table[modemr_pll >> MODEMR_BOOT_PLL_SHIFT];
+#endif /* RCAR_LSI == RZ_G2E */
+
+	/* Update memory mapped and register based frequency */
+	write_cntfrq_el0((u_register_t)reg_cntfid);
+	mmio_write_32(ARM_SYS_CNTCTL_BASE + (uintptr_t)CNTFID_OFF, reg_cntfid);
+	/* Enable counter */
+	mmio_setbits_32(RCAR_CNTC_BASE + (uintptr_t)CNTCR_OFF,
+			(uint32_t)CNTCR_EN);
+}
diff --git a/plat/renesas/rzg/platform.mk b/plat/renesas/rzg/platform.mk
new file mode 100644
index 0000000..f37d7d0
--- /dev/null
+++ b/plat/renesas/rzg/platform.mk
@@ -0,0 +1,274 @@
+#
+# Copyright (c) 2018-2021, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+include plat/renesas/common/common.mk
+
+ifndef LSI
+  $(error "Error: Unknown LSI. Please use LSI=<LSI name> to specify the LSI")
+else
+  ifeq (${LSI},AUTO)
+    RCAR_LSI:=${RCAR_AUTO}
+  else ifeq (${LSI},G2M)
+    RCAR_LSI:=${RZ_G2M}
+    ifndef LSI_CUT
+      # enable compatible function.
+      RCAR_LSI_CUT_COMPAT := 1
+      $(eval $(call add_define,RCAR_LSI_CUT_COMPAT))
+    else
+      # disable compatible function.
+      ifeq (${LSI_CUT},10)
+        RCAR_LSI_CUT:=0
+      else ifeq (${LSI_CUT},11)
+        RCAR_LSI_CUT:=1
+      else ifeq (${LSI_CUT},13)
+        RCAR_LSI_CUT:=3
+      else ifeq (${LSI_CUT},30)
+        RCAR_LSI_CUT:=20
+      else
+        $(error "Error: ${LSI_CUT} is not supported.")
+      endif
+      $(eval $(call add_define,RCAR_LSI_CUT))
+    endif
+  else ifeq (${LSI},G2H)
+    RCAR_LSI:=${RZ_G2H}
+    ifndef LSI_CUT
+      # enable compatible function.
+      RCAR_LSI_CUT_COMPAT := 1
+      $(eval $(call add_define,RCAR_LSI_CUT_COMPAT))
+    else
+      # disable compatible function.
+      ifeq (${LSI_CUT},30)
+        RCAR_LSI_CUT:=20
+      else
+        $(error "Error: ${LSI_CUT} is not supported.")
+      endif
+      $(eval $(call add_define,RCAR_LSI_CUT))
+    endif
+  else ifeq (${LSI},G2N)
+    RCAR_LSI:=${RZ_G2N}
+    ifndef LSI_CUT
+      # enable compatible function.
+      RCAR_LSI_CUT_COMPAT := 1
+      $(eval $(call add_define,RCAR_LSI_CUT_COMPAT))
+    else
+      # disable compatible function.
+      ifeq (${LSI_CUT},10)
+        RCAR_LSI_CUT:=0
+      else ifeq (${LSI_CUT},11)
+        RCAR_LSI_CUT:=1
+      else
+        $(error "Error: ${LSI_CUT} is not supported.")
+      endif
+      $(eval $(call add_define,RCAR_LSI_CUT))
+    endif
+  else ifeq (${LSI},G2E)
+    RCAR_LSI:=${RZ_G2E}
+    ifndef LSI_CUT
+      # enable compatible function.
+      RCAR_LSI_CUT_COMPAT := 1
+      $(eval $(call add_define,RCAR_LSI_CUT_COMPAT))
+    else
+      # disable compatible function.
+      ifeq (${LSI_CUT},10)
+        RCAR_LSI_CUT:=0
+      else ifeq (${LSI_CUT},11)
+        RCAR_LSI_CUT:=1
+      else
+        $(error "Error: ${LSI_CUT} is not supported.")
+      endif
+      $(eval $(call add_define,RCAR_LSI_CUT))
+    endif
+  else
+    $(error "Error: ${LSI} is not supported.")
+  endif
+  $(eval $(call add_define,RCAR_LSI))
+endif
+
+# Process RZG_LCS_STATE_DETECTION_ENABLE flag
+# Enable to get LCS state information
+ifndef RZG_LCS_STATE_DETECTION_ENABLE
+RZG_LCS_STATE_DETECTION_ENABLE := 0
+endif
+$(eval $(call add_define,RZG_LCS_STATE_DETECTION_ENABLE))
+
+# Process RCAR_SECURE_BOOT flag
+ifndef RCAR_SECURE_BOOT
+RCAR_SECURE_BOOT := 0
+endif
+$(eval $(call add_define,RCAR_SECURE_BOOT))
+
+# LCS state of RZ/G2 Chip is all CM.
+# However certain chips(RZ/G2M and RZ/G2E) have incorrect factory Fuse settings
+# which results in getting incorrect LCS states
+# if need to enable RCAR_SECURE_BOOT, make sure the chip has proper factory Fuse settings.
+ifeq (${RCAR_SECURE_BOOT},1)
+  ifeq (${RZG_LCS_STATE_DETECTION_ENABLE},0)
+    $(error "Error: Please check the chip has proper factory Fuse settings and set RZG_LCS_STATE_DETECTION_ENABLE to enable.")
+  endif
+endif
+
+# lock RPC HYPERFLASH access by default
+# unlock to repogram the ATF firmware from u-boot
+ifndef RCAR_RPC_HYPERFLASH_LOCKED
+RCAR_RPC_HYPERFLASH_LOCKED := 1
+endif
+$(eval $(call add_define,RCAR_RPC_HYPERFLASH_LOCKED))
+
+# Process RCAR_QOS_TYPE flag
+ifndef RCAR_QOS_TYPE
+RCAR_QOS_TYPE := 0
+endif
+$(eval $(call add_define,RCAR_QOS_TYPE))
+
+# Process RCAR_DRAM_SPLIT flag
+ifndef RCAR_DRAM_SPLIT
+RCAR_DRAM_SPLIT := 0
+endif
+$(eval $(call add_define,RCAR_DRAM_SPLIT))
+
+# Process RCAR_BL33_EXECUTION_EL flag
+ifndef RCAR_BL33_EXECUTION_EL
+RCAR_BL33_EXECUTION_EL := 0
+endif
+$(eval $(call add_define,RCAR_BL33_EXECUTION_EL))
+
+# Process RCAR_AVS_SETTING_ENABLE flag
+ifndef AVS_SETTING_ENABLE
+AVS_SETTING_ENABLE := 0
+endif
+$(eval $(call add_define,AVS_SETTING_ENABLE))
+
+# Process RCAR_LOSSY_ENABLE flag
+ifndef RCAR_LOSSY_ENABLE
+RCAR_LOSSY_ENABLE := 0
+endif
+$(eval $(call add_define,RCAR_LOSSY_ENABLE))
+
+# Process LIFEC_DBSC_PROTECT_ENABLE flag
+ifndef LIFEC_DBSC_PROTECT_ENABLE
+LIFEC_DBSC_PROTECT_ENABLE := 1
+endif
+$(eval $(call add_define,LIFEC_DBSC_PROTECT_ENABLE))
+
+# Process RCAR_GEN3_ULCB flag
+ifndef RCAR_GEN3_ULCB
+RCAR_GEN3_ULCB := 0
+endif
+
+# Process RCAR_REF_INT flag
+ifndef RCAR_REF_INT
+RCAR_REF_INT :=0
+endif
+$(eval $(call add_define,RCAR_REF_INT))
+
+# Process RCAR_REWT_TRAINING flag
+ifndef RCAR_REWT_TRAINING
+RCAR_REWT_TRAINING := 1
+endif
+$(eval $(call add_define,RCAR_REWT_TRAINING))
+
+# Process RCAR_SYSTEM_SUSPEND flag
+ifndef RCAR_SYSTEM_SUSPEND
+RCAR_SYSTEM_SUSPEND := 0
+endif
+$(eval $(call add_define,RCAR_SYSTEM_SUSPEND))
+
+# Process RCAR_DRAM_LPDDR4_MEMCONF flag
+ifndef RCAR_DRAM_LPDDR4_MEMCONF
+RCAR_DRAM_LPDDR4_MEMCONF :=1
+endif
+$(eval $(call add_define,RCAR_DRAM_LPDDR4_MEMCONF))
+
+# Process RCAR_DRAM_DDR3L_MEMCONF flag
+ifndef RCAR_DRAM_DDR3L_MEMCONF
+RCAR_DRAM_DDR3L_MEMCONF :=1
+endif
+$(eval $(call add_define,RCAR_DRAM_DDR3L_MEMCONF))
+
+# Process RCAR_DRAM_DDR3L_MEMDUAL flag
+ifndef RCAR_DRAM_DDR3L_MEMDUAL
+RCAR_DRAM_DDR3L_MEMDUAL :=1
+endif
+$(eval $(call add_define,RCAR_DRAM_DDR3L_MEMDUAL))
+
+# Process RCAR_BL33_ARG0 flag
+ifdef RCAR_BL33_ARG0
+$(eval $(call add_define,RCAR_BL33_ARG0))
+endif
+
+#Process RCAR_BL2_DCACHE flag
+ifndef RCAR_BL2_DCACHE
+RCAR_BL2_DCACHE := 0
+endif
+$(eval $(call add_define,RCAR_BL2_DCACHE))
+
+# Process RCAR_DRAM_CHANNEL flag
+ifndef RCAR_DRAM_CHANNEL
+RCAR_DRAM_CHANNEL :=15
+endif
+$(eval $(call add_define,RCAR_DRAM_CHANNEL))
+
+#Process RCAR_SYSTEM_RESET_KEEPON_DDR flag
+ifndef RCAR_SYSTEM_RESET_KEEPON_DDR
+RCAR_SYSTEM_RESET_KEEPON_DDR := 0
+endif
+$(eval $(call add_define,RCAR_SYSTEM_RESET_KEEPON_DDR))
+
+RZG_SOC :=1
+$(eval $(call add_define,RZG_SOC))
+
+include drivers/renesas/common/ddr/ddr.mk
+include drivers/renesas/rzg/qos/qos.mk
+include drivers/renesas/rzg/pfc/pfc.mk
+include lib/libfdt/libfdt.mk
+
+PLAT_INCLUDES	+=	-Idrivers/renesas/common/ddr		\
+			-Idrivers/renesas/rzg/qos		\
+			-Idrivers/renesas/rzg/board		\
+			-Idrivers/renesas/common		\
+			-Idrivers/renesas/common/iic_dvfs	\
+			-Idrivers/renesas/common/avs		\
+			-Idrivers/renesas/common/delay		\
+			-Idrivers/renesas/common/rom		\
+			-Idrivers/renesas/common/scif		\
+			-Idrivers/renesas/common/emmc		\
+			-Idrivers/renesas/common/pwrc		\
+			-Idrivers/renesas/common/io
+
+BL2_SOURCES	+=	plat/renesas/rzg/bl2_plat_setup.c	\
+			drivers/renesas/rzg/board/board.c
+
+# build the layout images for the bootrom and the necessary srecords
+rzg: rzg_layout_create rzg_srecord
+distclean realclean clean: clean_layout_tool clean_srecord
+
+# layout images
+LAYOUT_TOOLPATH ?= tools/renesas/rzg_layout_create
+
+clean_layout_tool:
+	@echo "clean layout tool"
+	${Q}${MAKE} -C ${LAYOUT_TOOLPATH} clean
+
+.PHONY: rzg_layout_create
+rzg_layout_create:
+	@echo "generating layout srecs"
+	${Q}${MAKE} CPPFLAGS="-D=AARCH64" --no-print-directory -C ${LAYOUT_TOOLPATH}
+
+# srecords
+SREC_PATH	= ${BUILD_PLAT}
+BL2_ELF_SRC	= ${SREC_PATH}/bl2/bl2.elf
+BL31_ELF_SRC	= ${SREC_PATH}/bl31/bl31.elf
+
+clean_srecord:
+	@echo "clean bl2 and bl31 srecs"
+	rm -f ${SREC_PATH}/bl2.srec ${SREC_PATH}/bl31.srec
+
+.PHONY: rzg_srecord
+rzg_srecord: $(BL2_ELF_SRC) $(BL31_ELF_SRC)
+	@echo "generating srec: ${SREC_PATH}/bl2.srec"
+	$(Q)$(OC) -O srec --srec-forceS3 ${BL2_ELF_SRC}  ${SREC_PATH}/bl2.srec
+	@echo "generating srec: ${SREC_PATH}/bl31.srec"
+	$(Q)$(OC) -O srec --srec-forceS3 ${BL31_ELF_SRC} ${SREC_PATH}/bl31.srec
diff --git a/plat/rockchip/common/rockchip_stack_protector.c b/plat/rockchip/common/rockchip_stack_protector.c
new file mode 100644
index 0000000..1898977
--- /dev/null
+++ b/plat/rockchip/common/rockchip_stack_protector.c
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#include <arch_helpers.h>
+#include <plat/common/platform.h>
+
+#define RANDOM_CANARY_VALUE ((u_register_t) 3288484550995823360ULL)
+
+u_register_t plat_get_stack_protector_canary(void)
+{
+	/*
+	 * Ideally, a random number should be returned instead of the
+	 * combination of a timer's value and a compile-time constant.
+	 * As the virt platform does not have any random number generator,
+	 * this is better than nothing but not necessarily really secure.
+	 */
+	return RANDOM_CANARY_VALUE ^ read_cntpct_el0();
+}
+
diff --git a/plat/rockchip/px30/platform.mk b/plat/rockchip/px30/platform.mk
index 87cf187..d14ffc4 100644
--- a/plat/rockchip/px30/platform.mk
+++ b/plat/rockchip/px30/platform.mk
@@ -4,6 +4,7 @@
 #SPDX-License-Identifier: BSD-3-Clause
 #
 
+include drivers/arm/gic/v2/gicv2.mk
 
 RK_PLAT			:=	plat/rockchip
 RK_PLAT_SOC		:=	${RK_PLAT}/${PLAT}
@@ -24,9 +25,7 @@
 				-I${RK_PLAT_SOC}/drivers/soc/			\
 				-I${RK_PLAT_SOC}/include/
 
-RK_GIC_SOURCES         :=	drivers/arm/gic/common/gic_common.c		\
-				drivers/arm/gic/v2/gicv2_main.c			\
-				drivers/arm/gic/v2/gicv2_helpers.c		\
+RK_GIC_SOURCES         :=	${GICV2_SOURCES}				\
 				plat/common/plat_gicv2.c			\
 				plat/common/aarch64/crash_console_helpers.S	\
 				${RK_PLAT}/common/rockchip_gicv2.c
@@ -36,6 +35,10 @@
 				lib/xlat_tables/aarch64/xlat_tables.c		\
 				plat/common/plat_psci_common.c
 
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+PLAT_BL_COMMON_SOURCES	+=	${RK_PLAT_COMMON}/rockchip_stack_protector.c
+endif
+
 BL31_SOURCES		+=	${RK_GIC_SOURCES}				\
 				common/desc_image_load.c			\
 				drivers/arm/cci/cci.c				\
diff --git a/plat/rockchip/rk3288/platform.mk b/plat/rockchip/rk3288/platform.mk
index faf7a15..b8dd195 100644
--- a/plat/rockchip/rk3288/platform.mk
+++ b/plat/rockchip/rk3288/platform.mk
@@ -4,6 +4,8 @@
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include drivers/arm/gic/v2/gicv2.mk
+
 ARM_CORTEX_A12		:=	yes
 ARM_ARCH_MAJOR		:=	7
 
@@ -24,9 +26,7 @@
 				-I${RK_PLAT_SOC}/include/			\
 				-I${RK_PLAT_SOC}/include/shared/		\
 
-RK_GIC_SOURCES         :=	drivers/arm/gic/common/gic_common.c		\
-				drivers/arm/gic/v2/gicv2_main.c			\
-				drivers/arm/gic/v2/gicv2_helpers.c		\
+RK_GIC_SOURCES         :=	${GICV2_SOURCES}				\
 				plat/common/plat_gicv2.c			\
 				${RK_PLAT}/common/rockchip_gicv2.c
 
diff --git a/plat/rockchip/rk3328/platform.mk b/plat/rockchip/rk3328/platform.mk
index 0219422..5b4766d 100644
--- a/plat/rockchip/rk3328/platform.mk
+++ b/plat/rockchip/rk3328/platform.mk
@@ -4,6 +4,8 @@
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include drivers/arm/gic/v2/gicv2.mk
+
 RK_PLAT			:=	plat/rockchip
 RK_PLAT_SOC		:=	${RK_PLAT}/${PLAT}
 RK_PLAT_COMMON		:=	${RK_PLAT}/common
@@ -22,9 +24,7 @@
 				-I${RK_PLAT_SOC}/drivers/soc/			\
 				-I${RK_PLAT_SOC}/include/
 
-RK_GIC_SOURCES		:=	drivers/arm/gic/common/gic_common.c		\
-				drivers/arm/gic/v2/gicv2_main.c			\
-				drivers/arm/gic/v2/gicv2_helpers.c		\
+RK_GIC_SOURCES		:=	${GICV2_SOURCES}				\
 				plat/common/plat_gicv2.c			\
 				${RK_PLAT}/common/rockchip_gicv2.c
 
@@ -35,6 +35,10 @@
 				plat/common/aarch64/crash_console_helpers.S	\
 				plat/common/plat_psci_common.c
 
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+PLAT_BL_COMMON_SOURCES	+=	${RK_PLAT_COMMON}/rockchip_stack_protector.c
+endif
+
 BL31_SOURCES		+=	${RK_GIC_SOURCES}				\
 				drivers/arm/cci/cci.c				\
 				drivers/ti/uart/aarch64/16550_console.S		\
diff --git a/plat/rockchip/rk3368/platform.mk b/plat/rockchip/rk3368/platform.mk
index cb0cb89..e6c62de 100644
--- a/plat/rockchip/rk3368/platform.mk
+++ b/plat/rockchip/rk3368/platform.mk
@@ -4,6 +4,8 @@
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
+include drivers/arm/gic/v2/gicv2.mk
+
 RK_PLAT			:=	plat/rockchip
 RK_PLAT_SOC		:=	${RK_PLAT}/${PLAT}
 RK_PLAT_COMMON		:=	${RK_PLAT}/common
@@ -20,9 +22,7 @@
 				-I${RK_PLAT_SOC}/drivers/ddr/			\
 				-I${RK_PLAT_SOC}/include/
 
-RK_GIC_SOURCES         :=	drivers/arm/gic/common/gic_common.c		\
-				drivers/arm/gic/v2/gicv2_main.c			\
-				drivers/arm/gic/v2/gicv2_helpers.c		\
+RK_GIC_SOURCES         :=	${GICV2_SOURCES}				\
 				plat/common/plat_gicv2.c			\
 				${RK_PLAT}/common/rockchip_gicv2.c
 
@@ -33,6 +33,10 @@
 				plat/common/aarch64/crash_console_helpers.S	\
 				plat/common/plat_psci_common.c
 
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+PLAT_BL_COMMON_SOURCES	+=	${RK_PLAT_COMMON}/rockchip_stack_protector.c
+endif
+
 BL31_SOURCES		+=	${RK_GIC_SOURCES}				\
 				drivers/arm/cci/cci.c				\
 				drivers/ti/uart/aarch64/16550_console.S		\
diff --git a/plat/rockchip/rk3399/drivers/dram/dram.h b/plat/rockchip/rk3399/drivers/dram/dram.h
index 0eb12cf..5572b16 100644
--- a/plat/rockchip/rk3399/drivers/dram/dram.h
+++ b/plat/rockchip/rk3399/drivers/dram/dram.h
@@ -149,7 +149,7 @@
 	uint32_t rx_cal_dqs[2][4];
 };
 
-extern __sramdata struct rk3399_sdram_params sdram_config;
+extern struct rk3399_sdram_params sdram_config;
 
 void dram_init(void);
 
diff --git a/plat/rockchip/rk3399/drivers/dram/suspend.c b/plat/rockchip/rk3399/drivers/dram/suspend.c
index 7f9fad1..a8b1c32 100644
--- a/plat/rockchip/rk3399/drivers/dram/suspend.c
+++ b/plat/rockchip/rk3399/drivers/dram/suspend.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -49,6 +49,7 @@
 
 __pmusramdata uint32_t dpll_data[PLL_CON_COUNT];
 __pmusramdata uint32_t cru_clksel_con6;
+__pmusramdata uint8_t pmu_enable_watchdog0;
 
 /*
  * Copy @num registers from @src to @dst
@@ -562,8 +563,14 @@
 
 	/* LPDDR4 f2 cann't do training, all training will fail */
 	for (ch = 0; ch < ch_count; ch++) {
-		mmio_clrsetbits_32(PHY_REG(ch, 896), (0x3 << 8) | 1,
-				   fn << 8);
+		/*
+		 * Without this disabled for LPDDR4 we end up writing 0's
+		 * in place of real data in an interesting pattern.
+		 */
+		if (sdram_params->dramtype != LPDDR4) {
+			mmio_clrsetbits_32(PHY_REG(ch, 896), (0x3 << 8) | 1,
+					fn << 8);
+		}
 
 		/* data_training failed */
 		if (data_training(ch, sdram_params, PI_FULL_TRAINING))
@@ -748,13 +755,44 @@
 	phy_regs->phy896[0] &= ~(0x3 << 8);
 }
 
+__pmusramfunc void phy_dll_bypass_set(uint32_t ch, uint32_t freq)
+{
+	if (freq <= (125 * 1000 * 1000)) {
+		/* Set master mode to SW for slices*/
+		mmio_setbits_32(PHY_REG(ch, 86), 3 << 10);
+		mmio_setbits_32(PHY_REG(ch, 214), 3 << 10);
+		mmio_setbits_32(PHY_REG(ch, 342), 3 << 10);
+		mmio_setbits_32(PHY_REG(ch, 470), 3 << 10);
+		/* Set master mode to SW for address slices*/
+		mmio_setbits_32(PHY_REG(ch, 547), 3 << 18);
+		mmio_setbits_32(PHY_REG(ch, 675), 3 << 18);
+		mmio_setbits_32(PHY_REG(ch, 803), 3 << 18);
+	} else {
+		/* Clear SW master mode for slices*/
+		mmio_clrbits_32(PHY_REG(ch, 86), 3 << 10);
+		mmio_clrbits_32(PHY_REG(ch, 214), 3 << 10);
+		mmio_clrbits_32(PHY_REG(ch, 342), 3 << 10);
+		mmio_clrbits_32(PHY_REG(ch, 470), 3 << 10);
+		/* Clear SW master mode for address slices*/
+		mmio_clrbits_32(PHY_REG(ch, 547), 3 << 18);
+		mmio_clrbits_32(PHY_REG(ch, 675), 3 << 18);
+		mmio_clrbits_32(PHY_REG(ch, 803), 3 << 18);
+	}
+}
+
 __pmusramfunc void dmc_resume(void)
 {
 	struct rk3399_sdram_params *sdram_params = &sdram_config;
 	uint32_t channel_mask = 0;
 	uint32_t channel;
 
-	pmusram_enable_watchdog();
+	/*
+	 * We can't turn off the watchdog, so if we have not turned it on before
+	 * we should not turn it on here.
+	 */
+	if ((pmu_enable_watchdog0 & 0x1) == 0x1) {
+		pmusram_enable_watchdog();
+	}
 	pmu_sgrf_rst_hld_release();
 	restore_pmu_rsthold();
 	sram_secure_timer_init();
@@ -772,6 +810,13 @@
 retry:
 	for (channel = 0; channel < sdram_params->num_channels; channel++) {
 		phy_pctrl_reset(channel);
+		/*
+		 * Without this, LPDDR4 will write 0's in place of real data
+		 * in a strange pattern.
+		 */
+		if (sdram_params->dramtype == LPDDR4) {
+			phy_dll_bypass_set(channel, sdram_params->ddr_freq);
+		}
 		pctl_cfg(channel, sdram_params);
 	}
 
@@ -788,8 +833,12 @@
 		if (sdram_params->dramtype == LPDDR3)
 			sram_udelay(10);
 
-		/* If traning fail, retry to do it again. */
-		if (data_training(channel, sdram_params, PI_FULL_TRAINING))
+		/*
+		 * Training here will always fail for LPDDR4, so skip it
+		 * If traning fail, retry to do it again.
+		 */
+		if (sdram_params->dramtype != LPDDR4 &&
+		    data_training(channel, sdram_params, PI_FULL_TRAINING))
 			goto retry;
 
 		set_ddrconfig(sdram_params, channel,
diff --git a/plat/rockchip/rk3399/drivers/dram/suspend.h b/plat/rockchip/rk3399/drivers/dram/suspend.h
index b99a926..1389944 100644
--- a/plat/rockchip/rk3399/drivers/dram/suspend.h
+++ b/plat/rockchip/rk3399/drivers/dram/suspend.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,6 +7,7 @@
 #ifndef SUSPEND_H
 #define SUSPEND_H
 
+#include <stdint.h>
 #include <dram.h>
 
 #define KHz (1000)
@@ -22,5 +23,6 @@
 
 void dmc_suspend(void);
 __pmusramfunc void dmc_resume(void);
+extern __pmusramdata uint8_t pmu_enable_watchdog0;
 
 #endif /* SUSPEND_H */
diff --git a/plat/rockchip/rk3399/drivers/pmu/pmu.c b/plat/rockchip/rk3399/drivers/pmu/pmu.c
index faee678..3084c4f 100644
--- a/plat/rockchip/rk3399/drivers/pmu/pmu.c
+++ b/plat/rockchip/rk3399/drivers/pmu/pmu.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -1324,6 +1324,7 @@
 		store_wdt0[i] = mmio_read_32(WDT0_BASE + i * 4);
 		store_wdt1[i] = mmio_read_32(WDT1_BASE + i * 4);
 	}
+	pmu_enable_watchdog0 = (uint8_t) store_wdt0[0] & 0x1;
 }
 
 void wdt_register_restore(void)
diff --git a/plat/rockchip/rk3399/platform.mk b/plat/rockchip/rk3399/platform.mk
index a658fb2..aba67c2 100644
--- a/plat/rockchip/rk3399/platform.mk
+++ b/plat/rockchip/rk3399/platform.mk
@@ -38,6 +38,10 @@
 				plat/common/aarch64/crash_console_helpers.S \
 				plat/common/plat_psci_common.c
 
+ifneq (${ENABLE_STACK_PROTECTOR},0)
+PLAT_BL_COMMON_SOURCES	+=	${RK_PLAT_COMMON}/rockchip_stack_protector.c
+endif
+
 BL31_SOURCES	+=	${RK_GIC_SOURCES}				\
 			drivers/arm/cci/cci.c				\
 			drivers/ti/uart/aarch64/16550_console.S		\
diff --git a/plat/rpi/rpi4/include/rpi_hw.h b/plat/rpi/rpi4/include/rpi_hw.h
index 7185106..0430d46 100644
--- a/plat/rpi/rpi4/include/rpi_hw.h
+++ b/plat/rpi/rpi4/include/rpi_hw.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,14 +13,16 @@
  * Peripherals
  */
 
-#define RPI_IO_BASE			ULL(0xFE000000)
-#define RPI_IO_SIZE			ULL(0x02000000)
+#define RPI_IO_BASE			ULL(0xFC000000)
+#define RPI_IO_SIZE			ULL(0x04000000)
+
+#define RPI_LEGACY_BASE			(ULL(0x02000000) + RPI_IO_BASE)
 
 /*
  * ARM <-> VideoCore mailboxes
  */
 #define RPI3_MBOX_OFFSET		ULL(0x0000B880)
-#define RPI3_MBOX_BASE			(RPI_IO_BASE + RPI3_MBOX_OFFSET)
+#define RPI3_MBOX_BASE			(RPI_LEGACY_BASE + RPI3_MBOX_OFFSET)
 /* VideoCore -> ARM */
 #define RPI3_MBOX0_READ_OFFSET		ULL(0x00000000)
 #define RPI3_MBOX0_PEEK_OFFSET		ULL(0x00000010)
@@ -41,7 +43,7 @@
  * Power management, reset controller, watchdog.
  */
 #define RPI3_IO_PM_OFFSET		ULL(0x00100000)
-#define RPI3_PM_BASE			(RPI_IO_BASE + RPI3_IO_PM_OFFSET)
+#define RPI3_PM_BASE			(RPI_LEGACY_BASE + RPI3_IO_PM_OFFSET)
 /* Registers on top of RPI3_PM_BASE. */
 #define RPI3_PM_RSTC_OFFSET		ULL(0x0000001C)
 #define RPI3_PM_RSTS_OFFSET		ULL(0x00000020)
@@ -62,7 +64,7 @@
  * Hardware random number generator.
  */
 #define RPI3_IO_RNG_OFFSET		ULL(0x00104000)
-#define RPI3_RNG_BASE			(RPI_IO_BASE + RPI3_IO_RNG_OFFSET)
+#define RPI3_RNG_BASE			(RPI_LEGACY_BASE + RPI3_IO_RNG_OFFSET)
 #define RPI3_RNG_CTRL_OFFSET		ULL(0x00000000)
 #define RPI3_RNG_STATUS_OFFSET		ULL(0x00000004)
 #define RPI3_RNG_DATA_OFFSET		ULL(0x00000008)
@@ -82,22 +84,22 @@
  * There is also a PL011 UART, multiplexed to the same pins.
  */
 #define RPI4_IO_MINI_UART_OFFSET	ULL(0x00215040)
-#define RPI4_MINI_UART_BASE		(RPI_IO_BASE + RPI4_IO_MINI_UART_OFFSET)
+#define RPI4_MINI_UART_BASE		(RPI_LEGACY_BASE + RPI4_IO_MINI_UART_OFFSET)
 #define RPI4_IO_PL011_UART_OFFSET	ULL(0x00201000)
-#define RPI4_PL011_UART_BASE		(RPI_IO_BASE + RPI4_IO_PL011_UART_OFFSET)
+#define RPI4_PL011_UART_BASE		(RPI_LEGACY_BASE + RPI4_IO_PL011_UART_OFFSET)
 #define RPI4_PL011_UART_CLOCK		ULL(48000000)
 
 /*
  * GPIO controller
  */
 #define RPI3_IO_GPIO_OFFSET		ULL(0x00200000)
-#define RPI3_GPIO_BASE			(RPI_IO_BASE + RPI3_IO_GPIO_OFFSET)
+#define RPI3_GPIO_BASE			(RPI_LEGACY_BASE + RPI3_IO_GPIO_OFFSET)
 
 /*
  * SDHost controller
  */
 #define RPI3_IO_SDHOST_OFFSET           ULL(0x00202000)
-#define RPI3_SDHOST_BASE                (RPI_IO_BASE + RPI3_IO_SDHOST_OFFSET)
+#define RPI3_SDHOST_BASE                (RPI_LEGACY_BASE + RPI3_IO_SDHOST_OFFSET)
 
 /*
  * GIC interrupt controller
diff --git a/plat/rpi/rpi4/platform.mk b/plat/rpi/rpi4/platform.mk
index 0744bce..528eb1d 100644
--- a/plat/rpi/rpi4/platform.mk
+++ b/plat/rpi/rpi4/platform.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013-2019, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -7,6 +7,8 @@
 include lib/libfdt/libfdt.mk
 include lib/xlat_tables_v2/xlat_tables.mk
 
+include drivers/arm/gic/v2/gicv2.mk
+
 PLAT_INCLUDES		:=	-Iplat/rpi/common/include		\
 				-Iplat/rpi/rpi4/include
 
@@ -18,9 +20,6 @@
 BL31_SOURCES		+=	lib/cpus/aarch64/cortex_a72.S		\
 				plat/rpi/common/aarch64/plat_helpers.S	\
 				plat/rpi/rpi4/aarch64/armstub8_header.S	\
-				drivers/arm/gic/common/gic_common.c     \
-				drivers/arm/gic/v2/gicv2_helpers.c      \
-				drivers/arm/gic/v2/gicv2_main.c         \
 				drivers/delay_timer/delay_timer.c	\
 				drivers/gpio/gpio.c			\
 				drivers/rpi3/gpio/rpi3_gpio.c		\
@@ -30,7 +29,8 @@
 				plat/common/plat_psci_common.c		\
 				plat/rpi/common/rpi3_topology.c		\
 				common/fdt_fixup.c			\
-				${LIBFDT_SRCS}
+				${LIBFDT_SRCS}				\
+				${GICV2_SOURCES}
 
 # For now we only support BL31, using the kernel loaded by the GPU firmware.
 RESET_TO_BL31		:=	1
@@ -86,6 +86,9 @@
 # Use normal memory mapping for ROM, FIP, SRAM and DRAM
 RPI3_USE_UEFI_MAP		:= 0
 
+# SMCCC PCI support (should be enabled for ACPI builds)
+SMC_PCI_SUPPORT            	:= 0
+
 # Process platform flags
 # ----------------------
 
@@ -96,6 +99,7 @@
 endif
 $(eval $(call add_define,RPI3_RUNTIME_UART))
 $(eval $(call add_define,RPI3_USE_UEFI_MAP))
+$(eval $(call add_define,SMC_PCI_SUPPORT))
 
 ifeq (${ARCH},aarch32)
   $(error Error: AArch32 not supported on rpi4)
@@ -105,3 +109,8 @@
 PLAT_BL_COMMON_SOURCES	+=	drivers/rpi3/rng/rpi3_rng.c		\
 				plat/rpi/common/rpi3_stack_protector.c
 endif
+
+ifeq ($(SMC_PCI_SUPPORT), 1)
+BL31_SOURCES            +=      plat/rpi/rpi4/rpi4_pci_svc.c
+endif
+
diff --git a/plat/rpi/rpi4/rpi4_bl31_setup.c b/plat/rpi/rpi4/rpi4_bl31_setup.c
index cfacd1f..2fb4d3d 100644
--- a/plat/rpi/rpi4/rpi4_bl31_setup.c
+++ b/plat/rpi/rpi4/rpi4_bl31_setup.c
@@ -5,6 +5,8 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <libfdt.h>
 
@@ -201,6 +203,44 @@
 	enable_mmu_el3(0);
 }
 
+/*
+ * Remove the FDT /memreserve/ entry that covers the region at the very
+ * beginning of memory (if that exists). This is where the secondaries
+ * originally spin, but we pull them out there.
+ * Having overlapping /reserved-memory and /memreserve/ regions confuses
+ * the Linux kernel, so we need to get rid of this one.
+ */
+static void remove_spintable_memreserve(void *dtb)
+{
+	uint64_t addr, size;
+	int regions = fdt_num_mem_rsv(dtb);
+	int i;
+
+	for (i = 0; i < regions; i++) {
+		if (fdt_get_mem_rsv(dtb, i, &addr, &size) != 0) {
+			return;
+		}
+		if (size == 0U) {
+			return;
+		}
+		/* We only look for the region at the beginning of DRAM. */
+		if (addr != 0U) {
+			continue;
+		}
+		/*
+		 * Currently the region in the existing DTs is exactly 4K
+		 * in size. Should this value ever change, there is probably
+		 * a reason for that, so inform the user about this.
+		 */
+		if (size == 4096U) {
+			fdt_del_mem_rsv(dtb, i);
+			return;
+		}
+		WARN("Keeping unknown /memreserve/ region at 0, size: %" PRId64 "\n",
+		     size);
+	}
+}
+
 static void rpi4_prepare_dtb(void)
 {
 	void *dtb = (void *)rpi4_get_dtb_address();
@@ -227,7 +267,11 @@
 		return;
 	}
 
-	/* Reserve memory used by Trusted Firmware. */
+	/*
+	 * Remove the original reserved region (used for the spintable), and
+	 * replace it with a region describing the whole of Trusted Firmware.
+	 */
+	remove_spintable_memreserve(dtb);
 	if (fdt_add_reserved_memory(dtb, "atf@0", 0, 0x80000))
 		WARN("Failed to add reserved memory nodes to DT.\n");
 
diff --git a/plat/rpi/rpi4/rpi4_pci_svc.c b/plat/rpi/rpi4/rpi4_pci_svc.c
new file mode 100644
index 0000000..7d1ca5c
--- /dev/null
+++ b/plat/rpi/rpi4/rpi4_pci_svc.c
@@ -0,0 +1,215 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ * The RPi4 has a single nonstandard PCI config region. It is broken into two
+ * pieces, the root port config registers and a window to a single device's
+ * config space which can move between devices. There isn't (yet) an
+ * authoritative public document on this since the available BCM2711 reference
+ * notes that there is a PCIe root port in the memory map but doesn't describe
+ * it. Given that it's not ECAM compliant yet reasonably simple, it makes for
+ * an excellent example of the PCI SMCCC interface.
+ *
+ * The PCI SMCCC interface is described in DEN0115 availabe from:
+ * https://developer.arm.com/documentation/den0115/latest
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <lib/pmf/pmf.h>
+#include <lib/runtime_instr.h>
+#include <services/pci_svc.h>
+#include <services/sdei.h>
+#include <services/std_svc.h>
+#include <smccc_helpers.h>
+
+#include <lib/mmio.h>
+
+static spinlock_t pci_lock;
+
+#define PCIE_REG_BASE		U(RPI_IO_BASE + 0x01500000)
+#define PCIE_MISC_PCIE_STATUS	0x4068
+#define PCIE_EXT_CFG_INDEX	0x9000
+/* A small window pointing at the ECAM of the device selected by CFG_INDEX */
+#define PCIE_EXT_CFG_DATA	0x8000
+#define INVALID_PCI_ADDR	0xFFFFFFFF
+
+#define	PCIE_EXT_BUS_SHIFT	20
+#define	PCIE_EXT_DEV_SHIFT	15
+#define	PCIE_EXT_FUN_SHIFT	12
+
+
+static uint64_t pci_segment_lib_get_base(uint32_t address, uint32_t offset)
+{
+	uint64_t	base;
+	uint32_t	bus, dev, fun;
+	uint32_t	status;
+
+	base = PCIE_REG_BASE;
+
+	offset &= PCI_OFFSET_MASK;  /* Pick off the 4k register offset */
+
+	/* The root port is at the base of the PCIe register space */
+	if (address != 0U) {
+		/*
+		 * The current device must be at CFG_DATA, a 4K window mapped,
+		 * via CFG_INDEX, to the device we are accessing. At the same
+		 * time we must avoid accesses to certain areas of the cfg
+		 * space via CFG_DATA. Detect those accesses and report that
+		 * the address is invalid.
+		 */
+		base += PCIE_EXT_CFG_DATA;
+		bus = PCI_ADDR_BUS(address);
+		dev = PCI_ADDR_DEV(address);
+		fun = PCI_ADDR_FUN(address);
+		address = (bus << PCIE_EXT_BUS_SHIFT) |
+			  (dev << PCIE_EXT_DEV_SHIFT) |
+			  (fun << PCIE_EXT_FUN_SHIFT);
+
+		/* Allow only dev = 0 on root port and bus 1 */
+		if ((bus < 2U) && (dev > 0U)) {
+			return INVALID_PCI_ADDR;
+		}
+
+		/* Assure link up before reading bus 1 */
+		status = mmio_read_32(PCIE_REG_BASE + PCIE_MISC_PCIE_STATUS);
+		if ((status & 0x30) != 0x30) {
+			return INVALID_PCI_ADDR;
+		}
+
+		/* Adjust which device the CFG_DATA window is pointing at */
+		mmio_write_32(PCIE_REG_BASE + PCIE_EXT_CFG_INDEX, address);
+	}
+	return base + offset;
+}
+
+/**
+ * pci_read_config() - Performs a config space read at addr
+ * @addr: 32-bit, segment, BDF of requested function encoded per DEN0115
+ * @off:  register offset of function described by @addr to read
+ * @sz:	  size of read (8,16,32) bits.
+ * @val:  returned zero extended value read from config space
+ *
+ * sz bits of PCI config space is read at addr:offset, and the value
+ * is returned in val. Invalid segment/offset values return failure.
+ * Reads to valid functions that don't exist return INVALID_PCI_ADDR
+ * as is specified by PCI for requests that aren't completed by EPs.
+ * The boilerplate in pci_svc.c tends to do basic segment, off
+ * and sz validation. This routine should avoid duplicating those
+ * checks.
+ *
+ * This function maps directly to the PCI_READ function in DEN0115
+ * where detailed requirements may be found.
+ *
+ * Return: SMC_PCI_CALL_SUCCESS with val set
+ *	   SMC_PCI_CALL_INVAL_PARAM, on parameter error
+ */
+uint32_t pci_read_config(uint32_t addr, uint32_t off, uint32_t sz, uint32_t *val)
+{
+	uint32_t ret = SMC_PCI_CALL_SUCCESS;
+	uint64_t base;
+
+	spin_lock(&pci_lock);
+	base = pci_segment_lib_get_base(addr, off);
+
+	if (base == INVALID_PCI_ADDR) {
+		*val = base;
+	} else {
+		switch (sz) {
+		case SMC_PCI_SZ_8BIT:
+			*val = mmio_read_8(base);
+			break;
+		case SMC_PCI_SZ_16BIT:
+			*val = mmio_read_16(base);
+			break;
+		case SMC_PCI_SZ_32BIT:
+			*val = mmio_read_32(base);
+			break;
+		default: /* should be unreachable */
+			*val = 0;
+			ret = SMC_PCI_CALL_INVAL_PARAM;
+		}
+	}
+	spin_unlock(&pci_lock);
+	return ret;
+}
+
+/**
+ * pci_write_config() - Performs a config space write at addr
+ * @addr: 32-bit, segment, BDF of requested function encoded per DEN0115
+ * @off:  register offset of function described by @addr to write
+ * @sz:	  size of write (8,16,32) bits.
+ * @val:  value to be written
+ *
+ * sz bits of PCI config space is written at addr:offset. Invalid
+ * segment/BDF values return failure. Writes to valid functions
+ * without valid EPs are ignored, as is specified by PCI.
+ * The boilerplate in pci_svc.c tends to do basic segment, off
+ * and sz validation, so it shouldn't need to be repeated here.
+ *
+ * This function maps directly to the PCI_WRITE function in DEN0115
+ * where detailed requirements may be found.
+ *
+ * Return: SMC_PCI_CALL_SUCCESS
+ *	   SMC_PCI_CALL_INVAL_PARAM, on parameter error
+ */
+uint32_t pci_write_config(uint32_t addr, uint32_t off, uint32_t sz, uint32_t val)
+{
+	uint32_t ret = SMC_PCI_CALL_SUCCESS;
+	uint64_t base;
+
+	spin_lock(&pci_lock);
+	base = pci_segment_lib_get_base(addr, off);
+
+	if (base != INVALID_PCI_ADDR) {
+		switch (sz) {
+		case SMC_PCI_SZ_8BIT:
+			mmio_write_8(base, val);
+			break;
+		case SMC_PCI_SZ_16BIT:
+			mmio_write_16(base, val);
+			break;
+		case SMC_PCI_SZ_32BIT:
+			mmio_write_32(base, val);
+			break;
+		default: /* should be unreachable */
+			ret = SMC_PCI_CALL_INVAL_PARAM;
+		}
+	}
+	spin_unlock(&pci_lock);
+	return ret;
+}
+
+/**
+ * pci_get_bus_for_seg() - returns the start->end bus range for a segment
+ * @seg:  segment being queried
+ * @bus_range:	returned bus begin + (end << 8)
+ * @nseg: returns next segment in this machine or 0 for end
+ *
+ * pci_get_bus_for_seg is called to check if a given segment is
+ * valid on this machine. If it is valid, then its bus ranges are
+ * returned along with the next valid segment on the machine. If
+ * this is the last segment, then nseg must be 0.
+ *
+ * This function maps directly to the PCI_GET_SEG_INFO function
+ * in DEN0115 where detailed requirements may be found.
+ *
+ * Return: SMC_PCI_CALL_SUCCESS, and appropriate bus_range and nseg
+ *	   SMC_PCI_CALL_NOT_IMPL, if the segment is invalid
+ */
+uint32_t pci_get_bus_for_seg(uint32_t seg, uint32_t *bus_range, uint32_t *nseg)
+{
+	uint32_t ret = SMC_PCI_CALL_SUCCESS;
+	*nseg = 0U; /* only a single segment */
+	if (seg == 0U) {
+		*bus_range = 0xFF00; /* start 0, end 255 */
+	} else {
+		*bus_range = 0U;
+		ret = SMC_PCI_CALL_NOT_IMPL;
+	}
+	return ret;
+}
diff --git a/plat/socionext/synquacer/sq_psci.c b/plat/socionext/synquacer/sq_psci.c
index 0c97fcf..4168df9 100644
--- a/plat/socionext/synquacer/sq_psci.c
+++ b/plat/socionext/synquacer/sq_psci.c
@@ -97,6 +97,14 @@
 void sq_pwr_domain_off(const psci_power_state_t *target_state)
 {
 #if SQ_USE_SCMI_DRIVER
+	/* Prevent interrupts from spuriously waking up this cpu */
+	sq_gic_cpuif_disable();
+
+	/* Cluster is to be turned off, so disable coherency */
+	if (SQ_CLUSTER_PWR_STATE(target_state) == SQ_LOCAL_STATE_OFF) {
+		plat_sq_interconnect_exit_coherency();
+	}
+
 	sq_scmi_off(target_state);
 #else
 	sq_power_down_common(target_state);
diff --git a/plat/st/common/bl2_io_storage.c b/plat/st/common/bl2_io_storage.c
index 3ec7d40..b0314d2 100644
--- a/plat/st/common/bl2_io_storage.c
+++ b/plat/st/common/bl2_io_storage.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -7,13 +7,13 @@
 #include <assert.h>
 #include <string.h>
 
-#include <platform_def.h>
-
 #include <arch_helpers.h>
 #include <common/debug.h>
+#include <common/desc_image_load.h>
 #include <drivers/io/io_block.h>
 #include <drivers/io/io_driver.h>
-#include <drivers/io/io_dummy.h>
+#include <drivers/io/io_fip.h>
+#include <drivers/io/io_memmap.h>
 #include <drivers/io/io_mtd.h>
 #include <drivers/io/io_storage.h>
 #include <drivers/mmc.h>
@@ -22,31 +22,33 @@
 #include <drivers/spi_nand.h>
 #include <drivers/spi_nor.h>
 #include <drivers/st/io_mmc.h>
-#include <drivers/st/io_stm32image.h>
 #include <drivers/st/stm32_fmc2_nand.h>
 #include <drivers/st/stm32_qspi.h>
 #include <drivers/st/stm32_sdmmc2.h>
+#include <drivers/usb_device.h>
+#include <lib/fconf/fconf.h>
 #include <lib/mmio.h>
 #include <lib/utils.h>
 #include <plat/common/platform.h>
+#include <tools_share/firmware_image_package.h>
+
+#include <platform_def.h>
+#include <stm32cubeprogrammer.h>
+#include <stm32mp_fconf_getter.h>
+#include <usb_dfu.h>
 
 /* IO devices */
-static const io_dev_connector_t *dummy_dev_con;
-static uintptr_t dummy_dev_handle;
-static uintptr_t dummy_dev_spec;
+uintptr_t fip_dev_handle;
+uintptr_t storage_dev_handle;
 
-static uintptr_t image_dev_handle;
-static uintptr_t storage_dev_handle;
+static const io_dev_connector_t *fip_dev_con;
 
 #if STM32MP_SDMMC || STM32MP_EMMC
-static io_block_spec_t gpt_block_spec = {
-	.offset = 0,
-	.length = 34 * MMC_BLOCK_SIZE, /* Size of GPT table */
-};
+static struct mmc_device_info mmc_info;
 
 static uint32_t block_buffer[MMC_BLOCK_SIZE] __aligned(MMC_BLOCK_SIZE);
 
-static const io_block_dev_spec_t mmc_block_dev_spec = {
+static io_block_dev_spec_t mmc_block_dev_spec = {
 	/* It's used as temp buffer in block driver */
 	.buffer = {
 		.offset = (size_t)&block_buffer,
@@ -76,6 +78,7 @@
 	.ops = {
 		.init = nand_raw_init,
 		.read = nand_read,
+		.seek = nand_seek_bb
 	},
 };
 
@@ -87,6 +90,7 @@
 	.ops = {
 		.init = spi_nand_init,
 		.read = nand_read,
+		.seek = nand_seek_bb
 	},
 };
 #endif
@@ -95,146 +99,21 @@
 static const io_dev_connector_t *spi_dev_con;
 #endif
 
-#ifdef AARCH32_SP_OPTEE
-static const struct stm32image_part_info optee_header_partition_spec = {
-	.name = OPTEE_HEADER_IMAGE_NAME,
-	.binary_type = OPTEE_HEADER_BINARY_TYPE,
-};
-
-static const struct stm32image_part_info optee_pager_partition_spec = {
-	.name = OPTEE_PAGER_IMAGE_NAME,
-	.binary_type = OPTEE_PAGER_BINARY_TYPE,
-};
-
-static const struct stm32image_part_info optee_paged_partition_spec = {
-	.name = OPTEE_PAGED_IMAGE_NAME,
-	.binary_type = OPTEE_PAGED_BINARY_TYPE,
-};
-#else
-static const io_block_spec_t bl32_block_spec = {
-	.offset = BL32_BASE,
-	.length = STM32MP_BL32_SIZE
-};
+#if STM32MP_USB_PROGRAMMER
+static const io_dev_connector_t *memmap_dev_con;
 #endif
 
-static const io_block_spec_t bl2_block_spec = {
-	.offset = BL2_BASE,
-	.length = STM32MP_BL2_SIZE,
+io_block_spec_t image_block_spec = {
+	.offset = 0U,
+	.length = 0U,
 };
 
-static const struct stm32image_part_info bl33_partition_spec = {
-	.name = BL33_IMAGE_NAME,
-	.binary_type = BL33_BINARY_TYPE,
-};
-
-enum {
-	IMG_IDX_BL33,
-#ifdef AARCH32_SP_OPTEE
-	IMG_IDX_OPTEE_HEADER,
-	IMG_IDX_OPTEE_PAGER,
-	IMG_IDX_OPTEE_PAGED,
-#endif
-	IMG_IDX_NUM
-};
-
-static struct stm32image_device_info stm32image_dev_info_spec __unused = {
-	.lba_size = MMC_BLOCK_SIZE,
-	.part_info[IMG_IDX_BL33] = {
-		.name = BL33_IMAGE_NAME,
-		.binary_type = BL33_BINARY_TYPE,
-	},
-#ifdef AARCH32_SP_OPTEE
-	.part_info[IMG_IDX_OPTEE_HEADER] = {
-		.name = OPTEE_HEADER_IMAGE_NAME,
-		.binary_type = OPTEE_HEADER_BINARY_TYPE,
-	},
-	.part_info[IMG_IDX_OPTEE_PAGER] = {
-		.name = OPTEE_PAGER_IMAGE_NAME,
-		.binary_type = OPTEE_PAGER_BINARY_TYPE,
-	},
-	.part_info[IMG_IDX_OPTEE_PAGED] = {
-		.name = OPTEE_PAGED_IMAGE_NAME,
-		.binary_type = OPTEE_PAGED_BINARY_TYPE,
-	},
-#endif
-};
-
-static io_block_spec_t stm32image_block_spec = {
-	.offset = 0,
-	.length = 0,
-};
-
-static const io_dev_connector_t *stm32image_dev_con __unused;
-
-static int open_dummy(const uintptr_t spec);
-static int open_image(const uintptr_t spec);
-static int open_storage(const uintptr_t spec);
-
-struct plat_io_policy {
-	uintptr_t *dev_handle;
-	uintptr_t image_spec;
-	int (*check)(const uintptr_t spec);
-};
-
-static const struct plat_io_policy policies[] = {
-	[BL2_IMAGE_ID] = {
-		.dev_handle = &dummy_dev_handle,
-		.image_spec = (uintptr_t)&bl2_block_spec,
-		.check = open_dummy
-	},
-#ifdef AARCH32_SP_OPTEE
-	[BL32_IMAGE_ID] = {
-		.dev_handle = &image_dev_handle,
-		.image_spec = (uintptr_t)&optee_header_partition_spec,
-		.check = open_image
-	},
-	[BL32_EXTRA1_IMAGE_ID] = {
-		.dev_handle = &image_dev_handle,
-		.image_spec = (uintptr_t)&optee_pager_partition_spec,
-		.check = open_image
-	},
-	[BL32_EXTRA2_IMAGE_ID] = {
-		.dev_handle = &image_dev_handle,
-		.image_spec = (uintptr_t)&optee_paged_partition_spec,
-		.check = open_image
-	},
-#else
-	[BL32_IMAGE_ID] = {
-		.dev_handle = &dummy_dev_handle,
-		.image_spec = (uintptr_t)&bl32_block_spec,
-		.check = open_dummy
-	},
-#endif
-	[BL33_IMAGE_ID] = {
-		.dev_handle = &image_dev_handle,
-		.image_spec = (uintptr_t)&bl33_partition_spec,
-		.check = open_image
-	},
-#if STM32MP_SDMMC || STM32MP_EMMC
-	[GPT_IMAGE_ID] = {
-		.dev_handle = &storage_dev_handle,
-		.image_spec = (uintptr_t)&gpt_block_spec,
-		.check = open_storage
-	},
-#endif
-	[STM32_IMAGE_ID] = {
-		.dev_handle = &storage_dev_handle,
-		.image_spec = (uintptr_t)&stm32image_block_spec,
-		.check = open_storage
-	}
-};
-
-static int open_dummy(const uintptr_t spec)
+int open_fip(const uintptr_t spec)
 {
-	return io_dev_init(dummy_dev_handle, 0);
+	return io_dev_init(fip_dev_handle, (uintptr_t)FIP_IMAGE_ID);
 }
 
-static int open_image(const uintptr_t spec)
-{
-	return io_dev_init(image_dev_handle, 0);
-}
-
-static int open_storage(const uintptr_t spec)
+int open_storage(const uintptr_t spec)
 {
 	return io_dev_init(storage_dev_handle, 0);
 }
@@ -257,8 +136,12 @@
 	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_QSPI:
 		INFO("Using SPI NAND\n");
 		break;
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_SERIAL_USB:
+		INFO("Using USB\n");
+		break;
 	default:
-		ERROR("Boot interface not found\n");
+		ERROR("Boot interface %u not found\n",
+		      boot_context->boot_interface_selected);
 		panic();
 		break;
 	}
@@ -273,16 +156,11 @@
 		     uint16_t boot_interface_instance)
 {
 	int io_result __unused;
-	uint8_t idx;
-	struct stm32image_part_info *part;
 	struct stm32_sdmmc2_params params;
-	struct mmc_device_info device_info;
-	const partition_entry_t *entry;
 
-	zeromem(&device_info, sizeof(struct mmc_device_info));
 	zeromem(&params, sizeof(struct stm32_sdmmc2_params));
 
-	device_info.mmc_dev_type = mmc_dev_type;
+	mmc_info.mmc_dev_type = mmc_dev_type;
 
 	switch (boot_interface_instance) {
 	case 1:
@@ -304,7 +182,7 @@
 		break;
 	}
 
-	params.device_info = &device_info;
+	params.device_info = &mmc_info;
 	if (stm32_sdmmc2_mmc_init(&params) != 0) {
 		ERROR("SDMMC%u init failed\n", boot_interface_instance);
 		panic();
@@ -319,44 +197,6 @@
 	io_result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_block_dev_spec,
 				&storage_dev_handle);
 	assert(io_result == 0);
-
-	partition_init(GPT_IMAGE_ID);
-
-	io_result = io_dev_close(storage_dev_handle);
-	assert(io_result == 0);
-
-	stm32image_dev_info_spec.device_size =
-		stm32_sdmmc2_mmc_get_device_size();
-
-	for (idx = 0U; idx < IMG_IDX_NUM; idx++) {
-		part = &stm32image_dev_info_spec.part_info[idx];
-		entry = get_partition_entry(part->name);
-		if (entry == NULL) {
-			ERROR("Partition %s not found\n", part->name);
-			panic();
-		}
-
-		part->part_offset = entry->start;
-		part->bkp_offset = 0U;
-	}
-
-	/*
-	 * Re-open MMC with io_mmc, for better perfs compared to
-	 * io_block.
-	 */
-	io_result = register_io_dev_mmc(&mmc_dev_con);
-	assert(io_result == 0);
-
-	io_result = io_dev_open(mmc_dev_con, 0, &storage_dev_handle);
-	assert(io_result == 0);
-
-	io_result = register_io_dev_stm32image(&stm32image_dev_con);
-	assert(io_result == 0);
-
-	io_result = io_dev_open(stm32image_dev_con,
-				(uintptr_t)&stm32image_dev_info_spec,
-				&image_dev_handle);
-	assert(io_result == 0);
 }
 #endif /* STM32MP_SDMMC || STM32MP_EMMC */
 
@@ -364,8 +204,6 @@
 static void boot_spi_nor(boot_api_context_t *boot_context)
 {
 	int io_result __unused;
-	uint8_t idx;
-	struct stm32image_part_info *part;
 
 	io_result = stm32_qspi_init();
 	assert(io_result == 0);
@@ -378,38 +216,6 @@
 				(uintptr_t)&spi_nor_dev_spec,
 				&storage_dev_handle);
 	assert(io_result == 0);
-
-	stm32image_dev_info_spec.device_size = spi_nor_dev_spec.device_size;
-
-	idx = IMG_IDX_BL33;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NOR_BL33_OFFSET;
-	part->bkp_offset = 0U;
-
-#ifdef AARCH32_SP_OPTEE
-	idx = IMG_IDX_OPTEE_HEADER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NOR_TEEH_OFFSET;
-	part->bkp_offset = 0U;
-
-	idx = IMG_IDX_OPTEE_PAGED;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NOR_TEED_OFFSET;
-	part->bkp_offset = 0U;
-
-	idx = IMG_IDX_OPTEE_PAGER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NOR_TEEX_OFFSET;
-	part->bkp_offset = 0U;
-#endif
-
-	io_result = register_io_dev_stm32image(&stm32image_dev_con);
-	assert(io_result == 0);
-
-	io_result = io_dev_open(stm32image_dev_con,
-				(uintptr_t)&stm32image_dev_info_spec,
-				&image_dev_handle);
-	assert(io_result == 0);
 }
 #endif /* STM32MP_SPI_NOR */
 
@@ -417,8 +223,6 @@
 static void boot_fmc2_nand(boot_api_context_t *boot_context)
 {
 	int io_result __unused;
-	uint8_t idx;
-	struct stm32image_part_info *part;
 
 	io_result = stm32_fmc2_init();
 	assert(io_result == 0);
@@ -431,38 +235,6 @@
 	io_result = io_dev_open(nand_dev_con, (uintptr_t)&nand_dev_spec,
 				&storage_dev_handle);
 	assert(io_result == 0);
-
-	stm32image_dev_info_spec.device_size = nand_dev_spec.device_size;
-
-	idx = IMG_IDX_BL33;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_BL33_OFFSET;
-	part->bkp_offset = nand_dev_spec.erase_size;
-
-#ifdef AARCH32_SP_OPTEE
-	idx = IMG_IDX_OPTEE_HEADER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEEH_OFFSET;
-	part->bkp_offset = nand_dev_spec.erase_size;
-
-	idx = IMG_IDX_OPTEE_PAGED;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEED_OFFSET;
-	part->bkp_offset = nand_dev_spec.erase_size;
-
-	idx = IMG_IDX_OPTEE_PAGER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEEX_OFFSET;
-	part->bkp_offset = nand_dev_spec.erase_size;
-#endif
-
-	io_result = register_io_dev_stm32image(&stm32image_dev_con);
-	assert(io_result == 0);
-
-	io_result = io_dev_open(stm32image_dev_con,
-				(uintptr_t)&stm32image_dev_info_spec,
-				&image_dev_handle);
-	assert(io_result == 0);
 }
 #endif /* STM32MP_RAW_NAND */
 
@@ -470,8 +242,6 @@
 static void boot_spi_nand(boot_api_context_t *boot_context)
 {
 	int io_result __unused;
-	uint8_t idx;
-	struct stm32image_part_info *part;
 
 	io_result = stm32_qspi_init();
 	assert(io_result == 0);
@@ -484,42 +254,35 @@
 				(uintptr_t)&spi_nand_dev_spec,
 				&storage_dev_handle);
 	assert(io_result == 0);
-
-	stm32image_dev_info_spec.device_size =
-		spi_nand_dev_spec.device_size;
-
-	idx = IMG_IDX_BL33;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_BL33_OFFSET;
-	part->bkp_offset = spi_nand_dev_spec.erase_size;
-
-#ifdef AARCH32_SP_OPTEE
-	idx = IMG_IDX_OPTEE_HEADER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEEH_OFFSET;
-	part->bkp_offset = spi_nand_dev_spec.erase_size;
-
-	idx = IMG_IDX_OPTEE_PAGED;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEED_OFFSET;
-	part->bkp_offset = spi_nand_dev_spec.erase_size;
-
-	idx = IMG_IDX_OPTEE_PAGER;
-	part = &stm32image_dev_info_spec.part_info[idx];
-	part->part_offset = STM32MP_NAND_TEEX_OFFSET;
-	part->bkp_offset = spi_nand_dev_spec.erase_size;
-#endif
-
-	io_result = register_io_dev_stm32image(&stm32image_dev_con);
-	assert(io_result == 0);
-
-	io_result = io_dev_open(stm32image_dev_con,
-				(uintptr_t)&stm32image_dev_info_spec,
-				&image_dev_handle);
-	assert(io_result == 0);
 }
 #endif /* STM32MP_SPI_NAND */
 
+#if STM32MP_USB_PROGRAMMER
+static void mmap_io_setup(void)
+{
+	int io_result __unused;
+
+	io_result = register_io_dev_memmap(&memmap_dev_con);
+	assert(io_result == 0);
+
+	io_result = io_dev_open(memmap_dev_con, (uintptr_t)NULL,
+				&storage_dev_handle);
+	assert(io_result == 0);
+}
+
+static void stm32cubeprogrammer_usb(void)
+{
+	int ret __unused;
+	struct usb_handle *pdev;
+
+	/* Init USB on platform */
+	pdev = usb_dfu_plat_init();
+
+	ret = stm32cubeprog_usb_load(pdev, DWL_BUFFER_BASE, DWL_BUFFER_SIZE);
+	assert(ret == 0);
+}
+#endif
+
 void stm32mp_io_setup(void)
 {
 	int io_result __unused;
@@ -530,16 +293,15 @@
 
 	if ((boot_context->boot_partition_used_toboot == 1U) ||
 	    (boot_context->boot_partition_used_toboot == 2U)) {
-		INFO("Boot used partition fsbl%d\n",
+		INFO("Boot used partition fsbl%u\n",
 		     boot_context->boot_partition_used_toboot);
 	}
 
-	io_result = register_io_dev_dummy(&dummy_dev_con);
+	io_result = register_io_dev_fip(&fip_dev_con);
 	assert(io_result == 0);
 
-	io_result = io_dev_open(dummy_dev_con, dummy_dev_spec,
-				&dummy_dev_handle);
-	assert(io_result == 0);
+	io_result = io_dev_open(fip_dev_con, (uintptr_t)NULL,
+				&fip_dev_handle);
 
 	switch (boot_context->boot_interface_selected) {
 #if STM32MP_SDMMC
@@ -572,14 +334,91 @@
 		boot_spi_nand(boot_context);
 		break;
 #endif
+#if STM32MP_USB_PROGRAMMER
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_SERIAL_USB:
+		dmbsy();
+		mmap_io_setup();
+		break;
+#endif
 
 	default:
 		ERROR("Boot interface %d not supported\n",
 		      boot_context->boot_interface_selected);
+		panic();
 		break;
 	}
 }
 
+int bl2_plat_handle_pre_image_load(unsigned int image_id)
+{
+	static bool gpt_init_done __unused;
+	uint16_t boot_itf = stm32mp_get_boot_itf_selected();
+
+	switch (boot_itf) {
+#if STM32MP_SDMMC || STM32MP_EMMC
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_SD:
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_EMMC:
+		if (!gpt_init_done) {
+			const partition_entry_t *entry;
+
+			partition_init(GPT_IMAGE_ID);
+			entry = get_partition_entry(FIP_IMAGE_NAME);
+			if (entry == NULL) {
+				ERROR("Could NOT find the %s partition!\n",
+				      FIP_IMAGE_NAME);
+				return -ENOENT;
+			}
+
+			image_block_spec.offset = entry->start;
+			image_block_spec.length = entry->length;
+
+			gpt_init_done = true;
+		} else {
+			bl_mem_params_node_t *bl_mem_params = get_bl_mem_params_node(image_id);
+
+			mmc_block_dev_spec.buffer.offset = bl_mem_params->image_info.image_base;
+			mmc_block_dev_spec.buffer.length = bl_mem_params->image_info.image_max_size;
+		}
+
+		break;
+#endif
+
+#if STM32MP_RAW_NAND || STM32MP_SPI_NAND
+#if STM32MP_RAW_NAND
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_FMC:
+#endif
+#if STM32MP_SPI_NAND
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_QSPI:
+#endif
+		image_block_spec.offset = STM32MP_NAND_FIP_OFFSET;
+		break;
+#endif
+
+#if STM32MP_SPI_NOR
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NOR_QSPI:
+		image_block_spec.offset = STM32MP_NOR_FIP_OFFSET;
+		break;
+#endif
+
+#if STM32MP_USB_PROGRAMMER
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_SERIAL_USB:
+		if (image_id == FW_CONFIG_ID) {
+			stm32cubeprogrammer_usb();
+			/* FIP loaded at DWL address */
+			image_block_spec.offset = DWL_BUFFER_BASE;
+			image_block_spec.length = DWL_BUFFER_SIZE;
+		}
+		break;
+#endif
+
+	default:
+		ERROR("FIP Not found\n");
+		panic();
+	}
+
+	return 0;
+}
+
 /*
  * Return an IO device handle and specification which can be used to access
  * an image. Use this to enforce platform load policy.
@@ -590,9 +429,7 @@
 	int rc;
 	const struct plat_io_policy *policy;
 
-	assert(image_id < ARRAY_SIZE(policies));
-
-	policy = &policies[image_id];
+	policy = FCONF_GET_PROPERTY(stm32mp, io_policies, image_id);
 	rc = policy->check(policy->image_spec);
 	if (rc == 0) {
 		*image_spec = policy->image_spec;
diff --git a/plat/st/common/bl2_stm32_io_storage.c b/plat/st/common/bl2_stm32_io_storage.c
new file mode 100644
index 0000000..2d68a50
--- /dev/null
+++ b/plat/st/common/bl2_stm32_io_storage.c
@@ -0,0 +1,665 @@
+/*
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <common/debug.h>
+#include <drivers/io/io_block.h>
+#include <drivers/io/io_driver.h>
+#include <drivers/io/io_dummy.h>
+#include <drivers/io/io_mtd.h>
+#include <drivers/io/io_storage.h>
+#include <drivers/mmc.h>
+#include <drivers/partition/partition.h>
+#include <drivers/raw_nand.h>
+#include <drivers/spi_nand.h>
+#include <drivers/spi_nor.h>
+#include <drivers/st/io_mmc.h>
+#include <drivers/st/io_stm32image.h>
+#include <drivers/st/stm32_fmc2_nand.h>
+#include <drivers/st/stm32_qspi.h>
+#include <drivers/st/stm32_sdmmc2.h>
+#include <lib/mmio.h>
+#include <lib/utils.h>
+#include <plat/common/platform.h>
+
+#include <platform_def.h>
+
+/* IO devices */
+#ifndef AARCH32_SP_OPTEE
+static const io_dev_connector_t *dummy_dev_con;
+static uintptr_t dummy_dev_handle;
+static uintptr_t dummy_dev_spec;
+#endif
+
+static uintptr_t image_dev_handle;
+static uintptr_t storage_dev_handle;
+
+#if STM32MP_SDMMC || STM32MP_EMMC
+static struct mmc_device_info mmc_info;
+static io_block_spec_t gpt_block_spec = {
+	.offset = 0U,
+	.length = 34U * MMC_BLOCK_SIZE, /* Size of GPT table */
+};
+
+static uint32_t block_buffer[MMC_BLOCK_SIZE] __aligned(MMC_BLOCK_SIZE);
+
+static const io_block_dev_spec_t mmc_block_dev_spec = {
+	/* It's used as temp buffer in block driver */
+	.buffer = {
+		.offset = (size_t)&block_buffer,
+		.length = MMC_BLOCK_SIZE,
+	},
+	.ops = {
+		.read = mmc_read_blocks,
+		.write = NULL,
+	},
+	.block_size = MMC_BLOCK_SIZE,
+};
+
+#if STM32MP_EMMC_BOOT
+static io_block_spec_t emmc_boot_ssbl_block_spec = {
+	.offset = PLAT_EMMC_BOOT_SSBL_OFFSET,
+	.length = MMC_BLOCK_SIZE, /* We are interested only in first 4 bytes */
+};
+
+static const io_block_dev_spec_t mmc_block_dev_boot_part_spec = {
+	/* It's used as temp buffer in block driver */
+	.buffer = {
+		.offset = (size_t)&block_buffer,
+		.length = MMC_BLOCK_SIZE,
+	},
+	.ops = {
+		.read = mmc_boot_part_read_blocks,
+		.write = NULL,
+	},
+	.block_size = MMC_BLOCK_SIZE,
+};
+#endif
+
+static struct io_mmc_dev_spec mmc_device_spec = {
+	.use_boot_part = false,
+};
+
+static const io_dev_connector_t *mmc_dev_con;
+#endif /* STM32MP_SDMMC || STM32MP_EMMC */
+
+#if STM32MP_SPI_NOR
+static io_mtd_dev_spec_t spi_nor_dev_spec = {
+	.ops = {
+		.init = spi_nor_init,
+		.read = spi_nor_read,
+	},
+};
+#endif
+
+#if STM32MP_RAW_NAND
+static io_mtd_dev_spec_t nand_dev_spec = {
+	.ops = {
+		.init = nand_raw_init,
+		.read = nand_read,
+	},
+};
+
+static const io_dev_connector_t *nand_dev_con;
+#endif
+
+#if STM32MP_SPI_NAND
+static io_mtd_dev_spec_t spi_nand_dev_spec = {
+	.ops = {
+		.init = spi_nand_init,
+		.read = nand_read,
+	},
+};
+#endif
+
+#if STM32MP_SPI_NAND || STM32MP_SPI_NOR
+static const io_dev_connector_t *spi_dev_con;
+#endif
+
+#ifdef AARCH32_SP_OPTEE
+static const struct stm32image_part_info optee_header_partition_spec = {
+	.name = OPTEE_HEADER_IMAGE_NAME,
+	.binary_type = OPTEE_HEADER_BINARY_TYPE,
+};
+
+static const struct stm32image_part_info optee_core_partition_spec = {
+	.name = OPTEE_CORE_IMAGE_NAME,
+	.binary_type = OPTEE_CORE_BINARY_TYPE,
+};
+
+static const struct stm32image_part_info optee_paged_partition_spec = {
+	.name = OPTEE_PAGED_IMAGE_NAME,
+	.binary_type = OPTEE_PAGED_BINARY_TYPE,
+};
+#else
+static const io_block_spec_t bl32_block_spec = {
+	.offset = BL32_BASE,
+	.length = STM32MP_BL32_SIZE
+};
+#endif
+
+static const struct stm32image_part_info bl33_partition_spec = {
+	.name = BL33_IMAGE_NAME,
+	.binary_type = BL33_BINARY_TYPE,
+};
+
+enum {
+	IMG_IDX_BL33,
+#ifdef AARCH32_SP_OPTEE
+	IMG_IDX_OPTEE_HEADER,
+	IMG_IDX_OPTEE_CORE,
+	IMG_IDX_OPTEE_PAGED,
+#endif
+	IMG_IDX_NUM
+};
+
+static struct stm32image_device_info stm32image_dev_info_spec __unused = {
+	.lba_size = MMC_BLOCK_SIZE,
+	.part_info[IMG_IDX_BL33] = {
+		.name = BL33_IMAGE_NAME,
+		.binary_type = BL33_BINARY_TYPE,
+	},
+#ifdef AARCH32_SP_OPTEE
+	.part_info[IMG_IDX_OPTEE_HEADER] = {
+		.name = OPTEE_HEADER_IMAGE_NAME,
+		.binary_type = OPTEE_HEADER_BINARY_TYPE,
+	},
+	.part_info[IMG_IDX_OPTEE_CORE] = {
+		.name = OPTEE_CORE_IMAGE_NAME,
+		.binary_type = OPTEE_CORE_BINARY_TYPE,
+	},
+	.part_info[IMG_IDX_OPTEE_PAGED] = {
+		.name = OPTEE_PAGED_IMAGE_NAME,
+		.binary_type = OPTEE_PAGED_BINARY_TYPE,
+	},
+#endif
+};
+
+static io_block_spec_t stm32image_block_spec = {
+	.offset = 0U,
+	.length = 0U,
+};
+
+static const io_dev_connector_t *stm32image_dev_con __unused;
+
+#ifndef AARCH32_SP_OPTEE
+static int open_dummy(const uintptr_t spec);
+#endif
+static int open_image(const uintptr_t spec);
+static int open_storage(const uintptr_t spec);
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+static const struct plat_io_policy policies[] = {
+#ifdef AARCH32_SP_OPTEE
+	[BL32_IMAGE_ID] = {
+		.dev_handle = &image_dev_handle,
+		.image_spec = (uintptr_t)&optee_header_partition_spec,
+		.check = open_image
+	},
+	[BL32_EXTRA1_IMAGE_ID] = {
+		.dev_handle = &image_dev_handle,
+		.image_spec = (uintptr_t)&optee_core_partition_spec,
+		.check = open_image
+	},
+	[BL32_EXTRA2_IMAGE_ID] = {
+		.dev_handle = &image_dev_handle,
+		.image_spec = (uintptr_t)&optee_paged_partition_spec,
+		.check = open_image
+	},
+#else
+	[BL32_IMAGE_ID] = {
+		.dev_handle = &dummy_dev_handle,
+		.image_spec = (uintptr_t)&bl32_block_spec,
+		.check = open_dummy
+	},
+#endif
+	[BL33_IMAGE_ID] = {
+		.dev_handle = &image_dev_handle,
+		.image_spec = (uintptr_t)&bl33_partition_spec,
+		.check = open_image
+	},
+#if STM32MP_SDMMC || STM32MP_EMMC
+	[GPT_IMAGE_ID] = {
+		.dev_handle = &storage_dev_handle,
+		.image_spec = (uintptr_t)&gpt_block_spec,
+		.check = open_storage
+	},
+#endif
+	[STM32_IMAGE_ID] = {
+		.dev_handle = &storage_dev_handle,
+		.image_spec = (uintptr_t)&stm32image_block_spec,
+		.check = open_storage
+	}
+};
+
+#ifndef AARCH32_SP_OPTEE
+static int open_dummy(const uintptr_t spec)
+{
+	return io_dev_init(dummy_dev_handle, 0);
+}
+#endif
+
+static int open_image(const uintptr_t spec)
+{
+	return io_dev_init(image_dev_handle, 0);
+}
+
+static int open_storage(const uintptr_t spec)
+{
+	return io_dev_init(storage_dev_handle, 0);
+}
+
+#if STM32MP_EMMC_BOOT
+static uint32_t get_boot_part_ssbl_header(void)
+{
+	uint32_t magic = 0U;
+	int io_result;
+	size_t bytes_read;
+
+	io_result = register_io_dev_block(&mmc_dev_con);
+	if (io_result != 0) {
+		panic();
+	}
+
+	io_result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_block_dev_boot_part_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+
+	io_result = io_open(storage_dev_handle, (uintptr_t)&emmc_boot_ssbl_block_spec,
+			    &image_dev_handle);
+	assert(io_result == 0);
+
+	io_result = io_read(image_dev_handle, (uintptr_t)&magic, sizeof(magic),
+			    &bytes_read);
+	assert(io_result == 0);
+	assert(bytes_read == sizeof(magic));
+
+	io_result = io_dev_close(storage_dev_handle);
+	assert(io_result == 0);
+
+	return magic;
+}
+#endif
+
+static void print_boot_device(boot_api_context_t *boot_context)
+{
+	switch (boot_context->boot_interface_selected) {
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_SD:
+		INFO("Using SDMMC\n");
+		break;
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_EMMC:
+		INFO("Using EMMC\n");
+		break;
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NOR_QSPI:
+		INFO("Using QSPI NOR\n");
+		break;
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_FMC:
+		INFO("Using FMC NAND\n");
+		break;
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_QSPI:
+		INFO("Using SPI NAND\n");
+		break;
+	default:
+		ERROR("Boot interface not found\n");
+		panic();
+		break;
+	}
+
+	if (boot_context->boot_interface_instance != 0U) {
+		INFO("  Instance %d\n", boot_context->boot_interface_instance);
+	}
+}
+
+static void stm32image_io_setup(void)
+{
+	int io_result __unused;
+
+	io_result = register_io_dev_stm32image(&stm32image_dev_con);
+	assert(io_result == 0);
+
+	io_result = io_dev_open(stm32image_dev_con,
+				(uintptr_t)&stm32image_dev_info_spec,
+				&image_dev_handle);
+	assert(io_result == 0);
+}
+
+#if STM32MP_SDMMC || STM32MP_EMMC
+static void boot_mmc(enum mmc_device_type mmc_dev_type,
+		     uint16_t boot_interface_instance)
+{
+	int io_result __unused;
+	uint8_t idx;
+	struct stm32image_part_info *part;
+	struct stm32_sdmmc2_params params;
+	const partition_entry_t *entry __unused;
+	uint32_t magic __unused;
+
+	zeromem(&params, sizeof(struct stm32_sdmmc2_params));
+
+	mmc_info.mmc_dev_type = mmc_dev_type;
+
+	switch (boot_interface_instance) {
+	case 1:
+		params.reg_base = STM32MP_SDMMC1_BASE;
+		break;
+	case 2:
+		params.reg_base = STM32MP_SDMMC2_BASE;
+		break;
+	case 3:
+		params.reg_base = STM32MP_SDMMC3_BASE;
+		break;
+	default:
+		WARN("SDMMC instance not found, using default\n");
+		if (mmc_dev_type == MMC_IS_SD) {
+			params.reg_base = STM32MP_SDMMC1_BASE;
+		} else {
+			params.reg_base = STM32MP_SDMMC2_BASE;
+		}
+		break;
+	}
+
+	params.device_info = &mmc_info;
+	if (stm32_sdmmc2_mmc_init(&params) != 0) {
+		ERROR("SDMMC%u init failed\n", boot_interface_instance);
+		panic();
+	}
+
+	stm32image_dev_info_spec.device_size =
+		stm32_sdmmc2_mmc_get_device_size();
+
+#if STM32MP_EMMC_BOOT
+	magic = get_boot_part_ssbl_header();
+
+	if (magic == BOOT_API_IMAGE_HEADER_MAGIC_NB) {
+		VERBOSE("%s, header found, jump to emmc load\n", __func__);
+		idx = IMG_IDX_BL33;
+		part = &stm32image_dev_info_spec.part_info[idx];
+		part->part_offset = PLAT_EMMC_BOOT_SSBL_OFFSET;
+		part->bkp_offset = 0U;
+		mmc_device_spec.use_boot_part = true;
+
+		goto emmc_boot;
+	} else {
+		WARN("%s: Can't find STM32 header on a boot partition\n", __func__);
+	}
+#endif
+
+	/* Open MMC as a block device to read GPT table */
+	io_result = register_io_dev_block(&mmc_dev_con);
+	if (io_result != 0) {
+		panic();
+	}
+
+	io_result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_block_dev_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+
+	partition_init(GPT_IMAGE_ID);
+
+	io_result = io_dev_close(storage_dev_handle);
+	assert(io_result == 0);
+
+	for (idx = 0U; idx < IMG_IDX_NUM; idx++) {
+		part = &stm32image_dev_info_spec.part_info[idx];
+		entry = get_partition_entry(part->name);
+		if (entry == NULL) {
+			ERROR("Partition %s not found\n", part->name);
+			panic();
+		}
+
+		part->part_offset = entry->start;
+		part->bkp_offset = 0U;
+	}
+
+#if STM32MP_EMMC_BOOT
+emmc_boot:
+#endif
+	/*
+	 * Re-open MMC with io_mmc, for better perfs compared to
+	 * io_block.
+	 */
+	io_result = register_io_dev_mmc(&mmc_dev_con);
+	assert(io_result == 0);
+
+	io_result = io_dev_open(mmc_dev_con, (uintptr_t)&mmc_device_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+}
+#endif /* STM32MP_SDMMC || STM32MP_EMMC */
+
+#if STM32MP_SPI_NOR
+static void boot_spi_nor(boot_api_context_t *boot_context)
+{
+	int io_result __unused;
+	uint8_t idx;
+	struct stm32image_part_info *part;
+
+	io_result = stm32_qspi_init();
+	assert(io_result == 0);
+
+	io_result = register_io_dev_mtd(&spi_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to device */
+	io_result = io_dev_open(spi_dev_con,
+				(uintptr_t)&spi_nor_dev_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+
+	stm32image_dev_info_spec.device_size = spi_nor_dev_spec.device_size;
+
+	idx = IMG_IDX_BL33;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NOR_BL33_OFFSET;
+	part->bkp_offset = 0U;
+
+#ifdef AARCH32_SP_OPTEE
+	idx = IMG_IDX_OPTEE_HEADER;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NOR_TEEH_OFFSET;
+	part->bkp_offset = 0U;
+
+	idx = IMG_IDX_OPTEE_PAGED;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NOR_TEED_OFFSET;
+	part->bkp_offset = 0U;
+
+	idx = IMG_IDX_OPTEE_CORE;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NOR_TEEX_OFFSET;
+	part->bkp_offset = 0U;
+#endif
+}
+#endif /* STM32MP_SPI_NOR */
+
+#if STM32MP_RAW_NAND
+static void boot_fmc2_nand(boot_api_context_t *boot_context)
+{
+	int io_result __unused;
+	uint8_t idx;
+	struct stm32image_part_info *part;
+
+	io_result = stm32_fmc2_init();
+	assert(io_result == 0);
+
+	/* Register the IO device on this platform */
+	io_result = register_io_dev_mtd(&nand_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to device */
+	io_result = io_dev_open(nand_dev_con, (uintptr_t)&nand_dev_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+
+	stm32image_dev_info_spec.device_size = nand_dev_spec.device_size;
+
+	idx = IMG_IDX_BL33;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_BL33_OFFSET;
+	part->bkp_offset = nand_dev_spec.erase_size;
+
+#ifdef AARCH32_SP_OPTEE
+	idx = IMG_IDX_OPTEE_HEADER;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEEH_OFFSET;
+	part->bkp_offset = nand_dev_spec.erase_size;
+
+	idx = IMG_IDX_OPTEE_PAGED;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEED_OFFSET;
+	part->bkp_offset = nand_dev_spec.erase_size;
+
+	idx = IMG_IDX_OPTEE_CORE;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEEX_OFFSET;
+	part->bkp_offset = nand_dev_spec.erase_size;
+#endif
+}
+#endif /* STM32MP_RAW_NAND */
+
+#if STM32MP_SPI_NAND
+static void boot_spi_nand(boot_api_context_t *boot_context)
+{
+	int io_result __unused;
+	uint8_t idx;
+	struct stm32image_part_info *part;
+
+	io_result = stm32_qspi_init();
+	assert(io_result == 0);
+
+	io_result = register_io_dev_mtd(&spi_dev_con);
+	assert(io_result == 0);
+
+	/* Open connections to device */
+	io_result = io_dev_open(spi_dev_con,
+				(uintptr_t)&spi_nand_dev_spec,
+				&storage_dev_handle);
+	assert(io_result == 0);
+
+	stm32image_dev_info_spec.device_size =
+		spi_nand_dev_spec.device_size;
+
+	idx = IMG_IDX_BL33;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_BL33_OFFSET;
+	part->bkp_offset = spi_nand_dev_spec.erase_size;
+
+#ifdef AARCH32_SP_OPTEE
+	idx = IMG_IDX_OPTEE_HEADER;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEEH_OFFSET;
+	part->bkp_offset = spi_nand_dev_spec.erase_size;
+
+	idx = IMG_IDX_OPTEE_PAGED;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEED_OFFSET;
+	part->bkp_offset = spi_nand_dev_spec.erase_size;
+
+	idx = IMG_IDX_OPTEE_CORE;
+	part = &stm32image_dev_info_spec.part_info[idx];
+	part->part_offset = STM32MP_NAND_TEEX_OFFSET;
+	part->bkp_offset = spi_nand_dev_spec.erase_size;
+#endif
+}
+#endif /* STM32MP_SPI_NAND */
+
+void stm32mp_io_setup(void)
+{
+	int io_result __unused;
+	boot_api_context_t *boot_context =
+		(boot_api_context_t *)stm32mp_get_boot_ctx_address();
+
+	print_boot_device(boot_context);
+
+	if ((boot_context->boot_partition_used_toboot == 1U) ||
+	    (boot_context->boot_partition_used_toboot == 2U)) {
+		INFO("Boot used partition fsbl%u\n",
+		     boot_context->boot_partition_used_toboot);
+	}
+
+#ifndef AARCH32_SP_OPTEE
+	io_result = register_io_dev_dummy(&dummy_dev_con);
+	assert(io_result == 0);
+
+	io_result = io_dev_open(dummy_dev_con, dummy_dev_spec,
+				&dummy_dev_handle);
+	assert(io_result == 0);
+#endif
+
+	switch (boot_context->boot_interface_selected) {
+#if STM32MP_SDMMC
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_SD:
+		dmbsy();
+		boot_mmc(MMC_IS_SD, boot_context->boot_interface_instance);
+		stm32image_io_setup();
+		break;
+#endif
+#if STM32MP_EMMC
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_EMMC:
+		dmbsy();
+		boot_mmc(MMC_IS_EMMC, boot_context->boot_interface_instance);
+		stm32image_io_setup();
+		break;
+#endif
+#if STM32MP_SPI_NOR
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NOR_QSPI:
+		dmbsy();
+		boot_spi_nor(boot_context);
+		stm32image_io_setup();
+		break;
+#endif
+#if STM32MP_RAW_NAND
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_FMC:
+		dmbsy();
+		boot_fmc2_nand(boot_context);
+		stm32image_io_setup();
+		break;
+#endif
+#if STM32MP_SPI_NAND
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_QSPI:
+		dmbsy();
+		boot_spi_nand(boot_context);
+		stm32image_io_setup();
+		break;
+#endif
+
+	default:
+		ERROR("Boot interface %d not supported\n",
+		      boot_context->boot_interface_selected);
+		panic();
+		break;
+	}
+}
+
+/*
+ * Return an IO device handle and specification which can be used to access
+ * an image. Use this to enforce platform load policy.
+ */
+int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
+			  uintptr_t *image_spec)
+{
+	int rc;
+	const struct plat_io_policy *policy;
+
+	assert(image_id < ARRAY_SIZE(policies));
+
+	policy = &policies[image_id];
+	rc = policy->check(policy->image_spec);
+	if (rc == 0) {
+		*image_spec = policy->image_spec;
+		*dev_handle = *(policy->dev_handle);
+	}
+
+	return rc;
+}
diff --git a/plat/st/common/include/stm32cubeprogrammer.h b/plat/st/common/include/stm32cubeprogrammer.h
new file mode 100644
index 0000000..503d919
--- /dev/null
+++ b/plat/st/common/include/stm32cubeprogrammer.h
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef STM32CUBEPROGRAMMER_H
+#define STM32CUBEPROGRAMMER_H
+
+#include <stdint.h>
+
+#include <usb_dfu.h>
+
+/* Phase definition */
+#define PHASE_FLASHLAYOUT	0U
+#define PHASE_SSBL		3U
+#define PHASE_CMD		0xF1U
+#define PHASE_RESET		0xFFU
+
+/* Functions provided by plat */
+uint8_t usb_dfu_get_phase(uint8_t alt);
+
+int stm32cubeprog_usb_load(struct usb_handle *usb_core_handle,
+			   uintptr_t ssbl_base,
+			   size_t ssbl_len);
+
+#endif /* STM32CUBEPROGRAMMER_H */
diff --git a/plat/st/common/include/stm32mp_common.h b/plat/st/common/include/stm32mp_common.h
index feeb4a7..8a5fe48 100644
--- a/plat/st/common/include/stm32mp_common.h
+++ b/plat/st/common/include/stm32mp_common.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (C) 2018-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,9 +11,13 @@
 
 #include <platform_def.h>
 
+#define JEDEC_ST_BKID U(0x0)
+#define JEDEC_ST_MFID U(0x20)
+
 /* Functions to save and get boot context address given by ROM code */
 void stm32mp_save_boot_ctx_address(uintptr_t address);
 uintptr_t stm32mp_get_boot_ctx_address(void);
+uint16_t stm32mp_get_boot_itf_selected(void);
 
 bool stm32mp_is_single_core(void);
 bool stm32mp_is_closed_device(void);
@@ -64,6 +68,15 @@
 /* Return node offset for target GPIO bank ID @bank or a FDT error code */
 int stm32_get_gpio_bank_pinctrl_node(void *fdt, unsigned int bank);
 
+/* Get the chip revision */
+uint32_t stm32mp_get_chip_version(void);
+/* Get the chip device ID */
+uint32_t stm32mp_get_chip_dev_id(void);
+
+/* Get SOC name */
+#define STM32_SOC_NAME_SIZE 20
+void stm32mp_get_soc_name(char name[STM32_SOC_NAME_SIZE]);
+
 /* Print CPU information */
 void stm32mp_print_cpuinfo(void);
 
@@ -82,6 +95,7 @@
 /* Initialise the IO layer and register platform IO devices */
 void stm32mp_io_setup(void);
 
+#if STM32MP_USE_STM32IMAGE
 /*
  * Check that the STM32 header of a .stm32 binary image is valid
  * @param header: pointer to the stm32 image header
@@ -89,6 +103,7 @@
  * @return: 0 on success, negative value in case of error
  */
 int stm32mp_check_header(boot_api_image_header_t *header, uintptr_t buffer);
+#endif /* STM32MP_USE_STM32IMAGE */
 
 /* Functions to map DDR in MMU with non-cacheable attribute, and unmap it */
 int stm32mp_map_ddr_non_cacheable(void);
diff --git a/plat/st/common/include/stm32mp_dt.h b/plat/st/common/include/stm32mp_dt.h
index e3b4e59..f7201c0 100644
--- a/plat/st/common/include/stm32mp_dt.h
+++ b/plat/st/common/include/stm32mp_dt.h
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 2020, STMicroelectronics - All Rights Reserved
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,6 +9,7 @@
 #define STM32MP_DT_H
 
 #include <stdbool.h>
+#include <stdint.h>
 
 #define DT_DISABLED		U(0)
 #define DT_NON_SECURE		U(1)
@@ -25,7 +26,7 @@
 /*******************************************************************************
  * Function and variable prototypes
  ******************************************************************************/
-int dt_open_and_check(void);
+int dt_open_and_check(uintptr_t dt_addr);
 int fdt_get_address(void **fdt_addr);
 bool fdt_check_node(int node);
 uint8_t fdt_get_status(int node);
@@ -33,6 +34,7 @@
 void dt_fill_device_info(struct dt_node_info *info, int node);
 int dt_get_node(struct dt_node_info *info, int offset, const char *compat);
 int dt_get_stdout_uart_info(struct dt_node_info *info);
+int dt_match_instance_by_compatible(const char *compatible, uintptr_t address);
 uint32_t dt_get_ddr_size(void);
 uint32_t dt_get_pwr_vdd_voltage(void);
 const char *dt_get_board_model(void);
diff --git a/plat/st/common/include/stm32mp_fconf_getter.h b/plat/st/common/include/stm32mp_fconf_getter.h
new file mode 100644
index 0000000..3a8bb11
--- /dev/null
+++ b/plat/st/common/include/stm32mp_fconf_getter.h
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef STM32MP_FCONF_GETTER
+#define STM32MP_FCONF_GETTER
+
+#include <assert.h>
+
+#include <lib/fconf/fconf.h>
+
+/* IO policies */
+#define stm32mp__io_policies_getter(id) __extension__ ({	\
+	assert((id) < MAX_NUMBER_IDS);				\
+	&policies[id];						\
+})
+
+struct plat_io_policy {
+	uintptr_t *dev_handle;
+	uintptr_t image_spec;
+	int (*check)(const uintptr_t spec);
+};
+
+extern struct plat_io_policy policies[];
+int fconf_populate_stm32mp_io_policies(uintptr_t config);
+
+#endif /* STM32MP_FCONF_GETTER */
diff --git a/plat/st/common/include/stm32mp_io_storage.h b/plat/st/common/include/stm32mp_io_storage.h
new file mode 100644
index 0000000..989c890
--- /dev/null
+++ b/plat/st/common/include/stm32mp_io_storage.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+#ifndef STM32MP_IO_STORAGE_H
+#define STM32MP_IO_STORAGE_H
+
+#include <stdint.h>
+
+#include <drivers/io/io_storage.h>
+
+/* IO devices handle */
+extern uintptr_t storage_dev_handle;
+extern uintptr_t fip_dev_handle;
+
+extern io_block_spec_t image_block_spec;
+
+/* Function declarations */
+int open_fip(const uintptr_t spec);
+int open_storage(const uintptr_t spec);
+
+#endif /* STM32MP_IO_STORAGE_H */
diff --git a/plat/st/common/include/usb_dfu.h b/plat/st/common/include/usb_dfu.h
new file mode 100644
index 0000000..f7d4245
--- /dev/null
+++ b/plat/st/common/include/usb_dfu.h
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef USB_DFU_H
+#define USB_DFU_H
+
+#include <stdint.h>
+
+#include <drivers/usb_device.h>
+
+#define DFU_DESCRIPTOR_TYPE		0x21U
+
+/* Max DFU Packet Size = 1024 bytes */
+#define USBD_DFU_XFER_SIZE		1024U
+
+#define TRANSFER_SIZE_BYTES(size) \
+	((uint8_t)((size) & 0xFF)), /* XFERSIZEB0 */\
+	((uint8_t)((size) >> 8))    /* XFERSIZEB1 */
+
+/*
+ * helper for descriptor of DFU interface 0 Alternate setting n
+ * with iInterface = index of string descriptor, assumed Nth user string
+ */
+#define USBD_DFU_IF_DESC(n)	0x09U, /* Interface Descriptor size */\
+				USB_DESC_TYPE_INTERFACE, /* descriptor type */\
+				0x00U, /* Number of Interface */\
+				(n), /* Alternate setting */\
+				0x00U, /* bNumEndpoints*/\
+				0xFEU, /* Application Specific Class Code */\
+				0x01U, /* Device Firmware Upgrade Code */\
+				0x02U, /* DFU mode protocol */ \
+				USBD_IDX_USER0_STR + (n) /* iInterface */
+
+/* DFU1.1 Standard */
+#define USB_DFU_VERSION			0x0110U
+#define USB_DFU_ITF_SIZ			9U
+#define USB_DFU_DESC_SIZ(itf)		(USB_DFU_ITF_SIZ * ((itf) + 2U))
+
+/*
+ * bmAttribute value for DFU:
+ * bitCanDnload = 1(bit 0)
+ * bitCanUpload = 1(bit 1)
+ * bitManifestationTolerant = 1 (bit 2)
+ * bitWillDetach = 1(bit 3)
+ * Reserved (bit4-6)
+ * bitAcceleratedST = 0(bit 7)
+ */
+#define DFU_BM_ATTRIBUTE		0x0FU
+
+#define DFU_STATUS_SIZE			6U
+
+/* Callback for media access */
+struct usb_dfu_media {
+	int (*upload)(uint8_t alt, uintptr_t *buffer, uint32_t *len,
+		      void *user_data);
+	int (*download)(uint8_t alt, uintptr_t *buffer, uint32_t *len,
+			void *user_data);
+	int (*manifestation)(uint8_t alt, void *user_data);
+};
+
+/* Internal DFU handle */
+struct usb_dfu_handle {
+	uint8_t status[DFU_STATUS_SIZE];
+	uint8_t dev_state;
+	uint8_t dev_status;
+	uint8_t alt_setting;
+	const struct usb_dfu_media *callback;
+};
+
+void usb_dfu_register(struct usb_handle *pdev, struct usb_dfu_handle *phandle);
+
+int usb_dfu_loop(struct usb_handle *pdev, const struct usb_dfu_media *pmedia);
+
+/* Function provided by plat */
+struct usb_handle *usb_dfu_plat_init(void);
+
+#endif /* USB_DFU_H */
diff --git a/plat/st/common/stm32cubeprogrammer_usb.c b/plat/st/common/stm32cubeprogrammer_usb.c
new file mode 100644
index 0000000..19a6bba
--- /dev/null
+++ b/plat/st/common/stm32cubeprogrammer_usb.c
@@ -0,0 +1,196 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+
+#include <tools_share/firmware_image_package.h>
+
+#include <stm32cubeprogrammer.h>
+#include <usb_dfu.h>
+
+/* Undefined download address */
+#define UNDEFINED_DOWN_ADDR	0xFFFFFFFF
+
+struct dfu_state {
+	uint8_t phase;
+	uintptr_t base;
+	size_t len;
+	uintptr_t address;
+	/* working buffer */
+	uint8_t buffer[UCHAR_MAX];
+};
+
+static struct dfu_state dfu_state;
+
+/* minimal size of Get Pḧase = offset for additionnl information */
+#define	GET_PHASE_LEN	9
+
+#define DFU_ERROR(...) \
+	{ \
+		ERROR(__VA_ARGS__); \
+		if (dfu->phase != PHASE_RESET) { \
+			snprintf((char *)&dfu->buffer[GET_PHASE_LEN], \
+				 sizeof(dfu->buffer) - GET_PHASE_LEN, \
+				 __VA_ARGS__); \
+			dfu->phase = PHASE_RESET; \
+			dfu->address = UNDEFINED_DOWN_ADDR; \
+			dfu->len = 0; \
+		} \
+	}
+
+static bool is_valid_header(fip_toc_header_t *header)
+{
+	if ((header->name == TOC_HEADER_NAME) && (header->serial_number != 0U)) {
+		return true;
+	}
+
+	return false;
+}
+
+static int dfu_callback_upload(uint8_t alt, uintptr_t *buffer, uint32_t *len,
+			       void *user_data)
+{
+	int result = 0;
+	uint32_t length = 0;
+	struct dfu_state *dfu = (struct dfu_state *)user_data;
+
+	switch (usb_dfu_get_phase(alt)) {
+	case PHASE_CMD:
+		/* Get Pḧase */
+		dfu->buffer[0] = dfu->phase;
+		dfu->buffer[1] = (uint8_t)(dfu->address);
+		dfu->buffer[2] = (uint8_t)(dfu->address >> 8);
+		dfu->buffer[3] = (uint8_t)(dfu->address >> 16);
+		dfu->buffer[4] = (uint8_t)(dfu->address >> 24);
+		dfu->buffer[5] = 0x00;
+		dfu->buffer[6] = 0x00;
+		dfu->buffer[7] = 0x00;
+		dfu->buffer[8] = 0x00;
+		length = GET_PHASE_LEN;
+		if (dfu->phase == PHASE_FLASHLAYOUT &&
+		    dfu->address == UNDEFINED_DOWN_ADDR) {
+			INFO("Send detach request\n");
+			dfu->buffer[length++] = 0x01;
+		}
+		if (dfu->phase == PHASE_RESET) {
+			/* error information is added by DFU_ERROR macro */
+			length += strnlen((char *)&dfu->buffer[GET_PHASE_LEN],
+					  sizeof(dfu->buffer) - GET_PHASE_LEN)
+				  - 1;
+		}
+		break;
+
+	default:
+		DFU_ERROR("phase ID :%i, alternate %i for phase %i\n",
+			  dfu->phase, alt, usb_dfu_get_phase(alt));
+		result = -EIO;
+		break;
+	}
+
+	if (result == 0) {
+		*len = length;
+		*buffer = (uintptr_t)dfu->buffer;
+	}
+
+	return result;
+}
+
+static int dfu_callback_download(uint8_t alt, uintptr_t *buffer, uint32_t *len,
+				 void *user_data)
+{
+	struct dfu_state *dfu = (struct dfu_state *)user_data;
+
+	if ((dfu->phase != usb_dfu_get_phase(alt)) ||
+	    (dfu->address == UNDEFINED_DOWN_ADDR)) {
+		DFU_ERROR("phase ID :%i, alternate %i, address %x\n",
+			  dfu->phase, alt, (uint32_t)dfu->address);
+		return -EIO;
+	}
+
+	VERBOSE("Download %d %lx %x\n", alt, dfu->address, *len);
+	*buffer = dfu->address;
+	dfu->address += *len;
+
+	if (dfu->address - dfu->base > dfu->len) {
+		return -EIO;
+	}
+
+	return 0;
+}
+
+static int dfu_callback_manifestation(uint8_t alt, void *user_data)
+{
+	struct dfu_state *dfu = (struct dfu_state *)user_data;
+
+	if (dfu->phase != usb_dfu_get_phase(alt)) {
+		ERROR("Manifestation phase ID :%i, alternate %i, address %lx\n",
+		      dfu->phase, alt, dfu->address);
+		return -EIO;
+	}
+
+	INFO("phase ID :%i, Manifestation %d at %lx\n",
+	     dfu->phase, alt, dfu->address);
+
+	switch (dfu->phase) {
+	case PHASE_SSBL:
+		if (!is_valid_header((fip_toc_header_t *)dfu->base)) {
+			DFU_ERROR("FIP Header check failed for phase %d\n", alt);
+			return -EIO;
+		}
+		VERBOSE("FIP header looks OK.\n");
+
+		/* Configure End with request detach */
+		dfu->phase = PHASE_FLASHLAYOUT;
+		dfu->address = UNDEFINED_DOWN_ADDR;
+		dfu->len = 0;
+		break;
+	default:
+		DFU_ERROR("Unknown phase\n");
+	}
+
+	return 0;
+}
+
+/* Open a connection to the USB device */
+static const struct usb_dfu_media usb_dfu_fops = {
+	.upload = dfu_callback_upload,
+	.download = dfu_callback_download,
+	.manifestation = dfu_callback_manifestation,
+};
+
+int stm32cubeprog_usb_load(struct usb_handle *usb_core_handle,
+			   uintptr_t base,
+			   size_t len)
+{
+	int ret;
+
+	usb_core_handle->user_data = (void *)&dfu_state;
+
+	INFO("DFU USB START...\n");
+	ret = usb_core_start(usb_core_handle);
+	if (ret != USBD_OK) {
+		return -EIO;
+	}
+
+	dfu_state.phase = PHASE_SSBL;
+	dfu_state.address = base;
+	dfu_state.base = base;
+	dfu_state.len = len;
+
+	ret = usb_dfu_loop(usb_core_handle, &usb_dfu_fops);
+	if (ret != USBD_OK) {
+		return -EIO;
+	}
+
+	INFO("DFU USB STOP...\n");
+	ret = usb_core_stop(usb_core_handle);
+	if (ret != USBD_OK) {
+		return -EIO;
+	}
+
+	return 0;
+}
diff --git a/plat/st/common/stm32mp_common.c b/plat/st/common/stm32mp_common.c
index 89d8078..9120408 100644
--- a/plat/st/common/stm32mp_common.c
+++ b/plat/st/common/stm32mp_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -12,8 +12,12 @@
 #include <arch_helpers.h>
 #include <common/debug.h>
 #include <drivers/st/stm32mp_clkfunc.h>
+#include <lib/smccc.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
 #include <plat/common/platform.h>
+#include <services/arm_arch_svc.h>
+
+#define HEADER_VERSION_MAJOR_MASK	GENMASK(23, 16)
 
 uintptr_t plat_get_ns_image_entrypoint(void)
 {
@@ -26,10 +30,14 @@
 }
 
 static uintptr_t boot_ctx_address;
+static uint16_t boot_itf_selected;
 
 void stm32mp_save_boot_ctx_address(uintptr_t address)
 {
+	boot_api_context_t *boot_context = (boot_api_context_t *)address;
+
 	boot_ctx_address = address;
+	boot_itf_selected = boot_context->boot_interface_selected;
 }
 
 uintptr_t stm32mp_get_boot_ctx_address(void)
@@ -37,6 +45,11 @@
 	return boot_ctx_address;
 }
 
+uint16_t stm32mp_get_boot_itf_selected(void)
+{
+	return boot_itf_selected;
+}
+
 uintptr_t stm32mp_ddrctrl_base(void)
 {
 	return DDRCTRL_BASE;
@@ -65,6 +78,7 @@
 	return (read_sctlr() & c_m_bits) == c_m_bits;
 }
 
+#if STM32MP_USE_STM32IMAGE
 int stm32mp_check_header(boot_api_image_header_t *header, uintptr_t buffer)
 {
 	uint32_t i;
@@ -81,7 +95,8 @@
 		return -EINVAL;
 	}
 
-	if (header->header_version != BOOT_API_HEADER_VERSION) {
+	if ((header->header_version & HEADER_VERSION_MAJOR_MASK) !=
+	    (BOOT_API_HEADER_VERSION & HEADER_VERSION_MAJOR_MASK)) {
 		ERROR("Header version\n");
 		return -EINVAL;
 	}
@@ -98,12 +113,13 @@
 
 	return 0;
 }
+#endif /* STM32MP_USE_STM32IMAGE */
 
 int stm32mp_map_ddr_non_cacheable(void)
 {
 	return  mmap_add_dynamic_region(STM32MP_DDR_BASE, STM32MP_DDR_BASE,
 					STM32MP_DDR_MAX_SIZE,
-					MT_NON_CACHEABLE | MT_RW | MT_NS);
+					MT_NON_CACHEABLE | MT_RW | MT_SECURE);
 }
 
 int stm32mp_unmap_ddr(void)
@@ -111,3 +127,36 @@
 	return  mmap_remove_dynamic_region(STM32MP_DDR_BASE,
 					   STM32MP_DDR_MAX_SIZE);
 }
+
+/*****************************************************************************
+ * plat_is_smccc_feature_available() - This function checks whether SMCCC
+ *                                     feature is availabile for platform.
+ * @fid: SMCCC function id
+ *
+ * Return SMC_ARCH_CALL_SUCCESS if SMCCC feature is available and
+ * SMC_ARCH_CALL_NOT_SUPPORTED otherwise.
+ *****************************************************************************/
+int32_t plat_is_smccc_feature_available(u_register_t fid)
+{
+	switch (fid) {
+	case SMCCC_ARCH_SOC_ID:
+		return SMC_ARCH_CALL_SUCCESS;
+	default:
+		return SMC_ARCH_CALL_NOT_SUPPORTED;
+	}
+}
+
+/* Get SOC version */
+int32_t plat_get_soc_version(void)
+{
+	uint32_t chip_id = stm32mp_get_chip_dev_id();
+	uint32_t manfid = SOC_ID_SET_JEP_106(JEDEC_ST_BKID, JEDEC_ST_MFID);
+
+	return (int32_t)(manfid | (chip_id & SOC_ID_IMPL_DEF_MASK));
+}
+
+/* Get SOC revision */
+int32_t plat_get_soc_revision(void)
+{
+	return (int32_t)(stm32mp_get_chip_version() & SOC_ID_REV_MASK);
+}
diff --git a/plat/st/common/stm32mp_dt.c b/plat/st/common/stm32mp_dt.c
index 391e5f0..4dc9908 100644
--- a/plat/st/common/stm32mp_dt.c
+++ b/plat/st/common/stm32mp_dt.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -19,20 +19,19 @@
 
 #include <stm32mp_dt.h>
 
-static int fdt_checked;
-
-static void *fdt = (void *)(uintptr_t)STM32MP_DTB_BASE;
+static void *fdt;
 
 /*******************************************************************************
  * This function checks device tree file with its header.
  * Returns 0 on success and a negative FDT error code on failure.
  ******************************************************************************/
-int dt_open_and_check(void)
+int dt_open_and_check(uintptr_t dt_addr)
 {
-	int ret = fdt_check_header(fdt);
+	int ret;
 
+	ret = fdt_check_header((void *)dt_addr);
 	if (ret == 0) {
-		fdt_checked = 1;
+		fdt = (void *)dt_addr;
 	}
 
 	return ret;
@@ -45,11 +44,13 @@
  ******************************************************************************/
 int fdt_get_address(void **fdt_addr)
 {
-	if (fdt_checked == 1) {
-		*fdt_addr = fdt;
+	if (fdt == NULL) {
+		return 0;
 	}
 
-	return fdt_checked;
+	*fdt_addr = fdt;
+
+	return 1;
 }
 
 /*******************************************************************************
@@ -72,21 +73,20 @@
 uint8_t fdt_get_status(int node)
 {
 	uint8_t status = DT_DISABLED;
-	int len;
 	const char *cchar;
 
-	cchar = fdt_getprop(fdt, node, "status", &len);
+	cchar = fdt_getprop(fdt, node, "status", NULL);
 	if ((cchar == NULL) ||
-	    (strncmp(cchar, "okay", (size_t)len) == 0)) {
+	    (strncmp(cchar, "okay", strlen("okay")) == 0)) {
 		status |= DT_NON_SECURE;
 	}
 
-	cchar = fdt_getprop(fdt, node, "secure-status", &len);
+	cchar = fdt_getprop(fdt, node, "secure-status", NULL);
 	if (cchar == NULL) {
 		if (status == DT_NON_SECURE) {
 			status |= DT_SECURE;
 		}
-	} else if (strncmp(cchar, "okay", (size_t)len) == 0) {
+	} else if (strncmp(cchar, "okay", strlen("okay")) == 0) {
 		status |= DT_SECURE;
 	}
 
@@ -204,20 +204,56 @@
 }
 
 /*******************************************************************************
+ * This function returns the node offset matching compatible string in the DT,
+ * and also matching the reg property with the given address.
+ * Returns value on success, and error value on failure.
+ ******************************************************************************/
+int dt_match_instance_by_compatible(const char *compatible, uintptr_t address)
+{
+	int node;
+
+	fdt_for_each_compatible_node(fdt, node, compatible) {
+		const fdt32_t *cuint;
+
+		assert(fdt_get_node_parent_address_cells(node) == 1);
+
+		cuint = fdt_getprop(fdt, node, "reg", NULL);
+		if (cuint == NULL) {
+			continue;
+		}
+
+		if ((uintptr_t)fdt32_to_cpu(*cuint) == address) {
+			return node;
+		}
+	}
+
+	return -FDT_ERR_NOTFOUND;
+}
+
+/*******************************************************************************
  * This function gets DDR size information from the DT.
  * Returns value in bytes on success, and 0 on failure.
  ******************************************************************************/
 uint32_t dt_get_ddr_size(void)
 {
+	static uint32_t size;
 	int node;
 
+	if (size != 0U) {
+		return size;
+	}
+
 	node = fdt_node_offset_by_compatible(fdt, -1, DT_DDR_COMPAT);
 	if (node < 0) {
 		INFO("%s: Cannot read DDR node in DT\n", __func__);
 		return 0;
 	}
 
-	return fdt_read_uint32_default(fdt, node, "st,mem-size", 0);
+	size = fdt_read_uint32_default(fdt, node, "st,mem-size", 0U);
+
+	flush_dcache_range((uintptr_t)&size, sizeof(uint32_t));
+
+	return size;
 }
 
 /*******************************************************************************
diff --git a/plat/st/common/stm32mp_fconf_io.c b/plat/st/common/stm32mp_fconf_io.c
new file mode 100644
index 0000000..aa8cd54
--- /dev/null
+++ b/plat/st/common/stm32mp_fconf_io.c
@@ -0,0 +1,121 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <common/fdt_wrappers.h>
+#include <drivers/io/io_storage.h>
+#include <drivers/mmc.h>
+#include <lib/fconf/fconf.h>
+#include <lib/object_pool.h>
+#include <libfdt.h>
+#include <tools_share/firmware_image_package.h>
+
+#include <platform_def.h>
+#include <stm32mp_fconf_getter.h>
+#include <stm32mp_io_storage.h>
+
+#if STM32MP_SDMMC || STM32MP_EMMC
+static io_block_spec_t gpt_block_spec = {
+	.offset = 0U,
+	.length = 34U * MMC_BLOCK_SIZE, /* Size of GPT table */
+};
+#endif
+
+/* By default, STM32 platforms load images from the FIP */
+struct plat_io_policy policies[MAX_NUMBER_IDS] = {
+	[FIP_IMAGE_ID] = {
+		&storage_dev_handle,
+		(uintptr_t)&image_block_spec,
+		open_storage
+	},
+#if STM32MP_SDMMC || STM32MP_EMMC
+	[GPT_IMAGE_ID] = {
+		&storage_dev_handle,
+		(uintptr_t)&gpt_block_spec,
+		open_storage
+	},
+#endif
+};
+
+#define FCONF_ST_IO_UUID_NUMBER	U(8)
+
+static io_uuid_spec_t fconf_stm32mp_uuids[FCONF_ST_IO_UUID_NUMBER];
+static OBJECT_POOL_ARRAY(fconf_stm32mp_uuids_pool, fconf_stm32mp_uuids);
+
+struct policies_load_info {
+	unsigned int image_id;
+	const char *name;
+};
+
+/* image id to property name table */
+static const struct policies_load_info load_info[FCONF_ST_IO_UUID_NUMBER] = {
+	{FW_CONFIG_ID, "fw_cfg_uuid"},
+	{BL32_IMAGE_ID, "bl32_uuid"},
+	{BL32_EXTRA1_IMAGE_ID, "bl32_extra1_uuid"},
+	{BL32_EXTRA2_IMAGE_ID, "bl32_extra2_uuid"},
+	{BL33_IMAGE_ID, "bl33_uuid"},
+	{HW_CONFIG_ID, "hw_cfg_uuid"},
+	{TOS_FW_CONFIG_ID, "tos_fw_cfg_uuid"},
+	{NT_FW_CONFIG_ID, "nt_fw_cfg_uuid"},
+};
+
+int fconf_populate_stm32mp_io_policies(uintptr_t config)
+{
+	int node;
+	unsigned int i;
+
+	/* As libfdt uses void *, we can't avoid this cast */
+	const void *dtb = (void *)config;
+
+	/* Assert the node offset point to "st,io-fip-handle" compatible property */
+	const char *compatible_str = "st,io-fip-handle";
+
+	node = fdt_node_offset_by_compatible(dtb, -1, compatible_str);
+	if (node < 0) {
+		ERROR("FCONF: Can't find %s compatible in dtb\n", compatible_str);
+		return node;
+	}
+
+	/* Locate the uuid cells and read the value for all the load info uuid */
+	for (i = 0U; i < FCONF_ST_IO_UUID_NUMBER; i++) {
+		union uuid_helper_t uuid_helper;
+		io_uuid_spec_t *uuid_ptr;
+		int err;
+
+		uuid_ptr = pool_alloc(&fconf_stm32mp_uuids_pool);
+		err = fdtw_read_uuid(dtb, node, load_info[i].name, 16,
+				     (uint8_t *)&uuid_helper);
+		if (err < 0) {
+			WARN("FCONF: Read cell failed for %s\n", load_info[i].name);
+			return err;
+		}
+
+		VERBOSE("FCONF: stm32mp-io_policies.%s cell found with value = "
+			"%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x\n",
+			load_info[i].name,
+			uuid_helper.uuid_struct.time_low[0], uuid_helper.uuid_struct.time_low[1],
+			uuid_helper.uuid_struct.time_low[2], uuid_helper.uuid_struct.time_low[3],
+			uuid_helper.uuid_struct.time_mid[0], uuid_helper.uuid_struct.time_mid[1],
+			uuid_helper.uuid_struct.time_hi_and_version[0],
+			uuid_helper.uuid_struct.time_hi_and_version[1],
+			uuid_helper.uuid_struct.clock_seq_hi_and_reserved,
+			uuid_helper.uuid_struct.clock_seq_low,
+			uuid_helper.uuid_struct.node[0], uuid_helper.uuid_struct.node[1],
+			uuid_helper.uuid_struct.node[2], uuid_helper.uuid_struct.node[3],
+			uuid_helper.uuid_struct.node[4], uuid_helper.uuid_struct.node[5]);
+
+		uuid_ptr->uuid = uuid_helper.uuid_struct;
+		policies[load_info[i].image_id].image_spec = (uintptr_t)uuid_ptr;
+		policies[load_info[i].image_id].dev_handle = &fip_dev_handle;
+		policies[load_info[i].image_id].check = open_fip;
+	}
+
+	return 0;
+}
+
+FCONF_REGISTER_POPULATOR(TB_FW, stm32mp_io, fconf_populate_stm32mp_io_policies);
diff --git a/plat/st/common/usb_dfu.c b/plat/st/common/usb_dfu.c
new file mode 100644
index 0000000..8bb0994
--- /dev/null
+++ b/plat/st/common/usb_dfu.c
@@ -0,0 +1,538 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <errno.h>
+#include <string.h>
+
+#include <common/debug.h>
+
+#include <platform_def.h>
+#include <usb_dfu.h>
+
+/* Device states as defined in DFU spec */
+#define STATE_APP_IDLE			0
+#define STATE_APP_DETACH		1
+#define STATE_DFU_IDLE			2
+#define STATE_DFU_DNLOAD_SYNC		3
+#define STATE_DFU_DNLOAD_BUSY		4
+#define STATE_DFU_DNLOAD_IDLE		5
+#define STATE_DFU_MANIFEST_SYNC		6
+#define STATE_DFU_MANIFEST		7
+#define STATE_DFU_MANIFEST_WAIT_RESET	8
+#define STATE_DFU_UPLOAD_IDLE		9
+#define STATE_DFU_ERROR			10
+
+/* DFU errors */
+#define DFU_ERROR_NONE			0x00
+#define DFU_ERROR_TARGET		0x01
+#define DFU_ERROR_FILE			0x02
+#define DFU_ERROR_WRITE			0x03
+#define DFU_ERROR_ERASE			0x04
+#define DFU_ERROR_CHECK_ERASED		0x05
+#define DFU_ERROR_PROG			0x06
+#define DFU_ERROR_VERIFY		0x07
+#define DFU_ERROR_ADDRESS		0x08
+#define DFU_ERROR_NOTDONE		0x09
+#define DFU_ERROR_FIRMWARE		0x0A
+#define DFU_ERROR_VENDOR		0x0B
+#define DFU_ERROR_USB			0x0C
+#define DFU_ERROR_POR			0x0D
+#define DFU_ERROR_UNKNOWN		0x0E
+#define DFU_ERROR_STALLEDPKT		0x0F
+
+/* DFU request */
+#define DFU_DETACH			0
+#define DFU_DNLOAD			1
+#define DFU_UPLOAD			2
+#define DFU_GETSTATUS			3
+#define DFU_CLRSTATUS			4
+#define DFU_GETSTATE			5
+#define DFU_ABORT			6
+
+static bool usb_dfu_detach_req;
+
+/*
+ * usb_dfu_init
+ *         Initialize the DFU interface
+ * pdev: device instance
+ * cfgidx: Configuration index
+ * return: status
+ */
+static uint8_t usb_dfu_init(struct usb_handle *pdev, uint8_t cfgidx)
+{
+	(void)pdev;
+	(void)cfgidx;
+
+	/* Nothing to do in this stage */
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_de_init
+ *         De-Initialize the DFU layer
+ * pdev: device instance
+ * cfgidx: Configuration index
+ * return: status
+ */
+static uint8_t usb_dfu_de_init(struct usb_handle *pdev, uint8_t cfgidx)
+{
+	(void)pdev;
+	(void)cfgidx;
+
+	/* Nothing to do in this stage */
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_data_in
+ *         handle data IN Stage
+ * pdev: device instance
+ * epnum: endpoint index
+ * return: status
+ */
+static uint8_t usb_dfu_data_in(struct usb_handle *pdev, uint8_t epnum)
+{
+	(void)pdev;
+	(void)epnum;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_ep0_rx_ready
+ *         handle EP0 Rx Ready event
+ * pdev: device
+ * return: status
+ */
+static uint8_t usb_dfu_ep0_rx_ready(struct usb_handle *pdev)
+{
+	(void)pdev;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_ep0_tx_ready
+ *         handle EP0 TRx Ready event
+ * pdev: device instance
+ * return: status
+ */
+static uint8_t usb_dfu_ep0_tx_ready(struct usb_handle *pdev)
+{
+	(void)pdev;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_sof
+ *         handle SOF event
+ * pdev: device instance
+ * return: status
+ */
+static uint8_t usb_dfu_sof(struct usb_handle *pdev)
+{
+	(void)pdev;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_iso_in_incomplete
+ *         handle data ISO IN Incomplete event
+ * pdev: device instance
+ * epnum: endpoint index
+ * return: status
+ */
+static uint8_t usb_dfu_iso_in_incomplete(struct usb_handle *pdev, uint8_t epnum)
+{
+	(void)pdev;
+	(void)epnum;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_iso_out_incomplete
+ *         handle data ISO OUT Incomplete event
+ * pdev: device instance
+ * epnum: endpoint index
+ * return: status
+ */
+static uint8_t usb_dfu_iso_out_incomplete(struct usb_handle *pdev,
+					  uint8_t epnum)
+{
+	(void)pdev;
+	(void)epnum;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_data_out
+ *         handle data OUT Stage
+ * pdev: device instance
+ * epnum: endpoint index
+ * return: status
+ */
+static uint8_t usb_dfu_data_out(struct usb_handle *pdev, uint8_t epnum)
+{
+	(void)pdev;
+	(void)epnum;
+
+	return USBD_OK;
+}
+
+/*
+ * usb_dfu_detach
+ *         Handles the DFU DETACH request.
+ * pdev: device instance
+ * req: pointer to the request structure.
+ */
+static void usb_dfu_detach(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	INFO("Receive DFU Detach\n");
+
+	if ((hdfu->dev_state == STATE_DFU_IDLE) ||
+	    (hdfu->dev_state == STATE_DFU_DNLOAD_SYNC) ||
+	    (hdfu->dev_state == STATE_DFU_DNLOAD_IDLE) ||
+	    (hdfu->dev_state == STATE_DFU_MANIFEST_SYNC) ||
+	    (hdfu->dev_state == STATE_DFU_UPLOAD_IDLE)) {
+		/* Update the state machine */
+		hdfu->dev_state = STATE_DFU_IDLE;
+		hdfu->dev_status = DFU_ERROR_NONE;
+	}
+
+	usb_dfu_detach_req = true;
+}
+
+/*
+ * usb_dfu_download
+ *         Handles the DFU DNLOAD request.
+ * pdev: device instance
+ * req: pointer to the request structure
+ */
+static void usb_dfu_download(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+	uintptr_t data_ptr;
+	uint32_t length;
+	int ret;
+
+	/* Data setup request */
+	if (req->length > 0) {
+		/* Unsupported state */
+		if ((hdfu->dev_state != STATE_DFU_IDLE) &&
+		    (hdfu->dev_state != STATE_DFU_DNLOAD_IDLE)) {
+			/* Call the error management function (command will be nacked) */
+			usb_core_ctl_error(pdev);
+			return;
+		}
+
+		/* Get the data address */
+		length = req->length;
+		ret = hdfu->callback->download(hdfu->alt_setting, &data_ptr,
+					       &length, pdev->user_data);
+		if (ret == 0U) {
+			/* Update the state machine */
+			hdfu->dev_state = STATE_DFU_DNLOAD_SYNC;
+			/* Start the transfer */
+			usb_core_receive_ep0(pdev, (uint8_t *)data_ptr, length);
+		} else {
+			usb_core_ctl_error(pdev);
+		}
+	} else {
+		/* End of DNLOAD operation*/
+		if (hdfu->dev_state != STATE_DFU_DNLOAD_IDLE) {
+			/* Call the error management function (command will be nacked) */
+			usb_core_ctl_error(pdev);
+			return;
+		}
+		/* End of DNLOAD operation*/
+		hdfu->dev_state = STATE_DFU_MANIFEST_SYNC;
+		ret = hdfu->callback->manifestation(hdfu->alt_setting, pdev->user_data);
+		if (ret == 0U) {
+			hdfu->dev_state = STATE_DFU_MANIFEST_SYNC;
+		} else {
+			usb_core_ctl_error(pdev);
+		}
+	}
+}
+
+/*
+ * usb_dfu_upload
+ *         Handles the DFU UPLOAD request.
+ * pdev: instance
+ * req: pointer to the request structure
+ */
+static void usb_dfu_upload(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+	uintptr_t data_ptr;
+	uint32_t length;
+	int ret;
+
+	/* Data setup request */
+	if (req->length == 0) {
+		/* No Data setup request */
+		hdfu->dev_state = STATE_DFU_IDLE;
+		return;
+	}
+
+	/* Unsupported state */
+	if ((hdfu->dev_state != STATE_DFU_IDLE) && (hdfu->dev_state != STATE_DFU_UPLOAD_IDLE)) {
+		ERROR("UPLOAD : Unsupported State\n");
+		/* Call the error management function (command will be nacked) */
+		usb_core_ctl_error(pdev);
+		return;
+	}
+
+	/* Update the data address */
+	length = req->length;
+	ret = hdfu->callback->upload(hdfu->alt_setting, &data_ptr, &length, pdev->user_data);
+	if (ret == 0U) {
+		/* Short frame */
+		hdfu->dev_state = (req->length > length) ? STATE_DFU_IDLE : STATE_DFU_UPLOAD_IDLE;
+
+		/* Start the transfer */
+		usb_core_transmit_ep0(pdev, (uint8_t *)data_ptr, length);
+	} else {
+		ERROR("UPLOAD : bad block %i on alt %i\n", req->value, req->index);
+		hdfu->dev_state = STATE_DFU_ERROR;
+		hdfu->dev_status = DFU_ERROR_STALLEDPKT;
+
+		/* Call the error management function (command will be nacked) */
+		usb_core_ctl_error(pdev);
+	}
+}
+
+/*
+ * usb_dfu_get_status
+ *         Handles the DFU GETSTATUS request.
+ * pdev: instance
+ */
+static void usb_dfu_get_status(struct usb_handle *pdev)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	hdfu->status[0] = hdfu->dev_status;	/* bStatus */
+	hdfu->status[1] = 0;			/* bwPollTimeout[3] */
+	hdfu->status[2] = 0;
+	hdfu->status[3] = 0;
+	hdfu->status[4] = hdfu->dev_state;	/* bState */
+	hdfu->status[5] = 0;			/* iString */
+
+	/* next step */
+	switch (hdfu->dev_state) {
+	case STATE_DFU_DNLOAD_SYNC:
+		hdfu->dev_state = STATE_DFU_DNLOAD_IDLE;
+		break;
+	case STATE_DFU_MANIFEST_SYNC:
+		/* the device is 'ManifestationTolerant' */
+		hdfu->status[4] = STATE_DFU_MANIFEST;
+		hdfu->status[1] = 1U; /* bwPollTimeout = 1ms */
+		hdfu->dev_state = STATE_DFU_IDLE;
+		break;
+
+	default:
+		break;
+	}
+
+	/* Start the transfer */
+	usb_core_transmit_ep0(pdev, (uint8_t *)&hdfu->status[0], sizeof(hdfu->status));
+}
+
+/*
+ * usb_dfu_clear_status
+ *         Handles the DFU CLRSTATUS request.
+ * pdev: device instance
+ */
+static void usb_dfu_clear_status(struct usb_handle *pdev)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	if (hdfu->dev_state == STATE_DFU_ERROR) {
+		hdfu->dev_state = STATE_DFU_IDLE;
+		hdfu->dev_status = DFU_ERROR_NONE;
+	} else {
+		/* State Error */
+		hdfu->dev_state = STATE_DFU_ERROR;
+		hdfu->dev_status = DFU_ERROR_UNKNOWN;
+	}
+}
+
+/*
+ * usb_dfu_get_state
+ *         Handles the DFU GETSTATE request.
+ * pdev: device instance
+ */
+static void usb_dfu_get_state(struct usb_handle *pdev)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	/* Return the current state of the DFU interface */
+	usb_core_transmit_ep0(pdev, &hdfu->dev_state, 1);
+}
+
+/*
+ * usb_dfu_abort
+ *         Handles the DFU ABORT request.
+ * pdev: device instance
+ */
+static void usb_dfu_abort(struct usb_handle *pdev)
+{
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	if ((hdfu->dev_state == STATE_DFU_IDLE) ||
+	    (hdfu->dev_state == STATE_DFU_DNLOAD_SYNC) ||
+	    (hdfu->dev_state == STATE_DFU_DNLOAD_IDLE) ||
+	    (hdfu->dev_state == STATE_DFU_MANIFEST_SYNC) ||
+	    (hdfu->dev_state == STATE_DFU_UPLOAD_IDLE)) {
+		hdfu->dev_state = STATE_DFU_IDLE;
+		hdfu->dev_status = DFU_ERROR_NONE;
+	}
+}
+
+/*
+ * usb_dfu_setup
+ *         Handle the DFU specific requests
+ * pdev: instance
+ * req: usb requests
+ * return: status
+ */
+static uint8_t usb_dfu_setup(struct usb_handle *pdev, struct usb_setup_req *req)
+{
+	uint8_t *pbuf = NULL;
+	uint16_t len = 0U;
+	uint8_t ret = USBD_OK;
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	switch (req->bm_request & USB_REQ_TYPE_MASK) {
+	case USB_REQ_TYPE_CLASS:
+		switch (req->b_request) {
+		case DFU_DNLOAD:
+			usb_dfu_download(pdev, req);
+			break;
+
+		case DFU_UPLOAD:
+			usb_dfu_upload(pdev, req);
+			break;
+
+		case DFU_GETSTATUS:
+			usb_dfu_get_status(pdev);
+			break;
+
+		case DFU_CLRSTATUS:
+			usb_dfu_clear_status(pdev);
+			break;
+
+		case DFU_GETSTATE:
+			usb_dfu_get_state(pdev);
+			break;
+
+		case DFU_ABORT:
+			usb_dfu_abort(pdev);
+			break;
+
+		case DFU_DETACH:
+			usb_dfu_detach(pdev, req);
+			break;
+
+		default:
+			ERROR("unknown request %x on alternate %i\n",
+			      req->b_request, hdfu->alt_setting);
+			usb_core_ctl_error(pdev);
+			ret = USBD_FAIL;
+			break;
+		}
+		break;
+	case USB_REQ_TYPE_STANDARD:
+		switch (req->b_request) {
+		case USB_REQ_GET_DESCRIPTOR:
+			if (HIBYTE(req->value) == DFU_DESCRIPTOR_TYPE) {
+				pbuf = pdev->desc->get_config_desc(&len);
+				/* DFU descriptor at the end of the USB */
+				pbuf += len - 9U;
+				len = 9U;
+				len = MIN(len, req->length);
+			}
+
+			/* Start the transfer */
+			usb_core_transmit_ep0(pdev, pbuf, len);
+
+			break;
+
+		case USB_REQ_GET_INTERFACE:
+			/* Start the transfer */
+			usb_core_transmit_ep0(pdev, (uint8_t *)&hdfu->alt_setting, 1U);
+			break;
+
+		case USB_REQ_SET_INTERFACE:
+			hdfu->alt_setting = LOBYTE(req->value);
+			break;
+
+		default:
+			usb_core_ctl_error(pdev);
+			ret = USBD_FAIL;
+			break;
+		}
+	default:
+		break;
+	}
+
+	return ret;
+}
+
+static const struct usb_class usb_dfu = {
+	.init = usb_dfu_init,
+	.de_init = usb_dfu_de_init,
+	.setup = usb_dfu_setup,
+	.ep0_tx_sent = usb_dfu_ep0_tx_ready,
+	.ep0_rx_ready = usb_dfu_ep0_rx_ready,
+	.data_in = usb_dfu_data_in,
+	.data_out = usb_dfu_data_out,
+	.sof = usb_dfu_sof,
+	.iso_in_incomplete = usb_dfu_iso_in_incomplete,
+	.iso_out_incomplete = usb_dfu_iso_out_incomplete,
+};
+
+void usb_dfu_register(struct usb_handle *pdev, struct usb_dfu_handle *phandle)
+{
+	pdev->class = (struct usb_class *)&usb_dfu;
+	pdev->class_data = phandle;
+
+	phandle->dev_state = STATE_DFU_IDLE;
+	phandle->dev_status = DFU_ERROR_NONE;
+}
+
+int usb_dfu_loop(struct usb_handle *pdev, const struct usb_dfu_media *pmedia)
+{
+	uint32_t it_count;
+	enum usb_status ret;
+	struct usb_dfu_handle *hdfu = (struct usb_dfu_handle *)pdev->class_data;
+
+	hdfu->callback = pmedia;
+	usb_dfu_detach_req = false;
+	/* Continue to handle USB core IT to assure complete data transmission */
+	it_count = 100U;
+
+	/* DFU infinite loop until DETACH_REQ */
+	while (it_count != 0U) {
+		ret = usb_core_handle_it(pdev);
+		if (ret != USBD_OK) {
+			return -EIO;
+		}
+
+		/* Detach request received */
+		if (usb_dfu_detach_req) {
+			it_count--;
+		}
+	}
+
+	return 0;
+}
diff --git a/plat/st/stm32mp1/bl2_plat_setup.c b/plat/st/stm32mp1/bl2_plat_setup.c
index e09ce63..7eaf0ed 100644
--- a/plat/st/stm32mp1/bl2_plat_setup.c
+++ b/plat/st/stm32mp1/bl2_plat_setup.c
@@ -1,10 +1,11 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <errno.h>
 #include <string.h>
 
 #include <platform_def.h>
@@ -15,6 +16,7 @@
 #include <common/desc_image_load.h>
 #include <drivers/delay_timer.h>
 #include <drivers/generic_delay_timer.h>
+#include <drivers/mmc.h>
 #include <drivers/st/bsec.h>
 #include <drivers/st/stm32_console.h>
 #include <drivers/st/stm32_iwdg.h>
@@ -23,6 +25,8 @@
 #include <drivers/st/stm32mp1_clk.h>
 #include <drivers/st/stm32mp1_pwr.h>
 #include <drivers/st/stm32mp1_ram.h>
+#include <lib/fconf/fconf.h>
+#include <lib/fconf/fconf_dyn_cfg_getter.h>
 #include <lib/mmio.h>
 #include <lib/optee_utils.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
@@ -132,7 +136,6 @@
 void bl2_platform_setup(void)
 {
 	int ret;
-	uint32_t ddr_ns_size;
 
 	if (dt_pmic_status() > 0) {
 		initialize_pmic();
@@ -144,29 +147,21 @@
 		panic();
 	}
 
-	ddr_ns_size = stm32mp_get_ddr_ns_size();
-	assert(ddr_ns_size > 0U);
-
-	/* Map non secure DDR for BL33 load, now with cacheable attribute */
+	/* Map DDR for binary load, now with cacheable attribute */
 	ret = mmap_add_dynamic_region(STM32MP_DDR_BASE, STM32MP_DDR_BASE,
-				      ddr_ns_size, MT_MEMORY | MT_RW | MT_NS);
-	assert(ret == 0);
+				      STM32MP_DDR_MAX_SIZE, MT_MEMORY | MT_RW | MT_SECURE);
+	if (ret < 0) {
+		ERROR("DDR mapping: error %d\n", ret);
+		panic();
+	}
 
+#if STM32MP_USE_STM32IMAGE
 #ifdef AARCH32_SP_OPTEE
 	INFO("BL2 runs OP-TEE setup\n");
-
-	/* Map secure DDR for OP-TEE paged area */
-	ret = mmap_add_dynamic_region(STM32MP_DDR_BASE + ddr_ns_size,
-				      STM32MP_DDR_BASE + ddr_ns_size,
-				      STM32MP_DDR_S_SIZE,
-				      MT_MEMORY | MT_RW | MT_SECURE);
-	assert(ret == 0);
-
-	/* Initialize tzc400 after DDR initialization */
-	stm32mp1_security_setup();
 #else
 	INFO("BL2 runs SP_MIN setup\n");
 #endif
+#endif /* STM32MP_USE_STM32IMAGE */
 }
 
 void bl2_el3_plat_arch_setup(void)
@@ -184,6 +179,7 @@
 			BL_CODE_END - BL_CODE_BASE,
 			MT_CODE | MT_SECURE);
 
+#if STM32MP_USE_STM32IMAGE
 #ifdef AARCH32_SP_OPTEE
 	mmap_add_region(STM32MP_OPTEE_BASE, STM32MP_OPTEE_BASE,
 			STM32MP_OPTEE_SIZE,
@@ -194,6 +190,8 @@
 			BL32_LIMIT - BL32_BASE,
 			MT_RO_DATA | MT_SECURE);
 #endif
+#endif /* STM32MP_USE_STM32IMAGE */
+
 	/* Prevent corruption of preloaded Device Tree */
 	mmap_add_region(DTB_BASE, DTB_BASE,
 			DTB_LIMIT - DTB_BASE,
@@ -201,7 +199,7 @@
 
 	configure_mmu();
 
-	if (dt_open_and_check() < 0) {
+	if (dt_open_and_check(STM32MP_DTB_BASE) < 0) {
 		panic();
 	}
 
@@ -332,10 +330,13 @@
 
 	print_reset_reason();
 
+#if !STM32MP_USE_STM32IMAGE
+	fconf_populate("TB_FW", STM32MP_DTB_BASE);
+#endif /* !STM32MP_USE_STM32IMAGE */
+
 	stm32mp_io_setup();
 }
 
-#if defined(AARCH32_SP_OPTEE)
 /*******************************************************************************
  * This function can be used by the platforms to update/use image
  * information for given `image_id`.
@@ -345,44 +346,119 @@
 	int err = 0;
 	bl_mem_params_node_t *bl_mem_params = get_bl_mem_params_node(image_id);
 	bl_mem_params_node_t *bl32_mem_params;
-	bl_mem_params_node_t *pager_mem_params;
-	bl_mem_params_node_t *paged_mem_params;
+	bl_mem_params_node_t *pager_mem_params __unused;
+	bl_mem_params_node_t *paged_mem_params __unused;
+#if !STM32MP_USE_STM32IMAGE
+	const struct dyn_cfg_dtb_info_t *config_info;
+	bl_mem_params_node_t *tos_fw_mem_params;
+	unsigned int i;
+	unsigned long long ddr_top __unused;
+	const unsigned int image_ids[] = {
+		BL32_IMAGE_ID,
+		BL33_IMAGE_ID,
+		HW_CONFIG_ID,
+		TOS_FW_CONFIG_ID,
+	};
+#endif /* !STM32MP_USE_STM32IMAGE */
 
 	assert(bl_mem_params != NULL);
 
 	switch (image_id) {
-	case BL32_IMAGE_ID:
-		bl_mem_params->ep_info.pc =
-					bl_mem_params->image_info.image_base;
+#if !STM32MP_USE_STM32IMAGE
+	case FW_CONFIG_ID:
+		/* Set global DTB info for fixed fw_config information */
+		set_config_info(STM32MP_FW_CONFIG_BASE, STM32MP_FW_CONFIG_MAX_SIZE, FW_CONFIG_ID);
+		fconf_populate("FW_CONFIG", STM32MP_FW_CONFIG_BASE);
 
-		pager_mem_params = get_bl_mem_params_node(BL32_EXTRA1_IMAGE_ID);
-		assert(pager_mem_params != NULL);
-		pager_mem_params->image_info.image_base = STM32MP_OPTEE_BASE;
-		pager_mem_params->image_info.image_max_size =
-			STM32MP_OPTEE_SIZE;
+		/* Iterate through all the fw config IDs */
+		for (i = 0U; i < ARRAY_SIZE(image_ids); i++) {
+			bl_mem_params = get_bl_mem_params_node(image_ids[i]);
+			assert(bl_mem_params != NULL);
 
-		paged_mem_params = get_bl_mem_params_node(BL32_EXTRA2_IMAGE_ID);
-		assert(paged_mem_params != NULL);
-		paged_mem_params->image_info.image_base = STM32MP_DDR_BASE +
-			stm32mp_get_ddr_ns_size();
-		paged_mem_params->image_info.image_max_size =
-			STM32MP_DDR_S_SIZE;
+			config_info = FCONF_GET_PROPERTY(dyn_cfg, dtb, image_ids[i]);
+			if (config_info == NULL) {
+				continue;
+			}
 
-		err = parse_optee_header(&bl_mem_params->ep_info,
-					 &pager_mem_params->image_info,
-					 &paged_mem_params->image_info);
-		if (err) {
-			ERROR("OPTEE header parse error.\n");
-			panic();
+			bl_mem_params->image_info.image_base = config_info->config_addr;
+			bl_mem_params->image_info.image_max_size = config_info->config_max_size;
+
+			bl_mem_params->image_info.h.attr &= ~IMAGE_ATTRIB_SKIP_LOADING;
+
+			switch (image_ids[i]) {
+			case BL32_IMAGE_ID:
+				bl_mem_params->ep_info.pc = config_info->config_addr;
+
+				/* In case of OPTEE, initialize address space with tos_fw addr */
+				pager_mem_params = get_bl_mem_params_node(BL32_EXTRA1_IMAGE_ID);
+				pager_mem_params->image_info.image_base = config_info->config_addr;
+				pager_mem_params->image_info.image_max_size =
+					config_info->config_max_size;
+
+				/* Init base and size for pager if exist */
+				paged_mem_params = get_bl_mem_params_node(BL32_EXTRA2_IMAGE_ID);
+				paged_mem_params->image_info.image_base = STM32MP_DDR_BASE +
+					(dt_get_ddr_size() - STM32MP_DDR_S_SIZE -
+					 STM32MP_DDR_SHMEM_SIZE);
+				paged_mem_params->image_info.image_max_size = STM32MP_DDR_S_SIZE;
+				break;
+
+			case BL33_IMAGE_ID:
+				bl_mem_params->ep_info.pc = config_info->config_addr;
+				break;
+
+			case HW_CONFIG_ID:
+			case TOS_FW_CONFIG_ID:
+				break;
+
+			default:
+				return -EINVAL;
+			}
 		}
+		break;
+#endif /* !STM32MP_USE_STM32IMAGE */
 
-		/* Set optee boot info from parsed header data */
-		bl_mem_params->ep_info.pc =
-				pager_mem_params->image_info.image_base;
-		bl_mem_params->ep_info.args.arg0 =
-				paged_mem_params->image_info.image_base;
-		bl_mem_params->ep_info.args.arg1 = 0; /* Unused */
-		bl_mem_params->ep_info.args.arg2 = 0; /* No DT supported */
+	case BL32_IMAGE_ID:
+		if (optee_header_is_valid(bl_mem_params->image_info.image_base)) {
+			/* BL32 is OP-TEE header */
+			bl_mem_params->ep_info.pc = bl_mem_params->image_info.image_base;
+			pager_mem_params = get_bl_mem_params_node(BL32_EXTRA1_IMAGE_ID);
+			paged_mem_params = get_bl_mem_params_node(BL32_EXTRA2_IMAGE_ID);
+			assert((pager_mem_params != NULL) && (paged_mem_params != NULL));
+
+#if STM32MP_USE_STM32IMAGE && defined(AARCH32_SP_OPTEE)
+			/* Set OP-TEE extra image load areas at run-time */
+			pager_mem_params->image_info.image_base = STM32MP_OPTEE_BASE;
+			pager_mem_params->image_info.image_max_size = STM32MP_OPTEE_SIZE;
+
+			paged_mem_params->image_info.image_base = STM32MP_DDR_BASE +
+								  dt_get_ddr_size() -
+								  STM32MP_DDR_S_SIZE -
+								  STM32MP_DDR_SHMEM_SIZE;
+			paged_mem_params->image_info.image_max_size = STM32MP_DDR_S_SIZE;
+#endif /* STM32MP_USE_STM32IMAGE && defined(AARCH32_SP_OPTEE) */
+
+			err = parse_optee_header(&bl_mem_params->ep_info,
+						 &pager_mem_params->image_info,
+						 &paged_mem_params->image_info);
+			if (err) {
+				ERROR("OPTEE header parse error.\n");
+				panic();
+			}
+
+			/* Set optee boot info from parsed header data */
+			bl_mem_params->ep_info.args.arg0 = paged_mem_params->image_info.image_base;
+			bl_mem_params->ep_info.args.arg1 = 0; /* Unused */
+			bl_mem_params->ep_info.args.arg2 = 0; /* No DT supported */
+		} else {
+#if !STM32MP_USE_STM32IMAGE
+			bl_mem_params->ep_info.pc = bl_mem_params->image_info.image_base;
+			tos_fw_mem_params = get_bl_mem_params_node(TOS_FW_CONFIG_ID);
+			bl_mem_params->image_info.image_max_size +=
+				tos_fw_mem_params->image_info.image_max_size;
+#endif /* !STM32MP_USE_STM32IMAGE */
+			bl_mem_params->ep_info.args.arg0 = 0;
+		}
 		break;
 
 	case BL33_IMAGE_ID:
@@ -396,6 +472,37 @@
 		break;
 	}
 
+#if STM32MP_SDMMC || STM32MP_EMMC
+	/*
+	 * Invalidate remaining data read from MMC but not flushed by load_image_flush().
+	 * We take the worst case which is 2 MMC blocks.
+	 */
+	if ((image_id != FW_CONFIG_ID) &&
+	    ((bl_mem_params->image_info.h.attr & IMAGE_ATTRIB_SKIP_LOADING) == 0U)) {
+		inv_dcache_range(bl_mem_params->image_info.image_base +
+				 bl_mem_params->image_info.image_size,
+				 2U * MMC_BLOCK_SIZE);
+	}
+#endif /* STM32MP_SDMMC || STM32MP_EMMC */
+
 	return err;
 }
+
+void bl2_el3_plat_prepare_exit(void)
+{
+	uint16_t boot_itf = stm32mp_get_boot_itf_selected();
+
+	switch (boot_itf) {
+#if STM32MP_USB_PROGRAMMER
+	case BOOT_API_CTX_BOOT_INTERFACE_SEL_SERIAL_USB:
+		/* Invalidate the downloaded buffer used with io_memmap */
+		inv_dcache_range(DWL_BUFFER_BASE, DWL_BUFFER_SIZE);
+		break;
 #endif
+	default:
+		/* Do nothing in default case */
+		break;
+	}
+
+	stm32mp1_security_setup();
+}
diff --git a/plat/st/stm32mp1/include/boot_api.h b/plat/st/stm32mp1/include/boot_api.h
index c16639a..52b1d1a 100644
--- a/plat/st/stm32mp1/include/boot_api.h
+++ b/plat/st/stm32mp1/include/boot_api.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -39,6 +39,9 @@
 /* Boot occurred on QSPI NOR */
 #define BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NOR_QSPI		0x4U
 
+/* Boot occurred on USB */
+#define BOOT_API_CTX_BOOT_INTERFACE_SEL_SERIAL_USB		0x6U
+
 /* Boot occurred on QSPI NAND */
 #define BOOT_API_CTX_BOOT_INTERFACE_SEL_FLASH_NAND_QSPI		0x7U
 
diff --git a/plat/st/stm32mp1/include/platform_def.h b/plat/st/stm32mp1/include/platform_def.h
index 7076a71..1e9443e 100644
--- a/plat/st/stm32mp1/include/platform_def.h
+++ b/plat/st/stm32mp1/include/platform_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -25,18 +25,22 @@
 #define PLATFORM_STACK_SIZE		0xC00
 #endif
 
+#if STM32MP_USE_STM32IMAGE
 #ifdef AARCH32_SP_OPTEE
 #define OPTEE_HEADER_IMAGE_NAME		"teeh"
+#define OPTEE_CORE_IMAGE_NAME		"teex"
 #define OPTEE_PAGED_IMAGE_NAME		"teed"
-#define OPTEE_PAGER_IMAGE_NAME		"teex"
 #define OPTEE_HEADER_BINARY_TYPE	U(0x20)
-#define OPTEE_PAGER_BINARY_TYPE		U(0x21)
+#define OPTEE_CORE_BINARY_TYPE		U(0x21)
 #define OPTEE_PAGED_BINARY_TYPE		U(0x22)
 #endif
 
 /* SSBL = second stage boot loader */
 #define BL33_IMAGE_NAME			"ssbl"
 #define BL33_BINARY_TYPE		U(0x0)
+#else /* STM32MP_USE_STM32IMAGE */
+#define FIP_IMAGE_NAME			"fip"
+#endif /* STM32MP_USE_STM32IMAGE */
 
 #define STM32MP_PRIMARY_CPU		U(0x0)
 #define STM32MP_SECONDARY_CPU		U(0x1)
@@ -67,11 +71,16 @@
 /*******************************************************************************
  * BL32 specific defines.
  ******************************************************************************/
-#ifndef AARCH32_SP_OPTEE
+#if STM32MP_USE_STM32IMAGE || defined(IMAGE_BL32)
+#if ENABLE_PIE
+#define BL32_BASE			0
+#define BL32_LIMIT			STM32MP_BL32_SIZE
+#else
 #define BL32_BASE			STM32MP_BL32_BASE
 #define BL32_LIMIT			(STM32MP_BL32_BASE + \
 					 STM32MP_BL32_SIZE)
 #endif
+#endif /* STM32MP_USE_STM32IMAGE || defined(IMAGE_BL32) */
 
 /*******************************************************************************
  * BL33 specific defines.
@@ -83,6 +92,16 @@
  */
 #define PLAT_STM32MP_NS_IMAGE_OFFSET	BL33_BASE
 
+/* Needed by STM32CubeProgrammer support */
+#define DWL_BUFFER_BASE			(STM32MP_DDR_BASE + U(0x08000000))
+#define DWL_BUFFER_SIZE			U(0x08000000)
+
+/*
+ * SSBL offset in case it's stored in eMMC boot partition.
+ * We can fix it to 256K because TF-A size can't be bigger than SRAM
+ */
+#define PLAT_EMMC_BOOT_SSBL_OFFSET		U(0x40000)
+
 /*******************************************************************************
  * DTB specific defines.
  ******************************************************************************/
diff --git a/plat/st/stm32mp1/include/stm32mp1_private.h b/plat/st/stm32mp1/include/stm32mp1_private.h
index b6cb91e..729d233 100644
--- a/plat/st/stm32mp1/include/stm32mp1_private.h
+++ b/plat/st/stm32mp1/include/stm32mp1_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -21,7 +21,9 @@
 void stm32mp1_syscfg_enable_io_compensation(void);
 void stm32mp1_syscfg_disable_io_compensation(void);
 
+#if STM32MP_USE_STM32IMAGE
 uint32_t stm32mp_get_ddr_ns_size(void);
+#endif /* STM32MP_USE_STM32IMAGE */
 
 void stm32mp1_init_scmi_server(void);
 #endif /* STM32MP1_PRIVATE_H */
diff --git a/plat/st/stm32mp1/include/stm32mp1_smc.h b/plat/st/stm32mp1/include/stm32mp1_smc.h
index 57240bc..52088de 100644
--- a/plat/st/stm32mp1/include/stm32mp1_smc.h
+++ b/plat/st/stm32mp1/include/stm32mp1_smc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2016-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -58,4 +58,10 @@
 #define STM32_SMC_WRITE_SHADOW		0x03
 #define STM32_SMC_READ_OTP		0x04
 
+/* SMC error codes */
+#define STM32_SMC_OK			0x00000000U
+#define STM32_SMC_NOT_SUPPORTED		0xFFFFFFFFU
+#define STM32_SMC_FAILED		0xFFFFFFFEU
+#define STM32_SMC_INVALID_PARAMS	0xFFFFFFFDU
+
 #endif /* STM32MP1_SMC_H */
diff --git a/plat/st/stm32mp1/plat_bl2_mem_params_desc.c b/plat/st/stm32mp1/plat_bl2_mem_params_desc.c
index 1d407bb..7963c4a 100644
--- a/plat/st/stm32mp1/plat_bl2_mem_params_desc.c
+++ b/plat/st/stm32mp1/plat_bl2_mem_params_desc.c
@@ -1,15 +1,15 @@
 /*
- * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
-#include <platform_def.h>
-
 #include <common/bl_common.h>
 #include <common/desc_image_load.h>
 #include <plat/common/platform.h>
 
+#include <platform_def.h>
+
 /*******************************************************************************
  * Following descriptor provides BL image/ep information that gets used
  * by BL2 to load the images and also subset of this information is
@@ -19,6 +19,22 @@
  * the next executable image id.
  ******************************************************************************/
 static bl_mem_params_node_t bl2_mem_params_descs[] = {
+	/* Fill FW_CONFIG related information if it exists */
+	{
+		.image_id = FW_CONFIG_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_PLAT_SETUP),
+
+		.image_info.image_base = STM32MP_FW_CONFIG_BASE,
+		.image_info.image_max_size = STM32MP_FW_CONFIG_MAX_SIZE,
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+
 	/* Fill BL32 related information */
 	{
 		.image_id = BL32_IMAGE_ID,
@@ -27,28 +43,17 @@
 				      VERSION_2, entry_point_info_t,
 				      SECURE | EXECUTABLE | EP_FIRST_EXE),
 
-#if !defined(AARCH32_SP_OPTEE)
-		.ep_info.pc = BL32_BASE,
-#endif
 		.ep_info.spsr = SPSR_MODE32(MODE32_svc, SPSR_T_ARM,
 					    SPSR_E_LITTLE,
 					    DISABLE_ALL_EXCEPTIONS),
 
 		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
 				      VERSION_2, image_info_t,
-				      IMAGE_ATTRIB_PLAT_SETUP),
-#if defined(AARCH32_SP_OPTEE)
-		/* optee header is loaded in SYSRAM above BL2 */
-		.image_info.image_base = STM32MP_OPTEE_BASE,
-		.image_info.image_max_size = STM32MP_OPTEE_SIZE,
-#else
-		.image_info.image_base = BL32_BASE,
-		.image_info.image_max_size = BL32_LIMIT - BL32_BASE,
-#endif
+				      IMAGE_ATTRIB_SKIP_LOADING),
+
 		.next_handoff_image_id = BL33_IMAGE_ID,
 	},
 
-#if defined(AARCH32_SP_OPTEE)
 	/* Fill BL32 external 1 image related information */
 	{
 		.image_id = BL32_EXTRA1_IMAGE_ID,
@@ -77,7 +82,32 @@
 
 		.next_handoff_image_id = INVALID_IMAGE_ID,
 	},
-#endif /* AARCH32_SP_OPTEE */
+
+	/* Fill HW_CONFIG related information if it exists */
+	{
+		.image_id = HW_CONFIG_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, entry_point_info_t,
+				      NON_SECURE | NON_EXECUTABLE),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+
+	/* Fill TOS_FW_CONFIG related information if it exists */
+	{
+		.image_id = TOS_FW_CONFIG_ID,
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_IMAGE_BINARY,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
 
 	/* Fill BL33 related information */
 	{
@@ -87,17 +117,13 @@
 				      VERSION_2, entry_point_info_t,
 				      NON_SECURE | EXECUTABLE),
 
-		.ep_info.pc = PLAT_STM32MP_NS_IMAGE_OFFSET,
 		.ep_info.spsr = SPSR_MODE32(MODE32_svc, SPSR_T_ARM,
 					    SPSR_E_LITTLE,
 					    DISABLE_ALL_EXCEPTIONS),
 
 		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
-				      VERSION_2, image_info_t, 0),
-
-		.image_info.image_base = PLAT_STM32MP_NS_IMAGE_OFFSET,
-		.image_info.image_max_size = STM32MP_DDR_MAX_SIZE -
-			(PLAT_STM32MP_NS_IMAGE_OFFSET - STM32MP_DDR_BASE),
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
 
 		.next_handoff_image_id = INVALID_IMAGE_ID,
 	}
diff --git a/plat/st/stm32mp1/plat_bl2_stm32_mem_params_desc.c b/plat/st/stm32mp1/plat_bl2_stm32_mem_params_desc.c
new file mode 100644
index 0000000..4fce55a
--- /dev/null
+++ b/plat/st/stm32mp1/plat_bl2_stm32_mem_params_desc.c
@@ -0,0 +1,103 @@
+/*
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <common/bl_common.h>
+#include <common/desc_image_load.h>
+#include <plat/common/platform.h>
+
+#include <platform_def.h>
+
+/*******************************************************************************
+ * Following descriptor provides BL image/ep information that gets used
+ * by BL2 to load the images and also subset of this information is
+ * passed to next BL image. The image loading sequence is managed by
+ * populating the images in required loading order. The image execution
+ * sequence is managed by populating the `next_handoff_image_id` with
+ * the next executable image id.
+ ******************************************************************************/
+static bl_mem_params_node_t bl2_mem_params_descs[] = {
+	/* Fill BL32 related information */
+	{
+		.image_id = BL32_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | EXECUTABLE | EP_FIRST_EXE),
+
+		/* Updated at runtime if OP-TEE is loaded */
+		.ep_info.pc = STM32MP_BL32_BASE,
+
+		.ep_info.spsr = SPSR_MODE32(MODE32_svc, SPSR_T_ARM,
+					    SPSR_E_LITTLE,
+					    DISABLE_ALL_EXCEPTIONS),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_PLAT_SETUP),
+
+		/* Updated at runtime if OP-TEE is loaded */
+		.image_info.image_base = STM32MP_BL32_BASE,
+		.image_info.image_max_size = STM32MP_BL32_SIZE,
+
+		.next_handoff_image_id = BL33_IMAGE_ID,
+	},
+
+#if defined(AARCH32_SP_OPTEE)
+	/* Fill BL32 external 1 image related information */
+	{
+		.image_id = BL32_EXTRA1_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+	/* Fill BL32 external 2 image related information */
+	{
+		.image_id = BL32_EXTRA2_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      SECURE | NON_EXECUTABLE),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t,
+				      IMAGE_ATTRIB_SKIP_LOADING),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	},
+#endif /* AARCH32_SP_OPTEE */
+
+	/* Fill BL33 related information */
+	{
+		.image_id = BL33_IMAGE_ID,
+
+		SET_STATIC_PARAM_HEAD(ep_info, PARAM_EP,
+				      VERSION_2, entry_point_info_t,
+				      NON_SECURE | EXECUTABLE),
+
+		.ep_info.pc = PLAT_STM32MP_NS_IMAGE_OFFSET,
+		.ep_info.spsr = SPSR_MODE32(MODE32_svc, SPSR_T_ARM,
+					    SPSR_E_LITTLE,
+					    DISABLE_ALL_EXCEPTIONS),
+
+		SET_STATIC_PARAM_HEAD(image_info, PARAM_EP,
+				      VERSION_2, image_info_t, 0U),
+
+		.image_info.image_base = PLAT_STM32MP_NS_IMAGE_OFFSET,
+		.image_info.image_max_size = STM32MP_DDR_MAX_SIZE -
+			(PLAT_STM32MP_NS_IMAGE_OFFSET - STM32MP_DDR_BASE),
+
+		.next_handoff_image_id = INVALID_IMAGE_ID,
+	}
+};
+
+REGISTER_BL_IMAGE_DESCS(bl2_mem_params_descs)
diff --git a/plat/st/stm32mp1/plat_image_load.c b/plat/st/stm32mp1/plat_image_load.c
index 6d7af74..36a3a1c 100644
--- a/plat/st/stm32mp1/plat_image_load.c
+++ b/plat/st/stm32mp1/plat_image_load.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -23,12 +23,14 @@
  ******************************************************************************/
 bl_load_info_t *plat_get_bl_image_load_info(void)
 {
+#if STM32MP_USE_STM32IMAGE
 	bl_mem_params_node_t *bl33 = get_bl_mem_params_node(BL33_IMAGE_ID);
 	uint32_t ddr_ns_size = stm32mp_get_ddr_ns_size();
 
 	/* Max size is non-secure DDR end address minus image_base */
 	bl33->image_info.image_max_size = STM32MP_DDR_BASE + ddr_ns_size -
 					  bl33->image_info.image_base;
+#endif /* STM32MP_USE_STM32IMAGE */
 
 	return get_bl_load_info_from_mem_params_desc();
 }
@@ -38,5 +40,9 @@
  ******************************************************************************/
 bl_params_t *plat_get_next_bl_params(void)
 {
-	return get_next_bl_params_from_mem_params_desc();
+	bl_params_t *bl_params = get_next_bl_params_from_mem_params_desc();
+
+	populate_next_bl_params_config(bl_params);
+
+	return bl_params;
 }
diff --git a/plat/st/stm32mp1/platform.mk b/plat/st/stm32mp1/platform.mk
index 3595819..badc926 100644
--- a/plat/st/stm32mp1/platform.mk
+++ b/plat/st/stm32mp1/platform.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -9,6 +9,15 @@
 BL2_AT_EL3		:=	1
 USE_COHERENT_MEM	:=	0
 
+# Allow TF-A to concatenate BL2 & BL32 binaries in a single file,
+# share DTB file between BL2 and BL32
+# If it is set to 0, then FIP is used
+STM32MP_USE_STM32IMAGE	?=	0
+
+ifneq ($(STM32MP_USE_STM32IMAGE),1)
+ENABLE_PIE		:=	1
+endif
+
 STM32_TF_VERSION	?=	0
 
 # Enable dynamic memory mapping
@@ -27,8 +36,10 @@
 STM32_BL33_PARTS_NUM		:=	1
 ifeq ($(AARCH32_SP),optee)
 STM32_RUNTIME_PARTS_NUM		:=	3
-else
+else ifeq ($(STM32MP_USE_STM32IMAGE),1)
 STM32_RUNTIME_PARTS_NUM		:=	0
+else
+STM32_RUNTIME_PARTS_NUM		:=	1
 endif
 PLAT_PARTITION_MAX_ENTRIES	:=	$(shell echo $$(($(STM32_TF_A_COPIES) + \
 							 $(STM32_BL33_PARTS_NUM) + \
@@ -40,15 +51,29 @@
 STM32MP_RAW_NAND	?=	0
 STM32MP_SPI_NAND	?=	0
 STM32MP_SPI_NOR		?=	0
+STM32MP_EMMC_BOOT	?=	0
 
-ifeq ($(filter 1,${STM32MP_EMMC} ${STM32MP_SDMMC} ${STM32MP_RAW_NAND} \
-	${STM32MP_SPI_NAND} ${STM32MP_SPI_NOR}),)
-$(error "No boot device driver is enabled")
-endif
+# Serial boot devices
+STM32MP_USB_PROGRAMMER	?=	0
 
 # Device tree
 DTB_FILE_NAME		?=	stm32mp157c-ev1.dtb
+ifeq ($(STM32MP_USE_STM32IMAGE),1)
+ifeq ($(AARCH32_SP),optee)
+BL2_DTSI		:=	stm32mp15-bl2.dtsi
+FDT_SOURCES		:=	$(addprefix ${BUILD_PLAT}/fdts/, $(patsubst %.dtb,%-bl2.dts,$(DTB_FILE_NAME)))
+else
 FDT_SOURCES		:=	$(addprefix fdts/, $(patsubst %.dtb,%.dts,$(DTB_FILE_NAME)))
+endif
+else
+BL2_DTSI		:=	stm32mp15-bl2.dtsi
+FDT_SOURCES		:=	$(addprefix ${BUILD_PLAT}/fdts/, $(patsubst %.dtb,%-bl2.dts,$(DTB_FILE_NAME)))
+ifeq ($(AARCH32_SP),sp_min)
+BL32_DTSI		:=	stm32mp15-bl32.dtsi
+FDT_SOURCES		+=	$(addprefix ${BUILD_PLAT}/fdts/, $(patsubst %.dtb,%-bl32.dts,$(DTB_FILE_NAME)))
+endif
+endif
+DTC_CPPFLAGS		+=	${INCLUDES}
 DTC_FLAGS		+=	-Wno-unit_address_vs_reg
 
 # Macros and rules to build TF binary
@@ -66,6 +91,34 @@
 # Variables for use with stm32image
 STM32IMAGEPATH		?= tools/stm32image
 STM32IMAGE		?= ${STM32IMAGEPATH}/stm32image${BIN_EXT}
+STM32IMAGE_SRC		:= ${STM32IMAGEPATH}/stm32image.c
+
+ifneq (${STM32MP_USE_STM32IMAGE},1)
+FIP_DEPS		+=	dtbs
+STM32MP_HW_CONFIG	:=	${BL33_CFG}
+STM32MP_FW_CONFIG_NAME	:=	$(patsubst %.dtb,%-fw-config.dtb,$(DTB_FILE_NAME))
+STM32MP_FW_CONFIG	:=	${BUILD_PLAT}/fdts/$(STM32MP_FW_CONFIG_NAME)
+ifneq (${AARCH32_SP},none)
+FDT_SOURCES		+=	$(addprefix fdts/, $(patsubst %.dtb,%.dts,$(STM32MP_FW_CONFIG_NAME)))
+endif
+# Add the FW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${STM32MP_FW_CONFIG},--fw-config))
+# Add the HW_CONFIG to FIP and specify the same to certtool
+$(eval $(call TOOL_ADD_PAYLOAD,${STM32MP_HW_CONFIG},--hw-config))
+ifeq ($(AARCH32_SP),sp_min)
+STM32MP_TOS_FW_CONFIG	:= $(addprefix ${BUILD_PLAT}/fdts/, $(patsubst %.dtb,%-bl32.dtb,$(DTB_FILE_NAME)))
+$(eval $(call TOOL_ADD_PAYLOAD,${STM32MP_TOS_FW_CONFIG},--tos-fw-config))
+else
+# Add the build options to pack Trusted OS Extra1 and Trusted OS Extra2 images
+# in the FIP if the platform requires.
+ifneq ($(BL32_EXTRA1),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA1,--tos-fw-extra1))
+endif
+ifneq ($(BL32_EXTRA2),)
+$(eval $(call TOOL_ADD_IMG,BL32_EXTRA2,--tos-fw-extra2))
+endif
+endif
+endif
 
 # Enable flags for C files
 $(eval $(call assert_booleans,\
@@ -75,7 +128,10 @@
 		STM32MP_RAW_NAND \
 		STM32MP_SPI_NAND \
 		STM32MP_SPI_NOR \
+		STM32MP_EMMC_BOOT \
 		PLAT_XLAT_TABLES_DYNAMIC \
+		STM32MP_USB_PROGRAMMER \
+		STM32MP_USE_STM32IMAGE \
 )))
 
 $(eval $(call assert_numerics,\
@@ -91,18 +147,26 @@
 		STM32MP_RAW_NAND \
 		STM32MP_SPI_NAND \
 		STM32MP_SPI_NOR \
+		STM32MP_EMMC_BOOT \
 		PLAT_XLAT_TABLES_DYNAMIC \
 		STM32_TF_A_COPIES \
 		PLAT_PARTITION_MAX_ENTRIES \
+		STM32MP_USB_PROGRAMMER \
+		STM32MP_USE_STM32IMAGE \
 )))
 
 # Include paths and source files
 PLAT_INCLUDES		:=	-Iplat/st/common/include/
 PLAT_INCLUDES		+=	-Iplat/st/stm32mp1/include/
 
+ifeq (${STM32MP_USE_STM32IMAGE},1)
+include common/fdt_wrappers.mk
+else
+include lib/fconf/fconf.mk
+endif
 include lib/libfdt/libfdt.mk
 
-PLAT_BL_COMMON_SOURCES	:=	common/fdt_wrappers.c					\
+PLAT_BL_COMMON_SOURCES	:=	common/uuid.c						\
 				plat/st/common/stm32mp_common.c				\
 				plat/st/stm32mp1/stm32mp1_private.c
 
@@ -134,17 +198,31 @@
 				plat/st/stm32mp1/stm32mp1_context.c			\
 				plat/st/stm32mp1/stm32mp1_dbgmcu.c			\
 				plat/st/stm32mp1/stm32mp1_helper.S			\
-				plat/st/stm32mp1/stm32mp1_security.c			\
 				plat/st/stm32mp1/stm32mp1_syscfg.c
 
+ifneq (${STM32MP_USE_STM32IMAGE},1)
+BL2_SOURCES		+=	${FCONF_SOURCES} ${FCONF_DYN_SOURCES}
+
+BL2_SOURCES		+=	drivers/io/io_fip.c					\
+				plat/st/common/bl2_io_storage.c				\
+				plat/st/common/stm32mp_fconf_io.c			\
+				plat/st/stm32mp1/plat_bl2_mem_params_desc.c		\
+				plat/st/stm32mp1/stm32mp1_fconf_firewall.c
+else
+BL2_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
+BL2_SOURCES		+=	drivers/io/io_dummy.c					\
+				drivers/st/io/io_stm32image.c				\
+				plat/st/common/bl2_stm32_io_storage.c			\
+				plat/st/stm32mp1/plat_bl2_stm32_mem_params_desc.c	\
+				plat/st/stm32mp1/stm32mp1_security.c
+endif
+
 BL2_SOURCES		+=	drivers/io/io_block.c					\
-				drivers/io/io_dummy.c					\
 				drivers/io/io_mtd.c					\
 				drivers/io/io_storage.c					\
 				drivers/st/crypto/stm32_hash.c				\
-				drivers/st/io/io_stm32image.c				\
 				plat/st/common/stm32mp_auth.c				\
-				plat/st/common/bl2_io_storage.c				\
 				plat/st/stm32mp1/bl2_plat_setup.c
 
 ifneq ($(filter 1,${STM32MP_EMMC} ${STM32MP_SDMMC}),)
@@ -182,25 +260,46 @@
 BL2_SOURCES		+=	plat/st/stm32mp1/stm32mp1_boot_device.c
 endif
 
+ifeq (${STM32MP_USB_PROGRAMMER},1)
+#The DFU stack uses only one end point, reduce the USB stack footprint
+$(eval $(call add_define_val,CONFIG_USBD_EP_NB,1U))
+BL2_SOURCES		+=	drivers/io/io_memmap.c					\
+				drivers/st/usb/stm32mp1_usb.c				\
+				drivers/usb/usb_device.c				\
+				plat/st/common/stm32cubeprogrammer_usb.c		\
+				plat/st/common/usb_dfu.c					\
+				plat/st/stm32mp1/stm32mp1_usb_dfu.c
+endif
+
 BL2_SOURCES		+=	drivers/st/ddr/stm32mp1_ddr.c				\
 				drivers/st/ddr/stm32mp1_ram.c
 
 BL2_SOURCES		+=	common/desc_image_load.c				\
-				plat/st/stm32mp1/plat_bl2_mem_params_desc.c		\
 				plat/st/stm32mp1/plat_image_load.c
 
-ifeq ($(AARCH32_SP),optee)
 BL2_SOURCES		+=	lib/optee/optee_utils.c
-endif
 
 # Compilation rules
-.PHONY: check_dtc_version stm32image clean_stm32image
+.PHONY: check_dtc_version stm32image clean_stm32image check_boot_device
 .SUFFIXES:
 
 all: check_dtc_version stm32image ${STM32_TF_STM32}
 
 distclean realclean clean: clean_stm32image
 
+bl2: check_boot_device
+
+check_boot_device:
+	@if [ ${STM32MP_EMMC} != 1 ] && \
+	    [ ${STM32MP_SDMMC} != 1 ] && \
+	    [ ${STM32MP_RAW_NAND} != 1 ] && \
+	    [ ${STM32MP_SPI_NAND} != 1 ] && \
+	    [ ${STM32MP_SPI_NOR} != 1 ] && \
+	    [ ${STM32MP_USB_PROGRAMMER} != 1 ]; then \
+		echo "No boot device driver is enabled"; \
+		false; \
+	fi
+
 stm32image: ${STM32IMAGE}
 
 ${STM32IMAGE}: ${STM32IMAGE_SRC}
@@ -217,14 +316,37 @@
 		false; \
 	fi
 
-
+ifeq ($(STM32MP_USE_STM32IMAGE)-$(AARCH32_SP),1-sp_min)
 ${BUILD_PLAT}/stm32mp1-%.o: ${BUILD_PLAT}/fdts/%.dtb plat/st/stm32mp1/stm32mp1.S bl2 ${BL32_DEP}
 	@echo "  AS      stm32mp1.S"
 	${Q}${AS} ${ASFLAGS} ${TF_CFLAGS} \
 		-DDTB_BIN_PATH=\"$<\" \
-		-c plat/st/stm32mp1/stm32mp1.S -o $@
+		-c $(word 2,$^) -o $@
+else
+# Create DTB file for BL2
+${BUILD_PLAT}/fdts/%-bl2.dts: fdts/%.dts fdts/${BL2_DTSI} | ${BUILD_PLAT} fdt_dirs
+	@echo '#include "$(patsubst fdts/%,%,$<)"' > $@
+	@echo '#include "${BL2_DTSI}"' >> $@
 
-$(eval $(call MAKE_LD,${STM32_TF_LINKERFILE},plat/st/stm32mp1/stm32mp1.ld.S,2))
+${BUILD_PLAT}/fdts/%-bl2.dtb: ${BUILD_PLAT}/fdts/%-bl2.dts
+
+ifeq ($(AARCH32_SP),sp_min)
+# Create DTB file for BL32
+${BUILD_PLAT}/fdts/%-bl32.dts: fdts/%.dts fdts/${BL32_DTSI} | ${BUILD_PLAT} fdt_dirs
+	@echo '#include "$(patsubst fdts/%,%,$<)"' > $@
+	@echo '#include "${BL32_DTSI}"' >> $@
+
+${BUILD_PLAT}/fdts/%-bl32.dtb: ${BUILD_PLAT}/fdts/%-bl32.dts
+endif
+
+${BUILD_PLAT}/stm32mp1-%.o: ${BUILD_PLAT}/fdts/%-bl2.dtb plat/st/stm32mp1/stm32mp1.S bl2
+	@echo "  AS      stm32mp1.S"
+	${Q}${AS} ${ASFLAGS} ${TF_CFLAGS} \
+		-DDTB_BIN_PATH=\"$<\" \
+		-c plat/st/stm32mp1/stm32mp1.S -o $@
+endif
+
+$(eval $(call MAKE_LD,${STM32_TF_LINKERFILE},plat/st/stm32mp1/stm32mp1.ld.S,bl2))
 
 tf-a-%.elf: stm32mp1-%.o ${STM32_TF_LINKERFILE}
 	@echo "  LDS     $<"
diff --git a/plat/st/stm32mp1/services/bsec_svc.c b/plat/st/stm32mp1/services/bsec_svc.c
index 2a60e43..a1d7fc6 100644
--- a/plat/st/stm32mp1/services/bsec_svc.c
+++ b/plat/st/stm32mp1/services/bsec_svc.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2016-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -28,11 +28,11 @@
 		result = bsec_program_otp(x3, x2);
 		break;
 	case STM32_SMC_WRITE_SHADOW:
-		*ret_otp_value = 0;
+		*ret_otp_value = 0U;
 		result = bsec_write_otp(x3, x2);
 		break;
 	case STM32_SMC_READ_OTP:
-		*ret_otp_value = 0;
+		*ret_otp_value = 0U;
 		result = bsec_read_otp(&tmp_data, x2);
 		if (result != BSEC_OK) {
 			break;
@@ -52,9 +52,8 @@
 		break;
 
 	default:
-		result = BSEC_ERROR;
-		break;
+		return STM32_SMC_INVALID_PARAMS;
 	}
 
-	return result;
+	return (result == BSEC_OK) ? STM32_SMC_OK : STM32_SMC_FAILED;
 }
diff --git a/plat/st/stm32mp1/services/stm32mp1_svc_setup.c b/plat/st/stm32mp1/services/stm32mp1_svc_setup.c
index 49375a6..ed8a448 100644
--- a/plat/st/stm32mp1/services/stm32mp1_svc_setup.c
+++ b/plat/st/stm32mp1/services/stm32mp1_svc_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2019, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2014-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -9,7 +9,7 @@
 
 #include <common/debug.h>
 #include <common/runtime_svc.h>
-#include <drivers/st/scmi-msg.h>
+#include <drivers/scmi-msg.h>
 #include <lib/psci/psci.h>
 #include <tools_share/uuid.h>
 
@@ -75,7 +75,7 @@
 
 	default:
 		WARN("Unimplemented STM32MP1 Service Call: 0x%x\n", smc_fid);
-		ret1 = SMC_UNK;
+		ret1 = STM32_SMC_NOT_SUPPORTED;
 		break;
 	}
 
diff --git a/plat/st/stm32mp1/sp_min/sp_min-stm32mp1.mk b/plat/st/stm32mp1/sp_min/sp_min-stm32mp1.mk
index 8866fb5..239b60a 100644
--- a/plat/st/stm32mp1/sp_min/sp_min-stm32mp1.mk
+++ b/plat/st/stm32mp1/sp_min/sp_min-stm32mp1.mk
@@ -15,6 +15,10 @@
 				plat/st/stm32mp1/stm32mp1_shared_resources.c	\
 				plat/st/stm32mp1/stm32mp1_topology.c
 
+# FDT wrappers
+include common/fdt_wrappers.mk
+BL32_SOURCES		+=	${FDT_WRAPPERS_SOURCES}
+
 # Generic GIC v2
 include drivers/arm/gic/v2/gicv2.mk
 
@@ -26,11 +30,11 @@
 BL32_SOURCES		+=	plat/common/plat_psci_common.c
 
 # SCMI server drivers
-BL32_SOURCES		+=	drivers/st/scmi-msg/base.c		\
-				drivers/st/scmi-msg/clock.c		\
-				drivers/st/scmi-msg/entry.c		\
-				drivers/st/scmi-msg/reset_domain.c	\
-				drivers/st/scmi-msg/smt.c
+BL32_SOURCES		+=	drivers/scmi-msg/base.c		\
+				drivers/scmi-msg/clock.c		\
+				drivers/scmi-msg/entry.c		\
+				drivers/scmi-msg/reset_domain.c	\
+				drivers/scmi-msg/smt.c
 
 # stm32mp1 specific services
 BL32_SOURCES		+=	plat/st/stm32mp1/services/bsec_svc.c		\
diff --git a/plat/st/stm32mp1/sp_min/sp_min_setup.c b/plat/st/stm32mp1/sp_min/sp_min_setup.c
index b639fcb..1495e02 100644
--- a/plat/st/stm32mp1/sp_min/sp_min_setup.c
+++ b/plat/st/stm32mp1/sp_min/sp_min_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -45,7 +45,8 @@
 {
 	switch (id & INT_ID_MASK) {
 	case STM32MP1_IRQ_TZC400:
-		ERROR("STM32MP1_IRQ_TZC400 generated\n");
+		tzc400_init(STM32MP1_TZC_BASE);
+		(void)tzc400_it_handler();
 		panic();
 		break;
 	case STM32MP1_IRQ_AXIERRIRQ:
@@ -117,6 +118,11 @@
 	struct dt_node_info dt_uart_info;
 	int result;
 	bl_params_t *params_from_bl2 = (bl_params_t *)arg0;
+#if STM32MP_USE_STM32IMAGE
+	uintptr_t dt_addr = STM32MP_DTB_BASE;
+#else
+	uintptr_t dt_addr = arg1;
+#endif
 
 	/* Imprecise aborts can be masked in NonSecure */
 	write_scr(read_scr() | SCR_AW_BIT);
@@ -140,13 +146,23 @@
 	while (bl_params != NULL) {
 		if (bl_params->image_id == BL33_IMAGE_ID) {
 			bl33_image_ep_info = *bl_params->ep_info;
+			/*
+			 *  Check if hw_configuration is given to BL32 and
+			 *  share it to BL33.
+			 */
+			if (arg2 != 0U) {
+				bl33_image_ep_info.args.arg0 = 0U;
+				bl33_image_ep_info.args.arg1 = 0U;
+				bl33_image_ep_info.args.arg2 = arg2;
+			}
+
 			break;
 		}
 
 		bl_params = bl_params->next_params_info;
 	}
 
-	if (dt_open_and_check() < 0) {
+	if (dt_open_and_check(dt_addr) < 0) {
 		panic();
 	}
 
@@ -185,9 +201,6 @@
  ******************************************************************************/
 void sp_min_platform_setup(void)
 {
-	/* Initialize tzc400 after DDR initialization */
-	stm32mp1_security_setup();
-
 	generic_delay_timer_init();
 
 	stm32mp1_gic_init();
diff --git a/plat/st/stm32mp1/stm32mp1.S b/plat/st/stm32mp1/stm32mp1.S
index 7255fe5..85caa0a 100644
--- a/plat/st/stm32mp1/stm32mp1.S
+++ b/plat/st/stm32mp1/stm32mp1.S
@@ -1,13 +1,15 @@
 /*
- * Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
+#if STM32MP_USE_STM32IMAGE
 #ifdef BL32_BIN_PATH
 .section .bl32_image
 .incbin BL32_BIN_PATH
 #endif
+#endif /* STM32MP_USE_STM32IMAGE */
 
 .section .bl2_image
 .incbin BL2_BIN_PATH
diff --git a/plat/st/stm32mp1/stm32mp1.ld.S b/plat/st/stm32mp1/stm32mp1.ld.S
index b347bad..945de99 100644
--- a/plat/st/stm32mp1/stm32mp1.ld.S
+++ b/plat/st/stm32mp1/stm32mp1.ld.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -43,7 +43,11 @@
          * The strongest and only alignment contraint is MMU 4K page.
          * Indeed as images below will be removed, 4K pages will be re-used.
          */
+#if STM32MP_USE_STM32IMAGE
         . = ( STM32MP_DTB_BASE - STM32MP_BINARY_BASE );
+#else
+        . = ( STM32MP_BL2_DTB_BASE - STM32MP_BINARY_BASE );
+#endif /* STM32MP_USE_STM32IMAGE */
         __DTB_IMAGE_START__ = .;
         *(.dtb_image*)
         __DTB_IMAGE_END__ = .;
@@ -58,7 +62,7 @@
         *(.bl2_image*)
         __BL2_IMAGE_END__ = .;
 
-#ifndef AARCH32_SP_OPTEE
+#if STM32MP_USE_STM32IMAGE && !defined(AARCH32_SP_OPTEE)
         /*
          * bl32 will be settled by bl2.
          * The strongest and only alignment constraint is 8 words to simplify
@@ -68,7 +72,7 @@
         __BL32_IMAGE_START__ = .;
         *(.bl32_image*)
         __BL32_IMAGE_END__ = .;
-#endif
+#endif /* STM32MP_USE_STM32IMAGE && !defined(AARCH32_SP_OPTEE) */
 
         __DATA_END__ = .;
     } >RAM
diff --git a/plat/st/stm32mp1/stm32mp1_def.h b/plat/st/stm32mp1/stm32mp1_def.h
index ee04a23..f5d4b2f 100644
--- a/plat/st/stm32mp1/stm32mp1_def.h
+++ b/plat/st/stm32mp1/stm32mp1_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -28,9 +28,17 @@
 #include <stm32mp1_shared_resources.h>
 #endif
 
+#if !STM32MP_USE_STM32IMAGE
+#include "stm32mp1_fip_def.h"
+#else /* STM32MP_USE_STM32IMAGE */
+#include "stm32mp1_stm32image_def.h"
+#endif /* STM32MP_USE_STM32IMAGE */
+
 /*******************************************************************************
  * CHIP ID
  ******************************************************************************/
+#define STM32MP1_CHIP_ID	U(0x500)
+
 #define STM32MP157C_PART_NB	U(0x05000000)
 #define STM32MP157A_PART_NB	U(0x05000001)
 #define STM32MP153C_PART_NB	U(0x05000024)
@@ -79,13 +87,6 @@
 /* DDR configuration */
 #define STM32MP_DDR_BASE		U(0xC0000000)
 #define STM32MP_DDR_MAX_SIZE		U(0x40000000)	/* Max 1GB */
-#ifdef AARCH32_SP_OPTEE
-#define STM32MP_DDR_S_SIZE		U(0x01E00000)	/* 30 MB */
-#define STM32MP_DDR_SHMEM_SIZE		U(0x00200000)	/* 2 MB */
-#else
-#define STM32MP_DDR_S_SIZE		U(0)
-#define STM32MP_DDR_SHMEM_SIZE		U(0)
-#endif
 
 /* DDR power initializations */
 #ifndef __ASSEMBLER__
@@ -109,42 +110,6 @@
 					 (STM32MP_PARAM_LOAD_SIZE +	\
 					  STM32MP_HEADER_SIZE))
 
-#ifdef AARCH32_SP_OPTEE
-#define STM32MP_BL32_SIZE		U(0)
-
-#define STM32MP_OPTEE_BASE		STM32MP_SEC_SYSRAM_BASE
-
-#define STM32MP_OPTEE_SIZE		(STM32MP_DTB_BASE -  \
-					 STM32MP_OPTEE_BASE)
-#else
-#if STACK_PROTECTOR_ENABLED
-#define STM32MP_BL32_SIZE		U(0x00012000)	/* 72 KB for BL32 */
-#else
-#define STM32MP_BL32_SIZE		U(0x00011000)	/* 68 KB for BL32 */
-#endif
-#endif
-
-#define STM32MP_BL32_BASE		(STM32MP_SEC_SYSRAM_BASE + \
-					 STM32MP_SEC_SYSRAM_SIZE - \
-					 STM32MP_BL32_SIZE)
-
-#ifdef AARCH32_SP_OPTEE
-#if STACK_PROTECTOR_ENABLED
-#define STM32MP_BL2_SIZE		U(0x0001A000)	/* 100 KB for BL2 */
-#else
-#define STM32MP_BL2_SIZE		U(0x00018000)	/* 92 KB for BL2 */
-#endif
-#else
-#if STACK_PROTECTOR_ENABLED
-#define STM32MP_BL2_SIZE		U(0x00019000)	/* 96 KB for BL2 */
-#else
-#define STM32MP_BL2_SIZE		U(0x00017000)	/* 88 KB for BL2 */
-#endif
-#endif
-
-#define STM32MP_BL2_BASE		(STM32MP_BL32_BASE - \
-					 STM32MP_BL2_SIZE)
-
 /* BL2 and BL32/sp_min require 4 tables */
 #define MAX_XLAT_TABLES			U(4)		/* 16 KB for mapping */
 
@@ -155,39 +120,14 @@
 #if defined(IMAGE_BL2)
   #define MAX_MMAP_REGIONS		11
 #endif
-#if defined(IMAGE_BL32)
-  #define MAX_MMAP_REGIONS		6
-#endif
-
-/* DTB initialization value */
-#define STM32MP_DTB_SIZE		U(0x00005000)	/* 20 KB for DTB */
-
-#define STM32MP_DTB_BASE		(STM32MP_BL2_BASE - \
-					 STM32MP_DTB_SIZE)
 
 #define STM32MP_BL33_BASE		(STM32MP_DDR_BASE + U(0x100000))
+#define STM32MP_BL33_MAX_SIZE		U(0x400000)
 
 /* Define maximum page size for NAND devices */
 #define PLATFORM_MTD_MAX_PAGE_SIZE	U(0x1000)
 
 /*******************************************************************************
- * STM32MP1 RAW partition offset for MTD devices
- ******************************************************************************/
-#define STM32MP_NOR_BL33_OFFSET		U(0x00080000)
-#ifdef AARCH32_SP_OPTEE
-#define STM32MP_NOR_TEEH_OFFSET		U(0x00280000)
-#define STM32MP_NOR_TEED_OFFSET		U(0x002C0000)
-#define STM32MP_NOR_TEEX_OFFSET		U(0x00300000)
-#endif
-
-#define STM32MP_NAND_BL33_OFFSET	U(0x00200000)
-#ifdef AARCH32_SP_OPTEE
-#define STM32MP_NAND_TEEH_OFFSET	U(0x00600000)
-#define STM32MP_NAND_TEED_OFFSET	U(0x00680000)
-#define STM32MP_NAND_TEEX_OFFSET	U(0x00700000)
-#endif
-
-/*******************************************************************************
  * STM32MP1 device/io map related constants (used for MMU)
  ******************************************************************************/
 #define STM32MP1_DEVICE1_BASE		U(0x40000000)
@@ -265,6 +205,8 @@
 #define DEBUG_UART_TX_CLKSRC		RCC_UART24CKSELR_HSI
 #define DEBUG_UART_TX_EN_REG		RCC_MP_APB1ENSETR
 #define DEBUG_UART_TX_EN		RCC_MP_APB1ENSETR_UART4EN
+#define DEBUG_UART_RST_REG		RCC_APB1RSTSETR
+#define DEBUG_UART_RST_BIT		RCC_APB1RSTSETR_UART4RST
 
 /*******************************************************************************
  * STM32MP1 ETZPC
@@ -369,19 +311,8 @@
  ******************************************************************************/
 #define STM32MP1_TZC_BASE		U(0x5C006000)
 
-#define STM32MP1_TZC_A7_ID		U(0)
-#define STM32MP1_TZC_M4_ID		U(1)
-#define STM32MP1_TZC_LCD_ID		U(3)
-#define STM32MP1_TZC_GPU_ID		U(4)
-#define STM32MP1_TZC_MDMA_ID		U(5)
-#define STM32MP1_TZC_DMA_ID		U(6)
-#define STM32MP1_TZC_USB_HOST_ID	U(7)
-#define STM32MP1_TZC_USB_OTG_ID		U(8)
-#define STM32MP1_TZC_SDMMC_ID		U(9)
-#define STM32MP1_TZC_ETH_ID		U(10)
-#define STM32MP1_TZC_DAP_ID		U(15)
-
-#define STM32MP1_FILTER_BIT_ALL		U(3)
+#define STM32MP1_FILTER_BIT_ALL		(TZC_400_REGION_ATTR_FILTER_BIT(0) | \
+					 TZC_400_REGION_ATTR_FILTER_BIT(1))
 
 /*******************************************************************************
  * STM32MP1 SDMMC
@@ -408,6 +339,9 @@
 #define DATA0_OTP			U(0)
 #define PART_NUMBER_OTP			U(1)
 #define NAND_OTP			U(9)
+#define UID0_OTP			U(13)
+#define UID1_OTP			U(14)
+#define UID2_OTP			U(15)
 #define PACKAGE_OTP			U(16)
 #define HW2_OTP				U(18)
 
@@ -470,6 +404,9 @@
 /* NAND number of planes */
 #define NAND_PLANE_BIT_NB_MASK		BIT(14)
 
+/* UID OTP */
+#define UID_WORD_NB			U(3)
+
 /*******************************************************************************
  * STM32MP1 TAMP
  ******************************************************************************/
@@ -484,6 +421,11 @@
 #endif
 
 /*******************************************************************************
+ * STM32MP1 USB
+ ******************************************************************************/
+#define USB_OTG_BASE			U(0x49000000)
+
+/*******************************************************************************
  * STM32MP1 DDRCTRL
  ******************************************************************************/
 #define DDRCTRL_BASE			U(0x5A003000)
diff --git a/plat/st/stm32mp1/stm32mp1_fconf_firewall.c b/plat/st/stm32mp1/stm32mp1_fconf_firewall.c
new file mode 100644
index 0000000..caf9ff1
--- /dev/null
+++ b/plat/st/stm32mp1/stm32mp1_fconf_firewall.c
@@ -0,0 +1,123 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+
+#include <common/debug.h>
+#include <common/fdt_wrappers.h>
+#include <drivers/arm/tzc400.h>
+#include <drivers/st/stm32mp1_clk.h>
+#include <dt-bindings/clock/stm32mp1-clks.h>
+#include <lib/fconf/fconf.h>
+#include <lib/object_pool.h>
+#include <libfdt.h>
+#include <tools_share/firmware_image_package.h>
+
+#include <platform_def.h>
+#include <stm32mp_fconf_getter.h>
+
+#define STM32MP_REGION_PARAMS	4
+#define STM32MP_MAX_REGIONS	8
+#define FORCE_SEC_REGION	BIT(31)
+
+static uint32_t nb_regions;
+
+struct dt_id_attr {
+	fdt32_t id_attr[STM32MP_MAX_REGIONS];
+};
+
+void stm32mp1_arch_security_setup(void)
+{
+	stm32mp_clk_enable(TZC1);
+	stm32mp_clk_enable(TZC2);
+
+	tzc400_init(STM32MP1_TZC_BASE);
+	tzc400_disable_filters();
+
+	/*
+	 * Region 0 set to cover all DRAM at 0xC000_0000
+	 * Only secure access is granted in read/write.
+	 */
+	tzc400_configure_region0(TZC_REGION_S_RDWR, 0);
+
+	tzc400_set_action(TZC_ACTION_ERR);
+	tzc400_enable_filters();
+}
+
+void stm32mp1_security_setup(void)
+{
+	uint8_t i;
+
+	assert(nb_regions > 0U);
+
+	tzc400_init(STM32MP1_TZC_BASE);
+	tzc400_disable_filters();
+
+	/*
+	 * Region 0 set to cover all DRAM at 0xC000_0000
+	 * No access is allowed.
+	 */
+	tzc400_configure_region0(TZC_REGION_S_NONE, 0);
+
+	for (i = 1U; i <= nb_regions; i++) {
+		tzc400_update_filters(i, STM32MP1_FILTER_BIT_ALL);
+	}
+
+	tzc400_set_action(TZC_ACTION_INT);
+	tzc400_enable_filters();
+}
+
+static int fconf_populate_stm32mp1_firewall(uintptr_t config)
+{
+	int node, len;
+	unsigned int i;
+	const struct dt_id_attr *conf_list;
+	const void *dtb = (const void *)config;
+
+	/* Assert the node offset point to "st,mem-firewall" compatible property */
+	const char *compatible_str = "st,mem-firewall";
+
+	node = fdt_node_offset_by_compatible(dtb, -1, compatible_str);
+	if (node < 0) {
+		ERROR("FCONF: Can't find %s compatible in dtb\n", compatible_str);
+		return node;
+	}
+
+	conf_list = (const struct dt_id_attr *)fdt_getprop(dtb, node, "memory-ranges", &len);
+	if (conf_list == NULL) {
+		WARN("FCONF: Read cell failed for %s\n", "memory-ranges");
+		return -1;
+	}
+
+	/* Locate the memory cells and read all values */
+	for (i = 0U; i < (unsigned int)(len / (sizeof(uint32_t) * STM32MP_REGION_PARAMS)); i++) {
+		uint32_t base;
+		uint32_t size;
+		uint32_t sec_attr;
+		uint32_t nsaid;
+
+		base = fdt32_to_cpu(conf_list->id_attr[i * STM32MP_REGION_PARAMS]);
+		size = fdt32_to_cpu(conf_list->id_attr[i * STM32MP_REGION_PARAMS + 1]);
+		sec_attr = fdt32_to_cpu(conf_list->id_attr[i * STM32MP_REGION_PARAMS + 2]);
+		nsaid = fdt32_to_cpu(conf_list->id_attr[i * STM32MP_REGION_PARAMS + 3]);
+
+		VERBOSE("FCONF: stm32mp1-firewall cell found with value = 0x%x 0x%x 0x%x 0x%x\n",
+			base, size, sec_attr, nsaid);
+
+		nb_regions++;
+
+		/* Configure region but keep disabled for secure access for BL2 load */
+		tzc400_configure_region(0U, nb_regions, (unsigned long long)base,
+					(unsigned long long)base + size - 1ULL, sec_attr, nsaid);
+	}
+
+	/* Force flush as the value will be used cache off */
+	flush_dcache_range((uintptr_t)&nb_regions, sizeof(uint32_t));
+
+	return 0;
+}
+
+FCONF_REGISTER_POPULATOR(FW_CONFIG, stm32mp1_firewall, fconf_populate_stm32mp1_firewall);
diff --git a/plat/st/stm32mp1/stm32mp1_fip_def.h b/plat/st/stm32mp1/stm32mp1_fip_def.h
new file mode 100644
index 0000000..d8561dc
--- /dev/null
+++ b/plat/st/stm32mp1/stm32mp1_fip_def.h
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef STM32MP1_FIP_DEF_H
+#define STM32MP1_FIP_DEF_H
+
+#define STM32MP_DDR_S_SIZE		U(0x01E00000)	/* 30 MB */
+#define STM32MP_DDR_SHMEM_SIZE		U(0x00200000)	/* 2 MB */
+
+#define STM32MP_BL2_SIZE		U(0x0001B000)	/* 108 KB for BL2 */
+#define STM32MP_BL2_DTB_SIZE		U(0x00006000)	/* 24 KB for DTB */
+#define STM32MP_BL32_SIZE		U(0x00019000)	/* 100 KB for BL32 */
+#define STM32MP_BL32_DTB_SIZE		U(0x00005000)	/* 20 KB for DTB */
+#define STM32MP_FW_CONFIG_MAX_SIZE	PAGE_SIZE	/* 4 KB for FCONF DTB */
+#define STM32MP_HW_CONFIG_MAX_SIZE	U(0x40000)	/* 256 KB for HW config DTB */
+
+#define STM32MP_BL2_BASE		(STM32MP_SEC_SYSRAM_BASE + \
+					 STM32MP_SEC_SYSRAM_SIZE - \
+					 STM32MP_BL2_SIZE)
+
+#define STM32MP_BL2_DTB_BASE		(STM32MP_BL2_BASE - \
+					 STM32MP_BL2_DTB_SIZE)
+
+#define STM32MP_BL32_DTB_BASE		STM32MP_SYSRAM_BASE
+
+#define STM32MP_BL32_BASE		(STM32MP_BL32_DTB_BASE + \
+					 STM32MP_BL32_DTB_SIZE)
+
+
+#if defined(IMAGE_BL2)
+#define STM32MP_DTB_SIZE		STM32MP_BL2_DTB_SIZE
+#define STM32MP_DTB_BASE		STM32MP_BL2_DTB_BASE
+#endif
+#if defined(IMAGE_BL32)
+#define STM32MP_DTB_SIZE		STM32MP_BL32_DTB_SIZE
+#define STM32MP_DTB_BASE		STM32MP_BL32_DTB_BASE
+#endif
+
+#ifdef AARCH32_SP_OPTEE
+#define STM32MP_OPTEE_BASE		STM32MP_SEC_SYSRAM_BASE
+
+#define STM32MP_OPTEE_SIZE		(STM32MP_BL2_DTB_BASE -  \
+					 STM32MP_OPTEE_BASE)
+#endif
+
+#define STM32MP_FW_CONFIG_BASE		(STM32MP_SYSRAM_BASE + \
+					 STM32MP_SYSRAM_SIZE - \
+					 PAGE_SIZE)
+#define STM32MP_HW_CONFIG_BASE		(STM32MP_BL33_BASE + \
+					STM32MP_BL33_MAX_SIZE)
+
+/*
+ * MAX_MMAP_REGIONS is usually:
+ * BL stm32mp1_mmap size + mmap regions in *_plat_arch_setup
+ */
+#if defined(IMAGE_BL32)
+#define MAX_MMAP_REGIONS		10
+#endif
+
+/*******************************************************************************
+ * STM32MP1 RAW partition offset for MTD devices
+ ******************************************************************************/
+#define STM32MP_NOR_FIP_OFFSET		U(0x00080000)
+#define STM32MP_NAND_FIP_OFFSET		U(0x00200000)
+
+#endif /* STM32MP1_FIP_DEF_H */
diff --git a/plat/st/stm32mp1/stm32mp1_helper.S b/plat/st/stm32mp1/stm32mp1_helper.S
index 3021362..cac9752 100644
--- a/plat/st/stm32mp1/stm32mp1_helper.S
+++ b/plat/st/stm32mp1/stm32mp1_helper.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -148,6 +148,19 @@
 	 * ---------------------------------------------
 	 */
 func plat_crash_console_init
+	/* Reset UART peripheral */
+	ldr	r1, =(RCC_BASE + DEBUG_UART_RST_REG)
+	ldr	r2, =DEBUG_UART_RST_BIT
+	str	r2, [r1]
+1:
+	ldr	r0, [r1]
+	ands	r2, r0, r2
+	beq	1b
+	str	r2, [r1, #4] /* RSTCLR register */
+2:
+	ldr	r0, [r1]
+	ands	r2, r0, r2
+	bne	2b
 	/* Enable GPIOs for UART TX */
 	ldr	r1, =(RCC_BASE + DEBUG_UART_TX_GPIO_BANK_CLK_REG)
 	ldr	r2, [r1]
@@ -204,7 +217,7 @@
 	 * ---------------------------------------------
 	 */
 func plat_crash_console_flush
-	ldr	r1, =STM32MP_DEBUG_USART_BASE
+	ldr	r0, =STM32MP_DEBUG_USART_BASE
 	b	console_stm32_core_flush
 endfunc plat_crash_console_flush
 
diff --git a/plat/st/stm32mp1/stm32mp1_private.c b/plat/st/stm32mp1/stm32mp1_private.c
index bc77ee3..e4065c1 100644
--- a/plat/st/stm32mp1/stm32mp1_private.c
+++ b/plat/st/stm32mp1/stm32mp1_private.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -153,63 +153,70 @@
 	}
 }
 
-static int get_part_number(uint32_t *part_nb)
+uint32_t stm32mp_get_chip_version(void)
 {
-	uint32_t part_number;
+	uint32_t version = 0U;
+
+	if (stm32mp1_dbgmcu_get_chip_version(&version) < 0) {
+		INFO("Cannot get CPU version, debug disabled\n");
+		return 0U;
+	}
+
+	return version;
+}
+
+uint32_t stm32mp_get_chip_dev_id(void)
+{
 	uint32_t dev_id;
 
-	assert(part_nb != NULL);
-
 	if (stm32mp1_dbgmcu_get_chip_dev_id(&dev_id) < 0) {
-		return -1;
+		INFO("Use default chip ID, debug disabled\n");
+		dev_id = STM32MP1_CHIP_ID;
+	}
+
+	return dev_id;
+}
+
+static uint32_t get_part_number(void)
+{
+	static uint32_t part_number;
+
+	if (part_number != 0U) {
+		return part_number;
 	}
 
 	if (bsec_shadow_read_otp(&part_number, PART_NUMBER_OTP) != BSEC_OK) {
-		ERROR("BSEC: PART_NUMBER_OTP Error\n");
-		return -1;
+		panic();
 	}
 
 	part_number = (part_number & PART_NUMBER_OTP_PART_MASK) >>
 		PART_NUMBER_OTP_PART_SHIFT;
 
-	*part_nb = part_number | (dev_id << 16);
+	part_number |= stm32mp_get_chip_dev_id() << 16;
 
-	return 0;
+	return part_number;
 }
 
-static int get_cpu_package(uint32_t *cpu_package)
+static uint32_t get_cpu_package(void)
 {
 	uint32_t package;
 
-	assert(cpu_package != NULL);
-
 	if (bsec_shadow_read_otp(&package, PACKAGE_OTP) != BSEC_OK) {
-		ERROR("BSEC: PACKAGE_OTP Error\n");
-		return -1;
+		panic();
 	}
 
-	*cpu_package = (package & PACKAGE_OTP_PKG_MASK) >>
+	package = (package & PACKAGE_OTP_PKG_MASK) >>
 		PACKAGE_OTP_PKG_SHIFT;
 
-	return 0;
+	return package;
 }
 
-void stm32mp_print_cpuinfo(void)
+void stm32mp_get_soc_name(char name[STM32_SOC_NAME_SIZE])
 {
-	const char *cpu_s, *cpu_r, *pkg;
-	uint32_t part_number;
-	uint32_t cpu_package;
-	uint32_t chip_dev_id;
-	int ret;
+	char *cpu_s, *cpu_r, *pkg;
 
 	/* MPUs Part Numbers */
-	ret = get_part_number(&part_number);
-	if (ret < 0) {
-		WARN("Cannot get part number\n");
-		return;
-	}
-
-	switch (part_number) {
+	switch (get_part_number()) {
 	case STM32MP157C_PART_NB:
 		cpu_s = "157C";
 		break;
@@ -252,13 +259,7 @@
 	}
 
 	/* Package */
-	ret = get_cpu_package(&cpu_package);
-	if (ret < 0) {
-		WARN("Cannot get CPU package\n");
-		return;
-	}
-
-	switch (cpu_package) {
+	switch (get_cpu_package()) {
 	case PKG_AA_LFBGA448:
 		pkg = "AA";
 		break;
@@ -277,13 +278,7 @@
 	}
 
 	/* REVISION */
-	ret = stm32mp1_dbgmcu_get_chip_version(&chip_dev_id);
-	if (ret < 0) {
-		WARN("Cannot get CPU version\n");
-		return;
-	}
-
-	switch (chip_dev_id) {
+	switch (stm32mp_get_chip_version()) {
 	case STM32MP1_REV_B:
 		cpu_r = "B";
 		break;
@@ -295,7 +290,16 @@
 		break;
 	}
 
-	NOTICE("CPU: STM32MP%s%s Rev.%s\n", cpu_s, pkg, cpu_r);
+	snprintf(name, STM32_SOC_NAME_SIZE,
+		 "STM32MP%s%s Rev.%s", cpu_s, pkg, cpu_r);
+}
+
+void stm32mp_print_cpuinfo(void)
+{
+	char name[STM32_SOC_NAME_SIZE];
+
+	stm32mp_get_soc_name(name);
+	NOTICE("CPU: %s\n", name);
 }
 
 void stm32mp_print_boardinfo(void)
@@ -349,20 +353,12 @@
 /* Return true when SoC provides a single Cortex-A7 core, and false otherwise */
 bool stm32mp_is_single_core(void)
 {
-	uint32_t part_number;
-
-	if (get_part_number(&part_number) < 0) {
-		ERROR("Invalid part number, assume single core chip");
-		return true;
-	}
-
-	switch (part_number) {
+	switch (get_part_number()) {
 	case STM32MP151A_PART_NB:
 	case STM32MP151C_PART_NB:
 	case STM32MP151D_PART_NB:
 	case STM32MP151F_PART_NB:
 		return true;
-
 	default:
 		return false;
 	}
@@ -456,6 +452,7 @@
 }
 #endif
 
+#if STM32MP_USE_STM32IMAGE
 /* Get the non-secure DDR size */
 uint32_t stm32mp_get_ddr_ns_size(void)
 {
@@ -476,3 +473,4 @@
 
 	return ddr_ns_size;
 }
+#endif /* STM32MP_USE_STM32IMAGE */
diff --git a/plat/st/stm32mp1/stm32mp1_scmi.c b/plat/st/stm32mp1/stm32mp1_scmi.c
index 80faf0c..6d60bd4 100644
--- a/plat/st/stm32mp1/stm32mp1_scmi.c
+++ b/plat/st/stm32mp1/stm32mp1_scmi.c
@@ -8,8 +8,8 @@
 
 #include <platform_def.h>
 
-#include <drivers/st/scmi-msg.h>
-#include <drivers/st/scmi.h>
+#include <drivers/scmi-msg.h>
+#include <drivers/scmi.h>
 #include <drivers/st/stm32mp1_clk.h>
 #include <drivers/st/stm32mp_reset.h>
 #include <dt-bindings/clock/stm32mp1-clks.h>
diff --git a/plat/st/stm32mp1/stm32mp1_security.c b/plat/st/stm32mp1/stm32mp1_security.c
index 3a29ba9..19ef4f0 100644
--- a/plat/st/stm32mp1/stm32mp1_security.c
+++ b/plat/st/stm32mp1/stm32mp1_security.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -12,20 +12,47 @@
 #include <drivers/arm/tzc400.h>
 #include <drivers/st/stm32mp1_clk.h>
 #include <dt-bindings/clock/stm32mp1-clks.h>
+#include <dt-bindings/soc/stm32mp15-tzc400.h>
 #include <lib/mmio.h>
 
-#define TZC_REGION_NSEC_ALL_ACCESS_RDWR \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_A7_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_GPU_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_LCD_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_MDMA_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_M4_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DMA_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_HOST_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_OTG_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_SDMMC_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_ETH_ID) | \
-	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DAP_ID)
+static unsigned int region_nb;
+
+static void init_tzc400_begin(unsigned int region0_attr)
+{
+	tzc400_init(STM32MP1_TZC_BASE);
+	tzc400_disable_filters();
+
+	/* Region 0 set to cover all DRAM at 0xC000_0000 */
+	tzc400_configure_region0(region0_attr, 0);
+
+	region_nb = 1U;
+}
+
+static void init_tzc400_end(unsigned int action)
+{
+	tzc400_set_action(action);
+	tzc400_enable_filters();
+}
+
+static void tzc400_add_region(unsigned long long region_base,
+			      unsigned long long region_top, bool sec)
+{
+	unsigned int sec_attr;
+	unsigned int nsaid_permissions;
+
+	if (sec) {
+		sec_attr = TZC_REGION_S_RDWR;
+		nsaid_permissions = 0;
+	} else {
+		sec_attr = TZC_REGION_S_NONE;
+		nsaid_permissions = TZC_REGION_NSEC_ALL_ACCESS_RDWR;
+	}
+
+	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, region_nb, region_base,
+				region_top, sec_attr, nsaid_permissions);
+
+	region_nb++;
+}
 
 /*******************************************************************************
  * Initialize the TrustZone Controller. Configure Region 0 with Secure RW access
@@ -38,10 +65,9 @@
 	unsigned long long ddr_ns_size =
 		(unsigned long long)stm32mp_get_ddr_ns_size();
 	unsigned long long ddr_ns_top = ddr_base + (ddr_ns_size - 1U);
+	unsigned long long ddr_top __unused;
 
-	tzc400_init(STM32MP1_TZC_BASE);
-
-	tzc400_disable_filters();
+	init_tzc400_begin(TZC_REGION_S_NONE);
 
 	/*
 	 * Region 1 set to cover all non-secure DRAM at 0xC000_0000. Apply the
@@ -49,36 +75,28 @@
 	 */
 	region_base = ddr_base;
 	region_top = ddr_ns_top;
-	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, 1,
-				region_base,
-				region_top,
-				TZC_REGION_S_NONE,
-				TZC_REGION_NSEC_ALL_ACCESS_RDWR);
+	tzc400_add_region(region_base, region_top, false);
 
 #ifdef AARCH32_SP_OPTEE
 	/* Region 2 set to cover all secure DRAM. */
 	region_base = region_top + 1U;
 	region_top += STM32MP_DDR_S_SIZE;
-	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, 2,
-				region_base,
-				region_top,
-				TZC_REGION_S_RDWR,
-				0);
+	tzc400_add_region(region_base, region_top, true);
 
-	/* Region 3 set to cover non-secure shared memory DRAM. */
-	region_base = region_top + 1U;
-	region_top += STM32MP_DDR_SHMEM_SIZE;
-	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, 3,
-				region_base,
-				region_top,
-				TZC_REGION_S_NONE,
-				TZC_REGION_NSEC_ALL_ACCESS_RDWR);
+	ddr_top = STM32MP_DDR_BASE + dt_get_ddr_size() - 1U;
+	if (region_top < ddr_top) {
+		/* Region 3 set to cover non-secure memory DRAM after BL32. */
+		region_base = region_top + 1U;
+		region_top = ddr_top;
+		tzc400_add_region(region_base, region_top, false);
+	}
 #endif
 
-	/* Raise an exception if a NS device tries to access secure memory */
-	tzc400_set_action(TZC_ACTION_ERR);
-
-	tzc400_enable_filters();
+	/*
+	 * Raise an interrupt (secure FIQ) if a NS device tries to access
+	 * secure memory
+	 */
+	init_tzc400_end(TZC_ACTION_INT);
 }
 
 /*******************************************************************************
@@ -91,23 +109,11 @@
 	stm32mp_clk_enable(TZC1);
 	stm32mp_clk_enable(TZC2);
 
-	tzc400_init(STM32MP1_TZC_BASE);
-
-	tzc400_disable_filters();
-
-	/* Region 1 set to cover Non-Secure DRAM at 0xC000_0000 */
-	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, 1,
-				STM32MP_DDR_BASE,
-				STM32MP_DDR_BASE +
-				(STM32MP_DDR_MAX_SIZE - 1U),
-				TZC_REGION_S_NONE,
-				TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_A7_ID) |
-				TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_SDMMC_ID));
+	/* Region 0 set to cover all DRAM secure at 0xC000_0000 */
+	init_tzc400_begin(TZC_REGION_S_RDWR);
 
 	/* Raise an exception if a NS device tries to access secure memory */
-	tzc400_set_action(TZC_ACTION_ERR);
-
-	tzc400_enable_filters();
+	init_tzc400_end(TZC_ACTION_ERR);
 }
 
 /*******************************************************************************
diff --git a/plat/st/stm32mp1/stm32mp1_shared_resources.c b/plat/st/stm32mp1/stm32mp1_shared_resources.c
index 208e34a..6b1bcaa 100644
--- a/plat/st/stm32mp1/stm32mp1_shared_resources.c
+++ b/plat/st/stm32mp1/stm32mp1_shared_resources.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -114,7 +114,7 @@
 	if (bank != GPIO_BANK_Z) {
 		int count = fdt_get_gpio_bank_pin_count(bank);
 
-		assert((count >= 0) || (count <= (GPIO_PIN_MAX + 1)));
+		assert((count >= 0) && ((unsigned int)count <= (GPIO_PIN_MAX + 1)));
 
 		return (unsigned int)count;
 	}
@@ -163,7 +163,7 @@
 
 	if ((id >= STM32MP1_SHRES_GPIOZ(0)) &&
 	    (id <= STM32MP1_SHRES_GPIOZ(7)) &&
-	    ((id - STM32MP1_SHRES_GPIOZ(0)) >= get_gpioz_nbpin())) {
+	    ((unsigned int)(id - STM32MP1_SHRES_GPIOZ(0)) >= get_gpioz_nbpin())) {
 		ERROR("Invalid GPIO pin %u, %u pin(s) available\n",
 		      id - STM32MP1_SHRES_GPIOZ(0), get_gpioz_nbpin());
 		panic();
diff --git a/plat/st/stm32mp1/stm32mp1_stm32image_def.h b/plat/st/stm32mp1/stm32mp1_stm32image_def.h
new file mode 100644
index 0000000..8efa342
--- /dev/null
+++ b/plat/st/stm32mp1/stm32mp1_stm32image_def.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (C) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef STM32MP1_STM32IMAGE_DEF_H
+#define STM32MP1_STM32IMAGE_DEF_H
+
+#ifdef AARCH32_SP_OPTEE
+#define STM32MP_DDR_S_SIZE		U(0x01E00000)	/* 30 MB */
+#define STM32MP_DDR_SHMEM_SIZE		U(0x00200000)	/* 2 MB */
+#else
+#define STM32MP_DDR_S_SIZE		U(0)
+#define STM32MP_DDR_SHMEM_SIZE		U(0)
+#endif
+
+#define STM32MP_BL2_SIZE		U(0x0001C000)	/* 112 KB for BL2 */
+#define STM32MP_DTB_SIZE		U(0x00006000)	/* 24 KB for DTB */
+
+#ifdef AARCH32_SP_OPTEE
+#define STM32MP_BL32_BASE		STM32MP_SEC_SYSRAM_BASE
+
+#define STM32MP_BL2_BASE		(STM32MP_SEC_SYSRAM_BASE + \
+					 STM32MP_SEC_SYSRAM_SIZE - \
+					 STM32MP_BL2_SIZE)
+
+/* OP-TEE loads from SYSRAM base to BL2 DTB start address */
+#define STM32MP_OPTEE_BASE		STM32MP_BL32_BASE
+#define STM32MP_OPTEE_SIZE		(STM32MP_SEC_SYSRAM_SIZE -  \
+					 STM32MP_BL2_SIZE - STM32MP_DTB_SIZE)
+#define STM32MP_BL32_SIZE		STM32MP_OPTEE_SIZE
+#else /* AARCH32_SP_OPTEE */
+#define STM32MP_BL32_SIZE		U(0x00019000)	/* 96 KB for BL32 */
+
+#define STM32MP_BL32_BASE		(STM32MP_SEC_SYSRAM_BASE + \
+					 STM32MP_SEC_SYSRAM_SIZE - \
+					 STM32MP_BL32_SIZE)
+
+#define STM32MP_BL2_BASE		(STM32MP_BL32_BASE - \
+					 STM32MP_BL2_SIZE)
+#endif /* AARCH32_SP_OPTEE */
+
+/* DTB initialization value */
+#define STM32MP_DTB_BASE		(STM32MP_BL2_BASE -	\
+					 STM32MP_DTB_SIZE)
+
+/*
+ * MAX_MMAP_REGIONS is usually:
+ * BL stm32mp1_mmap size + mmap regions in *_plat_arch_setup
+ */
+#if defined(IMAGE_BL32)
+#define MAX_MMAP_REGIONS		6
+#endif
+
+/*******************************************************************************
+ * STM32MP1 RAW partition offset for MTD devices
+ ******************************************************************************/
+#define STM32MP_NOR_BL33_OFFSET		U(0x00080000)
+#ifdef AARCH32_SP_OPTEE
+#define STM32MP_NOR_TEEH_OFFSET		U(0x00280000)
+#define STM32MP_NOR_TEED_OFFSET		U(0x002C0000)
+#define STM32MP_NOR_TEEX_OFFSET		U(0x00300000)
+#endif
+
+#define STM32MP_NAND_BL33_OFFSET	U(0x00200000)
+#ifdef AARCH32_SP_OPTEE
+#define STM32MP_NAND_TEEH_OFFSET	U(0x00600000)
+#define STM32MP_NAND_TEED_OFFSET	U(0x00680000)
+#define STM32MP_NAND_TEEX_OFFSET	U(0x00700000)
+#endif
+
+#endif /* STM32MP1_STM32IMAGE_DEF_H */
diff --git a/plat/st/stm32mp1/stm32mp1_syscfg.c b/plat/st/stm32mp1/stm32mp1_syscfg.c
index 109725c..793ad71 100644
--- a/plat/st/stm32mp1/stm32mp1_syscfg.c
+++ b/plat/st/stm32mp1/stm32mp1_syscfg.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2019-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -22,6 +22,7 @@
 #define SYSCFG_ICNR				0x1CU
 #define SYSCFG_CMPCR				0x20U
 #define SYSCFG_CMPENSETR			0x24U
+#define SYSCFG_CMPENCLRR			0x28U
 
 /*
  * SYSCFG_BOOTR Register
@@ -167,8 +168,7 @@
 
 	mmio_write_32(SYSCFG_BASE + SYSCFG_CMPCR, value | SYSCFG_CMPCR_SW_CTRL);
 
-	mmio_clrbits_32(SYSCFG_BASE + SYSCFG_CMPENSETR,
-			SYSCFG_CMPENSETR_MPU_EN);
+	mmio_setbits_32(SYSCFG_BASE + SYSCFG_CMPENCLRR, SYSCFG_CMPENSETR_MPU_EN);
 
 	stm32mp1_clk_disable_non_secure(SYSCFG);
 }
diff --git a/plat/st/stm32mp1/stm32mp1_usb_dfu.c b/plat/st/stm32mp1/stm32mp1_usb_dfu.c
new file mode 100644
index 0000000..70fbba6
--- /dev/null
+++ b/plat/st/stm32mp1/stm32mp1_usb_dfu.c
@@ -0,0 +1,390 @@
+/*
+ * Copyright (c) 2021, STMicroelectronics - All Rights Reserved
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <limits.h>
+#include <string.h>
+
+#include <common/debug.h>
+#include <drivers/st/bsec.h>
+#include <drivers/st/stm32mp1_usb.h>
+#include <drivers/usb_device.h>
+
+#include <platform_def.h>
+#include <stm32cubeprogrammer.h>
+#include <stm32mp_common.h>
+#include <usb_dfu.h>
+
+/*  String size (1 byte) + type (1 byte) + 24 UTF16 characters: 2 bytes each */
+#define SIZ_STRING_SERIAL		U(24)
+#define USB_SIZ_STRING_SERIAL		(1U + 1U + (SIZ_STRING_SERIAL * 2U))
+#define USBD_MAX_STR_DESC_SIZ		0x100
+#define USBD_VID			0x0483
+#define USBD_PID			0xDF11
+#define USBD_LANGID_STRING		0x409
+#define USBD_MANUFACTURER_STRING	"STMicroelectronics"
+#define USBD_CONFIGURATION_STRING	"DFU Config"
+#define USBD_INTERFACE_STRING		"DFU Interface"
+
+#define USB_DFU_ITF_NUM			6
+
+#define USB_DFU_CONFIG_DESC_SIZ		USB_DFU_DESC_SIZ(USB_DFU_ITF_NUM)
+
+/* DFU devices */
+static struct usb_dfu_handle usb_dfu_handle;
+
+/* USB Standard Device Descriptor */
+static const uint8_t usb_stm32mp1_desc[USB_LEN_DEV_DESC] = {
+	USB_LEN_DEV_DESC,           /* bLength */
+	USB_DESC_TYPE_DEVICE,       /* bDescriptorType */
+	0x00,                       /* bcdUSB */
+	0x02,                       /* version */
+	0x00,                       /* bDeviceClass */
+	0x00,                       /* bDeviceSubClass */
+	0x00,                       /* bDeviceProtocol */
+	USB_MAX_EP0_SIZE,           /* bMaxPacketSize */
+	LOBYTE(USBD_VID),           /* idVendor */
+	HIBYTE(USBD_VID),           /* idVendor */
+	LOBYTE(USBD_PID),           /* idVendor */
+	HIBYTE(USBD_PID),           /* idVendor */
+	0x00,                       /* bcdDevice rel. 2.00 */
+	0x02,
+	USBD_IDX_MFC_STR,           /* Index of manufacturer string */
+	USBD_IDX_PRODUCT_STR,       /* Index of product string */
+	USBD_IDX_SERIAL_STR,        /* Index of serial number string */
+	USBD_MAX_NUM_CONFIGURATION  /* bNumConfigurations */
+}; /* USB_DeviceDescriptor */
+
+/* USB Standard String Descriptor */
+static const uint8_t usb_stm32mp1_lang_id_desc[USB_LEN_LANGID_STR_DESC] = {
+	USB_LEN_LANGID_STR_DESC,
+	USB_DESC_TYPE_STRING,
+	LOBYTE(USBD_LANGID_STRING),
+	HIBYTE(USBD_LANGID_STRING),
+};
+
+/* USB Standard Device Descriptor */
+static const uint8_t
+usbd_stm32mp1_qualifier_desc[USB_LEN_DEV_QUALIFIER_DESC] = {
+	USB_LEN_DEV_QUALIFIER_DESC,
+	USB_DESC_TYPE_DEVICE_QUALIFIER,
+	0x00,
+	0x02,
+	0x00,
+	0x00,
+	0x00,
+	0x40,
+	0x01,
+	0x00,
+};
+
+/* USB serial number: build dynamically */
+static uint8_t usb_stm32mp1_serial[USB_SIZ_STRING_SERIAL + 1];
+
+/* USB DFU device Configuration Descriptor */
+static const uint8_t usb_stm32mp1_config_desc[USB_DFU_CONFIG_DESC_SIZ] = {
+	0x09, /* bLength: Configuration Descriptor size */
+	USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
+	USB_DFU_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
+	0x00,
+	0x01, /* bNumInterfaces: 1 interface */
+	0x01, /* bConfigurationValue: Configuration value */
+	0x02, /* iConfiguration: Index of string descriptor for configuration */
+	0xC0, /* bmAttributes: bus powered and Supprts Remote Wakeup */
+	0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */
+
+	/* Descriptor of DFU interface 0 Alternate setting 0..N */
+	USBD_DFU_IF_DESC(0),
+	USBD_DFU_IF_DESC(1),
+	USBD_DFU_IF_DESC(2),
+	USBD_DFU_IF_DESC(3),
+	USBD_DFU_IF_DESC(4),
+	USBD_DFU_IF_DESC(5),
+
+	/* DFU Functional Descriptor */
+	0x09, /* blength = 9 Bytes */
+	DFU_DESCRIPTOR_TYPE, /* DFU Functional Descriptor */
+	DFU_BM_ATTRIBUTE, /* bmAttribute for DFU */
+	0xFF, /* DetachTimeOut = 255 ms */
+	0x00,
+	TRANSFER_SIZE_BYTES(USBD_DFU_XFER_SIZE), /* TransferSize = 1024 Byte */
+	((USB_DFU_VERSION >> 0) & 0xFF), /* bcdDFUVersion */
+	((USB_DFU_VERSION >> 8) & 0xFF)
+};
+
+/* The user strings: one by alternate as defined in USBD_DFU_IF_DESC */
+const char *const if_desc_string[USB_DFU_ITF_NUM] = {
+	"@Partition0 /0x00/1*256Ke",
+	"@FSBL /0x01/1*1Me",
+	"@Partition2 /0x02/1*1Me",
+	"@Partition3 /0x03/1*16Me",
+	"@Partition4 /0x04/1*16Me",
+	"@virtual /0xF1/1*512Ba"
+};
+
+/* Buffer to build the unicode string provided to USB device stack */
+static uint8_t usb_str_dec[USBD_MAX_STR_DESC_SIZ];
+
+/*
+ * Convert Ascii string into unicode one
+ * desc : descriptor buffer
+ * unicode : Formatted string buffer (unicode)
+ * len : descriptor length
+ */
+static void stm32mp1_get_string(const char *desc, uint8_t *unicode, uint16_t *len)
+{
+	uint8_t idx = 0U;
+
+	if (desc == NULL) {
+		return;
+	}
+
+	*len =  strlen(desc) * 2U + 2U;
+	unicode[idx++] = *len;
+	unicode[idx++] =  USB_DESC_TYPE_STRING;
+
+	while (*desc != '\0') {
+		unicode[idx++] = *desc++;
+		unicode[idx++] =  0x00U;
+	}
+}
+
+/*
+ * Create the serial number string descriptor
+ */
+static void update_serial_num_string(void)
+{
+	uint8_t i;
+	uint32_t result;
+	char serial_string[SIZ_STRING_SERIAL + 2U];
+	uint32_t deviceserial[UID_WORD_NB];
+	uint16_t length;
+
+	for (i = 0U; i < UID_WORD_NB; i++) {
+		result = bsec_shadow_register(i + UID0_OTP);
+		if (result != BSEC_OK) {
+			ERROR("BSEC: UID%d Shadowing Error\n", i);
+			break;
+		}
+		result = bsec_read_otp(&deviceserial[i], i + UID0_OTP);
+		if (result != BSEC_OK) {
+			ERROR("BSEC: UID%d Read Error\n", i);
+			break;
+		}
+	}
+	/* On bsec error: serial number is set to 0 */
+	if (result != BSEC_OK) {
+		for (i = 0; i < UID_WORD_NB; i++) {
+			deviceserial[i] = 0U;
+		}
+	}
+	/* build serial number with OTP value as in ROM code */
+	snprintf(serial_string, sizeof(serial_string), "%08X%08X%08X",
+		 deviceserial[0], deviceserial[1], deviceserial[2]);
+
+	length = USB_SIZ_STRING_SERIAL;
+	stm32mp1_get_string(serial_string, usb_stm32mp1_serial, &length);
+}
+
+/*
+ * Return Device Qualifier descriptor
+ * length : pointer data length
+ * return : pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_get_qualifier_desc(uint16_t *length)
+{
+	*length = sizeof(usbd_stm32mp1_qualifier_desc);
+
+	return (uint8_t *)usbd_stm32mp1_qualifier_desc;
+}
+
+/*
+ * Return configuration descriptor
+ * length : pointer data length
+ * return : pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_get_config_desc(uint16_t *length)
+{
+	*length = sizeof(usb_stm32mp1_config_desc);
+
+	return (uint8_t *)usb_stm32mp1_config_desc;
+}
+
+/*
+ * Returns the device descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_device_desc(uint16_t *length)
+{
+	*length = sizeof(usb_stm32mp1_desc);
+
+	return (uint8_t *)usb_stm32mp1_desc;
+}
+
+/*
+ * Returns the LangID string descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_lang_id_desc(uint16_t *length)
+{
+	*length = sizeof(usb_stm32mp1_lang_id_desc);
+
+	return (uint8_t *)usb_stm32mp1_lang_id_desc;
+}
+
+/*
+ *  Returns the product string descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_product_desc(uint16_t *length)
+{
+	char name[STM32_SOC_NAME_SIZE];
+	char product[128];
+	uint32_t chip_id;
+	uint32_t chip_version;
+
+	stm32mp_get_soc_name(name);
+	chip_id = stm32mp_get_chip_dev_id();
+	chip_version = stm32mp_get_chip_version();
+
+	snprintf(product, sizeof(product),
+		 "DFU @Device ID /0x%03X, @Revision ID /0x%04X, @Name /%s,",
+		 chip_id, chip_version, name);
+
+	stm32mp1_get_string(product, usb_str_dec, length);
+
+	return usb_str_dec;
+}
+
+/*
+ * Returns the manufacturer string descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_manufacturer_desc(uint16_t *length)
+{
+	stm32mp1_get_string(USBD_MANUFACTURER_STRING, usb_str_dec, length);
+
+	return usb_str_dec;
+}
+
+/*
+ * Returns the serial number string descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_serial_desc(uint16_t *length)
+{
+	*length = USB_SIZ_STRING_SERIAL;
+
+	return (uint8_t *)usb_stm32mp1_serial;
+}
+
+/*
+ * Returns the configuration string descriptor.
+ * length: Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_config_desc(uint16_t *length)
+{
+	stm32mp1_get_string(USBD_CONFIGURATION_STRING, usb_str_dec, length);
+
+	return usb_str_dec;
+}
+
+/*
+ * Returns the interface string descriptor.
+ * length : Pointer to data length variable
+ * return : Pointer to descriptor buffer
+ */
+static uint8_t *stm32mp1_interface_desc(uint16_t *length)
+{
+	stm32mp1_get_string(USBD_INTERFACE_STRING, usb_str_dec, length);
+
+	return usb_str_dec;
+}
+
+/*
+ * Manages the transfer of memory interfaces string descriptors.
+ * index: descriptor index
+ * length : pointer data length
+ * return : pointer to the descriptor table or NULL if the descriptor
+ *          is not supported.
+ */
+static uint8_t *stm32mp1_get_usr_desc(uint8_t index, uint16_t *length)
+{
+	if (index >= ARRAY_SIZE(if_desc_string)) {
+		return NULL;
+	}
+
+	stm32mp1_get_string(if_desc_string[index], usb_str_dec, length);
+
+	return usb_str_dec;
+}
+
+static const struct usb_desc dfu_desc = {
+	.get_device_desc = stm32mp1_device_desc,
+	.get_lang_id_desc = stm32mp1_lang_id_desc,
+	.get_manufacturer_desc = stm32mp1_manufacturer_desc,
+	.get_product_desc = stm32mp1_product_desc,
+	.get_configuration_desc = stm32mp1_config_desc,
+	.get_serial_desc = stm32mp1_serial_desc,
+	.get_interface_desc = stm32mp1_interface_desc,
+	.get_usr_desc = stm32mp1_get_usr_desc,
+	.get_config_desc = stm32mp1_get_config_desc,
+	.get_device_qualifier_desc = stm32mp1_get_qualifier_desc,
+	/* only HS is supported, as ROM code */
+	.get_other_speed_config_desc = NULL,
+};
+
+static struct usb_handle usb_core_handle;
+static struct pcd_handle pcd_handle;
+
+struct usb_handle *usb_dfu_plat_init(void)
+{
+	/* Prepare USB Driver */
+	pcd_handle.in_ep[0].maxpacket = USB_MAX_EP0_SIZE;
+	pcd_handle.out_ep[0].maxpacket = USB_MAX_EP0_SIZE;
+	stm32mp1_usb_init_driver(&usb_core_handle, &pcd_handle,
+				 (uint32_t *)USB_OTG_BASE);
+
+	/* STM32MP15 = keep the configuration from ROM code */
+	usb_core_handle.ep0_state = USBD_EP0_DATA_IN;
+	usb_core_handle.dev_state = USBD_STATE_CONFIGURED;
+
+	/* Update the serial number string descriptor from the unique ID */
+	update_serial_num_string();
+
+	/* Prepare USB DFU stack */
+	usb_dfu_register(&usb_core_handle, &usb_dfu_handle);
+
+	/* Register DFU descriptor in USB stack */
+	register_platform(&usb_core_handle, &dfu_desc);
+
+	return &usb_core_handle;
+}
+
+/* Link between USB alternate and STM32CubeProgramer phase */
+uint8_t usb_dfu_get_phase(uint8_t alt)
+{
+	uint8_t ret;
+
+	switch (alt) {
+	case 3:
+		ret = PHASE_SSBL;
+		break;
+	case 5:
+		ret = PHASE_CMD;
+		break;
+	default:
+		ret = PHASE_RESET;
+		break;
+	}
+
+	return ret;
+}
diff --git a/plat/ti/k3/board/generic/board.mk b/plat/ti/k3/board/generic/board.mk
index a342214..ef74cd6 100644
--- a/plat/ti/k3/board/generic/board.mk
+++ b/plat/ti/k3/board/generic/board.mk
@@ -13,5 +13,12 @@
 K3_HW_CONFIG_BASE ?= 0x82000000
 $(eval $(call add_define,K3_HW_CONFIG_BASE))
 
+# Define sec_proxy usage as the full prioritized communication scheme
+K3_SEC_PROXY_LITE	:=	0
+$(eval $(call add_define,K3_SEC_PROXY_LITE))
+
+# System coherency is managed in hardware
+USE_COHERENT_MEM	:=	1
+
 PLAT_INCLUDES		+=	\
 				-Iplat/ti/k3/board/generic/include	\
diff --git a/plat/ti/k3/board/generic/include/board_def.h b/plat/ti/k3/board/generic/include/board_def.h
index 0d45116..4ff687c 100644
--- a/plat/ti/k3/board/generic/include/board_def.h
+++ b/plat/ti/k3/board/generic/include/board_def.h
@@ -18,15 +18,26 @@
 /*
  * This RAM will be used for the bootloader including code, bss, and stacks.
  * It may need to be increased if BL31 grows in size.
+ *
+ * The link addresses are determined by SEC_SRAM_BASE + offset.
+ * When ENABLE_PIE is set, the TF images can be loaded anywhere, so
+ * SEC_SRAM_BASE is really arbitrary.
+ *
+ * When ENABLE_PIE is unset, SEC_SRAM_BASE should be chosen so that
+ * it matches to the physical address where BL31 is loaded, that is,
+ * SEC_SRAM_BASE should be the base address of the RAM region.
+ *
+ * Lets make things explicit by mapping SRAM_BASE to 0x0 since ENABLE_PIE is
+ * defined as default for our platform.
  */
-#define SEC_SRAM_BASE			0x70000000 /* Base of MSMC SRAM */
-#define SEC_SRAM_SIZE			0x00020000 /* 128k */
+#define SEC_SRAM_BASE			UL(0x00000000) /* PIE remapped on fly */
+#define SEC_SRAM_SIZE			UL(0x00020000) /* 128k */
 
 #define PLAT_MAX_OFF_STATE		U(2)
 #define PLAT_MAX_RET_STATE		U(1)
 
-#define PLAT_PROC_START_ID		32
-#define PLAT_PROC_DEVICE_START_ID	202
-#define PLAT_CLUSTER_DEVICE_START_ID	198
+#define PLAT_PROC_START_ID		U(32)
+#define PLAT_PROC_DEVICE_START_ID	U(202)
+#define PLAT_CLUSTER_DEVICE_START_ID	U(198)
 
 #endif /* BOARD_DEF_H */
diff --git a/plat/ti/k3/board/lite/board.mk b/plat/ti/k3/board/lite/board.mk
new file mode 100644
index 0000000..76246be
--- /dev/null
+++ b/plat/ti/k3/board/lite/board.mk
@@ -0,0 +1,24 @@
+#
+# Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+BL32_BASE ?= 0x9e800000
+$(eval $(call add_define,BL32_BASE))
+
+PRELOADED_BL33_BASE ?= 0x80080000
+$(eval $(call add_define,PRELOADED_BL33_BASE))
+
+K3_HW_CONFIG_BASE ?= 0x82000000
+$(eval $(call add_define,K3_HW_CONFIG_BASE))
+
+# Define sec_proxy usage as the lite version
+K3_SEC_PROXY_LITE	:=	1
+$(eval $(call add_define,K3_SEC_PROXY_LITE))
+
+# We dont have system level coherency capability
+USE_COHERENT_MEM	:=	0
+
+PLAT_INCLUDES	+=			\
+	-Iplat/ti/k3/board/lite/include	\
diff --git a/plat/ti/k3/board/lite/include/board_def.h b/plat/ti/k3/board/lite/include/board_def.h
new file mode 100644
index 0000000..18b7f42
--- /dev/null
+++ b/plat/ti/k3/board/lite/include/board_def.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef BOARD_DEF_H
+#define BOARD_DEF_H
+
+#include <lib/utils_def.h>
+
+/* The ports must be in order and contiguous */
+#define K3_CLUSTER0_CORE_COUNT		U(4)
+#define K3_CLUSTER1_CORE_COUNT		U(0)
+#define K3_CLUSTER2_CORE_COUNT		U(0)
+#define K3_CLUSTER3_CORE_COUNT		U(0)
+
+/*
+ * This RAM will be used for the bootloader including code, bss, and stacks.
+ * It may need to be increased if BL31 grows in size.
+ * Current computation assumes data structures necessary for GIC and ARM for
+ * a single cluster of 4 processor.
+ *
+ * The link addresses are determined by SEC_SRAM_BASE + offset.
+ * When ENABLE_PIE is set, the TF images can be loaded anywhere, so
+ * SEC_SRAM_BASE is really arbitrary.
+ *
+ * When ENABLE_PIE is unset, SEC_SRAM_BASE should be chosen so that
+ * it matches to the physical address where BL31 is loaded, that is,
+ * SEC_SRAM_BASE should be the base address of the RAM region.
+ *
+ * Lets make things explicit by mapping SRAM_BASE to 0x0 since ENABLE_PIE is
+ * defined as default for our platform.
+ */
+#define SEC_SRAM_BASE			UL(0x00000000) /* PIE remapped on fly */
+#define SEC_SRAM_SIZE			UL(0x0001c000) /* 112k */
+
+#define PLAT_MAX_OFF_STATE		U(2)
+#define PLAT_MAX_RET_STATE		U(1)
+
+#define PLAT_PROC_START_ID		U(32)
+#define PLAT_PROC_DEVICE_START_ID	U(135)
+#define PLAT_CLUSTER_DEVICE_START_ID	U(134)
+
+#endif /* BOARD_DEF_H */
diff --git a/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.c b/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.c
index ee1eecf..a0bfdee 100644
--- a/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.c
+++ b/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.c
@@ -97,11 +97,16 @@
 		.data_end_offset = 0x3C,
 	},
 	.threads = {
+#if !K3_SEC_PROXY_LITE
 		SP_THREAD(SP_NOTIFY),
 		SP_THREAD(SP_RESPONSE),
 		SP_THREAD(SP_HIGH_PRIORITY),
 		SP_THREAD(SP_LOW_PRIORITY),
 		SP_THREAD(SP_NOTIFY_RESP),
+#else
+		SP_THREAD(SP_RESPONSE),
+		SP_THREAD(SP_HIGH_PRIORITY),
+#endif /* K3_SEC_PROXY_LITE */
 	},
 };
 
@@ -261,9 +266,14 @@
 	/*
 	 * 'data_reg' indicates next register to write. If we did not already
 	 * write on tx complete reg(last reg), we must do so for transmit
+	 * In addition, we also need to make sure all intermediate data
+	 * registers(if any required), are reset to 0 for TISCI backward
+	 * compatibility to be maintained.
 	 */
-	if (data_reg <= spm.desc.data_end_offset)
-		mmio_write_32(spt->data + spm.desc.data_end_offset, 0);
+	while (data_reg <= spm.desc.data_end_offset) {
+		mmio_write_32(spt->data + data_reg, 0);
+		data_reg += sizeof(uint32_t);
+	}
 
 	VERBOSE("Message successfully sent on thread %s\n", spt->name);
 
diff --git a/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.h b/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.h
index 6c4f5df..f4b0b4b 100644
--- a/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.h
+++ b/plat/ti/k3/common/drivers/sec_proxy/sec_proxy.h
@@ -16,13 +16,28 @@
  * enum k3_sec_proxy_chan_id - Secure Proxy thread IDs
  *
  * These the available IDs used in k3_sec_proxy_{send,recv}()
+ * There are two schemes we use:
+ * * if K3_SEC_PROXY_LITE = 1, we just have two threads to talk
+ * * if K3_SEC_PROXY_LITE = 0, we have the full fledged
+ *   communication scheme available.
  */
 enum k3_sec_proxy_chan_id {
+#if !K3_SEC_PROXY_LITE
 	SP_NOTIFY = 0,
 	SP_RESPONSE,
 	SP_HIGH_PRIORITY,
 	SP_LOW_PRIORITY,
 	SP_NOTIFY_RESP,
+#else
+	SP_RESPONSE = 8,
+	/*
+	 * Note: TISCI documentation indicates "low priority", but in reality
+	 * with a single thread, there is no low or high priority.. This usage
+	 * is more appropriate for TF-A since we can reduce the churn as a
+	 * result.
+	 */
+	SP_HIGH_PRIORITY,
+#endif /* K3_SEC_PROXY_LITE */
 };
 
 /**
diff --git a/plat/ti/k3/common/drivers/ti_sci/ti_sci.c b/plat/ti/k3/common/drivers/ti_sci/ti_sci.c
index e390efe..2c3313c 100644
--- a/plat/ti/k3/common/drivers/ti_sci/ti_sci.c
+++ b/plat/ti/k3/common/drivers/ti_sci/ti_sci.c
@@ -1163,6 +1163,7 @@
 		ERROR("Message alloc failed (%d)\n", ret);
 		return ret;
 	}
+	req.domain = TI_SCI_DOMAIN_FULL_SOC_RESET;
 
 	ret = ti_sci_do_xfer(&xfer);
 	if (ret) {
diff --git a/plat/ti/k3/common/drivers/ti_sci/ti_sci_protocol.h b/plat/ti/k3/common/drivers/ti_sci/ti_sci_protocol.h
index 2d23f9a..310bf45 100644
--- a/plat/ti/k3/common/drivers/ti_sci/ti_sci_protocol.h
+++ b/plat/ti/k3/common/drivers/ti_sci/ti_sci_protocol.h
@@ -95,12 +95,15 @@
 /**
  * struct ti_sci_msg_req_reboot - Reboot the SoC
  * @hdr:	Generic Header
+ * @domain:	Domain to be reset, 0 for full SoC reboot
  *
  * Request type is TI_SCI_MSG_SYS_RESET, responded with a generic
  * ACK/NACK message.
  */
 struct ti_sci_msg_req_reboot {
 	struct ti_sci_msg_hdr hdr;
+#define TI_SCI_DOMAIN_FULL_SOC_RESET	0x0
+	uint8_t domain;
 } __packed;
 
 /**
diff --git a/plat/ti/k3/common/k3_bl31_setup.c b/plat/ti/k3/common/k3_bl31_setup.c
index 8bd7362..457c95d 100644
--- a/plat/ti/k3/common/k3_bl31_setup.c
+++ b/plat/ti/k3/common/k3_bl31_setup.c
@@ -13,6 +13,7 @@
 #include <arch_helpers.h>
 #include <common/bl_common.h>
 #include <common/debug.h>
+#include <lib/mmio.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
 
 #include <k3_console.h>
@@ -23,6 +24,7 @@
 const mmap_region_t plat_k3_mmap[] = {
 	MAP_REGION_FLAT(K3_USART_BASE,       K3_USART_SIZE,       MT_DEVICE | MT_RW | MT_SECURE),
 	MAP_REGION_FLAT(K3_GIC_BASE,         K3_GIC_SIZE,         MT_DEVICE | MT_RW | MT_SECURE),
+	MAP_REGION_FLAT(K3_GTC_BASE,         K3_GTC_SIZE,         MT_DEVICE | MT_RW | MT_SECURE),
 	MAP_REGION_FLAT(SEC_PROXY_RT_BASE,   SEC_PROXY_RT_SIZE,   MT_DEVICE | MT_RW | MT_SECURE),
 	MAP_REGION_FLAT(SEC_PROXY_SCFG_BASE, SEC_PROXY_SCFG_SIZE, MT_DEVICE | MT_RW | MT_SECURE),
 	MAP_REGION_FLAT(SEC_PROXY_DATA_BASE, SEC_PROXY_DATA_SIZE, MT_DEVICE | MT_RW | MT_SECURE),
@@ -99,7 +101,7 @@
 void bl31_plat_arch_setup(void)
 {
 	const mmap_region_t bl_regions[] = {
-		MAP_REGION_FLAT(BL31_START,           BL31_END            - BL31_START,           MT_MEMORY  | MT_RW | MT_SECURE),
+		MAP_REGION_FLAT(BL31_START,           BL31_SIZE,			          MT_MEMORY  | MT_RW | MT_SECURE),
 		MAP_REGION_FLAT(BL_CODE_BASE,         BL_CODE_END         - BL_CODE_BASE,         MT_CODE    | MT_RO | MT_SECURE),
 		MAP_REGION_FLAT(BL_RO_DATA_BASE,      BL_RO_DATA_END      - BL_RO_DATA_BASE,      MT_RO_DATA | MT_RO | MT_SECURE),
 #if USE_COHERENT_MEM
@@ -127,6 +129,38 @@
 
 unsigned int plat_get_syscnt_freq2(void)
 {
+	uint32_t gtc_freq;
+	uint32_t gtc_ctrl;
+
+	/* Lets try and provide basic diagnostics - cost is low */
+	gtc_ctrl = mmio_read_32(K3_GTC_BASE + K3_GTC_CNTCR_OFFSET);
+	/* Did the bootloader fail to enable timer and OS guys are confused? */
+	if ((gtc_ctrl & K3_GTC_CNTCR_EN_MASK) == 0U) {
+		ERROR("GTC is disabled! Timekeeping broken. Fix Bootloader\n");
+	}
+	/*
+	 * If debug will not pause time, we will have issues like
+	 * drivers timing out while debugging, in cases of OS like Linux,
+	 * RCU stall errors, which can be hard to differentiate vs real issues.
+	 */
+	if ((gtc_ctrl & K3_GTC_CNTCR_HDBG_MASK) == 0U) {
+		WARN("GTC: Debug access doesn't stop time. Fix Bootloader\n");
+	}
+
+	gtc_freq = mmio_read_32(K3_GTC_BASE + K3_GTC_CNTFID0_OFFSET);
+	/* Many older bootloaders may have missed programming FID0 register */
+	if (gtc_freq != 0U) {
+		return gtc_freq;
+	}
+
+	/*
+	 * We could have just warned about this, but this can have serious
+	 * hard to debug side effects if we are NOT sure what the actual
+	 * frequency is. Lets make sure people don't miss this.
+	 */
+	ERROR("GTC_CNTFID0 is 0! Assuming %d Hz. Fix Bootloader\n",
+	      SYS_COUNTER_FREQ_IN_TICKS);
+
 	return SYS_COUNTER_FREQ_IN_TICKS;
 }
 
diff --git a/plat/ti/k3/common/plat_common.mk b/plat/ti/k3/common/plat_common.mk
index c00262b..ab7366b 100644
--- a/plat/ti/k3/common/plat_common.mk
+++ b/plat/ti/k3/common/plat_common.mk
@@ -11,9 +11,8 @@
 # We can choose where a core starts executing
 PROGRAMMABLE_RESET_ADDRESS:=	1
 
-# System coherency is managed in hardware
+# ARM coherency is managed in hardware
 WARMBOOT_ENABLE_DCACHE_EARLY :=	1
-USE_COHERENT_MEM	:=	1
 
 # A53 erratum for SoC. (enable them all)
 ERRATA_A53_826319	:=	1
@@ -21,9 +20,11 @@
 ERRATA_A53_836870	:=	1
 ERRATA_A53_843419	:=	1
 ERRATA_A53_855873	:=	1
+ERRATA_A53_1530924	:=	1
 
 # A72 Erratum for SoC
 ERRATA_A72_859971	:=	1
+ERRATA_A72_1319367	:=	1
 
 CRASH_REPORTING		:= 1
 HANDLE_EA_EL3_FIRST	:= 1
diff --git a/plat/ti/k3/include/platform_def.h b/plat/ti/k3/include/platform_def.h
index 98db626..81a383a 100644
--- a/plat/ti/k3/include/platform_def.h
+++ b/plat/ti/k3/include/platform_def.h
@@ -60,7 +60,11 @@
  * used, choose the smallest value needed to map the required virtual addresses
  * for each BL stage.
  */
-#define MAX_XLAT_TABLES		8
+#if USE_COHERENT_MEM
+#define MAX_XLAT_TABLES		10
+#else
+#define MAX_XLAT_TABLES		9
+#endif
 
 /*
  * Defines the maximum number of regions that are allocated by the translation
@@ -150,15 +154,33 @@
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_6, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_EDGE)
 
+
+#define K3_GTC_BASE		0x00A90000
+/* We just need 20 byte offset, but simpler to just remap the 64K page in */
+#define K3_GTC_SIZE		0x10000
+#define K3_GTC_CNTCR_OFFSET	0x00
+#define K3_GTC_CNTCR_EN_MASK	0x01
+#define K3_GTC_CNTCR_HDBG_MASK	0x02
+#define K3_GTC_CNTFID0_OFFSET	0x20
+
 #define K3_GIC_BASE	0x01800000
 #define K3_GIC_SIZE	0x200000
 
+#if !K3_SEC_PROXY_LITE
 #define SEC_PROXY_DATA_BASE	0x32C00000
 #define SEC_PROXY_DATA_SIZE	0x80000
 #define SEC_PROXY_SCFG_BASE	0x32800000
 #define SEC_PROXY_SCFG_SIZE	0x80000
 #define SEC_PROXY_RT_BASE	0x32400000
 #define SEC_PROXY_RT_SIZE	0x80000
+#else
+#define SEC_PROXY_DATA_BASE	0x4D000000
+#define SEC_PROXY_DATA_SIZE	0x80000
+#define SEC_PROXY_SCFG_BASE	0x4A400000
+#define SEC_PROXY_SCFG_SIZE	0x80000
+#define SEC_PROXY_RT_BASE	0x4A600000
+#define SEC_PROXY_RT_SIZE	0x80000
+#endif /* K3_SEC_PROXY_LITE */
 
 #define SEC_PROXY_TIMEOUT_US		1000000
 #define SEC_PROXY_MAX_MESSAGE_SIZE	56
diff --git a/plat/xilinx/common/include/pm_common.h b/plat/xilinx/common/include/pm_common.h
index c0a51f0..0c24a36 100644
--- a/plat/xilinx/common/include/pm_common.h
+++ b/plat/xilinx/common/include/pm_common.h
@@ -15,6 +15,18 @@
 #include <stdint.h>
 #include <plat_pm_common.h>
 
+#if IPI_CRC_CHECK
+#define PAYLOAD_ARG_CNT         8U
+#define IPI_W0_TO_W6_SIZE       28U
+#define PAYLOAD_CRC_POS         7U
+#define CRC_INIT_VALUE          0x4F4EU
+#define CRC_ORDER               16U
+#define CRC_POLYNOM             0x8005U
+#else
+#define PAYLOAD_ARG_CNT         6U
+#endif
+#define PAYLOAD_ARG_SIZE	4U	/* size in bytes */
+
 /**
  * pm_ipi - struct for capturing IPI-channel specific info
  * @local_ipi_id	Local IPI agent ID
diff --git a/plat/xilinx/common/include/pm_ipi.h b/plat/xilinx/common/include/pm_ipi.h
index 7bcf596..8c7738d 100644
--- a/plat/xilinx/common/include/pm_ipi.h
+++ b/plat/xilinx/common/include/pm_ipi.h
@@ -26,7 +26,7 @@
 void pm_ipi_irq_enable(const struct pm_proc *proc);
 void pm_ipi_irq_clear(const struct pm_proc *proc);
 uint32_t pm_ipi_irq_status(const struct pm_proc *proc);
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 uint32_t calculate_crc(uint32_t payload[PAYLOAD_ARG_CNT], uint32_t buffersize);
 #endif
 
diff --git a/plat/xilinx/common/plat_startup.c b/plat/xilinx/common/plat_startup.c
index 8c9a049..f02f41e 100644
--- a/plat/xilinx/common/plat_startup.c
+++ b/plat/xilinx/common/plat_startup.c
@@ -5,6 +5,8 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 
 #include <arch_helpers.h>
 #include <common/debug.h>
@@ -170,12 +172,12 @@
 	    (ATFHandoffParams->magic[1] != 'L') ||
 	    (ATFHandoffParams->magic[2] != 'N') ||
 	    (ATFHandoffParams->magic[3] != 'X')) {
-		ERROR("BL31: invalid ATF handoff structure at %llx\n",
+		ERROR("BL31: invalid ATF handoff structure at %" PRIx64 "\n",
 		      atf_handoff_addr);
 		return FSBL_HANDOFF_INVAL_STRUCT;
 	}
 
-	VERBOSE("BL31: ATF handoff params at:0x%llx, entries:%u\n",
+	VERBOSE("BL31: ATF handoff params at:0x%" PRIx64 ", entries:%u\n",
 		atf_handoff_addr, ATFHandoffParams->num_entries);
 	if (ATFHandoffParams->num_entries > FSBL_MAX_PARTITIONS) {
 		ERROR("BL31: ATF handoff params: too many partitions (%u/%u)\n",
@@ -193,7 +195,7 @@
 		int target_estate, target_secure;
 		int target_cpu, target_endianness, target_el;
 
-		VERBOSE("BL31: %zd: entry:0x%llx, flags:0x%llx\n", i,
+		VERBOSE("BL31: %zd: entry:0x%" PRIx64 ", flags:0x%" PRIx64 "\n", i,
 			ATFHandoffParams->partition[i].entry_point,
 			ATFHandoffParams->partition[i].flags);
 
@@ -254,7 +256,7 @@
 			}
 		}
 
-		VERBOSE("Setting up %s entry point to:%llx, el:%x\n",
+		VERBOSE("Setting up %s entry point to:%" PRIx64 ", el:%x\n",
 			target_secure == FSBL_FLAGS_SECURE ? "BL32" : "BL33",
 			ATFHandoffParams->partition[i].entry_point,
 			target_el);
diff --git a/plat/xilinx/common/pm_service/pm_ipi.c b/plat/xilinx/common/pm_service/pm_ipi.c
index c83d25b..7b2c8ec 100644
--- a/plat/xilinx/common/pm_service/pm_ipi.c
+++ b/plat/xilinx/common/pm_service/pm_ipi.c
@@ -18,6 +18,8 @@
 #include "pm_ipi.h"
 
 
+#define ERROR_CODE_MASK		0xFFFFU
+
 DEFINE_BAKERY_LOCK(pm_secure_lock);
 
 /**
@@ -57,7 +59,7 @@
 	uintptr_t buffer_base = proc->ipi->buffer_base +
 					IPI_BUFFER_TARGET_REMOTE_OFFSET +
 					IPI_BUFFER_REQ_OFFSET;
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 	payload[PAYLOAD_CRC_POS] = calculate_crc(payload, IPI_W0_TO_W6_SIZE);
 #endif
 
@@ -135,7 +137,7 @@
 					   unsigned int *value, size_t count)
 {
 	size_t i;
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 	size_t j;
 	unsigned int response_payload[PAYLOAD_ARG_CNT];
 #endif
@@ -154,7 +156,7 @@
 		*value = mmio_read_32(buffer_base + (i * PAYLOAD_ARG_SIZE));
 		value++;
 	}
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 	for (j = 0; j < PAYLOAD_ARG_CNT; j++)
 		response_payload[j] = mmio_read_32(buffer_base +
 						(j * PAYLOAD_ARG_SIZE));
@@ -179,7 +181,7 @@
 void pm_ipi_buff_read_callb(unsigned int *value, size_t count)
 {
 	size_t i;
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 	size_t j;
 	unsigned int response_payload[PAYLOAD_ARG_CNT];
 #endif
@@ -194,7 +196,7 @@
 		*value = mmio_read_32(buffer_base + (i * PAYLOAD_ARG_SIZE));
 		value++;
 	}
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 	for (j = 0; j < PAYLOAD_ARG_CNT; j++)
 		response_payload[j] = mmio_read_32(buffer_base +
 						(j * PAYLOAD_ARG_SIZE));
@@ -230,7 +232,7 @@
 	if (ret != PM_RET_SUCCESS)
 		goto unlock;
 
-	ret = pm_ipi_buff_read(proc, value, count);
+	ret = ERROR_CODE_MASK & (pm_ipi_buff_read(proc, value, count));
 
 unlock:
 	bakery_lock_release(&pm_secure_lock);
@@ -260,7 +262,7 @@
 		return 0;
 }
 
-#if ZYNQMP_IPI_CRC_CHECK
+#if IPI_CRC_CHECK
 uint32_t calculate_crc(uint32_t *payload, uint32_t bufsize)
 {
 	uint32_t crcinit = CRC_INIT_VALUE;
diff --git a/plat/xilinx/versal/bl31_versal_setup.c b/plat/xilinx/versal/bl31_versal_setup.c
index 03b7fbb..8b8714c 100644
--- a/plat/xilinx/versal/bl31_versal_setup.c
+++ b/plat/xilinx/versal/bl31_versal_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,6 +11,7 @@
 #include <bl31/bl31.h>
 #include <common/bl_common.h>
 #include <common/debug.h>
+#include <drivers/arm/dcc.h>
 #include <drivers/arm/pl011.h>
 #include <drivers/console.h>
 #include <lib/mmio.h>
@@ -22,7 +23,6 @@
 
 static entry_point_info_t bl32_image_ep_info;
 static entry_point_info_t bl33_image_ep_info;
-static console_t versal_runtime_console;
 
 /*
  * Return a pointer to the 'entry_point_info' structure of the next image for
@@ -34,8 +34,9 @@
 {
 	assert(sec_state_is_valid(type));
 
-	if (type == NON_SECURE)
+	if (type == NON_SECURE) {
 		return &bl33_image_ep_info;
+	}
 
 	return &bl32_image_ep_info;
 }
@@ -63,17 +64,26 @@
 {
 	uint64_t atf_handoff_addr;
 
-	/* Initialize the console to provide early debug support */
-	int rc = console_pl011_register(VERSAL_UART_BASE,
-					VERSAL_UART_CLOCK,
-					VERSAL_UART_BAUDRATE,
-					&versal_runtime_console);
-	if (rc == 0)
-		panic();
+	if (VERSAL_CONSOLE_IS(pl011)) {
+		static console_t versal_runtime_console;
+		/* Initialize the console to provide early debug support */
+		int rc = console_pl011_register(VERSAL_UART_BASE,
+						VERSAL_UART_CLOCK,
+						VERSAL_UART_BAUDRATE,
+						&versal_runtime_console);
+		if (rc == 0) {
+			panic();
+		}
 
-	console_set_scope(&versal_runtime_console, CONSOLE_FLAG_BOOT |
-			  CONSOLE_FLAG_RUNTIME);
-
+		console_set_scope(&versal_runtime_console, CONSOLE_FLAG_BOOT |
+				  CONSOLE_FLAG_RUNTIME);
+	} else if (VERSAL_CONSOLE_IS(dcc)) {
+		/* Initialize the dcc console for debug */
+		int rc = console_dcc_register();
+		if (rc == 0) {
+			panic();
+		}
+	}
 	/* Initialize the platform config for future decision making */
 	versal_config_setup();
 	/* There are no parameters from BL2 if BL31 is a reset vector */
@@ -97,7 +107,7 @@
 	enum fsbl_handoff ret = fsbl_atf_handover(&bl32_image_ep_info,
 						  &bl33_image_ep_info,
 						  atf_handoff_addr);
-	if (ret == FSBL_HANDOFF_NO_STRUCT) {
+	if (ret == FSBL_HANDOFF_NO_STRUCT || ret == FSBL_HANDOFF_INVAL_STRUCT) {
 		bl31_set_default_config();
 	} else if (ret != FSBL_HANDOFF_SUCCESS) {
 		panic();
@@ -107,6 +117,40 @@
 	NOTICE("BL31: Non secure code at 0x%lx\n", bl33_image_ep_info.pc);
 }
 
+static interrupt_type_handler_t type_el3_interrupt_handler;
+
+int request_intr_type_el3(uint32_t id, interrupt_type_handler_t handler)
+{
+	/* Validate 'handler'*/
+	if (!handler) {
+		return -EINVAL;
+	}
+
+	type_el3_interrupt_handler = handler;
+
+	return 0;
+}
+
+static uint64_t rdo_el3_interrupt_handler(uint32_t id, uint32_t flags,
+					  void *handle, void *cookie)
+{
+	uint32_t intr_id;
+	interrupt_type_handler_t handler;
+
+	intr_id = plat_ic_get_pending_interrupt_id();
+	/* Currently we support one interrupt */
+	if (intr_id != PLAT_VERSAL_IPI_IRQ) {
+		WARN("Unexpected interrupt call: 0x%x\n", intr_id);
+		return 0;
+	}
+
+	handler = type_el3_interrupt_handler;
+	if (handler) {
+		return handler(intr_id, flags, handle, cookie);
+	}
+
+	return 0;
+}
 void bl31_platform_setup(void)
 {
 	/* Initialize the gic cpu and distributor interfaces */
@@ -116,6 +160,15 @@
 
 void bl31_plat_runtime_setup(void)
 {
+	uint64_t flags = 0;
+	uint64_t rc;
+
+	set_interrupt_rm_flag(flags, NON_SECURE);
+	rc = register_interrupt_type_handler(INTR_TYPE_EL3,
+					     rdo_el3_interrupt_handler, flags);
+	if (rc) {
+		panic();
+	}
 }
 
 /*
diff --git a/plat/xilinx/versal/include/plat_ipi.h b/plat/xilinx/versal/include/plat_ipi.h
index 6b08f32..36a4380 100644
--- a/plat/xilinx/versal/include/plat_ipi.h
+++ b/plat/xilinx/versal/include/plat_ipi.h
@@ -31,7 +31,7 @@
 #define IPI_BUFFER_APU_BASE	(IPI_BUFFER_BASEADDR + 0x400U)
 #define IPI_BUFFER_PMC_BASE	(IPI_BUFFER_BASEADDR + 0x200U)
 
-#define IPI_BUFFER_TARGET_APU_OFFSET	0x0U
+#define IPI_BUFFER_TARGET_APU_OFFSET	0x80U
 #define IPI_BUFFER_TARGET_PMC_OFFSET	0x40U
 
 #define IPI_BUFFER_LOCAL_BASE	IPI_BUFFER_APU_BASE
diff --git a/plat/xilinx/versal/include/plat_pm_common.h b/plat/xilinx/versal/include/plat_pm_common.h
index 2d00801..22c9d11 100644
--- a/plat/xilinx/versal/include/plat_pm_common.h
+++ b/plat/xilinx/versal/include/plat_pm_common.h
@@ -16,8 +16,8 @@
 #include <stdint.h>
 #include "pm_defs.h"
 
-#define PAYLOAD_ARG_CNT		6U
-#define PAYLOAD_ARG_SIZE	4U	/* size in bytes */
+#define NON_SECURE_FLAG		1U
+#define SECURE_FLAG		0U
 
 #define VERSAL_TZ_VERSION_MAJOR		1
 #define VERSAL_TZ_VERSION_MINOR		0
diff --git a/plat/xilinx/versal/include/plat_private.h b/plat/xilinx/versal/include/plat_private.h
index e302096..d12d13a 100644
--- a/plat/xilinx/versal/include/plat_private.h
+++ b/plat/xilinx/versal/include/plat_private.h
@@ -8,6 +8,7 @@
 #define PLAT_PRIVATE_H
 
 #include <lib/xlat_tables/xlat_tables.h>
+#include <bl31/interrupt_mgmt.h>
 
 void versal_config_setup(void);
 
@@ -22,5 +23,10 @@
 void plat_versal_gic_resume(void);
 
 unsigned int versal_calc_core_pos(u_register_t mpidr);
+/*
+ * Register handler to specific GIC entrance
+ * for INTR_TYPE_EL3 type of interrupt
+ */
+int request_intr_type_el3(uint32_t irq, interrupt_type_handler_t fiq_handler);
 
 #endif /* PLAT_PRIVATE_H */
diff --git a/plat/xilinx/versal/include/platform_def.h b/plat/xilinx/versal/include/platform_def.h
index 4cdaea2..8b513ef 100644
--- a/plat/xilinx/versal/include/platform_def.h
+++ b/plat/xilinx/versal/include/platform_def.h
@@ -91,11 +91,14 @@
  */
 #define PLAT_VERSAL_G1S_IRQS	VERSAL_IRQ_SEC_PHY_TIMER
 #define PLAT_VERSAL_G0_IRQS	VERSAL_IRQ_SEC_PHY_TIMER
+#define PLAT_VERSAL_IPI_IRQ	62
 
 #define PLAT_VERSAL_G1S_IRQ_PROPS(grp) \
 	INTR_PROP_DESC(VERSAL_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_LEVEL)
 
-#define PLAT_VERSAL_G0_IRQ_PROPS(grp)
+#define PLAT_VERSAL_G0_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(PLAT_VERSAL_IPI_IRQ, GIC_HIGHEST_SEC_PRIORITY, grp, \
+			GIC_INTR_CFG_EDGE), \
 
 #endif /* PLATFORM_DEF_H */
diff --git a/plat/xilinx/versal/include/versal_def.h b/plat/xilinx/versal/include/versal_def.h
index 810e5d8..001fb04 100644
--- a/plat/xilinx/versal/include/versal_def.h
+++ b/plat/xilinx/versal/include/versal_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -67,7 +67,7 @@
 #define VERSAL_UART0_BASE		0xFF000000
 #define VERSAL_UART1_BASE		0xFF010000
 
-#if VERSAL_CONSOLE_IS(pl011)
+#if VERSAL_CONSOLE_IS(pl011) || VERSAL_CONSOLE_IS(dcc)
 # define VERSAL_UART_BASE	VERSAL_UART0_BASE
 #elif VERSAL_CONSOLE_IS(pl011_1)
 # define VERSAL_UART_BASE	VERSAL_UART1_BASE
diff --git a/plat/xilinx/versal/plat_psci.c b/plat/xilinx/versal/plat_psci.c
index 3955085..fa0284c 100644
--- a/plat/xilinx/versal/plat_psci.c
+++ b/plat/xilinx/versal/plat_psci.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -33,7 +33,7 @@
 
 	/* Send request to PMC to wake up selected ACPU core */
 	pm_req_wakeup(proc->node_id, (versal_sec_entry & 0xFFFFFFFF) | 0x1,
-		      versal_sec_entry >> 32, 0);
+		      versal_sec_entry >> 32, 0, SECURE_FLAG);
 
 	/* Clear power down request */
 	pm_client_wakeup(proc);
@@ -59,13 +59,16 @@
 
 	plat_versal_gic_cpuif_disable();
 
-	plat_versal_gic_save();
+	if (target_state->pwr_domain_state[1] > PLAT_MAX_RET_STATE) {
+		plat_versal_gic_save();
+	}
 
 	state = target_state->pwr_domain_state[1] > PLAT_MAX_RET_STATE ?
 		PM_STATE_SUSPEND_TO_RAM : PM_STATE_CPU_IDLE;
 
 	/* Send request to PMC to suspend this core */
-	pm_self_suspend(proc->node_id, MAX_LATENCY, state, versal_sec_entry);
+	pm_self_suspend(proc->node_id, MAX_LATENCY, state, versal_sec_entry,
+			SECURE_FLAG);
 
 	/* APU is to be turned off */
 	if (target_state->pwr_domain_state[1] > PLAT_MAX_RET_STATE) {
@@ -99,11 +102,9 @@
 	/* APU was turned off, so restore GIC context */
 	if (target_state->pwr_domain_state[1] > PLAT_MAX_RET_STATE) {
 		plat_versal_gic_resume();
-		plat_versal_gic_cpuif_enable();
-	} else {
-		plat_versal_gic_cpuif_enable();
-		plat_versal_gic_pcpu_init();
 	}
+
+	plat_versal_gic_cpuif_enable();
 }
 
 void versal_pwr_domain_on_finish(const psci_power_state_t *target_state)
@@ -123,7 +124,7 @@
 {
 	/* Send the power down request to the PMC */
 	pm_system_shutdown(XPM_SHUTDOWN_TYPE_SHUTDOWN,
-			  pm_get_shutdown_scope());
+			  pm_get_shutdown_scope(), SECURE_FLAG);
 
 	while (1)
 		wfi();
@@ -137,7 +138,7 @@
 {
 	/* Send the system reset request to the PMC */
 	pm_system_shutdown(XPM_SHUTDOWN_TYPE_RESET,
-			  pm_get_shutdown_scope());
+			  pm_get_shutdown_scope(), SECURE_FLAG);
 
 	while (1)
 		wfi();
@@ -168,7 +169,8 @@
 	 * invoking CPU_on function, during which resume address will
 	 * be set.
 	 */
-	pm_self_suspend(proc->node_id, MAX_LATENCY, PM_STATE_CPU_IDLE, 0);
+	pm_self_suspend(proc->node_id, MAX_LATENCY, PM_STATE_CPU_IDLE, 0,
+			SECURE_FLAG);
 }
 
 /**
diff --git a/plat/xilinx/versal/plat_versal.c b/plat/xilinx/versal/plat_versal.c
index a080a76..107eae6 100644
--- a/plat/xilinx/versal/plat_versal.c
+++ b/plat/xilinx/versal/plat_versal.c
@@ -9,11 +9,13 @@
 
 int plat_core_pos_by_mpidr(u_register_t mpidr)
 {
-	if (mpidr & MPIDR_CLUSTER_MASK)
+	if (mpidr & MPIDR_CLUSTER_MASK) {
 		return -1;
+	}
 
-	if ((mpidr & MPIDR_CPU_MASK) >= PLATFORM_CORE_COUNT)
+	if ((mpidr & MPIDR_CPU_MASK) >= PLATFORM_CORE_COUNT) {
 		return -1;
+	}
 
 	return versal_calc_core_pos(mpidr);
 }
diff --git a/plat/xilinx/versal/platform.mk b/plat/xilinx/versal/platform.mk
index 16396dc..a8b2c94 100644
--- a/plat/xilinx/versal/platform.mk
+++ b/plat/xilinx/versal/platform.mk
@@ -1,4 +1,4 @@
-# Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 
@@ -8,6 +8,8 @@
 SEPARATE_CODE_AND_RODATA := 1
 override RESET_TO_BL31 := 1
 PL011_GENERIC_UART := 1
+IPI_CRC_CHECK := 0
+HARDEN_SLS_ALL := 0
 
 ifdef VERSAL_ATF_MEM_BASE
     $(eval $(call add_define,VERSAL_ATF_MEM_BASE))
@@ -31,12 +33,13 @@
     $(eval $(call add_define,VERSAL_BL32_MEM_SIZE))
 endif
 
+ifdef IPI_CRC_CHECK
+    $(eval $(call add_define,IPI_CRC_CHECK))
+endif
+
 VERSAL_PLATFORM ?= silicon
 $(eval $(call add_define_val,VERSAL_PLATFORM,VERSAL_PLATFORM_ID_${VERSAL_PLATFORM}))
 
-VERSAL_CONSOLE	?=	pl011
-$(eval $(call add_define_val,VERSAL_CONSOLE,VERSAL_CONSOLE_ID_${VERSAL_CONSOLE}))
-
 PLAT_INCLUDES		:=	-Iinclude/plat/arm/common/			\
 				-Iplat/xilinx/common/include/			\
 				-Iplat/xilinx/common/ipi_mailbox_service/	\
@@ -48,6 +51,7 @@
 
 PLAT_BL_COMMON_SOURCES	:=	lib/xlat_tables/xlat_tables_common.c		\
 				lib/xlat_tables/aarch64/xlat_tables.c		\
+				drivers/arm/dcc/dcc_console.c			\
 				drivers/delay_timer/delay_timer.c		\
 				drivers/delay_timer/generic_delay_timer.c	\
 				${GICV3_SOURCES}				\
@@ -59,8 +63,15 @@
 				plat/xilinx/versal/aarch64/versal_helpers.S	\
 				plat/xilinx/versal/aarch64/versal_common.c
 
+VERSAL_CONSOLE	?=	pl011
+ifeq (${VERSAL_CONSOLE}, $(filter ${VERSAL_CONSOLE},pl011 pl011_0 pl011_1 dcc))
+else
+  $(error "Please define VERSAL_CONSOLE")
+endif
+
+$(eval $(call add_define_val,VERSAL_CONSOLE,VERSAL_CONSOLE_ID_${VERSAL_CONSOLE}))
+
 BL31_SOURCES		+=	drivers/arm/cci/cci.c				\
-				lib/cpus/aarch64/cortex_a53.S			\
 				lib/cpus/aarch64/cortex_a72.S			\
 				plat/common/plat_psci_common.c			\
 				plat/xilinx/common/ipi.c			\
@@ -77,3 +88,7 @@
 				plat/xilinx/versal/pm_service/pm_svc_main.c	\
 				plat/xilinx/versal/pm_service/pm_api_sys.c	\
 				plat/xilinx/versal/pm_service/pm_client.c
+
+ifeq ($(HARDEN_SLS_ALL), 1)
+TF_CFLAGS_aarch64      +=      -mharden-sls=all
+endif
diff --git a/plat/xilinx/versal/pm_service/pm_api_sys.c b/plat/xilinx/versal/pm_service/pm_api_sys.c
index dbe94e6..912835a 100644
--- a/plat/xilinx/versal/pm_service/pm_api_sys.c
+++ b/plat/xilinx/versal/pm_service/pm_api_sys.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Xilinx, Inc. All rights reserved.
+ * Copyright (c) 2019-2020, Xilinx, Inc. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,6 +14,9 @@
 #include <plat/common/platform.h>
 #include "pm_api_sys.h"
 #include "pm_client.h"
+#include "pm_defs.h"
+#include "pm_svc_main.h"
+#include "../drivers/arm/gic/v3/gicv3_private.h"
 
 /*********************************************************************
  * Target module IDs macros
@@ -21,6 +24,7 @@
 #define LIBPM_MODULE_ID		0x2
 #define LOADER_MODULE_ID	0x7
 
+#define  MODE	0x80000000
 /* default shutdown/reboot scope is system(2) */
 static unsigned int pm_shutdown_scope = XPM_SHUTDOWN_SUBTYPE_RST_SYSTEM;
 
@@ -37,33 +41,33 @@
 /**
  * Assigning of argument values into array elements.
  */
-#define PM_PACK_PAYLOAD1(pl, mid, arg0) {	\
-	pl[0] = (uint32_t)((uint32_t)((arg0) & 0xFF) | (mid << 8)); \
+#define PM_PACK_PAYLOAD1(pl, mid, flag, arg0) {	\
+	pl[0] = (uint32_t)((uint32_t)((arg0) & 0xFF) | (mid << 8) | ((flag) << 24)); \
 }
 
-#define PM_PACK_PAYLOAD2(pl, mid, arg0, arg1) {		\
-	pl[1] = (uint32_t)(arg1);			\
-	PM_PACK_PAYLOAD1(pl, mid, arg0);		\
+#define PM_PACK_PAYLOAD2(pl, mid, flag, arg0, arg1) {		\
+	pl[1] = (uint32_t)(arg1);				\
+	PM_PACK_PAYLOAD1(pl, mid, flag, arg0);			\
 }
 
-#define PM_PACK_PAYLOAD3(pl, mid, arg0, arg1, arg2) {	\
-	pl[2] = (uint32_t)(arg2);			\
-	PM_PACK_PAYLOAD2(pl, mid, arg0, arg1);		\
+#define PM_PACK_PAYLOAD3(pl, mid, flag, arg0, arg1, arg2) {	\
+	pl[2] = (uint32_t)(arg2);				\
+	PM_PACK_PAYLOAD2(pl, mid, flag, arg0, arg1);		\
 }
 
-#define PM_PACK_PAYLOAD4(pl, mid, arg0, arg1, arg2, arg3) {	\
-	pl[3] = (uint32_t)(arg3);				\
-	PM_PACK_PAYLOAD3(pl, mid, arg0, arg1, arg2);		\
+#define PM_PACK_PAYLOAD4(pl, mid, flag, arg0, arg1, arg2, arg3) {	\
+	pl[3] = (uint32_t)(arg3);					\
+	PM_PACK_PAYLOAD3(pl, mid, flag, arg0, arg1, arg2);		\
 }
 
-#define PM_PACK_PAYLOAD5(pl, mid, arg0, arg1, arg2, arg3, arg4) {	\
+#define PM_PACK_PAYLOAD5(pl, mid, flag, arg0, arg1, arg2, arg3, arg4) {	\
 	pl[4] = (uint32_t)(arg4);					\
-	PM_PACK_PAYLOAD4(pl, mid, arg0, arg1, arg2, arg3);		\
+	PM_PACK_PAYLOAD4(pl, mid, flag, arg0, arg1, arg2, arg3);	\
 }
 
-#define PM_PACK_PAYLOAD6(pl, mid, arg0, arg1, arg2, arg3, arg4, arg5) {	\
-	pl[5] = (uint32_t)(arg5);					\
-	PM_PACK_PAYLOAD5(pl, mid, arg0, arg1, arg2, arg3, arg4);	\
+#define PM_PACK_PAYLOAD6(pl, mid, flag, arg0, arg1, arg2, arg3, arg4, arg5) {	\
+	pl[5] = (uint32_t)(arg5);						\
+	PM_PACK_PAYLOAD5(pl, mid, flag, arg0, arg1, arg2, arg3, arg4);		\
 }
 
 /* PM API functions */
@@ -71,24 +75,46 @@
 /**
  * pm_get_api_version() - Get version number of PMC PM firmware
  * @version	Returns 32-bit version number of PMC Power Management Firmware
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_get_api_version(unsigned int *version)
+enum pm_ret_status pm_get_api_version(unsigned int *version, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD1(payload, LIBPM_MODULE_ID, PM_GET_API_VERSION);
+	PM_PACK_PAYLOAD1(payload, LIBPM_MODULE_ID, flag, PM_GET_API_VERSION);
 	return pm_ipi_send_sync(primary_proc, payload, version, 1);
 }
 
 /**
+ * pm_init_finalize() - Call to notify PMC PM firmware that master has power
+ *			management enabled and that it has finished its
+ *			initialization
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
+ *
+ * @return	Status returned by the PMU firmware
+ */
+enum pm_ret_status pm_init_finalize(uint32_t flag)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD1(payload, LIBPM_MODULE_ID, flag, PM_INIT_FINALIZE);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+}
+
+/**
  * pm_self_suspend() - PM call for processor to suspend itself
  * @nid		Node id of the processor or subsystem
  * @latency	Requested maximum wakeup latency (not supported)
  * @state	Requested state
  * @address	Resume address
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * This is a blocking call, it will return only once PMU has responded.
  * On a wakeup, resume address will be automatically set by PMU.
@@ -98,7 +124,7 @@
 enum pm_ret_status pm_self_suspend(uint32_t nid,
 				   unsigned int latency,
 				   unsigned int state,
-				   uintptr_t address)
+				   uintptr_t address, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 	unsigned int cpuid = plat_my_core_pos();
@@ -116,7 +142,7 @@
 	pm_client_suspend(proc, state);
 
 	/* Send request to the PLM */
-	PM_PACK_PAYLOAD6(payload, LIBPM_MODULE_ID, PM_SELF_SUSPEND,
+	PM_PACK_PAYLOAD6(payload, LIBPM_MODULE_ID, flag, PM_SELF_SUSPEND,
 			 proc->node_id, latency, state, address,
 			 (address >> 32));
 	return pm_ipi_send_sync(proc, payload, NULL, 0);
@@ -126,13 +152,15 @@
  * pm_abort_suspend() - PM call to announce that a prior suspend request
  *			is to be aborted.
  * @reason	Reason for the abort
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * Calling PU expects the PMU to abort the initiated suspend procedure.
  * This is a non-blocking call without any acknowledge.
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_abort_suspend(enum pm_abort_reason reason)
+enum pm_ret_status pm_abort_suspend(enum pm_abort_reason reason, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
@@ -143,9 +171,9 @@
 	pm_client_abort_suspend();
 
 	/* Send request to the PLM */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_ABORT_SUSPEND, reason,
-			 primary_proc->node_id);
-	return pm_ipi_send(primary_proc, payload);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_ABORT_SUSPEND,
+			 reason, primary_proc->node_id);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -155,16 +183,19 @@
  * @ack		Flag to specify whether acknowledge is requested
  * @latency	Requested wakeup latency (not supported)
  * @state	Requested state (not supported)
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_req_suspend(uint32_t target, uint8_t ack,
-				  unsigned int latency, unsigned int state)
+				  unsigned int latency, unsigned int state,
+				  uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMU */
-	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, PM_REQ_SUSPEND, target,
+	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, flag, PM_REQ_SUSPEND, target,
 			 latency, state);
 	if (ack == IPI_BLOCKING)
 		return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -180,6 +211,8 @@
  *		1 - resume address specified, 0 - otherwise
  * @address	Resume address
  * @ack		Flag to specify whether acknowledge requested
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * This API function is either used to power up another APU core for SMP
  * (by PSCI) or to power up an entirely different PU or subsystem, such
@@ -189,12 +222,12 @@
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_req_wakeup(uint32_t target, uint32_t set_address,
-				 uintptr_t address, uint8_t ack)
+				 uintptr_t address, uint8_t ack, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC to perform the wake of the PU */
-	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, PM_REQ_WAKEUP, target,
+	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_REQ_WAKEUP, target,
 			 set_address, address, ack);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -206,16 +239,18 @@
  * @capabilities	Requested capabilities for the device
  * @qos			Required Quality of Service
  * @ack			Flag to specify whether acknowledge requested
+ * @flag		0 - Call from secure source
+ *			1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_request_device(uint32_t device_id, uint32_t capabilities,
-				     uint32_t qos, uint32_t ack)
+				     uint32_t qos, uint32_t ack, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, PM_REQUEST_DEVICE,
+	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_REQUEST_DEVICE,
 			 device_id, capabilities, qos, ack);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -224,15 +259,17 @@
 /**
  * pm_release_device() - Release a device
  * @device_id		Device ID
+ * @flag		0 - Call from secure source
+ *			1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_release_device(uint32_t device_id)
+enum pm_ret_status pm_release_device(uint32_t device_id, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_RELEASE_DEVICE,
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_RELEASE_DEVICE,
 			 device_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -244,16 +281,19 @@
  * @capabilities	Requested capabilities for the device
  * @latency		Requested maximum latency
  * @qos			Required Quality of Service
+ * @flag		0 - Call from secure source
+ *			1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_set_requirement(uint32_t device_id, uint32_t capabilities,
-				      uint32_t latency, uint32_t qos)
+				      uint32_t latency, uint32_t qos,
+				      uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, PM_SET_REQUIREMENT,
+	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_SET_REQUIREMENT,
 			 device_id, capabilities, latency, qos);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -263,15 +303,18 @@
  * pm_get_device_status() - Get device's status
  * @device_id		Device ID
  * @response		Buffer to store device status response
+ * @flag		0 - Call from secure source
+ *			1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_get_device_status(uint32_t device_id, uint32_t *response)
+enum pm_ret_status pm_get_device_status(uint32_t device_id, uint32_t *response,
+					uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_GET_DEVICE_STATUS,
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_GET_DEVICE_STATUS,
 			 device_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, response, 3);
@@ -281,15 +324,17 @@
  * pm_reset_assert() - Assert/De-assert reset
  * @reset	Reset ID
  * @assert	Assert (1) or de-assert (0)
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_reset_assert(uint32_t reset, bool assert)
+enum pm_ret_status pm_reset_assert(uint32_t reset, bool assert, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_RESET_ASSERT, reset,
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_RESET_ASSERT, reset,
 			 assert);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -299,15 +344,19 @@
  * pm_reset_get_status() - Get current status of a reset line
  * @reset	Reset ID
  * @status	Returns current status of selected reset ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_reset_get_status(uint32_t reset, uint32_t *status)
+enum pm_ret_status pm_reset_get_status(uint32_t reset, uint32_t *status,
+				       uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_RESET_ASSERT, reset);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_RESET_ASSERT,
+			 reset);
 
 	return pm_ipi_send_sync(primary_proc, payload, status, 1);
 }
@@ -315,10 +364,12 @@
 /**
  * pm_get_callbackdata() - Read from IPI response buffer
  * @data - array of PAYLOAD_ARG_CNT elements
+ * @flag - 0 - Call from secure source
+ *	   1 - Call from non-secure source
  *
  * Read value from ipi buffer response buffer.
  */
-void pm_get_callbackdata(uint32_t *data, size_t count)
+void pm_get_callbackdata(uint32_t *data, size_t count, uint32_t flag)
 {
 	/* Return if interrupt is not from PMU */
 	if (!pm_ipi_irq_status(primary_proc))
@@ -331,15 +382,18 @@
 /**
  * pm_pinctrl_request() - Request a pin
  * @pin		Pin ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_request(uint32_t pin)
+enum pm_ret_status pm_pinctrl_request(uint32_t pin, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_PINCTRL_REQUEST, pin);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_PINCTRL_REQUEST,
+			 pin);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -347,15 +401,18 @@
 /**
  * pm_pinctrl_release() - Release a pin
  * @pin		Pin ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_release(uint32_t pin)
+enum pm_ret_status pm_pinctrl_release(uint32_t pin, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_PINCTRL_RELEASE, pin);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_PINCTRL_RELEASE,
+			 pin);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -364,16 +421,19 @@
  * pm_pinctrl_set_function() - Set pin function
  * @pin		Pin ID
  * @function	Function ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_set_function(uint32_t pin, uint32_t function)
+enum pm_ret_status pm_pinctrl_set_function(uint32_t pin, uint32_t function,
+					   uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_PINCTRL_SET_FUNCTION, pin,
-			 function)
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag,
+			 PM_PINCTRL_SET_FUNCTION, pin, function)
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -382,16 +442,19 @@
  * pm_pinctrl_get_function() - Get function set on the pin
  * @pin		Pin ID
  * @function	Function set on the pin
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_get_function(uint32_t pin, uint32_t *function)
+enum pm_ret_status pm_pinctrl_get_function(uint32_t pin, uint32_t *function,
+					   uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_PINCTRL_SET_FUNCTION,
-			 pin);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag,
+			 PM_PINCTRL_SET_FUNCTION, pin);
 
 	return pm_ipi_send_sync(primary_proc, payload, function, 1);
 }
@@ -401,17 +464,19 @@
  * @pin		Pin ID
  * @param	Parameter ID
  * @value	Parameter value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_pinctrl_set_pin_param(uint32_t pin, uint32_t param,
-					    uint32_t value)
+					    uint32_t value, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, PM_PINCTRL_CONFIG_PARAM_SET,
-			 pin, param, value);
+	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, flag,
+			 PM_PINCTRL_CONFIG_PARAM_SET, pin, param, value);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -421,17 +486,19 @@
  * @pin		Pin ID
  * @param	Parameter ID
  * @value	Buffer to store parameter value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_pinctrl_get_pin_param(uint32_t pin, uint32_t param,
-					    uint32_t *value)
+					    uint32_t *value, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_PINCTRL_CONFIG_PARAM_GET,
-			 pin, param);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag,
+			 PM_PINCTRL_CONFIG_PARAM_GET, pin, param);
 
 	return pm_ipi_send_sync(primary_proc, payload, value, 1);
 }
@@ -439,15 +506,18 @@
 /**
  * pm_clock_enable() - Enable the clock
  * @clk_id	Clock ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_enable(uint32_t clk_id)
+enum pm_ret_status pm_clock_enable(uint32_t clk_id, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_CLOCK_ENABLE, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_ENABLE,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -455,15 +525,18 @@
 /**
  * pm_clock_disable() - Disable the clock
  * @clk_id	Clock ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_disable(uint32_t clk_id)
+enum pm_ret_status pm_clock_disable(uint32_t clk_id, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_CLOCK_DISABLE, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_DISABLE,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -472,15 +545,19 @@
  * pm_clock_get_state() - Get clock status
  * @clk_id	Clock ID
  * @state:	Buffer to store clock status (1: Enabled, 0:Disabled)
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_get_state(uint32_t clk_id, uint32_t *state)
+enum pm_ret_status pm_clock_get_state(uint32_t clk_id, uint32_t *state,
+				      uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_CLOCK_GETSTATE, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_GETSTATE,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, state, 1);
 }
@@ -489,16 +566,19 @@
  * pm_clock_set_divider() - Set divider for the clock
  * @clk_id	Clock ID
  * @divider	Divider value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_set_divider(uint32_t clk_id, uint32_t divider)
+enum pm_ret_status pm_clock_set_divider(uint32_t clk_id, uint32_t divider,
+					uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_CLOCK_SETDIVIDER, clk_id,
-			 divider);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_SETDIVIDER,
+			 clk_id, divider);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -507,15 +587,19 @@
  * pm_clock_get_divider() - Get divider value for the clock
  * @clk_id	Clock ID
  * @divider:	Buffer to store clock divider value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_get_divider(uint32_t clk_id, uint32_t *divider)
+enum pm_ret_status pm_clock_get_divider(uint32_t clk_id, uint32_t *divider,
+					uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_CLOCK_GETDIVIDER, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_GETDIVIDER,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, divider, 1);
 }
@@ -524,16 +608,19 @@
  * pm_clock_set_parent() - Set parent for the clock
  * @clk_id	Clock ID
  * @parent	Parent ID
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_set_parent(uint32_t clk_id, uint32_t parent)
+enum pm_ret_status pm_clock_set_parent(uint32_t clk_id, uint32_t parent,
+				       uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_CLOCK_SETPARENT, clk_id,
-			 parent);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_SETPARENT,
+			 clk_id, parent);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -542,35 +629,61 @@
  * pm_clock_get_parent() - Get parent value for the clock
  * @clk_id	Clock ID
  * @parent:	Buffer to store clock parent value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_clock_get_parent(uint32_t clk_id, uint32_t *parent)
+enum pm_ret_status pm_clock_get_parent(uint32_t clk_id, uint32_t *parent,
+				       uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_CLOCK_GETPARENT, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_GETPARENT,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, parent, 1);
 }
+/**
+ * pm_clock_get_rate() - Get the rate value for the clock
+ * @clk_id	Clock ID
+ * @rate:	Buffer to store clock rate value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
+ *
+ * @return	Returns status, either success or error+reason
+ */
+enum pm_ret_status pm_clock_get_rate(uint32_t clk_id, uint32_t *clk_rate,
+				     uint32_t flag)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMC */
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_CLOCK_GETRATE,
+			 clk_id);
+
+	return pm_ipi_send_sync(primary_proc, payload, clk_rate, 2);
+}
 
 /**
  * pm_pll_set_param() - Set PLL parameter
  * @clk_id	PLL clock ID
  * @param	PLL parameter ID
  * @value	Value to set for PLL parameter
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_pll_set_param(uint32_t clk_id, uint32_t param,
-				    uint32_t value)
+				    uint32_t value, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, PM_PLL_SET_PARAMETER, clk_id,
-			 param, value);
+	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, flag, PM_PLL_SET_PARAMETER,
+			 clk_id, param, value);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -580,17 +693,19 @@
  * @clk_id	PLL clock ID
  * @param	PLL parameter ID
  * @value:	Buffer to store PLL parameter value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_pll_get_param(uint32_t clk_id, uint32_t param,
-				    uint32_t *value)
+				    uint32_t *value, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_PLL_GET_PARAMETER, clk_id,
-			 param);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_PLL_GET_PARAMETER,
+			 clk_id, param);
 
 	return pm_ipi_send_sync(primary_proc, payload, value, 1);
 }
@@ -599,16 +714,19 @@
  * pm_pll_set_mode() - Set PLL mode
  * @clk_id	PLL clock ID
  * @mode	PLL mode
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pll_set_mode(uint32_t clk_id, uint32_t mode)
+enum pm_ret_status pm_pll_set_mode(uint32_t clk_id, uint32_t mode,
+				   uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_PLL_SET_MODE, clk_id,
-			 mode);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_PLL_SET_MODE,
+			 clk_id, mode);
 
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -617,15 +735,19 @@
  * pm_pll_get_mode() - Get PLL mode
  * @clk_id	PLL clock ID
  * @mode:	Buffer to store PLL mode
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pll_get_mode(uint32_t clk_id, uint32_t *mode)
+enum pm_ret_status pm_pll_get_mode(uint32_t clk_id, uint32_t *mode,
+				   uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_PLL_GET_MODE, clk_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag, PM_PLL_GET_MODE,
+			 clk_id);
 
 	return pm_ipi_send_sync(primary_proc, payload, mode, 1);
 }
@@ -635,16 +757,19 @@
  *			  be powered down forcefully
  * @target	Device ID of the PU node to be forced powered down.
  * @ack		Flag to specify whether acknowledge is requested
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_force_powerdown(uint32_t target, uint8_t ack)
+enum pm_ret_status pm_force_powerdown(uint32_t target, uint8_t ack,
+				      uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_FORCE_POWERDOWN, target,
-			 ack);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_FORCE_POWERDOWN,
+			 target, ack);
 
 	if (ack == IPI_BLOCKING)
 		return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
@@ -656,10 +781,13 @@
  * pm_system_shutdown() - PM call to request a system shutdown or restart
  * @type	Shutdown or restart? 0=shutdown, 1=restart, 2=setscope
  * @subtype	Scope: 0=APU-subsystem, 1=PS, 2=system
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_system_shutdown(uint32_t type, uint32_t subtype)
+enum pm_ret_status pm_system_shutdown(uint32_t type, uint32_t subtype,
+				      uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
@@ -670,8 +798,8 @@
 	}
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_SYSTEM_SHUTDOWN, type,
-			 subtype);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_SYSTEM_SHUTDOWN,
+			 type, subtype);
 
 	return pm_ipi_send_non_blocking(primary_proc, payload);
 }
@@ -683,18 +811,39 @@
 * @arg2	Argument 2 to requested query data call
 * @arg3	Argument 3 to requested query data call
 * @data	Returned output data
+* @flag 0 - Call from secure source
+*	1 - Call from non-secure source
 *
 * This function returns requested data.
 */
 enum pm_ret_status pm_query_data(uint32_t qid, uint32_t arg1, uint32_t arg2,
-				 uint32_t arg3, uint32_t *data)
+				 uint32_t arg3, uint32_t *data, uint32_t flag)
 {
+	uint32_t ret;
+	uint32_t version;
 	uint32_t payload[PAYLOAD_ARG_CNT];
+	uint32_t fw_api_version;
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, PM_QUERY_DATA, qid, arg1,
-			 arg2, arg3);
-	return pm_ipi_send_sync(primary_proc, payload, data, 4);
+	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_QUERY_DATA, qid,
+			 arg1, arg2, arg3);
+
+	ret = pm_feature_check(PM_QUERY_DATA, &version, flag);
+	if (PM_RET_SUCCESS == ret) {
+		fw_api_version = version & 0xFFFF ;
+		if ((2U == fw_api_version) &&
+		    ((XPM_QID_CLOCK_GET_NAME == qid) ||
+		     (XPM_QID_PINCTRL_GET_FUNCTION_NAME == qid))) {
+			ret = pm_ipi_send_sync(primary_proc, payload, data, 8);
+			ret = data[0];
+			data[0] = data[1];
+			data[1] = data[2];
+			data[2] = data[3];
+		} else {
+			ret = pm_ipi_send_sync(primary_proc, payload, data, 4);
+		}
+	}
+	return ret;
 }
 /**
  * pm_api_ioctl() -  PM IOCTL API for device control and configs
@@ -703,29 +852,42 @@
  * @arg1	Argument 1 to requested IOCTL call
  * @arg2	Argument 2 to requested IOCTL call
  * @value	Returned output value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * This function calls IOCTL to firmware for device control and configuration.
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_api_ioctl(uint32_t device_id, uint32_t ioctl_id,
-				uint32_t arg1, uint32_t arg2, uint32_t *value)
+				uint32_t arg1, uint32_t arg2, uint32_t *value,
+				uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
+	int ret;
 
 	switch (ioctl_id) {
 	case IOCTL_SET_PLL_FRAC_MODE:
-		return pm_pll_set_mode(arg1, arg2);
+		return pm_pll_set_mode(arg1, arg2, flag);
 	case IOCTL_GET_PLL_FRAC_MODE:
-		return pm_pll_get_mode(arg1, value);
+		return pm_pll_get_mode(arg1, value, flag);
 	case IOCTL_SET_PLL_FRAC_DATA:
-		return pm_pll_set_param(arg1, PM_PLL_PARAM_DATA, arg2);
+		return pm_pll_set_param(arg1, PM_PLL_PARAM_DATA, arg2, flag);
 	case IOCTL_GET_PLL_FRAC_DATA:
-		return pm_pll_get_param(arg1, PM_PLL_PARAM_DATA, value);
+		return pm_pll_get_param(arg1, PM_PLL_PARAM_DATA, value, flag);
+	case IOCTL_SET_SGI:
+		/* Get the sgi number */
+		ret = pm_register_sgi(arg1);
+		if (ret) {
+			return PM_RET_ERROR_ARGS;
+		}
+		gicd_write_irouter(gicv3_driver_data->gicd_base,
+				PLAT_VERSAL_IPI_IRQ, MODE);
+		return PM_RET_SUCCESS;
 	default:
 		/* Send request to the PMC */
-		PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, PM_IOCTL, device_id,
-				 ioctl_id, arg1, arg2);
+		PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_IOCTL,
+				 device_id, ioctl_id, arg1, arg2);
 		return pm_ipi_send_sync(primary_proc, payload, value, 1);
 	}
 }
@@ -735,32 +897,36 @@
  * @target	Device id of the targeted PU or subsystem
  * @wkup_node	Device id of the wakeup peripheral
  * @enable	Enable or disable the specified peripheral as wake source
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_set_wakeup_source(uint32_t target, uint32_t wkup_device,
-					uint8_t enable)
+					uint8_t enable, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
-	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, PM_SET_WAKEUP_SOURCE, target,
-			 wkup_device, enable);
-	return pm_ipi_send(primary_proc, payload);
+	PM_PACK_PAYLOAD4(payload, LIBPM_MODULE_ID, flag, PM_SET_WAKEUP_SOURCE,
+			 target, wkup_device, enable);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
  * pm_get_chipid() - Read silicon ID registers
  * @value       Buffer for return values. Must be large enough
  *		to hold 8 bytes.
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return      Returns silicon ID registers
  */
-enum pm_ret_status pm_get_chipid(uint32_t *value)
+enum pm_ret_status pm_get_chipid(uint32_t *value, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD1(payload, LIBPM_MODULE_ID, PM_GET_CHIPID);
+	PM_PACK_PAYLOAD1(payload, LIBPM_MODULE_ID, flag, PM_GET_CHIPID);
 
 	return pm_ipi_send_sync(primary_proc, payload, value, 2);
 }
@@ -769,10 +935,13 @@
  * pm_feature_check() - Returns the supported API version if supported
  * @api_id	API ID to check
  * @value	Returned supported API version
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_feature_check(uint32_t api_id, unsigned int *version)
+enum pm_ret_status pm_feature_check(uint32_t api_id, unsigned int *version,
+				    uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT], fw_api_version;
 	uint32_t status;
@@ -780,7 +949,7 @@
 	switch (api_id) {
 	case PM_GET_CALLBACK_DATA:
 	case PM_GET_TRUSTZONE_VERSION:
-	case PM_INIT_FINALIZE:
+	case PM_LOAD_PDI:
 		*version = (PM_API_BASE_VERSION << 16);
 		return PM_RET_SUCCESS;
 	case PM_GET_API_VERSION:
@@ -798,6 +967,7 @@
 	case PM_SET_REQUIREMENT:
 	case PM_RESET_ASSERT:
 	case PM_RESET_GET_STATUS:
+	case PM_GET_CHIPID:
 	case PM_PINCTRL_REQUEST:
 	case PM_PINCTRL_RELEASE:
 	case PM_PINCTRL_GET_FUNCTION:
@@ -805,7 +975,6 @@
 	case PM_PINCTRL_CONFIG_PARAM_GET:
 	case PM_PINCTRL_CONFIG_PARAM_SET:
 	case PM_IOCTL:
-	case PM_QUERY_DATA:
 	case PM_CLOCK_ENABLE:
 	case PM_CLOCK_DISABLE:
 	case PM_CLOCK_GETSTATE:
@@ -813,22 +982,27 @@
 	case PM_CLOCK_GETDIVIDER:
 	case PM_CLOCK_SETPARENT:
 	case PM_CLOCK_GETPARENT:
+	case PM_CLOCK_GETRATE:
 	case PM_PLL_SET_PARAMETER:
 	case PM_PLL_GET_PARAMETER:
 	case PM_PLL_SET_MODE:
 	case PM_PLL_GET_MODE:
 	case PM_FEATURE_CHECK:
+	case PM_INIT_FINALIZE:
+	case PM_SET_MAX_LATENCY:
+	case PM_REGISTER_NOTIFIER:
 		*version = (PM_API_BASE_VERSION << 16);
 		break;
-	case PM_LOAD_PDI:
-		*version = (PM_API_BASE_VERSION << 16);
-		return PM_RET_SUCCESS;
+	case PM_QUERY_DATA:
+		*version = (PM_API_QUERY_DATA_VERSION << 16);
+		break;
 	default:
 		*version = 0U;
 		return PM_RET_ERROR_NOFEATURE;
 	}
 
-	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, PM_FEATURE_CHECK, api_id);
+	PM_PACK_PAYLOAD2(payload, LIBPM_MODULE_ID, flag,
+			 PM_FEATURE_CHECK, api_id);
 
 	status = pm_ipi_send_sync(primary_proc, payload, &fw_api_version, 1);
 	if (status != PM_RET_SUCCESS)
@@ -847,16 +1021,18 @@
  * src:        Source device of pdi(DDR, OCM, SD etc)
  * address_low: lower 32-bit Linear memory space address
  * address_high: higher 32-bit Linear memory space address
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return      Returns status, either success or error+reason
  */
-enum pm_ret_status pm_load_pdi(uint32_t src,
-			       uint32_t address_low, uint32_t address_high)
+enum pm_ret_status pm_load_pdi(uint32_t src, uint32_t address_low,
+			       uint32_t address_high, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMU */
-	PM_PACK_PAYLOAD4(payload, LOADER_MODULE_ID, PM_LOAD_PDI, src,
+	PM_PACK_PAYLOAD4(payload, LOADER_MODULE_ID, flag, PM_LOAD_PDI, src,
 			 address_high, address_low);
 	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
@@ -869,17 +1045,67 @@
  *              (power, temperature and latency)
  * @result      Returns the operating characteristic for the requested device,
  *              specified by the type
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
  *
  * @return      Returns status, either success or error+reason
  */
 enum pm_ret_status pm_get_op_characteristic(uint32_t device_id,
 					    enum pm_opchar_type type,
-					    uint32_t *result)
+					    uint32_t *result, uint32_t flag)
 {
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	/* Send request to the PMC */
-	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, PM_GET_OP_CHARACTERISTIC,
-			 device_id, type);
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag,
+			 PM_GET_OP_CHARACTERISTIC, device_id, type);
 	return pm_ipi_send_sync(primary_proc, payload, result, 1);
 }
+
+/**
+ * pm_set_max_latency() - PM call to change in the maximum wake-up latency
+ *			  requirements for a specific device currently
+ *			  used by that CPU.
+ * @device_id	Device ID
+ * @latency	Latency value
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
+ *
+ * @return	Returns status, either success or error+reason
+ */
+enum pm_ret_status pm_set_max_latency(uint32_t device_id, uint32_t latency,
+				      uint32_t flag)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMC */
+	PM_PACK_PAYLOAD3(payload, LIBPM_MODULE_ID, flag, PM_SET_MAX_LATENCY,
+			 device_id, latency);
+
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+}
+
+/**
+ * pm_register_notifier() - PM call to register a subsystem to be notified
+ * 			    about the device event
+ * @device_id	Device ID for the Node to which the event is related
+ * @event	Event in question
+ * @wake	Wake subsystem upon capturing the event if value 1
+ * @enable	Enable the registration for value 1, disable for value 0
+ * @flag	0 - Call from secure source
+ *		1 - Call from non-secure source
+ *
+ * @return	Returns status, either success or error+reason
+ */
+enum pm_ret_status pm_register_notifier(uint32_t device_id, uint32_t event,
+					uint32_t wake, uint32_t enable,
+					uint32_t flag)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMC */
+	PM_PACK_PAYLOAD5(payload, LIBPM_MODULE_ID, flag, PM_REGISTER_NOTIFIER,
+			 device_id, event, wake, enable);
+
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+}
diff --git a/plat/xilinx/versal/pm_service/pm_api_sys.h b/plat/xilinx/versal/pm_service/pm_api_sys.h
index 4de592a..5a92704 100644
--- a/plat/xilinx/versal/pm_service/pm_api_sys.h
+++ b/plat/xilinx/versal/pm_service/pm_api_sys.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Xilinx, Inc. All rights reserved.
+ * Copyright (c) 2019-2020, Xilinx, Inc. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,62 +14,86 @@
  * PM API function declarations
  **********************************************************/
 
-enum pm_ret_status pm_get_api_version(unsigned int *version);
+enum pm_ret_status pm_get_api_version(unsigned int *version, uint32_t flag);
+enum pm_ret_status pm_init_finalize(uint32_t flag);
 enum pm_ret_status pm_self_suspend(uint32_t nid,
 				   unsigned int latency,
 				   unsigned int state,
-				   uintptr_t address);
-enum pm_ret_status pm_abort_suspend(enum pm_abort_reason reason);
+				   uintptr_t address, uint32_t flag);
+enum pm_ret_status pm_abort_suspend(enum pm_abort_reason reason, uint32_t flag);
 enum pm_ret_status pm_req_suspend(uint32_t target,
 				  uint8_t ack,
 				  unsigned int latency,
-				  unsigned int state);
+				  unsigned int state, uint32_t flag);
 enum pm_ret_status pm_req_wakeup(uint32_t target, uint32_t set_address,
-				 uintptr_t address, uint8_t ack);
+				 uintptr_t address, uint8_t ack, uint32_t flag);
 enum pm_ret_status pm_set_wakeup_source(uint32_t target, uint32_t device_id,
-					uint8_t enable);
+					uint8_t enable, uint32_t flag);
 enum pm_ret_status pm_request_device(uint32_t device_id, uint32_t capabilities,
-				     uint32_t qos, uint32_t ack);
-enum pm_ret_status pm_release_device(uint32_t device_id);
+				     uint32_t qos, uint32_t ack, uint32_t flag);
+enum pm_ret_status pm_release_device(uint32_t device_id, uint32_t flag);
 enum pm_ret_status pm_set_requirement(uint32_t device_id, uint32_t capabilities,
-				      uint32_t latency, uint32_t qos);
-enum pm_ret_status pm_get_device_status(uint32_t device_id, uint32_t *response);
-enum pm_ret_status pm_reset_assert(uint32_t reset, bool assert);
-enum pm_ret_status pm_reset_get_status(uint32_t reset, uint32_t *status);
-void pm_get_callbackdata(uint32_t *data, size_t count);
-enum pm_ret_status pm_pinctrl_request(uint32_t pin);
-enum pm_ret_status pm_pinctrl_release(uint32_t pin);
-enum pm_ret_status pm_pinctrl_set_function(uint32_t pin, uint32_t function);
-enum pm_ret_status pm_pinctrl_get_function(uint32_t pin, uint32_t *function);
+				      uint32_t latency, uint32_t qos,
+				      uint32_t flag);
+enum pm_ret_status pm_get_device_status(uint32_t device_id, uint32_t *response,
+					uint32_t flag);
+enum pm_ret_status pm_reset_assert(uint32_t reset, bool assert, uint32_t flag);
+enum pm_ret_status pm_reset_get_status(uint32_t reset, uint32_t *status,
+				       uint32_t flag);
+void pm_get_callbackdata(uint32_t *data, size_t count, uint32_t flag);
+enum pm_ret_status pm_pinctrl_request(uint32_t pin, uint32_t flag);
+enum pm_ret_status pm_pinctrl_release(uint32_t pin, uint32_t flag);
+enum pm_ret_status pm_pinctrl_set_function(uint32_t pin, uint32_t function,
+					   uint32_t flag);
+enum pm_ret_status pm_pinctrl_get_function(uint32_t pin, uint32_t *function,
+					   uint32_t flag);
 enum pm_ret_status pm_pinctrl_set_pin_param(uint32_t pin, uint32_t param,
-					    uint32_t value);
+					    uint32_t value, uint32_t flag);
 enum pm_ret_status pm_pinctrl_get_pin_param(uint32_t pin, uint32_t param,
-					    uint32_t *value);
-enum pm_ret_status pm_clock_enable(uint32_t clk_id);
-enum pm_ret_status pm_clock_disable(uint32_t clk_id);
-enum pm_ret_status pm_clock_get_state(uint32_t clk_id, uint32_t *state);
-enum pm_ret_status pm_clock_set_divider(uint32_t clk_id, uint32_t divider);
-enum pm_ret_status pm_clock_get_divider(uint32_t clk_id, uint32_t *divider);
-enum pm_ret_status pm_clock_set_parent(uint32_t clk_id, uint32_t parent);
-enum pm_ret_status pm_clock_get_parent(uint32_t clk_id, uint32_t *parent);
+					    uint32_t *value, uint32_t flag);
+enum pm_ret_status pm_clock_enable(uint32_t clk_id, uint32_t flag);
+enum pm_ret_status pm_clock_disable(uint32_t clk_id, uint32_t flag);
+enum pm_ret_status pm_clock_get_state(uint32_t clk_id, uint32_t *state,
+				      uint32_t flag);
+enum pm_ret_status pm_clock_set_divider(uint32_t clk_id, uint32_t divider,
+					uint32_t flag);
+enum pm_ret_status pm_clock_get_divider(uint32_t clk_id, uint32_t *divider,
+					uint32_t flag);
+enum pm_ret_status pm_clock_set_parent(uint32_t clk_id, uint32_t parent,
+				       uint32_t flag);
+enum pm_ret_status pm_clock_get_parent(uint32_t clk_id, uint32_t *parent,
+				       uint32_t flag);
+enum pm_ret_status pm_clock_get_rate(uint32_t clk_id, uint32_t *clk_rate,
+				     uint32_t flag);
 enum pm_ret_status pm_pll_set_param(uint32_t clk_id, uint32_t param,
-				    uint32_t value);
+				    uint32_t value, uint32_t flag);
 enum pm_ret_status pm_pll_get_param(uint32_t clk_id, uint32_t param,
-				    uint32_t *value);
-enum pm_ret_status pm_pll_set_mode(uint32_t clk_id, uint32_t mode);
-enum pm_ret_status pm_pll_get_mode(uint32_t clk_id, uint32_t *mode);
-enum pm_ret_status pm_force_powerdown(uint32_t target, uint8_t ack);
-enum pm_ret_status pm_system_shutdown(uint32_t type, uint32_t subtype);
+				    uint32_t *value, uint32_t flag);
+enum pm_ret_status pm_pll_set_mode(uint32_t clk_id, uint32_t mode,
+				   uint32_t flag);
+enum pm_ret_status pm_pll_get_mode(uint32_t clk_id, uint32_t *mode,
+				   uint32_t flag);
+enum pm_ret_status pm_force_powerdown(uint32_t target, uint8_t ack,
+				      uint32_t flag);
+enum pm_ret_status pm_system_shutdown(uint32_t type, uint32_t subtype,
+				      uint32_t flag);
 enum pm_ret_status pm_api_ioctl(uint32_t device_id, uint32_t ioctl_id,
-				uint32_t arg1, uint32_t arg2, uint32_t *value);
+				uint32_t arg1, uint32_t arg2, uint32_t *value,
+				uint32_t flag);
 enum pm_ret_status pm_query_data(uint32_t qid, uint32_t arg1, uint32_t arg2,
-				 uint32_t arg3, uint32_t *data);
+				 uint32_t arg3, uint32_t *data, uint32_t flag);
 unsigned int pm_get_shutdown_scope(void);
-enum pm_ret_status pm_get_chipid(uint32_t *value);
-enum pm_ret_status pm_feature_check(uint32_t api_id, unsigned int *version);
+enum pm_ret_status pm_get_chipid(uint32_t *value, uint32_t flag);
+enum pm_ret_status pm_feature_check(uint32_t api_id, unsigned int *version,
+				    uint32_t flag);
 enum pm_ret_status pm_load_pdi(uint32_t src, uint32_t address_low,
-			       uint32_t address_high);
+			       uint32_t address_high, uint32_t flag);
 enum pm_ret_status pm_get_op_characteristic(uint32_t device_id,
 					    enum pm_opchar_type type,
-					    uint32_t *result);
+					    uint32_t *result, uint32_t flag);
+enum pm_ret_status pm_set_max_latency(uint32_t device_id, uint32_t latency,
+				      uint32_t flag);
+enum pm_ret_status pm_register_notifier(uint32_t device_id, uint32_t event,
+					uint32_t wake, uint32_t enable,
+					uint32_t flag);
 #endif /* PM_API_SYS_H */
diff --git a/plat/xilinx/versal/pm_service/pm_client.c b/plat/xilinx/versal/pm_service/pm_client.c
index 5b47838..f6c3148 100644
--- a/plat/xilinx/versal/pm_service/pm_client.c
+++ b/plat/xilinx/versal/pm_service/pm_client.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Xilinx, Inc. All rights reserved.
+ * Copyright (c) 2019-2020, Xilinx, Inc. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -113,8 +113,9 @@
 /**
  * pm_client_set_wakeup_sources - Set all devices with enabled interrupts as
  *				  wake sources in the LibPM.
+ * @node_id:	Node id of processor
  */
-static void pm_client_set_wakeup_sources(void)
+static void pm_client_set_wakeup_sources(uint32_t node_id)
 {
 	uint32_t reg_num;
 	uint32_t device_id;
@@ -147,8 +148,9 @@
 			    (!pm_wakeup_nodes_set[node_idx])) {
 				/* Get device ID from node index */
 				device_id = PERIPH_DEVID(node_idx);
-				ret = pm_set_wakeup_source(XPM_DEVID_ACPU_0,
-							   device_id, 1);
+				ret = pm_set_wakeup_source(node_id,
+							   device_id, 1,
+							   SECURE_FLAG);
 				pm_wakeup_nodes_set[node_idx] = !ret;
 			}
 		}
@@ -167,7 +169,7 @@
 	bakery_lock_get(&pm_client_secure_lock);
 
 	if (state == PM_STATE_SUSPEND_TO_RAM)
-		pm_client_set_wakeup_sources();
+		pm_client_set_wakeup_sources(proc->node_id);
 
 	/* Set powerdown request */
 	mmio_write_32(FPD_APU_PWRCTL, mmio_read_32(FPD_APU_PWRCTL) |
diff --git a/plat/xilinx/versal/pm_service/pm_defs.h b/plat/xilinx/versal/pm_service/pm_defs.h
index 966b00b..ccb2617 100644
--- a/plat/xilinx/versal/pm_service/pm_defs.h
+++ b/plat/xilinx/versal/pm_service/pm_defs.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019, Xilinx, Inc. All rights reserved.
+ * Copyright (c) 2019-2020, Xilinx, Inc. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -39,10 +39,13 @@
 /* PM API Versions */
 #define PM_API_BASE_VERSION		1U
 
+#define PM_API_QUERY_DATA_VERSION	2U
+
 /* PM API ids */
 #define PM_GET_API_VERSION		1U
 #define PM_GET_DEVICE_STATUS		3U
 #define PM_GET_OP_CHARACTERISTIC	4U
+#define PM_REGISTER_NOTIFIER		5U
 #define PM_REQ_SUSPEND			6U
 #define PM_SELF_SUSPEND			7U
 #define PM_FORCE_POWERDOWN		8U
@@ -53,6 +56,7 @@
 #define PM_REQUEST_DEVICE		13U
 #define PM_RELEASE_DEVICE		14U
 #define PM_SET_REQUIREMENT		15U
+#define PM_SET_MAX_LATENCY		16U
 #define PM_RESET_ASSERT			17U
 #define PM_RESET_GET_STATUS		18U
 #define PM_INIT_FINALIZE		21U
@@ -88,6 +92,7 @@
 #define	IOCTL_GET_PLL_FRAC_MODE		9
 #define	IOCTL_SET_PLL_FRAC_DATA		10
 #define	IOCTL_GET_PLL_FRAC_DATA		11
+#define	IOCTL_SET_SGI			25
 
 /* Parameter ID for PLL IOCTLs */
 /* Fractional data portion for PLL */
@@ -163,4 +168,25 @@
 	PM_RET_ERROR_TIMEOUT = 2006,
 	PM_RET_ERROR_NODE_USED = 2007
 };
+
+/**
+ * Qids
+ */
+enum pm_query_id {
+	XPM_QID_INVALID,
+	XPM_QID_CLOCK_GET_NAME,
+	XPM_QID_CLOCK_GET_TOPOLOGY,
+	XPM_QID_CLOCK_GET_FIXEDFACTOR_PARAMS,
+	XPM_QID_CLOCK_GET_MUXSOURCES,
+	XPM_QID_CLOCK_GET_ATTRIBUTES,
+	XPM_QID_PINCTRL_GET_NUM_PINS,
+	XPM_QID_PINCTRL_GET_NUM_FUNCTIONS,
+	XPM_QID_PINCTRL_GET_NUM_FUNCTION_GROUPS,
+	XPM_QID_PINCTRL_GET_FUNCTION_NAME,
+	XPM_QID_PINCTRL_GET_FUNCTION_GROUPS,
+	XPM_QID_PINCTRL_GET_PIN_GROUPS,
+	XPM_QID_CLOCK_GET_NUM_CLOCKS,
+	XPM_QID_CLOCK_GET_MAX_DIVISOR,
+	XPM_QID_PLD_GET_PARENT,
+};
 #endif /* PM_DEFS_H */
diff --git a/plat/xilinx/versal/pm_service/pm_svc_main.c b/plat/xilinx/versal/pm_service/pm_svc_main.c
index 45b2803..87ba732 100644
--- a/plat/xilinx/versal/pm_service/pm_svc_main.c
+++ b/plat/xilinx/versal/pm_service/pm_svc_main.c
@@ -13,12 +13,64 @@
 #include <plat_private.h>
 #include <stdbool.h>
 #include <common/runtime_svc.h>
+#include <plat/common/platform.h>
 #include "pm_api_sys.h"
 #include "pm_client.h"
 #include "pm_ipi.h"
+#include <drivers/arm/gicv3.h>
+
+#define XSCUGIC_SGIR_EL1_INITID_SHIFT    24U
+#define INVALID_SGI    0xFF
+DEFINE_RENAME_SYSREG_RW_FUNCS(icc_asgi1r_el1, S3_0_C12_C11_6)
 
 /* pm_up = true - UP, pm_up = false - DOWN */
 static bool pm_up;
+static unsigned int sgi = INVALID_SGI;
+
+static uint64_t ipi_fiq_handler(uint32_t id, uint32_t flags, void *handle,
+				void *cookie)
+{
+	int cpu;
+	unsigned int reg;
+
+	(void)plat_ic_acknowledge_interrupt();
+	cpu = plat_my_core_pos() + 1;
+
+	if (sgi != INVALID_SGI) {
+		reg = (cpu | (sgi << XSCUGIC_SGIR_EL1_INITID_SHIFT));
+		write_icc_asgi1r_el1(reg);
+	}
+
+	/* Clear FIQ */
+	plat_ic_end_of_interrupt(id);
+
+	return 0;
+}
+
+/**
+ * pm_register_sgi() - PM register the IPI interrupt
+ *
+ * @sgi -  SGI number to be used for communication.
+ * @return	On success, the initialization function must return 0.
+ *		Any other return value will cause the framework to ignore
+ *		the service
+ *
+ * Update the SGI number to be used.
+ *
+ */
+int pm_register_sgi(unsigned int sgi_num)
+{
+	if (sgi != INVALID_SGI) {
+		return -EBUSY;
+	}
+
+	if (sgi_num >= GICV3_MAX_SGI_TARGETS) {
+		return -EINVAL;
+	}
+
+	sgi = sgi_num;
+	return 0;
+}
 
 /**
  * pm_setup() - PM service setup
@@ -46,6 +98,18 @@
 		pm_up = true;
 	}
 
+	/*
+	 * Enable IPI IRQ
+	 * assume the rich OS is OK to handle callback IRQs now.
+	 * Even if we were wrong, it would not enable the IRQ in
+	 * the GIC.
+	 */
+	pm_ipi_irq_enable(primary_proc);
+
+	ret = request_intr_type_el3(PLAT_VERSAL_IPI_IRQ, ipi_fiq_handler);
+	if (ret) {
+		WARN("BL31: registering IPI interrupt failed\n");
+	}
 	return ret;
 }
 
@@ -71,6 +135,7 @@
 	enum pm_ret_status ret;
 
 	uint32_t pm_arg[4];
+	uint32_t security_flag = SECURE_FLAG;
 
 	/* Handle case where PM wasn't initialized properly */
 	if (!pm_up)
@@ -81,57 +146,67 @@
 	pm_arg[2] = (uint32_t)x2;
 	pm_arg[3] = (uint32_t)(x2 >> 32);
 
+	/*
+	 * Mark BIT24 payload (i.e 1st bit of pm_arg[3] ) as non-secure (1)
+	 * if smc called is non secure
+	 */
+	if (is_caller_non_secure(flags)) {
+		security_flag = NON_SECURE_FLAG;
+	}
+
 	switch (smc_fid & FUNCID_NUM_MASK) {
 	/* PM API Functions */
 	case PM_SELF_SUSPEND:
 		ret = pm_self_suspend(pm_arg[0], pm_arg[1], pm_arg[2],
-				      pm_arg[3]);
+				      pm_arg[3], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_FORCE_POWERDOWN:
-		ret = pm_force_powerdown(pm_arg[0], pm_arg[1]);
+		ret = pm_force_powerdown(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_REQ_SUSPEND:
 		ret = pm_req_suspend(pm_arg[0], pm_arg[1], pm_arg[2],
-				     pm_arg[3]);
+				     pm_arg[3], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_ABORT_SUSPEND:
-		ret = pm_abort_suspend(pm_arg[0]);
+		ret = pm_abort_suspend(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_SYSTEM_SHUTDOWN:
-		ret = pm_system_shutdown(pm_arg[0], pm_arg[1]);
+		ret = pm_system_shutdown(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_REQ_WAKEUP:
-		ret = pm_req_wakeup(pm_arg[0], pm_arg[1], pm_arg[2], pm_arg[3]);
+		ret = pm_req_wakeup(pm_arg[0], pm_arg[1], pm_arg[2], pm_arg[3],
+				    security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_SET_WAKEUP_SOURCE:
-		ret = pm_set_wakeup_source(pm_arg[0], pm_arg[1], pm_arg[2]);
+		ret = pm_set_wakeup_source(pm_arg[0], pm_arg[1], pm_arg[2],
+					   security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_REQUEST_DEVICE:
 		ret = pm_request_device(pm_arg[0], pm_arg[1], pm_arg[2],
-					pm_arg[3]);
+					pm_arg[3], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_RELEASE_DEVICE:
-		ret = pm_release_device(pm_arg[0]);
+		ret = pm_release_device(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_SET_REQUIREMENT:
 		ret = pm_set_requirement(pm_arg[0], pm_arg[1], pm_arg[2],
-					 pm_arg[3]);
+					 pm_arg[3], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_GET_API_VERSION:
 	{
 		uint32_t api_version;
 
-		ret = pm_get_api_version(&api_version);
+		ret = pm_get_api_version(&api_version, security_flag);
 		SMC_RET1(handle, (uint64_t)PM_RET_SUCCESS |
 				 ((uint64_t)api_version << 32));
 	}
@@ -140,67 +215,72 @@
 	{
 		uint32_t buff[3];
 
-		ret = pm_get_device_status(pm_arg[0], buff);
+		ret = pm_get_device_status(pm_arg[0], buff, security_flag);
 		SMC_RET2(handle, (uint64_t)ret | ((uint64_t)buff[0] << 32),
 			 (uint64_t)buff[1] | ((uint64_t)buff[2] << 32));
 	}
 
 	case PM_RESET_ASSERT:
-		ret = pm_reset_assert(pm_arg[0], pm_arg[1]);
+		ret = pm_reset_assert(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_RESET_GET_STATUS:
 	{
 		uint32_t reset_status;
 
-		ret = pm_reset_get_status(pm_arg[0], &reset_status);
+		ret = pm_reset_get_status(pm_arg[0], &reset_status,
+					  security_flag);
 		SMC_RET1(handle, (uint64_t)ret |
 			 ((uint64_t)reset_status << 32));
 	}
 
 	case PM_INIT_FINALIZE:
-		SMC_RET1(handle, (uint64_t)PM_RET_SUCCESS);
+		ret = pm_init_finalize(security_flag);
+		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_GET_CALLBACK_DATA:
 	{
 		uint32_t result[4] = {0};
 
-		pm_get_callbackdata(result, ARRAY_SIZE(result));
+		pm_get_callbackdata(result, ARRAY_SIZE(result), security_flag);
 		SMC_RET2(handle,
 			 (uint64_t)result[0] | ((uint64_t)result[1] << 32),
 			 (uint64_t)result[2] | ((uint64_t)result[3] << 32));
 	}
 
 	case PM_PINCTRL_REQUEST:
-		ret = pm_pinctrl_request(pm_arg[0]);
+		ret = pm_pinctrl_request(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_PINCTRL_RELEASE:
-		ret = pm_pinctrl_release(pm_arg[0]);
+		ret = pm_pinctrl_release(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_PINCTRL_GET_FUNCTION:
 	{
 		uint32_t value = 0;
 
-		ret = pm_pinctrl_get_function(pm_arg[0], &value);
+		ret = pm_pinctrl_get_function(pm_arg[0], &value, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
 	case PM_PINCTRL_SET_FUNCTION:
-		ret = pm_pinctrl_set_function(pm_arg[0], pm_arg[1]);
+		ret = pm_pinctrl_set_function(pm_arg[0], pm_arg[1],
+					      security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_PINCTRL_CONFIG_PARAM_GET:
 	{
 		uint32_t value;
 
-		ret = pm_pinctrl_get_pin_param(pm_arg[0], pm_arg[1], &value);
+		ret = pm_pinctrl_get_pin_param(pm_arg[0], pm_arg[1], &value,
+					       security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
 	case PM_PINCTRL_CONFIG_PARAM_SET:
-		ret = pm_pinctrl_set_pin_param(pm_arg[0], pm_arg[1], pm_arg[2]);
+		ret = pm_pinctrl_set_pin_param(pm_arg[0], pm_arg[1], pm_arg[2],
+					       security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_IOCTL:
@@ -208,81 +288,93 @@
 		uint32_t value;
 
 		ret = pm_api_ioctl(pm_arg[0], pm_arg[1], pm_arg[2],
-				   pm_arg[3], &value);
+				   pm_arg[3], &value, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
 	case PM_QUERY_DATA:
 	{
-		uint32_t data[4] = { 0 };
+		uint32_t data[8] = { 0 };
 
 		ret = pm_query_data(pm_arg[0], pm_arg[1], pm_arg[2],
-			      pm_arg[3], data);
-		SMC_RET2(handle, (uint64_t)ret  | ((uint64_t)data[0] << 32),
-			 (uint64_t)data[1] | ((uint64_t)data[2] << 32));
-	}
+				      pm_arg[3], data, security_flag);
 
+		SMC_RET2(handle, (uint64_t)ret  | ((uint64_t)data[0] << 32),
+				 (uint64_t)data[1] | ((uint64_t)data[2] << 32));
+
+	}
 	case PM_CLOCK_ENABLE:
-		ret = pm_clock_enable(pm_arg[0]);
+		ret = pm_clock_enable(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_CLOCK_DISABLE:
-		ret = pm_clock_disable(pm_arg[0]);
+		ret = pm_clock_disable(pm_arg[0], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_CLOCK_GETSTATE:
 	{
 		uint32_t value;
 
-		ret = pm_clock_get_state(pm_arg[0], &value);
+		ret = pm_clock_get_state(pm_arg[0], &value, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
 	case PM_CLOCK_SETDIVIDER:
-		ret = pm_clock_set_divider(pm_arg[0], pm_arg[1]);
+		ret = pm_clock_set_divider(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_CLOCK_GETDIVIDER:
 	{
 		uint32_t value;
 
-		ret = pm_clock_get_divider(pm_arg[0], &value);
+		ret = pm_clock_get_divider(pm_arg[0], &value, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
 	case PM_CLOCK_SETPARENT:
-		ret = pm_clock_set_parent(pm_arg[0], pm_arg[1]);
+		ret = pm_clock_set_parent(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_CLOCK_GETPARENT:
 	{
 		uint32_t value;
 
-		ret = pm_clock_get_parent(pm_arg[0], &value);
+		ret = pm_clock_get_parent(pm_arg[0], &value, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
 	}
 
+	case PM_CLOCK_GETRATE:
+	{
+		uint32_t rate[2] = { 0 };
+
+		ret = pm_clock_get_rate(pm_arg[0], rate, security_flag);
+		SMC_RET2(handle, (uint64_t)ret | ((uint64_t)rate[0] << 32),
+			 rate[1]);
+	}
+
 	case PM_PLL_SET_PARAMETER:
-		ret = pm_pll_set_param(pm_arg[0], pm_arg[1], pm_arg[2]);
+		ret = pm_pll_set_param(pm_arg[0], pm_arg[1], pm_arg[2],
+				       security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_PLL_GET_PARAMETER:
 	{
 		uint32_t value;
 
-		ret = pm_pll_get_param(pm_arg[0], pm_arg[1], &value);
+		ret = pm_pll_get_param(pm_arg[0], pm_arg[1], &value,
+				       security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value << 32));
 	}
 
 	case PM_PLL_SET_MODE:
-		ret = pm_pll_set_mode(pm_arg[0], pm_arg[1]);
+		ret = pm_pll_set_mode(pm_arg[0], pm_arg[1], security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 
 	case PM_PLL_GET_MODE:
 	{
 		uint32_t mode;
 
-		ret = pm_pll_get_mode(pm_arg[0], &mode);
+		ret = pm_pll_get_mode(pm_arg[0], &mode, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)mode << 32));
 	}
 
@@ -294,7 +386,7 @@
 	{
 		uint32_t result[2];
 
-		ret = pm_get_chipid(result);
+		ret = pm_get_chipid(result, security_flag);
 		SMC_RET2(handle, (uint64_t)ret | ((uint64_t)result[0] << 32),
 			 result[1]);
 	}
@@ -303,13 +395,14 @@
 	{
 		uint32_t version;
 
-		ret = pm_feature_check(pm_arg[0], &version);
+		ret = pm_feature_check(pm_arg[0], &version, security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)version << 32));
 	}
 
 	case PM_LOAD_PDI:
 	{
-		ret = pm_load_pdi(pm_arg[0], pm_arg[1], pm_arg[2]);
+		ret = pm_load_pdi(pm_arg[0], pm_arg[1], pm_arg[2],
+				  security_flag);
 		SMC_RET1(handle, (uint64_t)ret);
 	}
 
@@ -317,10 +410,24 @@
 	{
 		uint32_t result;
 
-		ret = pm_get_op_characteristic(pm_arg[0], pm_arg[1], &result);
+		ret = pm_get_op_characteristic(pm_arg[0], pm_arg[1], &result,
+					       security_flag);
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)result << 32));
 	}
 
+	case PM_SET_MAX_LATENCY:
+	{
+		ret = pm_set_max_latency(pm_arg[0], pm_arg[1], security_flag);
+		SMC_RET1(handle, (uint64_t)ret);
+	}
+
+	case PM_REGISTER_NOTIFIER:
+	{
+		ret = pm_register_notifier(pm_arg[0], pm_arg[1], pm_arg[2],
+					   pm_arg[3], security_flag);
+		SMC_RET1(handle, (uint64_t)ret);
+	}
+
 	default:
 		WARN("Unimplemented PM Service Call: 0x%x\n", smc_fid);
 		SMC_RET1(handle, SMC_UNK);
diff --git a/plat/xilinx/versal/pm_service/pm_svc_main.h b/plat/xilinx/versal/pm_service/pm_svc_main.h
index 71329ca..4f8dc2b 100644
--- a/plat/xilinx/versal/pm_service/pm_svc_main.h
+++ b/plat/xilinx/versal/pm_service/pm_svc_main.h
@@ -14,4 +14,5 @@
 			uint64_t x4, void *cookie, void *handle,
 			uint64_t flags);
 
+int pm_register_sgi(unsigned int sgi_num);
 #endif /* PM_SVC_MAIN_H */
diff --git a/plat/xilinx/zynqmp/aarch64/zynqmp_common.c b/plat/xilinx/zynqmp/aarch64/zynqmp_common.c
index d6313a6..fae73cf 100644
--- a/plat/xilinx/zynqmp/aarch64/zynqmp_common.c
+++ b/plat/xilinx/zynqmp/aarch64/zynqmp_common.c
@@ -62,144 +62,151 @@
 } zynqmp_devices[] = {
 	{
 		.id = 0x10,
-		.name = "3EG",
+		.name = "XCZU3EG",
 	},
 	{
 		.id = 0x10,
 		.ver = 0x2c,
-		.name = "3CG",
+		.name = "XCZU3CG",
 	},
 	{
 		.id = 0x11,
-		.name = "2EG",
+		.name = "XCZU2EG",
 	},
 	{
 		.id = 0x11,
 		.ver = 0x2c,
-		.name = "2CG",
+		.name = "XCZU2CG",
 	},
 	{
 		.id = 0x20,
-		.name = "5EV",
+		.name = "XCZU5EV",
 		.evexists = true,
 	},
 	{
 		.id = 0x20,
 		.ver = 0x100,
-		.name = "5EG",
+		.name = "XCZU5EG",
 		.evexists = true,
 	},
 	{
 		.id = 0x20,
 		.ver = 0x12c,
-		.name = "5CG",
+		.name = "XCZU5CG",
 	},
 	{
 		.id = 0x21,
-		.name = "4EV",
+		.name = "XCZU4EV",
 		.evexists = true,
 	},
 	{
 		.id = 0x21,
 		.ver = 0x100,
-		.name = "4EG",
+		.name = "XCZU4EG",
 		.evexists = true,
 	},
 	{
 		.id = 0x21,
 		.ver = 0x12c,
-		.name = "4CG",
+		.name = "XCZU4CG",
 	},
 	{
 		.id = 0x30,
-		.name = "7EV",
+		.name = "XCZU7EV",
 		.evexists = true,
 	},
 	{
 		.id = 0x30,
 		.ver = 0x100,
-		.name = "7EG",
+		.name = "XCZU7EG",
 		.evexists = true,
 	},
 	{
 		.id = 0x30,
 		.ver = 0x12c,
-		.name = "7CG",
+		.name = "XCZU7CG",
 	},
 	{
 		.id = 0x38,
-		.name = "9EG",
+		.name = "XCZU9EG",
 	},
 	{
 		.id = 0x38,
 		.ver = 0x2c,
-		.name = "9CG",
+		.name = "XCZU9CG",
 	},
 	{
 		.id = 0x39,
-		.name = "6EG",
+		.name = "XCZU6EG",
 	},
 	{
 		.id = 0x39,
 		.ver = 0x2c,
-		.name = "6CG",
+		.name = "XCZU6CG",
 	},
 	{
 		.id = 0x40,
-		.name = "11EG",
-	},
-	{ /* For testing purpose only */
-		.id = 0x50,
-		.ver = 0x2c,
-		.name = "15CG",
+		.name = "XCZU11EG",
 	},
 	{
 		.id = 0x50,
-		.name = "15EG",
+		.name = "XCZU15EG",
 	},
 	{
 		.id = 0x58,
-		.name = "19EG",
+		.name = "XCZU19EG",
 	},
 	{
 		.id = 0x59,
-		.name = "17EG",
+		.name = "XCZU17EG",
 	},
 	{
 		.id = 0x60,
-		.name = "28DR",
+		.name = "XCZU28DR",
 	},
 	{
 		.id = 0x61,
-		.name = "21DR",
+		.name = "XCZU21DR",
 	},
 	{
 		.id = 0x62,
-		.name = "29DR",
+		.name = "XCZU29DR",
 	},
 	{
 		.id = 0x63,
-		.name = "23DR",
+		.name = "XCZU23DR",
 	},
 	{
 		.id = 0x64,
-		.name = "27DR",
+		.name = "XCZU27DR",
 	},
 	{
 		.id = 0x65,
-		.name = "25DR",
+		.name = "XCZU25DR",
 	},
 	{
 		.id = 0x66,
-		.name = "39DR",
+		.name = "XCZU39DR",
+	},
+	{
+		.id = 0x7d,
+		.name = "XCZU43DR",
+	},
+	{
+		.id = 0x78,
+		.name = "XCZU46DR",
+	},
+	{
+		.id = 0x7f,
+		.name = "XCZU47DR",
 	},
 	{
 		.id = 0x7b,
-		.name = "48DR",
+		.name = "XCZU48DR",
 	},
 	{
 		.id = 0x7e,
-		.name = "49DR",
+		.name = "XCZU49DR",
 	},
 };
 
@@ -207,6 +214,8 @@
 #define ZYNQMP_PL_STATUS_MASK	BIT(ZYNQMP_PL_STATUS_BIT)
 #define ZYNQMP_CSU_VERSION_MASK	~(ZYNQMP_PL_STATUS_MASK)
 
+#define SILICON_ID_XCK26       0x4724093
+
 static char *zynqmp_get_silicon_idcode_name(void)
 {
 	uint32_t id, ver, chipid[2];
@@ -224,7 +233,7 @@
 	chipid[1] = mmio_read_32(EFUSE_BASEADDR + EFUSE_IPDISABLE_OFFSET);
 #else
 	if (pm_get_chipid(chipid) != PM_RET_SUCCESS)
-		return "UNKN";
+		return "XCZUUNKN";
 #endif
 
 	id = chipid[0] & (ZYNQMP_CSU_IDCODE_DEVICE_CODE_MASK |
@@ -238,8 +247,13 @@
 			break;
 	}
 
-	if (i >= ARRAY_SIZE(zynqmp_devices))
-		return "UNKN";
+	if (i >= ARRAY_SIZE(zynqmp_devices)) {
+		if (chipid[0] == SILICON_ID_XCK26) {
+			return "XCK26";
+		} else {
+			return "XCZUUNKN";
+		}
+	}
 
 	if (!zynqmp_devices[i].evexists)
 		return zynqmp_devices[i].name;
@@ -315,9 +329,10 @@
 		break;
 	}
 
-	NOTICE("ATF running on XCZU%s/%s v%d/RTL%d.%d at 0x%x\n",
-	       zynqmp_print_silicon_idcode(), label, zynqmp_get_ps_ver(),
-	       (rtl & 0xf0) >> 4, rtl & 0xf, BL31_BASE);
+	NOTICE("TF-A running on %s/%s at 0x%x\n",
+	       zynqmp_print_silicon_idcode(), label, BL31_BASE);
+	VERBOSE("TF-A running on v%d/RTL%d.%d\n",
+	       zynqmp_get_ps_ver(), (rtl & 0xf0) >> 4, rtl & 0xf);
 }
 #else
 static inline void zynqmp_print_platform_name(void) { }
@@ -338,10 +353,19 @@
 
 void zynqmp_config_setup(void)
 {
+	uint64_t counter_freq;
+
 	/* Configure IPI data for ZynqMP */
 	zynqmp_ipi_config_table_init();
 
 	zynqmp_print_platform_name();
+
+	/* Configure counter frequency */
+	counter_freq = read_cntfrq_el0();
+	if (counter_freq == ZYNQMP_DEFAULT_COUNTER_FREQ) {
+		write_cntfrq_el0(plat_get_syscnt_freq2());
+	}
+
 	generic_delay_timer_init();
 }
 
diff --git a/plat/xilinx/zynqmp/aarch64/zynqmp_helpers.S b/plat/xilinx/zynqmp/aarch64/zynqmp_helpers.S
index 7eab337..d8439f7 100644
--- a/plat/xilinx/zynqmp/aarch64/zynqmp_helpers.S
+++ b/plat/xilinx/zynqmp/aarch64/zynqmp_helpers.S
@@ -12,9 +12,6 @@
 	.globl	plat_is_my_cpu_primary
 	.globl	zynqmp_calc_core_pos
 	.globl	plat_my_core_pos
-	.globl	plat_crash_console_init
-	.globl	plat_crash_console_putc
-	.globl	plat_crash_console_flush
 	.globl	platform_mem_init
 
 	/* -----------------------------------------------------
@@ -79,45 +76,6 @@
 	ret
 endfunc zynqmp_calc_core_pos
 
-	/* ---------------------------------------------
-	 * int plat_crash_console_init(void)
-	 * Function to initialize the crash console
-	 * without a C Runtime to print crash report.
-	 * Clobber list : x0 - x4
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_init
-	mov_imm	x0, ZYNQMP_CRASH_UART_BASE
-	mov_imm	x1, ZYNQMP_CRASH_UART_CLK_IN_HZ
-	mov_imm	x2, ZYNQMP_UART_BAUDRATE
-	b	console_cdns_core_init
-endfunc plat_crash_console_init
-
-	/* ---------------------------------------------
-	 * int plat_crash_console_putc(int c)
-	 * Function to print a character on the crash
-	 * console without a C Runtime.
-	 * Clobber list : x1, x2
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_putc
-	mov_imm	x1, ZYNQMP_CRASH_UART_BASE
-	b	console_cdns_core_putc
-endfunc plat_crash_console_putc
-
-	/* ---------------------------------------------
-	 * void plat_crash_console_flush()
-	 * Function to force a write of all buffered
-	 * data that hasn't been output.
-	 * Out : void.
-	 * Clobber list : r0
-	 * ---------------------------------------------
-	 */
-func plat_crash_console_flush
-	mov_imm	x0, ZYNQMP_CRASH_UART_BASE
-	b	console_cdns_core_flush
-endfunc plat_crash_console_flush
-
 	/* ---------------------------------------------------------------------
 	 * We don't need to carry out any memory initialization on ARM
 	 * platforms. The Secure RAM is accessible straight away.
diff --git a/plat/xilinx/zynqmp/bl31_zynqmp_setup.c b/plat/xilinx/zynqmp/bl31_zynqmp_setup.c
index b6d8770..47be4e1 100644
--- a/plat/xilinx/zynqmp/bl31_zynqmp_setup.c
+++ b/plat/xilinx/zynqmp/bl31_zynqmp_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,6 +10,7 @@
 #include <bl31/bl31.h>
 #include <common/bl_common.h>
 #include <common/debug.h>
+#include <drivers/arm/dcc.h>
 #include <drivers/console.h>
 #include <plat/arm/common/plat_arm.h>
 #include <plat/common/platform.h>
@@ -19,6 +20,10 @@
 #include <plat_private.h>
 #include <zynqmp_def.h>
 
+#include <common/fdt_fixup.h>
+#include <common/fdt_wrappers.h>
+#include <libfdt.h>
+
 static entry_point_info_t bl32_image_ep_info;
 static entry_point_info_t bl33_image_ep_info;
 
@@ -32,8 +37,9 @@
 {
 	assert(sec_state_is_valid(type));
 
-	if (type == NON_SECURE)
+	if (type == NON_SECURE) {
 		return &bl33_image_ep_info;
+	}
 
 	return &bl32_image_ep_info;
 }
@@ -61,15 +67,23 @@
 				u_register_t arg2, u_register_t arg3)
 {
 	uint64_t atf_handoff_addr;
-	/* Register the console to provide early debug support */
-	static console_t bl31_boot_console;
-	(void)console_cdns_register(ZYNQMP_UART_BASE,
-				       zynqmp_get_uart_clk(),
-				       ZYNQMP_UART_BAUDRATE,
-				       &bl31_boot_console);
-	console_set_scope(&bl31_boot_console,
-			  CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_BOOT);
 
+	if (ZYNQMP_CONSOLE_IS(cadence)) {
+		/* Register the console to provide early debug support */
+		static console_t bl31_boot_console;
+		(void)console_cdns_register(ZYNQMP_UART_BASE,
+					       zynqmp_get_uart_clk(),
+					       ZYNQMP_UART_BAUDRATE,
+					       &bl31_boot_console);
+		console_set_scope(&bl31_boot_console,
+				  CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_BOOT);
+	} else if (ZYNQMP_CONSOLE_IS(dcc)) {
+		/* Initialize the dcc console for debug */
+		int rc = console_dcc_register();
+		if (rc == 0) {
+			panic();
+		}
+	}
 	/* Initialize the platform config for future decision making */
 	zynqmp_config_setup();
 
@@ -99,47 +113,34 @@
 		enum fsbl_handoff ret = fsbl_atf_handover(&bl32_image_ep_info,
 							  &bl33_image_ep_info,
 							  atf_handoff_addr);
-		if (ret == FSBL_HANDOFF_NO_STRUCT)
+		if (ret == FSBL_HANDOFF_NO_STRUCT) {
 			bl31_set_default_config();
-		else if (ret != FSBL_HANDOFF_SUCCESS)
+		} else if (ret != FSBL_HANDOFF_SUCCESS) {
 			panic();
+		}
 	}
-
-	NOTICE("BL31: Secure code at 0x%lx\n", bl32_image_ep_info.pc);
-	NOTICE("BL31: Non secure code at 0x%lx\n", bl33_image_ep_info.pc);
+	if (bl32_image_ep_info.pc) {
+		VERBOSE("BL31: Secure code at 0x%lx\n", bl32_image_ep_info.pc);
+	}
+	if (bl33_image_ep_info.pc) {
+		VERBOSE("BL31: Non secure code at 0x%lx\n", bl33_image_ep_info.pc);
+	}
 }
 
-/* Enable the test setup */
-#ifndef ZYNQMP_TESTING
-static void zynqmp_testing_setup(void) { }
-#else
-static void zynqmp_testing_setup(void)
-{
-	uint32_t actlr_el3, actlr_el2;
-
-	/* Enable CPU ACTLR AND L2ACTLR RW access from non-secure world */
-	actlr_el3 = read_actlr_el3();
-	actlr_el2 = read_actlr_el2();
-
-	actlr_el3 |= ACTLR_EL3_L2ACTLR_BIT | ACTLR_EL3_CPUACTLR_BIT;
-	actlr_el2 |= ACTLR_EL3_L2ACTLR_BIT | ACTLR_EL3_CPUACTLR_BIT;
-	write_actlr_el3(actlr_el3);
-	write_actlr_el2(actlr_el2);
-}
-#endif
-
 #if ZYNQMP_WDT_RESTART
 static interrupt_type_handler_t type_el3_interrupt_table[MAX_INTR_EL3];
 
 int request_intr_type_el3(uint32_t id, interrupt_type_handler_t handler)
 {
 	/* Validate 'handler' and 'id' parameters */
-	if (!handler || id >= MAX_INTR_EL3)
+	if (!handler || id >= MAX_INTR_EL3) {
 		return -EINVAL;
+	}
 
 	/* Check if a handler has already been registered */
-	if (type_el3_interrupt_table[id])
+	if (type_el3_interrupt_table[id]) {
 		return -EALREADY;
+	}
 
 	type_el3_interrupt_table[id] = handler;
 
@@ -154,19 +155,66 @@
 
 	intr_id = plat_ic_get_pending_interrupt_id();
 	handler = type_el3_interrupt_table[intr_id];
-	if (handler != NULL)
+	if (handler != NULL) {
 		handler(intr_id, flags, handle, cookie);
+	}
 
 	return 0;
 }
 #endif
 
+#if (BL31_LIMIT < PLAT_DDR_LOWMEM_MAX)
+static void prepare_dtb(void)
+{
+	void *dtb = (void *)XILINX_OF_BOARD_DTB_ADDR;
+	int ret;
+
+	/* Return if no device tree is detected */
+	if (fdt_check_header(dtb) != 0) {
+		NOTICE("Can't read DT at 0x%p\n", dtb);
+		return;
+	}
+
+	ret = fdt_open_into(dtb, dtb, XILINX_OF_BOARD_DTB_MAX_SIZE);
+	if (ret < 0) {
+		ERROR("Invalid Device Tree at %p: error %d\n", dtb, ret);
+		return;
+	}
+
+	if (dt_add_psci_node(dtb)) {
+		ERROR("Failed to add PSCI Device Tree node\n");
+		return;
+	}
+
+	if (dt_add_psci_cpu_enable_methods(dtb)) {
+		ERROR("Failed to add PSCI cpu enable methods in Device Tree\n");
+		return;
+	}
+
+	/* Reserve memory used by Trusted Firmware. */
+	if (fdt_add_reserved_memory(dtb, "tf-a", BL31_BASE, BL31_LIMIT - BL31_BASE)) {
+		WARN("Failed to add reserved memory nodes to DT.\n");
+	}
+
+	ret = fdt_pack(dtb);
+	if (ret < 0) {
+		ERROR("Failed to pack Device Tree at %p: error %d\n", dtb, ret);
+	}
+
+	clean_dcache_range((uintptr_t)dtb, fdt_blob_size(dtb));
+	INFO("Changed device tree to advertise PSCI and reserved memories.\n");
+}
+#endif
+
 void bl31_platform_setup(void)
 {
+#if (BL31_LIMIT < PLAT_DDR_LOWMEM_MAX)
+		prepare_dtb();
+#endif
+
 	/* Initialize the gic cpu and distributor interfaces */
 	plat_arm_gic_driver_init();
 	plat_arm_gic_init();
-	zynqmp_testing_setup();
 }
 
 void bl31_plat_runtime_setup(void)
@@ -178,8 +226,9 @@
 	set_interrupt_rm_flag(flags, NON_SECURE);
 	rc = register_interrupt_type_handler(INTR_TYPE_EL3,
 					     rdo_el3_interrupt_handler, flags);
-	if (rc)
+	if (rc) {
 		panic();
+	}
 #endif
 }
 
@@ -193,6 +242,10 @@
 
 
 	const mmap_region_t bl_regions[] = {
+#if (BL31_LIMIT < PLAT_DDR_LOWMEM_MAX)
+		MAP_REGION_FLAT(XILINX_OF_BOARD_DTB_ADDR, XILINX_OF_BOARD_DTB_MAX_SIZE,
+			MT_MEMORY | MT_RW | MT_NS),
+#endif
 		MAP_REGION_FLAT(BL31_BASE, BL31_END - BL31_BASE,
 			MT_MEMORY | MT_RW | MT_SECURE),
 		MAP_REGION_FLAT(BL_CODE_BASE, BL_CODE_END - BL_CODE_BASE,
diff --git a/plat/xilinx/zynqmp/include/plat_pm_common.h b/plat/xilinx/zynqmp/include/plat_pm_common.h
index 56a747a..a57aebe 100644
--- a/plat/xilinx/zynqmp/include/plat_pm_common.h
+++ b/plat/xilinx/zynqmp/include/plat_pm_common.h
@@ -16,17 +16,6 @@
 #include <common/debug.h>
 #include "pm_defs.h"
 
-#if ZYNQMP_IPI_CRC_CHECK
-#define PAYLOAD_ARG_CNT         8U
-#define IPI_W0_TO_W6_SIZE       28U
-#define PAYLOAD_CRC_POS         7U
-#define CRC_INIT_VALUE          0x4F4EU
-#define CRC_ORDER               16U
-#define CRC_POLYNOM             0x8005U
-#else
-#define PAYLOAD_ARG_CNT         6U
-#endif
-#define PAYLOAD_ARG_SIZE	4U	/* size in bytes */
 
 #define ZYNQMP_TZ_VERSION_MAJOR		1
 #define ZYNQMP_TZ_VERSION_MINOR		0
diff --git a/plat/xilinx/zynqmp/include/platform_def.h b/plat/xilinx/zynqmp/include/platform_def.h
index 2796840..0c14315 100644
--- a/plat/xilinx/zynqmp/include/platform_def.h
+++ b/plat/xilinx/zynqmp/include/platform_def.h
@@ -36,7 +36,7 @@
  * little space for growth.
  */
 #ifndef ZYNQMP_ATF_MEM_BASE
-#if !DEBUG && defined(SPD_none)
+#if !DEBUG && defined(SPD_none) && !SDEI_SUPPORT
 # define BL31_BASE			0xfffea000
 # define BL31_LIMIT			0xffffffff
 #else
@@ -83,14 +83,29 @@
 /*******************************************************************************
  * Platform specific page table and MMU setup constants
  ******************************************************************************/
+#define XILINX_OF_BOARD_DTB_ADDR	0x100000
+#define XILINX_OF_BOARD_DTB_MAX_SIZE	0x200000
+#define PLAT_DDR_LOWMEM_MAX		0x80000000
+
 #define PLAT_PHY_ADDR_SPACE_SIZE	(1ULL << 32)
 #define PLAT_VIRT_ADDR_SPACE_SIZE	(1ULL << 32)
+#if (BL31_LIMIT < PLAT_DDR_LOWMEM_MAX)
+#define MAX_MMAP_REGIONS		8
+#else
 #define MAX_MMAP_REGIONS		7
+#endif
 #define MAX_XLAT_TABLES			5
 
 #define CACHE_WRITEBACK_SHIFT   6
 #define CACHE_WRITEBACK_GRANULE (1 << CACHE_WRITEBACK_SHIFT)
 
+#define ZYNQMP_SDEI_SGI_PRIVATE		U(8)
+
+/* Platform macros to support exception handling framework */
+#define PLAT_PRI_BITS			U(3)
+#define PLAT_SDEI_CRITICAL_PRI		0x10
+#define PLAT_SDEI_NORMAL_PRI		0x20
+
 #define PLAT_ARM_GICD_BASE	BASE_GICD_BASE
 #define PLAT_ARM_GICC_BASE	BASE_GICC_BASE
 /*
@@ -102,8 +117,6 @@
 #define PLAT_ARM_G1S_IRQ_PROPS(grp) \
 	INTR_PROP_DESC(ARM_IRQ_SEC_PHY_TIMER, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_LEVEL), \
-	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_0, GIC_HIGHEST_SEC_PRIORITY, grp, \
-			GIC_INTR_CFG_EDGE), \
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_1, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_EDGE), \
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_2, GIC_HIGHEST_SEC_PRIORITY, grp, \
@@ -124,8 +137,6 @@
 			GIC_INTR_CFG_LEVEL), \
 	INTR_PROP_DESC(IRQ_TTC3_1, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_EDGE), \
-	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_0, GIC_HIGHEST_SEC_PRIORITY, grp, \
-			GIC_INTR_CFG_EDGE), \
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_1, GIC_HIGHEST_SEC_PRIORITY, grp, \
 			GIC_INTR_CFG_EDGE), \
 	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_2, GIC_HIGHEST_SEC_PRIORITY, grp, \
@@ -142,6 +153,8 @@
 			GIC_INTR_CFG_EDGE)
 #endif
 
-#define PLAT_ARM_G0_IRQ_PROPS(grp)
+#define PLAT_ARM_G0_IRQ_PROPS(grp) \
+	INTR_PROP_DESC(ARM_IRQ_SEC_SGI_0, PLAT_SDEI_NORMAL_PRI,	grp, \
+			GIC_INTR_CFG_EDGE)
 
 #endif /* PLATFORM_DEF_H */
diff --git a/plat/xilinx/zynqmp/include/zynqmp_def.h b/plat/xilinx/zynqmp/include/zynqmp_def.h
index 5e7254e..7e58391 100644
--- a/plat/xilinx/zynqmp/include/zynqmp_def.h
+++ b/plat/xilinx/zynqmp/include/zynqmp_def.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -17,6 +17,9 @@
 
 #define ZYNQMP_CONSOLE_IS(con)	(ZYNQMP_CONSOLE_ID_ ## con == ZYNQMP_CONSOLE)
 
+/* Default counter frequency */
+#define ZYNQMP_DEFAULT_COUNTER_FREQ	0U
+
 /* Firmware Image Package */
 #define ZYNQMP_PRIMARY_CPU		0
 
@@ -341,12 +344,22 @@
 #define PGGS_BASEADDR		(0xFFD80050U)
 #define PGGS_NUM_REGS		U(4)
 
-/* Warm restart boot health status register and mask */
-#define PM_BOOT_HEALTH_STATUS_REG		(GGS_BASEADDR + U(0x10))
+/* PMU GGS4 register 4 is used for warm restart boot health status */
+#define PMU_GLOBAL_GEN_STORAGE4			(GGS_BASEADDR + 0x10)
+/* Warm restart boot health status mask */
 #define PM_BOOT_HEALTH_STATUS_MASK		U(0x01)
+/* WDT restart scope shift and mask */
+#define RESTART_SCOPE_SHIFT			(3)
+#define RESTART_SCOPE_MASK			(0x3U << RESTART_SCOPE_SHIFT)
 
 /*AFI registers */
 #define  AFIFM6_WRCTRL		U(13)
 #define  FABRIC_WIDTH		U(3)
 
+/* CSUDMA Module Base Address*/
+#define CSUDMA_BASE		0xFFC80000
+
+/* RSA-CORE Module Base Address*/
+#define RSA_CORE_BASE		0xFFCE0000
+
 #endif /* ZYNQMP_DEF_H */
diff --git a/plat/xilinx/zynqmp/plat_psci.c b/plat/xilinx/zynqmp/plat_psci.c
index f579f79..f78b88c 100644
--- a/plat/xilinx/zynqmp/plat_psci.c
+++ b/plat/xilinx/zynqmp/plat_psci.c
@@ -179,14 +179,6 @@
 	return PSCI_E_SUCCESS;
 }
 
-int zynqmp_validate_ns_entrypoint(unsigned long ns_entrypoint)
-{
-	VERBOSE("%s: ns_entrypoint: 0x%lx\n", __func__, ns_entrypoint);
-
-	/* FIXME: Actually validate */
-	return PSCI_E_SUCCESS;
-}
-
 void zynqmp_get_sys_suspend_power_state(psci_power_state_t *req_state)
 {
 	req_state->pwr_domain_state[PSCI_CPU_PWR_LVL] = PLAT_MAX_OFF_STATE;
@@ -206,7 +198,6 @@
 	.system_off			= zynqmp_system_off,
 	.system_reset			= zynqmp_system_reset,
 	.validate_power_state		= zynqmp_validate_power_state,
-	.validate_ns_entrypoint		= zynqmp_validate_ns_entrypoint,
 	.get_sys_suspend_power_state	= zynqmp_get_sys_suspend_power_state,
 };
 
diff --git a/plat/xilinx/zynqmp/plat_zynqmp.c b/plat/xilinx/zynqmp/plat_zynqmp.c
index 906ce1b..58a52a3 100644
--- a/plat/xilinx/zynqmp/plat_zynqmp.c
+++ b/plat/xilinx/zynqmp/plat_zynqmp.c
@@ -9,11 +9,13 @@
 
 int plat_core_pos_by_mpidr(u_register_t mpidr)
 {
-	if (mpidr & MPIDR_CLUSTER_MASK)
+	if (mpidr & MPIDR_CLUSTER_MASK) {
 		return -1;
+	}
 
-	if ((mpidr & MPIDR_CPU_MASK) >= PLATFORM_CORE_COUNT)
+	if ((mpidr & MPIDR_CPU_MASK) >= PLATFORM_CORE_COUNT) {
 		return -1;
+	}
 
 	return zynqmp_calc_core_pos(mpidr);
 }
diff --git a/plat/xilinx/zynqmp/platform.mk b/plat/xilinx/zynqmp/platform.mk
index 44f20f6..d075a56 100644
--- a/plat/xilinx/zynqmp/platform.mk
+++ b/plat/xilinx/zynqmp/platform.mk
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 
@@ -9,11 +9,13 @@
 A53_DISABLE_NON_TEMPORAL_HINT := 0
 SEPARATE_CODE_AND_RODATA := 1
 ZYNQMP_WDT_RESTART := 0
-ZYNQMP_IPI_CRC_CHECK := 0
+IPI_CRC_CHECK := 0
 override RESET_TO_BL31 := 1
 override GICV2_G0_FOR_EL3 := 1
 override WARMBOOT_ENABLE_DCACHE_EARLY := 1
 
+EL3_EXCEPTION_HANDLING := $(SDEI_SUPPORT)
+
 # Do not enable SVE
 ENABLE_SVE_FOR_NS	:= 0
 
@@ -41,15 +43,17 @@
     $(eval $(call add_define,ZYNQMP_BL32_MEM_SIZE))
 endif
 
-ZYNQMP_CONSOLE	?=	cadence
-$(eval $(call add_define_val,ZYNQMP_CONSOLE,ZYNQMP_CONSOLE_ID_${ZYNQMP_CONSOLE}))
 
 ifdef ZYNQMP_WDT_RESTART
 $(eval $(call add_define,ZYNQMP_WDT_RESTART))
 endif
 
 ifdef ZYNQMP_IPI_CRC_CHECK
-    $(eval $(call add_define,ZYNQMP_IPI_CRC_CHECK))
+  $(warning "ZYNQMP_IPI_CRC_CHECK macro is deprecated...instead please use IPI_CRC_CHECK.")
+endif
+
+ifdef IPI_CRC_CHECK
+    $(eval $(call add_define,IPI_CRC_CHECK))
 endif
 
 PLAT_INCLUDES		:=	-Iinclude/plat/arm/common/			\
@@ -59,27 +63,40 @@
 				-Iplat/xilinx/zynqmp/include/			\
 				-Iplat/xilinx/zynqmp/pm_service/		\
 
+include lib/libfdt/libfdt.mk
+# Include GICv2 driver files
+include drivers/arm/gic/v2/gicv2.mk
+
 PLAT_BL_COMMON_SOURCES	:=	lib/xlat_tables/xlat_tables_common.c		\
 				lib/xlat_tables/aarch64/xlat_tables.c		\
+				drivers/arm/dcc/dcc_console.c			\
 				drivers/delay_timer/delay_timer.c		\
 				drivers/delay_timer/generic_delay_timer.c	\
-				drivers/arm/gic/common/gic_common.c		\
-				drivers/arm/gic/v2/gicv2_main.c			\
-				drivers/arm/gic/v2/gicv2_helpers.c		\
+				${GICV2_SOURCES}				\
 				drivers/cadence/uart/aarch64/cdns_console.S	\
 				plat/arm/common/arm_cci.c			\
 				plat/arm/common/arm_common.c			\
 				plat/arm/common/arm_gicv2.c			\
 				plat/common/plat_gicv2.c			\
 				plat/xilinx/common/ipi.c			\
-				plat/xilinx/zynqmp/zynqmp_ipi.c		\
+				plat/xilinx/zynqmp/zynqmp_ipi.c			\
+				plat/common/aarch64/crash_console_helpers.S	\
 				plat/xilinx/zynqmp/aarch64/zynqmp_helpers.S	\
 				plat/xilinx/zynqmp/aarch64/zynqmp_common.c
 
+ZYNQMP_CONSOLE	?=	cadence
+ifeq (${ZYNQMP_CONSOLE}, $(filter ${ZYNQMP_CONSOLE},cadence cadence0 cadence1 dcc))
+else
+  $(error "Please define ZYNQMP_CONSOLE")
+endif
+$(eval $(call add_define_val,ZYNQMP_CONSOLE,ZYNQMP_CONSOLE_ID_${ZYNQMP_CONSOLE}))
+
 BL31_SOURCES		+=	drivers/arm/cci/cci.c				\
 				lib/cpus/aarch64/aem_generic.S			\
 				lib/cpus/aarch64/cortex_a53.S			\
 				plat/common/plat_psci_common.c			\
+				common/fdt_fixup.c				\
+				${LIBFDT_SRCS}					\
 				plat/xilinx/common/ipi_mailbox_service/ipi_mailbox_svc.c \
 				plat/xilinx/common/pm_service/pm_ipi.c		\
 				plat/xilinx/common/plat_startup.c		\
@@ -95,6 +112,13 @@
 				plat/xilinx/zynqmp/pm_service/pm_api_clock.c	\
 				plat/xilinx/zynqmp/pm_service/pm_client.c
 
+ifeq (${SDEI_SUPPORT},1)
+BL31_SOURCES		+=	plat/xilinx/zynqmp/zynqmp_ehf.c			\
+				plat/xilinx/zynqmp/zynqmp_sdei.c
+endif
+
+BL31_CPPFLAGS		+=	-fno-jump-tables
+
 ifneq (${RESET_TO_BL31},1)
   $(error "Using BL31 as the reset vector is only one option supported on ZynqMP. Please set RESET_TO_BL31 to 1.")
 endif
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_clock.c b/plat/xilinx/zynqmp/pm_service/pm_api_clock.c
index 852f927..0cc517e 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_clock.c
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_clock.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -129,11 +129,11 @@
 		.div = NA_DIV,				\
 	}
 
-#define GENERIC_DIV(id)						\
+#define GENERIC_DIV1						\
 	{							\
-		.type = TYPE_DIV##id,				\
-		.offset = PERIPH_DIV##id##_SHIFT,		\
-		.width = PERIPH_DIV##id##_WIDTH,		\
+		.type = TYPE_DIV1,				\
+		.offset = PERIPH_DIV1_SHIFT,			\
+		.width = PERIPH_DIV1_WIDTH,			\
 		.clkflags = CLK_SET_RATE_NO_REPARENT |		\
 			    CLK_IS_BASIC,			\
 		.typeflags = CLK_DIVIDER_ONE_BASED |		\
@@ -142,6 +142,20 @@
 		.div = NA_DIV,					\
 	}
 
+#define GENERIC_DIV2						\
+	{							\
+		.type = TYPE_DIV2,				\
+		.offset = PERIPH_DIV2_SHIFT,			\
+		.width = PERIPH_DIV2_WIDTH,			\
+		.clkflags = CLK_SET_RATE_NO_REPARENT |		\
+			    CLK_SET_RATE_PARENT |		\
+			    CLK_IS_BASIC,			\
+		.typeflags = CLK_DIVIDER_ONE_BASED |		\
+			     CLK_DIVIDER_ALLOW_ZERO,		\
+		.mult = NA_MULT,				\
+		.div = NA_DIV,					\
+	}
+
 #define IGNORE_UNUSED_DIV(id)					\
 	{							\
 		.type = TYPE_DIV##id,				\
@@ -340,25 +354,25 @@
 
 static struct pm_clock_node generic_mux_div_nodes[] = {
 	GENERIC_MUX,
-	GENERIC_DIV(1),
+	GENERIC_DIV1,
 };
 
 static struct pm_clock_node generic_mux_div_gate_nodes[] = {
 	GENERIC_MUX,
-	GENERIC_DIV(1),
+	GENERIC_DIV1,
 	GENERIC_GATE,
 };
 
 static struct pm_clock_node generic_mux_div_unused_gate_nodes[] = {
 	GENERIC_MUX,
-	GENERIC_DIV(1),
+	GENERIC_DIV1,
 	IGNORE_UNUSED_GATE,
 };
 
 static struct pm_clock_node generic_mux_div_div_gate_nodes[] = {
 	GENERIC_MUX,
-	GENERIC_DIV(1),
-	GENERIC_DIV(2),
+	GENERIC_DIV1,
+	GENERIC_DIV2,
 	GENERIC_GATE,
 };
 
@@ -410,8 +424,8 @@
 
 static struct pm_clock_node usb_nodes[] = {
 	GENERIC_MUX,
-	GENERIC_DIV(1),
-	GENERIC_DIV(2),
+	GENERIC_DIV1,
+	GENERIC_DIV2,
 	{
 		.type = TYPE_GATE,
 		.offset = USB_GATE_SHIFT,
@@ -2432,10 +2446,11 @@
  *
  * @return	Returns success. In case of error, name data is 0.
  */
-enum pm_ret_status pm_api_clock_get_name(unsigned int clock_id, char *name)
+void pm_api_clock_get_name(unsigned int clock_id, char *name)
 {
 	if (clock_id == CLK_MAX)
-		memcpy(name, END_OF_CLK, CLK_NAME_LEN);
+		memcpy(name, END_OF_CLK, sizeof(END_OF_CLK) > CLK_NAME_LEN ?
+					 CLK_NAME_LEN : sizeof(END_OF_CLK));
 	else if (!pm_clock_valid(clock_id))
 		memset(name, 0, CLK_NAME_LEN);
 	else if (clock_id < CLK_MAX_OUTPUT_CLK)
@@ -2443,8 +2458,6 @@
 	else
 		memcpy(name, ext_clocks[clock_id - CLK_MAX_OUTPUT_CLK].name,
 		       CLK_NAME_LEN);
-
-	return PM_RET_SUCCESS;
 }
 
 /**
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_clock.h b/plat/xilinx/zynqmp/pm_service/pm_api_clock.h
index 301ed24..5efd63f 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_clock.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_clock.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -294,7 +294,7 @@
 struct pm_pll *pm_clock_get_pll_by_related_clk(enum clock_id clock_id);
 uint8_t pm_clock_has_div(unsigned int clock_id, enum pm_clock_div_id div_id);
 
-enum pm_ret_status pm_api_clock_get_name(unsigned int clock_id, char *name);
+void pm_api_clock_get_name(unsigned int clock_id, char *name);
 enum pm_ret_status pm_api_clock_get_num_clocks(unsigned int *nclocks);
 enum pm_ret_status pm_api_clock_get_topology(unsigned int clock_id,
 					     unsigned int index,
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.c b/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.c
index 60e80d9..9c5af88 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.c
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -282,17 +282,29 @@
 {
 	unsigned int shift;
 	enum pm_ret_status ret;
+	unsigned int val, mask;
 
-	if (nid == NODE_SD_0)
+	if (nid == NODE_SD_0) {
 		shift = 0;
-	else if (nid == NODE_SD_1)
+		mask = ZYNQMP_SD0_DLL_RST_MASK;
+	} else if (nid == NODE_SD_1) {
 		shift = ZYNQMP_SD_TAP_OFFSET;
-	else
+		mask = ZYNQMP_SD1_DLL_RST_MASK;
+	} else {
 		return PM_RET_ERROR_ARGS;
+	}
 
-	ret = pm_ioctl_sd_dll_reset(nid, PM_DLL_RESET_ASSERT);
-	if (ret != PM_RET_SUCCESS)
+	ret = pm_mmio_read(ZYNQMP_SD_DLL_CTRL, &val);
+	if (ret != PM_RET_SUCCESS) {
 		return ret;
+	}
+
+	if ((val & mask) == 0) {
+		ret = pm_ioctl_sd_dll_reset(nid, PM_DLL_RESET_ASSERT);
+		if (ret != PM_RET_SUCCESS) {
+			return ret;
+		}
+	}
 
 	if (type == PM_TAPDELAY_INPUT) {
 		ret = pm_mmio_write(ZYNQMP_SD_ITAP_DLY,
@@ -300,9 +312,15 @@
 				    (ZYNQMP_SD_ITAPCHGWIN << shift));
 		if (ret != PM_RET_SUCCESS)
 			goto reset_release;
-		ret = pm_mmio_write(ZYNQMP_SD_ITAP_DLY,
-				    (ZYNQMP_SD_ITAPDLYENA_MASK << shift),
-				    (ZYNQMP_SD_ITAPDLYENA << shift));
+		if (value == 0)
+			ret = pm_mmio_write(ZYNQMP_SD_ITAP_DLY,
+					    (ZYNQMP_SD_ITAPDLYENA_MASK <<
+					     shift), 0);
+		else
+			ret = pm_mmio_write(ZYNQMP_SD_ITAP_DLY,
+					    (ZYNQMP_SD_ITAPDLYENA_MASK <<
+					    shift), (ZYNQMP_SD_ITAPDLYENA <<
+					    shift));
 		if (ret != PM_RET_SUCCESS)
 			goto reset_release;
 		ret = pm_mmio_write(ZYNQMP_SD_ITAP_DLY,
@@ -314,8 +332,7 @@
 				    (ZYNQMP_SD_ITAPCHGWIN_MASK << shift), 0);
 	} else if (type == PM_TAPDELAY_OUTPUT) {
 		ret = pm_mmio_write(ZYNQMP_SD_OTAP_DLY,
-				    (ZYNQMP_SD_OTAPDLYENA_MASK << shift),
-				    (ZYNQMP_SD_OTAPDLYENA << shift));
+				    (ZYNQMP_SD_OTAPDLYENA_MASK << shift), 0);
 		if (ret != PM_RET_SUCCESS)
 			goto reset_release;
 		ret = pm_mmio_write(ZYNQMP_SD_OTAP_DLY,
@@ -326,7 +343,10 @@
 	}
 
 reset_release:
-	pm_ioctl_sd_dll_reset(nid, PM_DLL_RESET_RELEASE);
+	if ((val & mask) == 0) {
+		(void)pm_ioctl_sd_dll_reset(nid, PM_DLL_RESET_RELEASE);
+	}
+
 	return ret;
 }
 
@@ -575,7 +595,7 @@
  */
 static enum pm_ret_status pm_ioctl_set_boot_health_status(unsigned int value)
 {
-	return pm_mmio_write(PM_BOOT_HEALTH_STATUS_REG,
+	return pm_mmio_write(PMU_GLOBAL_GEN_STORAGE4,
 			     PM_BOOT_HEALTH_STATUS_MASK, value);
 }
 
@@ -657,6 +677,10 @@
 	case IOCTL_AFI:
 		ret = pm_ioctl_afi(arg1, arg2);
 		break;
+	case IOCTL_SET_FEATURE_CONFIG:
+	case IOCTL_GET_FEATURE_CONFIG:
+		ret = pm_feature_config(ioctl_id, arg1, arg2, value);
+		break;
 	default:
 		ret = PM_RET_ERROR_NOTSUPPORTED;
 		break;
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.h b/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.h
index 337f732..f18dc00 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_ioctl.h
@@ -15,28 +15,43 @@
 
 //ioctl id
 enum {
-	IOCTL_GET_RPU_OPER_MODE,
-	IOCTL_SET_RPU_OPER_MODE,
-	IOCTL_RPU_BOOT_ADDR_CONFIG,
-	IOCTL_TCM_COMB_CONFIG,
-	IOCTL_SET_TAPDELAY_BYPASS,
-	IOCTL_SET_SGMII_MODE,
-	IOCTL_SD_DLL_RESET,
-	IOCTL_SET_SD_TAPDELAY,
+	IOCTL_GET_RPU_OPER_MODE = 0,
+	IOCTL_SET_RPU_OPER_MODE = 1,
+	IOCTL_RPU_BOOT_ADDR_CONFIG = 2,
+	IOCTL_TCM_COMB_CONFIG = 3,
+	IOCTL_SET_TAPDELAY_BYPASS = 4,
+	IOCTL_SET_SGMII_MODE = 5,
+	IOCTL_SD_DLL_RESET = 6,
+	IOCTL_SET_SD_TAPDELAY = 7,
 	 /* Ioctl for clock driver */
-	IOCTL_SET_PLL_FRAC_MODE,
-	IOCTL_GET_PLL_FRAC_MODE,
-	IOCTL_SET_PLL_FRAC_DATA,
-	IOCTL_GET_PLL_FRAC_DATA,
-	IOCTL_WRITE_GGS,
-	IOCTL_READ_GGS,
-	IOCTL_WRITE_PGGS,
-	IOCTL_READ_PGGS,
+	IOCTL_SET_PLL_FRAC_MODE = 8,
+	IOCTL_GET_PLL_FRAC_MODE = 9,
+	IOCTL_SET_PLL_FRAC_DATA = 10,
+	IOCTL_GET_PLL_FRAC_DATA = 11,
+	IOCTL_WRITE_GGS = 12,
+	IOCTL_READ_GGS = 13,
+	IOCTL_WRITE_PGGS = 14,
+	IOCTL_READ_PGGS = 15,
 	/* IOCTL for ULPI reset */
-	IOCTL_ULPI_RESET,
+	IOCTL_ULPI_RESET = 16,
 	/* Set healthy bit value */
-	IOCTL_SET_BOOT_HEALTH_STATUS,
-	IOCTL_AFI,
+	IOCTL_SET_BOOT_HEALTH_STATUS = 17,
+	IOCTL_AFI = 18,
+	/* Probe counter read/write */
+	IOCTL_PROBE_COUNTER_READ = 19,
+	IOCTL_PROBE_COUNTER_WRITE = 20,
+	IOCTL_OSPI_MUX_SELECT = 21,
+	/* IOCTL for USB power request */
+	IOCTL_USB_SET_STATE = 22,
+	/* IOCTL to get last reset reason */
+	IOCTL_GET_LAST_RESET_REASON = 23,
+	/* AI engine NPI ISR clear */
+	IOCTL_AIE_ISR_CLEAR = 24,
+	/* Register SGI to ATF */
+	IOCTL_REGISTER_SGI = 25,
+	/* Runtime feature configuration */
+	IOCTL_SET_FEATURE_CONFIG = 26,
+	IOCTL_GET_FEATURE_CONFIG = 27,
 };
 
 //RPU operation mode
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.c b/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.c
index 4b8dfb6..9a6b497 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.c
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.c
@@ -19,39 +19,6 @@
 #include "pm_common.h"
 #include "pm_ipi.h"
 
-#define PINCTRL_FUNCTION_MASK			U(0xFE)
-#define PINCTRL_VOLTAGE_STATUS_MASK		U(0x01)
-#define NFUNCS_PER_PIN				U(13)
-#define PINCTRL_NUM_MIOS			U(78)
-#define MAX_PIN_PER_REG				U(26)
-#define PINCTRL_BANK_ADDR_STEP			U(28)
-
-#define PINCTRL_DRVSTRN0_REG_OFFSET		U(0)
-#define PINCTRL_DRVSTRN1_REG_OFFSET		U(4)
-#define PINCTRL_SCHCMOS_REG_OFFSET		U(8)
-#define PINCTRL_PULLCTRL_REG_OFFSET		U(12)
-#define PINCTRL_PULLSTAT_REG_OFFSET		U(16)
-#define PINCTRL_SLEWCTRL_REG_OFFSET		U(20)
-#define PINCTRL_VOLTAGE_STAT_REG_OFFSET		U(24)
-
-#define IOU_SLCR_BANK1_CTRL5			U(0XFF180164)
-
-#define PINCTRL_CFG_ADDR_OFFSET(addr, reg, miopin)			\
-	((addr) + 4 * PINCTRL_NUM_MIOS + PINCTRL_BANK_ADDR_STEP *	\
-	((miopin) / MAX_PIN_PER_REG) + (reg))
-
-#define PINCTRL_PIN_OFFSET(_miopin) \
-	((_miopin) - (MAX_PIN_PER_REG * ((_miopin) / MAX_PIN_PER_REG)))
-
-#define PINCTRL_REGVAL_TO_PIN_CONFIG(_pin, _val)			\
-	(((_val) >> PINCTRL_PIN_OFFSET(_pin)) & 0x1)
-
-static uint8_t pm_pinctrl_mux[NFUNCS_PER_PIN] = {
-	0x02, 0x04, 0x08, 0x10, 0x18,
-	0x00, 0x20, 0x40, 0x60, 0x80,
-	0xA0, 0xC0, 0xE0
-};
-
 struct pinctrl_function {
 	char name[FUNCTION_NAME_LEN];
 	uint16_t (*groups)[];
@@ -2604,18 +2571,13 @@
  *
  * This function is used by master to get name of function specified
  * by given function ID.
- *
- * @return	Returns success. In case of error, name data is 0.
  */
-enum pm_ret_status pm_api_pinctrl_get_function_name(unsigned int fid,
-						    char *name)
+void pm_api_pinctrl_get_function_name(unsigned int fid, char *name)
 {
 	if (fid >= MAX_FUNCTION)
 		memcpy(name, END_OF_FUNCTION, FUNCTION_NAME_LEN);
 	else
 		memcpy(name, pinctrl_functions[fid].name, FUNCTION_NAME_LEN);
-
-	return PM_RET_SUCCESS;
 }
 
 /**
@@ -2713,330 +2675,3 @@
 
 	return PM_RET_SUCCESS;
 }
-
-/**
- * pm_api_pinctrl_get_function() - Read function id set for the given pin
- * @pin		Pin number
- * @nid		Node ID of function currently set for given pin
- *
- * This function provides the function currently set for the given pin.
- *
- * @return	Returns status, either success or error+reason
- */
-enum pm_ret_status pm_api_pinctrl_get_function(unsigned int pin,
-					       unsigned int *id)
-{
-	unsigned int i = 0, j = 0;
-	enum pm_ret_status ret = PM_RET_SUCCESS;
-	unsigned int ctrlreg, val, gid;
-	uint16_t *grps;
-
-	ctrlreg = IOU_SLCR_BASEADDR + 4U * pin;
-	ret = pm_mmio_read(ctrlreg, &val);
-	if (ret != PM_RET_SUCCESS)
-		return ret;
-
-	val &= PINCTRL_FUNCTION_MASK;
-
-	for (i = 0; i < NFUNCS_PER_PIN; i++)
-		if (val == pm_pinctrl_mux[i])
-			break;
-
-	if (i == NFUNCS_PER_PIN)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	gid = *(*zynqmp_pin_groups[pin].groups + i);
-
-	for (i = 0; i < MAX_FUNCTION; i++) {
-		grps = *pinctrl_functions[i].groups;
-		if (grps == NULL)
-			continue;
-		if (val != pinctrl_functions[i].regval)
-			continue;
-
-		for (j = 0; grps[j] != (uint16_t)END_OF_GROUPS; j++) {
-			if (gid == grps[j]) {
-				*id = i;
-				goto done;
-			}
-		}
-	}
-	if (i == MAX_FUNCTION)
-		ret = PM_RET_ERROR_ARGS;
-done:
-	return ret;
-}
-
-/**
- * pm_api_pinctrl_set_function() - Set function id set for the given pin
- * @pin		Pin number
- * @nid		Node ID of function to set for given pin
- *
- * This function provides the function currently set for the given pin.
- *
- * @return	Returns status, either success or error+reason
- */
-enum pm_ret_status pm_api_pinctrl_set_function(unsigned int pin,
-					       unsigned int fid)
-{
-	int i, j;
-	unsigned int ctrlreg, val;
-	uint16_t *pgrps, *fgrps;
-
-	ctrlreg = IOU_SLCR_BASEADDR + 4U * pin;
-	val = pinctrl_functions[fid].regval;
-
-	for (i = 0; i < NFUNCS_PER_PIN; i++)
-		if (val == pm_pinctrl_mux[i])
-			break;
-
-	if (i == NFUNCS_PER_PIN)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	pgrps = *zynqmp_pin_groups[pin].groups;
-	if (!pgrps)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	fgrps = *pinctrl_functions[fid].groups;
-	if (!fgrps)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	for (i = 0; fgrps[i] != (uint16_t)END_OF_GROUPS; i++)
-		for (j = 0; pgrps[j] != (uint16_t)END_OF_GROUPS; j++)
-			if (fgrps[i] == pgrps[j])
-				goto match;
-
-	return PM_RET_ERROR_NOTSUPPORTED;
-
-match:
-	return pm_mmio_write(ctrlreg, PINCTRL_FUNCTION_MASK, val);
-}
-
-/**
- * pm_api_pinctrl_set_config() - Set configuration parameter for given pin
- * @pin: Pin for which configuration is to be set
- * @param: Configuration parameter to be set
- * @value: Value to be set for configuration parameter
- *
- * This function sets value of requested configuration parameter for given pin.
- *
- * @return	Returns status, either success or error+reason
- */
-enum pm_ret_status pm_api_pinctrl_set_config(unsigned int pin,
-					     unsigned int param,
-					     unsigned int value)
-{
-	enum pm_ret_status ret;
-	unsigned int ctrlreg, mask, val, offset;
-
-	if (param >= PINCTRL_CONFIG_MAX)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	if (pin >=  PINCTRL_NUM_MIOS)
-		return PM_RET_ERROR_ARGS;
-
-	mask = 1 << PINCTRL_PIN_OFFSET(pin);
-
-	switch (param) {
-	case PINCTRL_CONFIG_SLEW_RATE:
-		if (value != PINCTRL_SLEW_RATE_FAST &&
-		    value != PINCTRL_SLEW_RATE_SLOW)
-			return PM_RET_ERROR_ARGS;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_SLEWCTRL_REG_OFFSET,
-					      pin);
-		val = value << PINCTRL_PIN_OFFSET(pin);
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		break;
-	case PINCTRL_CONFIG_BIAS_STATUS:
-		if (value != PINCTRL_BIAS_ENABLE &&
-		    value != PINCTRL_BIAS_DISABLE)
-			return PM_RET_ERROR_ARGS;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_PULLSTAT_REG_OFFSET,
-					      pin);
-
-		offset = PINCTRL_PIN_OFFSET(pin);
-		if (ctrlreg == IOU_SLCR_BANK1_CTRL5)
-			offset = (offset < 12U) ?
-					(offset + 14U) : (offset - 12U);
-
-		val = value << offset;
-		mask = 1 << offset;
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		break;
-	case PINCTRL_CONFIG_PULL_CTRL:
-
-		if (value != PINCTRL_BIAS_PULL_DOWN &&
-		    value != PINCTRL_BIAS_PULL_UP)
-			return PM_RET_ERROR_ARGS;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_PULLSTAT_REG_OFFSET,
-					      pin);
-
-		offset = PINCTRL_PIN_OFFSET(pin);
-		if (ctrlreg == IOU_SLCR_BANK1_CTRL5)
-			offset = (offset < 12U) ?
-					(offset + 14U) : (offset - 12U);
-
-		val = PINCTRL_BIAS_ENABLE << offset;
-		ret = pm_mmio_write(ctrlreg, 1 << offset, val);
-		if (ret != PM_RET_SUCCESS)
-			return ret;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_PULLCTRL_REG_OFFSET,
-					      pin);
-		val = value << PINCTRL_PIN_OFFSET(pin);
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		break;
-	case PINCTRL_CONFIG_SCHMITT_CMOS:
-		if (value != PINCTRL_INPUT_TYPE_CMOS &&
-		    value != PINCTRL_INPUT_TYPE_SCHMITT)
-			return PM_RET_ERROR_ARGS;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_SCHCMOS_REG_OFFSET,
-					      pin);
-
-		val = value << PINCTRL_PIN_OFFSET(pin);
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		break;
-	case PINCTRL_CONFIG_DRIVE_STRENGTH:
-		if (value > PINCTRL_DRIVE_STRENGTH_12MA)
-			return PM_RET_ERROR_ARGS;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_DRVSTRN0_REG_OFFSET,
-					      pin);
-		val = (value >> 1) << PINCTRL_PIN_OFFSET(pin);
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		if (ret)
-			return ret;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_DRVSTRN1_REG_OFFSET,
-					      pin);
-		val = (value & 0x01U) << PINCTRL_PIN_OFFSET(pin);
-		ret = pm_mmio_write(ctrlreg, mask, val);
-		break;
-	default:
-		ERROR("Invalid parameter %u\n", param);
-		ret = PM_RET_ERROR_NOTSUPPORTED;
-		break;
-	}
-
-	return ret;
-}
-
-/**
- * pm_api_pinctrl_get_config() - Get configuration parameter value for given pin
- * @pin: Pin for which configuration is to be read
- * @param: Configuration parameter to be read
- * @value: buffer to store value of configuration parameter
- *
- * This function reads value of requested configuration parameter for given pin.
- *
- * @return	Returns status, either success or error+reason
- */
-enum pm_ret_status pm_api_pinctrl_get_config(unsigned int pin,
-					     unsigned int param,
-					     unsigned int *value)
-{
-	enum pm_ret_status ret;
-	unsigned int ctrlreg, val;
-
-	if (param >= PINCTRL_CONFIG_MAX)
-		return PM_RET_ERROR_NOTSUPPORTED;
-
-	if (pin >=  PINCTRL_NUM_MIOS)
-		return PM_RET_ERROR_ARGS;
-
-	switch (param) {
-	case PINCTRL_CONFIG_SLEW_RATE:
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_SLEWCTRL_REG_OFFSET,
-					      pin);
-
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret != PM_RET_SUCCESS)
-			return ret;
-
-		*value = PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val);
-		break;
-	case PINCTRL_CONFIG_BIAS_STATUS:
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_PULLSTAT_REG_OFFSET,
-					      pin);
-
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		if (ctrlreg == IOU_SLCR_BANK1_CTRL5)
-			val = ((val & 0x3FFF) << 12) | ((val >> 14) & 0xFFF);
-
-		*value = PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val);
-		break;
-	case PINCTRL_CONFIG_PULL_CTRL:
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_PULLCTRL_REG_OFFSET,
-					      pin);
-
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		*value = PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val);
-		break;
-	case PINCTRL_CONFIG_SCHMITT_CMOS:
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_SCHCMOS_REG_OFFSET,
-					      pin);
-
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		*value = PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val);
-		break;
-	case PINCTRL_CONFIG_DRIVE_STRENGTH:
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_DRVSTRN0_REG_OFFSET,
-					      pin);
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		*value = PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val) << 1;
-
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_DRVSTRN1_REG_OFFSET,
-					      pin);
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		*value |= PINCTRL_REGVAL_TO_PIN_CONFIG(pin, val);
-		break;
-	case PINCTRL_CONFIG_VOLTAGE_STATUS:
-		ctrlreg = PINCTRL_CFG_ADDR_OFFSET(IOU_SLCR_BASEADDR,
-					      PINCTRL_VOLTAGE_STAT_REG_OFFSET,
-					      pin);
-
-		ret = pm_mmio_read(ctrlreg, &val);
-		if (ret)
-			return ret;
-
-		*value = val & PINCTRL_VOLTAGE_STATUS_MASK;
-		break;
-	default:
-		return PM_RET_ERROR_NOTSUPPORTED;
-	}
-
-	return PM_RET_SUCCESS;
-}
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.h b/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.h
index 9923c00..2b8fca3 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_pinctrl.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -709,18 +709,7 @@
 #define	PINCTRL_DRIVE_STRENGTH_8MA 2U
 #define	PINCTRL_DRIVE_STRENGTH_12MA 3U
 
-enum pm_ret_status pm_api_pinctrl_set_function(unsigned int pin,
-					       unsigned int fid);
-enum pm_ret_status pm_api_pinctrl_get_function(unsigned int pin,
-					       unsigned int *id);
-enum pm_ret_status pm_api_pinctrl_set_config(unsigned int pin,
-					     unsigned int param,
-					     unsigned int value);
-enum pm_ret_status pm_api_pinctrl_get_config(unsigned int pin,
-					     unsigned int param,
-					     unsigned int *value);
-enum pm_ret_status pm_api_pinctrl_get_function_name(unsigned int fid,
-						    char *name);
+void pm_api_pinctrl_get_function_name(unsigned int fid, char *name);
 enum pm_ret_status pm_api_pinctrl_get_function_groups(unsigned int fid,
 						      unsigned int index,
 						      uint16_t *groups);
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_sys.c b/plat/xilinx/zynqmp/pm_service/pm_api_sys.c
index b1720d9..5d9408c 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_sys.c
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_sys.c
@@ -65,6 +65,10 @@
 	PM_PACK_PAYLOAD5(pl, arg0, arg1, arg2, arg3, arg4);		\
 }
 
+#define EM_PACK_PAYLOAD1(pl, arg0) {	\
+	pl[0] = (uint16_t)(0xE) << 16 | (uint16_t)arg0;	\
+}
+
 /**
  * pm_self_suspend() - PM call for processor to suspend itself
  * @nid		Node id of the processor or subsystem
@@ -205,7 +209,7 @@
 	/* TODO: allow passing the node ID of the affected CPU */
 	PM_PACK_PAYLOAD3(payload, PM_ABORT_SUSPEND, reason,
 			 primary_proc->node_id);
-	return pm_ipi_send(primary_proc, payload);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -224,7 +228,7 @@
 
 	PM_PACK_PAYLOAD4(payload, PM_SET_WAKEUP_SOURCE, target, wkup_node,
 			 enable);
-	return pm_ipi_send(primary_proc, payload);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -312,7 +316,7 @@
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	PM_PACK_PAYLOAD2(payload, PM_RELEASE_NODE, nid);
-	return pm_ipi_send(primary_proc, payload);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -328,7 +332,7 @@
 	uint32_t payload[PAYLOAD_ARG_CNT];
 
 	PM_PACK_PAYLOAD3(payload, PM_SET_MAX_LATENCY, nid, latency);
-	return pm_ipi_send(primary_proc, payload);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /* Miscellaneous API functions */
@@ -457,7 +461,7 @@
 
 	/* Send request to the PMU */
 	PM_PACK_PAYLOAD3(payload, PM_RESET_ASSERT, reset, assert);
-	return pm_ipi_send(primary_proc, payload);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -655,7 +659,11 @@
  */
 enum pm_ret_status pm_pinctrl_request(unsigned int pin)
 {
-	return PM_RET_SUCCESS;
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD2(payload, PM_PINCTRL_REQUEST, pin);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -668,37 +676,44 @@
  */
 enum pm_ret_status pm_pinctrl_release(unsigned int pin)
 {
-	return PM_RET_SUCCESS;
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD2(payload, PM_PINCTRL_RELEASE, pin);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
  * pm_pinctrl_get_function() - Read function id set for the given pin
  * @pin		Pin number
- * @nid		Node ID of function currently set for given pin
+ * @fid		ID of function currently set for given pin
  *
  * This function provides the function currently set for the given pin.
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_get_function(unsigned int pin,
-					   enum pm_node_id *nid)
+enum pm_ret_status pm_pinctrl_get_function(unsigned int pin, unsigned int *fid)
 {
-	return pm_api_pinctrl_get_function(pin, nid);
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	PM_PACK_PAYLOAD2(payload, PM_PINCTRL_GET_FUNCTION, pin);
+	return pm_ipi_send_sync(primary_proc, payload, fid, 1);
 }
 
 /**
  * pm_pinctrl_set_function() - Set function id set for the given pin
  * @pin		Pin number
- * @nid		Node ID of function to set for given pin
- *
- * This function provides the function currently set for the given pin.
+ * @fid		ID of function to set for given pin
  *
  * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_pinctrl_set_function(unsigned int pin,
-					   enum pm_node_id nid)
+enum pm_ret_status pm_pinctrl_set_function(unsigned int pin, unsigned int fid)
 {
-	return pm_api_pinctrl_set_function(pin, (unsigned int)nid);
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD3(payload, PM_PINCTRL_SET_FUNCTION, pin, fid);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -715,24 +730,30 @@
 					 unsigned int param,
 					 unsigned int *value)
 {
-	return pm_api_pinctrl_get_config(pin, param, value);
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	PM_PACK_PAYLOAD3(payload, PM_PINCTRL_CONFIG_PARAM_GET, pin, param);
+	return pm_ipi_send_sync(primary_proc, payload, value, 1);
 }
 
 /**
- * pm_pinctrl_set_config() - Read value of requested config param for given pin
+ * pm_pinctrl_set_config() - Set value of requested config param for given pin
  * @pin		Pin number
  * @param	Parameter to set
  * @value	Parameter value to set
  *
- * This function provides the configuration parameter value for the given pin.
- *
  * @return	Returns status, either success or error+reason
  */
 enum pm_ret_status pm_pinctrl_set_config(unsigned int pin,
 					 unsigned int param,
 					 unsigned int value)
 {
-	return pm_api_pinctrl_set_config(pin, param, value);
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD4(payload, PM_PINCTRL_CONFIG_PARAM_SET, pin, param,
+			 value);
+	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
 }
 
 /**
@@ -793,12 +814,10 @@
  *
  * This function is used by master to get nmae of clock specified
  * by given clock ID.
- *
- * @return	Returns status, either success or error+reason
  */
-static enum pm_ret_status pm_clock_get_name(unsigned int clock_id, char *name)
+static void pm_clock_get_name(unsigned int clock_id, char *name)
 {
-	return pm_api_clock_get_name(clock_id, name);
+	pm_api_clock_get_name(clock_id, name);
 }
 
 /**
@@ -907,7 +926,13 @@
 
 	/* Send request to the PMU */
 	PM_PACK_PAYLOAD2(payload, api_id, clock_id);
-	return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+	status = pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+
+	/* If action fails due to the lack of permissions filter the error */
+	if (status == PM_RET_ERROR_ACCESS)
+		status = PM_RET_SUCCESS;
+
+	return status;
 }
 
 /**
@@ -1229,13 +1254,10 @@
  *
  * This function is used by master to get name of function specified
  * by given function Id
- *
- * Return: Returns status, either success or error+reason.
  */
-static enum pm_ret_status pm_pinctrl_get_function_name(unsigned int fid,
-						       char *name)
+static void pm_pinctrl_get_function_name(unsigned int fid, char *name)
 {
-	return pm_api_pinctrl_get_function_name(fid, name);
+	pm_api_pinctrl_get_function_name(fid, name);
 }
 
 /**
@@ -1295,78 +1317,58 @@
  * @data	Returned output data
  *
  * This function returns requested data.
- *
- * @return	Returns status, either success or error+reason
  */
-enum pm_ret_status pm_query_data(enum pm_query_id qid,
-				 unsigned int arg1,
-				 unsigned int arg2,
-				 unsigned int arg3,
-				 unsigned int *data)
+void pm_query_data(enum pm_query_id qid, unsigned int arg1, unsigned int arg2,
+		   unsigned int arg3, unsigned int *data)
 {
-	enum pm_ret_status ret;
-
 	switch (qid) {
 	case PM_QID_CLOCK_GET_NAME:
-		ret = pm_clock_get_name(arg1, (char *)data);
+		pm_clock_get_name(arg1, (char *)data);
 		break;
 	case PM_QID_CLOCK_GET_TOPOLOGY:
-		ret = pm_clock_get_topology(arg1, arg2, &data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_topology(arg1, arg2, &data[1]);
 		break;
 	case PM_QID_CLOCK_GET_FIXEDFACTOR_PARAMS:
-		ret = pm_clock_get_fixedfactor_params(arg1, &data[1], &data[2]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_fixedfactor_params(arg1, &data[1],
+							  &data[2]);
 		break;
 	case PM_QID_CLOCK_GET_PARENTS:
-		ret = pm_clock_get_parents(arg1, arg2, &data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_parents(arg1, arg2, &data[1]);
 		break;
 	case PM_QID_CLOCK_GET_ATTRIBUTES:
-		ret = pm_clock_get_attributes(arg1, &data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_attributes(arg1, &data[1]);
 		break;
 	case PM_QID_PINCTRL_GET_NUM_PINS:
-		ret = pm_pinctrl_get_num_pins(&data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_pinctrl_get_num_pins(&data[1]);
 		break;
 	case PM_QID_PINCTRL_GET_NUM_FUNCTIONS:
-		ret = pm_pinctrl_get_num_functions(&data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_pinctrl_get_num_functions(&data[1]);
 		break;
 	case PM_QID_PINCTRL_GET_NUM_FUNCTION_GROUPS:
-		ret = pm_pinctrl_get_num_function_groups(arg1, &data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_pinctrl_get_num_function_groups(arg1, &data[1]);
 		break;
 	case PM_QID_PINCTRL_GET_FUNCTION_NAME:
-		ret = pm_pinctrl_get_function_name(arg1, (char *)data);
+		pm_pinctrl_get_function_name(arg1, (char *)data);
 		break;
 	case PM_QID_PINCTRL_GET_FUNCTION_GROUPS:
-		ret = pm_pinctrl_get_function_groups(arg1, arg2,
-						     (uint16_t *)&data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_pinctrl_get_function_groups(arg1, arg2,
+							 (uint16_t *)&data[1]);
 		break;
 	case PM_QID_PINCTRL_GET_PIN_GROUPS:
-		ret = pm_pinctrl_get_pin_groups(arg1, arg2,
-						(uint16_t *)&data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_pinctrl_get_pin_groups(arg1, arg2,
+						    (uint16_t *)&data[1]);
 		break;
 	case PM_QID_CLOCK_GET_NUM_CLOCKS:
-		ret = pm_clock_get_num_clocks(&data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_num_clocks(&data[1]);
 		break;
 
 	case PM_QID_CLOCK_GET_MAX_DIVISOR:
-		ret = pm_clock_get_max_divisor(arg1, arg2, &data[1]);
-		data[0] = (unsigned int)ret;
+		data[0] = pm_clock_get_max_divisor(arg1, arg2, &data[1]);
 		break;
 	default:
-		ret = PM_RET_ERROR_ARGS;
+		data[0] = PM_RET_ERROR_ARGS;
 		WARN("Unimplemented query service call: 0x%x\n", qid);
-		break;
 	}
-
-	return ret;
 }
 
 enum pm_ret_status pm_sha_hash(uint32_t address_high,
@@ -1548,3 +1550,134 @@
 	PM_PACK_PAYLOAD2(payload, PM_PLL_GET_MODE, nid);
 	return pm_ipi_send_sync(primary_proc, payload, mode, 1);
 }
+
+/**
+ * pm_register_access() -  PM API for register read/write access data
+ *
+ * @register_access_id	Register_access_id which says register read/write
+ *
+ * @address		Address of the register to be accessed
+ *
+ * @mask		Mask value to be used while writing value
+ *
+ * @value		Value to be written to register
+ *
+ * @out			Returned output data
+ *
+ * This function returns requested data.
+ *
+ * @return	Returns status, either success or error+reason
+ */
+enum pm_ret_status pm_register_access(unsigned int register_access_id,
+				      unsigned int address,
+				      unsigned int mask,
+				      unsigned int value,
+				      unsigned int *out)
+{
+	enum pm_ret_status ret;
+
+	if (((ZYNQMP_CSU_BASEADDR & address) != ZYNQMP_CSU_BASEADDR) &&
+			((CSUDMA_BASE & address) != CSUDMA_BASE) &&
+			((RSA_CORE_BASE & address) != RSA_CORE_BASE) &&
+			((PMU_GLOBAL_BASE & address) != PMU_GLOBAL_BASE))
+		return PM_RET_ERROR_ACCESS;
+
+	switch (register_access_id) {
+	case CONFIG_REG_WRITE:
+		ret = pm_mmio_write(address, mask, value);
+		break;
+	case CONFIG_REG_READ:
+		ret = pm_mmio_read(address, out);
+		break;
+	default:
+		ret = PM_RET_ERROR_ARGS;
+		WARN("Unimplemented register_access call\n\r");
+	}
+	return ret;
+}
+
+/**
+ * pm_efuse_access() - To program or read efuse bits.
+ *
+ * This function provides access to the xilskey library to program/read
+ * efuse bits.
+ *
+ * address_low: lower 32-bit Linear memory space address
+ * address_high: higher 32-bit Linear memory space address
+ *
+ * value: Returned output value
+ *
+ * @return  Returns status, either success or error+reason
+ *
+ */
+enum pm_ret_status pm_efuse_access(uint32_t address_high,
+				   uint32_t address_low,
+				   uint32_t *value)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD3(payload, PM_EFUSE_ACCESS, address_high, address_low);
+
+	return pm_ipi_send_sync(primary_proc, payload, value, 1);
+}
+
+enum pm_ret_status em_set_action(unsigned int *value)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	EM_PACK_PAYLOAD1(payload, EM_SET_ACTION);
+	return pm_ipi_send_sync(primary_proc, payload, value, 1);
+}
+
+enum pm_ret_status em_remove_action(unsigned int *value)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	EM_PACK_PAYLOAD1(payload, EM_REMOVE_ACTION);
+	return pm_ipi_send_sync(primary_proc, payload, value, 1);
+}
+
+enum pm_ret_status em_send_errors(unsigned int *value)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	EM_PACK_PAYLOAD1(payload, EM_SEND_ERRORS);
+	return pm_ipi_send_sync(primary_proc, payload, value, 1);
+}
+
+/**
+ * pm_feature_config() - feature configuration at runtime
+ *
+ * This function is used to send IPI request to PMUFW to configure feature
+ * at runtime. The feature can be enable or disable as well as the feature
+ * can be configure at runtime using an IOCTL call.
+ *
+ * @ioctl_id	The ioctl id for the feature configuration
+ * @config_id	The config id of the feature to be configured
+ * @value	The value to be configured
+ * @response	Return to reference pointer
+ *
+ * @return      Returns 0 on success or error value on failure
+ */
+enum pm_ret_status pm_feature_config(unsigned int ioctl_id,
+				     unsigned int config_id,
+				     unsigned int value,
+				     unsigned int *response)
+{
+	uint32_t payload[PAYLOAD_ARG_CNT];
+
+	/* Send request to the PMU */
+	PM_PACK_PAYLOAD5(payload, PM_IOCTL, 0, ioctl_id, config_id, value);
+
+	if (ioctl_id == IOCTL_GET_FEATURE_CONFIG) {
+		return pm_ipi_send_sync(primary_proc, payload, response, 1);
+	} else if (ioctl_id == IOCTL_SET_FEATURE_CONFIG) {
+		return pm_ipi_send_sync(primary_proc, payload, NULL, 0);
+	} else {
+		return PM_RET_ERROR_ARGS;
+	}
+}
diff --git a/plat/xilinx/zynqmp/pm_service/pm_api_sys.h b/plat/xilinx/zynqmp/pm_service/pm_api_sys.h
index ff66d3f..ca07cef 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_api_sys.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_api_sys.h
@@ -28,6 +28,11 @@
 	PM_QID_CLOCK_GET_MAX_DIVISOR,
 };
 
+enum pm_register_access_id {
+	CONFIG_REG_WRITE,
+	CONFIG_REG_READ,
+};
+
 /**********************************************************
  * System-level API function declarations
  **********************************************************/
@@ -151,11 +156,8 @@
 				      unsigned int parent_id);
 enum pm_ret_status pm_clock_getparent(unsigned int clock_id,
 				      unsigned int *parent_id);
-enum pm_ret_status pm_query_data(enum pm_query_id qid,
-				 unsigned int arg1,
-				 unsigned int arg2,
-				 unsigned int arg3,
-				 unsigned int *data);
+void pm_query_data(enum pm_query_id qid, unsigned int arg1, unsigned int arg2,
+		   unsigned int arg3, unsigned int *data);
 enum pm_ret_status pm_sha_hash(uint32_t address_high,
 				    uint32_t address_low,
 				    uint32_t size,
@@ -178,6 +180,11 @@
 enum pm_ret_status pm_aes_engine(uint32_t address_high,
 				 uint32_t address_low,
 				 uint32_t  *value);
+enum pm_ret_status pm_register_access(unsigned int register_access_id,
+				      unsigned int address,
+				      unsigned int mask,
+				      unsigned int value,
+				      unsigned int *out);
 
 enum pm_ret_status pm_pll_set_parameter(enum pm_node_id nid,
 				enum pm_pll_param param_id,
@@ -189,5 +196,15 @@
 
 enum pm_ret_status pm_pll_set_mode(enum pm_node_id nid, enum pm_pll_mode mode);
 enum pm_ret_status pm_pll_get_mode(enum pm_node_id nid, enum pm_pll_mode *mode);
+enum pm_ret_status pm_efuse_access(uint32_t address_high,
+				   uint32_t address_low, uint32_t *value);
+enum pm_ret_status em_set_action(unsigned int *value);
+enum pm_ret_status em_remove_action(unsigned int *value);
+enum pm_ret_status em_send_errors(unsigned int *value);
+
+enum pm_ret_status pm_feature_config(unsigned int ioctl_id,
+				     unsigned int config_id,
+				     unsigned int value,
+				     unsigned int *response);
 
 #endif /* PM_API_SYS_H */
diff --git a/plat/xilinx/zynqmp/pm_service/pm_defs.h b/plat/xilinx/zynqmp/pm_service/pm_defs.h
index cae36c9..3324431 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_defs.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_defs.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -18,7 +18,7 @@
  * (PM_VERSION_MAJOR << 16) | PM_VERSION_MINOR
  */
 #define PM_VERSION_MAJOR	1
-#define PM_VERSION_MINOR	0
+#define PM_VERSION_MINOR	1
 
 #define PM_VERSION	((PM_VERSION_MAJOR << 16) | PM_VERSION_MINOR)
 
@@ -33,6 +33,7 @@
 #define PM_STATE_CPU_IDLE		0x0U
 #define PM_STATE_SUSPEND_TO_RAM		0xFU
 
+#define EM_FUNID_NUM_MASK    0xF0000U
 /*********************************************************************
  * Enum definitions
  ********************************************************************/
@@ -97,6 +98,9 @@
 	PM_PLL_GET_PARAMETER,
 	PM_PLL_SET_MODE,
 	PM_PLL_GET_MODE,
+	/* PM Register Access API */
+	PM_REGISTER_ACCESS,
+	PM_EFUSE_ACCESS,
 	PM_API_MAX
 };
 
@@ -215,26 +219,29 @@
 
 /**
  * @PM_RET_SUCCESS:		success
- * @PM_RET_ERROR_ARGS:		illegal arguments provided
+ * @PM_RET_ERROR_ARGS:		illegal arguments provided (deprecated)
+ * @PM_RET_ERROR_NOTSUPPORTED:	feature not supported  (deprecated)
+ * @PM_RET_ERROR_INTERNAL:	internal error
+ * @PM_RET_ERROR_CONFLICT:	conflict
  * @PM_RET_ERROR_ACCESS:	access rights violation
+ * @PM_RET_ERROR_INVALID_NODE:	invalid node
+ * @PM_RET_ERROR_DOUBLE_REQ:	duplicate request for same node
+ * @PM_RET_ERROR_ABORT_SUSPEND:	suspend procedure has been aborted
  * @PM_RET_ERROR_TIMEOUT:	timeout in communication with PMU
- * @PM_RET_ERROR_NOTSUPPORTED:	feature not supported
- * @PM_RET_ERROR_PROC:		node is not a processor node
- * @PM_RET_ERROR_API_ID:	illegal API ID
- * @PM_RET_ERROR_OTHER:		other error
+ * @PM_RET_ERROR_NODE_USED:	node is already in use
  */
 enum pm_ret_status {
 	PM_RET_SUCCESS,
-	PM_RET_ERROR_ARGS,
-	PM_RET_ERROR_ACCESS,
-	PM_RET_ERROR_TIMEOUT,
-	PM_RET_ERROR_NOTSUPPORTED,
-	PM_RET_ERROR_PROC,
-	PM_RET_ERROR_API_ID,
-	PM_RET_ERROR_FAILURE,
-	PM_RET_ERROR_COMMUNIC,
-	PM_RET_ERROR_DOUBLEREQ,
-	PM_RET_ERROR_OTHER,
+	PM_RET_ERROR_ARGS = 1,
+	PM_RET_ERROR_NOTSUPPORTED = 4,
+	PM_RET_ERROR_INTERNAL = 2000,
+	PM_RET_ERROR_CONFLICT = 2001,
+	PM_RET_ERROR_ACCESS = 2002,
+	PM_RET_ERROR_INVALID_NODE = 2003,
+	PM_RET_ERROR_DOUBLE_REQ = 2004,
+	PM_RET_ERROR_ABORT_SUSPEND = 2005,
+	PM_RET_ERROR_TIMEOUT = 2006,
+	PM_RET_ERROR_NODE_USED = 2007
 };
 
 /**
@@ -317,4 +324,13 @@
 	PM_CLOCK_DIV1_ID,
 };
 
+/**
+ * EM API IDs
+ */
+enum em_api_id {
+	EM_SET_ACTION = 1,
+	EM_REMOVE_ACTION,
+	EM_SEND_ERRORS,
+};
+
 #endif /* PM_DEFS_H */
diff --git a/plat/xilinx/zynqmp/pm_service/pm_svc_main.c b/plat/xilinx/zynqmp/pm_service/pm_svc_main.c
index 3f4f069..a49bda8 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_svc_main.c
+++ b/plat/xilinx/zynqmp/pm_service/pm_svc_main.c
@@ -29,8 +29,8 @@
 #define PM_SET_SUSPEND_MODE	0xa02
 #define PM_GET_TRUSTZONE_VERSION	0xa03
 
-/* !0 - UP, 0 - DOWN */
-static int32_t pm_up = 0;
+/* pm_up = !0 - UP, pm_up = 0 - DOWN */
+static int32_t pm_up, ipi_irq_flag;
 
 #if ZYNQMP_WDT_RESTART
 static spinlock_t inc_lock;
@@ -142,6 +142,8 @@
                                                 void *handle, void *cookie)
 {
 	int i;
+	uint32_t value;
+
 	/* enter wfi and stay there */
 	INFO("Entering wfi\n");
 
@@ -156,8 +158,9 @@
 	spin_unlock(&inc_lock);
 
 	if (active_cores == 0) {
-		pm_system_shutdown(PMF_SHUTDOWN_TYPE_RESET,
-				PMF_SHUTDOWN_SUBTYPE_SUBSYSTEM);
+		pm_mmio_read(PMU_GLOBAL_GEN_STORAGE4, &value);
+		value = (value & RESTART_SCOPE_MASK) >> RESTART_SCOPE_SHIFT;
+		pm_system_shutdown(PMF_SHUTDOWN_TYPE_RESET, value);
 	}
 
 	/* enter wfi and stay there */
@@ -210,6 +213,15 @@
 
 	status = pm_ipi_init(primary_proc);
 
+	ret = pm_get_api_version(&pm_ctx.api_version);
+	if (pm_ctx.api_version < PM_VERSION) {
+		ERROR("BL31: Platform Management API version error. Expected: "
+		      "v%d.%d - Found: v%d.%d\n", PM_VERSION_MAJOR,
+		      PM_VERSION_MINOR, pm_ctx.api_version >> 16,
+		      pm_ctx.api_version & 0xFFFF);
+		return -EINVAL;
+	}
+
 #if ZYNQMP_WDT_RESTART
 	status = pm_wdt_restart_setup();
 	if (status)
@@ -321,22 +333,21 @@
 
 	case PM_GET_API_VERSION:
 		/* Check is PM API version already verified */
-		if (pm_ctx.api_version == PM_VERSION) {
+		if (pm_ctx.api_version >= PM_VERSION) {
+			if (!ipi_irq_flag) {
+				/*
+				 * Enable IPI IRQ
+				 * assume the rich OS is OK to handle callback IRQs now.
+				 * Even if we were wrong, it would not enable the IRQ in
+				 * the GIC.
+				 */
+				pm_ipi_irq_enable(primary_proc);
+				ipi_irq_flag = 1;
+			}
 			SMC_RET1(handle, (uint64_t)PM_RET_SUCCESS |
-				 ((uint64_t)PM_VERSION << 32));
+				 ((uint64_t)pm_ctx.api_version << 32));
 		}
 
-		ret = pm_get_api_version(&pm_ctx.api_version);
-		/*
-		 * Enable IPI IRQ
-		 * assume the rich OS is OK to handle callback IRQs now.
-		 * Even if we were wrong, it would not enable the IRQ in
-		 * the GIC.
-		 */
-		pm_ipi_irq_enable(primary_proc);
-		SMC_RET1(handle, (uint64_t)ret |
-			 ((uint64_t)pm_ctx.api_version << 32));
-
 	case PM_SET_CONFIGURATION:
 		ret = pm_set_configuration(pm_arg[0]);
 		SMC_RET1(handle, (uint64_t)ret);
@@ -474,8 +485,8 @@
 	{
 		uint32_t data[4] = { 0 };
 
-		ret = pm_query_data(pm_arg[0], pm_arg[1], pm_arg[2],
-				    pm_arg[3], data);
+		pm_query_data(pm_arg[0], pm_arg[1], pm_arg[2],
+			      pm_arg[3], data);
 		SMC_RET2(handle, (uint64_t)data[0]  | ((uint64_t)data[1] << 32),
 			 (uint64_t)data[2] | ((uint64_t)data[3] << 32));
 	}
@@ -606,8 +617,78 @@
 		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)mode << 32));
 	}
 
+	case PM_REGISTER_ACCESS:
+	{
+		uint32_t value;
+
+		ret = pm_register_access(pm_arg[0], pm_arg[1], pm_arg[2],
+					 pm_arg[3], &value);
+		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
+	}
+
+	case PM_EFUSE_ACCESS:
+	{
+		uint32_t value;
+
+		ret = pm_efuse_access(pm_arg[0], pm_arg[1], &value);
+		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
+	}
+
 	default:
 		WARN("Unimplemented PM Service Call: 0x%x\n", smc_fid);
 		SMC_RET1(handle, SMC_UNK);
 	}
 }
+
+/**
+ * em_smc_handler() - SMC handler for EM-API calls coming from EL1/EL2.
+ * @smc_fid - Function Identifier
+ * @x1 - x4 - Arguments
+ * @cookie  - Unused
+ * @handler - Pointer to caller's context structure
+ *
+ * @return  - Unused
+ *
+ * Determines that smc_fid is valid and supported EM SMC Function ID from the
+ * list of em_api_ids, otherwise completes the request with
+ * the unknown SMC Function ID
+ *
+ * The SMC calls for EM service are forwarded from SIP Service SMC handler
+ * function with rt_svc_handle signature
+ */
+uint64_t em_smc_handler(uint32_t smc_fid, uint64_t x1, uint64_t x2, uint64_t x3,
+			uint64_t x4, void *cookie, void *handle, uint64_t flags)
+{
+	enum pm_ret_status ret;
+
+	switch (smc_fid & FUNCID_NUM_MASK) {
+	/* EM API Functions */
+	case EM_SET_ACTION:
+	{
+		uint32_t value;
+
+		ret = em_set_action(&value);
+		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
+	}
+
+	case EM_REMOVE_ACTION:
+	{
+		uint32_t value;
+
+		ret = em_remove_action(&value);
+		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
+	}
+
+	case EM_SEND_ERRORS:
+	{
+		uint32_t value;
+
+		ret = em_send_errors(&value);
+		SMC_RET1(handle, (uint64_t)ret | ((uint64_t)value) << 32);
+	}
+
+	default:
+		WARN("Unimplemented EM Service Call: 0x%x\n", smc_fid);
+		SMC_RET1(handle, SMC_UNK);
+	}
+}
diff --git a/plat/xilinx/zynqmp/pm_service/pm_svc_main.h b/plat/xilinx/zynqmp/pm_service/pm_svc_main.h
index 0968f64..abadd40 100644
--- a/plat/xilinx/zynqmp/pm_service/pm_svc_main.h
+++ b/plat/xilinx/zynqmp/pm_service/pm_svc_main.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2015, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -14,4 +14,7 @@
 			uint64_t x4, void *cookie, void *handle,
 			uint64_t flags);
 
+uint64_t em_smc_handler(uint32_t smc_fid, uint64_t x1, uint64_t x2, uint64_t x3,
+			uint64_t x4, void *cookie, void *handle,
+			uint64_t flags);
 #endif /* PM_SVC_MAIN_H */
diff --git a/plat/xilinx/zynqmp/sip_svc_setup.c b/plat/xilinx/zynqmp/sip_svc_setup.c
index 9b18274..114da33 100644
--- a/plat/xilinx/zynqmp/sip_svc_setup.c
+++ b/plat/xilinx/zynqmp/sip_svc_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -25,6 +25,9 @@
 #define PM_FID_MASK	0xf000u
 #define PM_FID_VALUE	0u
 #define IPI_FID_VALUE	0x1000u
+#define EM_FID_MASK     0xf0000u
+#define EM_FID_VALUE    0xE0000u
+#define is_em_fid(_fid) (((_fid) & EM_FID_MASK) == EM_FID_VALUE)
 #define is_pm_fid(_fid) (((_fid) & PM_FID_MASK) == PM_FID_VALUE)
 #define is_ipi_fid(_fid) (((_fid) & PM_FID_MASK) == IPI_FID_VALUE)
 
@@ -41,9 +44,7 @@
 static int32_t sip_svc_setup(void)
 {
 	/* PM implementation as SiP Service */
-	pm_setup();
-
-	return 0;
+	return pm_setup();
 }
 
 /**
@@ -61,8 +62,12 @@
 			      void *handle,
 			      u_register_t flags)
 {
+	/* Let EM SMC handler deal with EM-related requests */
+	if (is_em_fid(smc_fid)) {
+		return em_smc_handler(smc_fid, x1, x2, x3, x4, cookie, handle,
+					flags);
+	} else if (is_pm_fid(smc_fid)) {
 	/* Let PM SMC handler deal with PM-related requests */
-	if (is_pm_fid(smc_fid)) {
 		return pm_smc_handler(smc_fid, x1, x2, x3, x4, cookie, handle,
 				      flags);
 	}
diff --git a/plat/xilinx/zynqmp/zynqmp_ehf.c b/plat/xilinx/zynqmp/zynqmp_ehf.c
new file mode 100644
index 0000000..fbf1ed0
--- /dev/null
+++ b/plat/xilinx/zynqmp/zynqmp_ehf.c
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) Siemens AG, 2020-2021
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <platform_def.h>
+
+#include <bl31/ehf.h>
+
+/*
+ * Enumeration of priority levels on ARM platforms.
+ */
+ehf_pri_desc_t zynqmp_exceptions[] = {
+	/* Critical priority SDEI */
+	EHF_PRI_DESC(PLAT_PRI_BITS, PLAT_SDEI_CRITICAL_PRI),
+
+	/* Normal priority SDEI */
+	EHF_PRI_DESC(PLAT_PRI_BITS, PLAT_SDEI_NORMAL_PRI),
+};
+
+/* Plug in ARM exceptions to Exception Handling Framework. */
+EHF_REGISTER_PRIORITIES(zynqmp_exceptions, ARRAY_SIZE(zynqmp_exceptions), PLAT_PRI_BITS);
diff --git a/plat/xilinx/zynqmp/zynqmp_sdei.c b/plat/xilinx/zynqmp/zynqmp_sdei.c
new file mode 100644
index 0000000..7e92b58
--- /dev/null
+++ b/plat/xilinx/zynqmp/zynqmp_sdei.c
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) Siemens AG, 2020-2021
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+/* SDEI configuration for ARM platforms */
+
+#include <bl31/ehf.h>
+#include <common/debug.h>
+#include <services/sdei.h>
+
+#include <plat/common/platform.h>
+#include <platform_def.h>
+
+int arm_validate_ns_entrypoint(uintptr_t entrypoint)
+{
+	return (entrypoint < BL31_BASE || entrypoint > BL31_LIMIT) ? 0 : -1;
+}
+
+/* Private event mappings */
+static sdei_ev_map_t zynqmp_sdei_private[] = {
+	SDEI_DEFINE_EVENT_0(ZYNQMP_SDEI_SGI_PRIVATE),
+};
+
+/* Shared event mappings */
+static sdei_ev_map_t zynqmp_sdei_shared[] = {
+};
+
+void plat_sdei_setup(void)
+{
+	INFO("SDEI platform setup\n");
+}
+
+/* Export ARM SDEI events */
+REGISTER_SDEI_MAP(zynqmp_sdei_private, zynqmp_sdei_shared);
diff --git a/services/arm_arch_svc/arm_arch_svc_setup.c b/services/arm_arch_svc/arm_arch_svc_setup.c
index 37bfc62..1d4423c 100644
--- a/services/arm_arch_svc/arm_arch_svc_setup.c
+++ b/services/arm_arch_svc/arm_arch_svc_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2018-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2018-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -11,9 +11,19 @@
 #include <lib/cpus/wa_cve_2018_3639.h>
 #include <lib/smccc.h>
 #include <services/arm_arch_svc.h>
+#include <services/rmi_svc.h>
+#include <services/rmmd_svc.h>
 #include <smccc_helpers.h>
 #include <plat/common/platform.h>
 
+#if ENABLE_RME
+/* Setup Arm architecture Services */
+static int32_t arm_arch_svc_setup(void)
+{
+	return rmmd_setup();
+}
+#endif
+
 static int32_t smccc_version(void)
 {
 	return MAKE_SMCCC_VERSION(SMCCC_MAJOR_VERSION, SMCCC_MINOR_VERSION);
@@ -133,6 +143,16 @@
 		SMC_RET0(handle);
 #endif
 	default:
+#if ENABLE_RME
+		/*
+		 * RMI functions are allocated from the Arch service range. Call
+		 * the RMM dispatcher to handle RMI calls.
+		 */
+		if (is_rmi_fid(smc_fid)) {
+			return rmmd_rmi_handler(smc_fid, x1, x2, x3, x4, cookie,
+						handle, flags);
+		}
+#endif
 		WARN("Unimplemented Arm Architecture Service Call: 0x%x \n",
 			smc_fid);
 		SMC_RET1(handle, SMC_UNK);
@@ -145,6 +165,10 @@
 		OEN_ARM_START,
 		OEN_ARM_END,
 		SMC_TYPE_FAST,
+#if ENABLE_RME
+		arm_arch_svc_setup,
+#else
 		NULL,
+#endif
 		arm_arch_svc_smc_handler
 );
diff --git a/services/spd/trusty/trusty.c b/services/spd/trusty/trusty.c
index fef1294..e0f1ba2 100644
--- a/services/spd/trusty/trusty.c
+++ b/services/spd/trusty/trusty.c
@@ -6,8 +6,10 @@
  */
 
 #include <assert.h>
+#include <inttypes.h>
 #include <lib/xlat_tables/xlat_tables_v2.h>
 #include <stdbool.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <arch_helpers.h>
@@ -172,7 +174,7 @@
 	struct trusty_cpu_ctx *ctx;
 
 	if (cpu >= (uint64_t)PLATFORM_CORE_COUNT) {
-		ERROR("%s: cpu %lld >= %d\n", __func__, cpu, PLATFORM_CORE_COUNT);
+		ERROR("%s: cpu %" PRId64 " >= %d\n", __func__, cpu, PLATFORM_CORE_COUNT);
 		return (uint64_t)SM_ERR_INVALID_PARAMETERS;
 	}
 
@@ -204,7 +206,7 @@
 
 	ret = trusty_context_switch(NON_SECURE, SMC_FC_FIQ_EXIT, 0, 0, 0);
 	if (ret.r0 != 1U) {
-		INFO("%s(%p) SMC_FC_FIQ_EXIT returned unexpected value, %lld\n",
+		INFO("%s(%p) SMC_FC_FIQ_EXIT returned unexpected value, %" PRId64 "\n",
 		       __func__, handle, ret.r0);
 	}
 
@@ -356,7 +358,7 @@
 
 	ret = trusty_context_switch(NON_SECURE, SMC_FC_CPU_SUSPEND, off, 0, 0);
 	if (ret.r0 != 0U) {
-		INFO("%s: cpu %d, SMC_FC_CPU_SUSPEND returned unexpected value, %lld\n",
+		INFO("%s: cpu %d, SMC_FC_CPU_SUSPEND returned unexpected value, %" PRId64 "\n",
 		     __func__, plat_my_core_pos(), ret.r0);
 	}
 }
@@ -367,7 +369,7 @@
 
 	ret = trusty_context_switch(NON_SECURE, SMC_FC_CPU_RESUME, on, 0, 0);
 	if (ret.r0 != 0U) {
-		INFO("%s: cpu %d, SMC_FC_CPU_RESUME returned unexpected value, %lld\n",
+		INFO("%s: cpu %d, SMC_FC_CPU_RESUME returned unexpected value, %" PRId64 "\n",
 		     __func__, plat_my_core_pos(), ret.r0);
 	}
 }
diff --git a/services/spd/tspd/tspd_main.c b/services/spd/tspd/tspd_main.c
index b0cbf62..29fc238 100644
--- a/services/spd/tspd/tspd_main.c
+++ b/services/spd/tspd/tspd_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -92,6 +92,18 @@
  * This function is the handler registered for S-EL1 interrupts by the TSPD. It
  * validates the interrupt and upon success arranges entry into the TSP at
  * 'tsp_sel1_intr_entry()' for handling the interrupt.
+ * Typically, interrupts for a specific security state get handled in the same
+ * security execption level if the execution is in the same security state. For
+ * example, if a non-secure interrupt gets fired when CPU is executing in NS-EL2
+ * it gets handled in the non-secure world.
+ * However, interrupts belonging to the opposite security state typically demand
+ * a world(context) switch. This is inline with the security principle which
+ * states a secure interrupt has to be handled in the secure world.
+ * Hence, the TSPD in EL3 expects the context(handle) for a secure interrupt to
+ * be non-secure and vice versa.
+ * However, a race condition between non-secure and secure interrupts can lead to
+ * a scenario where the above assumptions do not hold true. This is demonstrated
+ * below through Note 1.
  ******************************************************************************/
 static uint64_t tspd_sel1_interrupt_handler(uint32_t id,
 					    uint32_t flags,
@@ -101,6 +113,60 @@
 	uint32_t linear_id;
 	tsp_context_t *tsp_ctx;
 
+	/* Get a reference to this cpu's TSP context */
+	linear_id = plat_my_core_pos();
+	tsp_ctx = &tspd_sp_context[linear_id];
+
+#if TSP_NS_INTR_ASYNC_PREEMPT
+
+	/*
+	 * Note 1:
+	 * Under the current interrupt routing model, interrupts from other
+	 * world are routed to EL3 when TSP_NS_INTR_ASYNC_PREEMPT is enabled.
+	 * Consider the following scenario:
+	 * 1/ A non-secure payload(like tftf) requests a secure service from
+	 *    TSP by invoking a yielding SMC call.
+	 * 2/ Later, execution jumps to TSP in S-EL1 with the help of TSP
+	 *    Dispatcher in Secure Monitor(EL3).
+	 * 3/ While CPU is executing TSP, a Non-secure interrupt gets fired.
+	 *    this demands a context switch to the non-secure world through
+	 *    secure monitor.
+	 * 4/ Consequently, TSP in S-EL1 get asynchronously pre-empted and
+	 *    execution switches to secure monitor(EL3).
+	 * 5/ EL3 tries to triage the (Non-secure) interrupt based on the
+	 *    highest pending interrupt.
+	 * 6/ However, while the NS Interrupt was pending, secure timer gets
+	 *    fired which makes a S-EL1 interrupt to be pending.
+	 * 7/ Hence, execution jumps to this companion handler of S-EL1
+	 *    interrupt (i.e., tspd_sel1_interrupt_handler) even though the TSP
+	 *    was pre-empted due to non-secure interrupt.
+	 * 8/ The above sequence of events explain how TSP was pre-empted by
+	 *    S-EL1 interrupt indirectly in an asynchronous way.
+	 * 9/ Hence, we track the TSP pre-emption by S-EL1 interrupt using a
+	 *    boolean variable per each core.
+	 * 10/ This helps us to indicate that SMC call for TSP service was
+	 *    pre-empted when execution resumes in non-secure world.
+	 */
+
+	/* Check the security state when the exception was generated */
+	if (get_interrupt_src_ss(flags) == NON_SECURE) {
+		/* Sanity check the pointer to this cpu's context */
+		assert(handle == cm_get_context(NON_SECURE));
+
+		/* Save the non-secure context before entering the TSP */
+		cm_el1_sysregs_context_save(NON_SECURE);
+		tsp_ctx->preempted_by_sel1_intr = false;
+	} else {
+		/* Sanity check the pointer to this cpu's context */
+		assert(handle == cm_get_context(SECURE));
+
+		/* Save the secure context before entering the TSP for S-EL1
+		 * interrupt handling
+		 */
+		cm_el1_sysregs_context_save(SECURE);
+		tsp_ctx->preempted_by_sel1_intr = true;
+	}
+#else
 	/* Check the security state when the exception was generated */
 	assert(get_interrupt_src_ss(flags) == NON_SECURE);
 
@@ -109,10 +175,8 @@
 
 	/* Save the non-secure context before entering the TSP */
 	cm_el1_sysregs_context_save(NON_SECURE);
+#endif
 
-	/* Get a reference to this cpu's TSP context */
-	linear_id = plat_my_core_pos();
-	tsp_ctx = &tspd_sp_context[linear_id];
 	assert(&tsp_ctx->cpu_ctx == cm_get_context(SECURE));
 
 	/*
@@ -131,7 +195,6 @@
 		tsp_ctx->saved_elr_el3 = SMC_GET_EL3(&tsp_ctx->cpu_ctx,
 						     CTX_ELR_EL3);
 #if TSP_NS_INTR_ASYNC_PREEMPT
-		/*Need to save the previously interrupted secure context */
 		memcpy(&tsp_ctx->sp_ctx, &tsp_ctx->cpu_ctx, TSPD_SP_CTX_SIZE);
 #endif
 	}
@@ -353,7 +416,20 @@
 		cm_el1_sysregs_context_restore(NON_SECURE);
 		cm_set_next_eret_context(NON_SECURE);
 
+		/* Refer to Note 1 in function tspd_sel1_interrupt_handler()*/
+#if TSP_NS_INTR_ASYNC_PREEMPT
+		if (tsp_ctx->preempted_by_sel1_intr) {
+			/* Reset the flag */
+			tsp_ctx->preempted_by_sel1_intr = false;
+
+			SMC_RET1(ns_cpu_context, SMC_PREEMPTED);
+		} else {
+			SMC_RET0((uint64_t) ns_cpu_context);
+		}
+#else
 		SMC_RET0((uint64_t) ns_cpu_context);
+#endif
+
 
 	/*
 	 * This function ID is used only by the SP to indicate it has
diff --git a/services/spd/tspd/tspd_private.h b/services/spd/tspd/tspd_private.h
index a81eb21..d6c03c9 100644
--- a/services/spd/tspd/tspd_private.h
+++ b/services/spd/tspd/tspd_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013-2018, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2013-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -188,6 +188,7 @@
 	uint64_t saved_tsp_args[TSP_NUM_ARGS];
 #if TSP_NS_INTR_ASYNC_PREEMPT
 	sp_ctx_regs_t sp_ctx;
+	bool preempted_by_sel1_intr;
 #endif
 } tsp_context_t;
 
diff --git a/services/std_svc/pci_svc.c b/services/std_svc/pci_svc.c
new file mode 100644
index 0000000..a02b8a7
--- /dev/null
+++ b/services/std_svc/pci_svc.c
@@ -0,0 +1,113 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdint.h>
+
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <services/pci_svc.h>
+#include <services/std_svc.h>
+#include <smccc_helpers.h>
+
+static uint64_t validate_rw_addr_sz(uint32_t addr, uint64_t off, uint64_t sz)
+{
+	uint32_t nseg;
+	uint32_t ret;
+	uint32_t start_end_bus;
+
+	ret = pci_get_bus_for_seg(PCI_ADDR_SEG(addr), &start_end_bus, &nseg);
+
+	if (ret != SMC_PCI_CALL_SUCCESS) {
+		return SMC_PCI_CALL_INVAL_PARAM;
+	}
+	switch (sz) {
+	case SMC_PCI_SZ_8BIT:
+	case SMC_PCI_SZ_16BIT:
+	case SMC_PCI_SZ_32BIT:
+		break;
+	default:
+		return SMC_PCI_CALL_INVAL_PARAM;
+	}
+	if ((off + sz) > (PCI_OFFSET_MASK + 1U)) {
+		return SMC_PCI_CALL_INVAL_PARAM;
+	}
+	return SMC_PCI_CALL_SUCCESS;
+}
+
+uint64_t pci_smc_handler(uint32_t smc_fid,
+			     u_register_t x1,
+			     u_register_t x2,
+			     u_register_t x3,
+			     u_register_t x4,
+			     void *cookie,
+			     void *handle,
+			     u_register_t flags)
+{
+	switch (smc_fid) {
+	case SMC_PCI_VERSION: {
+		pcie_version ver;
+
+		ver.major = 1U;
+		ver.minor = 0U;
+		SMC_RET4(handle, ver.val, 0U, 0U, 0U);
+	}
+	case SMC_PCI_FEATURES:
+		switch (x1) {
+		case SMC_PCI_VERSION:
+		case SMC_PCI_FEATURES:
+		case SMC_PCI_READ:
+		case SMC_PCI_WRITE:
+		case SMC_PCI_SEG_INFO:
+			SMC_RET1(handle, SMC_PCI_CALL_SUCCESS);
+		default:
+			SMC_RET1(handle, SMC_PCI_CALL_NOT_SUPPORTED);
+		}
+		break;
+	case SMC_PCI_READ: {
+		uint32_t ret;
+
+		if (validate_rw_addr_sz(x1, x2, x3) != SMC_PCI_CALL_SUCCESS) {
+			SMC_RET2(handle, SMC_PCI_CALL_INVAL_PARAM, 0U);
+		}
+		if (x4 != 0U) {
+			SMC_RET2(handle, SMC_PCI_CALL_INVAL_PARAM, 0U);
+		}
+		if (pci_read_config(x1, x2, x3, &ret) != 0U) {
+			SMC_RET2(handle, SMC_PCI_CALL_INVAL_PARAM, 0U);
+		} else {
+			SMC_RET2(handle, SMC_PCI_CALL_SUCCESS, ret);
+		}
+		break;
+	}
+	case SMC_PCI_WRITE: {
+		uint32_t ret;
+
+		if (validate_rw_addr_sz(x1, x2, x3) != SMC_PCI_CALL_SUCCESS) {
+			SMC_RET1(handle, SMC_PCI_CALL_INVAL_PARAM);
+		}
+		ret = pci_write_config(x1, x2, x3, x4);
+		SMC_RET1(handle, ret);
+		break;
+	}
+	case SMC_PCI_SEG_INFO: {
+		uint32_t nseg;
+		uint32_t ret;
+		uint32_t start_end_bus;
+
+		if ((x2 != 0U) || (x3 != 0U) || (x4 != 0U)) {
+		    SMC_RET3(handle, SMC_PCI_CALL_INVAL_PARAM, 0U, 0U);
+		}
+		ret = pci_get_bus_for_seg(x1, &start_end_bus, &nseg);
+		SMC_RET3(handle, ret, start_end_bus, nseg);
+		break;
+	}
+	default:
+		/* should be unreachable */
+		WARN("Unimplemented PCI Service Call: 0x%x\n", smc_fid);
+		SMC_RET1(handle, SMC_PCI_CALL_NOT_SUPPORTED);
+	}
+}
diff --git a/services/std_svc/rmmd/aarch64/rmmd_helpers.S b/services/std_svc/rmmd/aarch64/rmmd_helpers.S
new file mode 100644
index 0000000..6229baf
--- /dev/null
+++ b/services/std_svc/rmmd/aarch64/rmmd_helpers.S
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include "../rmmd_private.h"
+#include <asm_macros.S>
+
+	.global rmmd_rmm_enter
+	.global rmmd_rmm_exit
+
+	/* ---------------------------------------------------------------------
+	 * This function is called with SP_EL0 as stack. Here we stash our EL3
+	 * callee-saved registers on to the stack as a part of saving the C
+	 * runtime and enter the secure payload.
+	 * 'x0' contains a pointer to the memory where the address of the C
+	 *  runtime context is to be saved.
+	 * ---------------------------------------------------------------------
+	 */
+func rmmd_rmm_enter
+	/* Make space for the registers that we're going to save */
+	mov	x3, sp
+	str	x3, [x0, #0]
+	sub	sp, sp, #RMMD_C_RT_CTX_SIZE
+
+	/* Save callee-saved registers on to the stack */
+	stp	x19, x20, [sp, #RMMD_C_RT_CTX_X19]
+	stp	x21, x22, [sp, #RMMD_C_RT_CTX_X21]
+	stp	x23, x24, [sp, #RMMD_C_RT_CTX_X23]
+	stp	x25, x26, [sp, #RMMD_C_RT_CTX_X25]
+	stp	x27, x28, [sp, #RMMD_C_RT_CTX_X27]
+	stp	x29, x30, [sp, #RMMD_C_RT_CTX_X29]
+
+	/* ---------------------------------------------------------------------
+	 * Everything is setup now. el3_exit() will use the secure context to
+	 * restore to the general purpose and EL3 system registers to ERET
+	 * into the secure payload.
+	 * ---------------------------------------------------------------------
+	 */
+	b	el3_exit
+endfunc rmmd_rmm_enter
+
+	/* ---------------------------------------------------------------------
+	 * This function is called with 'x0' pointing to a C runtime context.
+	 * It restores the saved registers and jumps to that runtime with 'x0'
+	 * as the new SP register. This destroys the C runtime context that had
+	 * been built on the stack below the saved context by the caller. Later
+	 * the second parameter 'x1' is passed as a return value to the caller.
+	 * ---------------------------------------------------------------------
+	 */
+func rmmd_rmm_exit
+	/* Restore the previous stack */
+	mov	sp, x0
+
+	/* Restore callee-saved registers on to the stack */
+	ldp	x19, x20, [x0, #(RMMD_C_RT_CTX_X19 - RMMD_C_RT_CTX_SIZE)]
+	ldp	x21, x22, [x0, #(RMMD_C_RT_CTX_X21 - RMMD_C_RT_CTX_SIZE)]
+	ldp	x23, x24, [x0, #(RMMD_C_RT_CTX_X23 - RMMD_C_RT_CTX_SIZE)]
+	ldp	x25, x26, [x0, #(RMMD_C_RT_CTX_X25 - RMMD_C_RT_CTX_SIZE)]
+	ldp	x27, x28, [x0, #(RMMD_C_RT_CTX_X27 - RMMD_C_RT_CTX_SIZE)]
+	ldp	x29, x30, [x0, #(RMMD_C_RT_CTX_X29 - RMMD_C_RT_CTX_SIZE)]
+
+	/* ---------------------------------------------------------------------
+	 * This should take us back to the instruction after the call to the
+	 * last rmmd_rmm_enter().* Place the second parameter to x0
+	 * so that the caller will see it as a return value from the original
+	 * entry call.
+	 * ---------------------------------------------------------------------
+	 */
+	mov	x0, x1
+	ret
+endfunc rmmd_rmm_exit
diff --git a/services/std_svc/rmmd/rmmd.mk b/services/std_svc/rmmd/rmmd.mk
new file mode 100644
index 0000000..bac0a9f
--- /dev/null
+++ b/services/std_svc/rmmd/rmmd.mk
@@ -0,0 +1,18 @@
+#
+# Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+ifneq (${ARCH},aarch64)
+        $(error "Error: RMMD is only supported on aarch64.")
+endif
+
+include services/std_svc/rmmd/trp/trp.mk
+
+RMMD_SOURCES	+=	$(addprefix services/std_svc/rmmd/,	\
+			${ARCH}/rmmd_helpers.S			\
+			rmmd_main.c)
+
+# Let the top-level Makefile know that we intend to include RMM image
+NEED_RMM	:=	yes
diff --git a/services/std_svc/rmmd/rmmd_initial_context.h b/services/std_svc/rmmd/rmmd_initial_context.h
new file mode 100644
index 0000000..d7a743d
--- /dev/null
+++ b/services/std_svc/rmmd/rmmd_initial_context.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RMMD_INITIAL_CONTEXT_H
+#define RMMD_INITIAL_CONTEXT_H
+
+#include <arch.h>
+
+/*
+ * SPSR_EL2
+ *   M=0x9 (0b1001 EL2h)
+ *   M[4]=0
+ *   DAIF=0xF Exceptions masked on entry.
+ *   BTYPE=0  BTI not yet supported.
+ *   SSBS=0   Not yet supported.
+ *   IL=0     Not an illegal exception return.
+ *   SS=0     Not single stepping.
+ *   PAN=1    RMM shouldn't access realm memory.
+ *   UAO=0
+ *   DIT=0
+ *   TCO=0
+ *   NZCV=0
+ */
+#define REALM_SPSR_EL2		(					\
+					SPSR_M_EL2H			| \
+					(0xF << SPSR_DAIF_SHIFT)	| \
+					SPSR_PAN_BIT			\
+				)
+
+#endif /* RMMD_INITIAL_CONTEXT_H */
diff --git a/services/std_svc/rmmd/rmmd_main.c b/services/std_svc/rmmd/rmmd_main.c
new file mode 100644
index 0000000..7f85b63
--- /dev/null
+++ b/services/std_svc/rmmd/rmmd_main.c
@@ -0,0 +1,347 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
+#include <string.h>
+
+#include <arch_helpers.h>
+#include <arch_features.h>
+#include <bl31/bl31.h>
+#include <common/debug.h>
+#include <common/runtime_svc.h>
+#include <context.h>
+#include <lib/el3_runtime/context_mgmt.h>
+#include <lib/el3_runtime/pubsub.h>
+#include <lib/gpt_rme/gpt_rme.h>
+
+#include <lib/spinlock.h>
+#include <lib/utils.h>
+#include <lib/xlat_tables/xlat_tables_v2.h>
+#include <plat/common/common_def.h>
+#include <plat/common/platform.h>
+#include <platform_def.h>
+#include <services/gtsi_svc.h>
+#include <services/rmi_svc.h>
+#include <services/rmmd_svc.h>
+#include <smccc_helpers.h>
+#include "rmmd_initial_context.h"
+#include "rmmd_private.h"
+
+/*******************************************************************************
+ * RMM context information.
+ ******************************************************************************/
+rmmd_rmm_context_t rmm_context[PLATFORM_CORE_COUNT];
+
+/*******************************************************************************
+ * RMM entry point information. Discovered on the primary core and reused
+ * on secondary cores.
+ ******************************************************************************/
+static entry_point_info_t *rmm_ep_info;
+
+/*******************************************************************************
+ * Static function declaration.
+ ******************************************************************************/
+static int32_t rmm_init(void);
+static uint64_t rmmd_smc_forward(uint32_t smc_fid, uint32_t src_sec_state,
+					uint32_t dst_sec_state, uint64_t x1,
+					uint64_t x2, uint64_t x3, uint64_t x4,
+					void *handle);
+
+/*******************************************************************************
+ * This function takes an RMM context pointer and performs a synchronous entry
+ * into it.
+ ******************************************************************************/
+uint64_t rmmd_rmm_sync_entry(rmmd_rmm_context_t *rmm_ctx)
+{
+	uint64_t rc;
+
+	assert(rmm_ctx != NULL);
+
+	cm_set_context(&(rmm_ctx->cpu_ctx), REALM);
+
+	/* Save the current el1/el2 context before loading realm context. */
+	cm_el1_sysregs_context_save(NON_SECURE);
+	cm_el2_sysregs_context_save(NON_SECURE);
+
+	/* Restore the realm context assigned above */
+	cm_el1_sysregs_context_restore(REALM);
+	cm_el2_sysregs_context_restore(REALM);
+	cm_set_next_eret_context(REALM);
+
+	/* Enter RMM */
+	rc = rmmd_rmm_enter(&rmm_ctx->c_rt_ctx);
+
+	/* Save realm context */
+	cm_el1_sysregs_context_save(REALM);
+	cm_el2_sysregs_context_save(REALM);
+
+	/* Restore the el1/el2 context again. */
+	cm_el1_sysregs_context_restore(NON_SECURE);
+	cm_el2_sysregs_context_restore(NON_SECURE);
+
+	return rc;
+}
+
+/*******************************************************************************
+ * This function returns to the place where rmmd_rmm_sync_entry() was
+ * called originally.
+ ******************************************************************************/
+__dead2 void rmmd_rmm_sync_exit(uint64_t rc)
+{
+	rmmd_rmm_context_t *ctx = &rmm_context[plat_my_core_pos()];
+
+	/* Get context of the RMM in use by this CPU. */
+	assert(cm_get_context(REALM) == &(ctx->cpu_ctx));
+
+	/*
+	 * The RMMD must have initiated the original request through a
+	 * synchronous entry into RMM. Jump back to the original C runtime
+	 * context with the value of rc in x0;
+	 */
+	rmmd_rmm_exit(ctx->c_rt_ctx, rc);
+
+	panic();
+}
+
+static void rmm_el2_context_init(el2_sysregs_t *regs)
+{
+	regs->ctx_regs[CTX_SPSR_EL2 >> 3] = REALM_SPSR_EL2;
+	regs->ctx_regs[CTX_SCTLR_EL2 >> 3] = SCTLR_EL2_RES1;
+}
+
+/*******************************************************************************
+ * Jump to the RMM for the first time.
+ ******************************************************************************/
+static int32_t rmm_init(void)
+{
+
+	uint64_t rc;
+
+	rmmd_rmm_context_t *ctx = &rmm_context[plat_my_core_pos()];
+
+	INFO("RMM init start.\n");
+	ctx->state = RMM_STATE_RESET;
+
+	/* Initialize RMM EL2 context. */
+	rmm_el2_context_init(&ctx->cpu_ctx.el2_sysregs_ctx);
+
+	rc = rmmd_rmm_sync_entry(ctx);
+	if (rc != 0ULL) {
+		ERROR("RMM initialisation failed 0x%" PRIx64 "\n", rc);
+		panic();
+	}
+
+	ctx->state = RMM_STATE_IDLE;
+	INFO("RMM init end.\n");
+
+	return 1;
+}
+
+/*******************************************************************************
+ * Load and read RMM manifest, setup RMM.
+ ******************************************************************************/
+int rmmd_setup(void)
+{
+	uint32_t ep_attr;
+	unsigned int linear_id = plat_my_core_pos();
+	rmmd_rmm_context_t *rmm_ctx = &rmm_context[linear_id];
+
+	/* Make sure RME is supported. */
+	assert(get_armv9_2_feat_rme_support() != 0U);
+
+	rmm_ep_info = bl31_plat_get_next_image_ep_info(REALM);
+	if (rmm_ep_info == NULL) {
+		WARN("No RMM image provided by BL2 boot loader, Booting "
+		     "device without RMM initialization. SMCs destined for "
+		     "RMM will return SMC_UNK\n");
+		return -ENOENT;
+	}
+
+	/* Under no circumstances will this parameter be 0 */
+	assert(rmm_ep_info->pc == RMM_BASE);
+
+	/* Initialise an entrypoint to set up the CPU context */
+	ep_attr = EP_REALM;
+	if ((read_sctlr_el3() & SCTLR_EE_BIT) != 0U) {
+		ep_attr |= EP_EE_BIG;
+	}
+
+	SET_PARAM_HEAD(rmm_ep_info, PARAM_EP, VERSION_1, ep_attr);
+	rmm_ep_info->spsr = SPSR_64(MODE_EL2,
+					MODE_SP_ELX,
+					DISABLE_ALL_EXCEPTIONS);
+
+	/* Initialise RMM context with this entry point information */
+	cm_setup_context(&rmm_ctx->cpu_ctx, rmm_ep_info);
+
+	INFO("RMM setup done.\n");
+
+	/* Register init function for deferred init.  */
+	bl31_register_rmm_init(&rmm_init);
+
+	return 0;
+}
+
+/*******************************************************************************
+ * Forward SMC to the other security state
+ ******************************************************************************/
+static uint64_t	rmmd_smc_forward(uint32_t smc_fid, uint32_t src_sec_state,
+					uint32_t dst_sec_state, uint64_t x1,
+					uint64_t x2, uint64_t x3, uint64_t x4,
+					void *handle)
+{
+	/* Save incoming security state */
+	cm_el1_sysregs_context_save(src_sec_state);
+	cm_el2_sysregs_context_save(src_sec_state);
+
+	/* Restore outgoing security state */
+	cm_el1_sysregs_context_restore(dst_sec_state);
+	cm_el2_sysregs_context_restore(dst_sec_state);
+	cm_set_next_eret_context(dst_sec_state);
+
+	SMC_RET8(cm_get_context(dst_sec_state), smc_fid, x1, x2, x3, x4,
+			SMC_GET_GP(handle, CTX_GPREG_X5),
+			SMC_GET_GP(handle, CTX_GPREG_X6),
+			SMC_GET_GP(handle, CTX_GPREG_X7));
+}
+
+/*******************************************************************************
+ * This function handles all SMCs in the range reserved for RMI. Each call is
+ * either forwarded to the other security state or handled by the RMM dispatcher
+ ******************************************************************************/
+uint64_t rmmd_rmi_handler(uint32_t smc_fid, uint64_t x1, uint64_t x2,
+				uint64_t x3, uint64_t x4, void *cookie,
+				void *handle, uint64_t flags)
+{
+	rmmd_rmm_context_t *ctx = &rmm_context[plat_my_core_pos()];
+	uint32_t src_sec_state;
+
+	/* Determine which security state this SMC originated from */
+	src_sec_state = caller_sec_state(flags);
+
+	/* RMI must not be invoked by the Secure world */
+	if (src_sec_state == SMC_FROM_SECURE) {
+		WARN("RMM: RMI invoked by secure world.\n");
+		SMC_RET1(handle, SMC_UNK);
+	}
+
+	/*
+	 * Forward an RMI call from the Normal world to the Realm world as it
+	 * is.
+	 */
+	if (src_sec_state == SMC_FROM_NON_SECURE) {
+		VERBOSE("RMM: RMI call from non-secure world.\n");
+		return rmmd_smc_forward(smc_fid, NON_SECURE, REALM,
+					x1, x2, x3, x4, handle);
+	}
+
+	assert(src_sec_state == SMC_FROM_REALM);
+
+	switch (smc_fid) {
+	case RMI_RMM_REQ_COMPLETE:
+		if (ctx->state == RMM_STATE_RESET) {
+			VERBOSE("RMM: running rmmd_rmm_sync_exit\n");
+			rmmd_rmm_sync_exit(x1);
+		}
+
+		return rmmd_smc_forward(x1, REALM, NON_SECURE,
+					x2, x3, x4, 0, handle);
+
+	default:
+		WARN("RMM: Unsupported RMM call 0x%08x\n", smc_fid);
+		SMC_RET1(handle, SMC_UNK);
+	}
+}
+
+/*******************************************************************************
+ * This cpu has been turned on. Enter RMM to initialise R-EL2.  Entry into RMM
+ * is done after initialising minimal architectural state that guarantees safe
+ * execution.
+ ******************************************************************************/
+static void *rmmd_cpu_on_finish_handler(const void *arg)
+{
+	int32_t rc;
+	uint32_t linear_id = plat_my_core_pos();
+	rmmd_rmm_context_t *ctx = &rmm_context[linear_id];
+
+	ctx->state = RMM_STATE_RESET;
+
+	/* Initialise RMM context with this entry point information */
+	cm_setup_context(&ctx->cpu_ctx, rmm_ep_info);
+
+	/* Initialize RMM EL2 context. */
+	rmm_el2_context_init(&ctx->cpu_ctx.el2_sysregs_ctx);
+
+	rc = rmmd_rmm_sync_entry(ctx);
+	if (rc != 0) {
+		ERROR("RMM initialisation failed (%d) on CPU%d\n", rc,
+		      linear_id);
+		panic();
+	}
+
+	ctx->state = RMM_STATE_IDLE;
+	return NULL;
+}
+
+/* Subscribe to PSCI CPU on to initialize RMM on secondary */
+SUBSCRIBE_TO_EVENT(psci_cpu_on_finish, rmmd_cpu_on_finish_handler);
+
+static int gtsi_transition_granule(uint64_t pa,
+					unsigned int src_sec_state,
+					unsigned int target_pas)
+{
+	int ret;
+
+	ret = gpt_transition_pas(pa, PAGE_SIZE_4KB, src_sec_state, target_pas);
+
+	/* Convert TF-A error codes into GTSI error codes */
+	if (ret == -EINVAL) {
+		ERROR("[GTSI] Transition failed: invalid %s\n", "address");
+		ERROR("       PA: 0x%" PRIx64 ", SRC: %d, PAS: %d\n", pa,
+		      src_sec_state, target_pas);
+		ret = GRAN_TRANS_RET_BAD_ADDR;
+	} else if (ret == -EPERM) {
+		ERROR("[GTSI] Transition failed: invalid %s\n", "caller/PAS");
+		ERROR("       PA: 0x%" PRIx64 ", SRC: %d, PAS: %d\n", pa,
+		      src_sec_state, target_pas);
+		ret = GRAN_TRANS_RET_BAD_PAS;
+	}
+
+	return ret;
+}
+
+/*******************************************************************************
+ * This function handles all SMCs in the range reserved for GTF.
+ ******************************************************************************/
+uint64_t rmmd_gtsi_handler(uint32_t smc_fid, uint64_t x1, uint64_t x2,
+				uint64_t x3, uint64_t x4, void *cookie,
+				void *handle, uint64_t flags)
+{
+	uint32_t src_sec_state;
+
+	/* Determine which security state this SMC originated from */
+	src_sec_state = caller_sec_state(flags);
+
+	if (src_sec_state != SMC_FROM_REALM) {
+		WARN("RMM: GTF call originated from secure or normal world\n");
+		SMC_RET1(handle, SMC_UNK);
+	}
+
+	switch (smc_fid) {
+	case SMC_ASC_MARK_REALM:
+		SMC_RET1(handle, gtsi_transition_granule(x1, SMC_FROM_REALM,
+								GPT_GPI_REALM));
+	case SMC_ASC_MARK_NONSECURE:
+		SMC_RET1(handle, gtsi_transition_granule(x1, SMC_FROM_REALM,
+								GPT_GPI_NS));
+	default:
+		WARN("RMM: Unsupported GTF call 0x%08x\n", smc_fid);
+		SMC_RET1(handle, SMC_UNK);
+	}
+}
diff --git a/services/std_svc/rmmd/rmmd_private.h b/services/std_svc/rmmd/rmmd_private.h
new file mode 100644
index 0000000..d170bcd
--- /dev/null
+++ b/services/std_svc/rmmd/rmmd_private.h
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef RMMD_PRIVATE_H
+#define RMMD_PRIVATE_H
+
+#include <context.h>
+
+/*******************************************************************************
+ * Constants that allow assembler code to preserve callee-saved registers of the
+ * C runtime context while performing a security state switch.
+ ******************************************************************************/
+#define RMMD_C_RT_CTX_X19		0x0
+#define RMMD_C_RT_CTX_X20		0x8
+#define RMMD_C_RT_CTX_X21		0x10
+#define RMMD_C_RT_CTX_X22		0x18
+#define RMMD_C_RT_CTX_X23		0x20
+#define RMMD_C_RT_CTX_X24		0x28
+#define RMMD_C_RT_CTX_X25		0x30
+#define RMMD_C_RT_CTX_X26		0x38
+#define RMMD_C_RT_CTX_X27		0x40
+#define RMMD_C_RT_CTX_X28		0x48
+#define RMMD_C_RT_CTX_X29		0x50
+#define RMMD_C_RT_CTX_X30		0x58
+
+#define RMMD_C_RT_CTX_SIZE		0x60
+#define RMMD_C_RT_CTX_ENTRIES		(RMMD_C_RT_CTX_SIZE >> DWORD_SHIFT)
+
+#ifndef __ASSEMBLER__
+#include <stdint.h>
+#include <services/rmi_svc.h>
+
+typedef enum rmm_state {
+	RMM_STATE_RESET = 0,
+	RMM_STATE_IDLE
+} rmm_state_t;
+
+/*
+ * Data structure used by the RMM dispatcher (RMMD) in EL3 to track context of
+ * the RMM at R-EL2.
+ */
+typedef struct rmmd_rmm_context {
+	uint64_t c_rt_ctx;
+	cpu_context_t cpu_ctx;
+	rmm_state_t state;
+} rmmd_rmm_context_t;
+
+/* Functions used to enter/exit the RMM synchronously */
+uint64_t rmmd_rmm_sync_entry(rmmd_rmm_context_t *ctx);
+__dead2 void rmmd_rmm_sync_exit(uint64_t rc);
+
+/* Assembly helpers */
+uint64_t rmmd_rmm_enter(uint64_t *c_rt_ctx);
+void __dead2 rmmd_rmm_exit(uint64_t c_rt_ctx, uint64_t ret);
+
+/* Reference to PM ops for the RMMD */
+extern const spd_pm_ops_t rmmd_pm;
+
+#endif /* __ASSEMBLER__ */
+
+#endif /* RMMD_PRIVATE_H */
diff --git a/services/std_svc/rmmd/trp/linker.lds b/services/std_svc/rmmd/trp/linker.lds
new file mode 100644
index 0000000..2b7f383
--- /dev/null
+++ b/services/std_svc/rmmd/trp/linker.lds
@@ -0,0 +1,71 @@
+/*
+ * (C) COPYRIGHT 2021 Arm Limited or its affiliates.
+ * ALL RIGHTS RESERVED
+ */
+
+#include <common/bl_common.ld.h>
+#include <lib/xlat_tables/xlat_tables_defs.h>
+
+/* Mapped using 4K pages, requires us to align different sections with
+ * different property at the same granularity. */
+PAGE_SIZE_4K = 4096;
+
+OUTPUT_FORMAT("elf64-littleaarch64")
+OUTPUT_ARCH(aarch64)
+ENTRY(trp_head)
+
+MEMORY {
+	RAM (rwx): ORIGIN = RMM_BASE, LENGTH = RMM_LIMIT - RMM_BASE
+}
+
+
+SECTIONS
+{
+	. = RMM_BASE;
+
+	.text : {
+		*(.head.text)
+		. = ALIGN(8);
+		*(.text*)
+	} >RAM
+
+	. = ALIGN(PAGE_SIZE_4K);
+
+	.rodata : {
+		*(.rodata*)
+	} >RAM
+
+	. = ALIGN(PAGE_SIZE_4K);
+
+	 __RW_START__ = . ;
+
+	.data : {
+		*(.data*)
+	} >RAM
+
+	.bss (NOLOAD) : {
+		__BSS_START__ = .;
+		*(.bss*)
+		__BSS_END__ = .;
+	} >RAM
+	__BSS_SIZE__ = SIZEOF(.bss);
+
+
+	STACK_SECTION >RAM
+
+
+	/*
+	* Define a linker symbol to mark the end of the RW memory area for this
+	* image.
+	*/
+	__RW_END__ = .;
+	__RMM_END__ = .;
+
+
+	/DISCARD/ : { *(.dynstr*) }
+	/DISCARD/ : { *(.dynamic*) }
+	/DISCARD/ : { *(.plt*) }
+	/DISCARD/ : { *(.interp*) }
+	/DISCARD/ : { *(.gnu*) }
+	/DISCARD/ : { *(.note*) }
+}
diff --git a/services/std_svc/rmmd/trp/trp.mk b/services/std_svc/rmmd/trp/trp.mk
new file mode 100644
index 0000000..a4f6e03
--- /dev/null
+++ b/services/std_svc/rmmd/trp/trp.mk
@@ -0,0 +1,20 @@
+#
+# Copyright (c) 2021 Arm Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+RMM_SOURCES		+=	services/std_svc/rmmd/trp/trp_entry.S	\
+				services/std_svc/rmmd/trp/trp_main.c
+
+RMM_LINKERFILE		:=	services/std_svc/rmmd/trp/linker.lds
+
+# Include the platform-specific TRP Makefile
+# If no platform-specific TRP Makefile exists, it means TRP is not supported
+# on this platform.
+TRP_PLAT_MAKEFILE := $(wildcard ${PLAT_DIR}/trp/trp-${PLAT}.mk)
+ifeq (,${TRP_PLAT_MAKEFILE})
+  $(error TRP is not supported on platform ${PLAT})
+else
+  include ${TRP_PLAT_MAKEFILE}
+endif
diff --git a/services/std_svc/rmmd/trp/trp_entry.S b/services/std_svc/rmmd/trp/trp_entry.S
new file mode 100644
index 0000000..23b48fb
--- /dev/null
+++ b/services/std_svc/rmmd/trp/trp_entry.S
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <asm_macros.S>
+#include <services/gtsi_svc.h>
+#include <services/rmi_svc.h>
+#include "trp_private.h"
+
+.global trp_head
+.global trp_smc
+
+.section ".head.text", "ax"
+
+	/* ---------------------------------------------
+	 * Populate the params in x0-x7 from the pointer
+	 * to the smc args structure in x0.
+	 * ---------------------------------------------
+	 */
+	.macro restore_args_call_smc
+	ldp	x6, x7, [x0, #TRP_ARG6]
+	ldp	x4, x5, [x0, #TRP_ARG4]
+	ldp	x2, x3, [x0, #TRP_ARG2]
+	ldp	x0, x1, [x0, #TRP_ARG0]
+	smc	#0
+	.endm
+
+	/* ---------------------------------------------
+	 * Entry point for TRP
+	 * ---------------------------------------------
+	 */
+trp_head:
+	bl	plat_set_my_stack
+	bl	plat_is_my_cpu_primary
+	cbz	x0, trp_secondary_cpu_entry
+
+	/* ---------------------------------------------
+	 * Zero out BSS section
+	 * ---------------------------------------------
+	 */
+	ldr	x0, =__BSS_START__
+	ldr	x1, =__BSS_SIZE__
+	bl	zeromem
+
+	bl	trp_setup
+
+	bl	trp_main
+trp_secondary_cpu_entry:
+	mov_imm	x0, RMI_RMM_REQ_COMPLETE
+	mov	x1, xzr
+	smc	#0
+	b	trp_handler
+
+	/* ---------------------------------------------
+	 *   Direct SMC call to BL31 service provided by
+	 *   RMM Dispatcher
+	 * ---------------------------------------------
+	 */
+func trp_smc
+	restore_args_call_smc
+	ret
+endfunc trp_smc
+
+	/* ---------------------------------------------
+	 * RMI call handler
+	 * ---------------------------------------------
+	 */
+func trp_handler
+	bl	trp_rmi_handler
+	restore_args_call_smc
+	b	trp_handler
+endfunc trp_handler
diff --git a/services/std_svc/rmmd/trp/trp_main.c b/services/std_svc/rmmd/trp/trp_main.c
new file mode 100644
index 0000000..2ab9ecc
--- /dev/null
+++ b/services/std_svc/rmmd/trp/trp_main.c
@@ -0,0 +1,136 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+
+#include <common/debug.h>
+#include <plat/common/platform.h>
+#include <services/gtsi_svc.h>
+#include <services/rmi_svc.h>
+#include <services/trp/platform_trp.h>
+
+#include <platform_def.h>
+#include "trp_private.h"
+
+/*******************************************************************************
+ * Per cpu data structure to populate parameters for an SMC in C code and use
+ * a pointer to this structure in assembler code to populate x0-x7
+ ******************************************************************************/
+static trp_args_t trp_smc_args[PLATFORM_CORE_COUNT];
+
+/*******************************************************************************
+ * Set the arguments for SMC call
+ ******************************************************************************/
+static trp_args_t *set_smc_args(uint64_t arg0,
+				uint64_t arg1,
+				uint64_t arg2,
+				uint64_t arg3,
+				uint64_t arg4,
+				uint64_t arg5,
+				uint64_t arg6,
+				uint64_t arg7)
+{
+	uint32_t linear_id;
+	trp_args_t *pcpu_smc_args;
+
+	/*
+	 * Return to Secure Monitor by raising an SMC. The results of the
+	 * service are passed as an arguments to the SMC
+	 */
+	linear_id = plat_my_core_pos();
+	pcpu_smc_args = &trp_smc_args[linear_id];
+	write_trp_arg(pcpu_smc_args, TRP_ARG0, arg0);
+	write_trp_arg(pcpu_smc_args, TRP_ARG1, arg1);
+	write_trp_arg(pcpu_smc_args, TRP_ARG2, arg2);
+	write_trp_arg(pcpu_smc_args, TRP_ARG3, arg3);
+	write_trp_arg(pcpu_smc_args, TRP_ARG4, arg4);
+	write_trp_arg(pcpu_smc_args, TRP_ARG5, arg5);
+	write_trp_arg(pcpu_smc_args, TRP_ARG6, arg6);
+	write_trp_arg(pcpu_smc_args, TRP_ARG7, arg7);
+
+	return pcpu_smc_args;
+}
+
+/*******************************************************************************
+ * Setup function for TRP.
+ ******************************************************************************/
+void trp_setup(void)
+{
+	/* Perform early platform-specific setup */
+	trp_early_platform_setup();
+}
+
+/* Main function for TRP */
+void trp_main(void)
+{
+	NOTICE("TRP: %s\n", version_string);
+	NOTICE("TRP: %s\n", build_message);
+	INFO("TRP: Memory base : 0x%lx\n", (unsigned long)RMM_BASE);
+	INFO("TRP: Total size : 0x%lx bytes\n", (unsigned long)(RMM_END
+								- RMM_BASE));
+}
+
+/*******************************************************************************
+ * Returning RMI version back to Normal World
+ ******************************************************************************/
+static trp_args_t *trp_ret_rmi_version(void)
+{
+	VERBOSE("RMM version is %u.%u\n", RMI_ABI_VERSION_MAJOR,
+					  RMI_ABI_VERSION_MINOR);
+	return set_smc_args(RMI_RMM_REQ_COMPLETE, RMI_ABI_VERSION,
+			    0, 0, 0, 0, 0, 0);
+}
+
+/*******************************************************************************
+ * Transitioning granule of NON-SECURE type to REALM type
+ ******************************************************************************/
+static trp_args_t *trp_asc_mark_realm(unsigned long long x1)
+{
+	unsigned long long ret;
+
+	VERBOSE("Delegating granule 0x%llx\n", x1);
+	ret = trp_smc(set_smc_args(SMC_ASC_MARK_REALM, x1, 0, 0, 0, 0, 0, 0));
+
+	if (ret != 0ULL) {
+		ERROR("Granule transition from NON-SECURE type to REALM type "
+			"failed 0x%llx\n", ret);
+	}
+	return set_smc_args(RMI_RMM_REQ_COMPLETE, ret, 0, 0, 0, 0, 0, 0);
+}
+
+/*******************************************************************************
+ * Transitioning granule of REALM type to NON-SECURE type
+ ******************************************************************************/
+static trp_args_t *trp_asc_mark_nonsecure(unsigned long long x1)
+{
+	unsigned long long ret;
+
+	VERBOSE("Undelegating granule 0x%llx\n", x1);
+	ret = trp_smc(set_smc_args(SMC_ASC_MARK_NONSECURE, x1, 0, 0, 0, 0, 0, 0));
+
+	if (ret != 0ULL) {
+		ERROR("Granule transition from REALM type to NON-SECURE type "
+			"failed 0x%llx\n", ret);
+	}
+	return set_smc_args(RMI_RMM_REQ_COMPLETE, ret, 0, 0, 0, 0, 0, 0);
+}
+
+/*******************************************************************************
+ * Main RMI SMC handler function
+ ******************************************************************************/
+trp_args_t *trp_rmi_handler(unsigned long fid, unsigned long long x1)
+{
+	switch (fid) {
+	case RMI_RMM_REQ_VERSION:
+		return trp_ret_rmi_version();
+	case RMI_RMM_GRANULE_DELEGATE:
+		return trp_asc_mark_realm(x1);
+	case RMI_RMM_GRANULE_UNDELEGATE:
+		return trp_asc_mark_nonsecure(x1);
+	default:
+		ERROR("Invalid SMC code to %s, FID %lu\n", __func__, fid);
+	}
+	return set_smc_args(SMC_UNK, 0, 0, 0, 0, 0, 0, 0);
+}
diff --git a/services/std_svc/rmmd/trp/trp_private.h b/services/std_svc/rmmd/trp/trp_private.h
new file mode 100644
index 0000000..9231390
--- /dev/null
+++ b/services/std_svc/rmmd/trp/trp_private.h
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2021, Arm Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TRP_PRIVATE_H
+#define TRP_PRIVATE_H
+
+/* Definitions to help the assembler access the SMC/ERET args structure */
+#define TRP_ARGS_SIZE		TRP_ARGS_END
+#define TRP_ARG0		0x0
+#define TRP_ARG1		0x8
+#define TRP_ARG2		0x10
+#define TRP_ARG3		0x18
+#define TRP_ARG4		0x20
+#define TRP_ARG5		0x28
+#define TRP_ARG6		0x30
+#define TRP_ARG7		0x38
+#define TRP_ARGS_END		0x40
+
+#ifndef __ASSEMBLER__
+
+#include <stdint.h>
+
+/* Data structure to hold SMC arguments */
+typedef struct trp_args {
+	uint64_t regs[TRP_ARGS_END >> 3];
+} __aligned(CACHE_WRITEBACK_GRANULE) trp_args_t;
+
+#define write_trp_arg(args, offset, val) (((args)->regs[offset >> 3])	\
+					 = val)
+
+/* Definitions for RMI VERSION */
+#define RMI_ABI_VERSION_MAJOR		U(0x0)
+#define RMI_ABI_VERSION_MINOR		U(0x0)
+#define RMI_ABI_VERSION			((RMI_ABI_VERSION_MAJOR << 16) | \
+					RMI_ABI_VERSION_MINOR)
+
+/* Helper to issue SMC calls to BL31 */
+uint64_t trp_smc(trp_args_t *);
+
+/* The main function to executed only by Primary CPU */
+void trp_main(void);
+
+/* Setup TRP. Executed only by Primary CPU */
+void trp_setup(void);
+
+#endif /* __ASSEMBLER__ */
+#endif /* TRP_PRIVATE_H */
diff --git a/services/std_svc/sdei/sdei_intr_mgmt.c b/services/std_svc/sdei/sdei_intr_mgmt.c
index fa1d3d2..87a1fb7 100644
--- a/services/std_svc/sdei/sdei_intr_mgmt.c
+++ b/services/std_svc/sdei/sdei_intr_mgmt.c
@@ -1,13 +1,16 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <arch_helpers.h>
+#include <arch_features.h>
 #include <bl31/ehf.h>
 #include <bl31/interrupt_mgmt.h>
 #include <common/bl_common.h>
@@ -232,6 +235,77 @@
 }
 
 /*
+ * Prepare for ERET:
+ * - Set the ELR to the registered handler address
+ * - Set the SPSR register as described in the SDEI documentation and
+ *   the AArch64.TakeException() pseudocode function in
+ *   ARM DDI 0487F.c page J1-7635
+ */
+
+static void sdei_set_elr_spsr(sdei_entry_t *se, sdei_dispatch_context_t *disp_ctx)
+{
+	unsigned int client_el = sdei_client_el();
+	u_register_t sdei_spsr = SPSR_64(client_el, MODE_SP_ELX,
+					DISABLE_ALL_EXCEPTIONS);
+
+	u_register_t interrupted_pstate = disp_ctx->spsr_el3;
+
+	/* Check the SPAN bit in the client el SCTLR */
+	u_register_t client_el_sctlr;
+
+	if (client_el == MODE_EL2) {
+		client_el_sctlr = read_sctlr_el2();
+	} else {
+		client_el_sctlr = read_sctlr_el1();
+	}
+
+	/*
+	 * Check whether to force the PAN bit or use the value in the
+	 * interrupted EL according to the check described in
+	 * TakeException. Since the client can only be Non-Secure
+	 * EL2 or El1 some of the conditions in ElIsInHost() we know
+	 * will always be True.
+	 * When the client_el is EL2 we know that there will be a SPAN
+	 * bit in SCTLR_EL2 as we have already checked for the condition
+	 * HCR_EL2.E2H = 1 and HCR_EL2.TGE = 1
+	 */
+	u_register_t hcr_el2 = read_hcr();
+	bool el_is_in_host = is_armv8_1_vhe_present() &&
+			     (hcr_el2 & HCR_TGE_BIT) &&
+			     (hcr_el2 & HCR_E2H_BIT);
+
+	if (is_armv8_1_pan_present() &&
+	    ((client_el == MODE_EL1) ||
+		(client_el == MODE_EL2 && el_is_in_host)) &&
+	    ((client_el_sctlr & SCTLR_SPAN_BIT) == 0U)) {
+		sdei_spsr |=  SPSR_PAN_BIT;
+	} else {
+		sdei_spsr |= (interrupted_pstate & SPSR_PAN_BIT);
+	}
+
+	/* If SSBS is implemented, take the value from the client el SCTLR */
+	u_register_t ssbs_enabled = (read_id_aa64pfr1_el1()
+					>> ID_AA64PFR1_EL1_SSBS_SHIFT)
+					& ID_AA64PFR1_EL1_SSBS_MASK;
+	if (ssbs_enabled != SSBS_UNAVAILABLE) {
+		u_register_t  ssbs_bit = ((client_el_sctlr & SCTLR_DSSBS_BIT)
+						>> SCTLR_DSSBS_SHIFT)
+						<< SPSR_SSBS_SHIFT_AARCH64;
+		sdei_spsr |= ssbs_bit;
+	}
+
+	/* If MTE is implemented in the client el set the TCO bit */
+	if (get_armv8_5_mte_support() >= MTE_IMPLEMENTED_ELX) {
+		sdei_spsr |= SPSR_TCO_BIT_AARCH64;
+	}
+
+	/* Take the DIT field from the pstate of the interrupted el */
+	sdei_spsr |= (interrupted_pstate & SPSR_DIT_BIT);
+
+	cm_set_elr_spsr_el3(NON_SECURE, (uintptr_t) se->ep, sdei_spsr);
+}
+
+/*
  * Populate the Non-secure context so that the next ERET will dispatch to the
  * SDEI client.
  */
@@ -256,15 +330,8 @@
 	SMC_SET_GP(ctx, CTX_GPREG_X2, disp_ctx->elr_el3);
 	SMC_SET_GP(ctx, CTX_GPREG_X3, disp_ctx->spsr_el3);
 
-	/*
-	 * Prepare for ERET:
-	 *
-	 * - Set PC to the registered handler address
-	 * - Set SPSR to jump to client EL with exceptions masked
-	 */
-	cm_set_elr_spsr_el3(NON_SECURE, (uintptr_t) se->ep,
-			SPSR_64(sdei_client_el(), MODE_SP_ELX,
-				DISABLE_ALL_EXCEPTIONS));
+	/* Setup the elr and spsr register to prepare for ERET */
+	sdei_set_elr_spsr(se, disp_ctx);
 
 #if DYNAMIC_WORKAROUND_CVE_2018_3639
 	cve_2018_3639_t *tgt_cve_2018_3639;
@@ -394,8 +461,8 @@
 		 * Interrupts received while this PE was masked can't be
 		 * dispatched.
 		 */
-		SDEI_LOG("interrupt %u on %llx while PE masked\n", map->intr,
-				mpidr);
+		SDEI_LOG("interrupt %u on %" PRIx64 " while PE masked\n",
+			 map->intr, mpidr);
 		if (is_event_shared(map))
 			sdei_map_lock(map);
 
@@ -466,8 +533,8 @@
 	if (is_event_shared(map))
 		sdei_map_unlock(map);
 
-	SDEI_LOG("ACK %llx, ev:%d ss:%d spsr:%lx ELR:%lx\n", mpidr, map->ev_num,
-			sec_state, read_spsr_el3(), read_elr_el3());
+	SDEI_LOG("ACK %" PRIx64 ", ev:0x%x ss:%d spsr:%lx ELR:%lx\n",
+		 mpidr, map->ev_num, sec_state, read_spsr_el3(), read_elr_el3());
 
 	ctx = handle;
 
@@ -503,7 +570,7 @@
 	 * interrupt.
 	 */
 	if ((map->ev_num != SDEI_EVENT_0) && !is_map_bound(map)) {
-		ERROR("Invalid SDEI mapping: ev=%u\n", map->ev_num);
+		ERROR("Invalid SDEI mapping: ev=0x%x\n", map->ev_num);
 		panic();
 	}
 	plat_ic_end_of_interrupt(intr_raw);
@@ -571,15 +638,15 @@
 	if (!can_sdei_state_trans(se, DO_DISPATCH))
 		return -1;
 
-	/* Activate the priority corresponding to the event being dispatched */
-	ehf_activate_priority(sdei_event_priority(map));
-
 	/*
 	 * Prepare for NS dispatch by restoring the Non-secure context and
 	 * marking that as active.
 	 */
 	ns_ctx = restore_and_resume_ns_context();
 
+	/* Activate the priority corresponding to the event being dispatched */
+	ehf_activate_priority(sdei_event_priority(map));
+
 	/* Dispatch event synchronously */
 	setup_ns_dispatch(map, se, ns_ctx, &dispatch_jmp);
 	begin_sdei_synchronous_dispatch(&dispatch_jmp);
diff --git a/services/std_svc/sdei/sdei_main.c b/services/std_svc/sdei/sdei_main.c
index dba5e07..44178ed 100644
--- a/services/std_svc/sdei/sdei_main.c
+++ b/services/std_svc/sdei/sdei_main.c
@@ -6,7 +6,9 @@
 
 #include <arch_helpers.h>
 #include <assert.h>
+#include <inttypes.h>
 #include <stddef.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <bl31/bl31.h>
@@ -314,6 +316,9 @@
 
 	/* Update event registration flag */
 	se->reg_flags = (unsigned int) flags;
+	if (flags == SDEI_REGF_RM_PE) {
+		se->affinity = (mpidr & MPIDR_AFFINITY_MASK);
+	}
 
 	/*
 	 * ROUTING_SET is permissible only when event composite state is
@@ -356,8 +361,20 @@
 		return SDEI_EINVAL;
 
 	/* Private events always target the PE */
-	if (is_event_private(map))
+	if (is_event_private(map)) {
+		/*
+		 * SDEI internally handles private events in the same manner
+		 * as public events with routing mode=RM_PE, since the routing
+		 * mode flag and affinity fields are not used when registering
+		 * a private event, set them here.
+		 */
 		flags = SDEI_REGF_RM_PE;
+		/*
+		 * Kernel may pass 0 as mpidr, as we set flags to
+		 * SDEI_REGF_RM_PE, so set mpidr also.
+		 */
+		mpidr = read_mpidr_el1();
+	}
 
 	se = get_event_entry(map);
 
@@ -958,33 +975,33 @@
 	case SDEI_VERSION:
 		SDEI_LOG("> VER\n");
 		ret = (int64_t) sdei_version();
-		SDEI_LOG("< VER:%llx\n", ret);
+		SDEI_LOG("< VER:%" PRIx64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_REGISTER:
 		x5 = SMC_GET_GP(ctx, CTX_GPREG_X5);
-		SDEI_LOG("> REG(n:%d e:%llx a:%llx f:%x m:%llx)\n", ev_num,
+		SDEI_LOG("> REG(n:%d e:%" PRIx64 " a:%" PRIx64 " f:%x m:%" PRIx64 "\n", ev_num,
 				x2, x3, (int) x4, x5);
 		ret = sdei_event_register(ev_num, x2, x3, x4, x5);
-		SDEI_LOG("< REG:%lld\n", ret);
+		SDEI_LOG("< REG:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_ENABLE:
 		SDEI_LOG("> ENABLE(n:%d)\n", (int) x1);
 		ret = sdei_event_enable(ev_num);
-		SDEI_LOG("< ENABLE:%lld\n", ret);
+		SDEI_LOG("< ENABLE:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_DISABLE:
-		SDEI_LOG("> DISABLE(n:%d)\n", ev_num);
+		SDEI_LOG("> DISABLE(n:0x%x)\n", ev_num);
 		ret = sdei_event_disable(ev_num);
-		SDEI_LOG("< DISABLE:%lld\n", ret);
+		SDEI_LOG("< DISABLE:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_CONTEXT:
 		SDEI_LOG("> CTX(p:%d):%lx\n", (int) x1, read_mpidr_el1());
 		ret = sdei_event_context(ctx, (unsigned int) x1);
-		SDEI_LOG("< CTX:%lld\n", ret);
+		SDEI_LOG("< CTX:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_COMPLETE_AND_RESUME:
@@ -992,10 +1009,10 @@
 		/* Fallthrough */
 
 	case SDEI_EVENT_COMPLETE:
-		SDEI_LOG("> COMPLETE(r:%u sta/ep:%llx):%lx\n",
-				(unsigned int) resume, x1, read_mpidr_el1());
+		SDEI_LOG("> COMPLETE(r:%u sta/ep:%" PRIx64 "):%lx\n",
+			 (unsigned int) resume, x1, read_mpidr_el1());
 		ret = sdei_event_complete(resume, x1);
-		SDEI_LOG("< COMPLETE:%llx\n", ret);
+		SDEI_LOG("< COMPLETE:%" PRIx64 "\n", ret);
 
 		/*
 		 * Set error code only if the call failed. If the call
@@ -1010,21 +1027,21 @@
 		SMC_RET0(ctx);
 
 	case SDEI_EVENT_STATUS:
-		SDEI_LOG("> STAT(n:%d)\n", ev_num);
+		SDEI_LOG("> STAT(n:0x%x)\n", ev_num);
 		ret = sdei_event_status(ev_num);
-		SDEI_LOG("< STAT:%lld\n", ret);
+		SDEI_LOG("< STAT:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_GET_INFO:
-		SDEI_LOG("> INFO(n:%d, %d)\n", ev_num, (int) x2);
+		SDEI_LOG("> INFO(n:0x%x, %d)\n", ev_num, (int) x2);
 		ret = sdei_event_get_info(ev_num, (int) x2);
-		SDEI_LOG("< INFO:%lld\n", ret);
+		SDEI_LOG("< INFO:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_UNREGISTER:
-		SDEI_LOG("> UNREG(n:%d)\n", ev_num);
+		SDEI_LOG("> UNREG(n:0x%x)\n", ev_num);
 		ret = sdei_event_unregister(ev_num);
-		SDEI_LOG("< UNREG:%lld\n", ret);
+		SDEI_LOG("< UNREG:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_PE_UNMASK:
@@ -1036,49 +1053,49 @@
 	case SDEI_PE_MASK:
 		SDEI_LOG("> MASK:%lx\n", read_mpidr_el1());
 		ret = sdei_pe_mask();
-		SDEI_LOG("< MASK:%lld\n", ret);
+		SDEI_LOG("< MASK:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_INTERRUPT_BIND:
 		SDEI_LOG("> BIND(%d)\n", (int) x1);
 		ret = sdei_interrupt_bind((unsigned int) x1);
-		SDEI_LOG("< BIND:%lld\n", ret);
+		SDEI_LOG("< BIND:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_INTERRUPT_RELEASE:
-		SDEI_LOG("> REL(%d)\n", ev_num);
+		SDEI_LOG("> REL(0x%x)\n", ev_num);
 		ret = sdei_interrupt_release(ev_num);
-		SDEI_LOG("< REL:%lld\n", ret);
+		SDEI_LOG("< REL:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_SHARED_RESET:
 		SDEI_LOG("> S_RESET():%lx\n", read_mpidr_el1());
 		ret = sdei_shared_reset();
-		SDEI_LOG("< S_RESET:%lld\n", ret);
+		SDEI_LOG("< S_RESET:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_PRIVATE_RESET:
 		SDEI_LOG("> P_RESET():%lx\n", read_mpidr_el1());
 		ret = sdei_private_reset();
-		SDEI_LOG("< P_RESET:%lld\n", ret);
+		SDEI_LOG("< P_RESET:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_ROUTING_SET:
-		SDEI_LOG("> ROUTE_SET(n:%d f:%llx aff:%llx)\n", ev_num, x2, x3);
+		SDEI_LOG("> ROUTE_SET(n:%d f:%" PRIx64 " aff:%" PRIx64 ")\n", ev_num, x2, x3);
 		ret = sdei_event_routing_set(ev_num, x2, x3);
-		SDEI_LOG("< ROUTE_SET:%lld\n", ret);
+		SDEI_LOG("< ROUTE_SET:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_FEATURES:
-		SDEI_LOG("> FTRS(f:%llx)\n", x1);
+		SDEI_LOG("> FTRS(f:%" PRIx64 ")\n", x1);
 		ret = (int64_t) sdei_features((unsigned int) x1);
-		SDEI_LOG("< FTRS:%llx\n", ret);
+		SDEI_LOG("< FTRS:%" PRIx64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	case SDEI_EVENT_SIGNAL:
-		SDEI_LOG("> SIGNAL(e:%d t:%llx)\n", ev_num, x2);
+		SDEI_LOG("> SIGNAL(e:%d t:%" PRIx64 ")\n", ev_num, x2);
 		ret = sdei_signal(ev_num, x2);
-		SDEI_LOG("< SIGNAL:%lld\n", ret);
+		SDEI_LOG("< SIGNAL:%" PRId64 "\n", ret);
 		SMC_RET1(ctx, ret);
 
 	default:
diff --git a/services/std_svc/spm_mm/spm_mm.mk b/services/std_svc/spm_mm/spm_mm.mk
index 656488b..a87bdd8 100644
--- a/services/std_svc/spm_mm/spm_mm.mk
+++ b/services/std_svc/spm_mm/spm_mm.mk
@@ -10,6 +10,12 @@
 ifneq (${ARCH},aarch64)
         $(error "Error: SPM_MM is only supported on aarch64.")
 endif
+ifeq (${ENABLE_SVE_FOR_NS},1)
+        $(error "Error: SPM_MM is not compatible with ENABLE_SVE_FOR_NS")
+endif
+ifeq (${ENABLE_SME_FOR_NS},1)
+        $(error "Error: SPM_MM is not compatible with ENABLE_SME_FOR_NS")
+endif
 
 SPM_SOURCES	:=	$(addprefix services/std_svc/spm_mm/,	\
 			${ARCH}/spm_mm_helpers.S			\
diff --git a/services/std_svc/spm_mm/spm_mm_setup.c b/services/std_svc/spm_mm/spm_mm_setup.c
index 468e5b3..9d681c2 100644
--- a/services/std_svc/spm_mm/spm_mm_setup.c
+++ b/services/std_svc/spm_mm/spm_mm_setup.c
@@ -1,5 +1,6 @@
 /*
- * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2021, NVIDIA Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -26,6 +27,10 @@
 {
 	cpu_context_t *ctx = &(sp_ctx->cpu_ctx);
 
+	/* Pointer to the MP information from the platform port. */
+	const spm_mm_boot_info_t *sp_boot_info =
+			plat_get_secure_partition_boot_info(NULL);
+
 	/*
 	 * Initialize CPU context
 	 * ----------------------
@@ -36,7 +41,7 @@
 	SET_PARAM_HEAD(&ep_info, PARAM_EP, VERSION_1, SECURE | EP_ST_ENABLE);
 
 	/* Setup entrypoint and SPSR */
-	ep_info.pc = BL32_BASE;
+	ep_info.pc = sp_boot_info->sp_image_base;
 	ep_info.spsr = SPSR_64(MODE_EL0, MODE_SP_EL0, DISABLE_ALL_EXCEPTIONS);
 
 	/*
@@ -53,8 +58,8 @@
 	 *
 	 * X4 to X7 = 0
 	 */
-	ep_info.args.arg0 = PLAT_SPM_BUF_BASE;
-	ep_info.args.arg1 = PLAT_SPM_BUF_SIZE;
+	ep_info.args.arg0 = sp_boot_info->sp_shared_buf_base;
+	ep_info.args.arg1 = sp_boot_info->sp_shared_buf_size;
 	ep_info.args.arg2 = PLAT_SPM_COOKIE_0;
 	ep_info.args.arg3 = PLAT_SPM_COOKIE_1;
 
@@ -66,7 +71,7 @@
 	 * implementation defined means. The value will be 0 otherwise.
 	 */
 	write_ctx_reg(get_gpregs_ctx(ctx), CTX_GPREG_SP_EL0,
-			PLAT_SP_IMAGE_STACK_BASE + PLAT_SP_IMAGE_STACK_PCPU_SIZE);
+			sp_boot_info->sp_stack_base + sp_boot_info->sp_pcpu_stack_size);
 
 	/*
 	 * Setup translation tables
@@ -84,10 +89,10 @@
 	unsigned int max_granule_mask = max_granule - 1U;
 
 	/* Base must be aligned to the max granularity */
-	assert((PLAT_SP_IMAGE_NS_BUF_BASE & max_granule_mask) == 0);
+	assert((sp_boot_info->sp_ns_comm_buf_base & max_granule_mask) == 0);
 
 	/* Size must be a multiple of the max granularity */
-	assert((PLAT_SP_IMAGE_NS_BUF_SIZE & max_granule_mask) == 0);
+	assert((sp_boot_info->sp_ns_comm_buf_size & max_granule_mask) == 0);
 
 #endif /* ENABLE_ASSERTIONS */
 
@@ -142,6 +147,8 @@
 		SCTLR_DZE_BIT							|
 		/* Enable SP Alignment check for EL0 */
 		SCTLR_SA0_BIT							|
+		/* Don't change PSTATE.PAN on taking an exception to EL1 */
+		SCTLR_SPAN_BIT							|
 		/* Allow cacheable data and instr. accesses to normal memory. */
 		SCTLR_C_BIT | SCTLR_I_BIT					|
 		/* Enable MMU. */
@@ -189,16 +196,14 @@
 	 * ----------------------------------------------------------
 	 */
 
-	void *shared_buf_ptr = (void *) PLAT_SPM_BUF_BASE;
+	void *shared_buf_ptr = (void *) sp_boot_info->sp_shared_buf_base;
 
 	/* Copy the boot information into the shared buffer with the SP. */
 	assert((uintptr_t)shared_buf_ptr + sizeof(spm_mm_boot_info_t)
-	       <= (PLAT_SPM_BUF_BASE + PLAT_SPM_BUF_SIZE));
+	       <= (sp_boot_info->sp_shared_buf_base + sp_boot_info->sp_shared_buf_size));
 
-	assert(PLAT_SPM_BUF_BASE <= (UINTPTR_MAX - PLAT_SPM_BUF_SIZE + 1));
-
-	const spm_mm_boot_info_t *sp_boot_info =
-			plat_get_secure_partition_boot_info(NULL);
+	assert(sp_boot_info->sp_shared_buf_base <=
+				(UINTPTR_MAX - sp_boot_info->sp_shared_buf_size + 1));
 
 	assert(sp_boot_info != NULL);
 
@@ -232,7 +237,7 @@
 	assert(sp_boot_info->num_cpus <= PLATFORM_CORE_COUNT);
 
 	assert((uintptr_t)shared_buf_ptr
-	       <= (PLAT_SPM_BUF_BASE + PLAT_SPM_BUF_SIZE -
+	       <= (sp_boot_info->sp_shared_buf_base + sp_boot_info->sp_shared_buf_size -
 		       (sp_boot_info->num_cpus * sizeof(*sp_mp_info))));
 
 	memcpy(shared_buf_ptr, (const void *) sp_mp_info,
diff --git a/services/std_svc/spmd/spmd.mk b/services/std_svc/spmd/spmd.mk
index 73f7c85..8efbdc8 100644
--- a/services/std_svc/spmd/spmd.mk
+++ b/services/std_svc/spmd/spmd.mk
@@ -1,11 +1,15 @@
 #
-# Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
 
 ifneq (${ARCH},aarch64)
-        $(error "Error: SPMD is only supported on aarch64.")
+	$(error "Error: SPMD is only supported on aarch64.")
+endif
+
+ifeq (${ENABLE_SME_FOR_NS},1)
+	$(error "Error: SPMD is not compatible with ENABLE_SME_FOR_NS")
 endif
 
 SPMD_SOURCES	+=	$(addprefix services/std_svc/spmd/,	\
diff --git a/services/std_svc/spmd/spmd_main.c b/services/std_svc/spmd/spmd_main.c
index 6aab558..f5de549 100644
--- a/services/std_svc/spmd/spmd_main.c
+++ b/services/std_svc/spmd/spmd_main.c
@@ -1,16 +1,19 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
 #include <string.h>
 
 #include <arch_helpers.h>
 #include <arch/aarch64/arch_features.h>
 #include <bl31/bl31.h>
+#include <bl31/interrupt_mgmt.h>
 #include <common/debug.h>
 #include <common/runtime_svc.h>
 #include <lib/el3_runtime/context_mgmt.h>
@@ -49,7 +52,7 @@
 	int core_idx = plat_core_pos_by_mpidr(mpidr);
 
 	if (core_idx < 0) {
-		ERROR("Invalid mpidr: %llx, returned ID: %d\n", mpidr, core_idx);
+		ERROR("Invalid mpidr: %" PRIx64 ", returned ID: %d\n", mpidr, core_idx);
 		panic();
 	}
 
@@ -65,14 +68,6 @@
 }
 
 /*******************************************************************************
- * SPM Core entry point information get helper.
- ******************************************************************************/
-entry_point_info_t *spmd_spmc_ep_info_get(void)
-{
-	return spmc_ep_info;
-}
-
-/*******************************************************************************
  * SPM Core ID getter.
  ******************************************************************************/
 uint16_t spmd_spmc_id_get(void)
@@ -108,9 +103,10 @@
 	cm_set_context(&(spmc_ctx->cpu_ctx), SECURE);
 
 	/* Restore the context assigned above */
-	cm_el1_sysregs_context_restore(SECURE);
 #if SPMD_SPM_AT_SEL2
 	cm_el2_sysregs_context_restore(SECURE);
+#else
+	cm_el1_sysregs_context_restore(SECURE);
 #endif
 	cm_set_next_eret_context(SECURE);
 
@@ -118,9 +114,10 @@
 	rc = spmd_spm_core_enter(&spmc_ctx->c_rt_ctx);
 
 	/* Save secure state */
-	cm_el1_sysregs_context_save(SECURE);
 #if SPMD_SPM_AT_SEL2
 	cm_el2_sysregs_context_save(SECURE);
+#else
+	cm_el1_sysregs_context_save(SECURE);
 #endif
 
 	return rc;
@@ -154,23 +151,15 @@
 {
 	spmd_spm_core_context_t *ctx = spmd_get_context();
 	uint64_t rc;
-	unsigned int linear_id = plat_my_core_pos();
-	unsigned int core_id;
 
 	VERBOSE("SPM Core init start.\n");
-	ctx->state = SPMC_STATE_ON_PENDING;
 
-	/* Set the SPMC context state on other CPUs to OFF */
-	for (core_id = 0U; core_id < PLATFORM_CORE_COUNT; core_id++) {
-		if (core_id != linear_id) {
-			spm_core_context[core_id].state = SPMC_STATE_OFF;
-			spm_core_context[core_id].secondary_ep.entry_point = 0UL;
-		}
-	}
+	/* Primary boot core enters the SPMC for initialization. */
+	ctx->state = SPMC_STATE_ON_PENDING;
 
 	rc = spmd_spm_core_sync_entry(ctx);
 	if (rc != 0ULL) {
-		ERROR("SPMC initialisation failed 0x%llx\n", rc);
+		ERROR("SPMC initialisation failed 0x%" PRIx64 "\n", rc);
 		return 0;
 	}
 
@@ -182,12 +171,69 @@
 }
 
 /*******************************************************************************
+ * spmd_secure_interrupt_handler
+ * Enter the SPMC for further handling of the secure interrupt by the SPMC
+ * itself or a Secure Partition.
+ ******************************************************************************/
+static uint64_t spmd_secure_interrupt_handler(uint32_t id,
+					      uint32_t flags,
+					      void *handle,
+					      void *cookie)
+{
+	spmd_spm_core_context_t *ctx = spmd_get_context();
+	gp_regs_t *gpregs = get_gpregs_ctx(&ctx->cpu_ctx);
+	unsigned int linear_id = plat_my_core_pos();
+	int64_t rc;
+
+	/* Sanity check the security state when the exception was generated */
+	assert(get_interrupt_src_ss(flags) == NON_SECURE);
+
+	/* Sanity check the pointer to this cpu's context */
+	assert(handle == cm_get_context(NON_SECURE));
+
+	/* Save the non-secure context before entering SPMC */
+	cm_el1_sysregs_context_save(NON_SECURE);
+#if SPMD_SPM_AT_SEL2
+	cm_el2_sysregs_context_save(NON_SECURE);
+#endif
+
+	/* Convey the event to the SPMC through the FFA_INTERRUPT interface. */
+	write_ctx_reg(gpregs, CTX_GPREG_X0, FFA_INTERRUPT);
+	write_ctx_reg(gpregs, CTX_GPREG_X1, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X2, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X3, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X4, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X5, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X6, 0);
+	write_ctx_reg(gpregs, CTX_GPREG_X7, 0);
+
+	/* Mark current core as handling a secure interrupt. */
+	ctx->secure_interrupt_ongoing = true;
+
+	rc = spmd_spm_core_sync_entry(ctx);
+	if (rc != 0ULL) {
+		ERROR("%s failed (%" PRId64 ") on CPU%u\n", __func__, rc, linear_id);
+	}
+
+	ctx->secure_interrupt_ongoing = false;
+
+	cm_el1_sysregs_context_restore(NON_SECURE);
+#if SPMD_SPM_AT_SEL2
+	cm_el2_sysregs_context_restore(NON_SECURE);
+#endif
+	cm_set_next_eret_context(NON_SECURE);
+
+	SMC_RET0(&ctx->cpu_ctx);
+}
+
+/*******************************************************************************
  * Loads SPMC manifest and inits SPMC.
  ******************************************************************************/
 static int spmd_spmc_init(void *pm_addr)
 {
-	spmd_spm_core_context_t *spm_ctx = spmd_get_context();
-	uint32_t ep_attr;
+	cpu_context_t *cpu_ctx;
+	unsigned int core_id;
+	uint32_t ep_attr, flags;
 	int rc;
 
 	/* Load the SPM Core manifest */
@@ -279,13 +325,21 @@
 					     DISABLE_ALL_EXCEPTIONS);
 	}
 
-	/* Initialise SPM Core context with this entry point information */
-	cm_setup_context(&spm_ctx->cpu_ctx, spmc_ep_info);
+	/* Set an initial SPMC context state for all cores. */
+	for (core_id = 0U; core_id < PLATFORM_CORE_COUNT; core_id++) {
+		spm_core_context[core_id].state = SPMC_STATE_OFF;
 
-	/* Reuse PSCI affinity states to mark this SPMC context as off */
-	spm_ctx->state = AFF_STATE_OFF;
+		/* Setup an initial cpu context for the SPMC. */
+		cpu_ctx = &spm_core_context[core_id].cpu_ctx;
+		cm_setup_context(cpu_ctx, spmc_ep_info);
 
-	INFO("SPM Core setup done.\n");
+		/*
+		 * Pass the core linear ID to the SPMC through x4.
+		 * (TF-A implementation defined behavior helping
+		 * a legacy TOS migration to adopt FF-A).
+		 */
+		write_ctx_reg(get_gpregs_ctx(cpu_ctx), CTX_GPREG_X4, core_id);
+	}
 
 	/* Register power management hooks with PSCI */
 	psci_register_spd_pm_hook(&spmd_pm);
@@ -293,6 +347,21 @@
 	/* Register init function for deferred init. */
 	bl31_register_bl32_init(&spmd_init);
 
+	INFO("SPM Core setup done.\n");
+
+	/*
+	 * Register an interrupt handler routing secure interrupts to SPMD
+	 * while the NWd is running.
+	 */
+	flags = 0;
+	set_interrupt_rm_flag(flags, NON_SECURE);
+	rc = register_interrupt_type_handler(INTR_TYPE_S_EL1,
+					     spmd_secure_interrupt_handler,
+					     flags);
+	if (rc != 0) {
+		panic();
+	}
+
 	return 0;
 }
 
@@ -347,15 +416,23 @@
 	unsigned int secure_state_out = (!secure_origin) ? SECURE : NON_SECURE;
 
 	/* Save incoming security state */
-	cm_el1_sysregs_context_save(secure_state_in);
 #if SPMD_SPM_AT_SEL2
+	if (secure_state_in == NON_SECURE) {
+		cm_el1_sysregs_context_save(secure_state_in);
+	}
 	cm_el2_sysregs_context_save(secure_state_in);
+#else
+	cm_el1_sysregs_context_save(secure_state_in);
 #endif
 
 	/* Restore outgoing security state */
-	cm_el1_sysregs_context_restore(secure_state_out);
 #if SPMD_SPM_AT_SEL2
+	if (secure_state_out == NON_SECURE) {
+		cm_el1_sysregs_context_restore(secure_state_out);
+	}
 	cm_el2_sysregs_context_restore(secure_state_out);
+#else
+	cm_el1_sysregs_context_restore(secure_state_out);
 #endif
 	cm_set_next_eret_context(secure_state_out);
 
@@ -370,8 +447,8 @@
  ******************************************************************************/
 static uint64_t spmd_ffa_error_return(void *handle, int error_code)
 {
-	SMC_RET8(handle, FFA_ERROR,
-		 FFA_TARGET_INFO_MBZ, error_code,
+	SMC_RET8(handle, (uint32_t) FFA_ERROR,
+		 FFA_TARGET_INFO_MBZ, (uint32_t)error_code,
 		 FFA_PARAM_MBZ, FFA_PARAM_MBZ, FFA_PARAM_MBZ,
 		 FFA_PARAM_MBZ, FFA_PARAM_MBZ);
 }
@@ -406,13 +483,6 @@
 	VERBOSE("%s %llx %llx %llx %llx %llx\n", __func__,
 		msg, parm1, parm2, parm3, parm4);
 
-	switch (msg) {
-	case SPMD_DIRECT_MSG_SET_ENTRY_POINT:
-		return spmd_pm_secondary_core_set_ep(parm1, parm2, parm3);
-	default:
-		break;
-	}
-
 	return -EINVAL;
 }
 
@@ -429,6 +499,7 @@
 			  void *handle,
 			  uint64_t flags)
 {
+	unsigned int linear_id = plat_my_core_pos();
 	spmd_spm_core_context_t *ctx = spmd_get_context();
 	bool secure_origin;
 	int32_t ret;
@@ -437,10 +508,12 @@
 	/* Determine which security state this SMC originated from */
 	secure_origin = is_caller_secure(flags);
 
-	INFO("SPM: 0x%x 0x%llx 0x%llx 0x%llx 0x%llx 0x%llx 0x%llx 0x%llx\n",
-	     smc_fid, x1, x2, x3, x4, SMC_GET_GP(handle, CTX_GPREG_X5),
-	     SMC_GET_GP(handle, CTX_GPREG_X6),
-	     SMC_GET_GP(handle, CTX_GPREG_X7));
+	VERBOSE("SPM(%u): 0x%x 0x%" PRIx64 " 0x%" PRIx64 " 0x%" PRIx64 " 0x%" PRIx64
+		" 0x%" PRIx64 " 0x%" PRIx64 " 0x%" PRIx64 "\n",
+		    linear_id, smc_fid, x1, x2, x3, x4,
+		    SMC_GET_GP(handle, CTX_GPREG_X5),
+		    SMC_GET_GP(handle, CTX_GPREG_X6),
+		    SMC_GET_GP(handle, CTX_GPREG_X7));
 
 	switch (smc_fid) {
 	case FFA_ERROR:
@@ -470,14 +543,16 @@
 			(ctx->state == SPMC_STATE_RESET)) {
 			ret = FFA_ERROR_NOT_SUPPORTED;
 		} else if (!secure_origin) {
-			ret = MAKE_FFA_VERSION(spmc_attrs.major_version, spmc_attrs.minor_version);
+			ret = MAKE_FFA_VERSION(spmc_attrs.major_version,
+					       spmc_attrs.minor_version);
 		} else {
-			ret = MAKE_FFA_VERSION(FFA_VERSION_MAJOR, FFA_VERSION_MINOR);
+			ret = MAKE_FFA_VERSION(FFA_VERSION_MAJOR,
+					       FFA_VERSION_MINOR);
 		}
 
-		SMC_RET8(handle, ret, FFA_TARGET_INFO_MBZ, FFA_TARGET_INFO_MBZ,
-			 FFA_PARAM_MBZ, FFA_PARAM_MBZ, FFA_PARAM_MBZ,
-			 FFA_PARAM_MBZ, FFA_PARAM_MBZ);
+		SMC_RET8(handle, (uint32_t)ret, FFA_TARGET_INFO_MBZ,
+			 FFA_TARGET_INFO_MBZ, FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+			 FFA_PARAM_MBZ, FFA_PARAM_MBZ, FFA_PARAM_MBZ);
 		break; /* not reached */
 
 	case FFA_FEATURES:
@@ -486,15 +561,6 @@
 		 * forward to SPM Core which will handle it if implemented.
 		 */
 
-		/*
-		 * Check if x1 holds a valid FFA fid. This is an
-		 * optimization.
-		 */
-		if (!is_ffa_fid(x1)) {
-			return spmd_ffa_error_return(handle,
-						      FFA_ERROR_NOT_SUPPORTED);
-		}
-
 		/* Forward SMC from Normal world to the SPM Core */
 		if (!secure_origin) {
 			return spmd_smc_forward(smc_fid, secure_origin,
@@ -533,6 +599,52 @@
 
 		break; /* not reached */
 
+	case FFA_SECONDARY_EP_REGISTER_SMC64:
+		if (secure_origin) {
+			ret = spmd_pm_secondary_ep_register(x1);
+
+			if (ret < 0) {
+				SMC_RET8(handle, FFA_ERROR_SMC64,
+					FFA_TARGET_INFO_MBZ, ret,
+					FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+					FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+					FFA_PARAM_MBZ);
+			} else {
+				SMC_RET8(handle, FFA_SUCCESS_SMC64,
+					FFA_TARGET_INFO_MBZ, FFA_PARAM_MBZ,
+					FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+					FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+					FFA_PARAM_MBZ);
+			}
+		}
+
+		return spmd_ffa_error_return(handle, FFA_ERROR_NOT_SUPPORTED);
+		break; /* Not reached */
+
+	case FFA_SPM_ID_GET:
+		if (MAKE_FFA_VERSION(1, 1) > FFA_VERSION_COMPILED) {
+			return spmd_ffa_error_return(handle,
+						     FFA_ERROR_NOT_SUPPORTED);
+		}
+		/*
+		 * Returns the ID of the SPMC or SPMD depending on the FF-A
+		 * instance where this function is invoked
+		 */
+		if (!secure_origin) {
+			SMC_RET8(handle, FFA_SUCCESS_SMC32,
+				 FFA_TARGET_INFO_MBZ, spmc_attrs.spmc_id,
+				 FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+				 FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+				 FFA_PARAM_MBZ);
+		}
+		SMC_RET8(handle, FFA_SUCCESS_SMC32,
+			 FFA_TARGET_INFO_MBZ, SPMD_DIRECT_MSG_ENDPOINT_ID,
+			 FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+			 FFA_PARAM_MBZ, FFA_PARAM_MBZ,
+			 FFA_PARAM_MBZ);
+
+		break; /* not reached */
+
 	case FFA_MSG_SEND_DIRECT_REQ_SMC32:
 		if (secure_origin && spmd_is_spmc_message(x1)) {
 			ret = spmd_handle_spmc_message(x3, x4,
@@ -554,7 +666,7 @@
 
 	case FFA_MSG_SEND_DIRECT_RESP_SMC32:
 		if (secure_origin && spmd_is_spmc_message(x1)) {
-			spmd_spm_core_sync_exit(0);
+			spmd_spm_core_sync_exit(0ULL);
 		} else {
 			/* Forward direct message to the other world */
 			return spmd_smc_forward(smc_fid, secure_origin,
@@ -567,9 +679,19 @@
 	case FFA_RXTX_MAP_SMC64:
 	case FFA_RXTX_UNMAP:
 	case FFA_PARTITION_INFO_GET:
+#if MAKE_FFA_VERSION(1, 1) <= FFA_VERSION_COMPILED
+	case FFA_NOTIFICATION_BITMAP_CREATE:
+	case FFA_NOTIFICATION_BITMAP_DESTROY:
+	case FFA_NOTIFICATION_BIND:
+	case FFA_NOTIFICATION_UNBIND:
+	case FFA_NOTIFICATION_SET:
+	case FFA_NOTIFICATION_GET:
+	case FFA_NOTIFICATION_INFO_GET:
+	case FFA_NOTIFICATION_INFO_GET_SMC64:
+#endif
 		/*
-		 * Should not be allowed to forward FFA_PARTITION_INFO_GET
-		 * from Secure world to Normal world
+		 * Above calls should not be forwarded from Secure world to
+		 * Normal world.
 		 *
 		 * Fall through to forward the call to the other world
 		 */
@@ -616,11 +738,11 @@
 		 * SPM Core initialised successfully.
 		 */
 		if (secure_origin && (ctx->state == SPMC_STATE_ON_PENDING)) {
-			spmd_spm_core_sync_exit(0);
+			spmd_spm_core_sync_exit(0ULL);
 		}
 
 		/* Fall through to forward the call to the other world */
-
+	case FFA_INTERRUPT:
 	case FFA_MSG_YIELD:
 		/* This interface must be invoked only by the Secure world */
 		if (!secure_origin) {
@@ -632,6 +754,14 @@
 					x1, x2, x3, x4, handle);
 		break; /* not reached */
 
+	case FFA_NORMAL_WORLD_RESUME:
+		if (secure_origin && ctx->secure_interrupt_ongoing) {
+			spmd_spm_core_sync_exit(0ULL);
+		} else {
+			return spmd_ffa_error_return(handle, FFA_ERROR_DENIED);
+		}
+		break; /* Not reached */
+
 	default:
 		WARN("SPM: Unsupported call 0x%08x\n", smc_fid);
 		return spmd_ffa_error_return(handle, FFA_ERROR_NOT_SUPPORTED);
diff --git a/services/std_svc/spmd/spmd_pm.c b/services/std_svc/spmd/spmd_pm.c
index 5433e5d..6ebafca 100644
--- a/services/std_svc/spmd/spmd_pm.c
+++ b/services/std_svc/spmd/spmd_pm.c
@@ -1,14 +1,24 @@
 /*
- * Copyright (c) 2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2020-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
 
 #include <assert.h>
 #include <errno.h>
+#include <inttypes.h>
+#include <stdint.h>
+
 #include <lib/el3_runtime/context_mgmt.h>
+#include <lib/spinlock.h>
 #include "spmd_private.h"
 
+static struct {
+	bool secondary_ep_locked;
+	uintptr_t secondary_ep;
+	spinlock_t lock;
+} g_spmd_pm;
+
 /*******************************************************************************
  * spmd_build_spmc_message
  *
@@ -25,16 +35,16 @@
 }
 
 /*******************************************************************************
- * spmd_pm_secondary_core_set_ep
+ * spmd_pm_secondary_ep_register
  ******************************************************************************/
-int spmd_pm_secondary_core_set_ep(unsigned long long mpidr,
-		uintptr_t entry_point, unsigned long long context)
+int spmd_pm_secondary_ep_register(uintptr_t entry_point)
 {
-	int id = plat_core_pos_by_mpidr(mpidr);
+	int ret = FFA_ERROR_INVALID_PARAMETER;
 
-	if ((id < 0) || ((unsigned int)id >= PLATFORM_CORE_COUNT)) {
-		ERROR("%s inconsistent MPIDR (%llx)\n", __func__, mpidr);
-		return -EINVAL;
+	spin_lock(&g_spmd_pm.lock);
+
+	if (g_spmd_pm.secondary_ep_locked == true) {
+		goto out;
 	}
 
 	/*
@@ -42,27 +52,22 @@
 	 * load_address <= entry_point < load_address + binary_size
 	 */
 	if (!spmd_check_address_in_binary_image(entry_point)) {
-		ERROR("%s entry point is not within image boundaries (%llx)\n",
-		      __func__, mpidr);
-		return -EINVAL;
+		ERROR("%s entry point is not within image boundaries\n",
+			__func__);
+		goto out;
 	}
 
-	spmd_spm_core_context_t *ctx = spmd_get_context_by_mpidr(mpidr);
-	spmd_pm_secondary_ep_t *secondary_ep = &ctx->secondary_ep;
-	if (secondary_ep->locked) {
-		ERROR("%s entry locked (%llx)\n", __func__, mpidr);
-		return -EINVAL;
-	}
+	g_spmd_pm.secondary_ep = entry_point;
+	g_spmd_pm.secondary_ep_locked = true;
 
-	/* Fill new entry to corresponding secondary core id and lock it */
-	secondary_ep->entry_point = entry_point;
-	secondary_ep->context = context;
-	secondary_ep->locked = true;
+	VERBOSE("%s %lx\n", __func__, entry_point);
 
-	VERBOSE("%s %d %llx %lx %llx\n",
-		__func__, id, mpidr, entry_point, context);
+	ret = 0;
 
-	return 0;
+out:
+	spin_unlock(&g_spmd_pm.lock);
+
+	return ret;
 }
 
 /*******************************************************************************
@@ -73,40 +78,47 @@
  ******************************************************************************/
 static void spmd_cpu_on_finish_handler(u_register_t unused)
 {
-	entry_point_info_t *spmc_ep_info = spmd_spmc_ep_info_get();
 	spmd_spm_core_context_t *ctx = spmd_get_context();
 	unsigned int linear_id = plat_my_core_pos();
+	el3_state_t *el3_state;
+	uintptr_t entry_point;
 	uint64_t rc;
 
 	assert(ctx != NULL);
 	assert(ctx->state != SPMC_STATE_ON);
-	assert(spmc_ep_info != NULL);
+
+	spin_lock(&g_spmd_pm.lock);
 
 	/*
-	 * TODO: this might require locking the spmc_ep_info structure,
-	 * or provisioning one structure per cpu
+	 * Leave the possibility that the SPMC does not call
+	 * FFA_SECONDARY_EP_REGISTER in which case re-use the
+	 * primary core address for booting secondary cores.
 	 */
-	if (ctx->secondary_ep.entry_point == 0UL) {
-		goto exit;
+	if (g_spmd_pm.secondary_ep_locked == true) {
+		/*
+		 * The CPU context has already been initialized at boot time
+		 * (in spmd_spmc_init by a call to cm_setup_context). Adjust
+		 * below the target core entry point based on the address
+		 * passed to by FFA_SECONDARY_EP_REGISTER.
+		 */
+		entry_point = g_spmd_pm.secondary_ep;
+		el3_state = get_el3state_ctx(&ctx->cpu_ctx);
+		write_ctx_reg(el3_state, CTX_ELR_EL3, entry_point);
 	}
 
-	spmc_ep_info->pc = ctx->secondary_ep.entry_point;
-	cm_setup_context(&ctx->cpu_ctx, spmc_ep_info);
-	write_ctx_reg(get_gpregs_ctx(&ctx->cpu_ctx), CTX_GPREG_X0,
-		      ctx->secondary_ep.context);
+	spin_unlock(&g_spmd_pm.lock);
 
-	/* Mark CPU as initiating ON operation */
+	/* Mark CPU as initiating ON operation. */
 	ctx->state = SPMC_STATE_ON_PENDING;
 
 	rc = spmd_spm_core_sync_entry(ctx);
 	if (rc != 0ULL) {
-		ERROR("%s failed (%llu) on CPU%u\n", __func__, rc,
+		ERROR("%s failed (%" PRIu64 ") on CPU%u\n", __func__, rc,
 			linear_id);
 		ctx->state = SPMC_STATE_OFF;
 		return;
 	}
 
-exit:
 	ctx->state = SPMC_STATE_ON;
 
 	VERBOSE("CPU %u on!\n", linear_id);
@@ -124,21 +136,23 @@
 	assert(ctx != NULL);
 	assert(ctx->state != SPMC_STATE_OFF);
 
-	if (ctx->secondary_ep.entry_point == 0UL) {
-		goto exit;
-	}
-
 	/* Build an SPMD to SPMC direct message request. */
 	spmd_build_spmc_message(get_gpregs_ctx(&ctx->cpu_ctx), PSCI_CPU_OFF);
 
 	rc = spmd_spm_core_sync_entry(ctx);
 	if (rc != 0ULL) {
-		ERROR("%s failed (%llu) on CPU%u\n", __func__, rc, linear_id);
+		ERROR("%s failed (%" PRIu64 ") on CPU%u\n", __func__, rc, linear_id);
 	}
 
-	/* TODO expect FFA_DIRECT_MSG_RESP returned from SPMC */
+	/* Expect a direct message response from the SPMC. */
+	u_register_t ffa_resp_func = read_ctx_reg(get_gpregs_ctx(&ctx->cpu_ctx),
+						  CTX_GPREG_X0);
+	if (ffa_resp_func != FFA_MSG_SEND_DIRECT_RESP_SMC32) {
+		ERROR("%s invalid SPMC response (%lx).\n",
+			__func__, ffa_resp_func);
+		return -EINVAL;
+	}
 
-exit:
 	ctx->state = SPMC_STATE_OFF;
 
 	VERBOSE("CPU %u off!\n", linear_id);
diff --git a/services/std_svc/spmd/spmd_private.h b/services/std_svc/spmd/spmd_private.h
index eff0dd9..1fe5065 100644
--- a/services/std_svc/spmd/spmd_private.h
+++ b/services/std_svc/spmd/spmd_private.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2019-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -42,12 +42,6 @@
 	SPMC_STATE_ON
 } spmc_state_t;
 
-typedef struct spmd_pm_secondary_ep {
-	uintptr_t entry_point;
-	uintptr_t context;
-	bool locked;
-} spmd_pm_secondary_ep_t;
-
 /*
  * Data structure used by the SPM dispatcher (SPMD) in EL3 to track context of
  * the SPM core (SPMC) at the next lower EL.
@@ -56,7 +50,7 @@
 	uint64_t c_rt_ctx;
 	cpu_context_t cpu_ctx;
 	spmc_state_t state;
-	spmd_pm_secondary_ep_t secondary_ep;
+	bool secure_interrupt_ongoing;
 } spmd_spm_core_context_t;
 
 /*
@@ -69,7 +63,6 @@
 #define SPMC_SECURE_ID_SHIFT			U(15)
 
 #define SPMD_DIRECT_MSG_ENDPOINT_ID		U(FFA_ENDPOINT_ID_MAX - 1)
-#define SPMD_DIRECT_MSG_SET_ENTRY_POINT		U(1)
 
 /* Functions used to enter/exit SPMC synchronously */
 uint64_t spmd_spm_core_sync_entry(spmd_spm_core_context_t *ctx);
@@ -94,8 +87,7 @@
 /* SPMC context on current CPU get helper */
 spmd_spm_core_context_t *spmd_get_context(void);
 
-int spmd_pm_secondary_core_set_ep(unsigned long long mpidr,
-		uintptr_t entry_point, unsigned long long context);
+int spmd_pm_secondary_ep_register(uintptr_t entry_point);
 bool spmd_check_address_in_binary_image(uint64_t address);
 
 #endif /* __ASSEMBLER__ */
diff --git a/services/std_svc/std_svc_setup.c b/services/std_svc/std_svc_setup.c
index ddc7ad3..e6baafd 100644
--- a/services/std_svc/std_svc_setup.c
+++ b/services/std_svc/std_svc_setup.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,10 +13,14 @@
 #include <lib/pmf/pmf.h>
 #include <lib/psci/psci.h>
 #include <lib/runtime_instr.h>
+#include <services/gtsi_svc.h>
+#include <services/pci_svc.h>
+#include <services/rmmd_svc.h>
 #include <services/sdei.h>
 #include <services/spm_mm_svc.h>
 #include <services/spmd_svc.h>
 #include <services/std_svc.h>
+#include <services/trng_svc.h>
 #include <smccc_helpers.h>
 #include <tools_share/uuid.h>
 
@@ -63,6 +67,8 @@
 	sdei_init();
 #endif
 
+	trng_setup();
+
 	return ret;
 }
 
@@ -79,6 +85,15 @@
 			     void *handle,
 			     u_register_t flags)
 {
+	if (((smc_fid >> FUNCID_CC_SHIFT) & FUNCID_CC_MASK) == SMC_32) {
+		/* 32-bit SMC function, clear top parameter bits */
+
+		x1 &= UINT32_MAX;
+		x2 &= UINT32_MAX;
+		x3 &= UINT32_MAX;
+		x4 &= UINT32_MAX;
+	}
+
 	/*
 	 * Dispatch PSCI calls to PSCI SMC handler and return its return
 	 * value
@@ -139,6 +154,30 @@
 	}
 #endif
 
+#if TRNG_SUPPORT
+	if (is_trng_fid(smc_fid)) {
+		return trng_smc_handler(smc_fid, x1, x2, x3, x4, cookie, handle,
+				flags);
+	}
+#endif
+#if ENABLE_RME
+	/*
+	 * Granule transition service interface functions (GTSI) are allocated
+	 * from the Std service range. Call the RMM dispatcher to handle calls.
+	 */
+	if (is_gtsi_fid(smc_fid)) {
+		return rmmd_gtsi_handler(smc_fid, x1, x2, x3, x4, cookie,
+						handle, flags);
+	}
+#endif
+
+#if SMC_PCI_SUPPORT
+	if (is_pci_fid(smc_fid)) {
+		return pci_smc_handler(smc_fid, x1, x2, x3, x4, cookie, handle,
+				       flags);
+	}
+#endif
+
 	switch (smc_fid) {
 	case ARM_STD_SVC_CALL_COUNT:
 		/*
@@ -156,7 +195,7 @@
 		SMC_RET2(handle, STD_SVC_VERSION_MAJOR, STD_SVC_VERSION_MINOR);
 
 	default:
-		WARN("Unimplemented Standard Service Call: 0x%x \n", smc_fid);
+		VERBOSE("Unimplemented Standard Service Call: 0x%x \n", smc_fid);
 		SMC_RET1(handle, SMC_UNK);
 	}
 }
diff --git a/services/std_svc/trng/trng_entropy_pool.c b/services/std_svc/trng/trng_entropy_pool.c
new file mode 100644
index 0000000..ac13b1d
--- /dev/null
+++ b/services/std_svc/trng/trng_entropy_pool.c
@@ -0,0 +1,151 @@
+/*
+ * Copyright (c) 2021, ARM Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <lib/spinlock.h>
+#include <plat/common/plat_trng.h>
+
+/*
+ * # Entropy pool
+ * Note that the TRNG Firmware interface can request up to 192 bits of entropy
+ * in a single call or three 64bit words per call. We have 4 words in the pool
+ * so that when we have 1-63 bits in the pool, and we have a request for
+ * 192 bits of entropy, we don't have to throw out the leftover 1-63 bits of
+ * entropy.
+ */
+#define WORDS_IN_POOL (4)
+static uint64_t entropy[WORDS_IN_POOL];
+/* index in bits of the first bit of usable entropy */
+static uint32_t entropy_bit_index;
+/* then number of valid bits in the entropy pool */
+static uint32_t entropy_bit_size;
+
+static spinlock_t trng_pool_lock;
+
+#define BITS_PER_WORD (sizeof(entropy[0]) * 8)
+#define BITS_IN_POOL (WORDS_IN_POOL * BITS_PER_WORD)
+#define ENTROPY_MIN_WORD (entropy_bit_index / BITS_PER_WORD)
+#define ENTROPY_FREE_BIT (entropy_bit_size + entropy_bit_index)
+#define _ENTROPY_FREE_WORD (ENTROPY_FREE_BIT / BITS_PER_WORD)
+#define ENTROPY_FREE_INDEX (_ENTROPY_FREE_WORD % WORDS_IN_POOL)
+/* ENTROPY_WORD_INDEX(0) includes leftover bits in the lower bits */
+#define ENTROPY_WORD_INDEX(i) ((ENTROPY_MIN_WORD + i) % WORDS_IN_POOL)
+
+/*
+ * Fill the entropy pool until we have at least as many bits as requested.
+ * Returns true after filling the pool, and false if the entropy source is out
+ * of entropy and the pool could not be filled.
+ * Assumes locks are taken.
+ */
+static bool trng_fill_entropy(uint32_t nbits)
+{
+	while (nbits > entropy_bit_size) {
+		bool valid = plat_get_entropy(&entropy[ENTROPY_FREE_INDEX]);
+
+		if (valid) {
+			entropy_bit_size += BITS_PER_WORD;
+			assert(entropy_bit_size <= BITS_IN_POOL);
+		} else {
+			return false;
+		}
+	}
+	return true;
+}
+
+/*
+ * Pack entropy into the out buffer, filling and taking locks as needed.
+ * Returns true on success, false on failure.
+ *
+ * Note: out must have enough space for nbits of entropy
+ */
+bool trng_pack_entropy(uint32_t nbits, uint64_t *out)
+{
+	bool success = true;
+
+	spin_lock(&trng_pool_lock);
+
+	if (!trng_fill_entropy(nbits)) {
+		success = false;
+		goto out;
+	}
+
+	const unsigned int rshift = entropy_bit_index % BITS_PER_WORD;
+	const unsigned int lshift = BITS_PER_WORD - rshift;
+	const int to_fill = ((nbits + BITS_PER_WORD - 1) / BITS_PER_WORD);
+	int word_i;
+
+	for (word_i = 0; word_i < to_fill; word_i++) {
+		/*
+		 * Repack the entropy from the pool into the passed in out
+		 * buffer. This takes the lower bits from the valid upper bits
+		 * of word_i and the upper bits from the lower bits of
+		 * (word_i + 1).
+		 *
+		 * I found the following diagram useful. note: `e` represents
+		 * valid entropy, ` ` represents invalid bits (not entropy) and
+		 * `x` represents valid entropy that must not end up in the
+		 * packed word.
+		 *
+		 *          |---------entropy pool----------|
+		 * C var    |--(word_i + 1)-|----word_i-----|
+		 * bit idx  |7 6 5 4 3 2 1 0|7 6 5 4 3 2 1 0|
+		 *          [x,x,e,e,e,e,e,e|e,e, , , , , , ]
+		 *          |   [e,e,e,e,e,e,e,e]           |
+		 *          |   |--out[word_i]--|           |
+		 *    lshift|---|               |--rshift---|
+		 *
+		 *          ==== Which is implemented as ====
+		 *
+		 *          |---------entropy pool----------|
+		 * C var    |--(word_i + 1)-|----word_i-----|
+		 * bit idx  |7 6 5 4 3 2 1 0|7 6 5 4 3 2 1 0|
+		 *          [x,x,e,e,e,e,e,e|e,e, , , , , , ]
+		 * C expr       << lshift       >> rshift
+		 * bit idx   5 4 3 2 1 0                 7 6
+		 *          [e,e,e,e,e,e,0,0|0,0,0,0,0,0,e,e]
+		 *                ==== bit-wise or ====
+		 *                   5 4 3 2 1 0 7 6
+		 *                  [e,e,e,e,e,e,e,e]
+		 */
+		out[word_i] = 0;
+		out[word_i] |= entropy[ENTROPY_WORD_INDEX(word_i)] >> rshift;
+
+		/*
+		 * Note that a shift of 64 bits is treated as a shift of 0 bits.
+		 * When the shift amount is the same as the BITS_PER_WORD, we
+		 * don't want to include the next word of entropy, so we skip
+		 * the `|=` operation.
+		 */
+		if (lshift != BITS_PER_WORD) {
+			out[word_i] |= entropy[ENTROPY_WORD_INDEX(word_i + 1)]
+				<< lshift;
+		}
+	}
+	const uint64_t mask = ~0ULL >> (BITS_PER_WORD - (nbits % BITS_PER_WORD));
+
+	out[to_fill - 1] &= mask;
+
+	entropy_bit_index = (entropy_bit_index + nbits) % BITS_IN_POOL;
+	entropy_bit_size -= nbits;
+
+out:
+	spin_unlock(&trng_pool_lock);
+
+	return success;
+}
+
+void trng_entropy_pool_setup(void)
+{
+	int i;
+
+	for (i = 0; i < WORDS_IN_POOL; i++) {
+		entropy[i] = 0;
+	}
+	entropy_bit_index = 0;
+	entropy_bit_size = 0;
+}
diff --git a/services/std_svc/trng/trng_entropy_pool.h b/services/std_svc/trng/trng_entropy_pool.h
new file mode 100644
index 0000000..fab2367
--- /dev/null
+++ b/services/std_svc/trng/trng_entropy_pool.h
@@ -0,0 +1,16 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef TRNG_ENTROPY_POOL_H
+#define TRNG_ENTROPY_POOL_H
+
+#include <stdbool.h>
+#include <stdint.h>
+
+bool trng_pack_entropy(uint32_t nbits, uint64_t *out);
+void trng_entropy_pool_setup(void);
+
+#endif /* TRNG_ENTROPY_POOL_H */
diff --git a/services/std_svc/trng/trng_main.c b/services/std_svc/trng/trng_main.c
new file mode 100644
index 0000000..38aa649
--- /dev/null
+++ b/services/std_svc/trng/trng_main.c
@@ -0,0 +1,143 @@
+/*
+ * Copyright (c) 2021, ARM Limited and Contributors. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <assert.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+#include <arch_features.h>
+#include <lib/smccc.h>
+#include <services/trng_svc.h>
+#include <smccc_helpers.h>
+
+#include <plat/common/plat_trng.h>
+
+#include "trng_entropy_pool.h"
+
+static const uuid_t uuid_null;
+
+/* handle the RND call in SMC 32 bit mode */
+static uintptr_t trng_rnd32(uint32_t nbits, void *handle)
+{
+	uint32_t mask = ~0U;
+	uint64_t ent[2];
+
+	if (nbits == 0U || nbits > 96U) {
+		SMC_RET1(handle, TRNG_E_INVALID_PARAMS);
+	}
+
+	if (!trng_pack_entropy(nbits, &ent[0])) {
+		SMC_RET1(handle, TRNG_E_NO_ENTROPY);
+	}
+
+	if ((nbits % 32U) != 0U) {
+		mask >>= 32U - (nbits % 32U);
+	}
+
+	switch ((nbits - 1U) / 32U) {
+	case 0:
+		SMC_RET4(handle, TRNG_E_SUCCESS, 0, 0, ent[0] & mask);
+		break; /* unreachable */
+	case 1:
+		SMC_RET4(handle, TRNG_E_SUCCESS, 0, (ent[0] >> 32) & mask,
+			 ent[0] & 0xFFFFFFFF);
+		break; /* unreachable */
+	case 2:
+		SMC_RET4(handle, TRNG_E_SUCCESS, ent[1] & mask,
+			 (ent[0] >> 32) & 0xFFFFFFFF, ent[0] & 0xFFFFFFFF);
+		break; /* unreachable */
+	default:
+		SMC_RET1(handle, TRNG_E_INVALID_PARAMS);
+		break; /* unreachable */
+	}
+}
+
+/* handle the RND call in SMC 64 bit mode */
+static uintptr_t trng_rnd64(uint32_t nbits, void *handle)
+{
+	uint64_t mask = ~0ULL;
+	uint64_t ent[3];
+
+	if (nbits == 0U || nbits > 192U) {
+		SMC_RET1(handle, TRNG_E_INVALID_PARAMS);
+	}
+
+	if (!trng_pack_entropy(nbits, &ent[0])) {
+		SMC_RET1(handle, TRNG_E_NO_ENTROPY);
+	}
+
+	/* Mask off higher bits if only part of register requested */
+	if ((nbits % 64U) != 0U) {
+		mask >>= 64U - (nbits % 64U);
+	}
+
+	switch ((nbits - 1U) / 64U) {
+	case 0:
+		SMC_RET4(handle, TRNG_E_SUCCESS, 0, 0, ent[0] & mask);
+		break; /* unreachable */
+	case 1:
+		SMC_RET4(handle, TRNG_E_SUCCESS, 0, ent[1] & mask, ent[0]);
+		break; /* unreachable */
+	case 2:
+		SMC_RET4(handle, TRNG_E_SUCCESS, ent[2] & mask, ent[1], ent[0]);
+		break; /* unreachable */
+	default:
+		SMC_RET1(handle, TRNG_E_INVALID_PARAMS);
+		break; /* unreachable */
+	}
+}
+
+void trng_setup(void)
+{
+	trng_entropy_pool_setup();
+	plat_entropy_setup();
+}
+
+/* Predicate indicating that a function id is part of TRNG */
+bool is_trng_fid(uint32_t smc_fid)
+{
+	return ((smc_fid == ARM_TRNG_VERSION) ||
+		(smc_fid == ARM_TRNG_FEATURES) ||
+		(smc_fid == ARM_TRNG_GET_UUID) ||
+		(smc_fid == ARM_TRNG_RND32) ||
+		(smc_fid == ARM_TRNG_RND64));
+}
+
+uintptr_t trng_smc_handler(uint32_t smc_fid, u_register_t x1, u_register_t x2,
+			   u_register_t x3, u_register_t x4, void *cookie,
+			   void *handle, u_register_t flags)
+{
+	if (!memcmp(&plat_trng_uuid, &uuid_null, sizeof(uuid_t))) {
+		SMC_RET1(handle, TRNG_E_NOT_IMPLEMENTED);
+	}
+
+	switch (smc_fid) {
+	case ARM_TRNG_VERSION:
+		SMC_RET1(handle, MAKE_SMCCC_VERSION(
+			TRNG_VERSION_MAJOR, TRNG_VERSION_MINOR
+		));
+		break; /* unreachable */
+	case ARM_TRNG_FEATURES:
+		if (is_trng_fid((uint32_t)x1)) {
+			SMC_RET1(handle, TRNG_E_SUCCESS);
+		} else {
+			SMC_RET1(handle, TRNG_E_NOT_SUPPORTED);
+		}
+		break; /* unreachable */
+	case ARM_TRNG_GET_UUID:
+		SMC_UUID_RET(handle, plat_trng_uuid);
+		break; /* unreachable */
+	case ARM_TRNG_RND32:
+		return trng_rnd32((uint32_t)x1, handle);
+	case ARM_TRNG_RND64:
+		return trng_rnd64((uint32_t)x1, handle);
+	default:
+		WARN("Unimplemented TRNG Service Call: 0x%x\n",
+			smc_fid);
+		SMC_RET1(handle, TRNG_E_NOT_IMPLEMENTED);
+		break; /* unreachable */
+	}
+}
diff --git a/tools/cert_create/Makefile b/tools/cert_create/Makefile
index 0ec08b0..77d2007 100644
--- a/tools/cert_create/Makefile
+++ b/tools/cert_create/Makefile
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -16,6 +16,12 @@
 include ${MAKE_HELPERS_DIRECTORY}build_macros.mk
 include ${MAKE_HELPERS_DIRECTORY}build_env.mk
 
+ifneq (${PLAT},none)
+TF_PLATFORM_ROOT	:=	../../plat/
+include ${MAKE_HELPERS_DIRECTORY}plat_helpers.mk
+PLAT_CERT_CREATE_HELPER_MK := ${PLAT_DIR}/cert_create_tbbr.mk
+endif
+
 # Common source files.
 OBJECTS := src/cert.o \
            src/cmd_opt.o \
@@ -33,6 +39,10 @@
   $(error Unknown chain of trust ${COT})
 endif
 
+ifneq (,$(wildcard ${PLAT_CERT_CREATE_HELPER_MK}))
+include ${PLAT_CERT_CREATE_HELPER_MK}
+endif
+
 HOSTCCFLAGS := -Wall -std=c99
 
 ifeq (${DEBUG},1)
@@ -51,7 +61,7 @@
 
 # Make soft links and include from local directory otherwise wrong headers
 # could get pulled in from firmware tree.
-INC_DIR := -I ./include -I ${PLAT_INCLUDE} -I ${OPENSSL_DIR}/include
+INC_DIR += -I ./include -I ${PLAT_INCLUDE} -I ${OPENSSL_DIR}/include
 LIB_DIR := -L ${OPENSSL_DIR}/lib
 LIB := -lssl -lcrypto
 
@@ -59,7 +69,7 @@
 
 .PHONY: all clean realclean
 
-all: clean ${BINARY}
+all: ${BINARY}
 
 ${BINARY}: ${OBJECTS} Makefile
 	@echo "  HOSTLD  $@"
diff --git a/tools/cert_create/include/cert.h b/tools/cert_create/include/cert.h
index daf27a7..e63b474 100644
--- a/tools/cert_create/include/cert.h
+++ b/tools/cert_create/include/cert.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -57,11 +57,20 @@
 
 /* Macro to register the certificates used in the CoT */
 #define REGISTER_COT(_certs) \
-	cert_t *certs = &_certs[0]; \
-	const unsigned int num_certs = sizeof(_certs)/sizeof(_certs[0])
+	cert_t *def_certs = &_certs[0]; \
+	const unsigned int num_def_certs = sizeof(_certs)/sizeof(_certs[0])
+
+/* Macro to register the platform defined certificates used in the CoT */
+#define PLAT_REGISTER_COT(_pdef_certs) \
+	cert_t *pdef_certs = &_pdef_certs[0]; \
+	const unsigned int num_pdef_certs = sizeof(_pdef_certs)/sizeof(_pdef_certs[0])
 
 /* Exported variables */
-extern cert_t *certs;
-extern const unsigned int num_certs;
+extern cert_t *def_certs;
+extern const unsigned int num_def_certs;
+extern cert_t *pdef_certs;
+extern const unsigned int num_pdef_certs;
 
+extern cert_t *certs;
+extern unsigned int num_certs;
 #endif /* CERT_H */
diff --git a/tools/cert_create/include/ext.h b/tools/cert_create/include/ext.h
index 9c0b5c3..e900a6d 100644
--- a/tools/cert_create/include/ext.h
+++ b/tools/cert_create/include/ext.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -75,11 +75,20 @@
 
 /* Macro to register the extensions used in the CoT */
 #define REGISTER_EXTENSIONS(_ext) \
-	ext_t *extensions = &_ext[0]; \
-	const unsigned int num_extensions = sizeof(_ext)/sizeof(_ext[0])
+	ext_t *def_extensions = &_ext[0]; \
+	const unsigned int num_def_extensions = sizeof(_ext)/sizeof(_ext[0])
+
+/* Macro to register the platform defined extensions used in the CoT */
+#define PLAT_REGISTER_EXTENSIONS(_pdef_ext) \
+	ext_t *pdef_extensions = &_pdef_ext[0]; \
+	const unsigned int num_pdef_extensions = sizeof(_pdef_ext)/sizeof(_pdef_ext[0])
 
 /* Exported variables */
-extern ext_t *extensions;
-extern const unsigned int num_extensions;
+extern ext_t *def_extensions;
+extern const unsigned int num_def_extensions;
+extern ext_t *pdef_extensions;
+extern const unsigned int num_pdef_extensions;
 
+extern ext_t *extensions;
+extern unsigned int num_extensions;
 #endif /* EXT_H */
diff --git a/tools/cert_create/include/key.h b/tools/cert_create/include/key.h
index d96d983..128e7f7 100644
--- a/tools/cert_create/include/key.h
+++ b/tools/cert_create/include/key.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -73,11 +73,20 @@
 
 /* Macro to register the keys used in the CoT */
 #define REGISTER_KEYS(_keys) \
-	key_t *keys = &_keys[0]; \
-	const unsigned int num_keys = sizeof(_keys)/sizeof(_keys[0])
+	key_t *def_keys = &_keys[0]; \
+	const unsigned int num_def_keys = sizeof(_keys)/sizeof(_keys[0])
+
+/* Macro to register the platform defined keys used in the CoT */
+#define PLAT_REGISTER_KEYS(_pdef_keys) \
+	key_t *pdef_keys = &_pdef_keys[0]; \
+	const unsigned int num_pdef_keys = sizeof(_pdef_keys)/sizeof(_pdef_keys[0])
 
 /* Exported variables */
-extern key_t *keys;
-extern const unsigned int num_keys;
+extern key_t *def_keys;
+extern const unsigned int num_def_keys;
+extern key_t *pdef_keys;
+extern const unsigned int num_pdef_keys;
 
+extern key_t *keys;
+extern unsigned int num_keys;
 #endif /* KEY_H */
diff --git a/tools/cert_create/src/cert.c b/tools/cert_create/src/cert.c
index 153f555..4b35d73 100644
--- a/tools/cert_create/src/cert.c
+++ b/tools/cert_create/src/cert.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -24,6 +24,9 @@
 #define SERIAL_RAND_BITS	64
 #define RSA_SALT_LEN		32
 
+cert_t *certs;
+unsigned int num_certs;
+
 int rand_serial(BIGNUM *b, ASN1_INTEGER *ai)
 {
 	BIGNUM *btmp;
@@ -220,6 +223,28 @@
 	cert_t *cert;
 	unsigned int i;
 
+	certs = malloc((num_def_certs * sizeof(def_certs[0]))
+#ifdef PDEF_CERTS
+		       + (num_pdef_certs * sizeof(pdef_certs[0]))
+#endif
+		       );
+	if (certs == NULL) {
+		ERROR("%s:%d Failed to allocate memory.\n", __func__, __LINE__);
+		return 1;
+	}
+
+	memcpy(&certs[0], &def_certs[0],
+	       (num_def_certs * sizeof(def_certs[0])));
+
+#ifdef PDEF_CERTS
+	memcpy(&certs[num_def_certs], &pdef_certs[0],
+	       (num_pdef_certs * sizeof(pdef_certs[0])));
+
+	num_certs = num_def_certs + num_pdef_certs;
+#else
+	num_certs = num_def_certs;
+#endif
+
 	for (i = 0; i < num_certs; i++) {
 		cert = &certs[i];
 		cmd_opt.long_opt.name = cert->opt;
diff --git a/tools/cert_create/src/ext.c b/tools/cert_create/src/ext.c
index d9a92bb..2882123 100644
--- a/tools/cert_create/src/ext.c
+++ b/tools/cert_create/src/ext.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -13,8 +13,12 @@
 #include <openssl/x509v3.h>
 
 #include "cmd_opt.h"
+#include "debug.h"
 #include "ext.h"
 
+ext_t *extensions;
+unsigned int num_extensions;
+
 DECLARE_ASN1_ITEM(ASN1_INTEGER)
 DECLARE_ASN1_ITEM(X509_ALGOR)
 DECLARE_ASN1_ITEM(ASN1_OCTET_STRING)
@@ -51,6 +55,26 @@
 	int nid, ret;
 	unsigned int i;
 
+	extensions = malloc((num_def_extensions * sizeof(def_extensions[0]))
+#ifdef PDEF_EXTS
+			    + (num_pdef_extensions * sizeof(pdef_extensions[0]))
+#endif
+			    );
+	if (extensions == NULL) {
+		ERROR("%s:%d Failed to allocate memory.\n", __func__, __LINE__);
+		return 1;
+	}
+
+	memcpy(&extensions[0], &def_extensions[0],
+	       (num_def_extensions * sizeof(def_extensions[0])));
+#ifdef PDEF_EXTS
+	memcpy(&extensions[num_def_extensions], &pdef_extensions[0],
+		(num_pdef_extensions * sizeof(pdef_extensions[0])));
+	num_extensions = num_def_extensions + num_pdef_extensions;
+#else
+	num_extensions = num_def_extensions;
+#endif
+
 	for (i = 0; i < num_extensions; i++) {
 		ext = &extensions[i];
 		/* Register command line option */
@@ -158,51 +182,36 @@
 		unsigned char *buf, size_t len)
 {
 	X509_EXTENSION *ex;
-	ASN1_OCTET_STRING *octet;
 	HASH *hash;
 	ASN1_OBJECT *algorithm;
-	X509_ALGOR *x509_algor;
 	unsigned char *p = NULL;
 	int sz;
 
-	/* OBJECT_IDENTIFIER with hash algorithm */
-	algorithm = OBJ_nid2obj(EVP_MD_type(md));
-	if (algorithm == NULL) {
-		return NULL;
-	}
-
-	/* Create X509_ALGOR */
-	x509_algor = X509_ALGOR_new();
-	if (x509_algor == NULL) {
-		return NULL;
-	}
-	x509_algor->algorithm = algorithm;
-	x509_algor->parameter = ASN1_TYPE_new();
-	ASN1_TYPE_set(x509_algor->parameter, V_ASN1_NULL, NULL);
-
-	/* OCTET_STRING with the actual hash */
-	octet = ASN1_OCTET_STRING_new();
-	if (octet == NULL) {
-		X509_ALGOR_free(x509_algor);
-		return NULL;
-	}
-	ASN1_OCTET_STRING_set(octet, buf, len);
-
 	/* HASH structure containing algorithm + hash */
 	hash = HASH_new();
 	if (hash == NULL) {
-		ASN1_OCTET_STRING_free(octet);
-		X509_ALGOR_free(x509_algor);
 		return NULL;
 	}
-	hash->hashAlgorithm = x509_algor;
-	hash->dataHash = octet;
+
+	/* OBJECT_IDENTIFIER with hash algorithm */
+	algorithm = OBJ_nid2obj(EVP_MD_type(md));
+	if (algorithm == NULL) {
+		HASH_free(hash);
+		return NULL;
+	}
+
+	/* Create X509_ALGOR */
+	hash->hashAlgorithm->algorithm = algorithm;
+	hash->hashAlgorithm->parameter = ASN1_TYPE_new();
+	ASN1_TYPE_set(hash->hashAlgorithm->parameter, V_ASN1_NULL, NULL);
+
+	/* OCTET_STRING with the actual hash */
+	ASN1_OCTET_STRING_set(hash->dataHash, buf, len);
 
 	/* DER encoded HASH */
 	sz = i2d_HASH(hash, &p);
 	if ((sz <= 0) || (p == NULL)) {
 		HASH_free(hash);
-		X509_ALGOR_free(x509_algor);
 		return NULL;
 	}
 
diff --git a/tools/cert_create/src/key.c b/tools/cert_create/src/key.c
index fcc9d53..6435975 100644
--- a/tools/cert_create/src/key.c
+++ b/tools/cert_create/src/key.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -21,6 +21,9 @@
 
 #define MAX_FILENAME_LEN		1024
 
+key_t *keys;
+unsigned int num_keys;
+
 /*
  * Create a new key container
  */
@@ -182,6 +185,28 @@
 	key_t *key;
 	unsigned int i;
 
+	keys = malloc((num_def_keys * sizeof(def_keys[0]))
+#ifdef PDEF_KEYS
+		      + (num_pdef_keys * sizeof(pdef_keys[0]))
+#endif
+		      );
+
+	if (keys == NULL) {
+		ERROR("%s:%d Failed to allocate memory.\n", __func__, __LINE__);
+		return 1;
+	}
+
+	memcpy(&keys[0], &def_keys[0], (num_def_keys * sizeof(def_keys[0])));
+#ifdef PDEF_KEYS
+	memcpy(&keys[num_def_keys], &pdef_keys[0],
+		(num_pdef_keys * sizeof(pdef_keys[0])));
+
+	num_keys = num_def_keys + num_pdef_keys;
+#else
+	num_keys = num_def_keys;
+#endif
+		   ;
+
 	for (i = 0; i < num_keys; i++) {
 		key = &keys[i];
 		if (key->opt != NULL) {
diff --git a/tools/cert_create/src/main.c b/tools/cert_create/src/main.c
index 2ba1101..b39378c 100644
--- a/tools/cert_create/src/main.c
+++ b/tools/cert_create/src/main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -473,6 +473,11 @@
 
 		cert = &certs[i];
 
+		if (cert->fn == NULL) {
+			/* Certificate not requested. Skip to the next one */
+			continue;
+		}
+
 		/* Create a new stack of extensions. This stack will be used
 		 * to create the certificate */
 		CHECK_NULL(sk, sk_X509_EXTENSION_new_null());
@@ -492,7 +497,12 @@
 			 */
 			switch (ext->type) {
 			case EXT_TYPE_NVCOUNTER:
-				if (ext->arg) {
+				if (ext->optional && ext->arg == NULL) {
+					/* Skip this NVCounter */
+					continue;
+				} else {
+					/* Checked by `check_cmd_params` */
+					assert(ext->arg != NULL);
 					nvctr = atoi(ext->arg);
 					CHECK_NULL(cert_ext, ext_new_nvcounter(ext_nid,
 						EXT_CRIT, nvctr));
@@ -505,7 +515,7 @@
 						memset(md, 0x0, SHA512_DIGEST_LENGTH);
 					} else {
 						/* Do not include this hash in the certificate */
-						break;
+						continue;
 					}
 				} else {
 					/* Calculate the hash of the file */
@@ -534,11 +544,16 @@
 		}
 
 		/* Create certificate. Signed with corresponding key */
-		if (cert->fn && !cert_new(hash_alg, cert, VAL_DAYS, 0, sk)) {
+		if (!cert_new(hash_alg, cert, VAL_DAYS, 0, sk)) {
 			ERROR("Cannot create %s\n", cert->cn);
 			exit(1);
 		}
 
+		for (cert_ext = sk_X509_EXTENSION_pop(sk); cert_ext != NULL;
+				cert_ext = sk_X509_EXTENSION_pop(sk)) {
+			X509_EXTENSION_free(cert_ext);
+		}
+
 		sk_X509_EXTENSION_free(sk);
 	}
 
@@ -576,10 +591,44 @@
 		}
 	}
 
+	/* If we got here, then we must have filled the key array completely.
+	 * We can then safely call free on all of the keys in the array
+	 */
+	for (i = 0; i < num_keys; i++) {
+		EVP_PKEY_free(keys[i].key);
+	}
+
 #ifndef OPENSSL_NO_ENGINE
 	ENGINE_cleanup();
 #endif
 	CRYPTO_cleanup_all_ex_data();
 
+
+	/* We allocated strings through strdup, so now we have to free them */
+	for (i = 0; i < num_keys; i++) {
+		if (keys[i].fn != NULL) {
+			void *ptr = keys[i].fn;
+
+			keys[i].fn = NULL;
+			free(ptr);
+		}
+	}
+	for (i = 0; i < num_extensions; i++) {
+		if (extensions[i].arg != NULL) {
+			void *ptr = (void *)extensions[i].arg;
+
+			extensions[i].arg = NULL;
+			free(ptr);
+		}
+	}
+	for (i = 0; i < num_certs; i++) {
+		if (certs[i].fn != NULL) {
+			void *ptr = (void *)certs[i].fn;
+
+			certs[i].fn = NULL;
+			free(ptr);
+		}
+	}
+
 	return 0;
 }
diff --git a/tools/encrypt_fw/Makefile b/tools/encrypt_fw/Makefile
index 6eb6fae..96dff23 100644
--- a/tools/encrypt_fw/Makefile
+++ b/tools/encrypt_fw/Makefile
@@ -46,7 +46,7 @@
 
 .PHONY: all clean realclean
 
-all: clean ${BINARY}
+all: ${BINARY}
 
 ${BINARY}: ${OBJECTS} Makefile
 	@echo "  HOSTLD  $@"
diff --git a/tools/fiptool/Makefile b/tools/fiptool/Makefile
index df8ab5c..11d2e7b 100644
--- a/tools/fiptool/Makefile
+++ b/tools/fiptool/Makefile
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2014-2020, ARM Limited and Contributors. All rights reserved.
+# Copyright (c) 2014-2021, ARM Limited and Contributors. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 #
@@ -32,6 +32,16 @@
 
 HOSTCC ?= gcc
 
+ifneq (${PLAT},)
+TF_PLATFORM_ROOT	:=	../../plat/
+include ${MAKE_HELPERS_DIRECTORY}plat_helpers.mk
+PLAT_FIPTOOL_HELPER_MK := ${PLAT_DIR}/plat_fiptool.mk
+endif
+
+ifneq (,$(wildcard ${PLAT_FIPTOOL_HELPER_MK}))
+include ${PLAT_FIPTOOL_HELPER_MK}
+endif
+
 .PHONY: all clean distclean
 
 all: ${PROJECT}
@@ -43,7 +53,7 @@
 	@echo "Built $@ successfully"
 	@${ECHO_BLANK_LINE}
 
-%.o: %.c %.h Makefile
+%.o: %.c Makefile
 	@echo "  HOSTCC  $<"
 	${Q}${HOSTCC} -c ${CPPFLAGS} ${HOSTCCFLAGS} ${INCLUDE_PATHS} $< -o $@
 
diff --git a/tools/fiptool/fiptool.c b/tools/fiptool/fiptool.c
index 8c5b04a..d92c31d 100644
--- a/tools/fiptool/fiptool.c
+++ b/tools/fiptool/fiptool.c
@@ -215,6 +215,18 @@
 		    toc_entry->cmdline_name);
 		add_image_desc(desc);
 	}
+#ifdef PLAT_DEF_FIP_UUID
+	for (toc_entry = plat_def_toc_entries;
+	     toc_entry->cmdline_name != NULL;
+	     toc_entry++) {
+		image_desc_t *desc;
+
+		desc = new_image_desc(&toc_entry->uuid,
+		    toc_entry->name,
+		    toc_entry->cmdline_name);
+		add_image_desc(desc);
+	}
+#endif
 }
 
 static image_desc_t *lookup_image_desc_from_uuid(const uuid_t *uuid)
@@ -753,6 +765,12 @@
 	for (; toc_entry->cmdline_name != NULL; toc_entry++)
 		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
 		    toc_entry->name);
+#ifdef PLAT_DEF_FIP_UUID
+	toc_entry = plat_def_toc_entries;
+	for (; toc_entry->cmdline_name != NULL; toc_entry++)
+		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
+		    toc_entry->name);
+#endif
 	exit(exit_status);
 }
 
@@ -867,6 +885,12 @@
 	for (; toc_entry->cmdline_name != NULL; toc_entry++)
 		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
 		    toc_entry->name);
+#ifdef PLAT_DEF_FIP_UUID
+	toc_entry = plat_def_toc_entries;
+	for (; toc_entry->cmdline_name != NULL; toc_entry++)
+		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
+		    toc_entry->name);
+#endif
 	exit(exit_status);
 }
 
@@ -1001,6 +1025,12 @@
 	for (; toc_entry->cmdline_name != NULL; toc_entry++)
 		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
 		    toc_entry->name);
+#ifdef PLAT_DEF_FIP_UUID
+	toc_entry = plat_def_toc_entries;
+	for (; toc_entry->cmdline_name != NULL; toc_entry++)
+		printf("  --%-16s FILENAME\t%s\n", toc_entry->cmdline_name,
+		    toc_entry->name);
+#endif
 	printf("\n");
 	printf("If no options are provided, all images will be unpacked.\n");
 	exit(exit_status);
@@ -1126,6 +1156,12 @@
 	for (; toc_entry->cmdline_name != NULL; toc_entry++)
 		printf("  --%-16s\t%s\n", toc_entry->cmdline_name,
 		    toc_entry->name);
+#ifdef PLAT_DEF_FIP_UUID
+	toc_entry = plat_def_toc_entries;
+	for (; toc_entry->cmdline_name != NULL; toc_entry++)
+		printf("  --%-16s\t%s\n", toc_entry->cmdline_name,
+		    toc_entry->name);
+#endif
 	exit(exit_status);
 }
 
diff --git a/tools/fiptool/tbbr_config.c b/tools/fiptool/tbbr_config.c
index c1e5217..4998bb2 100644
--- a/tools/fiptool/tbbr_config.c
+++ b/tools/fiptool/tbbr_config.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2021, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -67,6 +67,11 @@
 		.uuid = UUID_NON_TRUSTED_FIRMWARE_BL33,
 		.cmdline_name = "nt-fw"
 	},
+	{
+		.name = "Realm Monitor Management Firmware",
+		.uuid = UUID_REALM_MONITOR_MGMT_FIRMWARE,
+		.cmdline_name = "rmm-fw"
+	},
 	/* Dynamic Configs */
 	{
 		.name = "FW_CONFIG",
diff --git a/tools/fiptool/tbbr_config.h b/tools/fiptool/tbbr_config.h
index 1fc6cad..b926ff0 100644
--- a/tools/fiptool/tbbr_config.h
+++ b/tools/fiptool/tbbr_config.h
@@ -21,4 +21,8 @@
 
 extern toc_entry_t toc_entries[];
 
+#ifdef PLAT_DEF_FIP_UUID
+extern toc_entry_t plat_def_toc_entries[];
+#endif
+
 #endif /* TBBR_CONFIG_H */
diff --git a/tools/nxp/cert_create_helper/cert_create_tbbr.mk b/tools/nxp/cert_create_helper/cert_create_tbbr.mk
new file mode 100644
index 0000000..e3b2e91
--- /dev/null
+++ b/tools/nxp/cert_create_helper/cert_create_tbbr.mk
@@ -0,0 +1,31 @@
+#
+# Copyright 2021 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Compile time defines used by NXP platforms
+
+PLAT_DEF_OID := yes
+
+ifeq (${PLAT_DEF_OID},yes)
+
+$(eval $(call add_define, PLAT_DEF_OID))
+$(eval $(call add_define, PDEF_KEYS))
+$(eval $(call add_define, PDEF_CERTS))
+$(eval $(call add_define, PDEF_EXTS))
+
+
+INC_DIR += -I../../plat/nxp/common/fip_handler/common/
+
+PDEF_CERT_TOOL_PATH		:=	../nxp/cert_create_helper
+PLAT_INCLUDE			+=	-I${PDEF_CERT_TOOL_PATH}/include
+
+PLAT_OBJECTS			+=	${PDEF_CERT_TOOL_PATH}/src/pdef_tbb_cert.o \
+					${PDEF_CERT_TOOL_PATH}/src/pdef_tbb_ext.o \
+					${PDEF_CERT_TOOL_PATH}/src/pdef_tbb_key.o
+
+$(shell rm ${PLAT_OBJECTS})
+
+OBJECTS				+= ${PLAT_OBJECTS}
+endif
diff --git a/tools/nxp/cert_create_helper/include/pdef_tbb_cert.h b/tools/nxp/cert_create_helper/include/pdef_tbb_cert.h
new file mode 100644
index 0000000..f185619
--- /dev/null
+++ b/tools/nxp/cert_create_helper/include/pdef_tbb_cert.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PDEF_TBB_CERT_H
+#define PDEF_TBB_CERT_H
+
+#include <tbbr/tbb_cert.h>
+
+/*
+ * Enumerate the certificates that are used to establish the chain of trust
+ */
+enum {
+	DDR_FW_KEY_CERT = FWU_CERT + 1,
+	DDR_UDIMM_FW_CONTENT_CERT,
+	DDR_RDIMM_FW_CONTENT_CERT
+};
+
+#endif /* PDEF_TBB_CERT_H */
diff --git a/tools/nxp/cert_create_helper/include/pdef_tbb_ext.h b/tools/nxp/cert_create_helper/include/pdef_tbb_ext.h
new file mode 100644
index 0000000..5fb349c
--- /dev/null
+++ b/tools/nxp/cert_create_helper/include/pdef_tbb_ext.h
@@ -0,0 +1,25 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PDEF_TBB_EXT_H
+#define PDEF_TBB_EXT_H
+
+#include <tbbr/tbb_ext.h>
+
+/* Plat Defined TBBR extensions */
+enum {
+	DDR_FW_CONTENT_CERT_PK_EXT = FWU_HASH_EXT + 1,
+	DDR_IMEM_UDIMM_1D_HASH_EXT,
+	DDR_IMEM_UDIMM_2D_HASH_EXT,
+	DDR_DMEM_UDIMM_1D_HASH_EXT,
+	DDR_DMEM_UDIMM_2D_HASH_EXT,
+	DDR_IMEM_RDIMM_1D_HASH_EXT,
+	DDR_IMEM_RDIMM_2D_HASH_EXT,
+	DDR_DMEM_RDIMM_1D_HASH_EXT,
+	DDR_DMEM_RDIMM_2D_HASH_EXT
+};
+
+#endif /* PDEF_TBB_EXT_H */
diff --git a/tools/nxp/cert_create_helper/include/pdef_tbb_key.h b/tools/nxp/cert_create_helper/include/pdef_tbb_key.h
new file mode 100644
index 0000000..b26b651
--- /dev/null
+++ b/tools/nxp/cert_create_helper/include/pdef_tbb_key.h
@@ -0,0 +1,18 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#ifndef PDEF_TBB_KEY_H
+#define PDEF_TBB_KEY_H
+
+#include <tbbr/tbb_key.h>
+
+/*
+ * Enumerate the pltform defined keys that are used to establish the chain of trust
+ */
+enum {
+	DDR_FW_CONTENT_KEY = NON_TRUSTED_FW_CONTENT_CERT_KEY + 1,
+};
+#endif /* PDEF_TBB_KEY_H */
diff --git a/tools/nxp/cert_create_helper/src/pdef_tbb_cert.c b/tools/nxp/cert_create_helper/src/pdef_tbb_cert.c
new file mode 100644
index 0000000..40bd928
--- /dev/null
+++ b/tools/nxp/cert_create_helper/src/pdef_tbb_cert.c
@@ -0,0 +1,62 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <pdef_tbb_cert.h>
+#include <pdef_tbb_ext.h>
+#include <pdef_tbb_key.h>
+
+static cert_t pdef_tbb_certs[] = {
+	[DDR_FW_KEY_CERT - DDR_FW_KEY_CERT] = {
+		.id = DDR_FW_KEY_CERT,
+		.opt = "ddr-fw-key-cert",
+		.help_msg = "DDR Firmware Key Certificate (output file)",
+		.fn = NULL,
+		.cn = "DDR Firmware Key Certificate",
+		.key = TRUSTED_WORLD_KEY,
+		.issuer = DDR_FW_KEY_CERT,
+		.ext = {
+			TRUSTED_FW_NVCOUNTER_EXT,
+			DDR_FW_CONTENT_CERT_PK_EXT,
+		},
+		.num_ext = 2
+	},
+	[DDR_UDIMM_FW_CONTENT_CERT - DDR_FW_KEY_CERT] = {
+		.id = DDR_UDIMM_FW_CONTENT_CERT,
+		.opt = "ddr-udimm-fw-cert",
+		.help_msg = "DDR UDIMM Firmware Content Certificate (output file)",
+		.fn = NULL,
+		.cn = "DDR UDIMM Firmware Content Certificate",
+		.key = DDR_FW_CONTENT_KEY,
+		.issuer = DDR_UDIMM_FW_CONTENT_CERT,
+		.ext = {
+			TRUSTED_FW_NVCOUNTER_EXT,
+			DDR_IMEM_UDIMM_1D_HASH_EXT,
+			DDR_IMEM_UDIMM_2D_HASH_EXT,
+			DDR_DMEM_UDIMM_1D_HASH_EXT,
+			DDR_DMEM_UDIMM_2D_HASH_EXT,
+		},
+		.num_ext = 5
+	},
+	[DDR_RDIMM_FW_CONTENT_CERT - DDR_FW_KEY_CERT] = {
+		.id = DDR_RDIMM_FW_CONTENT_CERT,
+		.opt = "ddr-rdimm-fw-cert",
+		.help_msg = "DDR RDIMM Firmware Content Certificate (output file)",
+		.fn = NULL,
+		.cn = "DDR RDIMM Firmware Content Certificate",
+		.key = DDR_FW_CONTENT_KEY,
+		.issuer = DDR_RDIMM_FW_CONTENT_CERT,
+		.ext = {
+			TRUSTED_FW_NVCOUNTER_EXT,
+			DDR_IMEM_RDIMM_1D_HASH_EXT,
+			DDR_IMEM_RDIMM_2D_HASH_EXT,
+			DDR_DMEM_RDIMM_1D_HASH_EXT,
+			DDR_DMEM_RDIMM_2D_HASH_EXT,
+		},
+		.num_ext = 5
+	}
+};
+
+PLAT_REGISTER_COT(pdef_tbb_certs);
diff --git a/tools/nxp/cert_create_helper/src/pdef_tbb_ext.c b/tools/nxp/cert_create_helper/src/pdef_tbb_ext.c
new file mode 100644
index 0000000..f6da6dd
--- /dev/null
+++ b/tools/nxp/cert_create_helper/src/pdef_tbb_ext.c
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdio.h>
+#include <string.h>
+#include <openssl/err.h>
+#include <openssl/x509v3.h>
+
+#if USE_TBBR_DEFS
+#include <tbbr_oid.h>
+#else
+#include <platform_oid.h>
+#endif
+
+#include "ext.h"
+#include "tbbr/tbb_ext.h"
+#include "tbbr/tbb_key.h"
+
+#include <pdef_tbb_ext.h>
+#include <pdef_tbb_key.h>
+
+static ext_t pdef_tbb_ext[] = {
+	[DDR_FW_CONTENT_CERT_PK_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_FW_CONTENT_CERT_PK_OID,
+		.sn = "DDR FirmwareContentCertPK",
+		.ln = "DDR Firmware content certificate public key",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_PKEY,
+		.attr.key = DDR_FW_CONTENT_KEY
+	},
+	[DDR_IMEM_UDIMM_1D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_IMEM_UDIMM_1D_HASH_OID,
+		.opt = "ddr-immem-udimm-1d",
+		.help_msg = "DDR Firmware IMEM UDIMM 1D image file",
+		.sn = "DDR UDIMM IMEM 1D FirmwareHash",
+		.ln = "DDR UDIMM IMEM 1D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_IMEM_UDIMM_2D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_IMEM_UDIMM_2D_HASH_OID,
+		.opt = "ddr-immem-udimm-2d",
+		.help_msg = "DDR Firmware IMEM UDIMM 2D image file",
+		.sn = "DDR UDIMM IMEM 2D FirmwareHash",
+		.ln = "DDR UDIMM IMEM 2D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_DMEM_UDIMM_1D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_DMEM_UDIMM_1D_HASH_OID,
+		.opt = "ddr-dmmem-udimm-1d",
+		.help_msg = "DDR Firmware DMEM UDIMM 1D image file",
+		.sn = "DDR UDIMM DMEM 1D FirmwareHash",
+		.ln = "DDR UDIMM DMEM 1D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_DMEM_UDIMM_2D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_DMEM_UDIMM_2D_HASH_OID,
+		.opt = "ddr-dmmem-udimm-2d",
+		.help_msg = "DDR Firmware DMEM UDIMM 2D image file",
+		.sn = "DDR UDIMM DMEM 2D FirmwareHash",
+		.ln = "DDR UDIMM DMEM 2D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_IMEM_RDIMM_1D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_IMEM_RDIMM_1D_HASH_OID,
+		.opt = "ddr-immem-rdimm-1d",
+		.help_msg = "DDR Firmware IMEM RDIMM 1D image file",
+		.sn = "DDR RDIMM IMEM 1D FirmwareHash",
+		.ln = "DDR RDIMM IMEM 1D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_IMEM_RDIMM_2D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_IMEM_RDIMM_2D_HASH_OID,
+		.opt = "ddr-immem-rdimm-2d",
+		.help_msg = "DDR Firmware IMEM RDIMM 2D image file",
+		.sn = "DDR RDIMM IMEM 2D FirmwareHash",
+		.ln = "DDR RDIMM IMEM 2D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_DMEM_RDIMM_1D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_DMEM_RDIMM_1D_HASH_OID,
+		.opt = "ddr-dmmem-rdimm-1d",
+		.help_msg = "DDR Firmware DMEM RDIMM 1D image file",
+		.sn = "DDR RDIMM DMEM 1D FirmwareHash",
+		.ln = "DDR RDIMM DMEM 1D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	},
+	[DDR_DMEM_RDIMM_2D_HASH_EXT - DDR_FW_CONTENT_CERT_PK_EXT] = {
+		.oid = DDR_DMEM_RDIMM_2D_HASH_OID,
+		.opt = "ddr-dmmem-rdimm-2d",
+		.help_msg = "DDR Firmware DMEM RDIMM 2D image file",
+		.sn = "DDR RDIMM DMEM 2D FirmwareHash",
+		.ln = "DDR RDIMM DMEM 2D Firmware hash (SHA256)",
+		.asn1_type = V_ASN1_OCTET_STRING,
+		.type = EXT_TYPE_HASH
+	}
+};
+
+PLAT_REGISTER_EXTENSIONS(pdef_tbb_ext);
diff --git a/tools/nxp/cert_create_helper/src/pdef_tbb_key.c b/tools/nxp/cert_create_helper/src/pdef_tbb_key.c
new file mode 100644
index 0000000..cf2ebda
--- /dev/null
+++ b/tools/nxp/cert_create_helper/src/pdef_tbb_key.c
@@ -0,0 +1,18 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <pdef_tbb_key.h>
+
+static key_t pdef_tbb_keys[] = {
+	[DDR_FW_CONTENT_KEY - DDR_FW_CONTENT_KEY] = {
+		.id = DDR_FW_CONTENT_KEY,
+		.opt = "ddr-fw-key",
+		.help_msg = "DDR Firmware Content Certificate key (input/output file)",
+		.desc = "DDR Firmware Content Certificate key"
+	}
+};
+
+PLAT_REGISTER_KEYS(pdef_tbb_keys);
diff --git a/tools/nxp/create_pbl/Makefile b/tools/nxp/create_pbl/Makefile
new file mode 100644
index 0000000..f971a74
--- /dev/null
+++ b/tools/nxp/create_pbl/Makefile
@@ -0,0 +1,61 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+MAKE_HELPERS_DIRECTORY := ../../../make_helpers/
+include ${MAKE_HELPERS_DIRECTORY}build_macros.mk
+include ${MAKE_HELPERS_DIRECTORY}build_env.mk
+
+PROJECT_1 := create_pbl${BIN_EXT}
+OBJECTS_1 := create_pbl.o
+PROJECT_2 := byte_swap${BIN_EXT}
+OBJECTS_2 := byte_swap.o
+V ?= 0
+
+override CPPFLAGS += -D_GNU_SOURCE -D_XOPEN_SOURCE=700
+CFLAGS := -Wall -Werror -pedantic -std=c99
+ifeq (${DEBUG},1)
+  CFLAGS += -g -O0 -DDEBUG
+else
+  CFLAGS += -O2
+endif
+LDLIBS :=
+
+ifeq (${V},0)
+  Q := @
+else
+  Q :=
+endif
+
+INCLUDE_PATHS :=
+
+HOSTCC ?= gcc
+CC = gcc
+
+.PHONY: all clean distclean
+
+all: create_pbl byte_swap
+
+${PROJECT_1}: ${OBJECTS_1} Makefile
+	@echo "  LD      $@"
+	${Q}${HOSTCC} ${OBJECTS_1} -o $@ ${LDLIBS}
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@${ECHO_BLANK_LINE}
+
+${PROJECT_2}: ${OBJECTS_2} Makefile
+	@echo "  LD      $@"
+	${Q}${HOSTCC} ${OBJECTS_2} -o $@ ${LDLIBS}
+	@${ECHO_BLANK_LINE}
+	@echo "Built $@ successfully"
+	@${ECHO_BLANK_LINE}
+
+%.o: %.c %.h Makefile
+	@echo "  CC      $<"
+	${Q}${HOSTCC} -c ${CPPFLAGS} ${CFLAGS} ${INCLUDE_PATHS} $< -o $@
+
+clean:
+	$(call SHELL_DELETE_ALL, ${PROJECT_1} ${OBJECTS_1})
+	$(call SHELL_DELETE_ALL, ${PROJECT_2} ${OBJECTS_2})
diff --git a/tools/nxp/create_pbl/README b/tools/nxp/create_pbl/README
new file mode 100644
index 0000000..3b6f854
--- /dev/null
+++ b/tools/nxp/create_pbl/README
@@ -0,0 +1,65 @@
+Description:
+------------
+Tool 'create_pbl' is a standalone tool to create the PBL images.
+	 where,
+	     On the basis of Chassis,
+	     RCW image is placed first followed by the,
+	     PBI commands to copy the,
+	     Input BL2 image stored on the,
+	     Specified boot source (QSPI or SD or NOR) to the,
+             Specified destination address.
+
+
+Usage in standalone way:
+-----------------------
+
+./create_pbl [options] (mentioned below):
+
+	-r  <RCW file-name>         - name of RCW binary file.
+	-i  <BL2 Bin file-name>     - file to be added to rcw file.
+	-c  <SoC Number>            - SoC numeric identifier, may be one of
+                                  1012,1023,1026.1028,
+                                  1043,1046,1088,2080,
+                                  2088,2160
+	-b  <boot source id>        - Boot source id string, may be one of
+                                  "qspi", "nor", "nand", "sd", "emmc"
+	-d  <Address>               - Destination address where BL2
+	                              image is to be copied
+	-o  <output filename>	    - Name of PBL image generated
+	                              as an output of the tool.
+	-e  <Address>               - [Optional] Entry Point Address
+	                              of the BL2.bin
+	-f  <Address>               - BL2 image offset
+	                              on Boot Source for block copy.
+	                              command for chassis >=3.)
+				      (Must for Ch3, Ignored for Ch2)
+	-h  Help.
+	-s  Secure boot.
+
+		-s 	secure boot
+		-c	SoC Number (see description above)
+		-b	Boot source.
+		-r	RCW binary file.
+		-i	Input file that is to be added to rcw file.
+		-o	Name of output file
+		-f	Source Offset (Block Copy)
+		-d	Destination address to which file has to be copied
+		-h	Help.
+
+Example:
+	./create_pbl -r <RCW file> -i <bl2.bin> -c <chassis_no> -b <boot_source = sd/qspi/nor> -d <Destination_Addr> -o <pbl_image_name>
+
+
+
+Usage at compilation time:
+--------------------------------
+
+	make <compilation command......> pbl RCW=<Path_to_RCW_File>/<rcw_file_name.bin>
+
+Example: QSPI Boot For LS1046ARDB-
+
+	make PLAT=ls1046rdb all fip BOOT_MODE=qspi SPD=opteed BL32=tee.bin BL33=u-boot-ls1046.bin pbl RCW=/home/pankaj/flexbuild/packages/firmware/dash-rcw/ls1046ardb/RR_FFSSPPPN_1133_5506/rcw_1600_qspiboot.bin
+
+Example: QSPI Boot For LX2160ARDB-
+
+	make PLAT=lx2160ardb all fip BOOT_MODE=flexspi_nor SPD=opteed BL32=tee_lx2.bin BL33=u-boot_lx2160.bin pbl RCW=plat/nxp/soc-lx2160/lx2160ardb/rcw_1900_600_1600_19_5_2.bin
diff --git a/tools/nxp/create_pbl/byte_swap.c b/tools/nxp/create_pbl/byte_swap.c
new file mode 100644
index 0000000..1d0bfce
--- /dev/null
+++ b/tools/nxp/create_pbl/byte_swap.c
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <getopt.h>
+#include <unistd.h>
+
+#define NUM_MEM_BLOCK		1
+#define FOUR_BYTE_ALIGN		4
+#define EIGHT_BYTE_ALIGN	8
+#define SIZE_TWO_PBL_CMD	24
+
+#define SUCCESS			 0
+#define FAILURE			-1
+#define BYTE_SWAP_32(word)	((((word) & 0xff000000) >> 24)|	\
+				(((word) & 0x00ff0000) >>  8) |	\
+				(((word) & 0x0000ff00) <<  8) |	\
+				(((word) & 0x000000ff) << 24))
+
+
+/*
+ * Returns:
+ *     SUCCESS, on successful byte swapping.
+ *     FAILURE, on failure.
+ */
+int do_byteswap(FILE *fp)
+{
+	int bytes = 0;
+	uint32_t  upper_byte;
+	uint32_t  lower_byte;
+	uint32_t  pad = 0U;
+	/* Carries number of Padding bytes to be appended to
+	 * make file size 8 byte aligned.
+	 */
+	int append_bytes;
+	int ret = FAILURE;
+
+	fseek(fp, 0L, SEEK_END);
+	bytes = ftell(fp);
+
+	append_bytes = EIGHT_BYTE_ALIGN - (bytes % EIGHT_BYTE_ALIGN);
+	if (append_bytes != 0) {
+		if (fwrite(&pad, append_bytes, NUM_MEM_BLOCK, fp)
+			!= NUM_MEM_BLOCK) {
+			printf("%s: Error in appending padding bytes.\n",
+				__func__);
+			goto byteswap_err;
+		}
+		bytes += append_bytes;
+	}
+
+	rewind(fp);
+	while (bytes > 0) {
+		if ((fread(&upper_byte, sizeof(upper_byte), NUM_MEM_BLOCK, fp)
+			!= NUM_MEM_BLOCK) && (feof(fp) == 0)) {
+			printf("%s: Error reading upper bytes.\n", __func__);
+			goto byteswap_err;
+		}
+		if ((fread(&lower_byte, sizeof(lower_byte), NUM_MEM_BLOCK, fp)
+			!= NUM_MEM_BLOCK) && (feof(fp) == 0)) {
+			printf("%s: Error reading lower bytes.\n", __func__);
+			goto byteswap_err;
+		}
+		fseek(fp, -8L, SEEK_CUR);
+		upper_byte = BYTE_SWAP_32(upper_byte);
+		lower_byte = BYTE_SWAP_32(lower_byte);
+		if (fwrite(&lower_byte, sizeof(lower_byte), NUM_MEM_BLOCK, fp)
+			!= NUM_MEM_BLOCK) {
+			printf("%s: Error writing lower bytes.\n", __func__);
+			goto byteswap_err;
+		}
+		if (fwrite(&upper_byte, sizeof(upper_byte), NUM_MEM_BLOCK, fp)
+			!= NUM_MEM_BLOCK) {
+			printf("%s: Error writing upper bytes.\n", __func__);
+			goto byteswap_err;
+		}
+		bytes -= EIGHT_BYTE_ALIGN;
+	}
+	ret = SUCCESS;
+
+byteswap_err:
+	return ret;
+}
+
+int main(int argc, char **argv)
+{
+	FILE *fp = NULL;
+	int ret = 0;
+
+	if (argc > 2) {
+		printf("Usage format is byteswap <filename>");
+		return -1;
+	}
+
+	fp = fopen(argv[1], "rb+");
+	if (fp == NULL) {
+		printf("%s: Error opening the input file: %s\n",
+			__func__, argv[1]);
+		return -1;
+	}
+
+	ret = do_byteswap(fp);
+	fclose(fp);
+	return ret;
+}
diff --git a/tools/nxp/create_pbl/create_pbl.c b/tools/nxp/create_pbl/create_pbl.c
new file mode 100644
index 0000000..244b0fb
--- /dev/null
+++ b/tools/nxp/create_pbl/create_pbl.c
@@ -0,0 +1,996 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <getopt.h>
+#include <unistd.h>
+
+#define NUM_MEM_BLOCK		1
+#define FOUR_BYTE_ALIGN		4
+#define EIGHT_BYTE_ALIGN	8
+#define SIZE_TWO_PBL_CMD	24
+
+/* Define for add_boot_ptr_cmd() */
+#define BOOTPTR_ADDR 0x09570604
+#define CSF_ADDR_SB 0x09ee0200
+/* CCSR write command to address 0x1e00400 i.e BOOTLOCPTR */
+#define BOOTPTR_ADDR_CH3 0x31e00400
+/* Load CSF header command */
+#define CSF_ADDR_SB_CH3 0x80220000
+
+#define	MAND_ARG_MASK				0xFFF3
+#define	ARG_INIT_MASK				0xFF00
+#define RCW_FILE_NAME_ARG_MASK			0x0080
+#define IN_FILE_NAME_ARG_MASK			0x0040
+#define CHASSIS_ARG_MASK			0x0020
+#define BOOT_SRC_ARG_MASK			0x0010
+#define ENTRY_POINT_ADDR_ARG_MASK		0x0008
+#define BL2_BIN_STRG_LOC_BOOT_SRC_ARG_MASK	0x0004
+#define BL2_BIN_CPY_DEST_ADDR_ARG_MASK		0x0002
+#define OP_FILE_NAME_ARG_MASK			0x0001
+
+/* Define for add_cpy_cmd() */
+#define OFFSET_MASK		        0x00ffffff
+#define WRITE_CMD_BASE		    0x81000000
+#define MAX_PBI_DATA_LEN_BYTE	64
+
+/* 140 Bytes = Preamble + LOAD RCW command + RCW (128 bytes) + Checksum */
+#define CHS3_CRC_PAYLOAD_START_OFFSET 140
+
+#define PBI_CRC_POLYNOMIAL	0x04c11db7
+
+typedef enum {
+	CHASSIS_UNKNOWN,
+	CHASSIS_2,
+	CHASSIS_3,
+	CHASSIS_3_2,
+	CHASSIS_MAX    /* must be last item in list */
+} chassis_t;
+
+typedef enum {
+	UNKNOWN_BOOT = 0,
+	IFC_NOR_BOOT,
+	IFC_NAND_BOOT,
+	QSPI_BOOT,
+	SD_BOOT,
+	EMMC_BOOT,
+	FLXSPI_NOR_BOOT,
+	FLXSPI_NAND_BOOT,
+	FLXSPI_NAND4K_BOOT,
+	MAX_BOOT    /* must be last item in list */
+} boot_src_t;
+
+/* Base Addresses where PBL image is copied depending on the boot source.
+ * Boot address map varies as per Chassis architecture.
+ */
+#define BASE_ADDR_UNDEFINED  0xFFFFFFFF
+#define BASE_ADDR_QSPI       0x20000000
+#define BASE_ADDR_SD         0x00001000
+#define BASE_ADDR_IFC_NOR    0x30000000
+#define BASE_ADDR_EMMC       0x00001000
+#define BASE_ADDR_FLX_NOR    0x20000000
+#define BASE_ADDR_NAND       0x20000000
+
+uint32_t base_addr_ch3[MAX_BOOT] = {
+	BASE_ADDR_UNDEFINED,
+	BASE_ADDR_IFC_NOR,
+	BASE_ADDR_UNDEFINED,	/*IFC NAND */
+	BASE_ADDR_QSPI,
+	BASE_ADDR_SD,
+	BASE_ADDR_EMMC,
+	BASE_ADDR_UNDEFINED,	/*FLXSPI NOR */
+	BASE_ADDR_UNDEFINED,	/*FLXSPI NAND 2K */
+	BASE_ADDR_UNDEFINED	/*FLXSPI NAND 4K */
+};
+
+uint32_t base_addr_ch32[MAX_BOOT] = {
+	BASE_ADDR_UNDEFINED,
+	BASE_ADDR_UNDEFINED,	/* IFC NOR */
+	BASE_ADDR_UNDEFINED,	/* IFC NAND */
+	BASE_ADDR_UNDEFINED,	/* QSPI */
+	BASE_ADDR_SD,
+	BASE_ADDR_EMMC,
+	BASE_ADDR_FLX_NOR,
+	BASE_ADDR_UNDEFINED,	/*FLXSPI NAND 2K */
+	BASE_ADDR_UNDEFINED	/*FLXSPI NAND 4K */
+};
+
+/* for Chassis 3 */
+uint32_t blk_cpy_hdr_map_ch3[] = {
+
+	0,		    /* Unknown Boot Source */
+	0x80000020,	/* NOR_BOOT */
+	0x0,		/* NAND_BOOT */
+	0x80000062,	/* QSPI_BOOT */
+	0x80000040,	/* SD_BOOT */
+	0x80000041,	/* EMMC_BOOT */
+	0x0,		/* FLEXSPI NOR_BOOT */
+	0x0,	/* FLEX SPI NAND2K BOOT */
+	0x0,	/* CHASIS3_2_NAND4K_BOOT */
+};
+
+uint32_t blk_cpy_hdr_map_ch32[] = {
+	0,		    /* Unknown Boot Source */
+	0x0,		/* NOR_BOOT */
+	0x0,		/* NAND_BOOT */
+	0x0,		/* QSPI_BOOT */
+	0x80000008,	/* SD_BOOT */
+	0x80000009,	/* EMMC_BOOT */
+	0x8000000F,	/* FLEXSPI NOR_BOOT */
+	0x8000000C,	/* FLEX SPI NAND2K BOOT */
+	0x8000000D,	/* CHASIS3_2_NAND4K_BOOT */
+};
+
+char *boot_src_string[] = {
+	"UNKNOWN_BOOT",
+	"IFC_NOR_BOOT",
+	"IFC_NAND_BOOT",
+	"QSPI_BOOT",
+	"SD_BOOT",
+	"EMMC_BOOT",
+	"FLXSPI_NOR_BOOT",
+	"FLXSPI_NAND_BOOT",
+	"FLXSPI_NAND4K_BOOT",
+};
+
+enum stop_command {
+	STOP_COMMAND = 0,
+	CRC_STOP_COMMAND
+};
+
+/* Structure will get populated in the main function
+ * as part of parsing the command line arguments.
+ * All member parameters are mandatory except:
+ *	-ep
+ *	-src_addr
+ */
+struct pbl_image {
+	char *rcw_nm;		/* Input RCW File */
+	char *sec_imgnm;	/* Input BL2 binary */
+	char *imagefile;	/* Generated output file */
+	boot_src_t boot_src;	/* Boot Source - QSPI, SD, NOR, NAND etc */
+	uint32_t src_addr;	/* Source Address */
+	uint32_t addr;		/* Load address */
+	uint32_t ep;		/* Entry point <opt> default is load address */
+	chassis_t chassis;	/* Chassis type */
+} pblimg;
+
+#define SUCCESS			 0
+#define FAILURE			-1
+#define CRC_STOP_CMD_ARM	0x08610040
+#define CRC_STOP_CMD_ARM_CH3	0x808f0000
+#define STOP_CMD_ARM_CH3	0x80ff0000
+#define BYTE_SWAP_32(word)	((((word) & 0xff000000) >> 24)|	\
+				(((word) & 0x00ff0000) >>  8) |	\
+				(((word) & 0x0000ff00) <<  8) |	\
+				(((word) & 0x000000ff) << 24))
+
+#define PBI_LEN_MASK	0xFFF00000
+#define PBI_LEN_SHIFT	20
+#define NUM_RCW_WORD	35
+#define PBI_LEN_ADD		6
+
+#define MAX_CRC_ENTRIES 256
+
+/* SoC numeric identifier */
+#define SOC_LS1012 1012
+#define SOC_LS1023 1023
+#define SOC_LS1026 1026
+#define SOC_LS1028 1028
+#define SOC_LS1043 1043
+#define SOC_LS1046 1046
+#define SOC_LS1088 1088
+#define SOC_LS2080 2080
+#define SOC_LS2088 2088
+#define SOC_LX2160 2160
+
+static uint32_t pbl_size;
+bool sb_flag;
+
+/***************************************************************************
+ * Description	:	CRC32 Lookup Table
+ ***************************************************************************/
+static uint32_t crc32_lookup[] = {
+	 0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA,
+	 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3,
+	 0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988,
+	 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91,
+	 0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE,
+	 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7,
+	 0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC,
+	 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5,
+	 0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172,
+	 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B,
+	 0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940,
+	 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59,
+	 0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116,
+	 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F,
+	 0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924,
+	 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D,
+	 0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A,
+	 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433,
+	 0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818,
+	 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01,
+	 0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E,
+	 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457,
+	 0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C,
+	 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65,
+	 0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2,
+	 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB,
+	 0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0,
+	 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9,
+	 0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086,
+	 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F,
+	 0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4,
+	 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD,
+	 0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A,
+	 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683,
+	 0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8,
+	 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1,
+	 0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE,
+	 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7,
+	 0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC,
+	 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5,
+	 0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252,
+	 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B,
+	 0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60,
+	 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79,
+	 0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236,
+	 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F,
+	 0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04,
+	 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D,
+	 0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A,
+	 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713,
+	 0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38,
+	 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21,
+	 0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E,
+	 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777,
+	 0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C,
+	 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45,
+	 0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2,
+	 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB,
+	 0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0,
+	 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9,
+	 0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6,
+	 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF,
+	 0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94,
+	 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D
+	};
+
+
+static void print_usage(void)
+{
+	printf("\nCorrect Usage of Tool is:\n");
+	printf("\n ./create_pbl [options] (mentioned below):\n\n");
+	printf("\t-r  <RCW file-name>     - name of RCW binary file.\n");
+	printf("\t-i  <BL2 Bin file-name> - file to be added to rcw file.\n");
+	printf("\t-c  <Number>            - Chassis Architecture (=2 or =3\n");
+	printf("\t                          or =4 for 3.2).\n");
+	printf("\t-b  <qspi/nor/nand/sd>  - Boot source.\n");
+	printf("\t-d  <Address>           - Destination address where BL2\n");
+	printf("\t                          image is to be copied\n");
+	printf("\t-o  <output filename>	  - Name of PBL image generated\n");
+	printf("\t                          as an output of the tool.\n");
+	printf("\t-f  <Address>           - BL2 image Src Offset\n");
+	printf("\t                          on Boot Source for block copy.\n");
+	printf("\t                          command for chassis >=3.)\n");
+	printf("\t-e  <Address>           - [Optional] Entry Point Address\n");
+	printf("\t                          of the BL2.bin\n");
+	printf("\t-s  Secure Boot.\n");
+	printf("\t-h  Help.\n");
+	printf("\n\n");
+	exit(0);
+
+}
+
+/***************************************************************************
+ * Function	:	crypto_calculate_checksum()
+ * Arguments	:	data - Pointer to FILE
+ *			num - Number of 32 bit words for checksum
+ * Return	:	Checksum Value
+ * Description	:	Calculate Checksum over the data
+ ***************************************************************************/
+uint32_t crypto_calculate_checksum(FILE *fp_rcw_pbi_op, uint32_t num)
+{
+	uint32_t i;
+	uint64_t sum = 0;
+	uint32_t word;
+
+	fseek(fp_rcw_pbi_op, 0L, SEEK_SET);
+	for (i = 0; i < num ; i++) {
+		if ((fread(&word, sizeof(word), NUM_MEM_BLOCK, fp_rcw_pbi_op))
+			< NUM_MEM_BLOCK) {
+			printf("%s: Error reading word.\n", __func__);
+			return FAILURE;
+		}
+		sum = sum + word;
+		sum = sum & 0xFFFFFFFF;
+	}
+	return (uint32_t)sum;
+}
+
+/***************************************************************************
+ * Function	:	add_pbi_stop_cmd
+ * Arguments	:	fp_rcw_pbi_op - output rcw_pbi file pointer
+ * Return	:	SUCCESS or FAILURE
+ * Description	:	This function insert pbi stop command.
+ ***************************************************************************/
+int add_pbi_stop_cmd(FILE *fp_rcw_pbi_op, enum stop_command flag)
+{
+	int ret = FAILURE;
+	int32_t pbi_stop_cmd;
+	uint32_t pbi_crc = 0xffffffff, i, j, c;
+	uint32_t crc_table[MAX_CRC_ENTRIES];
+	uint8_t data;
+
+	switch (pblimg.chassis) {
+	case CHASSIS_2:
+		pbi_stop_cmd = BYTE_SWAP_32(CRC_STOP_CMD_ARM);
+		break;
+	case CHASSIS_3:
+	case CHASSIS_3_2:
+		/* Based on flag add the corresponsding cmd
+		 * -- stop cmd or stop with CRC cmd
+		 */
+		if (flag == CRC_STOP_COMMAND) {
+			pbi_stop_cmd = CRC_STOP_CMD_ARM_CH3;
+		} else {
+			pbi_stop_cmd = STOP_CMD_ARM_CH3;
+		}
+		break;
+	case CHASSIS_UNKNOWN:
+	case CHASSIS_MAX:
+	default:
+		printf("Internal Error: Invalid Chassis val = %d.\n",
+			pblimg.chassis);
+		goto pbi_stop_err;
+	}
+
+	if (fwrite(&pbi_stop_cmd, sizeof(pbi_stop_cmd), NUM_MEM_BLOCK,
+			fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+		printf("%s: Error in Writing PBI STOP CMD\n", __func__);
+		goto pbi_stop_err;
+	}
+
+	if (flag == CRC_STOP_COMMAND) {
+		for (i = 0; i < MAX_CRC_ENTRIES; i++) {
+			c = i << 24;
+			for (j = 0; j < 8; j++) {
+				c = (c & 0x80000000) ?
+					PBI_CRC_POLYNOMIAL ^ (c << 1) : c << 1;
+			}
+
+			crc_table[i] = c;
+		}
+	}
+
+	switch (pblimg.chassis) {
+	case CHASSIS_2:
+		/* Chassis 2: CRC is calculated on  RCW + PBL cmd.*/
+		fseek(fp_rcw_pbi_op, 0L, SEEK_SET);
+		break;
+	case CHASSIS_3:
+	case CHASSIS_3_2:
+		/* Chassis 3: CRC is calculated on  PBL cmd only. */
+		fseek(fp_rcw_pbi_op, CHS3_CRC_PAYLOAD_START_OFFSET, SEEK_SET);
+		break;
+	case CHASSIS_UNKNOWN:
+	case CHASSIS_MAX:
+		printf("%s: Unknown Chassis.\n", __func__);
+		goto pbi_stop_err;
+	}
+
+	while ((fread(&data, sizeof(data), NUM_MEM_BLOCK, fp_rcw_pbi_op))
+		== NUM_MEM_BLOCK) {
+		if (flag == CRC_STOP_COMMAND) {
+			if (pblimg.chassis == CHASSIS_2) {
+				pbi_crc = crc_table
+					  [((pbi_crc >> 24) ^ (data)) & 0xff] ^
+					  (pbi_crc << 8);
+			} else {
+				pbi_crc =  (pbi_crc >> 8) ^
+					   crc32_lookup[((pbi_crc) ^
+							   (data)) & 0xff];
+			}
+		}
+	}
+
+	switch (pblimg.chassis) {
+	case CHASSIS_2:
+		pbi_crc = BYTE_SWAP_32(pbi_crc);
+		break;
+	case CHASSIS_3:
+	case CHASSIS_3_2:
+		if (flag == CRC_STOP_COMMAND) {
+			pbi_crc = pbi_crc ^ 0xFFFFFFFF;
+		} else {
+			pbi_crc = 0x00000000;
+		}
+		break;
+	case CHASSIS_UNKNOWN:
+	case CHASSIS_MAX:
+		printf("%s: Unknown Chassis.\n", __func__);
+		goto pbi_stop_err;
+	}
+
+	if (fwrite(&pbi_crc, sizeof(pbi_crc), NUM_MEM_BLOCK, fp_rcw_pbi_op)
+		!= NUM_MEM_BLOCK) {
+		printf("%s: Error in Writing PBI PBI CRC\n", __func__);
+		goto pbi_stop_err;
+	}
+	ret = SUCCESS;
+
+pbi_stop_err:
+	return ret;
+}
+
+/*
+ * Returns:
+ *     File size in bytes, on Success.
+ *     FAILURE, on failure.
+ */
+int get_filesize(const char *c)
+{
+	FILE *fp;
+	int ret = FAILURE;
+
+	fp = fopen(c, "rb");
+	if (fp == NULL) {
+		fprintf(stderr, "%s: Error in opening the file: %s\n",
+			__func__, c);
+		goto filesize_err;
+	}
+
+	fseek(fp, 0L, SEEK_END);
+	ret = ftell(fp);
+	fclose(fp);
+
+filesize_err:
+	return ret;
+}
+
+/***************************************************************************
+ * Function	:	get_bootptr
+ * Arguments	:	fp_rcw_pbi_op - Pointer to output file
+ * Return	:	SUCCESS or FAILURE
+ * Description	:	Add bootptr pbi command to output file
+ ***************************************************************************/
+int add_boot_ptr_cmd(FILE *fp_rcw_pbi_op)
+{
+	uint32_t bootptr_addr;
+	int ret = FAILURE;
+
+	switch (pblimg.chassis) {
+	case CHASSIS_2:
+		if (sb_flag == true)
+			bootptr_addr = BYTE_SWAP_32(CSF_ADDR_SB);
+		else
+			bootptr_addr = BYTE_SWAP_32(BOOTPTR_ADDR);
+		pblimg.ep    = BYTE_SWAP_32(pblimg.ep);
+		break;
+	case CHASSIS_3:
+	case CHASSIS_3_2:
+		if (sb_flag == true)
+			bootptr_addr = CSF_ADDR_SB_CH3;
+		else
+			bootptr_addr = BOOTPTR_ADDR_CH3;
+		break;
+	case CHASSIS_UNKNOWN:
+	case CHASSIS_MAX:
+	default:
+		printf("Internal Error: Invalid Chassis val = %d.\n",
+			pblimg.chassis);
+		goto bootptr_err;
+	}
+
+	if (fwrite(&bootptr_addr, sizeof(bootptr_addr), NUM_MEM_BLOCK,
+		fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+		printf("%s: Error in Writing PBI Words:[%d].\n",
+			 __func__, ret);
+		goto bootptr_err;
+	}
+
+	if (pblimg.ep != 0) {
+		if (fwrite(&pblimg.ep, sizeof(pblimg.ep), NUM_MEM_BLOCK,
+			fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error in Writing PBI Words\n", __func__);
+			goto bootptr_err;
+		}
+	}
+
+	printf("\nBoot Location Pointer= %x\n", BYTE_SWAP_32(pblimg.ep));
+	ret = SUCCESS;
+
+bootptr_err:
+	return ret;
+}
+
+/***************************************************************************
+ * Function	:	add_blk_cpy_cmd
+ * Arguments	:	pbi_word - pointer to pbi commands
+ *			args - Command  line args flag.
+ * Return	:	SUCCESS or FAILURE
+ * Description	:	Add pbi commands for block copy cmd in pbi_words
+ ***************************************************************************/
+int add_blk_cpy_cmd(FILE *fp_rcw_pbi_op, uint16_t args)
+{
+	uint32_t blk_cpy_hdr;
+	uint32_t file_size, new_file_size;
+	uint32_t align = 4;
+	int ret = FAILURE;
+	int num_pad_bytes = 0;
+
+	if ((args & BL2_BIN_STRG_LOC_BOOT_SRC_ARG_MASK) == 0) {
+		printf("ERROR: Offset not specified for Block Copy Cmd.\n");
+		printf("\tSee Usage and use -f option\n");
+		goto blk_copy_err;
+	}
+
+	switch (pblimg.chassis) {
+	case CHASSIS_3:
+		/* Block copy command */
+		blk_cpy_hdr = blk_cpy_hdr_map_ch3[pblimg.boot_src];
+		pblimg.src_addr += base_addr_ch3[pblimg.boot_src];
+		break;
+	case CHASSIS_3_2:
+		/* Block copy command */
+		blk_cpy_hdr = blk_cpy_hdr_map_ch32[pblimg.boot_src];
+		pblimg.src_addr += base_addr_ch32[pblimg.boot_src];
+		break;
+	default:
+		printf("%s: Error invalid chassis type for this command.\n",
+				__func__);
+		goto blk_copy_err;
+	}
+
+	file_size = get_filesize(pblimg.sec_imgnm);
+	if (file_size > 0) {
+		new_file_size = (file_size + (file_size % align));
+
+		/* Add Block copy command */
+		if (fwrite(&blk_cpy_hdr, sizeof(blk_cpy_hdr), NUM_MEM_BLOCK,
+			fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing blk_cpy_hdr to the file.\n",
+				 __func__);
+			goto blk_copy_err;
+		}
+
+		if ((args & BL2_BIN_STRG_LOC_BOOT_SRC_ARG_MASK) == 0)
+			num_pad_bytes = pblimg.src_addr % 4;
+
+		/* Add Src address word */
+		if (fwrite(&pblimg.src_addr + num_pad_bytes,
+			   sizeof(pblimg.src_addr), NUM_MEM_BLOCK,
+			   fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing BLK SRC Addr to the file.\n",
+				 __func__);
+			goto blk_copy_err;
+		}
+
+		/* Add Dest address word */
+		if (fwrite(&pblimg.addr, sizeof(pblimg.addr),
+			NUM_MEM_BLOCK, fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing DST Addr to the file.\n",
+			__func__);
+			goto blk_copy_err;
+		}
+
+		/* Add size */
+		if (fwrite(&new_file_size, sizeof(new_file_size),
+			NUM_MEM_BLOCK, fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing size to the file.\n",
+				__func__);
+			goto blk_copy_err;
+		}
+	}
+
+	ret = SUCCESS;
+
+blk_copy_err:
+	return ret;
+}
+
+/***************************************************************************
+ * Function	:	add_cpy_cmd
+ * Arguments	:	pbi_word - pointer to pbi commands
+ * Return	:	SUCCESS or FAILURE
+ * Description	:	Append pbi commands for copying BL2 image to the
+ *			load address stored in pbl_image.addr
+ ***************************************************************************/
+int add_cpy_cmd(FILE *fp_rcw_pbi_op)
+{
+	uint32_t ALTCBAR_ADDRESS = BYTE_SWAP_32(0x09570158);
+	uint32_t WAIT_CMD_WRITE_ADDRESS = BYTE_SWAP_32(0x096100c0);
+	uint32_t WAIT_CMD = BYTE_SWAP_32(0x000FFFFF);
+	int file_size;
+	uint32_t pbi_cmd, altcbar;
+	uint8_t pbi_data[MAX_PBI_DATA_LEN_BYTE];
+	uint32_t dst_offset;
+	FILE *fp_img = NULL;
+	int ret = FAILURE;
+
+	altcbar = pblimg.addr;
+	dst_offset = pblimg.addr;
+	fp_img = fopen(pblimg.sec_imgnm, "rb");
+	if (fp_img == NULL) {
+		printf("%s: Error in opening the file: %s\n", __func__,
+		      pblimg.sec_imgnm);
+		goto add_cpy_err;
+	}
+	file_size = get_filesize(pblimg.sec_imgnm);
+	altcbar = 0xfff00000 & altcbar;
+	altcbar = BYTE_SWAP_32(altcbar >> 16);
+	if (fwrite(&ALTCBAR_ADDRESS, sizeof(ALTCBAR_ADDRESS), NUM_MEM_BLOCK,
+		fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+		printf("%s: Error in writing address of ALTCFG CMD.\n",
+			 __func__);
+		goto add_cpy_err;
+	}
+	if (fwrite(&altcbar, sizeof(altcbar), NUM_MEM_BLOCK, fp_rcw_pbi_op)
+		!= NUM_MEM_BLOCK) {
+		printf("%s: Error in writing ALTCFG CMD.\n", __func__);
+		goto add_cpy_err;
+	}
+	if (fwrite(&WAIT_CMD_WRITE_ADDRESS, sizeof(WAIT_CMD_WRITE_ADDRESS),
+		NUM_MEM_BLOCK, fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+		printf("%s: Error in writing address of WAIT_CMD.\n",
+			__func__);
+		goto add_cpy_err;
+	}
+	if (fwrite(&WAIT_CMD, sizeof(WAIT_CMD), NUM_MEM_BLOCK, fp_rcw_pbi_op)
+		!= NUM_MEM_BLOCK) {
+		printf("%s: Error in writing WAIT_CMD.\n", __func__);
+		goto add_cpy_err;
+	}
+	do {
+		memset(pbi_data, 0, MAX_PBI_DATA_LEN_BYTE);
+
+		ret = fread(&pbi_data, MAX_PBI_DATA_LEN_BYTE,
+				NUM_MEM_BLOCK, fp_img);
+		if ((ret != NUM_MEM_BLOCK) && (!feof(fp_img))) {
+			printf("%s: Error writing ALTCFG Word: [%d].\n",
+				__func__, ret);
+			goto add_cpy_err;
+		}
+
+		dst_offset &= OFFSET_MASK;
+		pbi_cmd = WRITE_CMD_BASE | dst_offset;
+		pbi_cmd = BYTE_SWAP_32(pbi_cmd);
+		if (fwrite(&pbi_cmd, sizeof(pbi_cmd), NUM_MEM_BLOCK,
+			fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing ALTCFG Word write cmd.\n",
+				 __func__);
+			goto add_cpy_err;
+		}
+		if (fwrite(&pbi_data,  MAX_PBI_DATA_LEN_BYTE, NUM_MEM_BLOCK,
+			fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+			printf("%s: Error writing ALTCFG_Word.\n", __func__);
+			goto add_cpy_err;
+		}
+		dst_offset += MAX_PBI_DATA_LEN_BYTE;
+		file_size -= MAX_PBI_DATA_LEN_BYTE;
+	} while (!feof(fp_img));
+
+	ret = SUCCESS;
+
+add_cpy_err:
+	if (fp_img != NULL) {
+		fclose(fp_img);
+	}
+	return ret;
+}
+
+int main(int argc, char **argv)
+{
+	FILE *file = NULL;
+	char *ptr;
+	int opt;
+	int tmp;
+	uint16_t args = ARG_INIT_MASK;
+	FILE *fp_rcw_pbi_ip = NULL, *fp_rcw_pbi_op = NULL;
+	uint32_t word, word_1;
+	int ret = FAILURE;
+	bool bootptr_flag = false;
+	enum stop_command flag_stop_cmd = CRC_STOP_COMMAND;
+
+	/* Initializing the global structure to zero. */
+	memset(&pblimg, 0x0, sizeof(struct pbl_image));
+
+	while ((opt = getopt(argc, argv,
+			     ":b:f:r:i:e:d:c:o:h:s")) != -1) {
+		switch (opt) {
+		case 'd':
+			pblimg.addr = strtoull(optarg, &ptr, 16);
+			if (*ptr != 0) {
+				fprintf(stderr, "CMD Error: invalid load or destination address %s\n", optarg);
+				goto exit_main;
+			}
+			args |= BL2_BIN_CPY_DEST_ADDR_ARG_MASK;
+			break;
+		case 'r':
+			pblimg.rcw_nm = optarg;
+			file = fopen(pblimg.rcw_nm, "r");
+			if (file == NULL) {
+				printf("CMD Error: Opening the RCW File.\n");
+				goto exit_main;
+			} else {
+				args |= RCW_FILE_NAME_ARG_MASK;
+				fclose(file);
+			}
+			break;
+		case 'e':
+			bootptr_flag = true;
+			pblimg.ep = strtoull(optarg, &ptr, 16);
+			if (*ptr != 0) {
+				fprintf(stderr,
+				"CMD Error: Invalid entry point %s\n", optarg);
+				goto exit_main;
+			}
+			break;
+		case 'h':
+			print_usage();
+			break;
+		case 'i':
+			pblimg.sec_imgnm = optarg;
+			file = fopen(pblimg.sec_imgnm, "r");
+			if (file == NULL) {
+				printf("CMD Error: Opening Input file.\n");
+				goto exit_main;
+			} else {
+				args |= IN_FILE_NAME_ARG_MASK;
+				fclose(file);
+			}
+			break;
+		case 'c':
+			tmp = atoi(optarg);
+			switch (tmp) {
+			case SOC_LS1012:
+			case SOC_LS1023:
+			case SOC_LS1026:
+			case SOC_LS1043:
+			case SOC_LS1046:
+				pblimg.chassis = CHASSIS_2;
+				break;
+			case SOC_LS1088:
+			case SOC_LS2080:
+			case SOC_LS2088:
+				pblimg.chassis = CHASSIS_3;
+				break;
+			case SOC_LS1028:
+			case SOC_LX2160:
+				pblimg.chassis = CHASSIS_3_2;
+				break;
+			default:
+			printf("CMD Error: Invalid SoC Val = %d.\n", tmp);
+				goto exit_main;
+			}
+
+			args |= CHASSIS_ARG_MASK;
+			break;
+		case 'o':
+			pblimg.imagefile = optarg;
+			args |= OP_FILE_NAME_ARG_MASK;
+			break;
+		case 's':
+			sb_flag = true;
+			break;
+		case 'b':
+			if (strcmp(optarg, "qspi") == 0) {
+				pblimg.boot_src = QSPI_BOOT;
+			} else if (strcmp(optarg, "nor") == 0) {
+				pblimg.boot_src = IFC_NOR_BOOT;
+			} else if (strcmp(optarg, "nand") == 0) {
+				pblimg.boot_src = IFC_NAND_BOOT;
+			} else if (strcmp(optarg, "sd") == 0) {
+				pblimg.boot_src = SD_BOOT;
+			} else if (strcmp(optarg, "emmc") == 0) {
+				pblimg.boot_src = EMMC_BOOT;
+			} else if (strcmp(optarg, "flexspi_nor") == 0) {
+				pblimg.boot_src = FLXSPI_NOR_BOOT;
+			} else if (strcmp(optarg, "flexspi_nand") == 0) {
+				pblimg.boot_src = FLXSPI_NAND_BOOT;
+			} else if (strcmp(optarg, "flexspi_nand2k") == 0) {
+				pblimg.boot_src = FLXSPI_NAND4K_BOOT;
+			} else {
+				printf("CMD Error: Invalid boot source.\n");
+				goto exit_main;
+			}
+			args |= BOOT_SRC_ARG_MASK;
+			break;
+		case 'f':
+			pblimg.src_addr = strtoull(optarg, &ptr, 16);
+			if (*ptr != 0) {
+				fprintf(stderr,
+				"CMD Error: Invalid src offset %s\n", optarg);
+				goto exit_main;
+			}
+			args |= BL2_BIN_STRG_LOC_BOOT_SRC_ARG_MASK;
+			break;
+		default:
+			/* issue a warning and skip the unknown arg */
+			printf("Cmd Warning: Invalid Arg = %c.\n", opt);
+		}
+	}
+
+	if ((args & MAND_ARG_MASK) != MAND_ARG_MASK) {
+		print_usage();
+	}
+
+	fp_rcw_pbi_ip = fopen(pblimg.rcw_nm, "rb");
+	if (fp_rcw_pbi_ip == NULL) {
+		printf("%s: Error in opening the rcw file: %s\n",
+			__func__, pblimg.rcw_nm);
+		goto exit_main;
+	}
+
+	fp_rcw_pbi_op = fopen(pblimg.imagefile, "wb+");
+	if (fp_rcw_pbi_op == NULL) {
+		printf("%s: Error opening the input file: %s\n",
+			__func__, pblimg.imagefile);
+		goto exit_main;
+	}
+
+	printf("\nInput Boot Source: %s\n", boot_src_string[pblimg.boot_src]);
+	printf("Input RCW File: %s\n", pblimg.rcw_nm);
+	printf("Input BL2 Binary File: %s\n", pblimg.sec_imgnm);
+	printf("Input load address for BL2 Binary File: 0x%x\n", pblimg.addr);
+
+	printf("Chassis Type: %d\n", pblimg.chassis);
+	switch (pblimg.chassis) {
+	case CHASSIS_2:
+		if (fread(&word, sizeof(word), NUM_MEM_BLOCK, fp_rcw_pbi_ip)
+			!= NUM_MEM_BLOCK) {
+			printf("%s: Error in reading word from the rcw file.\n",
+				__func__);
+			goto exit_main;
+		}
+		while (BYTE_SWAP_32(word) != 0x08610040) {
+			if (BYTE_SWAP_32(word) == 0x09550000
+				|| BYTE_SWAP_32(word) == 0x000f400c) {
+				break;
+			}
+			if (fwrite(&word, sizeof(word), NUM_MEM_BLOCK,
+				fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+				printf("%s: [CH2] Error in Writing PBI Words\n",
+				__func__);
+				goto exit_main;
+			}
+			if (fread(&word, sizeof(word), NUM_MEM_BLOCK,
+				fp_rcw_pbi_ip) != NUM_MEM_BLOCK) {
+				printf("%s: [CH2] Error in Reading PBI Words\n",
+					__func__);
+				goto exit_main;
+			}
+		}
+
+		if (bootptr_flag == true) {
+			/* Add command to set boot_loc ptr */
+			ret = add_boot_ptr_cmd(fp_rcw_pbi_op);
+			if (ret != SUCCESS) {
+				goto exit_main;
+			}
+		}
+
+		/* Write acs write commands to output file */
+		ret = add_cpy_cmd(fp_rcw_pbi_op);
+		if (ret != SUCCESS) {
+			goto exit_main;
+		}
+
+		/* Add stop command after adding pbi commands
+		 * For Chasis 2.0 platforms it is always CRC &
+		 * Stop command
+		 */
+		flag_stop_cmd = CRC_STOP_COMMAND;
+		ret = add_pbi_stop_cmd(fp_rcw_pbi_op, flag_stop_cmd);
+		if (ret != SUCCESS) {
+			goto exit_main;
+		}
+
+	break;
+
+	case CHASSIS_3:
+	case CHASSIS_3_2:
+		if (fread(&word, sizeof(word), NUM_MEM_BLOCK, fp_rcw_pbi_ip)
+			!= NUM_MEM_BLOCK) {
+			printf("%s: Error reading PBI Cmd.\n", __func__);
+			goto exit_main;
+		}
+		while (word != 0x808f0000 && word != 0x80ff0000) {
+			pbl_size++;
+			/* 11th words in RCW has PBL length. Update it
+			 * with new length. 2 comamnds get added
+			 * Block copy + CCSR Write/CSF header write
+			 */
+			if (pbl_size == 11) {
+				word_1 = (word & PBI_LEN_MASK)
+					+ (PBI_LEN_ADD << 20);
+				word = word & ~PBI_LEN_MASK;
+				word = word | word_1;
+			}
+			/* Update the CRC command */
+			/* Check load command..
+			 * add a check if command is Stop with CRC
+			 * or stop without checksum
+			 */
+			if (pbl_size == 35) {
+				word = crypto_calculate_checksum(fp_rcw_pbi_op,
+						NUM_RCW_WORD - 1);
+				if (word == FAILURE) {
+					goto exit_main;
+				}
+			}
+			if (fwrite(&word, sizeof(word),	NUM_MEM_BLOCK,
+				fp_rcw_pbi_op) != NUM_MEM_BLOCK) {
+				printf("%s: [CH3] Error in Writing PBI Words\n",
+					__func__);
+				goto exit_main;
+			}
+			if (fread(&word, sizeof(word), NUM_MEM_BLOCK,
+				fp_rcw_pbi_ip) != NUM_MEM_BLOCK) {
+				printf("%s: [CH3] Error in Reading PBI Words\n",
+					 __func__);
+				goto exit_main;
+			}
+
+			if (word == CRC_STOP_CMD_ARM_CH3) {
+				flag_stop_cmd = CRC_STOP_COMMAND;
+			} else if (word == STOP_CMD_ARM_CH3) {
+				flag_stop_cmd = STOP_COMMAND;
+			}
+		}
+		if (bootptr_flag == true) {
+			/* Add command to set boot_loc ptr */
+			ret = add_boot_ptr_cmd(fp_rcw_pbi_op);
+			if (ret != SUCCESS) {
+				printf("%s: add_boot_ptr_cmd return failure.\n",
+					__func__);
+				goto exit_main;
+			}
+		}
+
+		/* Write acs write commands to output file */
+		ret = add_blk_cpy_cmd(fp_rcw_pbi_op, args);
+		if (ret != SUCCESS) {
+			printf("%s: Function add_blk_cpy_cmd return failure.\n",
+				 __func__);
+			goto exit_main;
+		}
+
+		/* Add stop command after adding pbi commands */
+		ret = add_pbi_stop_cmd(fp_rcw_pbi_op, flag_stop_cmd);
+		if (ret != SUCCESS) {
+			goto exit_main;
+		}
+
+	break;
+
+	default:
+		printf("%s: Unknown chassis type.\n",
+				__func__);
+	}
+
+	if (ret == SUCCESS) {
+		printf("Output file successfully created with name: %s\n\n",
+			   pblimg.imagefile);
+	}
+
+exit_main:
+	if (fp_rcw_pbi_op != NULL) {
+		fclose(fp_rcw_pbi_op);
+	}
+	if (fp_rcw_pbi_ip != NULL) {
+		fclose(fp_rcw_pbi_ip);
+	}
+
+	return ret;
+}
diff --git a/tools/nxp/create_pbl/create_pbl.mk b/tools/nxp/create_pbl/create_pbl.mk
new file mode 100644
index 0000000..b68882e
--- /dev/null
+++ b/tools/nxp/create_pbl/create_pbl.mk
@@ -0,0 +1,52 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+CREATE_PBL	?=	${CREATE_PBL_TOOL_PATH}/create_pbl${BIN_EXT}
+BYTE_SWAP	?=	${CREATE_PBL_PLAT_TOOL_PATH}/byte_swap${BIN_EXT}
+
+HOST_GCC	:= gcc
+
+#SWAP is required for Chassis 2 platforms - LS102, ls1043 and ls1046 for QSPI
+ifeq (${SOC},ls1046a)
+SOC_NUM :=	1046a
+SWAP	= 	1
+CH	=	2
+else ifeq (${SOC},ls1043a)
+SOC_NUM :=	1043a
+SWAP	= 	1
+CH	=	2
+else ifeq (${SOC},ls1012a)
+SOC_NUM :=	1012a
+SWAP	= 	1
+CH	=	2
+else ifeq (${SOC},ls1088a)
+SOC_NUM :=	1088a
+CH	=	3
+else ifeq (${SOC},ls2088a)
+SOC_NUM :=	2088a
+CH	=	3
+else ifeq (${SOC},lx2160a)
+SOC_NUM :=	2160a
+CH	=	3
+else ifeq (${SOC},ls1028a)
+SOC_NUM :=	1028a
+CH	=	3
+else
+$(error "Check SOC Not defined in create_pbl.mk.")
+endif
+
+ifeq (${CH},2)
+
+include ${CREATE_PBL_TOOL_PATH}/pbl_ch2.mk
+
+endif #CH2
+
+ifeq (${CH},3)
+
+include ${CREATE_PBL_TOOL_PATH}/pbl_ch3.mk
+
+endif #CH3
diff --git a/tools/nxp/create_pbl/pbl_ch2.mk b/tools/nxp/create_pbl/pbl_ch2.mk
new file mode 100644
index 0000000..e6f1d8b
--- /dev/null
+++ b/tools/nxp/create_pbl/pbl_ch2.mk
@@ -0,0 +1,60 @@
+#
+# Copyright 2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+
+CREATE_PBL	?=	${CREATE_PBL_TOOL_PATH}/create_pbl${BIN_EXT}
+BYTE_SWAP	?=	${CREATE_PBL_TOOL_PATH}/byte_swap${BIN_EXT}
+
+HOST_GCC	:= gcc
+
+.PHONY: pbl
+pbl:	${BUILD_PLAT}/bl2.bin
+ifeq ($(SECURE_BOOT),yes)
+pbl: ${BUILD_PLAT}/bl2.bin
+ifeq ($(RCW),"")
+	${Q}echo "Platform ${PLAT} requires rcw file. Please set RCW to point to the right RCW file for boot mode ${BOOT_MODE}"
+else
+	# Generate header for bl2.bin
+	$(Q)$(CST_DIR)/create_hdr_isbc --in ${BUILD_PLAT}/bl2.bin --out ${BUILD_PLAT}/hdr_bl2 ${BL2_INPUT_FILE}
+	# Compile create_pbl tool
+	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" --no-print-directory -C ${CREATE_PBL_TOOL_PATH};\
+	# Add bl2.bin to RCW
+	${CREATE_PBL} -r ${RCW} -i ${BUILD_PLAT}/bl2.bin -b ${BOOT_MODE} -c ${SOC_NUM} -d ${BL2_BASE} -e ${BL2_BASE}\
+			-o ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl ;\
+	# Add header to RCW
+	${CREATE_PBL} -r ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl -i ${BUILD_PLAT}/hdr_bl2 -b ${BOOT_MODE} -c ${SOC_NUM} \
+			-d ${BL2_HDR_LOC} -e ${BL2_HDR_LOC} -o ${BUILD_PLAT}/bl2_${BOOT_MODE}_sec.pbl -s;\
+	rm ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl
+# Swapping of RCW is required for QSPi Chassis 2 devices
+ifeq (${BOOT_MODE}, qspi)
+ifeq ($(SWAP),1)
+	${Q}echo "Byteswapping RCW for QSPI"
+	${BYTE_SWAP} ${BUILD_PLAT}/bl2_${BOOT_MODE}_sec.pbl;
+endif # SWAP
+endif # BOOT_MODE
+	cd ${CREATE_PBL_TOOL_PATH}; ${MAKE} clean ; cd -;
+endif
+else  # NON SECURE_BOOT
+ifeq ($(RCW),"")
+	${Q}echo "Platform ${PLAT} requires rcw file. Please set RCW to point to the right RCW file for boot mode ${BOOT_MODE}"
+else
+	# -a option appends the image for Chassis 3 devices in case of non secure boot
+	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" --no-print-directory -C ${CREATE_PBL_TOOL_PATH};
+	${CREATE_PBL} -r ${RCW} -i ${BUILD_PLAT}/bl2.bin -b ${BOOT_MODE} -c ${SOC_NUM} -d ${BL2_BASE} -e ${BL2_BASE} \
+	-o ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl ;
+# Swapping of RCW is required for QSPi Chassis 2 devices
+ifeq (${BOOT_MODE}, qspi)
+ifeq ($(SWAP),1)
+	${Q}echo "Byteswapping RCW for QSPI"
+	${BYTE_SWAP} ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl;
+endif # SWAP
+endif # BOOT_MODE
+	cd ${CREATE_PBL_TOOL_PATH}; ${MAKE} clean ; cd -;
+endif
+endif # SECURE_BOOT
+
+
+
diff --git a/tools/nxp/create_pbl/pbl_ch3.mk b/tools/nxp/create_pbl/pbl_ch3.mk
new file mode 100644
index 0000000..e9dbfb0
--- /dev/null
+++ b/tools/nxp/create_pbl/pbl_ch3.mk
@@ -0,0 +1,71 @@
+#
+# Copyright 2018-2020 NXP
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+#
+SHELL=/bin/bash
+
+CREATE_PBL	?=	${CREATE_PBL_TOOL_PATH}/create_pbl${BIN_EXT}
+BYTE_SWAP	?=	${CREATE_PBL_TOOL_PATH}/byte_swap${BIN_EXT}
+
+HOST_GCC	:= gcc
+
+BL2_SRC_OFFSET ?= 0x9000
+BL2_HDR_SRC_OFFSET ?= 0x5000
+bl2_hdr_loc=$(shell echo $$(( $(BL2_HDR_SRC_OFFSET) / 1024 )))
+bl2_loc=$(shell echo $$(( $(BL2_SRC_OFFSET) / 1024 )))
+
+.PHONY: pbl
+pbl:	${BUILD_PLAT}/bl2.bin
+ifeq ($(SECURE_BOOT),yes)
+pbl: ${BUILD_PLAT}/bl2.bin
+ifeq ($(RCW),"")
+	${Q}echo "Platform ${PLAT} requires rcw file. Please set RCW to point to the right RCW file for boot mode ${BOOT_MODE}"
+else
+	# Generate header for bl2.bin
+	$(Q)$(CST_DIR)/create_hdr_isbc --in ${BUILD_PLAT}/bl2.bin --out ${BUILD_PLAT}/hdr_bl2 ${BL2_INPUT_FILE}
+
+	# Compile create_pbl tool
+	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" --no-print-directory -C ${CREATE_PBL_TOOL_PATH};\
+
+	# Add Block Copy command for bl2.bin to RCW
+	${CREATE_PBL} -r ${RCW} -i ${BUILD_PLAT}/bl2.bin -b ${BOOT_MODE} -c ${SOC_NUM} -d ${BL2_BASE} -e ${BL2_BASE}\
+			-o ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl -f ${BL2_SRC_OFFSET};\
+
+	# Add Block Copy command and Load CSF header command to RCW
+	${CREATE_PBL} -r ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl -i ${BUILD_PLAT}/hdr_bl2 -b ${BOOT_MODE} -c ${SOC_NUM} \
+			-d ${BL2_HDR_LOC} -e ${BL2_HDR_LOC} -s -f ${BL2_HDR_SRC_OFFSET}	\
+			-o ${BUILD_PLAT}/rcw_sec.pbl
+
+	# Sign and add "Load Security Header command to PBI commands
+	$(Q)$(CST_DIR)/create_hdr_pbi --out ${BUILD_PLAT}/bl2_${BOOT_MODE}_sec.pbl --in ${BUILD_PLAT}/rcw_sec.pbl ${PBI_INPUT_FILE}
+
+	# Append the bl2_hdr to the RCW image
+	@echo "${bl2_hdr_loc}"
+	dd if=${BUILD_PLAT}/hdr_bl2 of=${BUILD_PLAT}/bl2_${BOOT_MODE}_sec.pbl bs=1K seek=${bl2_hdr_loc}
+
+	# Append the bl2.bin to the RCW image
+	@echo "${bl2_loc}"
+	dd if=${BUILD_PLAT}/bl2.bin of=${BUILD_PLAT}/bl2_${BOOT_MODE}_sec.pbl bs=1K seek=${bl2_loc}
+
+	rm ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl
+	cd ${CREATE_PBL_TOOL_PATH}; ${MAKE} clean ; cd -;
+endif
+else  #SECURE_BOOT
+ifeq ($(RCW),"")
+	${Q}echo "Platform ${PLAT} requires rcw file. Please set RCW to point to the right RCW file for boot mode ${BOOT_MODE}"
+else
+	${Q}${MAKE} CPPFLAGS="-DVERSION='\"${VERSION_STRING}\"'" --no-print-directory -C ${CREATE_PBL_TOOL_PATH};
+
+	# Add Block Copy command and populate boot loc ptrfor bl2.bin to RCW
+	${CREATE_PBL} -r ${RCW} -i ${BUILD_PLAT}/bl2.bin -b ${BOOT_MODE} -c ${SOC_NUM} -d ${BL2_BASE} -e ${BL2_BASE} \
+	-o ${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl -f ${BL2_SRC_OFFSET};
+
+	# Append the bl2.bin to the RCW image
+	@echo "bl2_loc is ${bl2_offset}"
+	dd if=${BUILD_PLAT}/bl2.bin of=${BUILD_PLAT}/bl2_${BOOT_MODE}.pbl bs=1K seek=${bl2_loc}
+
+	cd ${CREATE_PBL_TOOL_PATH}; ${MAKE} clean ; cd -;
+endif
+endif # SECURE_BOOT
diff --git a/tools/nxp/plat_fiptool/plat_def_uuid_config.c b/tools/nxp/plat_fiptool/plat_def_uuid_config.c
new file mode 100644
index 0000000..fdb4b93
--- /dev/null
+++ b/tools/nxp/plat_fiptool/plat_def_uuid_config.c
@@ -0,0 +1,90 @@
+/*
+ * Copyright 2021 NXP
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stddef.h>
+
+#include <firmware_image_package.h>
+
+#include "tbbr_config.h"
+
+toc_entry_t plat_def_toc_entries[] = {
+	/* DDR PHY firmwares */
+	{
+		.name = "DDR UDIMM PHY IMEM 1d FW",
+		.uuid = UUID_DDR_IMEM_UDIMM_1D,
+		.cmdline_name = "ddr-immem-udimm-1d"
+	},
+	{
+		.name = "DDR UDIMM PHY IMEM 2d FW",
+		.uuid = UUID_DDR_IMEM_UDIMM_2D,
+		.cmdline_name = "ddr-immem-udimm-2d"
+	},
+	{
+		.name = "DDR UDIMM PHY DMEM 1d FW",
+		.uuid = UUID_DDR_DMEM_UDIMM_1D,
+		.cmdline_name = "ddr-dmmem-udimm-1d"
+	},
+	{
+		.name = "DDR UDIMM PHY DMEM 2d FW",
+		.uuid = UUID_DDR_DMEM_UDIMM_2D,
+		.cmdline_name = "ddr-dmmem-udimm-2d"
+	},
+	{
+		.name = "DDR RDIMM PHY IMEM 1d FW",
+		.uuid = UUID_DDR_IMEM_RDIMM_1D,
+		.cmdline_name = "ddr-immem-rdimm-1d"
+	},
+	{
+		.name = "DDR RDIMM PHY IMEM 2d FW",
+		.uuid = UUID_DDR_IMEM_RDIMM_2D,
+		.cmdline_name = "ddr-immem-rdimm-2d"
+	},
+	{
+		.name = "DDR RDIMM PHY DMEM 1d FW",
+		.uuid = UUID_DDR_DMEM_RDIMM_1D,
+		.cmdline_name = "ddr-dmmem-rdimm-1d"
+	},
+	{
+		.name = "DDR RDIMM PHY DMEM 2d FW",
+		.uuid = UUID_DDR_DMEM_RDIMM_2D,
+		.cmdline_name = "ddr-dmmem-rdimm-2d"
+	},
+	{
+		.name = "FUSE PROV FW",
+		.uuid = UUID_FUSE_PROV,
+		.cmdline_name = "fuse-prov"
+	},
+	{
+		.name = "FUSE UPGRADE FW",
+		.uuid = UUID_FUSE_UP,
+		.cmdline_name = "fuse-upgrade"
+	},
+
+	/* Key Certificates */
+	{
+		.name = "DDR Firmware key certificate",
+		.uuid = UUID_DDR_FW_KEY_CERT,
+		.cmdline_name = "ddr-fw-key-cert"
+	},
+
+	/* Content certificates */
+	{
+		.name = "DDR UDIMM Firmware content certificate",
+		.uuid = UUID_DDR_UDIMM_FW_CONTENT_CERT,
+		.cmdline_name = "ddr-udimm-fw-cert"
+	},
+	{
+		.name = "DDR RDIMM Firmware content certificate",
+		.uuid = UUID_DDR_RDIMM_FW_CONTENT_CERT,
+		.cmdline_name = "ddr-rdimm-fw-cert"
+	},
+
+	{
+		.name = NULL,
+		.uuid = { {0} },
+		.cmdline_name = NULL,
+	}
+};
diff --git a/tools/nxp/plat_fiptool/plat_fiptool.mk b/tools/nxp/plat_fiptool/plat_fiptool.mk
new file mode 100644
index 0000000..ca2962a
--- /dev/null
+++ b/tools/nxp/plat_fiptool/plat_fiptool.mk
@@ -0,0 +1,33 @@
+#
+# Copyright (c) 2021, NXP. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# Name of the platform defined source file name,
+# which contains platform defined UUID entries populated
+# in the plat_def_toc_entries[].
+PLAT_DEF_UUID_CONFIG_FILE_NAME	:= plat_def_uuid_config
+
+PLAT_DEF_UUID_CONFIG_FILE_PATH := ../nxp/plat_fiptool
+
+PLAT_DEF_OID := yes
+PLAT_DEF_UUID := yes
+PLAT_DEF_UUID_OID_CONFIG_PATH := ../../plat/nxp/common/fip_handler/common
+
+
+INCLUDE_PATHS += -I${PLAT_DEF_UUID_OID_CONFIG_PATH} \
+		 -I./
+# Clean the stale object file.
+$(shell rm ${PLAT_DEF_UUID_CONFIG_FILE_PATH}/${PLAT_DEF_UUID_CONFIG_FILE_NAME}.o)
+
+ifeq (${PLAT_DEF_OID},yes)
+HOSTCCFLAGS += -DPLAT_DEF_OID
+endif
+
+ifeq (${PLAT_DEF_UUID},yes)
+HOSTCCFLAGS += -DPLAT_DEF_FIP_UUID
+PLAT_OBJECTS += ${PLAT_DEF_UUID_CONFIG_FILE_PATH}/${PLAT_DEF_UUID_CONFIG_FILE_NAME}.o
+endif
+
+OBJECTS += ${PLAT_OBJECTS}
diff --git a/tools/renesas/rcar_layout_create/sa6.c b/tools/renesas/rcar_layout_create/sa6.c
index fa828b9..8fafdad 100644
--- a/tools/renesas/rcar_layout_create/sa6.c
+++ b/tools/renesas/rcar_layout_create/sa6.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2017, Renesas Electronics Corporation. All rights reserved.
+ * Copyright (c) 2015-2021, Renesas Electronics Corporation. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -96,7 +96,7 @@
 #define RCAR_BL32DST_ADDRESS		(0x44100000U)
 #define RCAR_BL32DST_ADDRESSH		(0x00000000U)
 /* Destination size for BL32 */
-#define RCAR_BL32DST_SIZE		(0x00040000U)
+#define RCAR_BL32DST_SIZE		(0x00080000U)
 /* Destination address for BL33 */
 #define RCAR_BL33DST_ADDRESS		(0x50000000U)
 #define RCAR_BL33DST_ADDRESSH		(0x00000000U)
diff --git a/tools/renesas/rzg_layout_create/makefile b/tools/renesas/rzg_layout_create/makefile
new file mode 100644
index 0000000..2d438b9
--- /dev/null
+++ b/tools/renesas/rzg_layout_create/makefile
@@ -0,0 +1,118 @@
+#
+# Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+###################################################
+# makefile
+###################################################
+
+#output file name
+FILE_NAME_SA0 = bootparam_sa0
+FILE_NAME_SA6 = cert_header_sa6
+
+OUTPUT_FILE_SA0 = $(FILE_NAME_SA0).elf
+OUTPUT_FILE_SA6 = $(FILE_NAME_SA6).elf
+
+#object file name
+OBJ_FILE_SA0 = sa0.o
+OBJ_FILE_SA6 = sa6.o
+
+#linker script name
+MEMORY_DEF_SA0 = sa0.ld.S
+MEMORY_DEF_SA6 = sa6.ld.S
+
+###################################################
+# Convenience function for adding build definitions
+# $(eval $(call add_define,FOO)) will have:
+# -DFOO if $(FOO) is empty; -DFOO=$(FOO) otherwise
+define add_define
+DEFINES += -D$(1)$(if $(value $(1)),=$(value $(1)),)
+endef
+
+# Process RCAR_SA0_SIZE flag
+ifndef RCAR_SA0_SIZE
+RCAR_SA0_SIZE := 1
+else
+ifeq (${RCAR_SA0_SIZE},0)
+RCAR_SA0_SIZE := 0
+else
+RCAR_SA0_SIZE := 1
+endif
+endif
+$(eval $(call add_define,RCAR_SA0_SIZE))
+
+# Process RCAR_SA6_TYPE flag
+ifndef RCAR_SA6_TYPE
+RCAR_SA6_TYPE := 0
+else
+ifeq (${RCAR_SA6_TYPE},0)
+RCAR_SA6_TYPE := 0
+else
+RCAR_SA6_TYPE := 1
+endif
+endif
+$(eval $(call add_define,RCAR_SA6_TYPE))
+
+RCAR_VMA_ADJUST_ADDR := 0xE6320000
+$(eval $(call add_define,RCAR_VMA_ADJUST_ADDR))
+
+
+###################################################
+
+#c compiler
+CC = $(CROSS_COMPILE)gcc
+CFLAGS += ${DEFINES}
+CFLAGS += -nostdinc \
+	  -I../../../include/lib/libc \
+	  -I../../../include/lib/libc/aarch64
+
+#Linker
+LD = $(CROSS_COMPILE)ld
+
+#objcopy
+objcopy = $(CROSS_COMPILE)objcopy
+
+#clean
+CL = rm -f
+
+###################################################
+.SUFFIXES : .s .c .o
+
+###################################################
+# command
+
+.PHONY: all
+all: $(OUTPUT_FILE_SA0) $(OUTPUT_FILE_SA6)
+###################################################
+# Linker
+###################################################
+$(OUTPUT_FILE_SA0) : $(MEMORY_DEF_SA0) $(OBJ_FILE_SA0)
+	$(LD) $(OBJ_FILE_SA0)		 	\
+	-T $(MEMORY_DEF_SA0)			\
+	-o $(OUTPUT_FILE_SA0)			\
+	-Map $(FILE_NAME_SA0).map 		\
+
+	$(objcopy) -O srec --adjust-vma=$(RCAR_VMA_ADJUST_ADDR) --srec-forceS3  $(OUTPUT_FILE_SA0) $(FILE_NAME_SA0).srec
+	$(objcopy) -O binary --adjust-vma=$(RCAR_VMA_ADJUST_ADDR) --srec-forceS3  $(OUTPUT_FILE_SA0) $(FILE_NAME_SA0).bin
+
+$(OUTPUT_FILE_SA6) : $(MEMORY_DEF_SA6) $(OBJ_FILE_SA6)
+	$(LD) $(OBJ_FILE_SA6)		 	\
+	-T $(MEMORY_DEF_SA6)			\
+	-o $(OUTPUT_FILE_SA6)			\
+	-Map $(FILE_NAME_SA6).map 		\
+
+	$(objcopy) -O srec --adjust-vma=$(RCAR_VMA_ADJUST_ADDR) --srec-forceS3  $(OUTPUT_FILE_SA6) $(FILE_NAME_SA6).srec
+	$(objcopy) -O binary --adjust-vma=$(RCAR_VMA_ADJUST_ADDR) --srec-forceS3  $(OUTPUT_FILE_SA6) $(FILE_NAME_SA6).bin
+
+###################################################
+# Compile
+###################################################
+
+%.o:../%.c
+	$(CC) -c -I $< -o $@
+
+.PHONY: clean
+clean:
+	$(CL)  *.bin *.map *.srec *.elf *.o
diff --git a/tools/renesas/rzg_layout_create/sa0.c b/tools/renesas/rzg_layout_create/sa0.c
new file mode 100644
index 0000000..763d3a5
--- /dev/null
+++ b/tools/renesas/rzg_layout_create/sa0.c
@@ -0,0 +1,30 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#define RCAR_SA0_SIZE_SMALL	(0)	/* for RZ/G2E */
+#define RCAR_SA0_SIZE_NORMAL	(1)	/* for RZ/G2[HMN] */
+
+#define BL2_ADDRESS	(0xE6304000)	/* BL2 start address */
+
+#if (RCAR_SA0_SIZE == RCAR_SA0_SIZE_SMALL)
+#define BL2_SIZE	(80*1024/4)	/* BL2 size is 80KB(0x00005000) */
+#else  /* (RCAR_SA0_SIZE == RCAR_SA0_SIZE_SMALL) */
+#define BL2_SIZE	(170*1024/4)	/* BL2 size is 170KB(0x0000AA00) */
+#endif /* (RCAR_SA0_SIZE == RCAR_SA0_SIZE_SMALL) */
+
+/* SA0 */
+/* 0x00000000 */
+const unsigned int __attribute__ ((section(".sa0_bootrom"))) bootrom_paramA = 0x00000100;
+/* 0x00000080 (Map Type 3 for eMMC Boot)*/
+/* 0x000001D4 */
+const unsigned int __attribute__ ((section(".sa0_bl2dst_addr3"))) bl2dst_addr3 = BL2_ADDRESS;
+/* 0x000002E4 */
+const unsigned int __attribute__ ((section(".sa0_bl2dst_size3"))) bl2dst_size3 = BL2_SIZE;
+/* 0x00000C00 (Map Type 1 for HyperFlash/QSPI Flash Boot)*/
+/* 0x00000D54 */
+const unsigned int __attribute__ ((section(".sa0_bl2dst_addr1"))) bl2dst_addr1 = BL2_ADDRESS;
+/* 0x00000E64 */
+const unsigned int __attribute__ ((section(".sa0_bl2dst_size1"))) bl2dst_size1 = BL2_SIZE;
diff --git a/tools/renesas/rzg_layout_create/sa0.ld.S b/tools/renesas/rzg_layout_create/sa0.ld.S
new file mode 100644
index 0000000..23e2b23
--- /dev/null
+++ b/tools/renesas/rzg_layout_create/sa0.ld.S
@@ -0,0 +1,28 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+SECTIONS
+{
+	. = 0x00000000;
+	.rodata : {
+		KEEP(*(.sa0_bootrom))
+		/* Map Type 3 for eMMC Boot */
+                /* A-side IPL content cert "Start Address" */
+		. = 0x000001D4;		/* H'00000080 + H'00000154 */
+		KEEP(*(.sa0_bl2dst_addr3))
+                /* A-side IPL content cert "Size" */
+		. = 0x000002E4;		/* H'00000080 + H'00000264 */
+		KEEP(*(.sa0_bl2dst_size3))
+		/* Map Type 1 for HyperFlash/QSPI Flash Boot */
+		/* A-side IPL content cert "Start Address" */
+		. = 0x00000D54;		/* H'00000C00 + H'00000154 */
+		KEEP(*(.sa0_bl2dst_addr1))
+		/* A-side IPL content cert "Size" */
+		. = 0x00000E64;		/* H'00000C00 + H'00000264 */
+		KEEP(*(.sa0_bl2dst_size1))
+	}
+
+}
diff --git a/tools/renesas/rzg_layout_create/sa6.c b/tools/renesas/rzg_layout_create/sa6.c
new file mode 100644
index 0000000..76e3dc5
--- /dev/null
+++ b/tools/renesas/rzg_layout_create/sa6.c
@@ -0,0 +1,236 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+#include <stdint.h>
+
+#define RCAR_SA6_TYPE_QSPIFLASH		(0)
+#define RCAR_SA6_TYPE_EMMC		(1)
+
+#if (RCAR_SA6_TYPE == RCAR_SA6_TYPE_QSPIFLASH)
+
+/* Number of content cert for Non-secure Target Program(BL33x) */
+#define RCAR_IMAGE_NUM			(0x00000001U)
+/* Source address on flash for BL31 */
+#define RCAR_BL31SRC_ADDRESS		(0x001C0000U)
+/* Reserved */
+#define RCAR_BL31_PARTITION		(0x00000000U)
+/* Source address on flash for BL32 */
+#define RCAR_BL32SRC_ADDRESS		(0x00200000U)
+/* Reserved */
+#define RCAR_BL32_PARTITION		(0x00000000U)
+/* Source address on flash for BL33 */
+#define RCAR_BL33SRC_ADDRESS		(0x00300000U)
+/* Reserved */
+#define RCAR_BL33_PARTITION		(0x00000000U)
+#define RCAR_BL332SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL332_PARTITION		(0x00000000U)
+#define RCAR_BL333SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL333_PARTITION		(0x00000000U)
+#define RCAR_BL334SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL334_PARTITION		(0x00000000U)
+#define RCAR_BL335SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL335_PARTITION		(0x00000000U)
+#define RCAR_BL336SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL336_PARTITION		(0x00000000U)
+#define RCAR_BL337SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL337_PARTITION		(0x00000000U)
+#define RCAR_BL338SRC_ADDRESS		(0x00000000U)
+/* Reserved */
+#define RCAR_BL338_PARTITION		(0x00000000U)
+
+#else /* RCAR_SA6_TYPE == RCAR_SA6_TYPE_EMMC */
+
+/* Number of content cert for Non-secure Target Program(BL33x) */
+#define RCAR_IMAGE_NUM			(0x00000001U)
+/* Source address on eMMC for BL31 */
+#define RCAR_BL31SRC_ADDRESS		(0x00040000U)
+/* Source partition on eMMC for BL31 */
+#define RCAR_BL31_PARTITION		(0x00000001U)
+/* Source address on eMMC for BL32 */
+#define RCAR_BL32SRC_ADDRESS		(0x00200000U)
+/* Source partition on eMMC for BL32 */
+#define RCAR_BL32_PARTITION		(0x00000001U)
+/* Source address on eMMC for BL33 */
+#define RCAR_BL33SRC_ADDRESS		(0x00000000U)
+/* Source partition on eMMC for BL33 */
+#define RCAR_BL33_PARTITION		(0x00000002U)
+/* Reserved */
+#define RCAR_BL332SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL332_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL333SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL333_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL334SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL334_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL335SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL335_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL336SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL336_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL337SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL337_PARTITION		(0x00000000U)
+/* Reserved */
+#define RCAR_BL338SRC_ADDRESS		(0x00000000U)
+#define RCAR_BL338_PARTITION		(0x00000000U)
+
+#endif /* RCAR_SA6_TYPE == RCAR_SA6_TYPE_QSPIFLASH */
+
+/* Destination address for BL31 */
+#define RCAR_BL31DST_ADDRESS		(0x44000000U)
+#define RCAR_BL31DST_ADDRESSH		(0x00000000U)
+/* Destination size for BL31 */
+#define RCAR_BL31DST_SIZE		(0x00004000U)
+/* Destination address for BL32 */
+#define RCAR_BL32DST_ADDRESS		(0x44100000U)
+#define RCAR_BL32DST_ADDRESSH		(0x00000000U)
+/* Destination size for BL32 */
+#define RCAR_BL32DST_SIZE		(0x00040000U)
+/* Destination address for BL33 */
+#define RCAR_BL33DST_ADDRESS		(0x50000000U)
+#define RCAR_BL33DST_ADDRESSH		(0x00000000U)
+/* Destination size for BL33 */
+#define RCAR_BL33DST_SIZE		(0x00040000U)
+/* Reserved */
+#define RCAR_BL332DST_ADDRESS		(0x00000000U)
+#define RCAR_BL332DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL332DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL333DST_ADDRESS		(0x00000000U)
+#define RCAR_BL333DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL333DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL334DST_ADDRESS		(0x00000000U)
+#define RCAR_BL334DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL334DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL335DST_ADDRESS		(0x00000000U)
+#define RCAR_BL335DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL335DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL336DST_ADDRESS		(0x00000000U)
+#define RCAR_BL336DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL336DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL337DST_ADDRESS		(0x00000000U)
+#define RCAR_BL337DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL337DST_SIZE		(0x00000000U)
+/* Reserved */
+#define RCAR_BL338DST_ADDRESS		(0x00000000U)
+#define RCAR_BL338DST_ADDRESSH		(0x00000000U)
+#define RCAR_BL338DST_SIZE		(0x00000000U)
+
+/* SA6 */
+const uint64_t __attribute__ ((section(".sa6_image_num")))
+				image_num	= RCAR_IMAGE_NUM;
+const uint64_t __attribute__ ((section(".sa6_bl31src_addr")))
+				bl31src_addr	= RCAR_BL31SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl31partition")))
+				bl31partition	= RCAR_BL31_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl32src_addr")))
+				bl32src_addr	= RCAR_BL32SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl32partition")))
+				bl32partition	= RCAR_BL32_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl33src_addr")))
+				bl33src_addr	= RCAR_BL33SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl33partition")))
+				bl33partition	= RCAR_BL33_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl332src_addr")))
+				bl332src_addr	= RCAR_BL332SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl332partition")))
+				bl332partition	= RCAR_BL332_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl333src_addr")))
+				bl333src_addr	= RCAR_BL333SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl333partition")))
+				bl333partition	= RCAR_BL333_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl334src_addr")))
+				bl334src_addr	= RCAR_BL334SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl334partition")))
+				bl334partition	= RCAR_BL334_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl335src_addr")))
+				bl335src_addr	= RCAR_BL335SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl335partition")))
+				bl335partition	= RCAR_BL335_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl336src_addr")))
+				bl336src_addr	= RCAR_BL336SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl336partition")))
+				bl336partition	= RCAR_BL336_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl337src_addr")))
+				bl337src_addr	= RCAR_BL337SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl337partition")))
+				bl337partition	= RCAR_BL337_PARTITION;
+const uint64_t __attribute__ ((section(".sa6_bl338src_addr")))
+				bl338src_addr	= RCAR_BL338SRC_ADDRESS;
+const uint64_t __attribute__ ((section(".sa6_bl338partition")))
+				bl338partition	= RCAR_BL338_PARTITION;
+const uint32_t __attribute__ ((section(".sa6_bl31dst_addr")))
+				bl31dst_addr	= RCAR_BL31DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl31dst_addrh")))
+				bl31dst_addrh	= RCAR_BL31DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl31dst_size")))
+				bl31dst_size	= RCAR_BL31DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl32dst_addr")))
+				bl32dst_addr	= RCAR_BL32DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl32dst_addrh")))
+				bl32dst_addrh	= RCAR_BL32DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl32dst_size")))
+				bl32dst_size	= RCAR_BL32DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl33dst_addr")))
+				bl33dst_addr	= RCAR_BL33DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl33dst_addrh")))
+				bl33dst_addrh	= RCAR_BL33DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl33dst_size")))
+				bl33dst_size	= RCAR_BL33DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl332dst_addr")))
+				bl332dst_addr	= RCAR_BL332DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl332dst_addrh")))
+				bl332dst_addrh	= RCAR_BL332DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl332dst_size")))
+				bl332dst_size	= RCAR_BL332DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl333dst_addr")))
+				bl333dst_addr	= RCAR_BL333DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl333dst_addrh")))
+				bl333dst_addrh	= RCAR_BL333DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl333dst_size")))
+				bl333dst_size	= RCAR_BL333DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl334dst_addr")))
+				bl334dst_addr	= RCAR_BL334DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl334dst_addrh")))
+				bl334dst_addrh	= RCAR_BL334DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl334dst_size")))
+				bl334dst_size	= RCAR_BL334DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl335dst_addr")))
+				bl335dst_addr	= RCAR_BL335DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl335dst_addrh")))
+				bl335dst_addrh	= RCAR_BL335DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl335dst_size")))
+				bl335dst_size	= RCAR_BL335DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl336dst_addr")))
+				bl336dst_addr	= RCAR_BL336DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl336dst_addrh")))
+				bl336dst_addrh	= RCAR_BL336DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl336dst_size")))
+				bl336dst_size	= RCAR_BL336DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl337dst_addr")))
+				bl337dst_addr	= RCAR_BL337DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl337dst_addrh")))
+				bl337dst_addrh	= RCAR_BL337DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl337dst_size")))
+				bl337dst_size	= RCAR_BL337DST_SIZE;
+const uint32_t __attribute__ ((section(".sa6_bl338dst_addr")))
+				bl338dst_addr	= RCAR_BL338DST_ADDRESS;
+const uint32_t __attribute__ ((section(".sa6_bl338dst_addrh")))
+				bl338dst_addrh	= RCAR_BL338DST_ADDRESSH;
+const uint32_t __attribute__ ((section(".sa6_bl338dst_size")))
+				bl338dst_size	= RCAR_BL338DST_SIZE;
diff --git a/tools/renesas/rzg_layout_create/sa6.ld.S b/tools/renesas/rzg_layout_create/sa6.ld.S
new file mode 100644
index 0000000..efe40b0
--- /dev/null
+++ b/tools/renesas/rzg_layout_create/sa6.ld.S
@@ -0,0 +1,114 @@
+/*
+ * Copyright (c) 2020, Renesas Electronics Corporation. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ */
+
+SECTIONS
+{
+	. = 0x00000000;
+	.rodata : {
+		KEEP(*(.sa6_image_num))
+		. = 0x00000008;
+		KEEP(*(.sa6_bl31src_addr))
+		. = 0x00000010;
+		KEEP(*(.sa6_bl31partition))
+		. = 0x00000018;
+		KEEP(*(.sa6_bl32src_addr))
+		. = 0x00000020;
+		KEEP(*(.sa6_bl32partition))
+		. = 0x00000028;
+		KEEP(*(.sa6_bl33src_addr))
+		. = 0x00000030;
+		KEEP(*(.sa6_bl33partition))
+		. = 0x00000038;
+		KEEP(*(.sa6_bl332src_addr))
+		. = 0x00000040;
+		KEEP(*(.sa6_bl332partition))
+		. = 0x00000048;
+		KEEP(*(.sa6_bl333src_addr))
+		. = 0x00000050;
+		KEEP(*(.sa6_bl333partition))
+		. = 0x00000058;
+		KEEP(*(.sa6_bl334src_addr))
+		. = 0x00000060;
+		KEEP(*(.sa6_bl334partition))
+		. = 0x00000068;
+		KEEP(*(.sa6_bl335src_addr))
+		. = 0x00000070;
+		KEEP(*(.sa6_bl335partition))
+		. = 0x00000078;
+		KEEP(*(.sa6_bl336src_addr))
+		. = 0x00000080;
+		KEEP(*(.sa6_bl336partition))
+		. = 0x00000088;
+		KEEP(*(.sa6_bl337src_addr))
+		. = 0x00000090;
+		KEEP(*(.sa6_bl337partition))
+		. = 0x00000098;
+		KEEP(*(.sa6_bl338src_addr))
+		. = 0x000000A0;
+		KEEP(*(.sa6_bl338partition))
+		. = 0x00000554;
+		KEEP(*(.sa6_bl31dst_addr))
+		. = 0x00000558;
+		KEEP(*(.sa6_bl31dst_addrh))
+		. = 0x00000664;
+		KEEP(*(.sa6_bl31dst_size))
+		. = 0x00000D54;
+		KEEP(*(.sa6_bl32dst_addr))
+		. = 0x00000D58;
+		KEEP(*(.sa6_bl32dst_addrh))
+		. = 0x00000E64;
+		KEEP(*(.sa6_bl32dst_size))
+		. = 0x00001554;
+		KEEP(*(.sa6_bl33dst_addr))
+		. = 0x00001558;
+		KEEP(*(.sa6_bl33dst_addrh))
+		. = 0x00001664;
+		KEEP(*(.sa6_bl33dst_size))
+		. = 0x00001D54;
+		KEEP(*(.sa6_bl332dst_addr))
+		. = 0x00001D58;
+		KEEP(*(.sa6_bl332dst_addrh))
+		. = 0x00001E64;
+		KEEP(*(.sa6_bl332dst_size))
+		. = 0x00002554;
+		KEEP(*(.sa6_bl333dst_addr))
+		. = 0x00002558;
+		KEEP(*(.sa6_bl333dst_addrh))
+		. = 0x00002664;
+		KEEP(*(.sa6_bl333dst_size))
+		. = 0x00002D54;
+		KEEP(*(.sa6_bl334dst_addr))
+		. = 0x00002D58;
+		KEEP(*(.sa6_bl334dst_addrh))
+		. = 0x00002E64;
+		KEEP(*(.sa6_bl334dst_size))
+		. = 0x00003554;
+		KEEP(*(.sa6_bl335dst_addr))
+		. = 0x00003558;
+		KEEP(*(.sa6_bl335dst_addrh))
+		. = 0x00003664;
+		KEEP(*(.sa6_bl335dst_size))
+		. = 0x00003D54;
+		KEEP(*(.sa6_bl336dst_addr))
+		. = 0x00003D58;
+		KEEP(*(.sa6_bl336dst_addrh))
+		. = 0x00003E64;
+		KEEP(*(.sa6_bl336dst_size))
+		. = 0x00004554;
+		KEEP(*(.sa6_bl337dst_addr))
+		. = 0x00004558;
+		KEEP(*(.sa6_bl337dst_addrh))
+		. = 0x00004664;
+		KEEP(*(.sa6_bl337dst_size))
+		. = 0x00004D54;
+		KEEP(*(.sa6_bl338dst_addr))
+		. = 0x00004D58;
+		KEEP(*(.sa6_bl338dst_addrh))
+		. = 0x00004E64;
+		KEEP(*(.sa6_bl338dst_size))
+	}
+
+}
diff --git a/tools/sptool/sp_mk_generator.py b/tools/sptool/sp_mk_generator.py
index a37e702..f983ff3 100755
--- a/tools/sptool/sp_mk_generator.py
+++ b/tools/sptool/sp_mk_generator.py
@@ -1,5 +1,5 @@
 #!/usr/bin/python3
-# Copyright (c) 2020, Arm Limited. All rights reserved.
+# Copyright (c) 2020-2021, Arm Limited. All rights reserved.
 #
 # SPDX-License-Identifier: BSD-3-Clause
 
@@ -110,24 +110,36 @@
         Extract uuid from partition manifest
         """
         pm_file = open(dts)
-        uuid_key = "uuid"
-
         for line in pm_file:
-            if uuid_key in line:
-                uuid_hex = re.findall(r'\<(.+?)\>', line)[0];
+            if "uuid" in line:
+                # re.findall returns a list of string tuples.
+                # uuid_hex is the first item in this list representing the four
+                # uuid hex integers from the manifest uuid field. The heading
+                # '0x' of the hexadecimal representation is stripped out.
+                # e.g. uuid = <0x1e67b5b4 0xe14f904a 0x13fb1fb8 0xcbdae1da>;
+                # uuid_hex = ('1e67b5b4', 'e14f904a', '13fb1fb8', 'cbdae1da')
+                uuid_hex = re.findall(r'0x([0-9a-f]+) 0x([0-9a-f]+) 0x([0-9a-f]+) 0x([0-9a-f]+)', line)[0];
 
-        # PM has uuid in format 0xABC... 0x... 0x... 0x...
-        # Get rid of '0x' and spaces and convert to string of hex digits
-        uuid_hex = uuid_hex.replace('0x','').replace(' ','')
-        # make UUID from a string of hex digits
-        uuid_std = uuid.UUID(uuid_hex)
-        # convert UUID to a string of hex digits in standard form
-        uuid_std = str(uuid_std)
+        # uuid_hex is a list of four hex string values
+        if len(uuid_hex) != 4:
+            print("ERROR: malformed UUID")
+            exit(-1)
+
+        # The uuid field in SP manifest is the little endian representation
+        # mapped to arguments as described in SMCCC section 5.3.
+        # Convert each unsigned integer value to a big endian representation
+        # required by fiptool.
+        y=list(map(bytearray.fromhex, uuid_hex))
+        z=(int.from_bytes(y[0], byteorder='little', signed=False),
+        int.from_bytes(y[1], byteorder='little', signed=False),
+        int.from_bytes(y[2], byteorder='little', signed=False),
+        int.from_bytes(y[3], byteorder='little', signed=False))
+        uuid_std = uuid.UUID(f'{z[0]:04x}{z[1]:04x}{z[2]:04x}{z[3]:04x}')
 
         """
         Append FIP_ARGS
         """
-        out_file.write("FIP_ARGS += --blob uuid=" + uuid_std + ",file=" + dst + "\n")
+        out_file.write("FIP_ARGS += --blob uuid=" + str(uuid_std) + ",file=" + dst + "\n")
 
         """
         Append CRT_ARGS
diff --git a/tools/stm32image/stm32image.c b/tools/stm32image/stm32image.c
index 41024e2..fb1dee0 100644
--- a/tools/stm32image/stm32image.c
+++ b/tools/stm32image/stm32image.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2018, STMicroelectronics - All Rights Reserved
+ * Copyright (c) 2017-2021, STMicroelectronics - All Rights Reserved
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -45,8 +45,6 @@
 	uint8_t binary_type;
 };
 
-static struct stm32_header stm32image_header;
-
 static void stm32image_default_header(struct stm32_header *ptr)
 {
 	if (!ptr) {
@@ -54,10 +52,9 @@
 	}
 
 	ptr->magic_number = HEADER_MAGIC;
-	ptr->header_version[VER_MAJOR] = HEADER_VERSION_V1;
 	ptr->option_flags = HEADER_DEFAULT_OPTION;
-	ptr->ecdsa_algorithm = 1;
-	ptr->version_number = 0;
+	ptr->ecdsa_algorithm = __cpu_to_le32(1);
+	ptr->version_number = __cpu_to_le32(0);
 	ptr->binary_type = TF_BINARY_TYPE;
 }
 
@@ -105,27 +102,33 @@
 }
 
 static void stm32image_set_header(void *ptr, struct stat *sbuf, int ifd,
-				  uint32_t loadaddr, uint32_t ep, uint32_t ver)
+				  uint32_t loadaddr, uint32_t ep, uint32_t ver,
+				  uint32_t major, uint32_t minor)
 {
 	struct stm32_header *stm32hdr = (struct stm32_header *)ptr;
 
 	stm32image_default_header(stm32hdr);
 
+	stm32hdr->header_version[VER_MAJOR] = major;
+	stm32hdr->header_version[VER_MINOR] = minor;
 	stm32hdr->load_address = __cpu_to_le32(loadaddr);
 	stm32hdr->image_entry_point = __cpu_to_le32(ep);
 	stm32hdr->image_length = __cpu_to_le32((uint32_t)sbuf->st_size -
 					     sizeof(struct stm32_header));
-	stm32hdr->image_checksum = stm32image_checksum(ptr, sbuf->st_size);
+	stm32hdr->image_checksum =
+		__cpu_to_le32(stm32image_checksum(ptr, sbuf->st_size));
 	stm32hdr->version_number = __cpu_to_le32(ver);
 }
 
 static int stm32image_create_header_file(char *srcname, char *destname,
 					 uint32_t loadaddr, uint32_t entry,
-					 uint32_t version)
+					 uint32_t version, uint32_t major,
+					 uint32_t minor)
 {
 	int src_fd, dest_fd;
 	struct stat sbuf;
 	unsigned char *ptr;
+	struct stm32_header stm32image_header;
 
 	dest_fd = open(destname, O_RDWR | O_CREAT | O_TRUNC | O_APPEND, 0666);
 	if (dest_fd == -1) {
@@ -177,11 +180,12 @@
 		   dest_fd, 0);
 
 	if (ptr == MAP_FAILED) {
-		fprintf(stderr, "Can't read %s\n", srcname);
+		fprintf(stderr, "Can't write %s\n", destname);
 		return -1;
 	}
 
-	stm32image_set_header(ptr, &sbuf, dest_fd, loadaddr, entry, version);
+	stm32image_set_header(ptr, &sbuf, dest_fd, loadaddr, entry, version,
+			      major, minor);
 
 	stm32image_print_header(ptr);
 
@@ -193,9 +197,11 @@
 int main(int argc, char *argv[])
 {
 	int opt, loadaddr = -1, entry = -1, err = 0, version = 0;
+	int major = HEADER_VERSION_V1;
+	int minor = 0;
 	char *dest = NULL, *src = NULL;
 
-	while ((opt = getopt(argc, argv, ":s:d:l:e:v:")) != -1) {
+	while ((opt = getopt(argc, argv, ":s:d:l:e:v:m:n:")) != -1) {
 		switch (opt) {
 		case 's':
 			src = optarg;
@@ -204,17 +210,23 @@
 			dest = optarg;
 			break;
 		case 'l':
-			loadaddr = strtol(optarg, NULL, 16);
+			loadaddr = strtol(optarg, NULL, 0);
 			break;
 		case 'e':
-			entry = strtol(optarg, NULL, 16);
+			entry = strtol(optarg, NULL, 0);
 			break;
 		case 'v':
-			version = strtol(optarg, NULL, 10);
+			version = strtol(optarg, NULL, 0);
+			break;
+		case 'm':
+			major = strtol(optarg, NULL, 0);
+			break;
+		case 'n':
+			minor = strtol(optarg, NULL, 0);
 			break;
 		default:
 			fprintf(stderr,
-				"Usage : %s [-s srcfile] [-d destfile] [-l loadaddr] [-e entry_point]\n",
+				"Usage : %s [-s srcfile] [-d destfile] [-l loadaddr] [-e entry_point] [-m major] [-n minor]\n",
 					argv[0]);
 			return -1;
 		}
@@ -241,7 +253,7 @@
 	}
 
 	err = stm32image_create_header_file(src, dest, loadaddr,
-					    entry, version);
+					    entry, version, major, minor);
 
 	return err;
 }